# CKB ACL Brainstorming ## Metadata **Status**:: #x **Zettel**:: #zettel/literature **Created**:: [[2023-10-12]] ## Synopsis 权限代理是比较常见的 scripts composition。主要思路就是对逻辑进行模块化,然后通过 运行时 ACL 配置对模块进行组合。 我们也经常能看到 ACL 的实际应用。 1. Anyone Can Pay: 可以看做是 secp256k1 lock script 将部分的操作权限授予了任意 script。 2. .bit 中的 wrapper lock 也可以看做是 user lock script 将部分操作权限代理授予了 .bit type script。 3. Taproot MAST 也可以看做是权限的代理,一个 UTXO 可以有不同的解锁途径。 ## Lock Scripts Authorizing Type Scripts 按照约定 Lock Script 不会去验证 cell data,所以它主要就是整个 cell 的所有权,主要是其 CKB capacity 的所有权。 Lock ACL 表示在不需要对应的 Signature 的情况下对 cell 进行操作: - 更新 cell data - 修改 type script - 减少 ckb capacity 使用场景 - 游戏的高频操作,可以将 cell data 更新的权限授予游戏的 type script ### 场景 - 代付 CKB - 用于存储或者 tx fee - Offline Payment - User operations auto approvals (session key) - ESC 中 Component 授权 System ### 操作判断 #### 识别 inputs/outputs 的关联 Cell 的一次性的,在 tx 中总是销毁一批然后新创建一批。所以 Update 这种操作其实从 CKB 底层中是不存在的,但是在应用层来说这种需求又是非常常用的。 目前常用的识别的模式有: - 通过 lock script。这种关联是多对多的,Inputs / Outputs 都是使用该 lock script 的 cells 的集合。这时候一些操作就不太好定义,要么是根据这种集合的情况重新定义可以执行的操作,要么是再进一步定义如果推导出一对一的关系。 - 通过 ID,比如 Type ID 本身。因为占用了 Type Script,如果 Cell 本身需要使用应用的 type script,应用的 type script 就必须支持某种 ID 机制。 ### 代理方式 只要在 lock script 中加上分支即可 - 可以使用 private key signing 解锁, - 或者同一个 tx 在存在对应的 type script,并且所执行的操作在授权范围之内 授权可以在以下地方存储 - lock script args 里直接指定。如果需要更新就必须修改所有使用该 lock 的 cell - lock script args 里指定一个 cell,在 cell 里保存,这样更新会比较方便。因为需要更新,需要使用 type id (或者其它类似的方式)指定 cell。 授权可以直接保存,或者保存 Merkel Tree Root。 ### 一种可行方案 - 使用 Combine Lock 为 Lock Script 增加分支 - Type Script 必须兼容 Cell ID - 定义一个授权的格式,并支持使用 Merkle Tree 保存 - 将授权单独保存的一个 Cell 中 - 在 Combine Lock 的分支中加入授权的支持。 ## Type Scripts Authorizing Type Scripts Type Scripts 的授权和 Lock Scripts 是相似的,最在的挑战在于如何编码 Type Script 做了什么操作。 ### 场景 - 模块化 - Type scripts composition - ESC 中 System 授权 System ### 操作识别 第一种方法是通过 Type Script inputs/outputs 进行推导。对于复杂的应用需要一定的模式识别,比如: - Inputs / Outputs 能方便的归纳出各自的 states 和 values,这样所有的操作都可以编码成:`{from_state, to_state, value_diff_range}`。 - 例子,inputs / outputs 中的第一个 cell 的前 N 了字节保存了 state 和 value 第二种方法是 Type Script 直接声明自己的操作,比如在 [Witness, OTX, Typed Message](https://www.notion.so/cryptape/Witness-OTX-Typed-Message-c6f11cb982474d77aac534b75314595a) 中,可以把操作写到 `TypedMessage` 里。 第三种方法,把操作的判断代理给 script,只要 script 执行结果是成功就认为是对应的操作。这样只需要在授权对象里填上对应的 script。验证交易的时候需要执行对应的 script。不过这个对组装交易带来更多的挑战,至少需要知道怎么补上 cell deps。 ## 授权时效性 ### 次数 在指定授权 data cell 的同时指定一个计数器 cell 即可,也可以 计数会导致更新瓶颈,但是考虑到可以为不同的操作分配不同的次数器,单个操作可以对交易排序,避免并发使用计数器,对于大部分场景是没影响的。 ### 时间 CKB 不支持 until,如果不使用 time oracle,需要使用两步 commit 的方式来判断是否授权已经过期。 别一种就是用户需要手动操作移除过期的授权。 退一步的话,如果不是要求交易发生时间在某个时间这前,而是可以接受当 input cell 在某个时间之前授权有效,那可以使用 input cell + dep header 实现。