Closed countfloyd closed 5 years ago
Not sure how I request another review. I'll just add a comment here.
Hi @countfloyd , may I ask what are you trying to do with this manual module? Is this a settlement rail you have created for yourself?
@yikailim93 I think manual settlement is quite useful if you need to settle something off ledger but the rail isn't yet supported. If you trust your counterpart, you can compromise some automation and assurance to handle settlements. Cheers
@yikailim93 Yes we created manual settlement because we need it for our client who do off ledger settlements by writing checks, etc. The obligee can manually verify the payment was received. At the moment, we have no way of automatically verifying a payment was made.
Thanks for addressing my comments - I added a couple of more for information (no need to action any of them). The only thing I'd ask is that is it possible for you to add a test for the manual settlement mechanism and some unit tests? Other than that, I think this is good to merge. Many thanks for the contribution!
Update: Forgot to mention that the other thing which needs adding is some contract code for cancelling an obligation. Cheers!
There's already contract verification code for cancelling an obligation, or did you mean something else?
Thank you both for the reply.
@yikailim93 Yes we created manual settlement because we need it for our client who do off ledger settlements by writing checks, etc. The obligee can manually verify the payment was received. At the moment, we have no way of automatically verifying a payment was made.
@countfloyd is your CorDapp currently up and running? And if I may ask, did you have to make a lot of changes to the cordapp/cordapp-contracts-states/oracle modules (or any other module) in order to integrate your manual settlement module? Also, are the source files in your manual settlement module the only/main files you have created to achieve your objective? Asking all these because I'm currently trying to develop my own settler as well but is facing a lot of roadblocks. Would appreciate if you could shed some light on this corda-settler.
There's already contract verification code for cancelling an obligation, or did you mean something else?
Sorry, my bad - I think I even added it. Doh!
@yikailim93 Yes our app is running in private test but not in production. All I really did was add my own ManualSettlement class and ManualPayment as well as a MakeManualPayment flow. I don't use the oracle at all because we have no way to automatically verifying that a payment was made. Instead, I made a UpdatePaymentStatusManually flow so that the obligee could verify that the payment was received. The manual module in Corda-settler was all I added to make obligations work for me, yes.
New changes for review:
@yikailim93 Yes our app is running in private test but not in production. All I really did was add my own ManualSettlement class and ManualPayment as well as a MakeManualPayment flow. I don't use the oracle at all because we have no way to automatically verifying that a payment was made. Instead, I made a UpdatePaymentStatusManually flow so that the obligee could verify that the payment was received. The manual module in Corda-settler was all I added to make obligations work for me, yes.
Thank you @countfloyd! This information is very helpful. May I ask if you can share the commands you ran on the nodes' terminal for the process from creating an obligation up until settlement? This will solely be for demonstration purposes.
Also, if I may add on, I was trying to run the corda-settler repo that you have uploaded on your profile. I encountered the error below when running gradlew clean deployNodes, do you have any idea what went wrong?
C:\Users\aikka\Desktop\corda-settler-manual>gradlew --stacktrace clean deployNodes
> Task :cordapp-contracts-states:clean FAILED
FAILURE: Build failed with an exception.
* What went wrong:
Execution failed for task ':cordapp-contracts-states:clean'.
> Unable to delete file: C:\Users\aikka\Desktop\corda-settler-manual\cordapp-contracts-states\build\libs\cordapp-contracts-states-0.1.jar
* Try:
Run with --info or --debug option to get more log output. Run with --scan to get full insights.
* Exception is:
org.gradle.api.tasks.TaskExecutionException: Execution failed for task ':cordapp-contracts-states:clean'.
at org.gradle.api.internal.tasks.execution.ExecuteActionsTaskExecuter.executeActions(ExecuteActionsTaskExecuter.java:110)
at org.gradle.api.internal.tasks.execution.ExecuteActionsTaskExecuter.execute(ExecuteActionsTaskExecuter.java:77)
at org.gradle.api.internal.tasks.execution.OutputDirectoryCreatingTaskExecuter.execute(OutputDirectoryCreatingTaskExecuter.java:51)
at org.gradle.api.internal.tasks.execution.SkipUpToDateTaskExecuter.execute(SkipUpToDateTaskExecuter.java:59)
at org.gradle.api.internal.tasks.execution.ResolveTaskOutputCachingStateExecuter.execute(ResolveTaskOutputCachingStateExecuter.java:54)
at org.gradle.api.internal.tasks.execution.ValidatingTaskExecuter.execute(ValidatingTaskExecuter.java:59)
at org.gradle.api.internal.tasks.execution.SkipEmptySourceFilesTaskExecuter.execute(SkipEmptySourceFilesTaskExecuter.java:101)
at org.gradle.api.internal.tasks.execution.FinalizeInputFilePropertiesTaskExecuter.execute(FinalizeInputFilePropertiesTaskExecuter.java:44)
at org.gradle.api.internal.tasks.execution.CleanupStaleOutputsExecuter.execute(CleanupStaleOutputsExecuter.java:91)
at org.gradle.api.internal.tasks.execution.ResolveTaskArtifactStateTaskExecuter.execute(ResolveTaskArtifactStateTaskExecuter.java:62)
at org.gradle.api.internal.tasks.execution.SkipTaskWithNoActionsExecuter.execute(SkipTaskWithNoActionsExecuter.java:59)
at org.gradle.api.internal.tasks.execution.SkipOnlyIfTaskExecuter.execute(SkipOnlyIfTaskExecuter.java:54)
at org.gradle.api.internal.tasks.execution.ExecuteAtMostOnceTaskExecuter.execute(ExecuteAtMostOnceTaskExecuter.java:43)
at org.gradle.api.internal.tasks.execution.CatchExceptionTaskExecuter.execute(CatchExceptionTaskExecuter.java:34)
at org.gradle.api.internal.tasks.execution.EventFiringTaskExecuter$1.run(EventFiringTaskExecuter.java:51)
at org.gradle.internal.operations.DefaultBuildOperationExecutor$RunnableBuildOperationWorker.execute(DefaultBuildOperationExecutor.java:301)
at org.gradle.internal.operations.DefaultBuildOperationExecutor$RunnableBuildOperationWorker.execute(DefaultBuildOperationExecutor.java:293)
at org.gradle.internal.operations.DefaultBuildOperationExecutor.execute(DefaultBuildOperationExecutor.java:175)
at org.gradle.internal.operations.DefaultBuildOperationExecutor.run(DefaultBuildOperationExecutor.java:91)
at org.gradle.internal.operations.DelegatingBuildOperationExecutor.run(DelegatingBuildOperationExecutor.java:31)
at org.gradle.api.internal.tasks.execution.EventFiringTaskExecuter.execute(EventFiringTaskExecuter.java:46)
at org.gradle.execution.taskgraph.LocalTaskInfoExecutor.execute(LocalTaskInfoExecutor.java:42)
at org.gradle.execution.taskgraph.DefaultTaskExecutionGraph$BuildOperationAwareWorkItemExecutor.execute(DefaultTaskExecutionGraph.java:277)
at org.gradle.execution.taskgraph.DefaultTaskExecutionGraph$BuildOperationAwareWorkItemExecutor.execute(DefaultTaskExecutionGraph.java:262)
at org.gradle.execution.taskgraph.DefaultTaskPlanExecutor$ExecutorWorker$1.execute(DefaultTaskPlanExecutor.java:135)
at org.gradle.execution.taskgraph.DefaultTaskPlanExecutor$ExecutorWorker$1.execute(DefaultTaskPlanExecutor.java:130)
at org.gradle.execution.taskgraph.DefaultTaskPlanExecutor$ExecutorWorker.execute(DefaultTaskPlanExecutor.java:200)
at org.gradle.execution.taskgraph.DefaultTaskPlanExecutor$ExecutorWorker.executeWithWork(DefaultTaskPlanExecutor.java:191)
at org.gradle.execution.taskgraph.DefaultTaskPlanExecutor$ExecutorWorker.run(DefaultTaskPlanExecutor.java:130)
at org.gradle.internal.concurrent.ExecutorPolicy$CatchAndRecordFailures.onExecute(ExecutorPolicy.java:63)
at org.gradle.internal.concurrent.ManagedExecutorImpl$1.run(ManagedExecutorImpl.java:46)
at org.gradle.internal.concurrent.ThreadFactoryImpl$ManagedThreadRunnable.run(ThreadFactoryImpl.java:55)
Caused by: org.gradle.api.file.UnableToDeleteFileException: Unable to delete file: C:\Users\aikka\Desktop\corda-settler-manual\cordapp-contracts-states\build\libs\cordapp-contracts-states-0.1.jar
at org.gradle.api.internal.file.delete.Deleter.handleFailedDelete(Deleter.java:109)
at org.gradle.api.internal.file.delete.Deleter.doDeleteInternal(Deleter.java:86)
at org.gradle.api.internal.file.delete.Deleter.doDeleteInternal(Deleter.java:81)
at org.gradle.api.internal.file.delete.Deleter.doDeleteInternal(Deleter.java:81)
at org.gradle.api.internal.file.delete.Deleter.delete(Deleter.java:66)
at org.gradle.api.tasks.Delete.clean(Delete.java:67)
at org.gradle.internal.reflect.JavaMethod.invoke(JavaMethod.java:73)
at org.gradle.api.internal.project.taskfactory.StandardTaskAction.doExecute(StandardTaskAction.java:46)
at org.gradle.api.internal.project.taskfactory.StandardTaskAction.execute(StandardTaskAction.java:39)
at org.gradle.api.internal.project.taskfactory.StandardTaskAction.execute(StandardTaskAction.java:26)
at org.gradle.api.internal.AbstractTask$TaskActionWrapper.execute(AbstractTask.java:801)
at org.gradle.api.internal.AbstractTask$TaskActionWrapper.execute(AbstractTask.java:768)
at org.gradle.api.internal.tasks.execution.ExecuteActionsTaskExecuter$1.run(ExecuteActionsTaskExecuter.java:131)
at org.gradle.internal.operations.DefaultBuildOperationExecutor$RunnableBuildOperationWorker.execute(DefaultBuildOperationExecutor.java:301)
at org.gradle.internal.operations.DefaultBuildOperationExecutor$RunnableBuildOperationWorker.execute(DefaultBuildOperationExecutor.java:293)
at org.gradle.internal.operations.DefaultBuildOperationExecutor.execute(DefaultBuildOperationExecutor.java:175)
at org.gradle.internal.operations.DefaultBuildOperationExecutor.run(DefaultBuildOperationExecutor.java:91)
at org.gradle.internal.operations.DelegatingBuildOperationExecutor.run(DelegatingBuildOperationExecutor.java:31)
at org.gradle.api.internal.tasks.execution.ExecuteActionsTaskExecuter.executeAction(ExecuteActionsTaskExecuter.java:120)
at org.gradle.api.internal.tasks.execution.ExecuteActionsTaskExecuter.executeActions(ExecuteActionsTaskExecuter.java:99)
... 31 more
* Get more help at https://help.gradle.org
BUILD FAILED in 2s
3 actionable tasks: 3 executed
PS: I'm really sorry to keep bothering you here, I've been trying to develop my own settler for the past 2 months but kept getting errors and I'm still no where near completing my cordapp. Really hope that you wouldn't mind me asking all the questions.
@countfloyd I've tried to run the tests locally but none of them pass:
1) The gradle plugins version was updated but we need to disable sealing for all the cordapps because it doesn't work with the way the packages are currently structured.
cordapp { sealing { enabled false } }
2) it seems the create obligation flow doesn't work - sends and receives are not matched up. Need to add subFlow(SwapIdentitiesFlow(otherFlow))
in the responder flow as the first sub flow, to match up the sends and receives. The new swap identities flow in Corda 4 is not an initiating flow, so you need to add the responder flow.
3) Also, the FinalityFlow
in SendToSettlementOracle
needs a responder. This will be more tricky than you think to implement though.
Cheers
@yikailim93 can you please stop asking support questions in this PR? Either go on to slack and ask a question, use stack over flow or submit a github issue. Me or others will be happy to help you in those places. Cheers
@roger3cev okay, sorry for the inconvenience caused.
@yikailim93 no worries - is also better for you to ask questions in those places. There's more people to help :)
@roger3cev Hmmm weird. The tests passed for me. Although I only ran them from my IDE. I'll check it out along with your other issues. Won't be able to work on it until next week. Thanks for your review.
@roger3cev, addressed the issues you outlined. Just wondering what I need to run the SWIFT unit tests. README says I need to email you for API key and I need a swift.pem file? Can you email me what I need?
XRP tests all run successfully now.
Thanks.
@countfloyd dont worry about the SWIFT tests - I'll sort those out. Cheers!
This looks great - good to merge!
Thanks for the contribution @countfloyd !
Yes, thanks @countfloyd - great work and much appreciated by all.
My pleasure, thanks for the work reviewing this.
This PR is a result of the work I did working Corda-settler into our Cordapp.
The main change is the addition of a manual settlement rail. Since the oracle can't be used to verify manual payments, I added a flow to change a payment status. Also, made the settlementOracle field optional and the oracle will not be consulted if it's null
Updated deprecated flow constructors to use 4.0 constructors
Fixed some warnings
Updated kittinunf.fuel to latest version
I've been testing quite extensively (except for the oracle, swift and ripple modules). Still need to add some unit test for the manual module. Hope this PR isn't too big :)