// Look for transform mode(s)
String transformModes = rawMeta.get(TransformConstants.META_TRANSFORM_MODE);
if(transformModes == null) {
throw new DoesNotNeedRekeyException("Object is not encrypted");
}
// Split
String[] modes = transformModes.split("\\|");
// During decode, we process transforms in reverse order.
List<String> revModes = new ArrayList<String>();
revModes.addAll(Arrays.asList(modes));
Collections.reverse(revModes);
// Process transforms and look for encryption transforms. It's theoretically
// possible for an object to be encrypted more than once...
boolean rekeyed = false;
for(String mode : revModes) {
if(!mode.startsWith(TransformConstants.ENCRYPTION_CLASS)) {
continue;
}
boolean found = false;
for(TransformFactory<?, ?> f : factories) {
if(f instanceof EncryptionTransformFactory<?,?> && f.canDecode(mode, rawMeta)) {
EncryptionTransformFactory<?,?> ef = (EncryptionTransformFactory<?, ?>) f;
try {
rawMeta = ef.rekey(rawMeta);
rekeyed = true;
} catch (DoesNotNeedRekeyException e) {
throw e;
} catch (TransformException e) {
throw new AtmosException("Error rekeying object: " + e, e);
}
found = true;
break;
}
}
if(!found) {
throw new AtmosException("No transformation found to handle '" + mode + "'");
}
}
if(!rekeyed) {
throw new DoesNotNeedRekeyException("Object was not rekeyed");
}
// Update metadata.
Collection<Metadata> updatedMeta = updateMetadata(rawMeta, umeta.values());
delegate.setUserMetadata(identifier, updatedMeta.toArray(new Metadata[updatedMeta.size()]));