本文首要论述Filecoin中Payment Channel,即付出通道的具体完成。

概述

付出通道是一种提高区块链可扩展性的机制,使买卖的两边削减与链的交互。提高了体系的负载量,一起削减了与链交互发生的gas费。在Filecoin中,买卖两边经过智能合约运用付出通道。

效果

付出通道首要是解决付出两边在一次服务中屡次买卖,这些买卖不需求事实上链,只需求在终究状况上链进行结算。对买卖两边有一下几个好处:

1.削减等待时刻,因为区块链的特性,假如和链进行交互,相较于一般的计算机操作,会有巨大的延迟,以检索商场为例,假如检索一个30G文件,存在频频的付出买卖,当买卖有必要上链承认时,等待音讯上链简直占有了检索的整个耗时。

2.削减gas费,与链交互会发生gas费,降低与链的交互会降低服务的本钱。

3.提高网络容量,付出通道将屡次频频的买卖简化为只需求终究状况时上链进行结算,大大削减了频频买卖占有的网络容量。

术语

payment channel sender

付出通道建议者,是创立付出通道并向付出通道增加资金的一方,付出通道建议者承受付出通道接纳者供给的服务。

payment channel recipient

付出通道接纳者,接纳从付出通道来的资金并向付出通道建议者供给相应的服务。

voucher

付出凭据,由付出通道恣意一方创立的签名音讯,用于更新付出通道付出资金。

lane

付出航道,多个服务能够共享一个付出通道,经过付出航道区别不同的服务。每个付出凭据有必要指定一个付出航道

Redeeming a voucher

完成凭据,凭据有必要由创立凭据的另一方在链上提交。兑换凭据不会触发资金从途径转移到接纳者的账户,但它会发生gas费。凭据能够在任何时刻兑换,直到归集为止。

UpdateChannelState

更新付出通道状况,兑付凭据的进程,即在链上提交(但不完成)凭据。

Settle

结算,此进程开端封闭付出通道。它能够由通道的创立者(发送方)或通道接纳方调用,这个进程会发生gas费。

Collect

归集,经过此进程,资金终究从付出通道发送方转移到付出通道接纳方,这个进程会发生gas费。

履行逻辑

Filecoin支付通道研究

1.买卖两边进行一系列买卖,一方需求向一方付出付出通道资金。两边在链下协商好买卖的具体内容。

2.付出通道建议者经过PayChActor创立一个付出通道并质押一些资金。 (合约并没有约束创立付出通道的地址,任何账户地址都能够为恣意两个买卖两边创立付出通道。可是创立付出通道需求付出必定的费用,所以正常状况下是由付出通道建议者创立)

3.买卖两边创立并相互发送付出凭据

4.两边暂时将付出凭据保存在本地,付出凭据只能被付出凭据接纳者兑换

5.接纳到凭据的一方能够立即或许以后将凭据提交到链上

6.恣意一方调用Settle开端封闭付出通道(为了防止有一方过早的封闭付出通道,能够经过MinSettleHeight值约束付出通道最早的截止日期)

7.12小时后封闭付出通道

8.假如两边还有更高Nonce的付出凭据没有兑换,现在需求提交凭据到链上

9.12小时期限接纳,付出通道不再接纳付出凭据兑换

10.恣意一方调用Collect

11.付出资金转入到付出通道接纳者账户,剩下的资金回来给付出通道建议者

具体完成

源码完成

付出通道状况

付出通道建议者经过智能合约创立一个付出通道,付出通道建议者需求供给付出通道建议者地址付出通道接纳者地址。付出通道创立后生成一个PayChActor,以下是PayChActor状况:

type State struct {
    // Channel owner, who has funded the actor
    From addr.Address
    // Recipient of payouts from channel
    To addr.Address
    // Amount successfully redeemed through the payment channel, paid out on `Collect()`
    ToSend abi.TokenAmount
    // Height at which the channel can be `Collected`
    SettlingAt abi.ChainEpoch
    // Height before which the channel `ToSend` cannot be collected
    MinSettleHeight abi.ChainEpoch
    // Collections of lane states for the channel, maintained in ID order.
    LaneStates cid.Cid // AMT<LaneState>
}

