]> WPIA git - gigi.git/commitdiff
add: defense-in-depth mechanism to prevent unauthorized adding of groups
authorFelix Dörre <felix@dogcraft.de>
Mon, 22 Aug 2016 09:23:02 +0000 (11:23 +0200)
committerFelix Dörre <felix@dogcraft.de>
Tue, 23 Aug 2016 19:38:02 +0000 (21:38 +0200)
enforce that users must not add anyone to support-managed groups

Change-Id: I284842efba231ed7733837226626d80877e10cd7

23 files changed:
src/org/cacert/gigi/dbObjects/Group.java
src/org/cacert/gigi/dbObjects/SupportedUser.java
src/org/cacert/gigi/dbObjects/User.java
src/org/cacert/gigi/output/GroupSelector.java
tests/org/cacert/gigi/TestOrga.java
tests/org/cacert/gigi/TestUserGroupMembership.java
tests/org/cacert/gigi/api/IssueCert.java
tests/org/cacert/gigi/api/TestFindAgent.java
tests/org/cacert/gigi/pages/account/TestCertificateRequest.java
tests/org/cacert/gigi/pages/admin/TestSEAdminNotificationMail.java
tests/org/cacert/gigi/pages/admin/TestSEAdminPageDetails.java
tests/org/cacert/gigi/pages/admin/TestSEAdminPageUserDomainSearch.java
tests/org/cacert/gigi/pages/admin/TestSEAdminPageUserMailSearch.java
tests/org/cacert/gigi/pages/admin/TestSEAdminTicketSetting.java
tests/org/cacert/gigi/pages/orga/TestOrgDomain.java
tests/org/cacert/gigi/pages/orga/TestOrgManagement.java
tests/org/cacert/gigi/pages/wot/TestTTP.java
tests/org/cacert/gigi/pages/wot/TestTTPAdmin.java
tests/org/cacert/gigi/testUtils/BusinessTest.java
tests/org/cacert/gigi/testUtils/ManagedTest.java
tests/org/cacert/gigi/testUtils/OrgTest.java
tests/org/cacert/gigi/testUtils/RestrictedApiTest.java
util-testing/org/cacert/gigi/pages/Manager.java

index 13080efb208490a4ae7fc489cd57b5fb462a4001..287187a2d73482f5de592997a837da595c8f0827 100644 (file)
@@ -6,18 +6,18 @@ import org.cacert.gigi.output.template.Outputable;
 import org.cacert.gigi.output.template.TranslateCommand;
 
 public enum Group {
 import org.cacert.gigi.output.template.TranslateCommand;
 
 public enum Group {
-    SUPPORTER("supporter", "supporter", true, true), //
-    ARBITRATOR("arbitrator", "arbitrator", true, true), //
-    BLOCKEDASSURER("blockedassurer", "may not verify", true, false), //
-    BLOCKEDASSUREE("blockedassuree", "may not be verified", true, false), //
-    BLOCKEDLOGIN("blockedlogin", "may not login", true, false), //
-    BLOCKEDCERT("blockedcert", "may not issue certificates", true, false), //
-    TTP_ASSURER("ttp-assurer", "may verify via TTP", true, true), //
-    TTP_APPLICANT("ttp-applicant", "requests to be verified via ttp", true, false), //
-    CODESIGNING("codesigning", "may issue codesigning certificates", true, false), //
-    ORGASSURER("orgassurer", "may verify organisations", true, true), //
-    NUCLEUS_ASSURER("nucleus-assurer", "may enter nucleus verifications", true, true), //
-    LOCATE_AGENT("locate-agent", "wants access to the locate agent system", false, false);
+    SUPPORTER("supporter", "supporter", true, false, true), //
+    ARBITRATOR("arbitrator", "arbitrator", true, false, true), //
+    BLOCKEDASSURER("blockedassurer", "may not verify", true, false, false), //
+    BLOCKEDASSUREE("blockedassuree", "may not be verified", true, false, false), //
+    BLOCKEDLOGIN("blockedlogin", "may not login", true, false, false), //
+    BLOCKEDCERT("blockedcert", "may not issue certificates", true, false, false), //
+    TTP_ASSURER("ttp-assurer", "may verify via TTP", true, false, true), //
+    TTP_APPLICANT("ttp-applicant", "requests to be verified via ttp", false, true, false), //
+    CODESIGNING("codesigning", "may issue codesigning certificates", true, false, false), //
+    ORGASSURER("orgassurer", "may verify organisations", true, false, true), //
+    NUCLEUS_ASSURER("nucleus-assurer", "may enter nucleus verifications", true, false, true), //
+    LOCATE_AGENT("locate-agent", "wants access to the locate agent system", false, true, false);
 
     private final String dbName;
 
 
     private final String dbName;
 
@@ -25,6 +25,8 @@ public enum Group {
 
     private final boolean managedBySupport;
 
 
     private final boolean managedBySupport;
 
+    private final boolean managedByUser;
+
     private final boolean isSelfViewable;
 
     /**
     private final boolean isSelfViewable;
 
     /**
@@ -40,9 +42,16 @@ public enum Group {
      * @param isSelfViewable
      *            true iff user should be able to see others in the same group
      */
      * @param isSelfViewable
      *            true iff user should be able to see others in the same group
      */
-    private Group(String name, String display, boolean managedBySupport, boolean isSelfViewable) {
+    private Group(String name, String display, boolean managedBySupport, boolean managedByUser, boolean isSelfViewable) {
         dbName = name;
         tc = new TranslateCommand(display);
         dbName = name;
         tc = new TranslateCommand(display);
+        if (managedByUser && managedBySupport) {
+            throw new IllegalArgumentException("We do not allow groups to be user and support managable.");
+        }
+        if (managedByUser && isSelfViewable) {
+            throw new IllegalArgumentException("We do not allow groups to be self-viewable and managable by user.");
+        }
+        this.managedByUser = managedByUser;
         this.managedBySupport = managedBySupport;
         this.isSelfViewable = isSelfViewable;
     }
         this.managedBySupport = managedBySupport;
         this.isSelfViewable = isSelfViewable;
     }
@@ -55,6 +64,10 @@ public enum Group {
         return managedBySupport;
     }
 
         return managedBySupport;
     }
 
+    public boolean isManagedByUser() {
+        return managedByUser;
+    }
+
     public boolean isSelfViewable() {
         return isSelfViewable;
     }
     public boolean isSelfViewable() {
         return isSelfViewable;
     }
index a663215a8c658913c0d4991b552de9cc68941c6d..a4a3ba121e2c7dbab18d1646a46f9a2575138bbc 100644 (file)
@@ -85,7 +85,7 @@ public class SupportedUser {
         return target;
     }
 
         return target;
     }
 
-    public void grant(Group toMod) {
+    public void grant(Group toMod) throws GigiApiException {
         target.grantGroup(supporter, toMod);
     }
 
         target.grantGroup(supporter, toMod);
     }
 
index 3c9b972dba9930612a334d74b9d1236e77c40ce3..69b76ad2004ec9aa24c5401b7d8f1f0f42845c12 100644 (file)
@@ -45,7 +45,7 @@ public class User extends CertificateOwner {
 
     private Locale locale;
 
 
     private Locale locale;
 
-    private final Set<Group> groups = new HashSet<>();
+    private Set<Group> groups = new HashSet<>();
 
     public static final int MINIMUM_AGE = 16;
 
 
     public static final int MINIMUM_AGE = 16;
 
@@ -93,15 +93,21 @@ public class User extends CertificateOwner {
             locale = Language.getLocaleFromString(localeStr);
         }
 
             locale = Language.getLocaleFromString(localeStr);
         }
 
+        refreshGroups();
+    }
+
+    public synchronized void refreshGroups() {
+        HashSet<Group> hs = new HashSet<>();
         try (GigiPreparedStatement psg = new GigiPreparedStatement("SELECT `permission` FROM `user_groups` WHERE `user`=? AND `deleted` is NULL")) {
         try (GigiPreparedStatement psg = new GigiPreparedStatement("SELECT `permission` FROM `user_groups` WHERE `user`=? AND `deleted` is NULL")) {
-            psg.setInt(1, rs.getInt("id"));
+            psg.setInt(1, getId());
 
             try (GigiResultSet rs2 = psg.executeQuery()) {
                 while (rs2.next()) {
 
             try (GigiResultSet rs2 = psg.executeQuery()) {
                 while (rs2.next()) {
-                    groups.add(Group.getByString(rs2.getString(1)));
+                    hs.add(Group.getByString(rs2.getString(1)));
                 }
             }
         }
                 }
             }
         }
+        groups = hs;
     }
 
     public User(String email, String password, DayDate dob, Locale locale, Country residenceCountry, NamePart... preferred) throws GigiApiException {
     }
 
     public User(String email, String password, DayDate dob, Locale locale, Country residenceCountry, NamePart... preferred) throws GigiApiException {
@@ -438,7 +444,10 @@ public class User extends CertificateOwner {
         return Collections.unmodifiableSet(groups);
     }
 
         return Collections.unmodifiableSet(groups);
     }
 
