Scope validation by email
Change-Id: I252eed1861d02861c0bd0830fbc15eeca759c72a
diff --git a/src/main/java/com/googlesource/gerrit/plugins/uploadvalidator/ValidatorConfig.java b/src/main/java/com/googlesource/gerrit/plugins/uploadvalidator/ValidatorConfig.java
index e3d9260..cf80a6c 100644
--- a/src/main/java/com/googlesource/gerrit/plugins/uploadvalidator/ValidatorConfig.java
+++ b/src/main/java/com/googlesource/gerrit/plugins/uploadvalidator/ValidatorConfig.java
@@ -27,6 +27,7 @@
import org.slf4j.LoggerFactory;
import java.util.Arrays;
+import java.util.regex.Pattern;
import java.util.stream.Stream;
public class ValidatorConfig {
@@ -49,6 +50,7 @@
return conf != null
&& isValidConfig(conf, projectName)
&& (activeForRef(conf, refName))
+ && (activeForEmail(conf, user.getAccount().getPreferredEmail()))
&& (!hasCriteria(conf, "skipGroup")
|| !canSkipValidation(conf, validatorOp)
|| !canSkipRef(conf, refName)
@@ -79,22 +81,27 @@
}
private boolean activeForRef(PluginConfig config, String ref) {
- return matchCriteria(config, "ref", ref, true);
+ return matchCriteria(config, "ref", ref, true, true);
+ }
+
+ private boolean activeForEmail(PluginConfig config, String email) {
+ return matchCriteria(config, "email", email, true, false);
}
private boolean canSkipValidation(PluginConfig config, String validatorOp) {
- return matchCriteria(config, "skipValidation", validatorOp, false);
+ return matchCriteria(config, "skipValidation", validatorOp, false, false);
}
private boolean canSkipRef(PluginConfig config, String ref) {
- return matchCriteria(config, "skipRef", ref, true);
+ return matchCriteria(config, "skipRef", ref, true, true);
}
private boolean matchCriteria(PluginConfig config, String criteria,
- String value, boolean allowRegex) {
+ String value, boolean allowRegex, boolean refMatcher) {
boolean match = true;
for (String s : config.getStringList(criteria)) {
- if ((allowRegex && match(value, s)) || (!allowRegex && s.equals(value))) {
+ if ((allowRegex && match(value, s, refMatcher)) ||
+ (!allowRegex && s.equals(value))) {
return true;
}
match = false;
@@ -102,8 +109,13 @@
return match;
}
- private static boolean match(String value, String pattern) {
- return RefPatternMatcher.getMatcher(pattern).match(value, null);
+ private static boolean match(String value, String pattern,
+ boolean refMatcher) {
+ if (refMatcher) {
+ return RefPatternMatcher.getMatcher(pattern).match(value, null);
+ } else {
+ return Pattern.matches(pattern, value);
+ }
}
private boolean canSkipGroup(PluginConfig conf, IdentifiedUser user) {
diff --git a/src/main/resources/Documentation/config.md b/src/main/resources/Documentation/config.md
index 398a771..a4151a0 100644
--- a/src/main/resources/Documentation/config.md
+++ b/src/main/resources/Documentation/config.md
@@ -225,6 +225,22 @@
ref = ^refs/heads/stable-.*
```
+Email-specific validations
+---------------------------
+
+By default, the validation will be enabled for all users. However, it can
+be limited to users with particular emails by setting `plugin.@PLUGIN@.email`.
+The emails may be configured using specific emails, patterns, or regular
+expressions. Multiple emails may be specified.
+
+E.g. to limit the validation to all users whose emails match `.*@example.com$`
+the following could be configured:
+
+```
+ [plugin "@PLUGIN@"]
+ email = .*@example.com$
+```
+
Permission to skip the rules
----------------------------
diff --git a/src/test/java/com/googlesource/gerrit/plugins/uploadvalidator/EmailAwareValidatorConfigTest.java b/src/test/java/com/googlesource/gerrit/plugins/uploadvalidator/EmailAwareValidatorConfigTest.java
new file mode 100644
index 0000000..46bf3c7
--- /dev/null
+++ b/src/test/java/com/googlesource/gerrit/plugins/uploadvalidator/EmailAwareValidatorConfigTest.java
@@ -0,0 +1,108 @@
+// Copyright (C) 2017 The Android Open Source Project
+//
+// Licensed under the Apache License, Version 2.0 (the "License");
+// you may not use this file except in compliance with the License.
+// You may obtain a copy of the License at
+//
+// http://www.apache.org/licenses/LICENSE-2.0
+//
+// Unless required by applicable law or agreed to in writing, software
+// distributed under the License is distributed on an "AS IS" BASIS,
+// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+// See the License for the specific language governing permissions and
+// limitations under the License.
+
+package com.googlesource.gerrit.plugins.uploadvalidator;
+
+import static com.google.common.truth.Truth.assertThat;
+
+import com.google.gerrit.reviewdb.client.Project;
+import com.google.gerrit.server.IdentifiedUser;
+
+import org.eclipse.jgit.errors.ConfigInvalidException;
+import org.junit.Test;
+
+public class EmailAwareValidatorConfigTest {
+ private Project.NameKey projectName = new Project.NameKey("testProject");
+ private IdentifiedUser anyUser = new FakeUserProvider().get();
+
+ @Test
+ public void isEnabledForAllEmailsByDefault() throws Exception {
+ ValidatorConfig config =
+ getConfig("[plugin \"uploadvalidator\"]\n"
+ + "blockedFileExtension = jar");
+
+ assertThat(
+ config.isEnabledForRef(anyUser, projectName, "anyRef",
+ "blockedFileExtension")).isTrue();
+ }
+
+ @Test
+ public void isEnabledForSingleEmail() throws Exception {
+ ValidatorConfig config =
+ getConfig("[plugin \"uploadvalidator\"]\n"
+ + " email = " + FakeUserProvider.FAKE_EMAIL + "\n"
+ + " blockedFileExtension = jar");
+
+ assertThat(
+ config.isEnabledForRef(anyUser, projectName, "refs/heads/anyref",
+ "blockedFileExtension")).isTrue();
+ }
+
+ @Test
+ public void isDisabledForInvalidEmail() throws Exception {
+ ValidatorConfig config =
+ getConfig("[plugin \"uploadvalidator\"]\n"
+ + " email = anInvalidEmail@example.com\n"
+ + " blockedFileExtension = jar");
+
+ assertThat(
+ config.isEnabledForRef(anyUser, projectName, "refs/heads/anyref",
+ "blockedFileExtension")).isFalse();
+ }
+
+ @Test
+ public void isEnabledForRegexEmail() throws Exception {
+ IdentifiedUser exampleOrgUser = new FakeUserProvider().get("a@example.org");
+ ValidatorConfig config =
+ getConfig("[plugin \"uploadvalidator\"]\n"
+ + " email = .*@example.org$\n"
+ + " blockedFileExtension = jar");
+
+ assertThat(
+ config.isEnabledForRef(anyUser, projectName, "refs/heads/anyref",
+ "blockedFileExtension")).isFalse();
+ assertThat(
+ config.isEnabledForRef(exampleOrgUser, projectName,
+ "refs/heads/anyref", "blockedFileExtension")).isTrue();
+ }
+
+ @Test
+ public void isEnabledForMultipleEmails() throws Exception {
+ IdentifiedUser exampleOrgUser = new FakeUserProvider().get("a@example.org");
+ IdentifiedUser xUser = new FakeUserProvider().get("x@example.com");
+ ValidatorConfig config =
+ getConfig("[plugin \"uploadvalidator\"]\n"
+ + " email = .*@example.org$\n"
+ + " email = x@example.com\n"
+ + " blockedFileExtension = jar");
+
+ assertThat(
+ config.isEnabledForRef(exampleOrgUser, projectName, "refs/heads/anyref",
+ "blockedFileExtension")).isTrue();
+ assertThat(
+ config.isEnabledForRef(xUser, projectName, "refs/heads/anyref",
+ "blockedFileExtension")).isTrue();
+ assertThat(
+ config.isEnabledForRef(anyUser, projectName, "refs/heads/anyref",
+ "blockedFileExtension")).isFalse();
+ }
+
+ private ValidatorConfig getConfig(String defaultConfig)
+ throws ConfigInvalidException {
+ ValidatorConfig config =
+ new ValidatorConfig(new FakeConfigFactory(projectName, defaultConfig),
+ new FakeGroupCacheUUIDByName());
+ return config;
+ }
+}
diff --git a/src/test/java/com/googlesource/gerrit/plugins/uploadvalidator/FakeUserProvider.java b/src/test/java/com/googlesource/gerrit/plugins/uploadvalidator/FakeUserProvider.java
index f634090..e49e974 100644
--- a/src/test/java/com/googlesource/gerrit/plugins/uploadvalidator/FakeUserProvider.java
+++ b/src/test/java/com/googlesource/gerrit/plugins/uploadvalidator/FakeUserProvider.java
@@ -18,10 +18,14 @@
import static org.easymock.EasyMock.expect;
import static org.easymock.EasyMock.replay;
+import com.google.gerrit.common.TimeUtil;
+import com.google.gerrit.reviewdb.client.Account;
import com.google.gerrit.server.IdentifiedUser;
import com.google.inject.Provider;
public class FakeUserProvider implements Provider<IdentifiedUser> {
+ public static String FAKE_EMAIL = "fake@example.com";
+
private final String[] groupUUID;
public FakeUserProvider(String... groupUUID) {
@@ -30,13 +34,20 @@
@Override
public IdentifiedUser get() {
- return createNew();
+ return createNew(FAKE_EMAIL);
}
- private IdentifiedUser createNew() {
+ public IdentifiedUser get(String email) {
+ return createNew(email);
+ }
+
+ private IdentifiedUser createNew(String email) {
IdentifiedUser user = createMock(IdentifiedUser.class);
+ Account account = new Account(new Account.Id(1), TimeUtil.nowTs());
+ account.setPreferredEmail(email);
expect(user.isIdentifiedUser()).andReturn(true);
expect(user.asIdentifiedUser()).andReturn(user);
+ expect(user.getAccount()).andStubReturn(account);
expect(user.getEffectiveGroups()).andReturn(
new FakeGroupMembership(groupUUID));
replay(user);