// Query callback representing the query of a chaincode func (t *SimpleChaincode) Query(stub shim.ChaincodeStubInterface, function string, args []string) ([]byte, error) { if function != "query" { return nil, errors.New("Invalid query function name. Expecting \"query\"") } var sum string // Sum entity var Aval, Bval, sumVal int // value of sum entity - to be computed var err error // Can query another chaincode within query, but cannot put state or invoke another chaincode (in transaction context) if len(args) != 2 { return nil, errors.New("Incorrect number of arguments. Expecting 2") } chaincodeURL := args[0] sum = args[1] // Query chaincode_example02 f := "query" queryArgs := util.ToChaincodeArgs(f, "a") response, err := stub.QueryChaincode(chaincodeURL, queryArgs) if err != nil { errStr := fmt.Sprintf("Failed to query chaincode. Got error: %s", err.Error()) fmt.Printf(errStr) return nil, errors.New(errStr) } Aval, err = strconv.Atoi(string(response)) if err != nil { errStr := fmt.Sprintf("Error retrieving state from ledger for queried chaincode: %s", err.Error()) fmt.Printf(errStr) return nil, errors.New(errStr) } queryArgs = util.ToChaincodeArgs(f, "b") response, err = stub.QueryChaincode(chaincodeURL, queryArgs) if err != nil { errStr := fmt.Sprintf("Failed to query chaincode. Got error: %s", err.Error()) fmt.Printf(errStr) return nil, errors.New(errStr) } Bval, err = strconv.Atoi(string(response)) if err != nil { errStr := fmt.Sprintf("Error retrieving state from ledger for queried chaincode: %s", err.Error()) fmt.Printf(errStr) return nil, errors.New(errStr) } // Compute sum sumVal = Aval + Bval fmt.Printf("Query chaincode successful. Got sum %d\n", sumVal) jsonResp := "{\"Name\":\"" + sum + "\",\"Value\":\"" + strconv.Itoa(sumVal) + "\"}" fmt.Printf("Query Response:%s\n", jsonResp) return []byte(strconv.Itoa(sumVal)), nil }
// Invoke queries another chaincode and updates its own state func (t *SimpleChaincode) invoke(stub shim.ChaincodeStubInterface, args []string) ([]byte, error) { var sum string // Sum entity var Aval, Bval, sumVal int // value of sum entity - to be computed var err error if len(args) != 2 { return nil, errors.New("Incorrect number of arguments. Expecting 2") } chaincodeURL := args[0] // Expecting "github.com/hyperledger/fabric/core/example/chaincode/chaincode_example02" sum = args[1] // Query chaincode_example02 f := "query" queryArgs := util.ToChaincodeArgs(f, "a") response, err := stub.InvokeChaincode(chaincodeURL, queryArgs) if err != nil { errStr := fmt.Sprintf("Failed to query chaincode. Got error: %s", err.Error()) fmt.Printf(errStr) return nil, errors.New(errStr) } Aval, err = strconv.Atoi(string(response)) if err != nil { errStr := fmt.Sprintf("Error retrieving state from ledger for queried chaincode: %s", err.Error()) fmt.Printf(errStr) return nil, errors.New(errStr) } queryArgs = util.ToChaincodeArgs(f, "b") response, err = stub.InvokeChaincode(chaincodeURL, queryArgs) if err != nil { errStr := fmt.Sprintf("Failed to query chaincode. Got error: %s", err.Error()) fmt.Printf(errStr) return nil, errors.New(errStr) } Bval, err = strconv.Atoi(string(response)) if err != nil { errStr := fmt.Sprintf("Error retrieving state from ledger for queried chaincode: %s", err.Error()) fmt.Printf(errStr) return nil, errors.New(errStr) } // Compute sum sumVal = Aval + Bval // Write sumVal back to the ledger err = stub.PutState(sum, []byte(strconv.Itoa(sumVal))) if err != nil { return nil, err } fmt.Printf("Invoke chaincode successful. Got sum %d\n", sumVal) return []byte(strconv.Itoa(sumVal)), nil }
//helper func (p *PassthruChaincode) iq(invoke bool, stub shim.ChaincodeStubInterface, function string, args []string) ([]byte, error) { if function == "" { return nil, errors.New("Chaincode ID not provided") } chaincodeID := function if invoke { return stub.InvokeChaincode(chaincodeID, util.ToChaincodeArgs(args...)) } return stub.QueryChaincode(chaincodeID, util.ToChaincodeArgs(args...)) }
// TestUpgradeAndInvoke deploys chaincode_example01, upgrade it with chaincode_example02, then invoke it func TestDeployAndUpgrade(t *testing.T) { chainID := util.GetTestChainID() var ctxt = context.Background() url1 := "github.com/hyperledger/fabric/examples/chaincode/go/chaincode_example01" url2 := "github.com/hyperledger/fabric/examples/chaincode/go/chaincode_example02" chaincodeID1 := &pb.ChaincodeID{Path: url1, Name: "upgradeex01"} chaincodeID2 := &pb.ChaincodeID{Path: url2, Name: "upgradeex01"} f := "init" argsDeploy := util.ToChaincodeArgs(f, "a", "100", "b", "200") spec := &pb.ChaincodeSpec{Type: 1, ChaincodeID: chaincodeID1, CtorMsg: &pb.ChaincodeInput{Args: argsDeploy}} cccid1 := chaincode.NewCCContext(chainID, "upgradeex01", "", "", false, nil) cccid2 := chaincode.NewCCContext(chainID, "upgradeex02", "", "", false, nil) resp, prop, err := deploy(endorserServer, chainID, spec, nil) chaincodeName := spec.ChaincodeID.Name if err != nil { t.Fail() chaincode.GetChain().Stop(ctxt, cccid1, &pb.ChaincodeDeploymentSpec{ChaincodeSpec: &pb.ChaincodeSpec{ChaincodeID: chaincodeID1}}) chaincode.GetChain().Stop(ctxt, cccid2, &pb.ChaincodeDeploymentSpec{ChaincodeSpec: &pb.ChaincodeSpec{ChaincodeID: chaincodeID2}}) t.Logf("Error deploying <%s>: %s", chaincodeName, err) return } err = endorserServer.(*Endorser).commitTxSimulation(prop, chainID, signer, resp) if err != nil { t.Fail() chaincode.GetChain().Stop(ctxt, cccid1, &pb.ChaincodeDeploymentSpec{ChaincodeSpec: &pb.ChaincodeSpec{ChaincodeID: chaincodeID1}}) chaincode.GetChain().Stop(ctxt, cccid2, &pb.ChaincodeDeploymentSpec{ChaincodeSpec: &pb.ChaincodeSpec{ChaincodeID: chaincodeID2}}) t.Logf("Error committing <%s>: %s", chaincodeName, err) return } argsUpgrade := util.ToChaincodeArgs(f, "a", "150", "b", "300") spec = &pb.ChaincodeSpec{Type: 1, ChaincodeID: chaincodeID2, CtorMsg: &pb.ChaincodeInput{Args: argsUpgrade}} resp, prop, err = upgrade(endorserServer, chainID, spec, nil) if err != nil { t.Fail() chaincode.GetChain().Stop(ctxt, cccid1, &pb.ChaincodeDeploymentSpec{ChaincodeSpec: &pb.ChaincodeSpec{ChaincodeID: chaincodeID1}}) chaincode.GetChain().Stop(ctxt, cccid2, &pb.ChaincodeDeploymentSpec{ChaincodeSpec: &pb.ChaincodeSpec{ChaincodeID: chaincodeID2}}) t.Logf("Error upgrading <%s>: %s", chaincodeName, err) return } fmt.Printf("Upgrade test passed\n") t.Logf("Upgrade test passed") chaincode.GetChain().Stop(ctxt, cccid1, &pb.ChaincodeDeploymentSpec{ChaincodeSpec: &pb.ChaincodeSpec{ChaincodeID: chaincodeID1}}) chaincode.GetChain().Stop(ctxt, cccid2, &pb.ChaincodeDeploymentSpec{ChaincodeSpec: &pb.ChaincodeSpec{ChaincodeID: chaincodeID2}}) }
// Test the invocation of a transaction. func TestRangeQuery(t *testing.T) { //TODO enable after ledger enables RangeQuery t.Skip() chainID := util.GetTestChainID() lis, err := initPeer(chainID) if err != nil { t.Fail() t.Logf("Error creating peer: %s", err) } defer finitPeer(lis, chainID) var ctxt = context.Background() url := "github.com/hyperledger/fabric/examples/chaincode/go/map" cID := &pb.ChaincodeID{Name: "tmap", Path: url} f := "init" args := util.ToChaincodeArgs(f) spec := &pb.ChaincodeSpec{Type: 1, ChaincodeID: cID, CtorMsg: &pb.ChaincodeInput{Args: args}} cccid := NewCCContext(chainID, "tmap", "", "", false, nil) _, err = deploy(ctxt, cccid, spec) chaincodeID := spec.ChaincodeID.Name if err != nil { t.Fail() t.Logf("Error initializing chaincode %s(%s)", chaincodeID, err) theChaincodeSupport.Stop(ctxt, cccid, &pb.ChaincodeDeploymentSpec{ChaincodeSpec: spec}) return } // Invoke second chaincode, which will inturn invoke the first chaincode f = "keys" args = util.ToChaincodeArgs(f) spec = &pb.ChaincodeSpec{Type: 1, ChaincodeID: cID, CtorMsg: &pb.ChaincodeInput{Args: args}} _, _, _, err = invoke(ctxt, chainID, spec) if err != nil { t.Fail() t.Logf("Error invoking <%s>: %s", chaincodeID, err) theChaincodeSupport.Stop(ctxt, cccid, &pb.ChaincodeDeploymentSpec{ChaincodeSpec: spec}) return } theChaincodeSupport.Stop(ctxt, cccid, &pb.ChaincodeDeploymentSpec{ChaincodeSpec: spec}) }
// Invoke chaincode_example02 func invokeExample02Transaction(ctxt context.Context, cccid *CCContext, cID *pb.ChaincodeID, args []string, destroyImage bool) error { f := "init" argsDeploy := util.ToChaincodeArgs(f, "a", "100", "b", "200") spec := &pb.ChaincodeSpec{Type: 1, ChaincodeID: cID, CtorMsg: &pb.ChaincodeInput{Args: argsDeploy}} _, err := deploy(ctxt, cccid, spec) chaincodeID := spec.ChaincodeID.Name if err != nil { return fmt.Errorf("Error deploying <%s>: %s", chaincodeID, err) } time.Sleep(time.Second) if destroyImage { theChaincodeSupport.Stop(ctxt, cccid, &pb.ChaincodeDeploymentSpec{ChaincodeSpec: spec}) dir := container.DestroyImageReq{CCID: ccintf.CCID{ChaincodeSpec: spec, NetworkID: theChaincodeSupport.peerNetworkID, PeerID: theChaincodeSupport.peerID, ChainID: cccid.ChainID}, Force: true, NoPrune: true} _, err = container.VMCProcess(ctxt, container.DOCKER, dir) if err != nil { err = fmt.Errorf("Error destroying image: %s", err) return err } } f = "invoke" invokeArgs := append([]string{f}, args...) spec = &pb.ChaincodeSpec{Type: 1, ChaincodeID: cID, CtorMsg: &pb.ChaincodeInput{Args: util.ToChaincodeArgs(invokeArgs...)}} _, uuid, _, err := invoke(ctxt, cccid.ChainID, spec) if err != nil { return fmt.Errorf("Error invoking <%s>: %s", cccid.Name, err) } cccid.TxID = uuid err = checkFinalState(cccid) if err != nil { return fmt.Errorf("Incorrect final state after transaction for <%s>: %s", chaincodeID, err) } // Test for delete state f = "delete" delArgs := util.ToChaincodeArgs(f, "a") spec = &pb.ChaincodeSpec{Type: 1, ChaincodeID: cID, CtorMsg: &pb.ChaincodeInput{Args: delArgs}} _, uuid, _, err = invoke(ctxt, cccid.ChainID, spec) if err != nil { return fmt.Errorf("Error deleting state in <%s>: %s", cccid.Name, err) } return nil }
func deploy(admCert crypto.CertificateHandler) error { // Prepare the spec. The metadata includes the identity of the administrator spec := &pb.ChaincodeSpec{ Type: 1, ChaincodeID: &pb.ChaincodeID{Name: "mycc"}, CtorMsg: &pb.ChaincodeInput{Args: util.ToChaincodeArgs("init")}, Metadata: admCert.GetCertificate(), ConfidentialityLevel: pb.ConfidentialityLevel_PUBLIC, } // First build and get the deployment spec var ctx = context.Background() chaincodeDeploymentSpec, err := getDeploymentSpec(ctx, spec) if err != nil { return err } tid := chaincodeDeploymentSpec.ChaincodeSpec.ChaincodeID.Name // Now create the Transactions message and send to Peer. transaction, err := administrator.NewChaincodeDeployTransaction(chaincodeDeploymentSpec, tid) if err != nil { return fmt.Errorf("Error deploying chaincode: %s ", err) } ledger, err := ledger.GetLedger() ledger.BeginTxBatch("1") _, _, err = chaincode.Execute(ctx, chaincode.GetChain(chaincode.DefaultChain), transaction) if err != nil { return fmt.Errorf("Error deploying chaincode: %s", err) } ledger.CommitTxBatch("1", []*pb.Transaction{transaction}, nil, nil) return err }
// Execute multiple transactions and queries. func exec(ctxt context.Context, chainID string, chaincodeID string, numTrans int, numQueries int) []error { var wg sync.WaitGroup errs := make([]error, numTrans+numQueries) e := func(qnum int) { defer wg.Done() var spec *pb.ChaincodeSpec args := util.ToChaincodeArgs("invoke", "a", "b", "10") spec = &pb.ChaincodeSpec{Type: 1, ChaincodeID: &pb.ChaincodeID{Name: chaincodeID}, CtorMsg: &pb.ChaincodeInput{Args: args}} _, _, _, err := invoke(ctxt, chainID, spec) if err != nil { errs[qnum] = fmt.Errorf("Error executing <%s>: %s", chaincodeID, err) return } } wg.Add(numTrans + numQueries) //execute transactions sequentially.. go func() { for i := 0; i < numTrans; i++ { e(i) } }() wg.Wait() return errs }
// Invoke invokes another chaincode - chaincode_example02, upon receipt of an event and changes event state func (t *SimpleChaincode) Invoke(stub shim.ChaincodeStubInterface, function string, args []string) ([]byte, error) { var event string // Event entity var eventVal string // State of event var err error var amount int event = args[0] eventVal = args[1] chainCodeToCall := args[2] // Get the chaincode to call from the ledger if eventVal == "middleSchool" { amount = 2000 } else { amount = 5000 } // 转账操作 invokeArgs := util.ToChaincodeArgs("transferAcc", args[3], args[4], strconv.Itoa(amount)) response, err := stub.InvokeChaincode(chainCodeToCall, invokeArgs) if err != nil { errStr := fmt.Sprintf("Failed to invoke chaincode. Got error: %s", err.Error()) fmt.Printf(errStr) return nil, errors.New(errStr) } fmt.Printf("Invoke chaincode successful. Got response %s", string(response)) // Write the event state back to the ledger err = stub.PutState(event, []byte(args[1])) if err != nil { return nil, err } return nil, nil }
func deployInternal(deployer crypto.Client, adminCert crypto.CertificateHandler) (resp *pb.Response, err error) { // Prepare the spec. The metadata includes the identity of the administrator spec := &pb.ChaincodeSpec{ Type: 1, ChaincodeID: &pb.ChaincodeID{Path: "github.com/hyperledger/fabric/examples/chaincode/go/asset_management"}, //ChaincodeID: &pb.ChaincodeID{Name: chaincodeName}, CtorMsg: &pb.ChaincodeInput{Args: util.ToChaincodeArgs("init")}, Metadata: adminCert.GetCertificate(), ConfidentialityLevel: confidentialityLevel, } // First build the deployment spec cds, err := getChaincodeBytes(spec) if err != nil { return nil, fmt.Errorf("Error getting deployment spec: %s ", err) } // Now create the Transactions message and send to Peer. transaction, err := deployer.NewChaincodeDeployTransaction(cds, cds.ChaincodeSpec.ChaincodeID.Name) if err != nil { return nil, fmt.Errorf("Error deploying chaincode: %s ", err) } resp, err = processTransaction(transaction) appLogger.Debugf("resp [%s]", resp.String()) chaincodeName = cds.ChaincodeSpec.ChaincodeID.Name appLogger.Debugf("ChaincodeName [%s]", chaincodeName) return }
func whoIsTheOwner(asset string) ([]byte, error) { chaincodeInput := &pb.ChaincodeInput{Args: util.ToChaincodeArgs("query", asset)} // Prepare spec and submit spec := &pb.ChaincodeSpec{ Type: 1, ChaincodeID: &pb.ChaincodeID{Name: "mycc"}, CtorMsg: chaincodeInput, ConfidentialityLevel: pb.ConfidentialityLevel_PUBLIC, } var ctx = context.Background() chaincodeInvocationSpec := &pb.ChaincodeInvocationSpec{ChaincodeSpec: spec} tid := chaincodeInvocationSpec.ChaincodeSpec.ChaincodeID.Name // Now create the Transactions message and send to Peer. transaction, err := administrator.NewChaincodeQuery(chaincodeInvocationSpec, tid) if err != nil { return nil, fmt.Errorf("Error deploying chaincode: %s ", err) } ledger, err := ledger.GetLedger() ledger.BeginTxBatch("1") result, _, err := chaincode.Execute(ctx, chaincode.GetChain(chaincode.DefaultChain), transaction) if err != nil { return nil, fmt.Errorf("Error deploying chaincode: %s", err) } ledger.CommitTxBatch("1", []*pb.Transaction{transaction}, nil, nil) return result, err }
func executeDeployTransaction(t *testing.T, chainID string, name string, url string) { lis, err := initPeer(chainID) if err != nil { t.Fail() t.Logf("Error creating peer: %s", err) } defer finitPeer(lis, chainID) var ctxt = context.Background() f := "init" args := util.ToChaincodeArgs(f, "a", "100", "b", "200") spec := &pb.ChaincodeSpec{Type: 1, ChaincodeID: &pb.ChaincodeID{Name: name, Path: url}, CtorMsg: &pb.ChaincodeInput{Args: args}} cccid := NewCCContext(chainID, name, "", "", false, nil) _, err = deploy(ctxt, cccid, spec) chaincodeID := spec.ChaincodeID.Name if err != nil { theChaincodeSupport.Stop(ctxt, cccid, &pb.ChaincodeDeploymentSpec{ChaincodeSpec: spec}) t.Fail() t.Logf("Error deploying <%s>: %s", chaincodeID, err) return } theChaincodeSupport.Stop(ctxt, cccid, &pb.ChaincodeDeploymentSpec{ChaincodeSpec: spec}) }
func InitTestStub(funargs ...string) *ChaincodeStub { stub := ChaincodeStub{} allargs := util.ToChaincodeArgs(funargs...) newCI := &pb.ChaincodeInput{Args: allargs} stub.init(&Handler{}, "TEST-txid", newCI) return &stub }
// Execute multiple transactions and queries. func exec(ctxt context.Context, chaincodeID string, numTrans int, numQueries int) []error { var wg sync.WaitGroup errs := make([]error, numTrans+numQueries) e := func(qnum int, typ pb.Transaction_Type) { defer wg.Done() var spec *pb.ChaincodeSpec if typ == pb.Transaction_CHAINCODE_INVOKE { f := "invoke" args := util.ToChaincodeArgs(f, "a", "b", "10") spec = &pb.ChaincodeSpec{Type: 1, ChaincodeID: &pb.ChaincodeID{Name: chaincodeID}, CtorMsg: &pb.ChaincodeInput{Args: args}} } else { f := "query" args := util.ToChaincodeArgs(f, "a") spec = &pb.ChaincodeSpec{Type: 1, ChaincodeID: &pb.ChaincodeID{Name: chaincodeID}, CtorMsg: &pb.ChaincodeInput{Args: args}} } _, _, _, err := invoke(ctxt, spec, typ) if err != nil { errs[qnum] = fmt.Errorf("Error executing <%s>: %s", chaincodeID, err) return } } wg.Add(numTrans + numQueries) //execute transactions sequentially.. go func() { for i := 0; i < numTrans; i++ { e(i, pb.Transaction_CHAINCODE_INVOKE) } }() //...but queries in parallel for i := numTrans; i < numTrans+numQueries; i++ { go e(i, pb.Transaction_CHAINCODE_QUERY) } wg.Wait() return errs }
func transferOwnership(owner crypto.Client, ownerCert crypto.CertificateHandler, fromAttributes string, newOwnerCert crypto.CertificateHandler, toAttributes string, amount string) error { // Get a transaction handler to be used to submit the execute transaction // and bind the chaincode access control logic using the binding submittingCertHandler, err := owner.GetTCertificateHandlerNext("role") if err != nil { return err } txHandler, err := submittingCertHandler.GetTransactionHandler() if err != nil { return err } chaincodeInput := &pb.ChaincodeInput{Args: util.ToChaincodeArgs( "transferOwnership", base64.StdEncoding.EncodeToString(ownerCert.GetCertificate()), fromAttributes, base64.StdEncoding.EncodeToString(newOwnerCert.GetCertificate()), toAttributes, amount)} // Prepare spec and submit spec := &pb.ChaincodeSpec{ Type: 1, ChaincodeID: &pb.ChaincodeID{Name: "mycc"}, CtorMsg: chaincodeInput, ConfidentialityLevel: pb.ConfidentialityLevel_PUBLIC, } var ctx = context.Background() chaincodeInvocationSpec := &pb.ChaincodeInvocationSpec{ChaincodeSpec: spec} tid := chaincodeInvocationSpec.ChaincodeSpec.ChaincodeID.Name // Now create the Transactions message and send to Peer. transaction, err := txHandler.NewChaincodeExecute(chaincodeInvocationSpec, tid) if err != nil { return fmt.Errorf("Error deploying chaincode: %s ", err) } ledger, err := ledger.GetLedger() ledger.BeginTxBatch("1") _, _, err = chaincode.Execute(ctx, chaincode.GetChain(chaincode.DefaultChain), transaction) if err != nil { return fmt.Errorf("Error deploying chaincode: %s", err) } ledger.CommitTxBatch("1", []*pb.Transaction{transaction}, nil, nil) return err }
// UnmarshalJSON converts the string-based REST/JSON input to // the []byte-based current ChaincodeInput structure. func (c *ChaincodeInput) UnmarshalJSON(b []byte) error { sa := &strArgs{} err := json.Unmarshal(b, sa) if err != nil { return err } allArgs := sa.Args if sa.Function != "" { allArgs = append([]string{sa.Function}, sa.Args...) } c.Args = util.ToChaincodeArgs(allArgs...) return nil }
func executeDeployTransaction(t *testing.T, url string) { var opts []grpc.ServerOption if viper.GetBool("peer.tls.enabled") { creds, err := credentials.NewServerTLSFromFile(viper.GetString("peer.tls.cert.file"), viper.GetString("peer.tls.key.file")) if err != nil { grpclog.Fatalf("Failed to generate credentials %v", err) } opts = []grpc.ServerOption{grpc.Creds(creds)} } grpcServer := grpc.NewServer(opts...) viper.Set("peer.fileSystemPath", "/var/hyperledger/test/tmpdb") //lis, err := net.Listen("tcp", viper.GetString("peer.address")) //use a different address than what we usually use for "peer" //we override the peerAddress set in chaincode_support.go peerAddress := "0.0.0.0:21212" lis, err := net.Listen("tcp", peerAddress) if err != nil { t.Fail() t.Logf("Error starting peer listener %s", err) return } getPeerEndpoint := func() (*pb.PeerEndpoint, error) { return &pb.PeerEndpoint{ID: &pb.PeerID{Name: "testpeer"}, Address: peerAddress}, nil } ccStartupTimeout := time.Duration(chaincodeStartupTimeoutDefault) * time.Millisecond pb.RegisterChaincodeSupportServer(grpcServer, NewChaincodeSupport(DefaultChain, getPeerEndpoint, false, ccStartupTimeout, nil)) go grpcServer.Serve(lis) var ctxt = context.Background() f := "init" args := util.ToChaincodeArgs(f, "a", "100", "b", "200") spec := &pb.ChaincodeSpec{Type: 1, ChaincodeID: &pb.ChaincodeID{Path: url}, CtorMsg: &pb.ChaincodeInput{Args: args}} _, err = deploy(ctxt, spec) chaincodeID := spec.ChaincodeID.Name if err != nil { GetChain(DefaultChain).Stop(ctxt, &pb.ChaincodeDeploymentSpec{ChaincodeSpec: spec}) closeListenerAndSleep(lis) t.Fail() t.Logf("Error deploying <%s>: %s", chaincodeID, err) return } GetChain(DefaultChain).Stop(ctxt, &pb.ChaincodeDeploymentSpec{ChaincodeSpec: spec}) closeListenerAndSleep(lis) }
func transferOwnershipInternal(owner crypto.Client, ownerCert crypto.CertificateHandler, asset string, newOwnerCert crypto.CertificateHandler) (resp *pb.Response, err error) { // Get a transaction handler to be used to submit the execute transaction // and bind the chaincode access control logic using the binding submittingCertHandler, err := owner.GetTCertificateHandlerNext() if err != nil { return nil, err } txHandler, err := submittingCertHandler.GetTransactionHandler() if err != nil { return nil, err } binding, err := txHandler.GetBinding() if err != nil { return nil, err } chaincodeInput := &pb.ChaincodeInput{ Args: util.ToChaincodeArgs("transfer", asset, base64.StdEncoding.EncodeToString(newOwnerCert.GetCertificate())), } chaincodeInputRaw, err := proto.Marshal(chaincodeInput) if err != nil { return nil, err } // Access control. Owner signs chaincodeInputRaw || binding to confirm his identity sigma, err := ownerCert.Sign(append(chaincodeInputRaw, binding...)) if err != nil { return nil, err } // Prepare spec and submit spec := &pb.ChaincodeSpec{ Type: 1, ChaincodeID: &pb.ChaincodeID{Name: chaincodeName}, CtorMsg: chaincodeInput, Metadata: sigma, // Proof of identity ConfidentialityLevel: confidentialityLevel, } chaincodeInvocationSpec := &pb.ChaincodeInvocationSpec{ChaincodeSpec: spec} // Now create the Transactions message and send to Peer. transaction, err := txHandler.NewChaincodeExecute(chaincodeInvocationSpec, util.GenerateUUID()) if err != nil { return nil, fmt.Errorf("Error deploying chaincode: %s ", err) } return processTransaction(transaction) }
func (b *BDDContext) userCreatesAChaincodeSpecOfTypeForChaincodeWithArgs(enrollID, ccSpecAlias, ccType, chaincodePath string, argsTable *gherkin.DataTable) error { userRegistration, err := b.GetUserRegistration(enrollID) if err != nil { return err } args, err := b.GetArgsForUser(argsTable.Rows[1].Cells, userRegistration) //fmt.Printf("Args for user: %v, with err = %s", args, err) ccSpec := createChaincodeSpec(ccType, chaincodePath, util.ToChaincodeArgs(args...)) userRegistration.lastResult = ccSpec userRegistration.tags[ccSpecAlias] = userRegistration.lastResult return nil }
// TestDeployAndInvoke deploys and invokes chaincode_example01 func TestDeployAndInvoke(t *testing.T) { chainID := util.GetTestChainID() var ctxt = context.Background() url := "github.com/hyperledger/fabric/examples/chaincode/go/chaincode_example01" chaincodeID := &pb.ChaincodeID{Path: url, Name: "ex01"} args := []string{"10"} f := "init" argsDeploy := util.ToChaincodeArgs(f, "a", "100", "b", "200") spec := &pb.ChaincodeSpec{Type: 1, ChaincodeID: chaincodeID, CtorMsg: &pb.ChaincodeInput{Args: argsDeploy}} cccid := chaincode.NewCCContext(chainID, "ex01", "", "", false, nil) resp, prop, err := deploy(endorserServer, chainID, spec, nil) chaincodeID1 := spec.ChaincodeID.Name if err != nil { t.Fail() t.Logf("Error deploying <%s>: %s", chaincodeID1, err) chaincode.GetChain().Stop(ctxt, cccid, &pb.ChaincodeDeploymentSpec{ChaincodeSpec: &pb.ChaincodeSpec{ChaincodeID: chaincodeID}}) return } err = endorserServer.(*Endorser).commitTxSimulation(prop, chainID, signer, resp) if err != nil { t.Fail() t.Logf("Error committing <%s>: %s", chaincodeID1, err) chaincode.GetChain().Stop(ctxt, cccid, &pb.ChaincodeDeploymentSpec{ChaincodeSpec: &pb.ChaincodeSpec{ChaincodeID: chaincodeID}}) return } f = "invoke" invokeArgs := append([]string{f}, args...) spec = &pb.ChaincodeSpec{Type: 1, ChaincodeID: chaincodeID, CtorMsg: &pb.ChaincodeInput{Args: util.ToChaincodeArgs(invokeArgs...)}} resp, err = invoke(chainID, spec) if err != nil { t.Fail() t.Logf("Error invoking transaction: %s", err) chaincode.GetChain().Stop(ctxt, cccid, &pb.ChaincodeDeploymentSpec{ChaincodeSpec: &pb.ChaincodeSpec{ChaincodeID: chaincodeID}}) return } fmt.Printf("Invoke test passed\n") t.Logf("Invoke test passed") chaincode.GetChain().Stop(ctxt, cccid, &pb.ChaincodeDeploymentSpec{ChaincodeSpec: &pb.ChaincodeSpec{ChaincodeID: chaincodeID}}) }
// Invoke invokes another chaincode - chaincode_example02, upon receipt of an event and changes event state func (t *SimpleChaincode) Invoke(stub shim.ChaincodeStubInterface, function string, args []string) ([]byte, error) { var event string // Event entity var eventVal int // State of event var err error if len(args) != 2 { return nil, errors.New("Incorrect number of arguments. Expecting 2") } event = args[0] eventVal, err = strconv.Atoi(args[1]) if err != nil { return nil, errors.New("Expected integer value for event state change") } if eventVal != 1 { fmt.Printf("Unexpected event. Doing nothing\n") return nil, nil } // Get the chaincode to call from the ledger chainCodeToCall := t.GetChaincodeToCall() f := "invoke" invokeArgs := util.ToChaincodeArgs(f, "a", "b", "10") response, err := stub.InvokeChaincode(chainCodeToCall, invokeArgs) if err != nil { errStr := fmt.Sprintf("Failed to invoke chaincode. Got error: %s", err.Error()) fmt.Printf(errStr) return nil, errors.New(errStr) } fmt.Printf("Invoke chaincode successful. Got response %s", string(response)) // Write the event state back to the ledger err = stub.PutState(event, []byte(strconv.Itoa(eventVal))) if err != nil { return nil, err } return nil, nil }
func TestBlockChain_SingleBlock(t *testing.T) { testDBWrapper.CleanDB(t) blockchainTestWrapper := newTestBlockchainWrapper(t) blockchain := blockchainTestWrapper.blockchain // Create the Chaincode specification chaincodeSpec := &protos.ChaincodeSpec{Type: protos.ChaincodeSpec_GOLANG, ChaincodeID: &protos.ChaincodeID{Path: "Contracts"}, CtorMsg: &protos.ChaincodeInput{Args: util.ToChaincodeArgs("Initialize", "param1")}} chaincodeDeploymentSepc := &protos.ChaincodeDeploymentSpec{ChaincodeSpec: chaincodeSpec} uuid := testutil.GenerateID(t) newChaincodeTx, err := protos.NewChaincodeDeployTransaction(chaincodeDeploymentSepc, uuid) testutil.AssertNoError(t, err, "Failed to create new chaincode Deployment Transaction") t.Logf("New chaincode tx: %v", newChaincodeTx) block1 := protos.NewBlock([]*protos.Transaction{newChaincodeTx}, nil) blockNumber := blockchainTestWrapper.addNewBlock(block1, []byte("stateHash1")) t.Logf("New chain: %v", blockchain) testutil.AssertEquals(t, blockNumber, uint64(0)) testutil.AssertEquals(t, blockchain.getSize(), uint64(1)) testutil.AssertEquals(t, blockchainTestWrapper.fetchBlockchainSizeFromDB(), uint64(1)) }
func whoIsTheOwner(invoker crypto.Client, asset string) (transaction *pb.Transaction, resp *pb.Response, err error) { chaincodeInput := &pb.ChaincodeInput{Args: util.ToChaincodeArgs("query", asset)} // Prepare spec and submit spec := &pb.ChaincodeSpec{ Type: 1, ChaincodeID: &pb.ChaincodeID{Name: chaincodeName}, CtorMsg: chaincodeInput, ConfidentialityLevel: confidentialityLevel, } chaincodeInvocationSpec := &pb.ChaincodeInvocationSpec{ChaincodeSpec: spec} // Now create the Transactions message and send to Peer. transaction, err = invoker.NewChaincodeQuery(chaincodeInvocationSpec, util.GenerateUUID()) if err != nil { return nil, nil, fmt.Errorf("Error deploying chaincode: %s ", err) } resp, err = processTransaction(transaction) return }
func TestCar_BuildImage(t *testing.T) { vm, err := container.NewVM() if err != nil { t.Fail() t.Logf("Error getting VM: %s", err) return } // Build the spec cwd, err := os.Getwd() if err != nil { t.Fail() t.Logf("Error getting CWD: %s", err) return } chaincodePath := cwd + "/org.hyperledger.chaincode.example02-0.1-SNAPSHOT.car" spec := &pb.ChaincodeSpec{Type: pb.ChaincodeSpec_CAR, ChaincodeID: &pb.ChaincodeID{Path: chaincodePath}, CtorMsg: &pb.ChaincodeInput{Args: util.ToChaincodeArgs("f")}} if _, err := vm.BuildChaincodeContainer(spec); err != nil { t.Fail() t.Log(err) } }
// Test deploy of a transaction. func TestExecuteDeploySysChaincode(t *testing.T) { testDBWrapper.CleanDB(t) var opts []grpc.ServerOption grpcServer := grpc.NewServer(opts...) viper.Set("peer.fileSystemPath", "/var/hyperledger/test/tmpdb") //use a different address than what we usually use for "peer" //we override the peerAddress set in chaincode_support.go peerAddress := "0.0.0.0:21726" lis, err := net.Listen("tcp", peerAddress) if err != nil { t.Fail() t.Logf("Error starting peer listener %s", err) return } getPeerEndpoint := func() (*pb.PeerEndpoint, error) { return &pb.PeerEndpoint{ID: &pb.PeerID{Name: "testpeer"}, Address: peerAddress}, nil } ccStartupTimeout := time.Duration(5000) * time.Millisecond pb.RegisterChaincodeSupportServer(grpcServer, chaincode.NewChaincodeSupport(chaincode.DefaultChain, getPeerEndpoint, false, ccStartupTimeout, nil)) go grpcServer.Serve(lis) var ctxt = context.Background() //set systemChaincodes to sample systemChaincodes = []*api.SystemChaincode{ { Enabled: true, Name: "sample_syscc", Path: "github.com/hyperledger/fabric/core/system_chaincode/samplesyscc", InitArgs: [][]byte{}, Chaincode: &samplesyscc.SampleSysCC{}, }, } // System chaincode has to be enabled viper.Set("chaincode.system", map[string]string{"sample_syscc": "true"}) RegisterSysCCs() url := "github.com/hyperledger/fabric/core/system_chaincode/sample_syscc" f := "putval" args := util.ToChaincodeArgs(f, "greeting", "hey there") spec := &pb.ChaincodeSpec{Type: 1, ChaincodeID: &pb.ChaincodeID{Name: "sample_syscc", Path: url}, CtorMsg: &pb.ChaincodeInput{Args: args}} _, _, _, err = invoke(ctxt, spec, pb.Transaction_CHAINCODE_INVOKE) if err != nil { closeListenerAndSleep(lis) t.Fail() t.Logf("Error invoking sample_syscc: %s", err) return } f = "getval" args = util.ToChaincodeArgs(f, "greeting") spec = &pb.ChaincodeSpec{Type: 1, ChaincodeID: &pb.ChaincodeID{Name: "sample_syscc", Path: url}, CtorMsg: &pb.ChaincodeInput{Args: args}} _, _, _, err = invoke(ctxt, spec, pb.Transaction_CHAINCODE_QUERY) if err != nil { closeListenerAndSleep(lis) t.Fail() t.Logf("Error invoking sample_syscc: %s", err) return } cds := &pb.ChaincodeDeploymentSpec{ExecEnv: 1, ChaincodeSpec: &pb.ChaincodeSpec{Type: 1, ChaincodeID: &pb.ChaincodeID{Name: "sample_syscc", Path: url}, CtorMsg: &pb.ChaincodeInput{Args: args}}} chaincode.GetChain(chaincode.DefaultChain).Stop(ctxt, cds) closeListenerAndSleep(lis) }
func TestVM_BuildImage_ChaincodeRemote(t *testing.T) { t.Skip("Works but needs user credentials. Not suitable for automated unit tests as is") vm, err := NewVM() if err != nil { t.Fail() t.Logf("Error getting VM: %s", err) return } // Build the spec chaincodePath := "https://github.com/prjayach/chaincode_examples/chaincode_example02" spec := &pb.ChaincodeSpec{Type: pb.ChaincodeSpec_GOLANG, ChaincodeID: &pb.ChaincodeID{Name: "ex02", Path: chaincodePath}, CtorMsg: &pb.ChaincodeInput{Args: util.ToChaincodeArgs("f")}} if _, err := vm.BuildChaincodeContainer(spec); err != nil { t.Fail() t.Log(err) } }
func TestVM_BuildImage_ChaincodeLocal(t *testing.T) { vm, err := NewVM() if err != nil { t.Fail() t.Logf("Error getting VM: %s", err) return } // Build the spec chaincodePath := "github.com/hyperledger/fabric/examples/chaincode/go/chaincode_example01" spec := &pb.ChaincodeSpec{Type: pb.ChaincodeSpec_GOLANG, ChaincodeID: &pb.ChaincodeID{Name: "ex01", Path: chaincodePath}, CtorMsg: &pb.ChaincodeInput{Args: util.ToChaincodeArgs("f")}} if _, err := vm.BuildChaincodeContainer(spec); err != nil { t.Fail() t.Log(err) } }
func read(invoker crypto.Client, invokerCert crypto.CertificateHandler) ([]byte, error) { // Get a transaction handler to be used to submit the query transaction // and bind the chaincode access control logic using the binding submittingCertHandler, err := invoker.GetTCertificateHandlerNext() if err != nil { return nil, err } txHandler, err := submittingCertHandler.GetTransactionHandler() if err != nil { return nil, err } binding, err := txHandler.GetBinding() if err != nil { return nil, err } chaincodeInput := &pb.ChaincodeInput{Args: util.ToChaincodeArgs("read")} chaincodeInputRaw, err := proto.Marshal(chaincodeInput) if err != nil { return nil, err } // Access control: // invokerCert signs invokerCert.GetCertificate() || chaincodeInputRaw || binding to confirm his identity sigma, err := invokerCert.Sign(append(invokerCert.GetCertificate(), append(chaincodeInputRaw, binding...)...)) if err != nil { return nil, err } rbacMetadata := RBACMetadata{invokerCert.GetCertificate(), sigma} rbacMetadataRaw, err := asn1.Marshal(rbacMetadata) if err != nil { return nil, err } // Prepare spec and submit spec := &pb.ChaincodeSpec{ Type: 1, ChaincodeID: &pb.ChaincodeID{Name: "mycc"}, CtorMsg: chaincodeInput, Metadata: rbacMetadataRaw, ConfidentialityLevel: pb.ConfidentialityLevel_PUBLIC, } var ctx = context.Background() chaincodeInvocationSpec := &pb.ChaincodeInvocationSpec{ChaincodeSpec: spec} tid := chaincodeInvocationSpec.ChaincodeSpec.ChaincodeID.Name // Now create the Transactions message and send to Peer. transaction, err := txHandler.NewChaincodeQuery(chaincodeInvocationSpec, tid) if err != nil { return nil, fmt.Errorf("Error deploying chaincode: %s ", err) } ledger, err := ledger.GetLedger() ledger.BeginTxBatch("1") result, _, err := chaincode.Execute(ctx, chaincode.GetChain(chaincode.DefaultChain), transaction) if err != nil { return nil, fmt.Errorf("Error deploying chaincode: %s", err) } ledger.CommitTxBatch("1", []*pb.Transaction{transaction}, nil, nil) return result, err }
func TestJava_BuildImage(t *testing.T) { vm, err := container.NewVM() if err != nil { t.Fail() t.Logf("Error getting VM: %s", err) return } chaincodePath := "../../../../../examples/chaincode/java/SimpleSample" //TODO find a better way to launch example java chaincode spec := &pb.ChaincodeSpec{Type: pb.ChaincodeSpec_JAVA, ChaincodeID: &pb.ChaincodeID{Name: "ssample", Path: chaincodePath}, CtorMsg: &pb.ChaincodeInput{Args: util.ToChaincodeArgs("f")}} if _, err := vm.BuildChaincodeContainer(spec); err != nil { t.Fail() t.Log(err) } }
func (ml mockLedger) GetTransactionByID(txID string) (*protos.Transaction, error) { if txID == "noSuchTX" { return nil, fmt.Errorf("Some error") } newCCIS := &protos.ChaincodeInvocationSpec{ChaincodeSpec: &protos.ChaincodeSpec{CtorMsg: &protos.ChaincodeInput{Args: util.ToChaincodeArgs("execute", something)}}} pl, _ := proto.Marshal(newCCIS) return &protos.Transaction{Payload: pl}, nil }