You are viewing a plain text version of this content. The canonical link for it is here.
Posted to commits@sling.apache.org by je...@apache.org on 2019/08/20 18:16:48 UTC
[sling-whiteboard] 02/03: Minor cleanups
This is an automated email from the ASF dual-hosted git repository.
jeb pushed a commit to branch master
in repository https://gitbox.apache.org/repos/asf/sling-whiteboard.git
commit 56f655bbffa5e59c73170cea727a7740a149c1a0
Author: JE Bailey <ja...@sas.com>
AuthorDate: Fri Aug 16 10:39:59 2019 -0400
Minor cleanups
---
.../resource/encryption/EncryptableValueMap.java | 32 +--
.../resource/encryption/EncryptionException.java | 30 +-
.../resource/encryption/EncryptionProvider.java | 94 +++---
.../sling/resource/encryption/KeyProvider.java | 44 +--
.../encryption/impl/AesGcmEncryptionProvider.java | 265 ++++++++---------
.../encryption/impl/EncryptPostProcessor.java | 84 +++---
.../impl/EncryptableValueMapAdapterFactory.java | 32 +--
.../resource/encryption/impl/JCEKSKeyProvider.java | 190 ++++++------
.../resource/encryption/impl/OSGiKeyProvider.java | 183 ++++++------
.../wrapper/EncryptableValueMapDecorator.java | 280 +++++++++---------
.../encryption/Base64EncryptionProvider.java | 68 ++---
.../resource/encryption/BaseEncryptionTest.java | 320 ++++++++++-----------
.../apache/sling/resource/encryption/Create.java | 42 +--
.../encryption/EncryptionKeyStoreTest.java | 199 +++++++------
.../encryption/EncryptionOSGiStoreTest.java | 197 +++++++------
.../sling/transformer/impl/ProcessManager.java | 3 +-
.../transformer/impl/WebConsoleConfigPrinter.java | 74 -----
17 files changed, 1032 insertions(+), 1105 deletions(-)
diff --git a/encrypt/src/main/java/org/apache/sling/resource/encryption/EncryptableValueMap.java b/encrypt/src/main/java/org/apache/sling/resource/encryption/EncryptableValueMap.java
index 2d2fdce..e89bfc9 100644
--- a/encrypt/src/main/java/org/apache/sling/resource/encryption/EncryptableValueMap.java
+++ b/encrypt/src/main/java/org/apache/sling/resource/encryption/EncryptableValueMap.java
@@ -22,22 +22,22 @@ import org.apache.sling.api.resource.ModifiableValueMap;
*/
public interface EncryptableValueMap extends ModifiableValueMap {
- /**
- * Encrypts and stores the existing property value. Currently supports String
- * and String[]. Values that already encrypted will be re-encrypted.
- *
- * @param name
- * property
- */
- void encrypt(String property);
+ /**
+ * Encrypts and stores the existing property value. Currently supports String
+ * and String[]. Values that already encrypted will be re-encrypted.
+ *
+ * @param name
+ * property
+ */
+ void encrypt(String property);
- /**
- * Decrypts and stores the existing property value . Properties that are not
- * encrypted will not change.
- *
- * @param name
- * property
- */
- void decrypt(String property);
+ /**
+ * Decrypts and stores the existing property value . Properties that are not
+ * encrypted will not change.
+ *
+ * @param name
+ * property
+ */
+ void decrypt(String property);
}
diff --git a/encrypt/src/main/java/org/apache/sling/resource/encryption/EncryptionException.java b/encrypt/src/main/java/org/apache/sling/resource/encryption/EncryptionException.java
index fdece3b..2d46a21 100644
--- a/encrypt/src/main/java/org/apache/sling/resource/encryption/EncryptionException.java
+++ b/encrypt/src/main/java/org/apache/sling/resource/encryption/EncryptionException.java
@@ -16,24 +16,24 @@ package org.apache.sling.resource.encryption;
@SuppressWarnings("serial")
public class EncryptionException extends Exception {
- public EncryptionException() {
- super();
- }
+ public EncryptionException() {
+ super();
+ }
- public EncryptionException(String message, Throwable cause, boolean enableSuppression, boolean writableStackTrace) {
- super(message, cause, enableSuppression, writableStackTrace);
- }
+ public EncryptionException(String message, Throwable cause, boolean enableSuppression, boolean writableStackTrace) {
+ super(message, cause, enableSuppression, writableStackTrace);
+ }
- public EncryptionException(String message, Throwable cause) {
- super(message, cause);
- }
+ public EncryptionException(String message, Throwable cause) {
+ super(message, cause);
+ }
- public EncryptionException(String message) {
- super(message);
- }
+ public EncryptionException(String message) {
+ super(message);
+ }
- public EncryptionException(Throwable cause) {
- super(cause);
- }
+ public EncryptionException(Throwable cause) {
+ super(cause);
+ }
}
diff --git a/encrypt/src/main/java/org/apache/sling/resource/encryption/EncryptionProvider.java b/encrypt/src/main/java/org/apache/sling/resource/encryption/EncryptionProvider.java
index 31c5cc3..1c35a96 100644
--- a/encrypt/src/main/java/org/apache/sling/resource/encryption/EncryptionProvider.java
+++ b/encrypt/src/main/java/org/apache/sling/resource/encryption/EncryptionProvider.java
@@ -25,56 +25,56 @@ package org.apache.sling.resource.encryption;
*/
public interface EncryptionProvider {
- /**
- * Encrypts a byte array
- *
- * @param toEncode
- * @param aad
- * optional additional authentication data
- * @return encrypted byte array
- * @throws EncryptionException
- */
- byte[] encrypt(byte[] toEncode, byte[] aad) throws EncryptionException;
+ /**
+ * Encrypts a byte array
+ *
+ * @param toEncode
+ * @param aad
+ * optional additional authentication data
+ * @return encrypted byte array
+ * @throws EncryptionException
+ */
+ byte[] encrypt(byte[] toEncode, byte[] aad) throws EncryptionException;
- /**
- * Decrypts a previously encrypted byte array
- *
- * @param toDecode
- * @param aad
- * optional additional authentication data
- * @return
- * @throws EncryptionException
- */
- byte[] decrypt(byte[] toDecode, byte[] aad) throws EncryptionException;
+ /**
+ * Decrypts a previously encrypted byte array
+ *
+ * @param toDecode
+ * @param aad
+ * optional additional authentication data
+ * @return
+ * @throws EncryptionException
+ */
+ byte[] decrypt(byte[] toDecode, byte[] aad) throws EncryptionException;
- /**
- * Encrypts a String and returns a String representation of that encoding
- *
- * @param toEncode
- * @param aad
- * optional additional authentication data
- * @return
- * @throws EncryptionException
- */
- String encrypt(String toEncode, String aad) throws EncryptionException;
+ /**
+ * Encrypts a String and returns a String representation of that encoding
+ *
+ * @param toEncode
+ * @param aad
+ * optional additional authentication data
+ * @return
+ * @throws EncryptionException
+ */
+ String encrypt(String toEncode, String aad) throws EncryptionException;
- /**
- * Takes a previously encrypted String and returns the original value
- *
- * @param toDecode
- * @param aad
- * optional additional authentication data
- * @return
- * @throws EncryptionException
- */
- String decrypt(String toDecode, String aad) throws EncryptionException;
+ /**
+ * Takes a previously encrypted String and returns the original value
+ *
+ * @param toDecode
+ * @param aad
+ * optional additional authentication data
+ * @return
+ * @throws EncryptionException
+ */
+ String decrypt(String toDecode, String aad) throws EncryptionException;
- /**
- * Validate whether the String appears to be encrypted
- *
- * @param property
- * @return
- */
- boolean isEncrypted(String property);
+ /**
+ * Validate whether the String appears to be encrypted
+ *
+ * @param property
+ * @return
+ */
+ boolean isEncrypted(String property);
}
diff --git a/encrypt/src/main/java/org/apache/sling/resource/encryption/KeyProvider.java b/encrypt/src/main/java/org/apache/sling/resource/encryption/KeyProvider.java
index c53e7ae..c87f525 100644
--- a/encrypt/src/main/java/org/apache/sling/resource/encryption/KeyProvider.java
+++ b/encrypt/src/main/java/org/apache/sling/resource/encryption/KeyProvider.java
@@ -38,30 +38,30 @@ import java.security.Key;
*/
public interface KeyProvider {
- public static String TYPE = "provider.type";
+ public static String TYPE = "provider.type";
- /**
- * Provides an ID to access the primary encryption key, this ID must be uniquely
- * associated to the key such that no other key that is managed has the same ID
- *
- * @return an array of byte[] of consistent length that
- */
- byte[] getPrimaryKeyID();
+ /**
+ * Provides an ID to access the primary encryption key, this ID must be uniquely
+ * associated to the key such that no other key that is managed has the same ID
+ *
+ * @return an array of byte[] of consistent length that
+ */
+ byte[] getPrimaryKeyID();
- /**
- * ID's are byte arrays of consistent length which uniquely identifies a key
- *
- * @return length of byte[] for ID
- */
- int getIdLength();
+ /**
+ * ID's are byte arrays of consistent length which uniquely identifies a key
+ *
+ * @return length of byte[] for ID
+ */
+ int getIdLength();
- /**
- * Provides the key associated with this ID, either the primary key or one of
- * the maintained secondary keys
- *
- * @param alias
- * @return the requested key, or null if the id does not match an existing key
- */
- Key getKey(byte[] id) throws GeneralSecurityException;
+ /**
+ * Provides the key associated with this ID, either the primary key or one of
+ * the maintained secondary keys
+ *
+ * @param alias
+ * @return the requested key, or null if the id does not match an existing key
+ */
+ Key getKey(byte[] id) throws GeneralSecurityException;
}
diff --git a/encrypt/src/main/java/org/apache/sling/resource/encryption/impl/AesGcmEncryptionProvider.java b/encrypt/src/main/java/org/apache/sling/resource/encryption/impl/AesGcmEncryptionProvider.java
index a2d76e6..5f965db 100644
--- a/encrypt/src/main/java/org/apache/sling/resource/encryption/impl/AesGcmEncryptionProvider.java
+++ b/encrypt/src/main/java/org/apache/sling/resource/encryption/impl/AesGcmEncryptionProvider.java
@@ -15,6 +15,7 @@ package org.apache.sling.resource.encryption.impl;
import java.nio.ByteBuffer;
import java.nio.charset.Charset;
+import java.nio.charset.StandardCharsets;
import java.security.GeneralSecurityException;
import java.security.Key;
import java.security.SecureRandom;
@@ -47,140 +48,140 @@ import org.slf4j.LoggerFactory;
*
*/
@Component(immediate = true, property = { Constants.SERVICE_DESCRIPTION + "=Sling Encryption Service Provider",
- Constants.SERVICE_VENDOR
- + "=The Apache Software Foundation" }, configurationPolicy = ConfigurationPolicy.REQUIRE)
+ Constants.SERVICE_VENDOR
+ + "=The Apache Software Foundation" }, configurationPolicy = ConfigurationPolicy.REQUIRE)
@Designate(ocd = AesGcmEncryptionProvider.Configuration.class)
public class AesGcmEncryptionProvider implements EncryptionProvider {
- @ObjectClassDefinition(name = "Apache Sling Encryption Provider - AES/GCM ")
- public @interface Configuration {
-
- @AttributeDefinition(name = "Key Provider Target", description = "KeyProvider Filter")
- String keyProvider_target() default "(provider.type=KeyStore)";
-
- @AttributeDefinition(name = "Encryption Prefix", description = "Prepends to Encrypted string to identify content that is encrypted")
- String encryptionPrefix() default "\uD83D\uDD12";
-
- }
-
- @Reference(cardinality = ReferenceCardinality.MANDATORY, target = "(name=)")
- public KeyProvider keyProvider;
-
- private SecureRandom random;
-
- private int ivSize;
-
- private static String ALGORITHM = "AES/GCM/NoPadding";
-
- private String id = "\uD83D\uDD12";
-
- private static final Charset UTF8 = Charset.forName("UTF-8");
-
- private static final int GCM_TAG_LENGTH = 128;
-
- /** Default logger. */
- private final Logger logger = LoggerFactory.getLogger(this.getClass());
-
- /**
- * Provides an initial check to make sure that the pieces of the security
- * implementation are present
- *
- * @param config
- * @throws GeneralSecurityException
- */
- @Activate
- @Modified
- public void init(Configuration config) throws GeneralSecurityException {
- Key secretKey = keyProvider.getKey(keyProvider.getPrimaryKeyID());
- Cipher cipher = Cipher.getInstance(ALGORITHM);
- cipher.init(Cipher.ENCRYPT_MODE, secretKey);
- this.random = SecureRandom.getInstance("SHA1PRNG");
- this.ivSize = cipher.getIV().length;
- this.id = config.encryptionPrefix();
- }
-
- private Cipher getCipher(int cipherMode, byte[] iv, byte[] aad, byte[] keyId) throws GeneralSecurityException {
- Key secretKey = keyProvider.getKey(keyId);
- GCMParameterSpec spec = new GCMParameterSpec(GCM_TAG_LENGTH, iv);
- Cipher cipher = Cipher.getInstance(ALGORITHM);
- cipher.init(cipherMode, secretKey, spec);
- cipher.updateAAD(aad);
- return cipher;
- }
-
- private byte[] generateIV() {
- byte[] iv = new byte[ivSize];
- random.nextBytes(iv);
- return iv;
- }
-
- /**
- * Encrypts the byte[] using a random IV which is then prepended to the results.
- */
- @Override
- public byte[] encrypt(byte[] toEncode, byte[] aad) throws EncryptionException {
- byte[] iv = generateIV();
- byte[] keyId = keyProvider.getPrimaryKeyID();
- byte[] byteEncyrpted;
- try {
- byteEncyrpted = getCipher(Cipher.ENCRYPT_MODE, iv, aad, keyId).doFinal(toEncode);
- } catch (Exception e) {
- logger.debug("unable to decrypt {}", e);
- throw new EncryptionException(e);
- }
- ByteBuffer buffer = ByteBuffer.allocate(iv.length + keyId.length + byteEncyrpted.length);
- buffer.put(iv).put(keyId).put(byteEncyrpted);
- return buffer.array();
- }
-
- /**
- * Encryption occurs on the underlying bytes of the String. Before returning the
- * encrypted bytes are converted to a Base64 representation and prepended with
- * an ID to indicate that the String represents an encoded value.
- */
- @Override
- public String encrypt(String value, String aad) throws EncryptionException {
- byte[] encoded = encrypt(value.getBytes(), aad.getBytes(UTF8));
- return id + new String(Base64.getEncoder().encode(encoded), UTF8);
- }
-
- /**
- * Decrypts the supplied byte[] using the the IV that was prepending to the
- * byte[]
- */
- @Override
- public byte[] decrypt(byte[] toDecode, byte[] aad) throws EncryptionException {
- byte[] iv = new byte[ivSize];
- byte[] keyId = new byte[keyProvider.getIdLength()];
- byte[] byteEncrypted = new byte[toDecode.length - (ivSize + keyProvider.getIdLength())];
- ByteBuffer buffer = ByteBuffer.wrap(toDecode);
- buffer.get(iv).get(keyId).get(byteEncrypted);
- try {
- return getCipher(Cipher.DECRYPT_MODE, iv, aad, keyId).doFinal(byteEncrypted);
- } catch (GeneralSecurityException e) {
- throw new EncryptionException(e);
- }
- }
-
- /**
- * Decrypts the String after first removing the prepending ID and decrypting the
- * remaining Base64 encoded byte[]
- */
- @Override
- public String decrypt(String value, String aad) throws EncryptionException {
- byte[] bValue = value.substring(id.length()).getBytes(UTF8);
- byte[] toDecode;
- try {
- toDecode = Base64.getDecoder().decode(bValue);
- } catch (IllegalArgumentException e) {
- throw new EncryptionException("non-encrypted value");
- }
- return new String(decrypt(toDecode, aad.getBytes(UTF8)), UTF8);
- }
-
- @Override
- public boolean isEncrypted(String value) {
- return (value.startsWith(id) && value.length() > id.length() + ivSize);
- }
+ @ObjectClassDefinition(name = "Apache Sling Encryption Provider - AES/GCM ")
+ public @interface Configuration {
+
+ @AttributeDefinition(name = "Key Provider Target", description = "KeyProvider Filter")
+ String keyProvider_target() default "(provider.type=KeyStore)";
+
+ @AttributeDefinition(name = "Encryption Prefix", description = "Prepends to Encrypted string to identify content that is encrypted")
+ String encryptionPrefix() default "\uD83D\uDD12";
+
+ }
+
+ @Reference(cardinality = ReferenceCardinality.MANDATORY, target = "(name=)")
+ public KeyProvider keyProvider;
+
+ private SecureRandom random;
+
+ private int ivSize;
+
+ private static final String ALGORITHM = "AES/GCM/NoPadding";
+
+ private String id = "\uD83D\uDD12";
+
+ private static final Charset UTF8 = StandardCharsets.UTF_8;
+
+ private static final int GCM_TAG_LENGTH = 128;
+
+ /** Default logger. */
+ private final Logger logger = LoggerFactory.getLogger(this.getClass());
+
+ /**
+ * Provides an initial check to make sure that the pieces of the security
+ * implementation are present
+ *
+ * @param config
+ * @throws GeneralSecurityException
+ */
+ @Activate
+ @Modified
+ public void init(Configuration config) throws GeneralSecurityException {
+ Key secretKey = keyProvider.getKey(keyProvider.getPrimaryKeyID());
+ Cipher cipher = Cipher.getInstance(ALGORITHM);
+ cipher.init(Cipher.ENCRYPT_MODE, secretKey);
+ this.random = SecureRandom.getInstance("SHA1PRNG");
+ this.ivSize = cipher.getIV().length;
+ this.id = config.encryptionPrefix();
+ }
+
+ private Cipher getCipher(int cipherMode, byte[] iv, byte[] aad, byte[] keyId) throws GeneralSecurityException {
+ Key secretKey = keyProvider.getKey(keyId);
+ GCMParameterSpec spec = new GCMParameterSpec(GCM_TAG_LENGTH, iv);
+ Cipher cipher = Cipher.getInstance(ALGORITHM);
+ cipher.init(cipherMode, secretKey, spec);
+ cipher.updateAAD(aad);
+ return cipher;
+ }
+
+ private byte[] generateIV() {
+ byte[] iv = new byte[ivSize];
+ random.nextBytes(iv);
+ return iv;
+ }
+
+ /**
+ * Encrypts the byte[] using a random IV which is then prepended to the results.
+ */
+ @Override
+ public byte[] encrypt(byte[] toEncode, byte[] aad) throws EncryptionException {
+ byte[] iv = generateIV();
+ byte[] keyId = keyProvider.getPrimaryKeyID();
+ byte[] byteEncyrpted;
+ try {
+ byteEncyrpted = getCipher(Cipher.ENCRYPT_MODE, iv, aad, keyId).doFinal(toEncode);
+ } catch (Exception e) {
+ logger.debug("unable to decrypt {}", e);
+ throw new EncryptionException(e);
+ }
+ ByteBuffer buffer = ByteBuffer.allocate(iv.length + keyId.length + byteEncyrpted.length);
+ buffer.put(iv).put(keyId).put(byteEncyrpted);
+ return buffer.array();
+ }
+
+ /**
+ * Encryption occurs on the underlying bytes of the String. Before returning the
+ * encrypted bytes are converted to a Base64 representation and prepended with
+ * an ID to indicate that the String represents an encoded value.
+ */
+ @Override
+ public String encrypt(String value, String aad) throws EncryptionException {
+ byte[] encoded = encrypt(value.getBytes(), aad.getBytes(UTF8));
+ return id + new String(Base64.getEncoder().encode(encoded), UTF8);
+ }
+
+ /**
+ * Decrypts the supplied byte[] using the the IV that was prepending to the
+ * byte[]
+ */
+ @Override
+ public byte[] decrypt(byte[] toDecode, byte[] aad) throws EncryptionException {
+ byte[] iv = new byte[ivSize];
+ byte[] keyId = new byte[keyProvider.getIdLength()];
+ byte[] byteEncrypted = new byte[toDecode.length - (ivSize + keyProvider.getIdLength())];
+ ByteBuffer buffer = ByteBuffer.wrap(toDecode);
+ buffer.get(iv).get(keyId).get(byteEncrypted);
+ try {
+ return getCipher(Cipher.DECRYPT_MODE, iv, aad, keyId).doFinal(byteEncrypted);
+ } catch (GeneralSecurityException e) {
+ throw new EncryptionException(e);
+ }
+ }
+
+ /**
+ * Decrypts the String after first removing the prepending ID and decrypting the
+ * remaining Base64 encoded byte[]
+ */
+ @Override
+ public String decrypt(String value, String aad) throws EncryptionException {
+ byte[] bValue = value.substring(id.length()).getBytes(UTF8);
+ byte[] toDecode;
+ try {
+ toDecode = Base64.getDecoder().decode(bValue);
+ } catch (IllegalArgumentException e) {
+ throw new EncryptionException("non-encrypted value");
+ }
+ return new String(decrypt(toDecode, aad.getBytes(UTF8)), UTF8);
+ }
+
+ @Override
+ public boolean isEncrypted(String value) {
+ return (value.startsWith(id) && value.length() > id.length() + ivSize);
+ }
}
diff --git a/encrypt/src/main/java/org/apache/sling/resource/encryption/impl/EncryptPostProcessor.java b/encrypt/src/main/java/org/apache/sling/resource/encryption/impl/EncryptPostProcessor.java
index 1410eb9..866eec7 100644
--- a/encrypt/src/main/java/org/apache/sling/resource/encryption/impl/EncryptPostProcessor.java
+++ b/encrypt/src/main/java/org/apache/sling/resource/encryption/impl/EncryptPostProcessor.java
@@ -40,63 +40,63 @@ import org.slf4j.LoggerFactory;
@Designate(ocd = EncryptPostProcessor.Configuration.class)
public class EncryptPostProcessor implements SlingPostProcessor {
- @ObjectClassDefinition(name = "Apache Sling Encryption Post Processor", description = "Defines options for field encryption")
- public @interface Configuration {
+ @ObjectClassDefinition(name = "Apache Sling Encryption Post Processor", description = "Defines options for field encryption")
+ public @interface Configuration {
- @AttributeDefinition(name = "Suffix", description = "Define the suffix which will uniquely identify a field to be encrypted")
- String suffix() default "@Encrypt";
+ @AttributeDefinition(name = "Suffix", description = "Define the suffix which will uniquely identify a field to be encrypted")
+ String suffix() default "@Encrypt";
- @AttributeDefinition(name = "Inline", description = "Whether the encrypted flag is set on itself or another field")
- boolean inline() default false;
+ @AttributeDefinition(name = "Inline", description = "Whether the encrypted flag is set on itself or another field")
+ boolean inline() default false;
- }
+ }
- @Reference(policyOption = ReferencePolicyOption.GREEDY)
- public EncryptionProvider ep;
+ @Reference(policyOption = ReferencePolicyOption.GREEDY)
+ public EncryptionProvider ep;
- private final Logger logger = LoggerFactory.getLogger(this.getClass());
+ private final Logger logger = LoggerFactory.getLogger(this.getClass());
- private Configuration config;
+ private Configuration config;
- @Override
- public void process(SlingHttpServletRequest slingRequest, List<Modification> modifications) throws Exception {
+ @Override
+ public void process(SlingHttpServletRequest slingRequest, List<Modification> modifications) throws Exception {
- Set<Modification> mods = modifications.stream()
- .filter(modification -> modification.getSource().endsWith(config.suffix())).collect(Collectors.toSet());
+ Set<Modification> mods = modifications.stream()
+ .filter(modification -> modification.getSource().endsWith(config.suffix())).collect(Collectors.toSet());
- if (mods.size() == 0) {
- return;
- }
+ if (mods.isEmpty()) {
+ return;
+ }
- ResourceResolver resolver = slingRequest.getResourceResolver();
- Session session = resolver.adaptTo(Session.class);
+ ResourceResolver resolver = slingRequest.getResourceResolver();
+ Session session = resolver.adaptTo(Session.class);
- for (Modification mod : mods) {
- String encryptPropertyPath = mod.getSource();
+ for (Modification mod : mods) {
+ String encryptPropertyPath = mod.getSource();
- String propertyPath = encryptPropertyPath.substring(0, encryptPropertyPath.lastIndexOf(config.suffix()));
- String resourcePath = propertyPath.substring(0, propertyPath.lastIndexOf('/'));
+ String propertyPath = encryptPropertyPath.substring(0, encryptPropertyPath.lastIndexOf(config.suffix()));
+ String resourcePath = propertyPath.substring(0, propertyPath.lastIndexOf('/'));
- if (config.inline()) {
- session.move(encryptPropertyPath, propertyPath);
- }
-
- EncryptableValueMap map = resolver.resolve(resourcePath).adaptTo(EncryptableValueMap.class);
- map.encrypt(propertyPath.substring(resourcePath.length() + 1, propertyPath.length()));
- session.removeItem(encryptPropertyPath);
- }
+ if (config.inline()) {
+ session.move(encryptPropertyPath, propertyPath);
+ }
- modifications.removeAll(mods);
+ EncryptableValueMap map = resolver.resolve(resourcePath).adaptTo(EncryptableValueMap.class);
+ map.encrypt(propertyPath.substring(resourcePath.length() + 1, propertyPath.length()));
+ session.removeItem(encryptPropertyPath);
+ }
- mods.forEach(mod -> {
- logger.debug("removed {} for source {}", mod.getType().toString(), mod.getSource());
- });
- }
+ modifications.removeAll(mods);
- @Activate
- @Modified
- public void init(Configuration config) {
- this.config = config;
- }
+ mods.forEach(mod -> {
+ logger.debug("removed {} for source {}", mod.getType() , mod.getSource());
+ });
+ }
+
+ @Activate
+ @Modified
+ public void init(Configuration config) {
+ this.config = config;
+ }
}
diff --git a/encrypt/src/main/java/org/apache/sling/resource/encryption/impl/EncryptableValueMapAdapterFactory.java b/encrypt/src/main/java/org/apache/sling/resource/encryption/impl/EncryptableValueMapAdapterFactory.java
index b084f0a..3cd5169 100644
--- a/encrypt/src/main/java/org/apache/sling/resource/encryption/impl/EncryptableValueMapAdapterFactory.java
+++ b/encrypt/src/main/java/org/apache/sling/resource/encryption/impl/EncryptableValueMapAdapterFactory.java
@@ -25,23 +25,23 @@ import org.osgi.service.component.annotations.Reference;
import org.osgi.service.component.annotations.ReferencePolicyOption;
@Component(service = { AdapterFactory.class }, property = {
- Constants.SERVICE_VENDOR + "=The Apache Software Foundation",
- Constants.SERVICE_DESCRIPTION + "=Default SlingScriptResolver",
- org.apache.sling.api.adapter.AdapterFactory.ADAPTABLE_CLASSES + "=org.apache.sling.api.resource.Resource",
- org.apache.sling.api.adapter.AdapterFactory.ADAPTER_CLASSES
- + "=org.apache.sling.resource.encryption.EncryptableValueMap" })
+ Constants.SERVICE_VENDOR + "=The Apache Software Foundation",
+ Constants.SERVICE_DESCRIPTION + "=Default SlingScriptResolver",
+ org.apache.sling.api.adapter.AdapterFactory.ADAPTABLE_CLASSES + "=org.apache.sling.api.resource.Resource",
+ org.apache.sling.api.adapter.AdapterFactory.ADAPTER_CLASSES
+ + "=org.apache.sling.resource.encryption.EncryptableValueMap" })
public class EncryptableValueMapAdapterFactory implements AdapterFactory {
- @Reference(policyOption = ReferencePolicyOption.GREEDY)
- private EncryptionProvider encryptionProvider;
+ @Reference(policyOption = ReferencePolicyOption.GREEDY)
+ private EncryptionProvider encryptionProvider;
- @SuppressWarnings("unchecked")
- @Override
- public <AdapterType> AdapterType getAdapter(Object adaptable, Class<AdapterType> type) {
- ValueMap map = ((Resource)adaptable).adaptTo(ModifiableValueMap.class);
- if (map == null) {
- map = ((Resource)adaptable).adaptTo(ValueMap.class);
- }
- return (AdapterType) new EncryptableValueMapDecorator(map, encryptionProvider);
- }
+ @SuppressWarnings("unchecked")
+ @Override
+ public <T> T getAdapter(Object adaptable, Class<T> type) {
+ ValueMap map = ((Resource) adaptable).adaptTo(ModifiableValueMap.class);
+ if (map == null) {
+ map = ((Resource) adaptable).adaptTo(ValueMap.class);
+ }
+ return (T) new EncryptableValueMapDecorator(map, encryptionProvider);
+ }
}
diff --git a/encrypt/src/main/java/org/apache/sling/resource/encryption/impl/JCEKSKeyProvider.java b/encrypt/src/main/java/org/apache/sling/resource/encryption/impl/JCEKSKeyProvider.java
index 99db981..fa20a4d 100644
--- a/encrypt/src/main/java/org/apache/sling/resource/encryption/impl/JCEKSKeyProvider.java
+++ b/encrypt/src/main/java/org/apache/sling/resource/encryption/impl/JCEKSKeyProvider.java
@@ -16,7 +16,7 @@ package org.apache.sling.resource.encryption.impl;
import java.io.FileInputStream;
import java.io.IOException;
import java.io.InputStream;
-import java.nio.charset.Charset;
+import java.nio.charset.StandardCharsets;
import java.security.GeneralSecurityException;
import java.security.Key;
import java.security.KeyStore;
@@ -34,100 +34,104 @@ import org.osgi.service.metatype.annotations.Designate;
import org.osgi.service.metatype.annotations.ObjectClassDefinition;
@Component(immediate = true, property = { Constants.SERVICE_DESCRIPTION + "=Sling Java Key Store Provisioner",
- Constants.SERVICE_VENDOR + "=The Apache Software Foundation",
- KeyProvider.TYPE + "=KeyStore" }, configurationPolicy = ConfigurationPolicy.REQUIRE)
+ Constants.SERVICE_VENDOR + "=The Apache Software Foundation",
+ KeyProvider.TYPE + "=KeyStore" }, configurationPolicy = ConfigurationPolicy.REQUIRE)
@Designate(ocd = JCEKSKeyProvider.Configuration.class)
public class JCEKSKeyProvider implements KeyProvider {
- @ObjectClassDefinition(name = "Apache Sling Encryption Key Provider - KeyStore", description = "Apache Sling KeyProvider Implementation - KeyStore")
- public @interface Configuration {
-
- @AttributeDefinition(name = "Path", description = "File Location of Key Store")
- String path();
-
- @AttributeDefinition(name = "Password", description = "Password used to access both the store and alias", type = AttributeType.PASSWORD)
- String password();
-
- @AttributeDefinition(name = "Primary", description = "Primary alias stored in the local KeyStore", type = AttributeType.PASSWORD)
- String primaryAlias();
-
- @AttributeDefinition(name = "Secondary", required = false, description = "Secondary aliases that should be used only for decryption", cardinality = Integer.MAX_VALUE)
- String[] secondaryAliases() default {};
-
- }
-
- private Configuration config;
-
- private KeyStore keystore;
-
- private HashMap<Long, String> aliasIds;
-
- private Long primaryId;
-
- @Activate
- public void init(Configuration config) throws GeneralSecurityException, IOException {
- this.config = config;
- // init keystore
- keystore = KeyStore.getInstance("JCEKS");
- InputStream readStream = new FileInputStream(config.path());
- keystore.load(readStream, config.password().toCharArray());
- readStream.close();
-
- aliasIds = new HashMap<>();
- CRC32 crc = new CRC32();
- for (String alias : config.secondaryAliases()) {
- crc.update(alias.getBytes(Charset.forName("UTF-8")));
- Object prior = aliasIds.put(crc.getValue(), alias);
- if (prior != null) {
- throw new GeneralSecurityException("Two aliases are being used that generate the same CRC-32 hash, please correct");
- }
- crc.reset();
- }
-
- crc.update(config.primaryAlias().getBytes(Charset.forName("UTF-8")));
- primaryId = crc.getValue();
- if (aliasIds.containsKey(primaryId)) {
- throw new GeneralSecurityException(String.format("The primary alias %s is either the same as or has the same CRC-32 hash as %s in the secondary aliases, please correct",config.primaryAlias(),aliasIds.get(primaryId)));
- }
-
- aliasIds.put(primaryId, config.primaryAlias());
- crc.reset();
- }
-
- private byte[] toBytes(long value) {
- return new byte[] { (byte) (value >>> 24), (byte) (value >>> 16), (byte) (value >>> 8), (byte) value };
- }
-
- @Override
- public int getIdLength() {
- return 4;
- }
-
- @Override
- public byte[] getPrimaryKeyID() {
- return toBytes(primaryId);
- }
-
- @Override
- public Key getKey(byte[] id) throws GeneralSecurityException {
- Long value = toLong(id);
- String alias = aliasIds.get(value);
- if (alias == null) {
- if (!primaryId.equals(value)) {
- throw new GeneralSecurityException("ID that was provided does not match to any of the currently maintained aliases");
- }
- alias = config.primaryAlias();
- }
- return keystore.getKey(alias, config.password().toCharArray());
- }
-
- private Long toLong(byte[] bytes) {
- long reply = 0;
- for (byte b:bytes) {
- reply = reply << 8;
- reply = reply | (b & 0xff);
- }
- return reply;
- }
+ @ObjectClassDefinition(name = "Apache Sling Encryption Key Provider - KeyStore", description = "Apache Sling KeyProvider Implementation - KeyStore")
+ public @interface Configuration {
+
+ @AttributeDefinition(name = "Path", description = "File Location of Key Store")
+ String path();
+
+ @AttributeDefinition(name = "Password", description = "Password used to access both the store and alias", type = AttributeType.PASSWORD)
+ String password();
+
+ @AttributeDefinition(name = "Primary", description = "Primary alias stored in the local KeyStore", type = AttributeType.PASSWORD)
+ String primaryAlias();
+
+ @AttributeDefinition(name = "Secondary", required = false, description = "Secondary aliases that should be used only for decryption", cardinality = Integer.MAX_VALUE)
+ String[] secondaryAliases() default {};
+
+ }
+
+ private Configuration config;
+
+ private KeyStore keystore;
+
+ private HashMap<Long, String> aliasIds;
+
+ private Long primaryId;
+
+ @Activate
+ public void init(Configuration config) throws GeneralSecurityException, IOException {
+ this.config = config;
+ // init keystore
+ keystore = KeyStore.getInstance("JCEKS");
+ InputStream readStream = new FileInputStream(config.path());
+ keystore.load(readStream, config.password().toCharArray());
+ readStream.close();
+
+ aliasIds = new HashMap<>();
+ CRC32 crc = new CRC32();
+ for (String alias : config.secondaryAliases()) {
+ crc.update(alias.getBytes(StandardCharsets.UTF_8));
+ Object prior = aliasIds.put(crc.getValue(), alias);
+ if (prior != null) {
+ throw new GeneralSecurityException(
+ "Two aliases are being used that generate the same CRC-32 hash, please correct");
+ }
+ crc.reset();
+ }
+
+ crc.update(config.primaryAlias().getBytes(StandardCharsets.UTF_8));
+ primaryId = crc.getValue();
+ if (aliasIds.containsKey(primaryId)) {
+ throw new GeneralSecurityException(String.format(
+ "The primary alias %s is either the same as or has the same CRC-32 hash as %s in the secondary aliases, please correct",
+ config.primaryAlias(), aliasIds.get(primaryId)));
+ }
+
+ aliasIds.put(primaryId, config.primaryAlias());
+ crc.reset();
+ }
+
+ private byte[] toBytes(long value) {
+ return new byte[] { (byte) (value >>> 24), (byte) (value >>> 16), (byte) (value >>> 8), (byte) value };
+ }
+
+ @Override
+ public int getIdLength() {
+ return 4;
+ }
+
+ @Override
+ public byte[] getPrimaryKeyID() {
+ return toBytes(primaryId);
+ }
+
+ @Override
+ public Key getKey(byte[] id) throws GeneralSecurityException {
+ Long value = toLong(id);
+ String alias = aliasIds.get(value);
+ if (alias == null) {
+ if (!primaryId.equals(value)) {
+ throw new GeneralSecurityException(
+ "ID that was provided does not match to any of the currently maintained aliases");
+ }
+ alias = config.primaryAlias();
+ }
+ return keystore.getKey(alias, config.password().toCharArray());
+ }
+
+ private Long toLong(byte[] bytes) {
+ long reply = 0;
+ for (byte b : bytes) {
+ reply = reply << 8;
+ reply = reply | (b & 0xff);
+ }
+ return reply;
+ }
}
diff --git a/encrypt/src/main/java/org/apache/sling/resource/encryption/impl/OSGiKeyProvider.java b/encrypt/src/main/java/org/apache/sling/resource/encryption/impl/OSGiKeyProvider.java
index f004b22..ec3315b 100644
--- a/encrypt/src/main/java/org/apache/sling/resource/encryption/impl/OSGiKeyProvider.java
+++ b/encrypt/src/main/java/org/apache/sling/resource/encryption/impl/OSGiKeyProvider.java
@@ -13,8 +13,7 @@
*/
package org.apache.sling.resource.encryption.impl;
-import java.io.IOException;
-import java.nio.charset.Charset;
+import java.nio.charset.StandardCharsets;
import java.security.GeneralSecurityException;
import java.security.Key;
import java.util.Base64;
@@ -35,96 +34,100 @@ import org.osgi.service.metatype.annotations.ObjectClassDefinition;
import org.osgi.service.metatype.annotations.Option;
@Component(immediate = true, property = { Constants.SERVICE_DESCRIPTION + "=Sling Java Key Store Provisioner",
- Constants.SERVICE_VENDOR + "=The Apache Software Foundation",
- KeyProvider.TYPE + "=OSGi" }, configurationPolicy = ConfigurationPolicy.REQUIRE)
+ Constants.SERVICE_VENDOR + "=The Apache Software Foundation",
+ KeyProvider.TYPE + "=OSGi" }, configurationPolicy = ConfigurationPolicy.REQUIRE)
@Designate(ocd = OSGiKeyProvider.Configuration.class)
public class OSGiKeyProvider implements KeyProvider {
- @ObjectClassDefinition(name = "Apache Sling Encryption Key Provider - OSGi", description = "Apache Sling KeyProvider Implementation - OSGi")
- public @interface Configuration {
-
- @AttributeDefinition(name = "Key Algorithm", description = "Algorithm used to generate the key",options = {@Option(label="AES", value="AES") })
- String keyAlgorithm() default "AES";
-
- @AttributeDefinition(name = "Primary", description = "Base64 encoded primary key", type = AttributeType.PASSWORD)
- String primaryAlias();
-
- @AttributeDefinition(name = "Secondary", required = false, description = "Base 64 encoded secondary keys", cardinality = Integer.MAX_VALUE)
- String[] secondaryAliases() default {};
-
- }
-
-
- private Configuration config;
-
- private HashMap<Long, String> aliasIds;
-
- private Long primaryId;
-
- @Activate
- public void init(Configuration config) throws GeneralSecurityException, IOException {
- this.config = config;
- // init keystore
-
- aliasIds = new HashMap<>();
- CRC32 crc = new CRC32();
- String[] secondaryAlias = config.secondaryAliases();
- if (secondaryAlias == null) {
- secondaryAlias = new String[]{};
- }
- for (String alias : secondaryAlias) {
- crc.update(alias.getBytes(Charset.forName("UTF-8")));
- Object prior = aliasIds.put(crc.getValue() & 0xffff, alias);
- if (prior != null) {
- throw new GeneralSecurityException("Two keys are being used that generate the same CRC-32 hash, please correct");
- }
- crc.reset();
- }
-
- crc.update(config.primaryAlias().getBytes(Charset.forName("UTF-8")));
- primaryId = crc.getValue() & 0xffff;
- if (aliasIds.containsKey(primaryId)) {
- throw new GeneralSecurityException(String.format("The primary key %s is either the same as or has the same CRC-32 hash as %s in the secondary keys, please correct",config.primaryAlias(),aliasIds.get(primaryId)));
- }
-
- aliasIds.put(primaryId, config.primaryAlias());
- crc.reset();
- }
-
- private byte[] toBytes(long value) {
- return new byte[] { (byte) (value >>> 24), (byte) (value >>> 16), (byte) (value >>> 8), (byte) value };
- }
-
- @Override
- public int getIdLength() {
- return 4;
- }
-
- @Override
- public byte[] getPrimaryKeyID() {
- return toBytes(primaryId);
- }
-
- @Override
- public Key getKey(byte[] id) throws GeneralSecurityException {
- Long value = toLong(id);
- String alias = aliasIds.get(value);
- if (alias == null) {
- if (!primaryId.equals(value)) {
- throw new GeneralSecurityException("ID that was provided does not match to any of the currently maintained aliases");
- }
- alias = config.primaryAlias();
- }
- return new SecretKeySpec(Base64.getDecoder().decode(alias.getBytes()), config.keyAlgorithm());
- }
-
- private Long toLong(byte[] bytes) {
- long reply = 0;
- for (byte b:bytes) {
- reply = reply << 8;
- reply = reply | (b & 0xff);
- }
- return reply;
- }
+ @ObjectClassDefinition(name = "Apache Sling Encryption Key Provider - OSGi", description = "Apache Sling KeyProvider Implementation - OSGi")
+ public @interface Configuration {
+
+ @AttributeDefinition(name = "Key Algorithm", description = "Algorithm used to generate the key", options = {
+ @Option(label = "AES", value = "AES") })
+ String keyAlgorithm() default "AES";
+
+ @AttributeDefinition(name = "Primary", description = "Base64 encoded primary key", type = AttributeType.PASSWORD)
+ String primaryAlias();
+
+ @AttributeDefinition(name = "Secondary", required = false, description = "Base 64 encoded secondary keys", cardinality = Integer.MAX_VALUE)
+ String[] secondaryAliases() default {};
+
+ }
+
+ private Configuration config;
+
+ private HashMap<Long, String> aliasIds;
+
+ private Long primaryId;
+
+ @Activate
+ public void init(Configuration config) throws GeneralSecurityException {
+ this.config = config;
+ // init keystore
+
+ aliasIds = new HashMap<>();
+ CRC32 crc = new CRC32();
+ String[] secondaryAlias = config.secondaryAliases();
+ if (secondaryAlias == null) {
+ secondaryAlias = new String[] {};
+ }
+ for (String alias : secondaryAlias) {
+ crc.update(alias.getBytes(StandardCharsets.UTF_8));
+ Object prior = aliasIds.put(crc.getValue() & 0xffff, alias);
+ if (prior != null) {
+ throw new GeneralSecurityException(
+ "Two keys are being used that generate the same CRC-32 hash, please correct");
+ }
+ crc.reset();
+ }
+
+ crc.update(config.primaryAlias().getBytes(StandardCharsets.UTF_8));
+ primaryId = crc.getValue() & 0xffff;
+ if (aliasIds.containsKey(primaryId)) {
+ throw new GeneralSecurityException(String.format(
+ "The primary key %s is either the same as or has the same CRC-32 hash as %s in the secondary keys, please correct",
+ config.primaryAlias(), aliasIds.get(primaryId)));
+ }
+
+ aliasIds.put(primaryId, config.primaryAlias());
+ crc.reset();
+ }
+
+ private byte[] toBytes(long value) {
+ return new byte[] { (byte) (value >>> 24), (byte) (value >>> 16), (byte) (value >>> 8), (byte) value };
+ }
+
+ @Override
+ public int getIdLength() {
+ return 4;
+ }
+
+ @Override
+ public byte[] getPrimaryKeyID() {
+ return toBytes(primaryId);
+ }
+
+ @Override
+ public Key getKey(byte[] id) throws GeneralSecurityException {
+ Long value = toLong(id);
+ String alias = aliasIds.get(value);
+ if (alias == null) {
+ if (!primaryId.equals(value)) {
+ throw new GeneralSecurityException(
+ "ID that was provided does not match to any of the currently maintained aliases");
+ }
+ alias = config.primaryAlias();
+ }
+ return new SecretKeySpec(Base64.getDecoder().decode(alias.getBytes()), config.keyAlgorithm());
+ }
+
+ private Long toLong(byte[] bytes) {
+ long reply = 0;
+ for (byte b : bytes) {
+ reply = reply << 8;
+ reply = reply | (b & 0xff);
+ }
+ return reply;
+ }
}
diff --git a/encrypt/src/main/java/org/apache/sling/resource/encryption/wrapper/EncryptableValueMapDecorator.java b/encrypt/src/main/java/org/apache/sling/resource/encryption/wrapper/EncryptableValueMapDecorator.java
index 7a6cdb2..9d7daec 100644
--- a/encrypt/src/main/java/org/apache/sling/resource/encryption/wrapper/EncryptableValueMapDecorator.java
+++ b/encrypt/src/main/java/org/apache/sling/resource/encryption/wrapper/EncryptableValueMapDecorator.java
@@ -35,145 +35,145 @@ import org.slf4j.LoggerFactory;
* A <code>ValueMap</code> should be immutable.
*/
public class EncryptableValueMapDecorator extends ModifiableValueMapDecorator
- implements ModifiableValueMap, EncryptableValueMap {
-
- private EncryptionProvider ep;
-
- /** Default logger. */
- private final Logger logger = LoggerFactory.getLogger(this.getClass());
-
- public EncryptableValueMapDecorator(Map<String, Object> base, EncryptionProvider encryptionProvider) {
- super(base);
- ep = encryptionProvider;
- }
-
- /**
- * Encrypts the value for this
- *
- * @param property
- * property
- */
- @Nullable
- public void encrypt(String property) {
- super.put(property, doEncrypt(property, get(property)));
- }
-
- /**
- * Sets a String property with the given name as being a non-encrypted property.
- * If a String value currently exists for the property and that value is
- * currently encrypted, that value will be decrypted. Parameters that are
- * already decrypted will not change.
- *
- * @param property
- * The name of the property
- */
- public void decrypt(String property) {
- super.put(property, get(property));
- };
-
- @Override
- public Object get(Object key) {
- Object reply = super.get(key);
- if (isEncrypted(reply)) {
- return doDecrypt((String) key, reply);
- }
- return reply;
- }
-
- @Override
- public Object put(String key, Object value) {
- Object prior = super.put(key, value);
- if (isEncrypted(prior)) {
- super.put(key, doEncrypt(key, value));
- return doDecrypt(key, prior);
- }
- return prior;
- }
-
- /**
- * Method to encrypt an Object value.
- *
- * @param value
- * to be encrypted
- * @return the encrypted value
- */
- @SuppressWarnings("unchecked")
- private <T> T doEncrypt(String property, T value) {
- T reply = null;
-
- if (value instanceof String) {
- try {
- reply = (T) ep.encrypt((String) value, property);
- } catch (EncryptionException e) {
- logger.debug("unable to encrypt value {} of property {}",value, property);
- reply = value;
- }
- }
-
- if (value instanceof String[]) {
- reply = (T) Stream.of((String[]) value).map(string -> {
- try {
- return ep.encrypt(string, property);
- } catch (EncryptionException e) {
- logger.debug("unable to encrypt value {} of property {}",string, property);
- return string;
- }
- }).toArray(String[]::new);
- }
-
- return reply;
- }
-
- /**
- * Decrypt the object
- *
- * @param value
- * String representation of the encrypted value
- * @return decrypted value
- */
- @SuppressWarnings("unchecked")
- private <T> T doDecrypt(String property, T value) {
- T reply = null;
-
- if (value instanceof String) {
- try {
- reply = (T) ep.decrypt((String) value, property);
- } catch (EncryptionException e) {
- logger.debug("unable to decrypt value {} of property {}",value, property);
- reply = value;
- }
- }
-
- if (value instanceof String[]) {
- reply = (T) Stream.of((String[]) value).map(string -> {
- try {
- return ep.decrypt(string, property);
- } catch (EncryptionException e) {
- logger.debug("unable to decrypt value {} of property {}",string, property);
- return string;
- }
- }).toArray(String[]::new);
- }
-
- return reply;
- }
-
- private boolean isEncrypted(Object value) {
- if (value == null) {
- return false;
- }
-
- if (value instanceof String) {
- return ep.isEncrypted((String) value);
- }
-
- if (value instanceof String[]) {
- String[] temp = (String[]) value;
- if (temp.length > 0) {
- return ep.isEncrypted(temp[0]);
- }
- }
- return false;
- }
+ implements ModifiableValueMap, EncryptableValueMap {
+
+ private EncryptionProvider ep;
+
+ /** Default logger. */
+ private final Logger logger = LoggerFactory.getLogger(this.getClass());
+
+ public EncryptableValueMapDecorator(Map<String, Object> base, EncryptionProvider encryptionProvider) {
+ super(base);
+ ep = encryptionProvider;
+ }
+
+ /**
+ * Encrypts the value for this
+ *
+ * @param property
+ * property
+ */
+ @Nullable
+ public void encrypt(String property) {
+ super.put(property, doEncrypt(property, get(property)));
+ }
+
+ /**
+ * Sets a String property with the given name as being a non-encrypted property.
+ * If a String value currently exists for the property and that value is
+ * currently encrypted, that value will be decrypted. Parameters that are
+ * already decrypted will not change.
+ *
+ * @param property
+ * The name of the property
+ */
+ public void decrypt(String property) {
+ super.put(property, get(property));
+ };
+
+ @Override
+ public Object get(Object key) {
+ Object reply = super.get(key);
+ if (isEncrypted(reply)) {
+ return doDecrypt((String) key, reply);
+ }
+ return reply;
+ }
+
+ @Override
+ public Object put(String key, Object value) {
+ Object prior = super.put(key, value);
+ if (isEncrypted(prior)) {
+ super.put(key, doEncrypt(key, value));
+ return doDecrypt(key, prior);
+ }
+ return prior;
+ }
+
+ /**
+ * Method to encrypt an Object value.
+ *
+ * @param value
+ * to be encrypted
+ * @return the encrypted value
+ */
+ @SuppressWarnings("unchecked")
+ private <T> T doEncrypt(String property, T value) {
+ T reply = null;
+
+ if (value instanceof String) {
+ try {
+ reply = (T) ep.encrypt((String) value, property);
+ } catch (EncryptionException e) {
+ logger.debug("unable to encrypt value {} of property {}", value, property);
+ reply = value;
+ }
+ }
+
+ if (value instanceof String[]) {
+ reply = (T) Stream.of((String[]) value).map(string -> {
+ try {
+ return ep.encrypt(string, property);
+ } catch (EncryptionException e) {
+ logger.debug("unable to encrypt value {} of property {}", string, property);
+ return string;
+ }
+ }).toArray(String[]::new);
+ }
+
+ return reply;
+ }
+
+ /**
+ * Decrypt the object
+ *
+ * @param value
+ * String representation of the encrypted value
+ * @return decrypted value
+ */
+ @SuppressWarnings("unchecked")
+ private <T> T doDecrypt(String property, T value) {
+ T reply = null;
+
+ if (value instanceof String) {
+ try {
+ reply = (T) ep.decrypt((String) value, property);
+ } catch (EncryptionException e) {
+ logger.debug("unable to decrypt value {} of property {}", value, property);
+ reply = value;
+ }
+ }
+
+ if (value instanceof String[]) {
+ reply = (T) Stream.of((String[]) value).map(string -> {
+ try {
+ return ep.decrypt(string, property);
+ } catch (EncryptionException e) {
+ logger.debug("unable to decrypt value {} of property {}", string, property);
+ return string;
+ }
+ }).toArray(String[]::new);
+ }
+
+ return reply;
+ }
+
+ private boolean isEncrypted(Object value) {
+ if (value == null) {
+ return false;
+ }
+
+ if (value instanceof String) {
+ return ep.isEncrypted((String) value);
+ }
+
+ if (value instanceof String[]) {
+ String[] temp = (String[]) value;
+ if (temp.length > 0) {
+ return ep.isEncrypted(temp[0]);
+ }
+ }
+ return false;
+ }
}
diff --git a/encrypt/src/test/java/org/apache/sling/resource/encryption/Base64EncryptionProvider.java b/encrypt/src/test/java/org/apache/sling/resource/encryption/Base64EncryptionProvider.java
index 853e700..de0b03c 100644
--- a/encrypt/src/test/java/org/apache/sling/resource/encryption/Base64EncryptionProvider.java
+++ b/encrypt/src/test/java/org/apache/sling/resource/encryption/Base64EncryptionProvider.java
@@ -18,39 +18,39 @@ import java.util.Base64;
public class Base64EncryptionProvider implements EncryptionProvider {
- private static String ID = "|";
-
- @Override
- public byte[] encrypt(byte[] toEncode, byte[] aad) throws EncryptionException {
- return Base64.getEncoder().encode(toEncode);
- }
-
- @Override
- public byte[] decrypt(byte[] toDecode, byte[] aad) throws EncryptionException {
- return Base64.getDecoder().decode(toDecode);
- }
-
- @Override
- public String encrypt(String toEncode, String aad) throws EncryptionException {
- try {
- return ID + new String(encrypt(toEncode.getBytes("UTF-8"), aad.getBytes("UTF-8")),"UTF-8");
- } catch (UnsupportedEncodingException e) {
- throw new EncryptionException(e);
- }
- }
-
- @Override
- public String decrypt(String toDecode, String aad) throws EncryptionException {
- try {
- return new String(decrypt(toDecode.substring(1).getBytes("UTF-8"), aad.getBytes("UTF-8")),"UTF-8");
- } catch (UnsupportedEncodingException e) {
- throw new EncryptionException(e);
- }
- }
-
- @Override
- public boolean isEncrypted(String property) {
- return property.startsWith(ID);
- }
+ private static final String ID = "|";
+
+ @Override
+ public byte[] encrypt(byte[] toEncode, byte[] aad) throws EncryptionException {
+ return Base64.getEncoder().encode(toEncode);
+ }
+
+ @Override
+ public byte[] decrypt(byte[] toDecode, byte[] aad) throws EncryptionException {
+ return Base64.getDecoder().decode(toDecode);
+ }
+
+ @Override
+ public String encrypt(String toEncode, String aad) throws EncryptionException {
+ try {
+ return ID + new String(encrypt(toEncode.getBytes("UTF-8"), aad.getBytes("UTF-8")), "UTF-8");
+ } catch (UnsupportedEncodingException e) {
+ throw new EncryptionException(e);
+ }
+ }
+
+ @Override
+ public String decrypt(String toDecode, String aad) throws EncryptionException {
+ try {
+ return new String(decrypt(toDecode.substring(1).getBytes("UTF-8"), aad.getBytes("UTF-8")), "UTF-8");
+ } catch (UnsupportedEncodingException e) {
+ throw new EncryptionException(e);
+ }
+ }
+
+ @Override
+ public boolean isEncrypted(String property) {
+ return property.startsWith(ID);
+ }
}
diff --git a/encrypt/src/test/java/org/apache/sling/resource/encryption/BaseEncryptionTest.java b/encrypt/src/test/java/org/apache/sling/resource/encryption/BaseEncryptionTest.java
index a9bfb42..4907583 100644
--- a/encrypt/src/test/java/org/apache/sling/resource/encryption/BaseEncryptionTest.java
+++ b/encrypt/src/test/java/org/apache/sling/resource/encryption/BaseEncryptionTest.java
@@ -37,166 +37,164 @@ import org.junit.Test;
public class BaseEncryptionTest {
- @Rule
- public final SlingContext context = new SlingContext();
-
- private static String START_PATH = "/content/sample/en";
-
- private static String ARRAY_PATH = "/content/sample/en/testpage1/jcr:content";
-
- String encryptedProperty;
-
- @SuppressWarnings("serial")
- @Before
- public void setUp()
- throws IOException,GeneralSecurityException {
- context.load().json("/data.json", START_PATH);
- EncryptionProvider cipherProvider = new Base64EncryptionProvider();
- context.registerService(EncryptionProvider.class, cipherProvider);
- EncryptableValueMapAdapterFactory factory = new EncryptableValueMapAdapterFactory();
- injectCipherProvider(factory, cipherProvider);
- context.registerService(AdapterFactory.class, factory, new HashMap<String, Object>() {
- {
- put(AdapterFactory.ADAPTABLE_CLASSES, new String[] { Resource.class.getName() });
- put(AdapterFactory.ADAPTER_CLASSES, new String[] { EncryptableValueMap.class.getName() });
- }
- });
-
- this.encryptedProperty = "bar";
- }
-
- private void injectCipherProvider(EncryptableValueMapAdapterFactory factory, EncryptionProvider cipherProvider) {
- Class<?> resolverClass = factory.getClass();
- java.lang.reflect.Field resolverField;
- try {
- resolverField = resolverClass.getDeclaredField("encryptionProvider");
- resolverField.setAccessible(true);
- resolverField.set(factory, cipherProvider);
- } catch (NoSuchFieldException | SecurityException | IllegalArgumentException | IllegalAccessException e) {
- e.printStackTrace();
- }
-
- }
-
- /**
- * Tests initial access to the EncryptionProvider and that the test provider
- * returns expected results Cipher classes
- *
- * @throws Exception
- */
- @Test
- public void testCipherProvider()
- throws Exception {
- EncryptionProvider cipher = context.getService(EncryptionProvider.class);
- assertNotNull(cipher);
-
- String encrypted = cipher.encrypt(START_PATH, "foo");
- assertNotEquals(START_PATH, encrypted);
- String decoded = cipher.decrypt(encrypted, "foo");
- assertEquals(START_PATH, decoded);
- }
-
- /**
- * Tests encryption and decryption of a String value
- *
- */
- @Test
- public void testUnencryptedString() {
- Resource resource = context.resourceResolver().getResource(START_PATH);
-
- ValueMap map = resource.adaptTo(ValueMap.class);
- EncryptableValueMap encrytionMap = resource.adaptTo(EncryptableValueMap.class);
-
- String property = "jcr:primaryType";
-
- // get original value
- String value = encrytionMap.get(property, String.class);
- assertEquals("app:Page", value);
-
- // encrypt property and validate property appears to be the same
- encrytionMap.encrypt(property);
- value = encrytionMap.get(property, String.class);
- assertEquals("app:Page", value);
-
- // validate the underlying value is encrypted
- value = map.get(property, "fail");
- assertNotEquals("app:Page", value);
- assertNotEquals("fail", value);
-
- // decrypt property and validate the underlying map is back to normal
- encrytionMap.decrypt(property);
- value = map.get(property, String.class);
- assertEquals("app:Page", value);
- }
-
- /**
- * Tests Encodind and Decoding of an array of String values
- *
- * @throws NoSuchPaddingException
- * @throws NoSuchAlgorithmException
- * @throws InvalidKeyException
- */
- @Test
- public void testArrayofValues() {
- Resource resource = context.resourceResolver().getResource(ARRAY_PATH);
-
- ValueMap map = resource.adaptTo(ValueMap.class);
- EncryptableValueMap encrytionMap = resource.adaptTo(EncryptableValueMap.class);
-
- String property = "foo";
-
- // get original values
- String[] value = encrytionMap.get(property, String[].class);
- assertArrayEquals(new String[] { "foo", "dog" }, value);
-
- // encrypt property and verifies it looks good
- encrytionMap.encrypt(property);
- value = encrytionMap.get(property, String[].class);
- assertArrayEquals(new String[] { "foo", "dog" }, value);
-
- //verify underlying map is encrypted
- value = map.get(property, String[].class);
- assertNotEquals("foo", value[0]);
- assertNotEquals("dog", value[1]);
-
- //decrypt the property and validate
- encrytionMap.decrypt(property);
- value = encrytionMap.get(property, String[].class);
- assertArrayEquals(new String[] { "foo", "dog" }, value);
-
- //verify underlying map is decrypted
- value = map.get(property, String[].class);
- assertArrayEquals(new String[] { "foo", "dog" }, value);
-
- }
-
- /**
- * Tests the decryption and handling of pre-existing values
- *
- * @throws NoSuchPaddingException
- * @throws NoSuchAlgorithmException
- * @throws InvalidKeyException
- */
- @Test
- public void testPreEncryptedArrayofValues() {
- Resource resource = context.resourceResolver().getResource(ARRAY_PATH);
-
- ValueMap map = resource.adaptTo(ValueMap.class);
- EncryptableValueMap encryptionMap = resource.adaptTo(EncryptableValueMap.class);
-
- // verify original is encrypted
- String[] value = map.get(encryptedProperty, String[].class);
- assertNotEquals("foo", value[0]);
- assertNotEquals("dog", value[1]);
-
- // get decrypted values and validate
- value = (String[]) encryptionMap.get(encryptedProperty);
- assertArrayEquals(new String[] { "foo", "dog" }, value);
-
- //decrypt pre-encrypted properties
- encryptionMap.decrypt(encryptedProperty);
- value = (String[]) map.get(encryptedProperty);
- assertArrayEquals(new String[] { "foo", "dog" }, value);
- }
+ @Rule
+ public final SlingContext context = new SlingContext();
+
+ private static String START_PATH = "/content/sample/en";
+
+ private static String ARRAY_PATH = "/content/sample/en/testpage1/jcr:content";
+
+ String encryptedProperty;
+
+ @SuppressWarnings("serial")
+ @Before
+ public void setUp() throws IOException, GeneralSecurityException {
+ context.load().json("/data.json", START_PATH);
+ EncryptionProvider cipherProvider = new Base64EncryptionProvider();
+ context.registerService(EncryptionProvider.class, cipherProvider);
+ EncryptableValueMapAdapterFactory factory = new EncryptableValueMapAdapterFactory();
+ injectCipherProvider(factory, cipherProvider);
+ context.registerService(AdapterFactory.class, factory, new HashMap<String, Object>() {
+ {
+ put(AdapterFactory.ADAPTABLE_CLASSES, new String[] { Resource.class.getName() });
+ put(AdapterFactory.ADAPTER_CLASSES, new String[] { EncryptableValueMap.class.getName() });
+ }
+ });
+
+ this.encryptedProperty = "bar";
+ }
+
+ private void injectCipherProvider(EncryptableValueMapAdapterFactory factory, EncryptionProvider cipherProvider) {
+ Class<?> resolverClass = factory.getClass();
+ java.lang.reflect.Field resolverField;
+ try {
+ resolverField = resolverClass.getDeclaredField("encryptionProvider");
+ resolverField.setAccessible(true);
+ resolverField.set(factory, cipherProvider);
+ } catch (NoSuchFieldException | SecurityException | IllegalArgumentException | IllegalAccessException e) {
+ e.printStackTrace();
+ }
+
+ }
+
+ /**
+ * Tests initial access to the EncryptionProvider and that the test provider
+ * returns expected results Cipher classes
+ *
+ * @throws Exception
+ */
+ @Test
+ public void testCipherProvider() throws Exception {
+ EncryptionProvider cipher = context.getService(EncryptionProvider.class);
+ assertNotNull(cipher);
+
+ String encrypted = cipher.encrypt(START_PATH, "foo");
+ assertNotEquals(START_PATH, encrypted);
+ String decoded = cipher.decrypt(encrypted, "foo");
+ assertEquals(START_PATH, decoded);
+ }
+
+ /**
+ * Tests encryption and decryption of a String value
+ *
+ */
+ @Test
+ public void testUnencryptedString() {
+ Resource resource = context.resourceResolver().getResource(START_PATH);
+
+ ValueMap map = resource.adaptTo(ValueMap.class);
+ EncryptableValueMap encrytionMap = resource.adaptTo(EncryptableValueMap.class);
+
+ String property = "jcr:primaryType";
+
+ // get original value
+ String value = encrytionMap.get(property, String.class);
+ assertEquals("app:Page", value);
+
+ // encrypt property and validate property appears to be the same
+ encrytionMap.encrypt(property);
+ value = encrytionMap.get(property, String.class);
+ assertEquals("app:Page", value);
+
+ // validate the underlying value is encrypted
+ value = map.get(property, "fail");
+ assertNotEquals("app:Page", value);
+ assertNotEquals("fail", value);
+
+ // decrypt property and validate the underlying map is back to normal
+ encrytionMap.decrypt(property);
+ value = map.get(property, String.class);
+ assertEquals("app:Page", value);
+ }
+
+ /**
+ * Tests Encodind and Decoding of an array of String values
+ *
+ * @throws NoSuchPaddingException
+ * @throws NoSuchAlgorithmException
+ * @throws InvalidKeyException
+ */
+ @Test
+ public void testArrayofValues() {
+ Resource resource = context.resourceResolver().getResource(ARRAY_PATH);
+
+ ValueMap map = resource.adaptTo(ValueMap.class);
+ EncryptableValueMap encrytionMap = resource.adaptTo(EncryptableValueMap.class);
+
+ String property = "foo";
+
+ // get original values
+ String[] value = encrytionMap.get(property, String[].class);
+ assertArrayEquals(new String[] { "foo", "dog" }, value);
+
+ // encrypt property and verifies it looks good
+ encrytionMap.encrypt(property);
+ value = encrytionMap.get(property, String[].class);
+ assertArrayEquals(new String[] { "foo", "dog" }, value);
+
+ // verify underlying map is encrypted
+ value = map.get(property, String[].class);
+ assertNotEquals("foo", value[0]);
+ assertNotEquals("dog", value[1]);
+
+ // decrypt the property and validate
+ encrytionMap.decrypt(property);
+ value = encrytionMap.get(property, String[].class);
+ assertArrayEquals(new String[] { "foo", "dog" }, value);
+
+ // verify underlying map is decrypted
+ value = map.get(property, String[].class);
+ assertArrayEquals(new String[] { "foo", "dog" }, value);
+
+ }
+
+ /**
+ * Tests the decryption and handling of pre-existing values
+ *
+ * @throws NoSuchPaddingException
+ * @throws NoSuchAlgorithmException
+ * @throws InvalidKeyException
+ */
+ @Test
+ public void testPreEncryptedArrayofValues() {
+ Resource resource = context.resourceResolver().getResource(ARRAY_PATH);
+
+ ValueMap map = resource.adaptTo(ValueMap.class);
+ EncryptableValueMap encryptionMap = resource.adaptTo(EncryptableValueMap.class);
+
+ // verify original is encrypted
+ String[] value = map.get(encryptedProperty, String[].class);
+ assertNotEquals("foo", value[0]);
+ assertNotEquals("dog", value[1]);
+
+ // get decrypted values and validate
+ value = (String[]) encryptionMap.get(encryptedProperty);
+ assertArrayEquals(new String[] { "foo", "dog" }, value);
+
+ // decrypt pre-encrypted properties
+ encryptionMap.decrypt(encryptedProperty);
+ value = (String[]) map.get(encryptedProperty);
+ assertArrayEquals(new String[] { "foo", "dog" }, value);
+ }
}
diff --git a/encrypt/src/test/java/org/apache/sling/resource/encryption/Create.java b/encrypt/src/test/java/org/apache/sling/resource/encryption/Create.java
index a22381f..8ece90d 100644
--- a/encrypt/src/test/java/org/apache/sling/resource/encryption/Create.java
+++ b/encrypt/src/test/java/org/apache/sling/resource/encryption/Create.java
@@ -29,26 +29,26 @@ import javax.crypto.spec.SecretKeySpec;
*/
public class Create {
- private static String KEY_ALGORITHM = "AES";
-
- public static void main(String[] args) throws GeneralSecurityException, IOException {
- KeyStore ks = KeyStore.getInstance("JCEKS");
- ks.load(null);
- char[] password = "secret".toCharArray();
- ks.setKeyEntry("old", getCipher1(),password,(Certificate[])null);
- ks.setKeyEntry("new", getCipher2(),password,(Certificate[])null);
- FileOutputStream writeStream = new FileOutputStream("./src/test/resources/keystore.jks");
- ks.store(writeStream, password);
- writeStream.close();
- System.out.println(new File("./keystore").getAbsolutePath());
- }
-
- private static Key getCipher1() throws GeneralSecurityException {
- return new SecretKeySpec("passwordpassword".getBytes(), KEY_ALGORITHM);
- }
-
- private static Key getCipher2() throws GeneralSecurityException {
- return new SecretKeySpec("password2passwor".getBytes(), KEY_ALGORITHM);
- }
+ private static String KEY_ALGORITHM = "AES";
+
+ public static void main(String[] args) throws GeneralSecurityException, IOException {
+ KeyStore ks = KeyStore.getInstance("JCEKS");
+ ks.load(null);
+ char[] password = "secret".toCharArray();
+ ks.setKeyEntry("old", getCipher1(), password, (Certificate[]) null);
+ ks.setKeyEntry("new", getCipher2(), password, (Certificate[]) null);
+ FileOutputStream writeStream = new FileOutputStream("./src/test/resources/keystore.jks");
+ ks.store(writeStream, password);
+ writeStream.close();
+ System.out.println(new File("./keystore").getAbsolutePath());
+ }
+
+ private static Key getCipher1() throws GeneralSecurityException {
+ return new SecretKeySpec("passwordpassword".getBytes(), KEY_ALGORITHM);
+ }
+
+ private static Key getCipher2() throws GeneralSecurityException {
+ return new SecretKeySpec("password2passwor".getBytes(), KEY_ALGORITHM);
+ }
}
diff --git a/encrypt/src/test/java/org/apache/sling/resource/encryption/EncryptionKeyStoreTest.java b/encrypt/src/test/java/org/apache/sling/resource/encryption/EncryptionKeyStoreTest.java
index d584358..9589692 100644
--- a/encrypt/src/test/java/org/apache/sling/resource/encryption/EncryptionKeyStoreTest.java
+++ b/encrypt/src/test/java/org/apache/sling/resource/encryption/EncryptionKeyStoreTest.java
@@ -30,104 +30,103 @@ import org.junit.Before;
public class EncryptionKeyStoreTest extends BaseEncryptionTest {
- private static String START_PATH = "/content/sample/en";
-
- @SuppressWarnings("serial")
- @Before
- public synchronized void setUp()
- throws GeneralSecurityException, IOException {
-
- context.load().json("/data2.json", START_PATH);
-
- JCEKSKeyProvider kp = new JCEKSKeyProvider();
- kp.init(getConfig());
-
- AesGcmEncryptionProvider encryptionProvider = new AesGcmEncryptionProvider();
- injectKeyProvider(encryptionProvider, kp);
- encryptionProvider.init(new Configuration() {
-
- @Override
- public Class<? extends Annotation> annotationType() {
- // TODO Auto-generated method stub
- return null;
- }
-
- @Override
- public String keyProvider_target() {
- return null;
- }
-
- @Override
- public String encryptionPrefix() {
- return "\uD83D\uDD12";
- }
- });
-
- context.registerService(EncryptionProvider.class, encryptionProvider);
-
-
- context.registerService(AdapterFactory.class, adapterFactory(encryptionProvider), new HashMap<String, Object>() {
- {
- put(AdapterFactory.ADAPTABLE_CLASSES, new String[] { Resource.class.getName() });
- put(AdapterFactory.ADAPTER_CLASSES, new String[] { EncryptableValueMap.class.getName() });
- }
- });
- this.encryptedProperty = "bar";
- }
-
- private AdapterFactory adapterFactory(EncryptionProvider ep) {
- return new AdapterFactory() {
- @SuppressWarnings("unchecked")
- public <AdapterType> AdapterType getAdapter(Object adaptable, Class<AdapterType> type) {
- ValueMap map = ((Resource) adaptable).adaptTo(ModifiableValueMap.class);
- if (map == null) {
- map = ((Resource) adaptable).adaptTo(ValueMap.class);
- }
- return (AdapterType) new EncryptableValueMapDecorator(map, ep);
- }
- };
- }
-
- private void injectKeyProvider(EncryptionProvider ep, KeyProvider key) {
- Class<?> resolverClass = ep.getClass();
- java.lang.reflect.Field resolverField;
- try {
- resolverField = resolverClass.getDeclaredField("keyProvider");
- resolverField.setAccessible(true);
- resolverField.set(ep, key);
- } catch (NoSuchFieldException | SecurityException | IllegalArgumentException | IllegalAccessException e) {
- e.printStackTrace();
- }
-
- }
-
- private JCEKSKeyProvider.Configuration getConfig(){
- return new JCEKSKeyProvider.Configuration() {
-
- @Override
- public Class<? extends Annotation> annotationType() {
- // TODO Auto-generated method stub
- return null;
- }
-
- @Override
- public String path() {
- return "./src/test/resources/keystore.jks";
- }
-
- @Override
- public String password() {
- return "secret";
- }
-
- @Override
- public String primaryAlias() {
- return "new";
- }
-
- @Override
- public String[] secondaryAliases() {
- return new String[] {"old"};
- }};
- }
+ private static String START_PATH = "/content/sample/en";
+
+ @SuppressWarnings("serial")
+ @Before
+ public synchronized void setUp() throws GeneralSecurityException, IOException {
+
+ context.load().json("/data2.json", START_PATH);
+
+ JCEKSKeyProvider kp = new JCEKSKeyProvider();
+ kp.init(getConfig());
+
+ AesGcmEncryptionProvider encryptionProvider = new AesGcmEncryptionProvider();
+ injectKeyProvider(encryptionProvider, kp);
+ encryptionProvider.init(new Configuration() {
+
+ @Override
+ public Class<? extends Annotation> annotationType() {
+ return null;
+ }
+
+ @Override
+ public String keyProvider_target() {
+ return null;
+ }
+
+ @Override
+ public String encryptionPrefix() {
+ return "\uD83D\uDD12";
+ }
+ });
+
+ context.registerService(EncryptionProvider.class, encryptionProvider);
+
+ context.registerService(AdapterFactory.class, adapterFactory(encryptionProvider),
+ new HashMap<String, Object>() {
+ {
+ put(AdapterFactory.ADAPTABLE_CLASSES, new String[] { Resource.class.getName() });
+ put(AdapterFactory.ADAPTER_CLASSES, new String[] { EncryptableValueMap.class.getName() });
+ }
+ });
+ this.encryptedProperty = "bar";
+ }
+
+ private AdapterFactory adapterFactory(EncryptionProvider ep) {
+ return new AdapterFactory() {
+ @SuppressWarnings("unchecked")
+ public <AdapterType> AdapterType getAdapter(Object adaptable, Class<AdapterType> type) {
+ ValueMap map = ((Resource) adaptable).adaptTo(ModifiableValueMap.class);
+ if (map == null) {
+ map = ((Resource) adaptable).adaptTo(ValueMap.class);
+ }
+ return (AdapterType) new EncryptableValueMapDecorator(map, ep);
+ }
+ };
+ }
+
+ private void injectKeyProvider(EncryptionProvider ep, KeyProvider key) {
+ Class<?> resolverClass = ep.getClass();
+ java.lang.reflect.Field resolverField;
+ try {
+ resolverField = resolverClass.getDeclaredField("keyProvider");
+ resolverField.setAccessible(true);
+ resolverField.set(ep, key);
+ } catch (NoSuchFieldException | SecurityException | IllegalArgumentException | IllegalAccessException e) {
+ e.printStackTrace();
+ }
+
+ }
+
+ private JCEKSKeyProvider.Configuration getConfig() {
+ return new JCEKSKeyProvider.Configuration() {
+
+ @Override
+ public Class<? extends Annotation> annotationType() {
+ // TODO Auto-generated method stub
+ return null;
+ }
+
+ @Override
+ public String path() {
+ return "./src/test/resources/keystore.jks";
+ }
+
+ @Override
+ public String password() {
+ return "secret";
+ }
+
+ @Override
+ public String primaryAlias() {
+ return "new";
+ }
+
+ @Override
+ public String[] secondaryAliases() {
+ return new String[] { "old" };
+ }
+ };
+ }
}
diff --git a/encrypt/src/test/java/org/apache/sling/resource/encryption/EncryptionOSGiStoreTest.java b/encrypt/src/test/java/org/apache/sling/resource/encryption/EncryptionOSGiStoreTest.java
index 4a6308c..50363c9 100644
--- a/encrypt/src/test/java/org/apache/sling/resource/encryption/EncryptionOSGiStoreTest.java
+++ b/encrypt/src/test/java/org/apache/sling/resource/encryption/EncryptionOSGiStoreTest.java
@@ -15,7 +15,6 @@ package org.apache.sling.resource.encryption;
import static org.junit.Assert.assertTrue;
-import java.io.IOException;
import java.lang.annotation.Annotation;
import java.security.GeneralSecurityException;
import java.util.HashMap;
@@ -32,103 +31,101 @@ import org.junit.Before;
public class EncryptionOSGiStoreTest extends BaseEncryptionTest {
- private static String START_PATH = "/content/sample/en";
-
- @SuppressWarnings("serial")
- @Before
- public synchronized void setUp() {
-
- context.load().json("/data3.json", START_PATH);
- AesGcmEncryptionProvider encryptionProvider = new AesGcmEncryptionProvider();
- OSGiKeyProvider kp = new OSGiKeyProvider();
- try {
-
- kp.init(getConfig());
-
- injectKeyProvider(encryptionProvider, kp);
- encryptionProvider.init(new Configuration() {
-
- @Override
- public Class<? extends Annotation> annotationType() {
- // TODO Auto-generated method stub
- return null;
- }
-
- @Override
- public String keyProvider_target() {
- return null;
- }
-
- @Override
- public String encryptionPrefix() {
- return "\uD83D\uDD12";
- }
- });
-
- } catch (NullPointerException | GeneralSecurityException | IOException e) {
- assertTrue(false);
- }
- context.registerService(EncryptionProvider.class, encryptionProvider);
-
- context.registerService(AdapterFactory.class, adapterFactory(encryptionProvider),
- new HashMap<String, Object>() {
- {
- put(AdapterFactory.ADAPTABLE_CLASSES, new String[] { Resource.class.getName() });
- put(AdapterFactory.ADAPTER_CLASSES, new String[] { EncryptableValueMap.class.getName() });
- }
- });
- this.encryptedProperty = "cat";
- }
-
- private AdapterFactory adapterFactory(EncryptionProvider ep) {
- return new AdapterFactory() {
- @SuppressWarnings("unchecked")
- public <AdapterType> AdapterType getAdapter(Object adaptable, Class<AdapterType> type) {
- ValueMap map = ((Resource) adaptable).adaptTo(ModifiableValueMap.class);
- if (map == null) {
- map = ((Resource) adaptable).adaptTo(ValueMap.class);
- }
- return (AdapterType) new EncryptableValueMapDecorator(map, ep);
- }
- };
- }
-
- private void injectKeyProvider(EncryptionProvider ep, KeyProvider key) {
- Class<?> resolverClass = ep.getClass();
- java.lang.reflect.Field resolverField;
- try {
- resolverField = resolverClass.getDeclaredField("keyProvider");
- resolverField.setAccessible(true);
- resolverField.set(ep, key);
- } catch (NoSuchFieldException | SecurityException | IllegalArgumentException | IllegalAccessException e) {
- e.printStackTrace();
- }
-
- }
-
- private OSGiKeyProvider.Configuration getConfig() {
- return new OSGiKeyProvider.Configuration() {
-
- @Override
- public Class<? extends Annotation> annotationType() {
- // TODO Auto-generated method stub
- return null;
- }
-
- @Override
- public String keyAlgorithm() {
- return "AES";
- }
-
- @Override
- public String primaryAlias() {
- return "cGFzc3dvcmRwYXNzd29yZA==";
- }
-
- @Override
- public String[] secondaryAliases() {
- return new String[] {};
- }
- };
- }
+ private static String START_PATH = "/content/sample/en";
+
+ @SuppressWarnings("serial")
+ @Before
+ public synchronized void setUp() {
+
+ context.load().json("/data3.json", START_PATH);
+ AesGcmEncryptionProvider encryptionProvider = new AesGcmEncryptionProvider();
+ OSGiKeyProvider kp = new OSGiKeyProvider();
+ try {
+
+ kp.init(getConfig());
+
+ injectKeyProvider(encryptionProvider, kp);
+ encryptionProvider.init(new Configuration() {
+
+ @Override
+ public Class<? extends Annotation> annotationType() {
+ return null;
+ }
+
+ @Override
+ public String keyProvider_target() {
+ return null;
+ }
+
+ @Override
+ public String encryptionPrefix() {
+ return "\uD83D\uDD12";
+ }
+ });
+
+ } catch (NullPointerException | GeneralSecurityException e) {
+ assertTrue(false);
+ }
+ context.registerService(EncryptionProvider.class, encryptionProvider);
+
+ context.registerService(AdapterFactory.class, adapterFactory(encryptionProvider),
+ new HashMap<String, Object>() {
+ {
+ put(AdapterFactory.ADAPTABLE_CLASSES, new String[] { Resource.class.getName() });
+ put(AdapterFactory.ADAPTER_CLASSES, new String[] { EncryptableValueMap.class.getName() });
+ }
+ });
+ this.encryptedProperty = "cat";
+ }
+
+ private AdapterFactory adapterFactory(EncryptionProvider ep) {
+ return new AdapterFactory() {
+ @SuppressWarnings("unchecked")
+ public <AdapterType> AdapterType getAdapter(Object adaptable, Class<AdapterType> type) {
+ ValueMap map = ((Resource) adaptable).adaptTo(ModifiableValueMap.class);
+ if (map == null) {
+ map = ((Resource) adaptable).adaptTo(ValueMap.class);
+ }
+ return (AdapterType) new EncryptableValueMapDecorator(map, ep);
+ }
+ };
+ }
+
+ private void injectKeyProvider(EncryptionProvider ep, KeyProvider key) {
+ Class<?> resolverClass = ep.getClass();
+ java.lang.reflect.Field resolverField;
+ try {
+ resolverField = resolverClass.getDeclaredField("keyProvider");
+ resolverField.setAccessible(true);
+ resolverField.set(ep, key);
+ } catch (NoSuchFieldException | SecurityException | IllegalArgumentException | IllegalAccessException e) {
+ e.printStackTrace();
+ }
+
+ }
+
+ private OSGiKeyProvider.Configuration getConfig() {
+ return new OSGiKeyProvider.Configuration() {
+
+ @Override
+ public Class<? extends Annotation> annotationType() {
+ return null;
+ }
+
+ @Override
+ public String keyAlgorithm() {
+ return "AES";
+ }
+
+ @Override
+ public String primaryAlias() {
+ return "cGFzc3dvcmRwYXNzd29yZA==";
+ }
+
+ @Override
+ public String[] secondaryAliases() {
+ return new String[] {};
+ }
+ };
+ }
}
diff --git a/transformer/src/main/java/org/apache/sling/transformer/impl/ProcessManager.java b/transformer/src/main/java/org/apache/sling/transformer/impl/ProcessManager.java
index 61cb16e..d36a879 100644
--- a/transformer/src/main/java/org/apache/sling/transformer/impl/ProcessManager.java
+++ b/transformer/src/main/java/org/apache/sling/transformer/impl/ProcessManager.java
@@ -9,8 +9,7 @@ import org.osgi.service.component.annotations.Reference;
public class ProcessManager {
- @Reference
- private Process processes;
+
@Reference
void bindProcess(Process process, Map<String, ?> properties) {
diff --git a/transformer/src/main/java/org/apache/sling/transformer/impl/WebConsoleConfigPrinter.java b/transformer/src/main/java/org/apache/sling/transformer/impl/WebConsoleConfigPrinter.java
deleted file mode 100644
index 69897f0..0000000
--- a/transformer/src/main/java/org/apache/sling/transformer/impl/WebConsoleConfigPrinter.java
+++ /dev/null
@@ -1,74 +0,0 @@
-/*
- * Licensed to the Apache Software Foundation (ASF) under one
- * or more contributor license agreements. See the NOTICE file
- * distributed with this work for additional information
- * regarding copyright ownership. The ASF licenses this file
- * to you 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 org.apache.sling.transformer.impl;
-
-import java.io.PrintWriter;
-import java.util.Dictionary;
-import java.util.Hashtable;
-
-import org.osgi.framework.BundleContext;
-import org.osgi.framework.Constants;
-import org.osgi.framework.ServiceRegistration;
-
-/**
- * This is a configuration printer for the web console which
- * prints out the currently configured processors/pipelines.
- *
- */
-public class WebConsoleConfigPrinter {
-
- final ProcessorManagerImpl manager;
-
- private static ServiceRegistration REG;
-
- public WebConsoleConfigPrinter(final ProcessorManagerImpl manager) {
- this.manager = manager;
- }
-
- public static void register(final BundleContext bundleContext,
- final ProcessorManagerImpl manager) {
- final WebConsoleConfigPrinter printer = new WebConsoleConfigPrinter(manager);
- final Dictionary<String, String> serviceProps = new Hashtable<String, String>();
- serviceProps.put(Constants.SERVICE_DESCRIPTION,
- "Apache Sling Rewriter Configuration Printer");
- serviceProps.put(Constants.SERVICE_VENDOR, "The Apache Software Foundation");
- serviceProps.put("felix.webconsole.label", "slingrewriter");
- serviceProps.put("felix.webconsole.title", "Sling Rewriter");
- serviceProps.put("felix.webconsole.configprinter.modes", "always");
-
- REG = bundleContext.registerService(WebConsoleConfigPrinter.class.getName(),
- printer,
- serviceProps);
- }
-
- public static void unregister() {
- if ( REG != null) {
- REG.unregister();
- REG = null;
- }
- }
-
- /**
- * Print out the rewriter configs.
- * See org.apache.felix.webconsole.ConfigurationPrinter#printConfiguration(java.io.PrintWriter).
- */
- public void printConfiguration(PrintWriter pw) {
- this.manager.printConfiguration(pw);
- }
-}