From : 付出通道建议者,有必要和创立付出通道的地址共同
To : 付出通道接纳者
ToSend : 经过voucher更新的付出通道付出资金,结算后,ToSend资金付出给付出通道接纳者,付出通道余额归还付出通道建议者
SettlingAt : 付出通道的中止兑换付出凭据时刻,高度达到SettlingAt后,未兑换的付出凭据失效
MinSettleHeight : 最晚的兑换付出凭据时刻,SettlingAt不能够小于MinSettleHeight
LaneStates : 航道状况调集

Voucher

为了运用付出通道进行买卖,两边会互相发送签名音讯更新付出通道付出资金。在Filecoin网络,这个签名音讯称作voucher。voucher用于更新付出通道状况。

type SignedVoucher struct {
    // ChannelAddr is the address of the payment channel this signed voucher is valid for
    ChannelAddr addr.Address
    // TimeLockMin sets a min epoch before which the voucher cannot be redeemed
    TimeLockMin abi.ChainEpoch
    // TimeLockMax sets a max epoch beyond which the voucher cannot be redeemed
    // TimeLockMax set to 0 means no timeout
    TimeLockMax abi.ChainEpoch
    // (optional) The SecretPreImage is used by `To` to validate
    SecretPreimage []byte
    // (optional) Extra can be specified by `From` to add a verification method to the voucher
    Extra *ModVerifyParams
    // Specifies which lane the Voucher merges into (will be created if does not exist)
    Lane uint64
    // Nonce is set by `From` to prevent redemption of stale vouchers on a lane
    Nonce uint64
    // Amount voucher can be redeemed for
    Amount big.Int
    // (optional) MinSettleHeight can extend channel MinSettleHeight if needed
    MinSettleHeight abi.ChainEpoch
    // (optional) Set of lanes to be merged into `Lane`
    Merges []Merge
    // Sender's signature over the voucher
    Signature *crypto.Signature
}

介绍一些要点字段:

TimeLockMin字段约束了兑换付出凭据的最小高度
TimeLockMax字段约束了兑换付出凭据的最大高度,假如字段非0,当超越TimeLockMax高度后凭据过期
SecretPreimage字段会和Secret一起验证付出凭据的合法性。付出者向接纳者发送凭据时,会额定供给Secret,凭据在链上兑换时,会查看SecretPreimage是和Secret是否共同。SecretPreimage等于hash(Secret),现在filecoin实际暂时未运用这个功能。

if len(sv.SecretPreimage) > 0 {
    hashedSecret := rt.HashBlake2b(params.Secret)
    if !bytes.Equal(hashedSecret[:], sv.SecretPreimage) {
        rt.Abortf(exitcode.ErrIllegalArgument, "incorrect secret!")
    }
}

Extra比较有意思,在凭据兑换时,付出者能够要求验证某种条件是否满足。

if sv.Extra != nil {
    code := rt.Send(

        sv.Extra.Actor,

        sv.Extra.Method,

        builtin.CBORBytes(sv.Extra.Data),

        abi.NewTokenAmount(0),

        &builtin.Discard{},

    )

    builtin.RequireSuccess(rt, code, "spend voucher verification failed")

}

Merges用于将多个lane兼并。

创立付出通道

付出通道创立者经过智能合约创立一个付出通道,付出通道建议者需求供给付出通道建议者地址付出通道接纳者地址参数

type ConstructorParams struct {
    From addr.Address // Payer
    To addr.Address // Payee
}

创立完成后链上生成付出通道状况,回来付出通道的地址。买卖两边经过付出通道完成买卖

留意:付出通道创立者不必定是付出通道建议者。任何人都能够为一对买卖者创立付出通道。只需求向智能合约供给通道建议者地址付出通道接纳者地址参数和一笔手续费。可是一般状况下付出通道建议者是付出通道创立者

UpdateChannelState

UpdateChannelState用于兑换凭据,更新付出通道状况,只要凭据接纳刚才能够兑换凭据。UpdateChannelState办法除了更新付出金额定,还能够经过MinSettleHeight字段更新付出通道状况的MinSettleHeight。即便在Settle办法调用后,中止兑换付出凭据时刻还能够被凭据更新。

