From 5331bbce68c3fa79e98bc08a6c997093ff7cbd13 Mon Sep 17 00:00:00 2001 From: Andrew Coleman Date: Wed, 28 Jul 2021 14:43:34 +0100 Subject: [PATCH] FAB-18067 Discovery support Implicit Collections (#2784) Implemented the fix as suggested by Yacov in his Jira comment. Verified the fix works against the asset-transfer-secured-agreement sample which uses implicit collections. Signed-off-by: andrew-coleman --- core/chaincode/lifecycle/metadata_provider.go | 32 +++++++++++++++++++ .../lifecycle/metadata_provider_test.go | 5 +++ integration/discovery/discovery_test.go | 11 +++++++ 3 files changed, 48 insertions(+) diff --git a/core/chaincode/lifecycle/metadata_provider.go b/core/chaincode/lifecycle/metadata_provider.go index 94d1bd67bb8..fbc37c1efcb 100644 --- a/core/chaincode/lifecycle/metadata_provider.go +++ b/core/chaincode/lifecycle/metadata_provider.go @@ -13,6 +13,8 @@ import ( "github.com/hyperledger/fabric-protos-go/peer" "github.com/hyperledger/fabric/common/chaincode" "github.com/hyperledger/fabric/common/policies" + "github.com/hyperledger/fabric/common/policydsl" + "github.com/hyperledger/fabric/core/chaincode/implicitcollection" "github.com/hyperledger/fabric/protoutil" "github.com/pkg/errors" ) @@ -129,6 +131,36 @@ func (mp *MetadataProvider) Metadata(channel string, ccName string, collections CollectionsConfig: ccInfo.Definition.Collections, } + for _, col := range collections { + if isImplicit, mspID := implicitcollection.MspIDIfImplicitCollection(col); isImplicit { + // Implicit collection + + // Initialize definition of collections if it's missing + if ccInfo.Definition.Collections == nil { + ccInfo.Definition.Collections = &peer.CollectionConfigPackage{} + } + + spe := policydsl.SignedByMspMember(mspID) + ccInfo.Definition.Collections.Config = append(ccInfo.Definition.Collections.Config, &peer.CollectionConfig{ + Payload: &peer.CollectionConfig_StaticCollectionConfig{ + StaticCollectionConfig: &peer.StaticCollectionConfig{ + Name: col, + MemberOrgsPolicy: &peer.CollectionPolicyConfig{ + Payload: &peer.CollectionPolicyConfig_SignaturePolicy{ + SignaturePolicy: spe, + }, + }, + EndorsementPolicy: &peer.ApplicationPolicy{ + Type: &peer.ApplicationPolicy_SignaturePolicy{ + SignaturePolicy: spe, + }, + }, + }, + }, + }) + } + } + if ccInfo.Definition.Collections == nil { return ccMetadata } diff --git a/core/chaincode/lifecycle/metadata_provider_test.go b/core/chaincode/lifecycle/metadata_provider_test.go index f0f631278f6..82a1b93852f 100644 --- a/core/chaincode/lifecycle/metadata_provider_test.go +++ b/core/chaincode/lifecycle/metadata_provider_test.go @@ -78,6 +78,11 @@ var _ = Describe("MetadataProvider", func() { )) }) + It("returns metadata for implicit collections", func() { + metadata := metadataProvider.Metadata("testchannel", "cc-name", "_implicit_org_msp1") + Expect(metadata.CollectionPolicies).To(HaveKey("_implicit_org_msp1")) + }) + Context("when the chaincode is not found by the ChaincodeInfoProvider", func() { BeforeEach(func() { fakeChaincodeInfoProvider.ChaincodeInfoReturns(nil, errors.New("scrumtrulescent")) diff --git a/integration/discovery/discovery_test.go b/integration/discovery/discovery_test.go index 8b1ef3adadf..be441243785 100644 --- a/integration/discovery/discovery_test.go +++ b/integration/discovery/discovery_test.go @@ -645,6 +645,17 @@ var _ = Describe("DiscoveryService", func() { Expect(discovered[0].Layouts).To(HaveLen(1)) Expect(discovered[0].Layouts[0].QuantitiesByGroup).To(ConsistOf(uint32(1), uint32(1))) + By("discovering endorsers for Org1 implicit collection") + endorsers.Collection = "mycc:_implicit_org_Org1MSP" + de = discoverEndorsers(network, endorsers) + Eventually(endorsersByGroups(de), network.EventuallyTimeout).Should(ConsistOf( + ConsistOf(network.DiscoveredPeer(org1Peer0)), + )) + discovered = de() + Expect(discovered).To(HaveLen(1)) + Expect(discovered[0].Layouts).To(HaveLen(1)) + Expect(discovered[0].Layouts[0].QuantitiesByGroup).To(ConsistOf(uint32(1))) + By("trying to discover endorsers as an org3 admin") endorsers = commands.Endorsers{ UserCert: network.PeerUserCert(org3Peer0, "Admin"),