OperationState implements Identifiable<String> { public void setOperationEnd(Date operationEnd, V result, Throwable exception) { synchronized (this) { this.result = result; this.throwable = exception; this.operationEnd = operationEnd; } } OperationState(String opId, A operation, Date operationStart); String getLocator(); void setLocator(
      String locator); @Override boolean equals(Object o); @Override int hashCode(); @Override String getId(); A getOperation(); Date getOperationStart(); void setOperationEnd(Date operationEnd, V result, Throwable exception); Date getOperationEnd(); V getResult(); Throwable getThrowable();  }
@Test public void verifyEqualInstances() { OperationState<?, OperationResult> operationState1 = new OperationState<>(null, null, null); OperationState<?, OperationResult> operationState2 = new OperationState<>(null, null, null); assertThat(operationState1).isEqualTo(operationState2); ClusterManagementOperation operation = mock(ClusterManagementOperation.class); Date start = new Date(); Date end = new Date(); OperationResult result = mock(OperationResult.class); Throwable throwable = new Throwable(); operationState1 = new OperationState<>("opId", operation, start); operationState1.setOperationEnd(end, result, throwable); operationState2 = new OperationState<>("opId", operation, start); operationState2.setOperationEnd(end, result, throwable); assertThat(operationState1).isEqualTo(operationState2); }