-    public void grantGroup(User granter, Group toGrant) {
+    public void grantGroup(User granter, Group toGrant) throws GigiApiException {
+        if (toGrant.isManagedBySupport() && !granter.isInGroup(Group.SUPPORTER)) {
+            throw new GigiApiException("Group may only be managed by supporter");
+        }
         groups.add(toGrant);
         try (GigiPreparedStatement ps = new GigiPreparedStatement("INSERT INTO `user_groups` SET `user`=?, `permission`=?::`userGroup`, `grantedby`=?")) {
             ps.setInt(1, getId());
         groups.add(toGrant);
         try (GigiPreparedStatement ps = new GigiPreparedStatement("INSERT INTO `user_groups` SET `user`=?, `permission`=?::`userGroup`, `grantedby`=?")) {
             ps.setInt(1, getId());
index a12a5cd49b6bf9b1e4f84f8a958882798fdc7791..850e1d5ac72272c1e2b4e577b4b60007fb326723 100644 (file)
@@ -17,18 +17,18 @@ public class GroupSelector implements Outputable {
 
     private Group value = null;
 
 
     private Group value = null;
 
-    private final boolean supportFlag;
+    private final boolean bySupporter;
 
 
-    public GroupSelector(String name, boolean supportFlag) {
+    public GroupSelector(String name, boolean bySupporter) {
         this.name = HTMLEncoder.encodeHTML(name);
         this.name = HTMLEncoder.encodeHTML(name);
-        this.supportFlag = supportFlag;
+        this.bySupporter = bySupporter;
     }
 
     public void update(HttpServletRequest r) throws GigiApiException {
         String vS = r.getParameter(name);
         value = null;
         for (Group g : Group.values()) {
     }
 
     public void update(HttpServletRequest r) throws GigiApiException {
         String vS = r.getParameter(name);
         value = null;
         for (Group g : Group.values()) {
-            if (g.getDatabaseName().equals(vS) && g.isManagedBySupport() == supportFlag) {
+            if (g.getDatabaseName().equals(vS) && mayManage(g)) {
                 value = g;
             }
         }
                 value = g;
             }
         }
@@ -38,7 +38,7 @@ public class GroupSelector implements Outputable {
     public void output(PrintWriter out, Language l, Map<String, Object> vars) {
         out.println("<select name='" + name + "'>");
         for (Group g : Group.values()) {
     public void output(PrintWriter out, Language l, Map<String, Object> vars) {
         out.println("<select name='" + name + "'>");
         for (Group g : Group.values()) {
-            if (supportFlag == g.isManagedBySupport()) {
+            if (mayManage(g)) {
                 out.print("<option value='" + g.getDatabaseName());
                 if (g.equals(value)) {
                     out.print(" selected");
                 out.print("<option value='" + g.getDatabaseName());
                 if (g.equals(value)) {
                     out.print(" selected");
@@ -51,6 +51,10 @@ public class GroupSelector implements Outputable {
         out.println("</select>");
     }
 
         out.println("</select>");
     }
 
+    private boolean mayManage(Group g) {
+        return (bySupporter && g.isManagedBySupport()) || ( !bySupporter && g.isManagedByUser());
+    }
+
     public Group getGroup() {
         return value;
     }
     public Group getGroup() {
         return value;
     }
index 1a0a0aaf189b74537cc8a95971254df689e8ee80..ff3a56cc82fd3bc998101d1fd400fe78edde5b2e 100644 (file)
@@ -17,13 +17,13 @@ public class TestOrga extends BusinessTest {
     @Test
     public void testAddRm() throws GigiApiException, IOException {
         User u1 = User.getById(createAssuranceUser("fn", "ln", createUniqueName() + "@email.org", TEST_PASSWORD));
     @Test
     public void testAddRm() throws GigiApiException, IOException {
         User u1 = User.getById(createAssuranceUser("fn", "ln", createUniqueName() + "@email.org", TEST_PASSWORD));
-        u1.grantGroup(u1, Group.ORGASSURER);
+        u1.grantGroup(getSupporter(), Group.ORGASSURER);
         User u2 = User.getById(createAssuranceUser("fn", "ln", createUniqueName() + "@email.org", TEST_PASSWORD));
         User u2 = User.getById(createAssuranceUser("fn", "ln", createUniqueName() + "@email.org", TEST_PASSWORD));
-        u2.grantGroup(u1, Group.ORGASSURER);
+        u2.grantGroup(getSupporter(), Group.ORGASSURER);
         User u3 = User.getById(createAssuranceUser("fn", "ln", createUniqueName() + "@email.org", TEST_PASSWORD));
         User u3 = User.getById(createAssuranceUser("fn", "ln", createUniqueName() + "@email.org", TEST_PASSWORD));
-        u3.grantGroup(u1, Group.ORGASSURER);
+        u3.grantGroup(getSupporter(), Group.ORGASSURER);
         User u4 = User.getById(createAssuranceUser("fn", "ln", createUniqueName() + "@email.org", TEST_PASSWORD));
         User u4 = User.getById(createAssuranceUser("fn", "ln", createUniqueName() + "@email.org", TEST_PASSWORD));
-        u4.grantGroup(u1, Group.ORGASSURER);
+        u4.grantGroup(getSupporter(), Group.ORGASSURER);
         Organisation o1 = new Organisation("name", Country.getCountryByCode("DE", CountryCodeType.CODE_2_CHARS), "prov", "city", "email", "optional name", "postal address", u1);
         assertEquals(0, o1.getAllAdmins().size());
         o1.addAdmin(u2, u1, false);
         Organisation o1 = new Organisation("name", Country.getCountryByCode("DE", CountryCodeType.CODE_2_CHARS), "prov", "city", "email", "optional name", "postal address", u1);
         assertEquals(0, o1.getAllAdmins().size());
         o1.addAdmin(u2, u1, false);
index 32bb1a991de9120fadf00e2be0782ca9ff28b7f4..ea92218b2ecdc4f25273bfa9a39c3567270cdcde 100644 (file)
@@ -3,6 +3,7 @@ package org.cacert.gigi;
 import static org.hamcrest.CoreMatchers.*;
 import static org.junit.Assert.*;
 
 import static org.hamcrest.CoreMatchers.*;
 import static org.junit.Assert.*;
 
+import java.io.IOException;
 import java.sql.SQLException;
 import java.util.Arrays;
 import java.util.Collections;
 import java.sql.SQLException;
 import java.util.Arrays;
 import java.util.Collections;
@@ -23,10 +24,10 @@ public class TestUserGroupMembership extends BusinessTest {
     private final Group supporter = Group.getByString("supporter");
 
     @Test
     private final Group supporter = Group.getByString("supporter");
 
     @Test
-    public void testAddObject() throws GigiApiException, SQLException {
+    public void testAddObject() throws GigiApiException, SQLException, IOException {
         User u = User.getById(createVerifiedUser("fname", "lname", createUniqueName() + "@example.org", TEST_PASSWORD));
 
         User u = User.getById(createVerifiedUser("fname", "lname", createUniqueName() + "@example.org", TEST_PASSWORD));
 
-        User granter = User.getById(createVerifiedUser("grFname", "lname", createUniqueName() + "@example.org", TEST_PASSWORD));
+        User granter = getSupporter();
         assertBehavesEmpty(u);
 
         u.grantGroup(granter, ttpGroup);
         assertBehavesEmpty(u);
 
         u.grantGroup(granter, ttpGroup);
@@ -55,10 +56,10 @@ public class TestUserGroupMembership extends BusinessTest {
     }
 
     @Test
     }
 
     @Test
-    public void testRemoveObject() throws GigiApiException, SQLException {
+    public void testRemoveObject() throws GigiApiException, SQLException, IOException {
         User u = User.getById(createVerifiedUser("fname", "lname", createUniqueName() + "@example.org", TEST_PASSWORD));
 
         User u = User.getById(createVerifiedUser("fname", "lname", createUniqueName() + "@example.org", TEST_PASSWORD));
 
-        User granter = User.getById(createVerifiedUser("grFname", "lname", createUniqueName() + "@example.org", TEST_PASSWORD));
+        User granter = getSupporter();
 
         assertBehavesEmpty(u);
         u.grantGroup(granter, ttpGroup);
 
         assertBehavesEmpty(u);
         u.grantGroup(granter, ttpGroup);
@@ -99,20 +100,20 @@ public class TestUserGroupMembership extends BusinessTest {
     }
 
     @Test
     }
 
     @Test
-    public void testListGroup() throws GigiApiException {
-        Group g = Group.getByString("supporter");
+    public void testListGroup() throws GigiApiException, IOException {
+        Group g = Group.SUPPORTER;
         int start = g.getMembers(0, 10).length;
         User ux = User.getById(createVerifiedUser("fn", "ln", createUniqueName() + "@example.org", TEST_PASSWORD));
         User ux2 = User.getById(createVerifiedUser("fn", "ln", createUniqueName() + "@example.org", TEST_PASSWORD));
         assertEquals(0, g.getMembers(0, 10).length + start);
         int start = g.getMembers(0, 10).length;
         User ux = User.getById(createVerifiedUser("fn", "ln", createUniqueName() + "@example.org", TEST_PASSWORD));
         User ux2 = User.getById(createVerifiedUser("fn", "ln", createUniqueName() + "@example.org", TEST_PASSWORD));
         assertEquals(0, g.getMembers(0, 10).length + start);
-        ux.grantGroup(ux, g);
-        assertEquals(1, g.getMembers(0, 10).length + start);
-        ux2.grantGroup(ux, g);
+        ux.grantGroup(getSupporter(), g); // creates a supporter
         assertEquals(2, g.getMembers(0, 10).length + start);
         assertEquals(2, g.getMembers(0, 10).length + start);
+        ux2.grantGroup(ux, g);
+        assertEquals(3, g.getMembers(0, 10).length + start);
         ux2.revokeGroup(ux, g);
         ux2.revokeGroup(ux, g);
-        assertEquals(1, g.getMembers(0, 10).length + start);
+        assertEquals(2, g.getMembers(0, 10).length + start);
         ux.revokeGroup(ux, g);
         ux.revokeGroup(ux, g);
-        assertEquals(0, g.getMembers(0, 10).length + start);
+        assertEquals(1, g.getMembers(0, 10).length + start);
 
     }
 
 
     }
 
index 03ab3f3e53bc90767ad8d7e2f44440c43144a7a6..fc1e9d1ce0991dc52cce96cf7c1257742d9be4fe 100644 (file)
@@ -18,9 +18,9 @@ import java.security.cert.X509Certificate;
 import org.cacert.gigi.dbObjects.Certificate;
 import org.cacert.gigi.dbObjects.Certificate.CSRType;
 import org.cacert.gigi.dbObjects.Certificate.CertificateStatus;
 import org.cacert.gigi.dbObjects.Certificate;
 import org.cacert.gigi.dbObjects.Certificate.CSRType;
 import org.cacert.gigi.dbObjects.Certificate.CertificateStatus;
-import org.cacert.gigi.dbObjects.Country.CountryCodeType;
 import org.cacert.gigi.dbObjects.CertificateProfile;
 import org.cacert.gigi.dbObjects.Country;
 import org.cacert.gigi.dbObjects.CertificateProfile;
 import org.cacert.gigi.dbObjects.Country;
+import org.cacert.gigi.dbObjects.Country.CountryCodeType;
 import org.cacert.gigi.dbObjects.Digest;
 import org.cacert.gigi.dbObjects.Domain;
 import org.cacert.gigi.dbObjects.Group;
 import org.cacert.gigi.dbObjects.Digest;
 import org.cacert.gigi.dbObjects.Domain;
 import org.cacert.gigi.dbObjects.Group;
@@ -87,7 +87,7 @@ public class IssueCert extends ClientTest {
     @Test
     public void testIssueOrgCert() throws Exception {
         makeAssurer(id);
     @Test
     public void testIssueOrgCert() throws Exception {
         makeAssurer(id);
-        u.grantGroup(u, Group.ORGASSURER);
+        u.grantGroup(getSupporter(), Group.ORGASSURER);
 
         Organisation o1 = new Organisation("name", Country.getCountryByCode("DE", CountryCodeType.CODE_2_CHARS), "pr", "st", "test@mail", "", "", u);
         o1.addAdmin(u, u, false);
 
         Organisation o1 = new Organisation("name", Country.getCountryByCode("DE", CountryCodeType.CODE_2_CHARS), "pr", "st", "test@mail", "", "", u);
         o1.addAdmin(u, u, false);
index 3b8b9927e912107851c71d21765f17e79dad72d0..d7213961359eb67663f1f6090f5e1c07ba3af16b 100644 (file)
@@ -33,7 +33,7 @@ public class TestFindAgent extends RestrictedApiTest {
         assertEquals(501, v.getResponseCode());
         assertThat(IOUtils.readURL(new InputStreamReader(v.getErrorStream(), "UTF-8")), containsString(FindAgentAccess.PATH));
 
         assertEquals(501, v.getResponseCode());
         assertThat(IOUtils.readURL(new InputStreamReader(v.getErrorStream(), "UTF-8")), containsString(FindAgentAccess.PATH));
 
-        grant(u.getEmail(), Group.LOCATE_AGENT);
+        grant(u, Group.LOCATE_AGENT);
         v = doApi(FindAgent.PATH_RESOLVE, "serial=" + target2.getSerial().toLowerCase());
         assertEquals(u.getId(), Integer.parseInt(IOUtils.readURL(v)));
     }
         v = doApi(FindAgent.PATH_RESOLVE, "serial=" + target2.getSerial().toLowerCase());
         assertEquals(u.getId(), Integer.parseInt(IOUtils.readURL(v)));
     }
@@ -58,13 +58,13 @@ public class TestFindAgent extends RestrictedApiTest {
         assertThat(v.getResponseMessage(), containsString("needs to enable access"));
 
         // even if sender enables service
         assertThat(v.getResponseMessage(), containsString("needs to enable access"));
 
         // even if sender enables service
-        grant((userUFirst ? u : us2).getEmail(), Group.LOCATE_AGENT);
+        grant((userUFirst ? u : us2), Group.LOCATE_AGENT);
         v = doApi(FindAgent.PATH_MAIL, "from=" + id + "&to=" + u2 + "&subject=the-subject&body=body");
         assertEquals(v.getResponseMessage(), 501, v.getResponseCode());
         assertThat(v.getResponseMessage(), containsString("needs to enable access"));
 
         // receiver needs to enable access as well
         v = doApi(FindAgent.PATH_MAIL, "from=" + id + "&to=" + u2 + "&subject=the-subject&body=body");
         assertEquals(v.getResponseMessage(), 501, v.getResponseCode());
         assertThat(v.getResponseMessage(), containsString("needs to enable access"));
 
         // receiver needs to enable access as well
-        grant((userUFirst ? us2 : u).getEmail(), Group.LOCATE_AGENT);
+        grant((userUFirst ? us2 : u), Group.LOCATE_AGENT);
         v = doApi(FindAgent.PATH_MAIL, "from=" + id + "&to=" + u2 + "&subject=the-subject&body=body");
         assertEquals(v.getResponseMessage(), 200, v.getResponseCode());
         TestMail mail = getMailReceiver().receive();
         v = doApi(FindAgent.PATH_MAIL, "from=" + id + "&to=" + u2 + "&subject=the-subject&body=body");
         assertEquals(v.getResponseMessage(), 200, v.getResponseCode());
         TestMail mail = getMailReceiver().receive();
@@ -79,8 +79,8 @@ public class TestFindAgent extends RestrictedApiTest {
 
         String res = IOUtils.readURL(doApi(FindAgent.PATH_INFO, "id=" + id + "&id=" + u2)).replace("\r", "");
         assertEquals(res, "");
 
         String res = IOUtils.readURL(doApi(FindAgent.PATH_INFO, "id=" + id + "&id=" + u2)).replace("\r", "");
         assertEquals(res, "");
-        grant(email, Group.LOCATE_AGENT);
-        grant(User.getById(u2).getEmail(), Group.LOCATE_AGENT);
+        grant(u, Group.LOCATE_AGENT);
+        grant(User.getById(u2), Group.LOCATE_AGENT);
         res = IOUtils.readURL(doApi(FindAgent.PATH_INFO, "id=" + id + "&id=" + u2)).replace("\r", "");
         assertEquals(id + ",true," + u.getPreferredName().toAbbreviatedString() + "\n" + u2 + ",false," + User.getById(u2).getPreferredName().toAbbreviatedString() + "\n", res);
     }
         res = IOUtils.readURL(doApi(FindAgent.PATH_INFO, "id=" + id + "&id=" + u2)).replace("\r", "");
         assertEquals(id + ",true," + u.getPreferredName().toAbbreviatedString() + "\n" + u2 + ",false," + User.getById(u2).getPreferredName().toAbbreviatedString() + "\n", res);
     }
index 98f105f0995427570cbb637a9ee3b7ec006772d5..0beaef87998a8b24e1e4a7387bd9534329390094 100644 (file)
@@ -20,11 +20,9 @@ public class TestCertificateRequest extends ClientTest {
 
     AuthorizationContext ac;
 
 
     AuthorizationContext ac;
 
-    public TestCertificateRequest() throws GeneralSecurityException, IOException {
+    public TestCertificateRequest() throws GeneralSecurityException, IOException, GigiApiException {
         ac = new AuthorizationContext(u, u);
         makeAssurer(u.getId());
         ac = new AuthorizationContext(u, u);
         makeAssurer(u.getId());
-        grant(email, Group.CODESIGNING);
-
     }
 
     @Test
     }
 
     @Test
@@ -62,7 +60,7 @@ public class TestCertificateRequest extends ClientTest {
     @Test
     public void testCodesignModifiedName() throws Exception {
         try {
     @Test
     public void testCodesignModifiedName() throws Exception {
         try {
-            u.grantGroup(u, Group.CODESIGNING);
+            u.grantGroup(getSupporter(), Group.CODESIGNING);
             CertificateRequest cr = new CertificateRequest(ac, generatePEMCSR(kp, "CN=a ab"));
             cr.update("name", "SHA512", "code-a", null, null, "email:" + email);
             cr.draft();
             CertificateRequest cr = new CertificateRequest(ac, generatePEMCSR(kp, "CN=a ab"));
             cr.update("name", "SHA512", "code-a", null, null, "email:" + email);
             cr.draft();
index 689fb5137e813ea046dce5d58697d3b2f04bf4a8..c51e5cc46a6ae1aa31aeab212d22b6dd4c7ef9da 100644 (file)
@@ -6,6 +6,7 @@ import static org.junit.Assert.*;
 import java.io.IOException;
 import java.net.MalformedURLException;
 
 import java.io.IOException;
 import java.net.MalformedURLException;
 
+import org.cacert.gigi.GigiApiException;
 import org.cacert.gigi.dbObjects.Group;
 import org.cacert.gigi.pages.admin.support.SupportEnterTicketPage;
 import org.cacert.gigi.pages.admin.support.SupportUserDetailsPage;
 import org.cacert.gigi.dbObjects.Group;
 import org.cacert.gigi.pages.admin.support.SupportEnterTicketPage;
 import org.cacert.gigi.pages.admin.support.SupportUserDetailsPage;
@@ -18,8 +19,9 @@ public class TestSEAdminNotificationMail extends ClientTest {
 
     private int targetID;
 
 
     private int targetID;
 
-    public TestSEAdminNotificationMail() throws IOException {
-        grant(email, Group.SUPPORTER);
+    public TestSEAdminNotificationMail() throws IOException, GigiApiException {
+        grant(u, Group.SUPPORTER);
+        cookie = login(email, TEST_PASSWORD);
         assertEquals(302, post(cookie, SupportEnterTicketPage.PATH, "ticketno=a20140808.8&setTicket=action", 0).getResponseCode());
 
         String email = createUniqueName() + "@example.com";
         assertEquals(302, post(cookie, SupportEnterTicketPage.PATH, "ticketno=a20140808.8&setTicket=action", 0).getResponseCode());
 
         String email = createUniqueName() + "@example.com";
index 08541decf47f3eab2102b125983263b2d0eb4fff..e9b31abba12e6331f8e4f648b5ac0df8ff9ac612 100644 (file)
@@ -27,8 +27,9 @@ import org.junit.Test;
 
 public class TestSEAdminPageDetails extends ClientTest {
 
 
 public class TestSEAdminPageDetails extends ClientTest {
 
-    public TestSEAdminPageDetails() throws IOException {
-        grant(email, Group.SUPPORTER);
+    public TestSEAdminPageDetails() throws IOException, GigiApiException {
+        grant(u, Group.SUPPORTER);
+        cookie = login(email, TEST_PASSWORD);
         assertEquals(302, post(cookie, SupportEnterTicketPage.PATH, "ticketno=a20140808.8&setTicket=action", 0).getResponseCode());
     }
 
         assertEquals(302, post(cookie, SupportEnterTicketPage.PATH, "ticketno=a20140808.8&setTicket=action", 0).getResponseCode());
     }
 
index d1916c10d6bfa4cf139f1e46c633970bff2dab87..57c5c15cdcf84c06df864ff2da9e22c17f651580 100644 (file)
@@ -32,7 +32,8 @@ public class TestSEAdminPageUserDomainSearch extends ClientTest {
     private int tid;
 
     public TestSEAdminPageUserDomainSearch() throws IOException, GigiApiException {
     private int tid;
 
     public TestSEAdminPageUserDomainSearch() throws IOException, GigiApiException {
-        grant(email, Group.SUPPORTER);
+        grant(u, Group.SUPPORTER);
+        cookie = login(email, TEST_PASSWORD);
         assertEquals(302, post(cookie, SupportEnterTicketPage.PATH, "ticketno=a20140808.8&setTicket=action", 0).getResponseCode());
 
         String mail = createUniqueName() + "@example.com";
         assertEquals(302, post(cookie, SupportEnterTicketPage.PATH, "ticketno=a20140808.8&setTicket=action", 0).getResponseCode());
 
         String mail = createUniqueName() + "@example.com";
index 71dfeaee5071f1f52ad3ac95f172f699eab5a849..29918b5a0a55c5618e940a450c21c646d586a754 100644 (file)
@@ -22,8 +22,9 @@ import org.junit.Test;
 
 public class TestSEAdminPageUserMailSearch extends ClientTest {
 
 
 public class TestSEAdminPageUserMailSearch extends ClientTest {
 
-    public TestSEAdminPageUserMailSearch() throws IOException {
-        grant(email, Group.SUPPORTER);
+    public TestSEAdminPageUserMailSearch() throws IOException, GigiApiException {
+        grant(u, Group.SUPPORTER);
+        cookie = login(email, TEST_PASSWORD);
         assertEquals(302, post(cookie, SupportEnterTicketPage.PATH, "ticketno=a20140808.8&setTicket=action", 0).getResponseCode());
     }
 
         assertEquals(302, post(cookie, SupportEnterTicketPage.PATH, "ticketno=a20140808.8&setTicket=action", 0).getResponseCode());
     }
 
index 62d89de297e2ab527fcd0c83721b68ba90b80ee9..01e17b3c8568e2ba50415564c4d36b04a1e092c1 100644 (file)
@@ -6,6 +6,7 @@ import java.io.IOException;
 import java.io.UnsupportedEncodingException;
 import java.net.MalformedURLException;
 
 import java.io.UnsupportedEncodingException;
 import java.net.MalformedURLException;
 
+import org.cacert.gigi.GigiApiException;
 import org.cacert.gigi.dbObjects.Group;
 import org.cacert.gigi.pages.admin.support.FindUserByDomainPage;
 import org.cacert.gigi.pages.admin.support.FindUserByEmailPage;
 import org.cacert.gigi.dbObjects.Group;
 import org.cacert.gigi.pages.admin.support.FindUserByDomainPage;
 import org.cacert.gigi.pages.admin.support.FindUserByEmailPage;
@@ -15,8 +16,9 @@ import org.junit.Test;
 
 public class TestSEAdminTicketSetting extends ClientTest {
 
 
 public class TestSEAdminTicketSetting extends ClientTest {
 
-    public TestSEAdminTicketSetting() throws IOException {
-        grant(email, Group.SUPPORTER);
+    public TestSEAdminTicketSetting() throws IOException, GigiApiException {
+        grant(u, Group.SUPPORTER);
+        cookie = login(email, TEST_PASSWORD);
     }
 
     @Test
     }
 
     @Test
index d1b930db2edc0627b502d213492d2b393a0cdb24..b24bb83e9caa1ea6072b323d0c7b438a76cef89d 100644 (file)
@@ -13,7 +13,7 @@ import org.junit.Test;
 
 public class TestOrgDomain extends OrgTest {
 
 
 public class TestOrgDomain extends OrgTest {
 
-    public TestOrgDomain() throws IOException {
+    public TestOrgDomain() throws IOException, GigiApiException {
 
     }
 
 
     }
 
index 760ca198c5ba7c199eb410df307abb4933b3bb42..65951dc8fe7abab569a9dbdc2e4ee73f526f3740 100644 (file)
@@ -26,7 +26,7 @@ import org.junit.Test;
 
 public class TestOrgManagement extends OrgTest {
 
 
 public class TestOrgManagement extends OrgTest {
 
-    public TestOrgManagement() throws IOException {
+    public TestOrgManagement() throws IOException, GigiApiException {
 
     }
 
 
     }
 
index 34b0ca6dfc78c50d7ffad6d3c6a6a461ef72254d..0d3763868fd25b15383ef4fa833394b4e2c2b8d5 100644 (file)
@@ -21,7 +21,7 @@ public class TestTTP extends ClientTest {
     public void testTTPApply() throws IOException {
         String ttp = IOUtils.readURL(get(RequestTTPPage.PATH));
         assertThat(ttp, containsString("<form"));
     public void testTTPApply() throws IOException {
         String ttp = IOUtils.readURL(get(RequestTTPPage.PATH));
         assertThat(ttp, containsString("<form"));
-        executeBasicWebInteraction(cookie, RequestTTPPage.PATH, "country=0");
+        assertNull(executeBasicWebInteraction(cookie, RequestTTPPage.PATH, "country=0"));
 
         ttp = IOUtils.readURL(get(RequestTTPPage.PATH));
         assertThat(ttp, not(containsString("<form")));
 
         ttp = IOUtils.readURL(get(RequestTTPPage.PATH));
         assertThat(ttp, not(containsString("<form")));
index 31b0e51bd9d5bb3d77483fee2586cecc110a4ff7..d04b0b66cd921f22cef3649fc9cee94045400c5b 100644 (file)
@@ -5,6 +5,7 @@ import static org.junit.Assert.*;
 import java.io.IOException;
 import java.net.MalformedURLException;
 
 import java.io.IOException;
 import java.net.MalformedURLException;
 
+import org.cacert.gigi.GigiApiException;
 import org.cacert.gigi.dbObjects.Group;
 import org.cacert.gigi.dbObjects.User;
 import org.cacert.gigi.pages.admin.TTPAdminPage;
 import org.cacert.gigi.dbObjects.Group;
 import org.cacert.gigi.dbObjects.User;
 import org.cacert.gigi.pages.admin.TTPAdminPage;
@@ -20,20 +21,20 @@ public class TestTTPAdmin extends ClientTest {
     }
 
     @Test
     }
 
     @Test
-    public void testHasRight() throws IOException {
+    public void testHasRight() throws IOException, GigiApiException {
         testTTPAdmin(true);
     }
 
     @Test
         testTTPAdmin(true);
     }
 
     @Test
-    public void testHasNoRight() throws IOException {
+    public void testHasNoRight() throws IOException, GigiApiException {
         testTTPAdmin(false);
     }
 
         testTTPAdmin(false);
     }
 
-    public void testTTPAdmin(boolean hasRight) throws IOException {
+    public void testTTPAdmin(boolean hasRight) throws IOException, GigiApiException {
         if (hasRight) {
         if (hasRight) {
-            grant(email, Group.getByString("ttp-assurer"));
+            grant(u, Group.getByString("ttp-assurer"));
         }
         }
-        grant(u.getEmail(), TTPAdminPage.TTP_APPLICANT);
+        grant(u, TTPAdminPage.TTP_APPLICANT);
         cookie = login(u.getEmail(), TEST_PASSWORD);
 
         assertEquals( !hasRight ? 403 : 200, fetchStatusCode(TTPAdminPage.PATH));
         cookie = login(u.getEmail(), TEST_PASSWORD);
 
         assertEquals( !hasRight ? 403 : 200, fetchStatusCode(TTPAdminPage.PATH));
index cc095e30091a0f827c842917cb3ef564ec0e665a..db888c03e0088d75bfddd6b78a4549429d7f5ee3 100644 (file)
@@ -15,8 +15,10 @@ import java.util.regex.Matcher;
 import java.util.regex.Pattern;
 
 import org.cacert.gigi.GigiApiException;
 import java.util.regex.Pattern;
 
 import org.cacert.gigi.GigiApiException;
+import org.cacert.gigi.database.GigiPreparedStatement;
 import org.cacert.gigi.dbObjects.Domain;
 import org.cacert.gigi.dbObjects.EmailAddress;
 import org.cacert.gigi.dbObjects.Domain;
 import org.cacert.gigi.dbObjects.EmailAddress;
+import org.cacert.gigi.dbObjects.Group;
 import org.cacert.gigi.dbObjects.NamePart;
 import org.cacert.gigi.dbObjects.NamePart.NamePartType;
 import org.cacert.gigi.dbObjects.User;
 import org.cacert.gigi.dbObjects.NamePart;
 import org.cacert.gigi.dbObjects.NamePart.NamePartType;
 import org.cacert.gigi.dbObjects.User;
@@ -155,4 +157,21 @@ public abstract class BusinessTest extends ConfiguredTest {
     public MailReceiver getMailReceiver() {
         return InVMEmail.getInstance();
     }
     public MailReceiver getMailReceiver() {
         return InVMEmail.getInstance();
     }
+
+    private User supporter;
+
+    public User getSupporter() throws GigiApiException, IOException {
+        if (supporter != null) {
+            return supporter;
+        }
+        supporter = createVerifiedUser();
+        try (GigiPreparedStatement ps = new GigiPreparedStatement("INSERT INTO `user_groups` SET `user`=?, `permission`=?::`userGroup`, `grantedby`=?")) {
+            ps.setInt(1, supporter.getId());
+            ps.setString(2, Group.SUPPORTER.getDatabaseName());
+            ps.setInt(3, supporter.getId());
+            ps.execute();
+        }
+        supporter.refreshGroups();
+        return supporter;
+    }
 }
 }
index a0228f161180b27d231887ebaea05bec063e2966..22da1eab4a5ef9851d3187331cbabaff09608cbf 100644 (file)
@@ -42,7 +42,6 @@ import org.cacert.gigi.dbObjects.Group;
 import org.cacert.gigi.dbObjects.Job;
 import org.cacert.gigi.dbObjects.ObjectCache;
 import org.cacert.gigi.dbObjects.User;
 import org.cacert.gigi.dbObjects.Job;
 import org.cacert.gigi.dbObjects.ObjectCache;
 import org.cacert.gigi.dbObjects.User;
-import org.cacert.gigi.pages.Manager;
 import org.cacert.gigi.pages.account.MyDetails;
 import org.cacert.gigi.pages.main.RegisterPage;
 import org.cacert.gigi.testUtils.TestEmailReceiver.TestMail;
 import org.cacert.gigi.pages.account.MyDetails;
 import org.cacert.gigi.pages.main.RegisterPage;
 import org.cacert.gigi.testUtils.TestEmailReceiver.TestMail;
@@ -289,11 +288,9 @@ public class ManagedTest extends ConfiguredTest {
         }
     }
 
         }
     }
 
-    public static void grant(String email, Group g) throws IOException {
-        HttpURLConnection huc = (HttpURLConnection) new URL("https://" + getServerName() + Manager.PATH).openConnection();
-        huc.setDoOutput(true);
-        huc.getOutputStream().write(("addpriv=y&priv=" + URLEncoder.encode(g.getDatabaseName(), "UTF-8") + "&email=" + URLEncoder.encode(email, "UTF-8")).getBytes("UTF-8"));
-        assertEquals(200, huc.getResponseCode());
+    public static void grant(User u, Group g) throws IOException, GigiApiException {
+        u.grantGroup(getSupporter(), g);
+        clearCaches();
     }
 
     /**
     }
 
     /**
@@ -486,4 +483,21 @@ public class ManagedTest extends ConfiguredTest {
         return openConnection;
     }
 
         return openConnection;
     }
 
+    private static User supporter;
+
+    public static User getSupporter() throws GigiApiException, IOException {
+        if (supporter != null) {
+            return supporter;
+        }
+        int i = createVerifiedUser("fn", "ln", createUniqueName() + "@email.com", TEST_PASSWORD);
+        try (GigiPreparedStatement ps = new GigiPreparedStatement("INSERT INTO `user_groups` SET `user`=?, `permission`=?::`userGroup`, `grantedby`=?")) {
+            ps.setInt(1, i);
+            ps.setString(2, Group.SUPPORTER.getDatabaseName());
+            ps.setInt(3, i);
+            ps.execute();
+        }
+        clearCaches();
+        supporter = User.getById(i);
+        return supporter;
+    }
 }
 }
index 2a9f5da7fce27068953619bf0d903da998b44c84..5a42a4a6d8d44932d84a136da2aa8d339eb32df3 100644 (file)
@@ -10,9 +10,9 @@ import org.cacert.gigi.dbObjects.Organisation;
 
 public class OrgTest extends ClientTest {
 
 
 public class OrgTest extends ClientTest {
 
-    public OrgTest() throws IOException {
+    public OrgTest() throws IOException, GigiApiException {
         makeAssurer(u.getId());
         makeAssurer(u.getId());
-        u.grantGroup(u, Group.ORGASSURER);
+        u.grantGroup(getSupporter(), Group.ORGASSURER);
         clearCaches();
         cookie = login(email, TEST_PASSWORD);
     }
         clearCaches();
         cookie = login(email, TEST_PASSWORD);
     }
index 2301b0ae45471a5a5a8c02026d4337d6a55494c6..e4ec22b98ddf381b0f31847b753b105114b24901 100644 (file)
@@ -39,7 +39,7 @@ public class RestrictedApiTest extends ClientTest {
         initEnvironment();
         try {
             User u = User.getById(createAssuranceUser("f", "l", createUniqueName() + "@email.com", TEST_PASSWORD));
         initEnvironment();
         try {
             User u = User.getById(createAssuranceUser("f", "l", createUniqueName() + "@email.com", TEST_PASSWORD));
-            grant(u.getEmail(), Group.ORGASSURER);
+            grant(u, Group.ORGASSURER);
             clearCaches();
             u = User.getById(u.getId());
             Organisation o = new Organisation(Organisation.SELF_ORG_NAME, Country.getCountryByCode("DE", CountryCodeType.CODE_2_CHARS), "NA", "NA", "contact@cacert.org", "", "", u);
             clearCaches();
             u = User.getById(u.getId());
             Organisation o = new Organisation(Organisation.SELF_ORG_NAME, Country.getCountryByCode("DE", CountryCodeType.CODE_2_CHARS), "NA", "NA", "contact@cacert.org", "", "", u);
index a2435c95612d2a9b4c830ff5efa2738b48428257..2fd78ba7195bf3b84618e5b8df46e00d8015ed15 100644 (file)
@@ -96,6 +96,28 @@ public class Manager extends Page {
         }
     }
 
         }
     }
 
+    public User getSupporter() {
+        if (supporter != null) {
+            return supporter;
+        }
+        try {
+            User u = createAssurer( -1);
+            if ( !u.isInGroup(Group.SUPPORTER)) {
+                try (GigiPreparedStatement ps = new GigiPreparedStatement("INSERT INTO `user_groups` SET `user`=?, `permission`=?::`userGroup`, `grantedby`=?")) {
+                    ps.setInt(1, u.getId());
+                    ps.setString(2, Group.SUPPORTER.getDatabaseName());
+                    ps.setInt(3, u.getId());
+                    ps.execute();
+                }
+                u.refreshGroups();
+            }
+            supporter = u;
+        } catch (ReflectiveOperationException | GigiApiException e) {
+            e.printStackTrace();
+        }
+        return supporter;
+    }
+
     public User getAssurer(int i) {
         if (assurers[i] != null) {
             return assurers[i];
     public User getAssurer(int i) {
         if (assurers[i] != null) {
             return assurers[i];
@@ -261,6 +283,8 @@ public class Manager extends Page {
 
     User[] assurers = new User[25];
 
 
     User[] assurers = new User[25];
 
+    User supporter;
+
     @Override
     public void doPost(HttpServletRequest req, HttpServletResponse resp) throws IOException {
         if (req.getParameter("create") != null) {
     @Override
     public void doPost(HttpServletRequest req, HttpServletResponse resp) throws IOException {
         if (req.getParameter("create") != null) {
@@ -273,7 +297,11 @@ public class Manager extends Page {
                 return;
             }
             if (req.getParameter("addpriv") != null) {
                 return;
             }
             if (req.getParameter("addpriv") != null) {
-                u.grantGroup(u, Group.getByString(req.getParameter("priv")));
+                try {
+                    u.grantGroup(getSupporter(), Group.getByString(req.getParameter("priv")));
+                } catch (GigiApiException e) {
+                    throw new Error(e);
+                }
                 resp.getWriter().println("Privilege granted");
             } else {
                 u.revokeGroup(u, Group.getByString(req.getParameter("priv")));
                 resp.getWriter().println("Privilege granted");
             } else {
                 u.revokeGroup(u, Group.getByString(req.getParameter("priv")));