github.com/s7techlab/cckit@v0.10.5/gateway/opt.go (about) 1 package gateway 2 3 import ( 4 "context" 5 "fmt" 6 7 "github.com/golang/protobuf/jsonpb" 8 "github.com/golang/protobuf/proto" 9 "github.com/hyperledger/fabric-protos-go/peer" 10 "github.com/hyperledger/fabric/msp" 11 12 "github.com/s7techlab/cckit/extensions/encryption" 13 "github.com/s7techlab/cckit/state/mapping" 14 ) 15 16 type ( 17 Opts struct { 18 Context []ContextOpt 19 Input []InputOpt 20 Output []OutputOpt 21 Event []EventOpt 22 } 23 24 InstanceOpts struct { 25 Locator *ChaincodeLocator 26 Opts Opts 27 } 28 29 Opt func(*Opts) 30 31 ContextOpt func(ctx context.Context) context.Context 32 InputOpt func(input *ChaincodeInput) error 33 OutputOpt func(action InvocationType, response *peer.Response) error 34 EventOpt func(event *ChaincodeEvent) error 35 ) 36 37 func WithDefaultSigner(defaultSigner msp.SigningIdentity) Opt { 38 return func(opts *Opts) { 39 opts.Context = append(opts.Context, func(ctx context.Context) context.Context { 40 return ContextWithDefaultSigner(ctx, defaultSigner) 41 }) 42 } 43 } 44 45 func WithDefaultTransientMapValue(key string, value []byte) Opt { 46 return func(o *Opts) { 47 o.Input = append(o.Input, func(input *ChaincodeInput) error { 48 if input.Transient == nil { 49 input.Transient = make(map[string][]byte) 50 } 51 if _, exists := input.Transient[key]; !exists { 52 input.Transient[key] = value 53 } 54 return nil 55 }) 56 } 57 } 58 59 func WithEncryption(encKey []byte) Opt { 60 return func(o *Opts) { 61 WithDefaultTransientMapValue(encryption.TransientMapKey, encKey)(o) 62 WithArgsEncryption(encKey)(o) 63 WithInvokePayloadDecryption(encKey)(o) 64 WithEventDecryption(encKey)(o) 65 } 66 } 67 68 func WithArgsEncryption(encKey []byte) Opt { 69 return func(o *Opts) { 70 o.Input = append(o.Input, func(ccInput *ChaincodeInput) (err error) { 71 ccInput.Args, err = encryption.EncryptArgsBytes(encKey, ccInput.Args) 72 return err 73 }) 74 } 75 } 76 77 func WithInvokePayloadDecryption(encKey []byte) Opt { 78 return func(o *Opts) { 79 o.Output = append(o.Output, func(action InvocationType, r *peer.Response) (err error) { 80 if action != InvocationType_INVOCATION_TYPE_INVOKE { 81 return nil 82 } 83 r.Payload, err = encryption.Decrypt(encKey, r.Payload) 84 if err != nil { 85 return fmt.Errorf(`decrypt invoke payload: %w`, err) 86 } 87 return nil 88 }) 89 } 90 } 91 92 func WithEventDecryption(encKey []byte) Opt { 93 return func(o *Opts) { 94 o.Event = append(o.Event, func(e *ChaincodeEvent) error { 95 de, err := encryption.DecryptEvent(encKey, e.Event) 96 if err != nil { 97 return err 98 } 99 100 e.Event = de 101 return nil 102 }) 103 } 104 } 105 106 func WithEventResolver(resolver mapping.EventResolver) Opt { 107 return func(o *Opts) { 108 o.Event = append(o.Event, func(e *ChaincodeEvent) error { 109 eventPayload, err := resolver.Resolve(e.Event.EventName, e.Event.Payload) 110 if err != nil { 111 return err 112 } 113 114 bb, err := (&jsonpb.Marshaler{EmitDefaults: true, OrigName: true}).MarshalToString(eventPayload.(proto.Message)) 115 if err != nil { 116 return err 117 } 118 119 e.Payload = &RawJson{Value: []byte(bb)} 120 return nil 121 }) 122 } 123 }