Workflow Simulation
Financial Transactions
A simple workflow is simulated in the following example:
Database file: 'workflow.db': | |
updatable source/1. | |
finished :- not(unfinished). | |
unfinished :- source(W). | |
Transaction file 'workflow.ctr': | |
simulate :- getItem(W) * (workflow(W) # simulate). | |
simulate :- finished. | |
getItem(W) :- del(source(W)). | |
workflow(W) :- task(W,1) * task(W,2) * task(W,3). | |
task(I,W) :- monitor(task(I,W)). | |
load2 :- ins(source(a)) * ins(source(b)). | |
| ?- ctr_comp(workflow). | - program is compiled |
yes | |
?- exec(load2). | - load2 inserts two work items into the database |
yes | |
| | |
| ?- exec(simulate). | - execute simulate transaction |
committing task(a,1) | - the first workflow instance processes item a |
committing task(a,2) | |
committing task(b,1) | - the second workflow instance processes item b |
committing task(a,3) | |
committing task(b,2) | |
committing task(b,3) | |
yes |
The following example, which simulates financial transactions, shows how updates can be combined with queries to define complex transactions.
Transaction file 'financial.ctr': | |
| ?- ctr_comp(workflow). | - program is compiled |
transfer(Amt,Acct1,Acct2) :- o1(withdraw(Amt,Acct1) # deposit(Amt,Acct2)). | |
withdraw(Amt,Acct) :- o((Amt > 0) * bal(Acct,B1) * (Amt < B1) | |
* del(bal(Acct,B1)) * (B2 is B1-Amt) | |
* ins(bal(Acct,B2)) * monitor(withdraw(Amt,Acct))). | |
deposit(Amt,Acct) :- o ((Amt > 0) * del(bal(Acct,B1)) * (B2 is B1+Amt) | |
* ins(bal(Acct,B2)) * monitor(deposit(Amt,Acct))). | |
init :- ins(bal(acct1,100)) * ins(bal(acct2,100)) * ins(bal(acct3,100)) | |
* ins(bal(acct4,100)) * ins(bal(acct5,100)) * ins(bal(acct6,100)). | |
test(Amt) :- o1(transfer(Amt,acct1,acct2) # transfer(Amt,acct1,acct3) | |
# transfer(Amt,acct1,acct4)). | |
Database file 'financial.db': | |
updatable bal/2. | |
| ?- ctr_comp(financial). | - program is compiled |
yes | |
| ?- exec(init). | - init inserts $100 in 6 accounts |
yes | |
| ?- exec(test(10)). | - test transfers $10 from the first account to other 3 accounts |
committing withdraw(10,acct1) | - $10 are withdrawn from acct1 |
committing deposit(10,acct2) | - $10 are deposited into acct2 |
committing withdraw(10,acct1) | - $10 are withdrawn from acct1 |
committing deposit(10,acct3) | - $10 are deposited into acct3 |
committing withdraw(10,acct1) | - $10 are withdrawn from acct1 |
committing deposit(10,acct4) | - $10 are deposited into acct4 |
yes | - test completed with acct1 balance $70 |
| ?- exec(test(30)). | - test transfers $30 from the first account to other 3 accounts |
committing withdraw(30,acct1) | |
committing deposit(30,acct2) | |
committing withdraw(30,acct1) | |
committing deposit(30,acct3) | |
undoing deposit(30,acct3) | |
undoing withdraw(30,acct1) | - the third withdraw failed, so test execution is rolled back |
undoing deposit(30,acct2) | |
undoing withdraw(30,acct1) | |
no |