Move most GPG-related code to a gerrit-gpg module

Bouncy Castle is still an optional dependency for Gerrit, so we want
to avoid accidentally attempting to load Bouncy Castle classes when
they might not be available. Rather than try to guard every
org.bouncycastle.* reference with a hasPGP() check, reduce the surface
area of calls that actually require Bouncy Castle. Move almost all
code that calls Bouncy Castle into a new module, gerrit-gpg.

Callers need only interact with this module by installing the
GpgModule, which is careful to protect all Bouncy Castle class loading
with the appropriate havePGP() check. Moreover, this module doesn't
need to be installed in the gerrit-server package at all, so we can
break the compile-time dependency between gerrit-server and Bouncy
Castle, so accidentally introducing a dependency on Bouncy Castle
results in a compile error.

The REST API and extension APIs dealing with GPG keys only refer to
the GpgKeyInfo POJO, and don't need to actually refer to Bouncy Castle
classes. Add a shim interface, GpgApiAdapter, that is used by
AccountApiImpl to process GPG keys. GpgModule binds this interface to
either the Bouncy Castle enabled implementation, or a not-implemented
implementation.

Since there are various places in the server code where we want to
inspect whether signed push is enabled at the server level, but we
don't want to have to call into gerrit-gpg code to do this, bind a
boolean with @EnableSignedPush from GpgModule.

Change-Id: Idbab00a52d86216cae73d02876d56be54aef6581
This commit is contained in:
Dave Borowitz 2015-08-26 09:51:27 -04:00
parent b84c227162
commit b8336f176a
45 changed files with 521 additions and 164 deletions

View File

