@@ -11,14 +11,19 @@ import (
1111 "encoding/json"
1212 "fmt"
1313
14+ "github.com/golang/protobuf/proto"
15+
16+ "github.com/hyperledger/fabric-sdk-go/internal/github.com/hyperledger/fabric/common/channelconfig"
1417 "github.com/hyperledger/fabric-sdk-go/internal/github.com/hyperledger/fabric/common/tools/protolator"
1518 "github.com/hyperledger/fabric-sdk-go/internal/github.com/hyperledger/fabric/protoutil"
1619 "github.com/hyperledger/fabric-sdk-go/internal/github.com/hyperledger/fabric/sdkinternal/configtxgen/encoder"
20+ "github.com/hyperledger/fabric-sdk-go/internal/github.com/hyperledger/fabric/sdkinternal/configtxlator/update"
1721 "github.com/pkg/errors"
1822
1923 "github.com/hyperledger/fabric-sdk-go/internal/github.com/hyperledger/fabric/sdkinternal/configtxgen/localconfig"
2024
2125 "github.com/hyperledger/fabric-sdk-go/pkg/fab/resource/genesisconfig"
26+ "github.com/hyperledger/fabric-sdk-go/third_party/github.com/hyperledger/fabric/protos/common"
2227 cb "github.com/hyperledger/fabric-sdk-go/third_party/github.com/hyperledger/fabric/protos/common"
2328)
2429
@@ -38,14 +43,19 @@ func CreateGenesisBlock(config *genesisconfig.Profile, channelID string) ([]byte
3843 if config .Orderer == nil {
3944 return nil , errors .Errorf ("refusing to generate block which is missing orderer section" )
4045 }
41- if config .Consortiums == nil {
42- logger .Warn ("Genesis block does not contain a consortiums group definition. This block cannot be used for orderer bootstrap." )
43- }
4446 genesisBlock := pgen .GenesisBlockForChannel (channelID )
4547 logger .Debug ("Writing genesis block" )
4648 return protoutil .Marshal (genesisBlock )
4749}
4850
51+ // CreateGenesisBlock creates a genesis block for a channel
52+ func CreateGenesisBlockForOrderer (config * genesisconfig.Profile , channelID string ) ([]byte , error ) {
53+ if config .Consortiums == nil {
54+ return nil , errors .Errorf ("Genesis block does not contain a consortiums group definition. This block cannot be used for orderer bootstrap." )
55+ }
56+ return CreateGenesisBlock (config , channelID )
57+ }
58+
4959func genesisToLocalConfig (config * genesisconfig.Profile ) (* localconfig.Profile , error ) {
5060 b , err := json .Marshal (config )
5161 if err != nil {
@@ -59,8 +69,11 @@ func genesisToLocalConfig(config *genesisconfig.Profile) (*localconfig.Profile,
5969 return c , nil
6070}
6171
62- // InspectGenesisBlock inspects a block
63- func InspectGenesisBlock (data []byte ) (string , error ) {
72+ // InspectBlock inspects a block
73+ func InspectBlock (data []byte ) (string , error ) {
74+ if len (data ) == 0 {
75+ return "" , fmt .Errorf ("missing block" )
76+ }
6477 logger .Debug ("Parsing genesis block" )
6578 block , err := protoutil .UnmarshalBlock (data )
6679 if err != nil {
@@ -115,3 +128,52 @@ func InspectChannelCreateTx(data []byte) (string, error) {
115128 }
116129 return buf .String (), nil
117130}
131+
132+ // CreateAnchorPeersUpdate creates an anchor peers update transaction
133+ func CreateAnchorPeersUpdate (conf * genesisconfig.Profile , channelID string , asOrg string ) (* common.Envelope , error ) {
134+ logger .Debug ("Generating anchor peer update" )
135+ if asOrg == "" {
136+ return nil , fmt .Errorf ("Must specify an organization to update the anchor peer for" )
137+ }
138+
139+ if conf .Application == nil {
140+ return nil , fmt .Errorf ("Cannot update anchor peers without an application section" )
141+ }
142+
143+ localConf , err := genesisToLocalConfig (conf )
144+ if err != nil {
145+ return nil , err
146+ }
147+
148+ original , err := encoder .NewChannelGroup (localConf )
149+ if err != nil {
150+ return nil , errors .WithMessage (err , "error parsing profile as channel group" )
151+ }
152+ original .Groups [channelconfig .ApplicationGroupKey ].Version = 1
153+
154+ updated := proto .Clone (original ).(* cb.ConfigGroup )
155+
156+ originalOrg , ok := original .Groups [channelconfig .ApplicationGroupKey ].Groups [asOrg ]
157+ if ! ok {
158+ return nil , errors .Errorf ("org with name '%s' does not exist in config" , asOrg )
159+ }
160+
161+ if _ , ok = originalOrg .Values [channelconfig .AnchorPeersKey ]; ! ok {
162+ return nil , errors .Errorf ("org '%s' does not have any anchor peers defined" , asOrg )
163+ }
164+
165+ delete (originalOrg .Values , channelconfig .AnchorPeersKey )
166+
167+ updt , err := update .Compute (& cb.Config {ChannelGroup : original }, & cb.Config {ChannelGroup : updated })
168+ if err != nil {
169+ return nil , errors .WithMessage (err , "could not compute update" )
170+ }
171+ updt .ChannelId = channelID
172+
173+ newConfigUpdateEnv := & cb.ConfigUpdateEnvelope {
174+ ConfigUpdate : protoutil .MarshalOrPanic (updt ),
175+ }
176+
177+ return protoutil .CreateSignedEnvelope (cb .HeaderType_CONFIG_UPDATE , channelID , nil , newConfigUpdateEnv , 0 , 0 )
178+
179+ }
0 commit comments