I've been reading about pure methods and immutability in Java. I have a current application and want to convert all the methods to pure methods.
My app takes payment from users. I first create a payment in the DB:
Payment payment = new Payment();
payment = createPayment(orderId, status, address1, address2, country, state, price);
// createPayment() creates a row in the database table, saving orderId, status, address1, address2, country, state, price
// state is the inital state of the payment, in this cased INITIATED
createPayment() returns a Payment model
// make the payment with the payment processor
PaymentResult paymentResult = paymentService.pay(payment);
PaymentResult
contains properties such as authCode
, pspReference
, resultCode
, refusalReason
.
The Payment model also contains authCode
etc. properties. I now want to update my Payment model, including its status. I currently have:
paymentService.updatePaymentFromPaymentResultOnAuthorise(paymentResult, payment);
And updatePaymentFromPaymentResultOnAuthorise
is:
public void updatePaymentFromPaymentResultOnAuthorise(PaymentResult paymentResult, Payment payment) throws PaymentException {
try {
boolean success = !isNullOrEmpty(paymentResult.getAuthCode());
if (success) {
payment.setLastStatus(payment.getStatus());
payment.setStatus(PaymentStatus.PAID);
}
payment.setPspReference(paymentResult.getPspReference());
payment.setAuthCode(paymentResult.getAuthCode());
payment.setResultCode(String.valueOf(paymentResult.getResultCode()));
payment.setRefusalReason(paymentResult.getRefusalReason());
paymentDAO.updatePayment(payment);
} catch (Exception e) {
throw new PaymentException(String.format("there was an error updating the payment with paymentId %s", payment.getId()));
}
}
As you can see, updatePaymentFromPaymentResultOnAuthorise
is not a pure method as it changes the argument payment
. This pattern is repeated throughout the app.
Is the only way to make this method pure to create a copy of payment
within updatePaymentFromPaymentResultOnAuthorise
and return this new object? This seems expensive and it will need to be done in many places throughout my app. But is that my only option?