github.com/adnan-c/fabric_e2e_couchdb@v0.6.1-preview.0.20170228180935-21ce6b23cf91/examples/chaincode/go/authorizable_counter/authorizable_counter.go (about)

     1  /*
     2  Copyright IBM Corp. 2016 All Rights Reserved.
     3  
     4  Licensed under the Apache License, Version 2.0 (the "License");
     5  you may not use this file except in compliance with the License.
     6  You may obtain a copy of the License at
     7  
     8  		 http://www.apache.org/licenses/LICENSE-2.0
     9  
    10  Unless required by applicable law or agreed to in writing, software
    11  distributed under the License is distributed on an "AS IS" BASIS,
    12  WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
    13  See the License for the specific language governing permissions and
    14  limitations under the License.
    15  */
    16  
    17  package main
    18  
    19  import (
    20  	"fmt"
    21  	"strconv"
    22  
    23  	"github.com/hyperledger/fabric/accesscontrol/impl"
    24  	"github.com/hyperledger/fabric/core/chaincode/shim"
    25  	pb "github.com/hyperledger/fabric/protos/peer"
    26  )
    27  
    28  // AuthorizableCounterChaincode is an example that use Attribute Based Access Control to control the access to a counter by users with an specific role.
    29  // In this case only users which TCerts contains the attribute position with the value "Software Engineer" will be able to increment the counter.
    30  type AuthorizableCounterChaincode struct {
    31  }
    32  
    33  //Init the chaincode asigned the value "0" to the counter in the state.
    34  func (t *AuthorizableCounterChaincode) Init(stub shim.ChaincodeStubInterface) pb.Response {
    35  	err := stub.PutState("counter", []byte("0"))
    36  	if err != nil {
    37  		return shim.Error(err.Error())
    38  	}
    39  
    40  	return shim.Success(nil)
    41  }
    42  
    43  //Invoke makes increment counter
    44  func (t *AuthorizableCounterChaincode) increment(stub shim.ChaincodeStubInterface, args []string) pb.Response {
    45  	val, err := impl.NewAccessControlShim(stub).ReadCertAttribute("position")
    46  	fmt.Printf("Position => %v error %v \n", string(val), err)
    47  	isOk, _ := impl.NewAccessControlShim(stub).VerifyAttribute("position", []byte("Software Engineer")) // Here the ABAC API is called to verify the attribute, just if the value is verified the counter will be incremented.
    48  	if isOk {
    49  		counter, err := stub.GetState("counter")
    50  		if err != nil {
    51  			return shim.Error(err.Error())
    52  		}
    53  		var cInt int
    54  		cInt, err = strconv.Atoi(string(counter))
    55  		if err != nil {
    56  			return shim.Error(err.Error())
    57  		}
    58  		cInt = cInt + 1
    59  		counter = []byte(strconv.Itoa(cInt))
    60  		stub.PutState("counter", counter)
    61  	}
    62  	return shim.Success(nil)
    63  }
    64  
    65  func (t *AuthorizableCounterChaincode) read(stub shim.ChaincodeStubInterface, args []string) pb.Response {
    66  	var err error
    67  
    68  	// Get the state from the ledger
    69  	Avalbytes, err := stub.GetState("counter")
    70  	if err != nil {
    71  		jsonResp := "{\"Error\":\"Failed to get state for counter\"}"
    72  		return shim.Error(jsonResp)
    73  	}
    74  
    75  	if Avalbytes == nil {
    76  		jsonResp := "{\"Error\":\"Nil amount for counter\"}"
    77  		return shim.Error(jsonResp)
    78  	}
    79  
    80  	jsonResp := "{\"Name\":\"counter\",\"Amount\":\"" + string(Avalbytes) + "\"}"
    81  	fmt.Printf("Query Response:%s\n", jsonResp)
    82  	return shim.Success(Avalbytes)
    83  }
    84  
    85  // Invoke  method is the interceptor of all invocation transactions, its job is to direct
    86  // invocation transactions to intended APIs
    87  func (t *AuthorizableCounterChaincode) Invoke(stub shim.ChaincodeStubInterface) pb.Response {
    88  	function, args := stub.GetFunctionAndParameters()
    89  
    90  	//	 Handle different functions
    91  	if function == "increment" {
    92  		return t.increment(stub, args)
    93  	} else if function == "read" {
    94  		return t.read(stub, args)
    95  	}
    96  	return shim.Error("Received unknown function invocation, Expecting \"increment\" \"read\"")
    97  }
    98  
    99  func main() {
   100  	err := shim.Start(new(AuthorizableCounterChaincode))
   101  	if err != nil {
   102  		fmt.Printf("Error starting Simple chaincode: %s", err)
   103  	}
   104  }