ArkEcosystem / AIPs

ARK Improvement Proposals
26 stars 25 forks source link

Atomic Swap between ark, ark-forks and lightning network #95

Closed Moustikitos closed 5 years ago

Moustikitos commented 5 years ago

Because it allows peer to peer exchanges (or decentralized exchanges), atomic swap is one of the biggest feature every blockchain try to reach. For now, HTLC achievement on Bitcoin Network is the most promising procedure in that way.

See on mermaidjs.github.io an adaptation of HTLC atomic swap based on a freezer/defreezer transaction pair.

The transaction structure proposed

Freezer transaction

{
    "type": 111,
    "fee": <int>,
    "timelock" <expiration_timestamp>,
    "amount": <int>,
    "senderId": <BOB_address>,
    "senderPublicKey": <hex>,
    "recipientId": <ALICE_address>,
    "vendorField": <ascii>,
    "asset": {
        "image": <hex_issued_from_preimage_with_specific_method>,
    },
    "signatures": <hex>,
    ["signSignature": <hex>],
    "id": <freezer_id>
}

Defreezer transaction

{
    "type": 112,
    "fee": <int>,
    "amount": 0,
    "senderId": <ALICE_address>,
    "senderPublicKey": <hex>,
    "recipientId": <BOB_address>,
    "vendorField": <ascii>,
    "asset": {
        "freezer_id": <freezer_id>,
        "preimage": <ascii>,
        "method": "ecdsa:secp256k1:<verifyingKey>"
    },
    "signatures": <hex>,
    ["signSignature": <hex>],
    "id": <hex>
}

Different methods could be described in asset

"asset": {
    "freezer_id": <freezer_id>,
    "preimage": <ascii>,
    "method": "nacl:<verifyingKey>",
}
"asset": {
    "freezer_id": <freezer_id>,
    "preimage": <ascii>,
    "method": "hash:sha256",
}
...

Pseudo-code implementation

this is a first draw and may be improved

At transaction pool level, freezer tx are to be validated if wallet balance allows it. A defreezer tx is valid if described asset matches with the element sent before and if timelock did not expire.

[...]
FROZEN_TRANSACTIONS = {}
[...]
LAST_BLOCK_TIMESTAMP = getBlockchainHeight()["timestamp"]
[...]
for transaction in pool:
    [...]
    # if freezer transaction found
    if transaction["type"] == 111:
        address = transaction["senderId"]
        if transaction["timelock"] < LAST_BLOCK_TIMESTAMP and \
           checkSignatures(transaction) and \
           checkWalletBalance(address):
            validateTransaction(transaction)
    [...]
    # if defreezer transaction found
    if transaction["type"] == 112:
        address = transaction["recipientId"]
        freezer_tx = FROZEN_TRANSACTIONS.get(address, {}).get(transaction["asset"]["freezer_id"], False)
        if freezer_tx and \
           freezer_tx["timelock"] > transaction["timelock"] and \
           freezer_tx["timelock"] <= LAST_BLOCK_TIMESTAMP and \
           freezer_tx["senderID"] == address and \
           transaction["senderID"] == freezer_tx["recipientId"] and \
           checkSignatures(transaction) and \
           checkAssetMatch(transaction["asset"], freezer_tx["asset"]["image"]):
            validateTransaction(transaction)
    [...]
[...]

On relay side, all transactions are considered as valid. So balance computation could be done simply.

[...]
# on block added
for transaction in block:
    [...]
    # if freezer tx found
    if transaction["type"] == 111:
        address = transaction["senderId"]
        # remove amount and fee from wallet
        WALLET[address]["balance"] -= transaction["amount"] + transaction["fee"]
        # keep track of frozen transaction
        FROZEN_TRANSACTIONS.get(address, {})[transaction["id"]] = transaction
    [...]
    # if defreezer transaction found
    if transaction["type"] == 112:
        # get the wallet address councerned by this frozen balance
        address = transaction["recipientId"]
        # get the associated frozen tx
        freezer_tx = FROZEN_TRANSACTIONS.get(address, {}).get(transaction["asset"]["freezer_id"], False)
        if freezer_tx and \
           checkAsset(transaction["asset"], freezer_tx["asset"]["image"]) and \
           freezer_tx["timelock"] <= block["timestamp"]:
            WALLET[transaction["recipientId"]]["balance"] += freezer_tx["amount"]
            FROZEN_TRANSACTIONS.get(address, {}).pop(freezer_tx["id"])
    [...]
[...]

# after last block added defreeze frozen balances where expiration reached
for address in FROZEN_TRANSACTIONS:
    for transaction in list(FROZEN_TRANSACTIONS[address].values()):
        if LAST_BLOCK_TIMESTAMP > transaction["timelock"]:
            tx = FROZEN_TRANSACTIONS[address].pop(transaction["id"])
            WALLET[address]["balance"] += tx["amount"]

I think if this kind of atomic swap can be done between ark-forks, the path to do it directly with Bitcoin will be not so far...

Any comments and ideas are welcome, it is a first draw proposal about atomic swap and may be subject to improvements.

ghost commented 5 years ago

Thanks for opening this issue! A maintainer will review this in the next few days and explicitly select labels so you know what's going on.

If no reviewer appears after a week, a reminder will be sent out.

kristjank commented 5 years ago

@Moustikitos thanks for this. We are also working quite heavy on the HTLC part, in a similar way as outlined by your proposal.

This is something that will help us, when joining efforts. We will share more when we believe the specs are matured - so we can review and improve them together.

Moustikitos commented 5 years ago

Ok nice.

I think, the hardest part with HTLC between ARK and Lightning Network will be the end user interface with desktop wallet.

Getting the right info from Ligtning Network using SCRIPT is matter of coding. Putting it simply for end user will be quite a huge task but possible with Desktop Wallet "plugability".

Maybe on ark-core side, ARK LOGIC would be most appropriate in Lightning Network interactions.

kristjank commented 5 years ago

https://github.com/ArkEcosystem/AIPs/blob/master/AIPS/aip-102.md #102 Sharing updated docs from our side here. Thanks for your help with initial proposal.

and yes the biggest part will be user interface, but this is scope of other tools and new AIPs.

thanks @Moustikitos

ghost commented 5 years ago

This issue has been closed. If you wish to re-open it please provide additional information.