mirror of
https://github.com/pgpainless/pgpainless.git
synced 2024-12-27 13:28:00 +01:00
Allow the user to specify a purpose for encryption
This commit is contained in:
parent
8df752e995
commit
11c41e7ba7
4 changed files with 67 additions and 4 deletions
|
@ -66,12 +66,26 @@ public class PGPainless {
|
|||
|
||||
/**
|
||||
* Create an {@link EncryptionStream}, which can be used to encrypt and/or sign data using OpenPGP.
|
||||
* This method assumes that the stream will be used to encrypt data for communication purposes.
|
||||
* If you instead want to encrypt data that will be saved on disk (eg. a backup), use
|
||||
* {@link #encryptAndOrSign(EncryptionStream.Purpose)} and chose an appropriate purpose.
|
||||
*
|
||||
* @return builder
|
||||
*/
|
||||
public static EncryptionBuilder encryptAndOrSign() {
|
||||
return new EncryptionBuilder();
|
||||
}
|
||||
|
||||
/**
|
||||
* Create an {@link EncryptionStream}, that can be used to encrypt and/or sign data using OpenPGP.
|
||||
*
|
||||
* @param purpose how will the data be used?
|
||||
* @return builder
|
||||
*/
|
||||
public static EncryptionBuilder encryptAndOrSign(EncryptionStream.Purpose purpose) {
|
||||
return new EncryptionBuilder(purpose);
|
||||
}
|
||||
|
||||
/**
|
||||
* Create a {@link DecryptionStream}, which can be used to decrypt and/or verify data using OpenPGP.
|
||||
*
|
||||
|
|
|
@ -37,6 +37,7 @@ import org.bouncycastle.openpgp.PGPSecretKeyRingCollection;
|
|||
import org.bouncycastle.openpgp.operator.PBESecretKeyDecryptor;
|
||||
import org.pgpainless.algorithm.CompressionAlgorithm;
|
||||
import org.pgpainless.algorithm.HashAlgorithm;
|
||||
import org.pgpainless.algorithm.KeyFlag;
|
||||
import org.pgpainless.algorithm.SignatureType;
|
||||
import org.pgpainless.algorithm.SymmetricKeyAlgorithm;
|
||||
import org.pgpainless.exception.SecretKeyNotFoundException;
|
||||
|
@ -55,6 +56,7 @@ import org.pgpainless.util.Passphrase;
|
|||
|
||||
public class EncryptionBuilder implements EncryptionBuilderInterface {
|
||||
|
||||
private final EncryptionStream.Purpose purpose;
|
||||
private OutputStream outputStream;
|
||||
private final Set<PGPPublicKey> encryptionKeys = new HashSet<>();
|
||||
private final Set<Passphrase> encryptionPassphrases = new HashSet<>();
|
||||
|
@ -67,6 +69,14 @@ public class EncryptionBuilder implements EncryptionBuilderInterface {
|
|||
private CompressionAlgorithm compressionAlgorithm = CompressionAlgorithm.UNCOMPRESSED;
|
||||
private boolean asciiArmor = false;
|
||||
|
||||
public EncryptionBuilder() {
|
||||
this.purpose = EncryptionStream.Purpose.COMMUNICATIONS;
|
||||
}
|
||||
|
||||
public EncryptionBuilder(@Nonnull EncryptionStream.Purpose purpose) {
|
||||
this.purpose = purpose;
|
||||
}
|
||||
|
||||
@Override
|
||||
public ToRecipients onOutputStream(@Nonnull OutputStream outputStream) {
|
||||
this.outputStream = outputStream;
|
||||
|
@ -425,9 +435,28 @@ public class EncryptionBuilder implements EncryptionBuilderInterface {
|
|||
}
|
||||
|
||||
PublicKeySelectionStrategy encryptionKeySelector() {
|
||||
KeyFlag[] flags = mapPurposeToKeyFlags(purpose);
|
||||
return new And.PubKeySelectionStrategy(
|
||||
new NoRevocation.PubKeySelectionStrategy(),
|
||||
new EncryptionKeySelectionStrategy());
|
||||
new EncryptionKeySelectionStrategy(flags));
|
||||
}
|
||||
|
||||
private static KeyFlag[] mapPurposeToKeyFlags(EncryptionStream.Purpose purpose) {
|
||||
KeyFlag[] flags;
|
||||
switch (purpose) {
|
||||
case COMMUNICATIONS:
|
||||
flags = new KeyFlag[] {KeyFlag.ENCRYPT_COMMS};
|
||||
break;
|
||||
case STORAGE:
|
||||
flags = new KeyFlag[] {KeyFlag.ENCRYPT_STORAGE};
|
||||
break;
|
||||
case STORAGE_AND_COMMUNICATIONS:
|
||||
flags = new KeyFlag[] {KeyFlag.ENCRYPT_COMMS, KeyFlag.ENCRYPT_STORAGE};
|
||||
break;
|
||||
default:
|
||||
throw new AssertionError("Illegal purpose enum value encountered.");
|
||||
}
|
||||
return flags;
|
||||
}
|
||||
|
||||
SecretKeySelectionStrategy signingKeySelector() {
|
||||
|
|
|
@ -59,6 +59,23 @@ import org.pgpainless.util.Passphrase;
|
|||
*/
|
||||
public final class EncryptionStream extends OutputStream {
|
||||
|
||||
public enum Purpose {
|
||||
/**
|
||||
* The stream will encrypt communication that goes over the wire.
|
||||
* Eg. EMail, Chat...
|
||||
*/
|
||||
COMMUNICATIONS,
|
||||
/**
|
||||
* The stream will encrypt data that is stored on disk.
|
||||
* Eg. Encrypted backup...
|
||||
*/
|
||||
STORAGE,
|
||||
/**
|
||||
* The stream will use keys with either flags to encrypt the data.
|
||||
*/
|
||||
STORAGE_AND_COMMUNICATIONS
|
||||
}
|
||||
|
||||
private static final Logger LOGGER = Logger.getLogger(EncryptionStream.class.getName());
|
||||
private static final Level LEVEL = Level.FINE;
|
||||
|
||||
|
|
|
@ -26,11 +26,14 @@ import org.pgpainless.key.selection.key.PublicKeySelectionStrategy;
|
|||
*/
|
||||
public class EncryptionKeySelectionStrategy extends PublicKeySelectionStrategy {
|
||||
|
||||
private static final HasKeyFlagSelectionStrategy.PublicKey HAS_ENCRYPT_COMMS_FLAG =
|
||||
new HasKeyFlagSelectionStrategy.PublicKey(KeyFlag.ENCRYPT_COMMS);
|
||||
private final HasKeyFlagSelectionStrategy.PublicKey keyFlagSelector;
|
||||
|
||||
public EncryptionKeySelectionStrategy(KeyFlag... flags) {
|
||||
this.keyFlagSelector = new HasKeyFlagSelectionStrategy.PublicKey(flags);
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean accept(@Nonnull PGPPublicKey key) {
|
||||
return key.isEncryptionKey() && HAS_ENCRYPT_COMMS_FLAG.accept(key);
|
||||
return key.isEncryptionKey() && keyFlagSelector.accept(key);
|
||||
}
|
||||
}
|
||||
|
|
Loading…
Reference in a new issue