@ -5,6 +5,8 @@ java_library(
'//gerrit-common:annotations',
'//gerrit-common:server',
'//gerrit-extension-api:api',
'//gerrit-gpg:gpg',
'//gerrit-gpg:testutil',
'//gerrit-launcher:launcher',
'//gerrit-lucene:lucene',
'//gerrit-httpd:httpd',

View File

@ -17,7 +17,7 @@ package com.google.gerrit.acceptance.api.accounts;
import static com.google.common.base.Preconditions.checkNotNull;
import static com.google.common.truth.Truth.assertThat;
import static com.google.common.truth.Truth.assert_;
import static com.google.gerrit.server.git.gpg.PublicKeyStore.keyToString;
import static com.google.gerrit.gpg.PublicKeyStore.keyToString;
import static java.nio.charset.StandardCharsets.UTF_8;
import com.google.common.base.Function;
@ -33,21 +33,23 @@ import com.google.gerrit.extensions.common.GpgKeyInfo;
import com.google.gerrit.extensions.restapi.BadRequestException;
import com.google.gerrit.extensions.restapi.ResourceConflictException;
import com.google.gerrit.extensions.restapi.ResourceNotFoundException;
import com.google.gerrit.gpg.Fingerprint;
import com.google.gerrit.gpg.PublicKeyStore;
import com.google.gerrit.gpg.server.GpgKeys;
import com.google.gerrit.gpg.testutil.TestKey;
import com.google.gerrit.reviewdb.client.Account;
import com.google.gerrit.reviewdb.client.AccountExternalId;
import com.google.gerrit.reviewdb.client.RefNames;
import com.google.gerrit.server.IdentifiedUser;
import com.google.gerrit.server.account.GpgKeys;
import com.google.gerrit.server.config.AllUsersName;
import com.google.gerrit.server.git.gpg.Fingerprint;
import com.google.gerrit.server.git.gpg.PublicKeyStore;
import com.google.gerrit.server.git.gpg.TestKey;
import com.google.gerrit.testutil.ConfigSuite;
import com.google.inject.Inject;
import com.google.inject.Provider;
import org.bouncycastle.bcpg.ArmoredOutputStream;
import org.bouncycastle.openpgp.PGPPublicKey;
import org.bouncycastle.openpgp.PGPPublicKeyRing;
import org.eclipse.jgit.lib.Config;
import org.eclipse.jgit.lib.Ref;
import org.eclipse.jgit.lib.RefUpdate;
import org.eclipse.jgit.lib.Repository;
@ -65,6 +67,13 @@ import java.util.List;
import java.util.Map;
public class AccountIT extends AbstractDaemonTest {
@ConfigSuite.Default
public static Config enableSignedPushConfig() {
Config cfg = new Config();
cfg.setBoolean("receive", null, "enableSignedPush", true);
return cfg;
}
@Inject
private Provider<PublicKeyStore> publicKeyStoreProvider;

View File

@ -19,6 +19,10 @@ public class NotImplementedException extends UnsupportedOperationException {
private static final long serialVersionUID = 1L;
public NotImplementedException() {
super("Not implemented.");
this("Not implemented");
}
public NotImplementedException(String message) {
super(message);
}
}

65
gerrit-gpg/BUCK Normal file
View File

@ -0,0 +1,65 @@
java_library(
name = 'gpg',
srcs = glob(['src/main/java/**/*.java']),
deps = [
'//gerrit-common:server',
'//gerrit-extension-api:api',
'//gerrit-reviewdb:server',
'//gerrit-server:server',
'//lib:guava',
'//lib:gwtorm',
'//lib/guice:guice',
'//lib/guice:guice-assistedinject',
'//lib/guice:guice-servlet',
'//lib/jgit:jgit',
'//lib/log:api',
],
provided_deps = [
'//lib/bouncycastle:bcprov',
'//lib/bouncycastle:bcpg',
],
visibility = ['PUBLIC'],
)
TESTUTIL_SRCS = [
'src/test/java/com/google/gerrit/gpg/testutil/TestKey.java',
]
java_library(
name = 'testutil',
srcs = TESTUTIL_SRCS,
deps = [
':gpg',
'//lib:guava',
'//lib/bouncycastle:bcpg',
'//lib/bouncycastle:bcprov',
'//lib/jgit:jgit',
],
visibility = ['PUBLIC'],
)
java_test(
name = 'gpg_tests',
srcs = glob(
['src/test/java/**/*.java'],
excludes = TESTUTIL_SRCS,
),
deps = [
':gpg',
':testutil',
'//gerrit-extension-api:api',
'//gerrit-reviewdb:server',
'//gerrit-server:server',
'//gerrit-server:testutil',
'//lib:guava',
'//lib:gwtorm',
'//lib:truth',
'//lib/bouncycastle:bcpg',
'//lib/bouncycastle:bcprov',
'//lib/guice:guice',
'//lib/jgit:jgit',
'//lib/jgit:junit',
],
source_under_test = [':gpg'],
visibility = ['//tools/eclipse:classpath'],
)

View File

@ -12,7 +12,7 @@
// See the License for the specific language governing permissions and
// limitations under the License.
package com.google.gerrit.server.util;
package com.google.gerrit.gpg;
import org.bouncycastle.jce.provider.BouncyCastleProvider;
import org.bouncycastle.openpgp.PGPPublicKey;

View File

@ -12,7 +12,7 @@
// See the License for the specific language governing permissions and
// limitations under the License.
package com.google.gerrit.server.git.gpg;
package com.google.gerrit.gpg;
import java.util.ArrayList;
import java.util.Arrays;

View File

@ -12,7 +12,7 @@
// See the License for the specific language governing permissions and
// limitations under the License.
package com.google.gerrit.server.git.gpg;
package com.google.gerrit.gpg;
import static com.google.common.base.Preconditions.checkArgument;

View File

@ -12,10 +12,10 @@
// See the License for the specific language governing permissions and
// limitations under the License.
package com.google.gerrit.server.git.gpg;
package com.google.gerrit.gpg;
import static com.google.gerrit.gpg.PublicKeyStore.keyIdToString;
import static com.google.gerrit.reviewdb.client.AccountExternalId.SCHEME_GPGKEY;
import static com.google.gerrit.server.git.gpg.PublicKeyStore.keyIdToString;
import com.google.common.collect.FluentIterable;
import com.google.common.collect.Ordering;

View File

@ -0,0 +1,99 @@
// Copyright (C) 2015 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.google.gerrit.gpg;
import static com.google.gerrit.gpg.server.GpgKey.GPG_KEY_KIND;
import static com.google.gerrit.server.account.AccountResource.ACCOUNT_KIND;
import com.google.gerrit.extensions.api.accounts.GpgKeyApi;
import com.google.gerrit.extensions.common.GpgKeyInfo;
import com.google.gerrit.extensions.registration.DynamicMap;
import com.google.gerrit.extensions.restapi.IdString;
import com.google.gerrit.extensions.restapi.NotImplementedException;
import com.google.gerrit.extensions.restapi.RestApiModule;
import com.google.gerrit.gpg.api.GpgApiAdapterImpl;
import com.google.gerrit.gpg.api.GpgKeyApiImpl;
import com.google.gerrit.gpg.server.DeleteGpgKey;
import com.google.gerrit.gpg.server.GpgKeys;
import com.google.gerrit.gpg.server.PostGpgKeys;
import com.google.gerrit.server.EnableSignedPush;
import com.google.gerrit.server.account.AccountResource;
import com.google.gerrit.server.api.accounts.GpgApiAdapter;
import org.eclipse.jgit.lib.Config;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import java.util.List;
import java.util.Map;
public class GpgModule extends RestApiModule {
private static final Logger log = LoggerFactory.getLogger(GpgModule.class);
private final Config cfg;
public GpgModule(Config cfg) {
this.cfg = cfg;
}
@Override
protected void configure() {
boolean configEnableSignedPush =
cfg.getBoolean("receive", null, "enableSignedPush", false);
boolean havePgp = BouncyCastleUtil.havePGP();
boolean enableSignedPush = configEnableSignedPush && havePgp;
bindConstant().annotatedWith(EnableSignedPush.class).to(enableSignedPush);
if (configEnableSignedPush && !havePgp) {
log.info("Bouncy Castle PGP not installed; signed push verification is"
+ " disabled");
}
if (!enableSignedPush) {
bind(GpgApiAdapter.class).to(NoGpgApi.class);
return;
}
install(new SignedPushModule());
bind(GpgApiAdapter.class).to(GpgApiAdapterImpl.class);
factory(GpgKeyApiImpl.Factory.class);
DynamicMap.mapOf(binder(), GPG_KEY_KIND);
child(ACCOUNT_KIND, "gpgkeys").to(GpgKeys.class);
post(ACCOUNT_KIND, "gpgkeys").to(PostGpgKeys.class);
get(GPG_KEY_KIND).to(GpgKeys.Get.class);
delete(GPG_KEY_KIND).to(DeleteGpgKey.class);
}
private static class NoGpgApi implements GpgApiAdapter {
private static final String MSG = "GPG key APIs disabled";
@Override
public Map<String, GpgKeyInfo> listGpgKeys(AccountResource account) {
throw new NotImplementedException(MSG);
}
@Override
public Map<String, GpgKeyInfo> putGpgKeys(AccountResource account,
List<String> add, List<String> delete) {
throw new NotImplementedException(MSG);
}
@Override
public GpgKeyApi gpgKey(AccountResource account, IdString idStr) {
throw new NotImplementedException(MSG);
}
}
}

View File

@ -12,9 +12,9 @@
// See the License for the specific language governing permissions and
// limitations under the License.
package com.google.gerrit.server.git.gpg;
package com.google.gerrit.gpg;
import static com.google.gerrit.server.git.gpg.PublicKeyStore.keyIdToString;
import static com.google.gerrit.gpg.PublicKeyStore.keyIdToString;
import org.bouncycastle.openpgp.PGPPublicKey;

View File

@ -12,7 +12,7 @@
// See the License for the specific language governing permissions and
// limitations under the License.
package com.google.gerrit.server.git.gpg;
package com.google.gerrit.gpg;
import static com.google.common.base.Preconditions.checkState;
import static org.eclipse.jgit.lib.Constants.OBJ_BLOB;

View File

@ -12,10 +12,10 @@
// See the License for the specific language governing permissions and
// limitations under the License.
package com.google.gerrit.server.git.gpg;
package com.google.gerrit.gpg;
import static com.google.gerrit.server.git.gpg.PublicKeyStore.keyIdToString;
import static com.google.gerrit.server.git.gpg.PublicKeyStore.keyToString;
import static com.google.gerrit.gpg.PublicKeyStore.keyIdToString;
import static com.google.gerrit.gpg.PublicKeyStore.keyToString;
import org.bouncycastle.bcpg.ArmoredInputStream;
import org.bouncycastle.openpgp.PGPException;

View File

@ -12,19 +12,19 @@
// See the License for the specific language governing permissions and
// limitations under the License.
package com.google.gerrit.server.git.gpg;
package com.google.gerrit.gpg;
import com.google.common.base.Strings;
import com.google.common.collect.Lists;
import com.google.gerrit.extensions.registration.DynamicSet;
import com.google.gerrit.reviewdb.client.Project;
import com.google.gerrit.server.EnableSignedPush;
import com.google.gerrit.server.config.AllUsersName;
import com.google.gerrit.server.config.GerritServerConfig;
import com.google.gerrit.server.git.GitRepositoryManager;
import com.google.gerrit.server.git.ReceivePackInitializer;
import com.google.gerrit.server.project.ProjectCache;
import com.google.gerrit.server.project.ProjectState;
import com.google.gerrit.server.util.BouncyCastleUtil;
import com.google.inject.AbstractModule;
import com.google.inject.Inject;
import com.google.inject.Provider;
@ -44,20 +44,14 @@ import java.security.NoSuchAlgorithmException;
import java.security.SecureRandom;
import java.util.Random;
public class SignedPushModule extends AbstractModule {
class SignedPushModule extends AbstractModule {
private static final Logger log =
LoggerFactory.getLogger(SignedPushModule.class);
public static boolean isEnabled(Config cfg) {
return cfg.getBoolean("receive", null, "enableSignedPush", false);
}
@Override
protected void configure() {
if (!BouncyCastleUtil.havePGP()) {
log.info("BouncyCastle PGP not installed; signed push verification is"
+ " disabled");
return;
throw new ProvisionException("Bouncy Castle PGP not installed");
}
bind(PublicKeyChecker.class).to(GerritPublicKeyChecker.class);
bind(PublicKeyStore.class).toProvider(StoreProvider.class);
@ -73,12 +67,13 @@ public class SignedPushModule extends AbstractModule {
@Inject
Initializer(@GerritServerConfig Config cfg,
@EnableSignedPush boolean enableSignedPush,
SignedPushPreReceiveHook hook,
ProjectCache projectCache) {
this.hook = hook;
this.projectCache = projectCache;
if (isEnabled(cfg)) {
if (enableSignedPush) {
String seed = cfg.getString("receive", null, "certNonceSeed");
if (Strings.isNullOrEmpty(seed)) {
seed = randomString(64);

View File

@ -12,7 +12,7 @@
// See the License for the specific language governing permissions and
// limitations under the License.
package com.google.gerrit.server.git.gpg;
package com.google.gerrit.gpg;
import com.google.gerrit.server.config.AllUsersName;
import com.google.gerrit.server.git.GitRepositoryManager;

View File

@ -0,0 +1,83 @@
// Copyright (C) 2015 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.google.gerrit.gpg.api;
import com.google.gerrit.extensions.api.accounts.GpgKeyApi;
import com.google.gerrit.extensions.common.GpgKeyInfo;
import com.google.gerrit.extensions.restapi.IdString;
import com.google.gerrit.extensions.restapi.RestApiException;
import com.google.gerrit.gpg.server.GpgKeys;
import com.google.gerrit.gpg.server.PostGpgKeys;
import com.google.gerrit.server.GpgException;
import com.google.gerrit.server.account.AccountResource;
import com.google.gerrit.server.api.accounts.GpgApiAdapter;
import com.google.gwtorm.server.OrmException;
import com.google.inject.Inject;
import org.bouncycastle.openpgp.PGPException;
import java.io.IOException;
import java.util.List;
import java.util.Map;
public class GpgApiAdapterImpl implements GpgApiAdapter {
private final PostGpgKeys postGpgKeys;
private final GpgKeys gpgKeys;
private final GpgKeyApiImpl.Factory gpgKeyApiFactory;
@Inject
GpgApiAdapterImpl(
PostGpgKeys postGpgKeys,
GpgKeys gpgKeys,
GpgKeyApiImpl.Factory gpgKeyApiFactory) {
this.postGpgKeys = postGpgKeys;
this.gpgKeys = gpgKeys;
this.gpgKeyApiFactory = gpgKeyApiFactory;
}
@Override
public Map<String, GpgKeyInfo> listGpgKeys(AccountResource account)
throws RestApiException, GpgException {
try {
return gpgKeys.list().apply(account);
} catch (OrmException | PGPException | IOException e) {
throw new GpgException(e);
}
}
@Override
public Map<String, GpgKeyInfo> putGpgKeys(AccountResource account,
List<String> add, List<String> delete)
throws RestApiException, GpgException {
PostGpgKeys.Input in = new PostGpgKeys.Input();
in.add = add;
in.delete = delete;
try {
return postGpgKeys.apply(account, in);
} catch (PGPException | OrmException | IOException e) {
throw new GpgException(e);
}
}
@Override
public GpgKeyApi gpgKey(AccountResource account, IdString idStr)
throws RestApiException, GpgException {
try {
return gpgKeyApiFactory.create(gpgKeys.parse(account, idStr));
} catch (PGPException | OrmException | IOException e) {
throw new GpgException(e);
}
}
}

View File

@ -12,14 +12,14 @@
// See the License for the specific language governing permissions and
// limitations under the License.
package com.google.gerrit.server.api.accounts;
package com.google.gerrit.gpg.api;
import com.google.gerrit.extensions.api.accounts.GpgKeyApi;
import com.google.gerrit.extensions.common.GpgKeyInfo;
import com.google.gerrit.extensions.restapi.RestApiException;
import com.google.gerrit.server.account.AccountResource;
import com.google.gerrit.server.account.DeleteGpgKey;
import com.google.gerrit.server.account.GpgKeys;
import com.google.gerrit.gpg.server.DeleteGpgKey;
import com.google.gerrit.gpg.server.GpgKey;
import com.google.gerrit.gpg.server.GpgKeys;
import com.google.gwtorm.server.OrmException;
import com.google.inject.assistedinject.Assisted;
import com.google.inject.assistedinject.AssistedInject;
@ -28,20 +28,20 @@ import org.bouncycastle.openpgp.PGPException;
import java.io.IOException;
class GpgKeyApiImpl implements GpgKeyApi {
interface Factory {
GpgKeyApiImpl create(AccountResource.GpgKey rsrc);
public class GpgKeyApiImpl implements GpgKeyApi {
public interface Factory {
GpgKeyApiImpl create(GpgKey rsrc);
}
private final GpgKeys.Get get;
private final DeleteGpgKey delete;
private final AccountResource.GpgKey rsrc;
private final GpgKey rsrc;
@AssistedInject
GpgKeyApiImpl(
GpgKeys.Get get,
DeleteGpgKey delete,
@Assisted AccountResource.GpgKey rsrc) {
@Assisted GpgKey rsrc) {
this.get = get;
this.delete = delete;
this.rsrc = rsrc;

View File

@ -12,20 +12,19 @@
// See the License for the specific language governing permissions and
// limitations under the License.
package com.google.gerrit.server.account;
package com.google.gerrit.gpg.server;
import static com.google.gerrit.server.git.gpg.PublicKeyStore.keyIdToString;
import static com.google.gerrit.gpg.PublicKeyStore.keyIdToString;
import com.google.common.io.BaseEncoding;
import com.google.gerrit.extensions.restapi.ResourceConflictException;
import com.google.gerrit.extensions.restapi.Response;
import com.google.gerrit.extensions.restapi.RestModifyView;
import com.google.gerrit.gpg.PublicKeyStore;
import com.google.gerrit.gpg.server.DeleteGpgKey.Input;
import com.google.gerrit.reviewdb.client.AccountExternalId;
import com.google.gerrit.reviewdb.server.ReviewDb;
import com.google.gerrit.server.GerritPersonIdent;
import com.google.gerrit.server.account.AccountResource.GpgKey;
import com.google.gerrit.server.account.DeleteGpgKey.Input;
import com.google.gerrit.server.git.gpg.PublicKeyStore;
import com.google.gwtorm.server.OrmException;
import com.google.inject.Inject;
import com.google.inject.Provider;

View File

@ -0,0 +1,38 @@
// Copyright (C) 2015 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.google.gerrit.gpg.server;
import com.google.gerrit.extensions.restapi.RestView;
import com.google.gerrit.server.IdentifiedUser;
import com.google.gerrit.server.account.AccountResource;
import com.google.inject.TypeLiteral;
import org.bouncycastle.openpgp.PGPPublicKeyRing;
public class GpgKey extends AccountResource {
public static final TypeLiteral<RestView<GpgKey>> GPG_KEY_KIND =
new TypeLiteral<RestView<GpgKey>>() {};
private final PGPPublicKeyRing keyRing;
public GpgKey(IdentifiedUser user, PGPPublicKeyRing keyRing) {
super(user);
this.keyRing = keyRing;
}
public PGPPublicKeyRing getKeyRing() {
return keyRing;
}
}

View File

@ -12,7 +12,7 @@
// See the License for the specific language governing permissions and
// limitations under the License.
package com.google.gerrit.server.account;
package com.google.gerrit.gpg.server;
import static com.google.gerrit.reviewdb.client.AccountExternalId.SCHEME_GPGKEY;
import static java.nio.charset.StandardCharsets.UTF_8;
@ -31,13 +31,13 @@ import com.google.gerrit.extensions.restapi.IdString;
import com.google.gerrit.extensions.restapi.ResourceNotFoundException;
import com.google.gerrit.extensions.restapi.RestReadView;
import com.google.gerrit.extensions.restapi.RestView;
import com.google.gerrit.gpg.BouncyCastleUtil;
import com.google.gerrit.gpg.Fingerprint;
import com.google.gerrit.gpg.PublicKeyStore;
import com.google.gerrit.reviewdb.client.Account;
import com.google.gerrit.reviewdb.client.AccountExternalId;
import com.google.gerrit.reviewdb.server.ReviewDb;
import com.google.gerrit.server.account.AccountResource.GpgKey;
import com.google.gerrit.server.git.gpg.Fingerprint;
import com.google.gerrit.server.git.gpg.PublicKeyStore;
import com.google.gerrit.server.util.BouncyCastleUtil;
import com.google.gerrit.server.account.AccountResource;
import com.google.gwtorm.server.OrmException;
import com.google.inject.Inject;
import com.google.inject.Provider;
@ -60,17 +60,17 @@ import java.util.Map;
@Singleton
public class GpgKeys implements
ChildCollection<AccountResource, AccountResource.GpgKey> {
ChildCollection<AccountResource, GpgKey> {
private static final Logger log = LoggerFactory.getLogger(GpgKeys.class);
public static String MIME_TYPE = "application/pgp-keys";
private final DynamicMap<RestView<AccountResource.GpgKey>> views;
private final DynamicMap<RestView<GpgKey>> views;
private final Provider<ReviewDb> db;
private final Provider<PublicKeyStore> storeProvider;
@Inject
GpgKeys(DynamicMap<RestView<AccountResource.GpgKey>> views,
GpgKeys(DynamicMap<RestView<GpgKey>> views,
Provider<ReviewDb> db,
Provider<PublicKeyStore> storeProvider) {
this.views = views;
@ -102,7 +102,7 @@ public class GpgKeys implements
for (PGPPublicKeyRing keyRing : store.get(keyId)) {
PGPPublicKey key = keyRing.getPublicKey();
if (Arrays.equals(key.getFingerprint(), fp)) {
return new AccountResource.GpgKey(parent.getUser(), keyRing);
return new GpgKey(parent.getUser(), keyRing);
}
}
}
@ -172,7 +172,7 @@ public class GpgKeys implements
}
@Singleton
public static class Get implements RestReadView<AccountResource.GpgKey> {
public static class Get implements RestReadView<GpgKey> {
@Override
public GpgKeyInfo apply(GpgKey rsrc) throws IOException {
return toJson(rsrc.getKeyRing());

View File

@ -12,10 +12,10 @@
// See the License for the specific language governing permissions and
// limitations under the License.
package com.google.gerrit.server.account;
package com.google.gerrit.gpg.server;
import static com.google.gerrit.server.git.gpg.PublicKeyStore.keyIdToString;
import static com.google.gerrit.server.git.gpg.PublicKeyStore.keyToString;
import static com.google.gerrit.gpg.PublicKeyStore.keyIdToString;
import static com.google.gerrit.gpg.PublicKeyStore.keyToString;
import static java.nio.charset.StandardCharsets.UTF_8;
import com.google.common.base.Function;
@ -32,14 +32,15 @@ import com.google.gerrit.extensions.restapi.BadRequestException;
import com.google.gerrit.extensions.restapi.ResourceConflictException;
import com.google.gerrit.extensions.restapi.ResourceNotFoundException;
import com.google.gerrit.extensions.restapi.RestModifyView;
import com.google.gerrit.gpg.CheckResult;
import com.google.gerrit.gpg.Fingerprint;
import com.google.gerrit.gpg.PublicKeyChecker;
import com.google.gerrit.gpg.PublicKeyStore;
import com.google.gerrit.gpg.server.PostGpgKeys.Input;
import com.google.gerrit.reviewdb.client.AccountExternalId;
import com.google.gerrit.reviewdb.server.ReviewDb;
import com.google.gerrit.server.GerritPersonIdent;
import com.google.gerrit.server.account.PostGpgKeys.Input;
import com.google.gerrit.server.git.gpg.CheckResult;
import com.google.gerrit.server.git.gpg.Fingerprint;
import com.google.gerrit.server.git.gpg.PublicKeyChecker;
import com.google.gerrit.server.git.gpg.PublicKeyStore;
import com.google.gerrit.server.account.AccountResource;
import com.google.gwtorm.server.OrmException;
import com.google.inject.Inject;
import com.google.inject.Provider;

View File

@ -12,12 +12,13 @@
// See the License for the specific language governing permissions and
// limitations under the License.
package com.google.gerrit.server.git.gpg;
package com.google.gerrit.gpg;
import static com.google.common.base.Preconditions.checkArgument;
import static com.google.common.truth.Truth.assertThat;
import com.google.common.collect.ImmutableList;
import com.google.gerrit.gpg.testutil.TestKey;
import com.google.gerrit.lifecycle.LifecycleManager;
import com.google.gerrit.reviewdb.client.Account;
import com.google.gerrit.reviewdb.client.AccountExternalId;

View File

@ -12,10 +12,12 @@
// See the License for the specific language governing permissions and
// limitations under the License.
package com.google.gerrit.server.git.gpg;
package com.google.gerrit.gpg;
import static org.junit.Assert.assertEquals;
import com.google.gerrit.gpg.testutil.TestKey;
import org.junit.Before;
import org.junit.Test;

View File

@ -12,16 +12,17 @@
// See the License for the specific language governing permissions and
// limitations under the License.
package com.google.gerrit.server.git.gpg;
package com.google.gerrit.gpg;
import static com.google.gerrit.server.git.gpg.PublicKeyStore.keyIdToString;
import static com.google.gerrit.server.git.gpg.PublicKeyStore.keyObjectId;
import static com.google.gerrit.server.git.gpg.PublicKeyStore.keyToString;
import static com.google.gerrit.gpg.PublicKeyStore.keyIdToString;
import static com.google.gerrit.gpg.PublicKeyStore.keyObjectId;
import static com.google.gerrit.gpg.PublicKeyStore.keyToString;
import static java.nio.charset.StandardCharsets.UTF_8;
import static org.junit.Assert.assertEquals;
import static org.junit.Assert.assertFalse;
import static org.junit.Assert.assertTrue;
import com.google.gerrit.gpg.testutil.TestKey;
import com.google.gerrit.reviewdb.client.RefNames;
import org.bouncycastle.openpgp.PGPPublicKey;

View File

@ -12,13 +12,14 @@
// See the License for the specific language governing permissions and
// limitations under the License.
package com.google.gerrit.server.git.gpg;
package com.google.gerrit.gpg;
import static com.google.gerrit.server.git.gpg.PublicKeyStore.keyIdToString;
import static com.google.gerrit.server.git.gpg.PublicKeyStore.keyToString;
import static com.google.gerrit.gpg.PublicKeyStore.keyIdToString;
import static com.google.gerrit.gpg.PublicKeyStore.keyToString;
import static java.nio.charset.StandardCharsets.UTF_8;
import static org.junit.Assert.assertEquals;
import com.google.gerrit.gpg.testutil.TestKey;
import com.google.gerrit.reviewdb.client.RefNames;
import org.bouncycastle.bcpg.ArmoredOutputStream;

View File

@ -12,9 +12,9 @@
// See the License for the specific language governing permissions and
// limitations under the License.
package com.google.gerrit.server.git.gpg;
package com.google.gerrit.gpg.testutil;
import static com.google.gerrit.server.git.gpg.PublicKeyStore.keyIdToString;
import static com.google.gerrit.gpg.PublicKeyStore.keyIdToString;
import com.google.common.collect.ImmutableList;

View File

@ -100,6 +100,7 @@ java_library(
':init-api',
':util',
'//gerrit-cache-h2:cache-h2',
'//gerrit-gpg:gpg',
'//gerrit-lucene:lucene',
'//gerrit-oauth:oauth',
'//gerrit-openid:openid',

View File

@ -20,6 +20,7 @@ import static java.nio.charset.StandardCharsets.UTF_8;
import com.google.common.annotations.VisibleForTesting;
import com.google.common.base.MoreObjects;
import com.google.gerrit.common.ChangeHookRunner;
import com.google.gerrit.gpg.GpgModule;
import com.google.gerrit.httpd.AllRequestFilter;
import com.google.gerrit.httpd.GerritOptions;
import com.google.gerrit.httpd.GetUserFilter;
@ -143,6 +144,7 @@ public class Daemon extends SiteProgram {
private final LifecycleManager manager = new LifecycleManager();
private Injector dbInjector;
private Injector cfgInjector;
private Config config;
private Injector sysInjector;
private Injector sshInjector;
private Injector webInjector;
@ -272,14 +274,15 @@ public class Daemon extends SiteProgram {
dbInjector = createDbInjector(MULTI_USER);
}
cfgInjector = createCfgInjector();
config = cfgInjector.getInstance(
Key.get(Config.class, GerritServerConfig.class));
sysInjector = createSysInjector();
sysInjector.getInstance(PluginGuiceEnvironment.class)
.setDbCfgInjector(dbInjector, cfgInjector);
manager.add(dbInjector, cfgInjector, sysInjector);
if (!consoleLog) {
manager.add(ErrorLogFile.start(getSitePath(),
cfgInjector.getInstance(Key.get(Config.class, GerritServerConfig.class))));
manager.add(ErrorLogFile.start(getSitePath(), config));
}
sshd &= !sshdOff();
@ -300,8 +303,7 @@ public class Daemon extends SiteProgram {
}
private boolean sshdOff() {
Config cfg = cfgInjector.getInstance(Key.get(Config.class, GerritServerConfig.class));
return new SshAddressesModule().getListenAddresses(cfg).isEmpty();
return new SshAddressesModule().getListenAddresses(config).isEmpty();
}
private String myVersion() {
@ -335,6 +337,7 @@ public class Daemon extends SiteProgram {
modules.add(new SignedTokenEmailTokenVerifier.Module());
modules.add(new PluginRestApiModule());
modules.add(new RestCacheAdminModule());
modules.add(new GpgModule(config));
modules.add(createIndexModule());
if (MoreObjects.firstNonNull(httpd, true)) {
modules.add(new CanonicalWebUrlModule() {

View File

@ -59,7 +59,7 @@ public class RefNames {
/**
* Special ref for GPG public keys used by {@link
* com.google.gerrit.server.git.gpg.SignedPushPreReceiveHook}.
* com.google.gerrit.gpg.SignedPushPreReceiveHook}.
*/
public static final String REFS_GPG_KEYS = "refs/meta/gpg-keys";

View File

@ -72,9 +72,6 @@ java_library(
],
provided_deps = [
'//lib:servlet-api-3_1',
'//lib/bouncycastle:bcprov',
'//lib/bouncycastle:bcpg',
'//lib/bouncycastle:bcpkix',
],
visibility = ['PUBLIC'],
)
@ -88,7 +85,6 @@ java_sources(
TESTUTIL = glob([
'src/test/java/com/google/gerrit/testutil/**/*.java',
'src/test/java/com/google/gerrit/server/project/Util.java',
'src/test/java/com/google/gerrit/server/git/gpg/TestKey.java',
])
java_library(
name = 'testutil',
@ -98,14 +94,13 @@ java_library(
'//gerrit-common:server',
'//gerrit-cache-h2:cache-h2',
'//gerrit-extension-api:api',
'//gerrit-gpg:gpg',
'//gerrit-lucene:lucene',
'//gerrit-reviewdb:server',
'//lib:gwtorm',
'//lib:h2',
'//lib:truth',
'//lib/auto:auto-value',
'//lib/bouncycastle:bcpg',
'//lib/bouncycastle:bcprov',
'//lib/guice:guice',
'//lib/guice:guice-servlet',
'//lib/jgit:jgit',
@ -211,6 +206,7 @@ java_test(
'//gerrit-common:annotations',
'//gerrit-common:server',
'//gerrit-extension-api:api',
'//gerrit-gpg:gpg',
'//gerrit-reviewdb:server',
'//gerrit-server/src/main/prolog:common',
'//lib:args4j',
@ -218,9 +214,6 @@ java_test(
'//lib:guava',
'//lib:gwtorm',
'//lib:truth',
'//lib/bouncycastle:bcprov',
'//lib/bouncycastle:bcpg',
'//lib/bouncycastle:bcpkix',
'//lib/guice:guice',
'//lib/guice:guice-assistedinject',
'//lib/jgit:jgit',

View File

@ -0,0 +1,29 @@
// Copyright (C) 2015 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.google.gerrit.server;
import static java.lang.annotation.RetentionPolicy.RUNTIME;
import com.google.inject.BindingAnnotation;
import java.lang.annotation.Retention;
/**
* Marker on a boolean indicating whether signed push is enabled on the server.
*/
@Retention(RUNTIME)
@BindingAnnotation
public @interface EnableSignedPush {
}

View File

@ -0,0 +1,33 @@
// Copyright (C) 2015 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.google.gerrit.server;
/** Generic exception type for GPG-related exceptions. */
public class GpgException extends Exception {
private static final long serialVersionUID = 1L;
public GpgException(String message) {
super(message);
}
public GpgException(Throwable cause) {
super(cause);
}
public GpgException(String message, Throwable cause) {
super(message, cause);
}
}

View File

@ -22,8 +22,6 @@ import com.google.gerrit.server.IdentifiedUser;
import com.google.gerrit.server.change.ChangeResource;
import com.google.inject.TypeLiteral;
import org.bouncycastle.openpgp.PGPPublicKeyRing;
public class AccountResource implements RestResource {
public static final TypeLiteral<RestView<AccountResource>> ACCOUNT_KIND =
new TypeLiteral<RestView<AccountResource>>() {};
@ -37,9 +35,6 @@ public class AccountResource implements RestResource {
public static final TypeLiteral<RestView<SshKey>> SSH_KEY_KIND =
new TypeLiteral<RestView<SshKey>>() {};
public static final TypeLiteral<RestView<GpgKey>> GPG_KEY_KIND =
new TypeLiteral<RestView<GpgKey>>() {};
public static final TypeLiteral<RestView<StarredChange>> STARRED_CHANGE_KIND =
new TypeLiteral<RestView<StarredChange>>() {};
@ -101,19 +96,6 @@ public class AccountResource implements RestResource {
}
}
public static class GpgKey extends AccountResource {
private final PGPPublicKeyRing keyRing;
public GpgKey(IdentifiedUser user, PGPPublicKeyRing keyRing) {
super(user);
this.keyRing = keyRing;
}
public PGPPublicKeyRing getKeyRing() {
return keyRing;
}
}
public static class StarredChange extends AccountResource {
private final ChangeResource change;

View File

@ -17,7 +17,6 @@ package com.google.gerrit.server.account;
import static com.google.gerrit.server.account.AccountResource.ACCOUNT_KIND;
import static com.google.gerrit.server.account.AccountResource.CAPABILITY_KIND;
import static com.google.gerrit.server.account.AccountResource.EMAIL_KIND;
import static com.google.gerrit.server.account.AccountResource.GPG_KEY_KIND;
import static com.google.gerrit.server.account.AccountResource.SSH_KEY_KIND;
import static com.google.gerrit.server.account.AccountResource.STARRED_CHANGE_KIND;
@ -33,7 +32,6 @@ public class Module extends RestApiModule {
DynamicMap.mapOf(binder(), ACCOUNT_KIND);
DynamicMap.mapOf(binder(), CAPABILITY_KIND);
DynamicMap.mapOf(binder(), EMAIL_KIND);
DynamicMap.mapOf(binder(), GPG_KEY_KIND);
DynamicMap.mapOf(binder(), SSH_KEY_KIND);
DynamicMap.mapOf(binder(), STARRED_CHANGE_KIND);
@ -62,11 +60,6 @@ public class Module extends RestApiModule {
get(SSH_KEY_KIND).to(GetSshKey.class);
delete(SSH_KEY_KIND).to(DeleteSshKey.class);
child(ACCOUNT_KIND, "gpgkeys").to(GpgKeys.class);
post(ACCOUNT_KIND, "gpgkeys").to(PostGpgKeys.class);
get(GPG_KEY_KIND).to(GpgKeys.Get.class);
delete(GPG_KEY_KIND).to(DeleteGpgKey.class);
get(ACCOUNT_KIND, "avatar").to(GetAvatar.class);
get(ACCOUNT_KIND, "avatar.change.url").to(GetAvatarChangeUrl.class);

View File

@ -23,11 +23,10 @@ import com.google.gerrit.extensions.common.GpgKeyInfo;
import com.google.gerrit.extensions.restapi.IdString;
import com.google.gerrit.extensions.restapi.RestApiException;
import com.google.gerrit.extensions.restapi.TopLevelResource;
import com.google.gerrit.server.GpgException;
import com.google.gerrit.server.account.AccountLoader;
import com.google.gerrit.server.account.AccountResource;
import com.google.gerrit.server.account.CreateEmail;
import com.google.gerrit.server.account.GpgKeys;
import com.google.gerrit.server.account.PostGpgKeys;
import com.google.gerrit.server.account.StarredChanges;
import com.google.gerrit.server.change.ChangeResource;
import com.google.gerrit.server.change.ChangesCollection;
@ -35,9 +34,6 @@ import com.google.gwtorm.server.OrmException;
import com.google.inject.Inject;
import com.google.inject.assistedinject.Assisted;
import org.bouncycastle.openpgp.PGPException;
import java.io.IOException;
import java.util.List;
import java.util.Map;
@ -52,9 +48,7 @@ public class AccountApiImpl implements AccountApi {
private final StarredChanges.Create starredChangesCreate;
private final StarredChanges.Delete starredChangesDelete;
private final CreateEmail.Factory createEmailFactory;
private final PostGpgKeys postGpgKeys;
private final GpgKeys gpgKeys;
private final GpgKeyApiImpl.Factory gpgKeyApiFactory;
private final GpgApiAdapter gpgApiAdapter;
@Inject
AccountApiImpl(AccountLoader.Factory ailf,
@ -62,9 +56,7 @@ public class AccountApiImpl implements AccountApi {
StarredChanges.Create starredChangesCreate,
StarredChanges.Delete starredChangesDelete,
CreateEmail.Factory createEmailFactory,
PostGpgKeys postGpgKeys,
GpgKeys gpgKeys,
GpgKeyApiImpl.Factory gpgKeyApiFactory,
GpgApiAdapter gpgApiAdapter,
@Assisted AccountResource account) {
this.account = account;
this.accountLoaderFactory = ailf;
@ -72,9 +64,7 @@ public class AccountApiImpl implements AccountApi {
this.starredChangesCreate = starredChangesCreate;
this.starredChangesDelete = starredChangesDelete;
this.createEmailFactory = createEmailFactory;
this.postGpgKeys = postGpgKeys;
this.gpgKeys = gpgKeys;
this.gpgKeyApiFactory = gpgKeyApiFactory;
this.gpgApiAdapter = gpgApiAdapter;
}
@Override
@ -131,8 +121,8 @@ public class AccountApiImpl implements AccountApi {
@Override
public Map<String, GpgKeyInfo> listGpgKeys() throws RestApiException {
try {
return gpgKeys.list().apply(account);
} catch (OrmException | PGPException | IOException e) {
return gpgApiAdapter.listGpgKeys(account);
} catch (GpgException e) {
throw new RestApiException("Cannot list GPG keys", e);
}
}
@ -140,12 +130,9 @@ public class AccountApiImpl implements AccountApi {
@Override
public Map<String, GpgKeyInfo> putGpgKeys(List<String> add,
List<String> delete) throws RestApiException {
PostGpgKeys.Input in = new PostGpgKeys.Input();
in.add = add;
in.delete = delete;
try {
return postGpgKeys.apply(account, in);
} catch (PGPException | OrmException | IOException e) {
return gpgApiAdapter.putGpgKeys(account, add, delete);
} catch (GpgException e) {
throw new RestApiException("Cannot add GPG key", e);
}
}
@ -153,9 +140,8 @@ public class AccountApiImpl implements AccountApi {
@Override
public GpgKeyApi gpgKey(String id) throws RestApiException {
try {
IdString idStr = IdString.fromDecoded(id);
return gpgKeyApiFactory.create(gpgKeys.parse(account, idStr));
} catch (PGPException | OrmException | IOException e) {
return gpgApiAdapter.gpgKey(account, IdString.fromDecoded(id));
} catch (GpgException e) {
throw new RestApiException("Cannot get PGP key", e);
}
}

View File

@ -0,0 +1,34 @@
// Copyright (C) 2015 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.google.gerrit.server.api.accounts;
import com.google.gerrit.extensions.api.accounts.GpgKeyApi;
import com.google.gerrit.extensions.common.GpgKeyInfo;
import com.google.gerrit.extensions.restapi.IdString;
import com.google.gerrit.extensions.restapi.RestApiException;
import com.google.gerrit.server.GpgException;
import com.google.gerrit.server.account.AccountResource;
import java.util.List;
import java.util.Map;
public interface GpgApiAdapter {
Map<String, GpgKeyInfo> listGpgKeys(AccountResource account)
throws RestApiException, GpgException;
Map<String, GpgKeyInfo> putGpgKeys(AccountResource account, List<String> add,
List<String> delete) throws RestApiException, GpgException;
GpgKeyApi gpgKey(AccountResource account, IdString idStr)
throws RestApiException, GpgException;
}

View File

@ -23,6 +23,5 @@ public class Module extends FactoryModule {
bind(Accounts.class).to(AccountsImpl.class);
factory(AccountApiImpl.Factory.class);
factory(GpgKeyApiImpl.Factory.class);
}
}

View File

@ -83,7 +83,6 @@ import com.google.gerrit.server.git.NotesBranchUtil;
import com.google.gerrit.server.git.ReceivePackInitializer;
import com.google.gerrit.server.git.TagCache;
import com.google.gerrit.server.git.TransferConfig;
import com.google.gerrit.server.git.gpg.SignedPushModule;
import com.google.gerrit.server.git.validators.CommitValidationListener;
import com.google.gerrit.server.git.validators.CommitValidators;
import com.google.gerrit.server.git.validators.MergeValidationListener;
@ -181,7 +180,6 @@ public class GerritGlobalModule extends FactoryModule {
install(new NoteDbModule());
install(new PrologModule());
install(new SshAddressesModule());
install(new SignedPushModule());
install(ThreadLocalRequestContext.module());
bind(AccountResolver.class);

View File

@ -29,12 +29,12 @@ import com.google.gerrit.extensions.registration.DynamicMap;
import com.google.gerrit.extensions.restapi.RestReadView;
import com.google.gerrit.reviewdb.client.Account;
import com.google.gerrit.reviewdb.client.AuthType;
import com.google.gerrit.server.EnableSignedPush;
import com.google.gerrit.server.account.Realm;
import com.google.gerrit.server.avatar.AvatarProvider;
import com.google.gerrit.server.change.ArchiveFormat;
import com.google.gerrit.server.change.GetArchive;
import com.google.gerrit.server.change.Submit;
import com.google.gerrit.server.git.gpg.SignedPushModule;
import com.google.inject.Inject;
import org.eclipse.jgit.lib.Config;
@ -63,6 +63,7 @@ public class GetServerInfo implements RestReadView<ConfigResource> {
private final String anonymousCowardName;
private final GitwebConfig gitwebConfig;
private final DynamicItem<AvatarProvider> avatar;
private final boolean enableSignedPush;
@Inject
public GetServerInfo(
@ -77,7 +78,8 @@ public class GetServerInfo implements RestReadView<ConfigResource> {
AllUsersName allUsersName,
@AnonymousCowardName String anonymousCowardName,
GitwebConfig gitwebConfig,
DynamicItem<AvatarProvider> avatar) {
DynamicItem<AvatarProvider> avatar,
@EnableSignedPush boolean enableSignedPush) {
this.config = config;
this.authConfig = authConfig;
this.realm = realm;
@ -90,6 +92,7 @@ public class GetServerInfo implements RestReadView<ConfigResource> {
this.anonymousCowardName = anonymousCowardName;
this.gitwebConfig = gitwebConfig;
this.avatar = avatar;
this.enableSignedPush = enableSignedPush;
}
@Override
@ -110,7 +113,7 @@ public class GetServerInfo implements RestReadView<ConfigResource> {
info.urlAliases = !urlAliases.isEmpty() ? urlAliases : null;
info.user = getUserInfo(anonymousCowardName);
info.receive = getReceiveInfo(config);
info.receive = getReceiveInfo();
return info;
}
@ -298,9 +301,9 @@ public class GetServerInfo implements RestReadView<ConfigResource> {
return info;
}
private ReceiveInfo getReceiveInfo(Config cfg) {
private ReceiveInfo getReceiveInfo() {
ReceiveInfo info = new ReceiveInfo();
info.enableSignedPush = SignedPushModule.isEnabled(cfg);
info.enableSignedPush = enableSignedPush;
return info;
}

View File

@ -31,11 +31,8 @@ import com.google.gerrit.server.config.PluginConfigFactory;
import com.google.gerrit.server.config.ProjectConfigEntry;
import com.google.gerrit.server.extensions.webui.UiActions;
import com.google.gerrit.server.git.TransferConfig;
import com.google.gerrit.server.git.gpg.SignedPushModule;
import com.google.inject.util.Providers;
import org.eclipse.jgit.lib.Config;
import java.util.Arrays;
import java.util.List;
import java.util.Map;
@ -58,7 +55,7 @@ public class ConfigInfo {
public Map<String, CommentLinkInfo> commentlinks;
public ThemeInfo theme;
public ConfigInfo(Config gerritConfig,
public ConfigInfo(boolean serverEnableSignedPush,
ProjectControl control,
TransferConfig config,
DynamicMap<ProjectConfigEntry> pluginConfigEntries,
@ -112,7 +109,7 @@ public class ConfigInfo {
this.useContentMerge = useContentMerge;
this.requireChangeId = requireChangeId;
this.createNewChangeForAllNotInTarget = createNewChangeForAllNotInTarget;
if (SignedPushModule.isEnabled(gerritConfig)) {
if (serverEnableSignedPush) {
this.enableSignedPush = enableSignedPush;
}

View File

@ -17,19 +17,17 @@ package com.google.gerrit.server.project;
import com.google.gerrit.extensions.registration.DynamicMap;
import com.google.gerrit.extensions.restapi.RestReadView;
import com.google.gerrit.extensions.restapi.RestView;
import com.google.gerrit.server.EnableSignedPush;
import com.google.gerrit.server.config.AllProjectsNameProvider;
import com.google.gerrit.server.config.GerritServerConfig;
import com.google.gerrit.server.config.PluginConfigFactory;
import com.google.gerrit.server.config.ProjectConfigEntry;
import com.google.gerrit.server.git.TransferConfig;
import com.google.inject.Inject;
import com.google.inject.Singleton;
import org.eclipse.jgit.lib.Config;
@Singleton
public class GetConfig implements RestReadView<ProjectResource> {
private final Config gerritConfig;
private final boolean serverEnableSignedPush;
private final TransferConfig config;
private final DynamicMap<ProjectConfigEntry> pluginConfigEntries;
private final PluginConfigFactory cfgFactory;
@ -37,13 +35,13 @@ public class GetConfig implements RestReadView<ProjectResource> {
private final DynamicMap<RestView<ProjectResource>> views;
@Inject
public GetConfig(@GerritServerConfig Config gerritConfig,
public GetConfig(@EnableSignedPush boolean serverEnableSignedPush,
TransferConfig config,
DynamicMap<ProjectConfigEntry> pluginConfigEntries,
PluginConfigFactory cfgFactory,
AllProjectsNameProvider allProjects,
DynamicMap<RestView<ProjectResource>> views) {
this.gerritConfig = gerritConfig;
this.serverEnableSignedPush = serverEnableSignedPush;
this.config = config;
this.pluginConfigEntries = pluginConfigEntries;
this.allProjects = allProjects;
@ -53,7 +51,7 @@ public class GetConfig implements RestReadView<ProjectResource> {
@Override
public ConfigInfo apply(ProjectResource resource) {
return new ConfigInfo(gerritConfig, resource.getControl(), config,
return new ConfigInfo(serverEnableSignedPush, resource.getControl(), config,
pluginConfigEntries, cfgFactory, allProjects, views);
}
}

View File

@ -31,9 +31,9 @@ import com.google.gerrit.reviewdb.client.Branch;
import com.google.gerrit.reviewdb.client.Project;
import com.google.gerrit.reviewdb.client.RefNames;
import com.google.gerrit.server.CurrentUser;
import com.google.gerrit.server.EnableSignedPush;
import com.google.gerrit.server.IdentifiedUser;
import com.google.gerrit.server.config.AllProjectsNameProvider;
import com.google.gerrit.server.config.GerritServerConfig;
import com.google.gerrit.server.config.PluginConfig;
import com.google.gerrit.server.config.PluginConfigFactory;
import com.google.gerrit.server.config.ProjectConfigEntry;
@ -48,7 +48,6 @@ import com.google.inject.Singleton;
import org.eclipse.jgit.errors.ConfigInvalidException;
import org.eclipse.jgit.errors.RepositoryNotFoundException;
import org.eclipse.jgit.lib.Config;
import org.eclipse.jgit.lib.ObjectId;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
@ -78,7 +77,7 @@ public class PutConfig implements RestModifyView<ProjectResource, Input> {
public Map<String, Map<String, ConfigValue>> pluginConfigValues;
}
private final Config gerritConfig;
private final boolean serverEnableSignedPush;
private final Provider<MetaDataUpdate.User> metaDataUpdateFactory;
private final ProjectCache projectCache;
private final GitRepositoryManager gitMgr;
@ -92,7 +91,7 @@ public class PutConfig implements RestModifyView<ProjectResource, Input> {
private final ChangeHooks hooks;
@Inject
PutConfig(@GerritServerConfig Config gerritConfig,
PutConfig(@EnableSignedPush boolean serverEnableSignedPush,
Provider<MetaDataUpdate.User> metaDataUpdateFactory,
ProjectCache projectCache,
GitRepositoryManager gitMgr,
@ -104,7 +103,7 @@ public class PutConfig implements RestModifyView<ProjectResource, Input> {
DynamicMap<RestView<ProjectResource>> views,
ChangeHooks hooks,
Provider<CurrentUser> currentUser) {
this.gerritConfig = gerritConfig;
this.serverEnableSignedPush = serverEnableSignedPush;
this.metaDataUpdateFactory = metaDataUpdateFactory;
this.projectCache = projectCache;
this.gitMgr = gitMgr;
@ -214,8 +213,9 @@ public class PutConfig implements RestModifyView<ProjectResource, Input> {
}
ProjectState state = projectStateFactory.create(projectConfig);
return new ConfigInfo(gerritConfig, state.controlFor(currentUser.get()),
config, pluginConfigEntries, cfgFactory, allProjects, views);
return new ConfigInfo(serverEnableSignedPush,
state.controlFor(currentUser.get()), config, pluginConfigEntries,
cfgFactory, allProjects, views);
} catch (ConfigInvalidException err) {
throw new ResourceConflictException("Cannot read project " + projectName, err);
} catch (IOException err) {

View File

@ -21,6 +21,7 @@ import com.google.common.util.concurrent.MoreExecutors;
import com.google.gerrit.common.ChangeHooks;
import com.google.gerrit.common.DisabledChangeHooks;
import com.google.gerrit.extensions.config.FactoryModule;
import com.google.gerrit.gpg.GpgModule;
import com.google.gerrit.reviewdb.client.AuthType;
import com.google.gerrit.reviewdb.server.ReviewDb;
import com.google.gerrit.server.GerritPersonIdent;
@ -186,6 +187,7 @@ public class InMemoryModule extends FactoryModule {
install(new DefaultCacheFactory.Module());
install(new FakeEmailSender.Module());
install(new SignedTokenEmailTokenVerifier.Module());
install(new GpgModule(cfg));
IndexType indexType = null;
try {

View File

@ -6,6 +6,7 @@ java_library(
deps = [
'//gerrit-cache-h2:cache-h2',
'//gerrit-extension-api:api',
'//gerrit-gpg:gpg',
'//gerrit-httpd:httpd',
'//gerrit-lucene:lucene',
'//gerrit-oauth:oauth',

View File

@ -19,6 +19,7 @@ import static com.google.inject.Stage.PRODUCTION;
import com.google.common.base.Splitter;
import com.google.gerrit.common.ChangeHookRunner;
import com.google.gerrit.gpg.GpgModule;
import com.google.gerrit.httpd.auth.oauth.OAuthModule;
import com.google.gerrit.httpd.auth.openid.OpenIdModule;
import com.google.gerrit.httpd.plugins.HttpPluginModule;
@ -107,6 +108,7 @@ public class WebAppInitializer extends GuiceServletContextListener
private Path sitePath;
private Injector dbInjector;
private Injector cfgInjector;
private Config config;
private Injector sysInjector;
private Injector webInjector;
private Injector sshInjector;
@ -163,6 +165,8 @@ public class WebAppInitializer extends GuiceServletContextListener
}
cfgInjector = createCfgInjector();
config = cfgInjector.getInstance(
Key.get(Config.class, GerritServerConfig.class));
sysInjector = createSysInjector();
if (!sshdOff()) {
sshInjector = createSshInjector();
@ -202,8 +206,7 @@ public class WebAppInitializer extends GuiceServletContextListener
}
private boolean sshdOff() {
Config cfg = cfgInjector.getInstance(Key.get(Config.class, GerritServerConfig.class));
return new SshAddressesModule().getListenAddresses(cfg).isEmpty();
return new SshAddressesModule().getListenAddresses(config).isEmpty();
}
private Injector createDbInjector() {
@ -294,6 +297,7 @@ public class WebAppInitializer extends GuiceServletContextListener
modules.add(new SignedTokenEmailTokenVerifier.Module());
modules.add(new PluginRestApiModule());
modules.add(new RestCacheAdminModule());
modules.add(new GpgModule(config));
AbstractModule changeIndexModule;
switch (IndexModule.getIndexType(cfgInjector)) {
case LUCENE:

View File

@ -4,6 +4,7 @@ java_library(
name = 'classpath',
deps = LIBS + PGMLIBS + [
'//gerrit-acceptance-tests:lib',
'//gerrit-gpg:gpg_tests',
'//gerrit-gwtdebug:gwtdebug',
'//gerrit-gwtui:ui_module',
'//gerrit-gwtui:ui_tests',