use of com.quorum.tessera.encryption.PublicKey in project tessera by ConsenSys.
the class EncodedPayloadManagerImpl method create.
@Override
public EncodedPayload create(final SendRequest request) {
final PublicKey senderPublicKey = request.getSender();
LOGGER.debug("Sender for payload: {}", request.getSender().encodeToBase64());
final Set<PublicKey> recipientSet = new HashSet<>();
recipientSet.add(senderPublicKey);
recipientSet.addAll(request.getRecipients());
recipientSet.addAll(enclave.getForwardingKeys());
final List<PublicKey> recipientListNoDuplicate = new ArrayList<>(recipientSet);
LOGGER.debug("Recipients for payload: {}", recipientListNoDuplicate);
final PrivacyMode privacyMode = request.getPrivacyMode();
LOGGER.debug("Privacy mode for payload: {}", request.getPrivacyMode());
LOGGER.debug("ExecHash for payload: {}", new String(request.getExecHash()));
final Set<PublicKey> mandatoryRecipients = request.getMandatoryRecipients();
LOGGER.debug("Mandatory recipients for payload: {}", mandatoryRecipients);
final List<AffectedTransaction> affectedContractTransactions = privacyHelper.findAffectedContractTransactionsFromSendRequest(request.getAffectedContractTransactions());
LOGGER.debug("Validating request against affected contracts");
privacyHelper.validateSendRequest(privacyMode, recipientListNoDuplicate, affectedContractTransactions, mandatoryRecipients);
LOGGER.debug("Successful validation against affected contracts");
final PrivacyMetadata.Builder metaDataBuilder = PrivacyMetadata.Builder.create().withPrivacyMode(privacyMode).withAffectedTransactions(affectedContractTransactions).withExecHash(request.getExecHash());
request.getPrivacyGroupId().ifPresent(metaDataBuilder::withPrivacyGroupId);
return enclave.encryptPayload(request.getPayload(), senderPublicKey, recipientListNoDuplicate, metaDataBuilder.build());
}
use of com.quorum.tessera.encryption.PublicKey in project tessera by ConsenSys.
the class EncodedPayloadManagerImpl method decrypt.
@Override
public ReceiveResponse decrypt(final EncodedPayload payload, final PublicKey maybeDefaultRecipient) {
final MessageHash customPayloadHash = new MessageHash(payloadDigest.digest(payload.getCipherText()));
LOGGER.debug("Decrypt request for custom message with hash {}", customPayloadHash);
final PublicKey recipientKey = Optional.ofNullable(maybeDefaultRecipient).orElseGet(() -> searchForRecipientKey(payload).orElseThrow(() -> new RecipientKeyNotFoundException("No suitable recipient keys found to decrypt payload for " + customPayloadHash)));
LOGGER.debug("Decryption key found: {}", recipientKey.encodeToBase64());
final byte[] decryptedTransactionData = enclave.unencryptTransaction(payload, recipientKey);
final Set<MessageHash> affectedTransaction = payload.getAffectedContractTransactions().keySet().stream().map(TxHash::getBytes).map(MessageHash::new).collect(Collectors.toSet());
ReceiveResponse.Builder builder = ReceiveResponse.Builder.create().withUnencryptedTransactionData(decryptedTransactionData).withPrivacyMode(payload.getPrivacyMode()).withAffectedTransactions(affectedTransaction).withExecHash(payload.getExecHash()).withSender(payload.getSenderKey());
payload.getPrivacyGroupId().ifPresent(builder::withPrivacyGroupId);
return builder.build();
}
use of com.quorum.tessera.encryption.PublicKey in project tessera by ConsenSys.
the class EncodedPayloadManagerImpl method searchForRecipientKey.
private Optional<PublicKey> searchForRecipientKey(final EncodedPayload payload) {
final MessageHash customPayloadHash = new MessageHash(payloadDigest.digest(payload.getCipherText()));
for (final PublicKey potentialMatchingKey : enclave.getPublicKeys()) {
try {
LOGGER.debug("Attempting to decrypt {} using key {}", customPayloadHash, potentialMatchingKey.encodeToBase64());
enclave.unencryptTransaction(payload, potentialMatchingKey);
LOGGER.debug("Succeeded decrypting {} using key {}", customPayloadHash, potentialMatchingKey.encodeToBase64());
return Optional.of(potentialMatchingKey);
} catch (EnclaveException | IndexOutOfBoundsException | EncryptorException ex) {
LOGGER.debug("Attempted payload decryption using wrong key, discarding.");
}
}
return Optional.empty();
}
use of com.quorum.tessera.encryption.PublicKey in project tessera by ConsenSys.
the class TransactionManagerImpl method send.
@Override
public SendResponse send(SendRequest sendRequest) {
final PublicKey senderPublicKey = sendRequest.getSender();
final List<PublicKey> recipientList = new ArrayList<>(sendRequest.getRecipients());
recipientList.add(senderPublicKey);
recipientList.addAll(enclave.getForwardingKeys());
final List<PublicKey> recipientListNoDuplicate = recipientList.stream().distinct().collect(Collectors.toList());
final byte[] raw = sendRequest.getPayload();
final PrivacyMode privacyMode = sendRequest.getPrivacyMode();
final byte[] execHash = sendRequest.getExecHash();
final List<AffectedTransaction> affectedContractTransactions = privacyHelper.findAffectedContractTransactionsFromSendRequest(sendRequest.getAffectedContractTransactions());
privacyHelper.validateSendRequest(privacyMode, recipientList, affectedContractTransactions, sendRequest.getMandatoryRecipients());
final PrivacyMetadata.Builder metadataBuilder = PrivacyMetadata.Builder.create().withPrivacyMode(privacyMode).withAffectedTransactions(affectedContractTransactions).withExecHash(execHash).withMandatoryRecipients(sendRequest.getMandatoryRecipients());
sendRequest.getPrivacyGroupId().ifPresent(metadataBuilder::withPrivacyGroupId);
final EncodedPayload payload = enclave.encryptPayload(raw, senderPublicKey, recipientListNoDuplicate, metadataBuilder.build());
final MessageHash transactionHash = Optional.of(payload).map(EncodedPayload::getCipherText).map(payloadDigest::digest).map(MessageHash::new).get();
final EncryptedTransaction newTransaction = new EncryptedTransaction(transactionHash, payload);
final Set<PublicKey> managedPublicKeys = enclave.getPublicKeys();
final Set<PublicKey> managedParties = Stream.concat(Stream.of(senderPublicKey), recipientListNoDuplicate.stream()).filter(managedPublicKeys::contains).collect(Collectors.toSet());
final List<PublicKey> recipientListRemotesOnly = recipientListNoDuplicate.stream().filter(not(managedPublicKeys::contains)).collect(Collectors.toList());
this.encryptedTransactionDAO.save(newTransaction, () -> {
batchPayloadPublisher.publishPayload(payload, recipientListRemotesOnly);
return null;
});
return SendResponse.Builder.create().withMessageHash(transactionHash).withManagedParties(managedParties).withSender(payload.getSenderKey()).build();
}
use of com.quorum.tessera.encryption.PublicKey in project tessera by ConsenSys.
the class TransactionManagerImpl method receive.
@Override
public ReceiveResponse receive(ReceiveRequest request) {
final MessageHash hash = request.getTransactionHash();
LOGGER.info("Lookup transaction {}", hash);
if (request.isRaw()) {
final EncryptedRawTransaction encryptedRawTransaction = encryptedRawTransactionDAO.retrieveByHash(hash).orElseThrow(() -> new TransactionNotFoundException("Raw Message with hash " + hash + " was not found"));
final PublicKey senderKey = PublicKey.from(encryptedRawTransaction.getSender());
final RawTransaction rawTransaction = new RawTransaction(encryptedRawTransaction.getEncryptedPayload(), encryptedRawTransaction.getEncryptedKey(), new Nonce(encryptedRawTransaction.getNonce()), senderKey);
final byte[] response = enclave.unencryptRawPayload(rawTransaction);
return ReceiveResponse.Builder.create().withPrivacyMode(PrivacyMode.STANDARD_PRIVATE).withUnencryptedTransactionData(response).withManagedParties(Set.of(senderKey)).withSender(senderKey).build();
}
final EncryptedTransaction encryptedTransaction = encryptedTransactionDAO.retrieveByHash(hash).orElseThrow(() -> new TransactionNotFoundException("Message with hash " + hash + " was not found"));
final EncodedPayload payload = Optional.of(encryptedTransaction).map(EncryptedTransaction::getPayload).orElseThrow(() -> new IllegalStateException("Unable to decode previously encoded payload"));
PublicKey recipientKey = request.getRecipient().orElse(searchForRecipientKey(payload).orElseThrow(() -> new RecipientKeyNotFoundException("No suitable recipient keys found to decrypt payload for : " + hash)));
byte[] unencryptedTransactionData = enclave.unencryptTransaction(payload, recipientKey);
Set<MessageHash> affectedTransactions = payload.getAffectedContractTransactions().keySet().stream().map(TxHash::getBytes).map(MessageHash::new).collect(Collectors.toSet());
Set<PublicKey> managedParties = new HashSet<>();
if (payload.getRecipientKeys().isEmpty()) {
// legacy tx
for (RecipientBox box : payload.getRecipientBoxes()) {
EncodedPayload singleBoxPayload = EncodedPayload.Builder.from(payload).withRecipientBoxes(List.of(box.getData())).build();
Optional<PublicKey> possibleRecipient = searchForRecipientKey(singleBoxPayload);
possibleRecipient.ifPresent(managedParties::add);
}
} else {
managedParties = enclave.getPublicKeys().stream().filter(payload.getRecipientKeys()::contains).collect(Collectors.toSet());
}
final ReceiveResponse.Builder responseBuilder = ReceiveResponse.Builder.create();
payload.getPrivacyGroupId().ifPresent(responseBuilder::withPrivacyGroupId);
return responseBuilder.withUnencryptedTransactionData(unencryptedTransactionData).withPrivacyMode(payload.getPrivacyMode()).withAffectedTransactions(affectedTransactions).withExecHash(payload.getExecHash()).withManagedParties(managedParties).withSender(payload.getSenderKey()).build();
}
Aggregations