Skip to content

Instantly share code, notes, and snippets.

@paluh
Created August 29, 2022 11:08
Show Gist options
  • Star 0 You must be signed in to star a gist
  • Fork 0 You must be signed in to fork a gist
  • Save paluh/e3c1c450ee706f9e4214716217bae2b6 to your computer and use it in GitHub Desktop.
Save paluh/e3c1c450ee706f9e4214716217bae2b6 to your computer and use it in GitHub Desktop.
New project on github
{"valueParameterInfo":[["Collateral amount",{"valueParameterFormat":{"contents":[6,"₳"],"tag":"DecimalFormat"},"valueParameterDescription":"The amount of Lovelace to be deposited by both parties at the start of the contract to serve as an incentive for collaboration."}],["Price",{"valueParameterFormat":{"contents":[6,"₳"],"tag":"DecimalFormat"},"valueParameterDescription":"The amount of Lovelace to be paid by the _**Buyer**_ as part of the exchange."}]],"timeParameterDescriptions":[["Collateral deposit by seller timeout","The deadline by which the _**Seller**_ must deposit the _**Collateral amount**_ in the contract."],["Deposit of collateral by buyer timeout","The deadline by which the _**Buyer**_ must deposit the _**Collateral amount**_ in the contract."],["Deposit of price by buyer timeout","The deadline by which the _**Buyer**_ must deposit the _**Price**_ in the contract."],["Dispute by buyer timeout","The deadline by which, if the _**Buyer**_ has not opened a dispute, the _**Seller**_ will be paid."],["Complaint deadline","The deadline by which, if the _**Seller**_ has not responded to the dispute, the _**Buyer**_ will be refunded."]],"roleDescriptions":[["Buyer","The party that pays for the item on sale."],["Seller","The party that sells the item and gets the money if the exchange is successful."]],"contractType":"Escrow","contractShortDescription":"In this contract a _**seller**_ wants to sell an item (like a bicycle) to a _**buyer**_ for a _price_.","contractName":"Escrow with collateral","contractLongDescription":"In order to incentivise collaboration between the _**seller**_ and the _**buyer**_, at the beginning of the contract both parties deposit the _collateral amount_ that is burned if the parties disagree.","choiceInfo":[["Confirm problem",{"choiceFormat":{"contents":null,"tag":"DefaultFormat"},"choiceDescription":"Acknowledge that there was a problem and a refund must be granted."}],["Dispute problem",{"choiceFormat":{"contents":null,"tag":"DefaultFormat"},"choiceDescription":"The _**Seller**_ disagrees with the _**Buyer**_ about the claim that something went wrong and the collateral will be burnt."}],["Everything is alright",{"choiceFormat":{"contents":null,"tag":"DefaultFormat"},"choiceDescription":"The exchange was successful and the _**Buyer**_ agrees to pay the _**Seller**_."}],["Report problem",{"choiceFormat":{"contents":null,"tag":"DefaultFormat"},"choiceDescription":"The _**Buyer**_ claims not having received the product that was paid for as agreed and would like a refund."}]]}
/* We can set explicitRefunds true to run Close refund analysis
but we get a shorter contract if we set it to false */
const explicitRefunds: Boolean = false;
const buyer: Party = Role("Buyer");
const seller: Party = Role("Seller");
const burnAddress: Party = PK("0000000000000000000000000000000000000000000000000000000000000000");
const price: Value = ConstantParam("Price");
const collateral: Value = ConstantParam("Collateral amount");
const sellerCollateralTimeout: Timeout = TimeParam("Collateral deposit by seller timeout");
const buyerCollateralTimeout: Timeout = TimeParam("Deposit of collateral by buyer timeout");
const depositTimeout: Timeout = TimeParam("Deposit of price by buyer timeout");
const disputeTimeout: Timeout = TimeParam("Dispute by buyer timeout");
const answerTimeout: Timeout = TimeParam("Complaint deadline");
function depositCollateral(party: Party, timeout: Timeout, timeoutContinuation: Contract, continuation: Contract): Contract {
return When([Case(Deposit(party, party, ada, collateral), continuation)],
timeout,
timeoutContinuation);
}
function burnCollaterals(continuation: Contract): Contract {
return Pay(seller, Party(burnAddress), ada, collateral,
Pay(buyer, Party(burnAddress), ada, collateral,
continuation));
}
function deposit(timeout: Timeout, timeoutContinuation: Contract, continuation: Contract): Contract {
return When([Case(Deposit(seller, buyer, ada, price), continuation)],
timeout,
timeoutContinuation);
}
function choice(choiceName: string, chooser: Party, choiceValue: SomeNumber, continuation: Contract): Case {
return Case(Choice(ChoiceId(choiceName, chooser),
[Bound(choiceValue, choiceValue)]),
continuation);
}
function choices(timeout: Timeout, chooser: Party, timeoutContinuation: Contract, list: { value: SomeNumber, name: string, continuation: Contract }[]): Contract {
var caseList: Case[] = new Array(list.length);
list.forEach((element, index) =>
caseList[index] = choice(element.name, chooser, element.value, element.continuation)
);
return When(caseList, timeout, timeoutContinuation);
}
function sellerToBuyer(continuation: Contract): Contract {
return Pay(seller, Account(buyer), ada, price, continuation);
}
function refundSellerCollateral(continuation: Contract): Contract {
if (explicitRefunds) {
return Pay(seller, Party(seller), ada, collateral, continuation);
} else {
return continuation;
}
}
function refundBuyerCollateral(continuation: Contract): Contract {
if (explicitRefunds) {
return Pay(buyer, Party(buyer), ada, collateral, continuation);
} else {
return continuation;
}
}
function refundCollaterals(continuation: Contract): Contract {
return refundSellerCollateral(refundBuyerCollateral(continuation));
}
const refundBuyer: Contract = explicitRefunds ? Pay(buyer, Party(buyer), ada, price, Close) : Close;
const refundSeller: Contract = explicitRefunds ? Pay(seller, Party(seller), ada, price, Close) : Close;
const contract: Contract =
depositCollateral(seller, sellerCollateralTimeout, Close,
depositCollateral(buyer, buyerCollateralTimeout, refundSellerCollateral(Close),
deposit(depositTimeout, refundCollaterals(Close),
choices(disputeTimeout, buyer, refundCollaterals(refundSeller),
[{ value: 0n, name: "Everything is alright", continuation: refundCollaterals(refundSeller) },
{
value: 1n, name: "Report problem",
continuation:
sellerToBuyer(
choices(answerTimeout, seller, refundCollaterals(refundBuyer),
[{ value: 1n, name: "Confirm problem", continuation: refundCollaterals(refundBuyer) },
{ value: 0n, name: "Dispute problem", continuation: burnCollaterals(refundBuyer) }]))
}]))));
return contract;
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment