github.com/true-sqn/fabric@v2.1.1+incompatible/core/cclifecycle/util.go (about) 1 /* 2 Copyright IBM Corp. All Rights Reserved. 3 4 SPDX-License-Identifier: Apache-2.0 5 */ 6 7 package cclifecycle 8 9 import ( 10 "github.com/golang/protobuf/proto" 11 "github.com/hyperledger/fabric/common/chaincode" 12 "github.com/hyperledger/fabric/core/common/ccprovider" 13 "github.com/hyperledger/fabric/core/common/privdata" 14 "github.com/pkg/errors" 15 ) 16 17 var ( 18 // AcceptAll returns a predicate that accepts all Metadata 19 AcceptAll ChaincodePredicate = func(cc chaincode.Metadata) bool { 20 return true 21 } 22 ) 23 24 // ChaincodePredicate accepts or rejects chaincode based on its metadata 25 type ChaincodePredicate func(cc chaincode.Metadata) bool 26 27 // DeployedChaincodes retrieves the metadata of the given deployed chaincodes 28 func DeployedChaincodes(q Query, filter ChaincodePredicate, loadCollections bool, chaincodes ...string) (chaincode.MetadataSet, error) { 29 defer q.Done() 30 31 var res chaincode.MetadataSet 32 for _, cc := range chaincodes { 33 data, err := q.GetState("lscc", cc) 34 if err != nil { 35 Logger.Error("Failed querying lscc namespace:", err) 36 return nil, errors.WithStack(err) 37 } 38 if len(data) == 0 { 39 Logger.Info("Chaincode", cc, "isn't instantiated") 40 continue 41 } 42 ccInfo, err := extractCCInfo(data) 43 if err != nil { 44 Logger.Error("Failed extracting chaincode info about", cc, "from LSCC returned payload. Error:", err) 45 continue 46 } 47 if ccInfo.Name != cc { 48 Logger.Error("Chaincode", cc, "is listed in LSCC as", ccInfo.Name) 49 continue 50 } 51 52 instCC := chaincode.Metadata{ 53 Name: ccInfo.Name, 54 Version: ccInfo.Version, 55 Id: ccInfo.Id, 56 Policy: ccInfo.Policy, 57 } 58 59 if !filter(instCC) { 60 Logger.Debug("Filtered out", instCC) 61 continue 62 } 63 64 if loadCollections { 65 key := privdata.BuildCollectionKVSKey(cc) 66 collectionData, err := q.GetState("lscc", key) 67 if err != nil { 68 Logger.Errorf("Failed querying lscc namespace for %s: %v", key, err) 69 return nil, errors.WithStack(err) 70 } 71 ccp, err := privdata.ParseCollectionConfig(collectionData) 72 if err != nil { 73 Logger.Errorf("failed to parse collection config, error %s", err.Error()) 74 return nil, errors.Wrapf(err, "failed to parse collection config") 75 } 76 instCC.CollectionsConfig = ccp 77 Logger.Debug("Retrieved collection config for", cc, "from", key) 78 } 79 80 res = append(res, instCC) 81 } 82 Logger.Debug("Returning", res) 83 return res, nil 84 } 85 86 func deployedCCToNameVersion(cc chaincode.Metadata) nameVersion { 87 return nameVersion{ 88 name: cc.Name, 89 version: cc.Version, 90 } 91 } 92 93 func extractCCInfo(data []byte) (*ccprovider.ChaincodeData, error) { 94 cd := &ccprovider.ChaincodeData{} 95 if err := proto.Unmarshal(data, cd); err != nil { 96 return nil, errors.Wrap(err, "failed unmarshaling lscc read value into ChaincodeData") 97 } 98 return cd, nil 99 } 100 101 type nameVersion struct { 102 name string 103 version string 104 } 105 106 func installedCCToNameVersion(cc chaincode.InstalledChaincode) nameVersion { 107 return nameVersion{ 108 name: cc.Name, 109 version: cc.Version, 110 } 111 } 112 113 func names(installedChaincodes []chaincode.InstalledChaincode) []string { 114 var ccs []string 115 for _, cc := range installedChaincodes { 116 ccs = append(ccs, cc.Name) 117 } 118 return ccs 119 }