Checker for GPG public keys for use in a push certificate.
| 55 | |
| 56 | /** Checker for GPG public keys for use in a push certificate. */ |
| 57 | public class PublicKeyChecker { |
| 58 | private static final FluentLogger logger = FluentLogger.forEnclosingClass(); |
| 59 | |
| 60 | // https://tools.ietf.org/html/rfc4880#section-5.2.3.13 |
| 61 | private static final int COMPLETE_TRUST = 120; |
| 62 | |
| 63 | private PublicKeyStore store; |
| 64 | private Map<Long, Fingerprint> trusted; |
| 65 | private int maxTrustDepth; |
| 66 | private Instant effectiveTime = Instant.now(); |
| 67 | |
| 68 | /** |
| 69 | * Enable web-of-trust checks. |
| 70 | * |
| 71 | * <p>If enabled, a store must be set with {@link #setStore(PublicKeyStore)}. (These methods are |
| 72 | * separate since the store is a closeable resource that may not be available when reading trusted |
| 73 | * keys from a config.) |
| 74 | * |
| 75 | * @param maxTrustDepth maximum depth to search while looking for a trusted key. |
| 76 | * @param trusted ultimately trusted key fingerprints, keyed by fingerprint; may not be empty. To |
| 77 | * construct a map, see {@link Fingerprint#byId(Iterable)}. |
| 78 | * @return a reference to this object. |
| 79 | */ |
| 80 | @CanIgnoreReturnValue |
| 81 | public PublicKeyChecker enableTrust(int maxTrustDepth, Map<Long, Fingerprint> trusted) { |
| 82 | if (maxTrustDepth <= 0) { |
| 83 | throw new IllegalArgumentException("maxTrustDepth must be positive, got: " + maxTrustDepth); |
| 84 | } |
| 85 | if (trusted == null || trusted.isEmpty()) { |
| 86 | throw new IllegalArgumentException("at least one trusted key is required"); |
| 87 | } |
| 88 | this.maxTrustDepth = maxTrustDepth; |
| 89 | this.trusted = trusted; |
| 90 | return this; |
| 91 | } |
| 92 | |
| 93 | /** Disable web-of-trust checks. */ |
| 94 | @CanIgnoreReturnValue |
| 95 | public PublicKeyChecker disableTrust() { |
| 96 | trusted = null; |
| 97 | return this; |
| 98 | } |
| 99 | |
| 100 | /** Set the public key store for reading keys referenced in signatures. */ |
| 101 | @CanIgnoreReturnValue |
| 102 | public PublicKeyChecker setStore(PublicKeyStore store) { |
| 103 | if (store == null) { |
| 104 | throw new IllegalArgumentException("PublicKeyStore is required"); |
| 105 | } |
| 106 | this.store = store; |
| 107 | return this; |
| 108 | } |
| 109 | |
| 110 | /** |
| 111 | * Set the effective time for checking the key. |
| 112 | * |
| 113 | * <p>If set, check whether the key should be considered valid (e.g. unexpired) as of this time. |
| 114 | * |