type UpdateChannelStateParams struct {
    Sv SignedVoucher
    Secret []byte
}

合约UpdateChannelState验证凭据和更新付出通道状况,逻辑首要有以下部分:

1.验证调用者是否是付出者或许接纳者,只要付出通道的两边才能够创立凭据

2.验证签名是否是凭据创立者

3.验证凭据的时刻是否能够承受

4.验证SecretPreimage和Secret是否匹配

5.Extra验证凭据创立者要求的额定条件是否满足

6.凭据对应的lane的nonce是否大于付出通道最大的nonce

7.处理兼并凭据

8.查看余额是否满足最新的付出金额

9.更新状况

Nonce最高的付出凭据会刷新掉其他付出凭据,例如以下状况:

当时付出通道有余额100FiL,付出资金为0。有某lane的三个付出凭据(voucher_val,voucher_nonce):(10,1),(20,2),(30,3),假如接纳者兑换了(20,2),则付出资金为20。(10,1)付出凭据不能够被兑换了。假如接着兑换(30,3),付出资金为30。付出凭据是一种无状况的凭据。 付出通道建议者根据付出通道接纳者供给的服务付出付出凭据,接纳到付出凭据的一方能够兑换凭据。兑换凭据的进程需求和链交互,会发生gas费。所以只需求在服务结束时将Nonce最高的付出凭据兑换即可。在付出凭据兑换之前能够在链上查看付出通道是否有满足的余额能够兑换付出凭据,这个进程不需求消耗gas费。

Settle

买卖两边都能够调用Settle办法,用于设置付出通道的答应兑换凭据的截止兑换高度,Settle办法不需求参数 首要逻辑:

1.验证调用者是否是付出者或许接纳者,只要付出通道的两边才能够调用Settle

2.验证截止兑换高度是否现已被设置

3.设置截止日期为Settle办法后12小时但不能够小于付出通道MinSettleHeight值

留意:可是还能够在截止兑换高度之前经过凭据更改截止兑换高度

Collect

买卖两边都能够调用Collect办法,用于结算资金 首要逻辑:

1.验证调用者是否是付出者或许接纳者,只要付出通道的两边才能够调用Collect

2.验证是否抵达截止兑换高度

3.将ToSend资金转给付出通道接纳者,销毁付出通道并将剩下资金归还付出通道建议者

当时完成问题

付出凭据在兼并时,兼并的不同的lane的付出凭据有必要有相应nonce小的凭据现已提交上链。所以只要在相应lane的凭据现已上链,当需求更新时才有效果。可是运用兼并还引进另一个问题,付出通道规划思维是终究凭据并不受曾经凭据影响,其时当运用兼并时这种思维被打破。被兼并之后的lane需求再次更新凭据时受接纳者最终一次相应lane兑换的凭据影响。

考虑

付出凭据总是指当时付出线的付出总数,付出凭据虽然不是绝对递增的,可是因为兑换的权力在于另一方。nonce值更大的付出凭据会刷新掉曾经的付出凭据,所以付出通道接纳者必定不会愿意兑换一个资金更少的凭据。

付出通道建议者,因为是付出资金的一方,假如发送的付出凭据少于上一个付出凭据付出的金额。作为付出凭据的兑换者-付出通道接纳者不会愿意承受这个付出凭据,能够用上一个金额更大的付出凭据作为兑换的凭据并中止供给服务。所以,付出通道建议者为了继续承受来自付出通道接纳者供给的服务,应当供给越来越大的付出凭据。

付出通道接纳者,是获取付出通道资金的一方,假如付出通道接纳者随意建议一个更高金额的付出凭据,作为付出凭据的兑换者-一个理性的付出通道建议者必定不会接纳这个付出凭据,所以这个付出凭据也就毫无意义。当然,假如付出通道接纳者因为供给的供给的服务没有完成,出于人道的好心,能够会退回部分资金给付出通道建议者,付出通道接纳者可能会建议一个较低金额的付出凭据,最为付出的一方,付出通道建议者必定也会欢喜的承受并感叹世界上仍是有好人。