本節(jié)詳細(xì)介紹可以參考官方文檔
Quorum目前的許可系統(tǒng)只限于節(jié)點(diǎn)等級的許可辐马,只有在permission-nodes.json
文件中定義的節(jié)點(diǎn)才能夠加入網(wǎng)絡(luò)辽聊。這個準(zhǔn)許模型已經(jīng)要被優(yōu)化成基于智能合約的授權(quán)許可模型壳坪,新模型在管理節(jié)點(diǎn)、賬戶和賬戶權(quán)限管理上都有一定靈活度显押,整體框架模型如下圖所示
在優(yōu)化模型結(jié)構(gòu)圖中,一個網(wǎng)絡(luò)聚合了一群組織。網(wǎng)絡(luò)層級有網(wǎng)絡(luò)管理員賬號匀借,網(wǎng)絡(luò)管理員可以提議和投票新組織加入網(wǎng)絡(luò),也可以指定某個賬號為機(jī)構(gòu)管理員賬號平窘。
機(jī)構(gòu)管理員賬號可以創(chuàng)建機(jī)構(gòu)內(nèi)角色吓肋、子機(jī)構(gòu)、為自己機(jī)構(gòu)下的賬號賦予某種角色的功能瑰艘,指定某個節(jié)點(diǎn)為本機(jī)構(gòu)節(jié)點(diǎn)是鬼。子機(jī)構(gòu)也可以創(chuàng)建自己的角色、子機(jī)構(gòu)紫新、節(jié)點(diǎn)均蜜。。弊琴。機(jī)構(gòu)管理賬號在機(jī)構(gòu)層面管理和控制各項行為活動兆龙。父級機(jī)構(gòu)管理原可以創(chuàng)建管理員角色,并將該角色的功能賦予其他賬號敲董。
一紫皇、智能合約設(shè)計
Quorum權(quán)限系統(tǒng)智能合約的設(shè)計遵循Proxy-Implementation-Storage pattern
(代理-實(shí)現(xiàn)-存儲 模式),采用該模式可以保證及時業(yè)務(wù)邏輯層改變腋寨,也不會影響數(shù)據(jù)存儲層和接口層的聪铺。智能合約的具體描述如下:
PermissionsUpgrade.sol
存儲implementation合約的地址,這份合約地址只有g(shù)uardian賬戶可以操作改變PermissionsInterface.sol
接口定義萄窜,不含任何業(yè)務(wù)邏輯铃剔,會將接收到的請求轉(zhuǎn)發(fā)給業(yè)務(wù)合約PermissionsImplementation.sol
包含所有授權(quán)系統(tǒng)的操作邏輯。只接收在PermissionsUpgradable.sol
中定義的接口請求查刻,并根據(jù)相應(yīng)操作和對應(yīng)的存儲合約交互OrgManager.sol
存儲機(jī)構(gòu)和子機(jī)構(gòu)信息键兜,只接受來自PermissionsUpgrade.sol
合約中定義的implementation合約地址的請求AccountManager.sol
存儲所有賬戶相關(guān)的信息,包括賬戶和組織和歸屬關(guān)系穗泵,一個賬戶地址有哪些權(quán)限等普气。同時也存儲一個賬號的狀態(tài):PendingApproval
,Active
,Inactive
,Suspended
,Blacklisted
orRevoked
NodeManager.sol
存儲所有和節(jié)點(diǎn)相關(guān)的數(shù)據(jù),包括節(jié)點(diǎn)和機(jī)構(gòu)佃延、子機(jī)構(gòu)的關(guān)系现诀,節(jié)點(diǎn)的狀態(tài):PendingApproval
,Approved
,Deactivated
orBlacklisted
-
RoleManager.sol
同樣只接收在PermissionsUpgrdable.sol
定義的implementation合約的請求夷磕。 存儲角色和組織的關(guān)系。角色能夠包括的權(quán)限如下:-
Readonly
只讀權(quán)限 -
Transact
只能交易仔沿,不能部署合約 -
ContractDeploy
可以交易坐桩,也可以部署合約 -
FullAccess
全權(quán)限
如果一個角色被撤銷,那么所有被賦予這個角色的賬戶都會失去角色原有的權(quán)限封锉。
-
VoterManager.sol
存儲網(wǎng)絡(luò)管理員信息绵跷。在創(chuàng)建網(wǎng)絡(luò)時會預(yù)先定義一系列的網(wǎng)路管理員賬號,這些賬號都會被記錄在本合約中烘浦。一旦網(wǎng)絡(luò)層級有需要投票的事件發(fā)生抖坪,投票事件也會被記錄在本合約中。
<a name='init'>二闷叉、權(quán)限模型的部署</a>
- 部署網(wǎng)絡(luò)初始節(jié)點(diǎn)
- 部署
PermissionsUpgradable.sol
合約。部署該合約時脊阴,作為參數(shù)需要指定一個guardian賬號地址 - 部署剩余的合約握侧。部署剩余合約的時候都需要
PermissionsUpgradable.sol
合約地址作為部署參數(shù) - 所有合約部署完成后,按以下格式創(chuàng)建
permission-config.json
文件
{
"upgradableAddress": "0x1932c48b2bf8102ba33b4a6b545c32236e342f34",
"interfaceAddress": "0x4d3bfd7821e237ffe84209d8e638f9f309865b87",
"implAddress": "0xfe0602d820f42800e3ef3f89e1c39cd15f78d283",
"nodeMgrAddress": "0x8a5e2a6343108babed07899510fb42297938d41f",
"accountMgrAddress": "0x9d13c6d3afe1721beef56b55d303b09e021e27ab",
"roleMgrAddress": "0x1349f3e1b8d71effb47b840594ff27da7e603d17",
"voterMgrAddress": "0xd9d64b7dc034fafdba5dc2902875a67b5d586420",
"orgMgrAddress" : "0x938781b9796aea6376e40ca158f67fa89d5d8a18",
"nwAdminOrg": "ADMINORG",
"nwAdminRole" : "ADMIN",
"orgAdminRole" : "ORGADMIN",
"accounts":["0xed9d02e382b34818e88b88a309c7fe71e65f419d", "0xca843569e3427144cead5e4d5999a3d0ccf92b8e"],
"subOrgBreadth" : 3,
"subOrgDepth" : 4
}
-
使用guardian account調(diào)用
PermissionsUpgradable.sol
的init服務(wù)-
使用geth加載以下內(nèi)容
ac = eth.accounts[0]; web3.eth.defaultAccount = ac; var abi = [{"constant":true,"inputs":[],"name":"getPermImpl","outputs":[{"name":"","type":"address"}],"payable":false,"stateMutability":"view","type":"function"},{"constant":false,"inputs":[{"name":"_proposedImpl","type":"address"}],"name":"confirmImplChange","outputs":[],"payable":false,"stateMutability":"nonpayable","type":"function"},{"constant":true,"inputs":[],"name":"getGuardian","outputs":[{"name":"","type":"address"}],"payable":false,"stateMutability":"view","type":"function"},{"constant":true,"inputs":[],"name":"getPermInterface","outputs":[{"name":"","type":"address"}],"payable":false,"stateMutability":"view","type":"function"},{"constant":false,"inputs":[{"name":"_permInterface","type":"address"},{"name":"_permImpl","type":"address"}],"name":"init","outputs":[],"payable":false,"stateMutability":"nonpayable","type":"function"},{"inputs":[{"name":"_guardian","type":"address"}],"payable":false,"stateMutability":"nonpayable","type":"constructor"}]; var upgr = web3.eth.contract(abi).at("0x1932c48b2bf8102ba33b4a6b545c32236e342f34"); // address of the upgradable contracts var impl = "0xfe0602d820f42800e3ef3f89e1c39cd15f78d283" // address of the implementation contracts var intr = "0x4d3bfd7821e237ffe84209d8e638f9f309865b87" // address of the interface contracts
執(zhí)行
upgr.init(intr, impl, {from: <guardian account>, gas: 4500000})
-
關(guān)閉所有g(shù)eth節(jié)點(diǎn)嘿期,并將
permission-config.json
文件拷貝進(jìn)每個節(jié)點(diǎn)的data文件夾下將所有
geth
節(jié)點(diǎn)以--permissioned
方式啟動
三品擎、API文檔
四、使用方法
1 初始化網(wǎng)絡(luò)
具體操作方法可以參照本章第二節(jié)權(quán)限模型的部署
-
假設(shè)初始節(jié)點(diǎn)的配置文件
static-nodes.json
的內(nèi)容如下:[ "enode://72c0572f7a2492cffb5efc3463ef350c68a0446402a123dacec9db5c378789205b525b3f5f623f7548379ab0e5957110bffcf43a6115e450890f97a9f65a681a@127.0.0.1:21000?discport=0", "enode://7a1e3b5c6ad614086a4e5fb55b6fe0a7cf7a7ac92ac3a60e6033de29df14148e7a6a7b4461eb70639df9aa379bd77487937bea0a8da862142b12d326c7285742@127.0.0.1:21001?discport=0", "enode://5085e86db5324ca4a55aeccfbb35befb412def36e6bc74f166102796ac3c8af3cc83a5dec9c32e6fd6d359b779dba9a911da8f3e722cb11eb4e10694c59fd4a1@127.0.0.1:21002?discport=0", "enode://28a4afcf56ee5e435c65b9581fc36896cc684695fa1db83c9568de4353dc6664b5cab09694d9427e9cf26a5cd2ac2fb45a63b43bb24e46ee121f21beb3a7865e@127.0.0.1:21003?discport=0" ]
-
網(wǎng)絡(luò)的權(quán)限配置如下
> quorumPermission.orgList [{ fullOrgId: "ADMINORG", level: 1, orgId: "ADMINORG", parentOrgId: "", status: 2, subOrgList: null, ultimateParent: "ADMINORG" }] > quorumPermission.getOrgDetails("ADMINORG") { acctList: [{ acctId: "0xed9d02e382b34818e88b88a309c7fe71e65f419d", isOrgAdmin: true, orgId: "ADMINORG", roleId: "ADMIN", status: 2 }, { acctId: "0xca843569e3427144cead5e4d5999a3d0ccf92b8e", isOrgAdmin: true, orgId: "ADMINORG", roleId: "ADMIN", status: 2 }], nodeList: [{ orgId: "ADMINORG", status: 2, url: "enode://72c0572f7a2492cffb5efc3463ef350c68a0446402a123dacec9db5c378789205b525b3f5f623f7548379ab0e5957110bffcf43a6115e450890f97a9f65a681a@127.0.0.1:21000?discport=0" }, { orgId: "ADMINORG", status: 2, url: "enode://7a1e3b5c6ad614086a4e5fb55b6fe0a7cf7a7ac92ac3a60e6033de29df14148e7a6a7b4461eb70639df9aa379bd77487937bea0a8da862142b12d326c7285742@127.0.0.1:21001?discport=0" }, { orgId: "ADMINORG", status: 2, url: "enode://5085e86db5324ca4a55aeccfbb35befb412def36e6bc74f166102796ac3c8af3cc83a5dec9c32e6fd6d359b779dba9a911da8f3e722cb11eb4e10694c59fd4a1@127.0.0.1:21002?discport=0" }, { orgId: "ADMINORG", status: 2, url: "enode://28a4afcf56ee5e435c65b9581fc36896cc684695fa1db83c9568de4353dc6664b5cab09694d9427e9cf26a5cd2ac2fb45a63b43bb24e46ee121f21beb3a7865e@127.0.0.1:21003?discport=0" }], roleList: [{ access: 3, active: true, isAdmin: true, isVoter: true, orgId: "ADMINORG", roleId: "ADMIN" }], subOrgList: null }
2 提議新組織加入網(wǎng)絡(luò)
一旦網(wǎng)絡(luò)部署完成以后备徐,網(wǎng)絡(luò)管理員賬號可以提議一個新的組織加入網(wǎng)絡(luò)萄传。網(wǎng)絡(luò)中所有的管理員賬號會對這件事進(jìn)行投票,投票通過后新組織被允許加入網(wǎng)絡(luò)蜜猾。
具體操作執(zhí)行可以查看API文檔中的proposing 和 approving 操作
具體步驟示意可以查看官方文檔說明
步驟
- 提議
- 查看提議的組織狀態(tài)
- 投票
- 投票結(jié)果超過半數(shù)秀菱,同意新組織節(jié)點(diǎn)加入
- 新組織的節(jié)點(diǎn)加入網(wǎng)絡(luò)。如果當(dāng)前網(wǎng)絡(luò)使用的是raft共識蹭睡,需要注意衍菱,在新組織節(jié)點(diǎn)加入網(wǎng)絡(luò)時要確保:
- 新的節(jié)點(diǎn)在raft層已經(jīng)被添加為peer
raft.addPeer(<<enodeId>>)
- 根據(jù)上一步獲得的raft peer id,使用
geth
以--raftjoinexisting
模式啟動新節(jié)點(diǎn)
- 新的節(jié)點(diǎn)在raft層已經(jīng)被添加為peer
3 組織管理員管理和準(zhǔn)入許可
> quorumPermission.addSubOrg("ORG1", "SUB1", "enode://239c1f044a2b03b6c4713109af036b775c5418fe4ca63b04b1ce00124af00ddab7cc088fc46020cdc783b6207efe624551be4c06a994993d8d70f684688fb7cf@127.0.0.1:21006?discport=0", {from: eth.accounts[0]})
"Action completed successfully"
> quorumPermission.getOrgDetails("ORG1.SUB1")
{
acctList: null,
nodeList: [{
orgId: "ORG1.SUB1",
status: 2,
url: "enode://239c1f044a2b03b6c4713109af036b775c5418fe4ca63b04b1ce00124af00ddab7cc088fc46020cdc783b6207efe624551be4c06a994993d8d70f684688fb7cf@127.0.0.1:21006?discport=0"
}],
roleList: null,
subOrgList: null
}
添加子機(jī)構(gòu)并不是強(qiáng)制性的肩豁,如果機(jī)構(gòu)管理員想為新創(chuàng)建的子機(jī)構(gòu)添加一個管理賬號脊串,那么機(jī)構(gòu)管理員首先需要
- 創(chuàng)建一個具有isAdmin權(quán)限的角色,并賦予子機(jī)構(gòu)下某個賬戶這個角色 API
- 將新建的角色賦予子機(jī)構(gòu)的賬號
需要注意的一點(diǎn)清钥,上級機(jī)構(gòu)擁有本機(jī)構(gòu)和自己子機(jī)構(gòu)的所有管理權(quán)限琼锋,而子機(jī)構(gòu)管理員只擁有自己組織的管理權(quán)限。
4 暫停某個機(jī)構(gòu)
- 網(wǎng)絡(luò)管理員(Network Admin) 提議修改某個組織的狀態(tài)為“暫時關(guān)閉”
- 所有網(wǎng)絡(luò)管理員針對此條提議進(jìn)行投票
5 組織層/網(wǎng)絡(luò)層管理權(quán)限的授予
在某些情況下祟昭,我們可以一個賬號同時具有機(jī)構(gòu)管理員的權(quán)限和網(wǎng)絡(luò)管理員的權(quán)限缕坎。同樣也是需要進(jìn)過兩個步驟
- 提議
- 投票