github.com/inklabsfoundation/inkchain@v0.17.1-0.20181025012015-c3cef8062f19/examples/creative/invoke/production.go (about)

     1  package invoke
     2  
     3  import (
     4  	"github.com/inklabsfoundation/inkchain/core/chaincode/shim"
     5  	pb "github.com/inklabsfoundation/inkchain/protos/peer"
     6  	. "github.com/inklabsfoundation/inkchain/examples/creative/model"
     7  	. "github.com/inklabsfoundation/inkchain/examples/creative/conf"
     8  	. "github.com/inklabsfoundation/inkchain/examples/creative/util"
     9  	"fmt"
    10  	"encoding/json"
    11  	"strings"
    12  	"math/big"
    13  	"strconv"
    14  )
    15  
    16  type ProductionInvoke struct{}
    17  
    18  func (*ProductionInvoke) AddProduction(stub shim.ChaincodeStubInterface, args []string) pb.Response {
    19  	fmt.Println("add production start.")
    20  	username := args[0]
    21  	production_type := args[1]
    22  	production_serial := args[2]
    23  	production_name := args[3]
    24  	production_desc := args[4]
    25  	production_price_type := args[5]
    26  	production_price := args[6]
    27  	production_num := args[7]
    28  	production_transfer_part := args[8]
    29  
    30  	// verify weather the user exists
    31  	user_key := GetUserKey(username)
    32  	userAsBytes, err := stub.GetState(user_key)
    33  	if err != nil {
    34  		return shim.Error("Fail to get user: " + err.Error())
    35  	}
    36  	if userAsBytes == nil {
    37  		fmt.Println("This user doesn't exist: " + username)
    38  		return shim.Error("This user doesn't exist: " + username)
    39  	}
    40  
    41  	// verify weather the artist exists
    42  	artist_key := GetArtistKey(username)
    43  	artistAsBytes, err := stub.GetState(artist_key)
    44  	if err != nil {
    45  		return shim.Error("Fail to get artist: " + err.Error())
    46  	}
    47  
    48  	if artistAsBytes == nil {
    49  		fmt.Println("This artist doesn't exist: " + artist_key)
    50  		return shim.Error("This artist doesn't exist: " + artist_key)
    51  	}
    52  
    53  	product_key := GetProductionKey(username, production_type, production_serial)
    54  
    55  	// check if user exists
    56  	productionAsBtyes, err := stub.GetState(product_key)
    57  	if err != nil {
    58  		return shim.Error("Fail to get production: " + err.Error())
    59  	} else if productionAsBtyes != nil {
    60  		fmt.Println("This production already exists: " + product_key)
    61  		return shim.Error("This production already exists: " + product_key)
    62  	}
    63  
    64  	// add production
    65  	production := Production{
    66  		Type:                  production_type,
    67  		Serial:                production_serial,
    68  		Name:                  production_name,
    69  		Desc:                  production_desc,
    70  		CopyrightPriceType:    production_price_type,
    71  		CopyrightPrice:        production_price,
    72  		CopyrightNum:          production_num,
    73  		CopyrightTransferPart: production_transfer_part,
    74  		Username:              username,
    75  	}
    76  
    77  	productionAsBtyes, err = json.Marshal(production)
    78  	err = stub.PutState(product_key, productionAsBtyes)
    79  	if err != nil {
    80  		return shim.Error(err.Error())
    81  	}
    82  	return shim.Success([]byte("add production success."))
    83  }
    84  
    85  func (*ProductionInvoke) ModifyProduction(stub shim.ChaincodeStubInterface, args []string) pb.Response {
    86  	fmt.Println("modify production start.")
    87  	username := args[0]
    88  	production_type := args[1]
    89  	production_serial := args[2]
    90  	user_key := GetUserKey(username)
    91  	// verify weather the user exists
    92  	userAsBytes, err := stub.GetState(user_key)
    93  	if err != nil {
    94  		return shim.Error("Fail to get user: " + err.Error())
    95  	}
    96  	if userAsBytes == nil {
    97  		fmt.Println("This user doesn't exist: " + username)
    98  		return shim.Error("This user doesn't exist: " + username)
    99  	}
   100  
   101  	// get user's address
   102  	address, err := stub.GetSender()
   103  	if err != nil {
   104  		return shim.Error("Fail to reveal user's address.")
   105  	}
   106  	address = strings.ToLower(address)
   107  
   108  	var userJSON User
   109  	err = json.Unmarshal([]byte(userAsBytes), &userJSON)
   110  	if userJSON.Address != address {
   111  		return shim.Error("The sender's address doesn't correspond with the user's.")
   112  	}
   113  
   114  	production_key := GetProductionKey(username, production_type, production_serial)
   115  	// verify weather the production exists
   116  	productionAsBytes, err := stub.GetState(production_key)
   117  	if err != nil {
   118  		return shim.Error("Fail to get artist: " + err.Error())
   119  	}
   120  	if productionAsBytes == nil {
   121  		fmt.Println("This production doesn't exist: " + production_key)
   122  		return shim.Error("This production doesn't exist: " + production_key)
   123  	}
   124  
   125  	var productionJSON Production
   126  	err = json.Unmarshal([]byte(productionAsBytes), &productionJSON)
   127  
   128  	if productionJSON.Username != userJSON.Username {
   129  		return shim.Error("The artist's username doesn't correspond with the user's.")
   130  	}
   131  
   132  	err = GetModifyProduction(&productionJSON, args[3:])
   133  	if err != nil {
   134  		return shim.Error(err.Error())
   135  	}
   136  	artistJSONasBytes, err := json.Marshal(productionJSON)
   137  	if err != nil {
   138  		return shim.Error(err.Error())
   139  	}
   140  	err = stub.PutState(production_key, artistJSONasBytes)
   141  	if err != nil {
   142  		return shim.Error(err.Error())
   143  	}
   144  	return shim.Success([]byte("modify production success."))
   145  }
   146  
   147  func (*ProductionInvoke) DeleteProduction(stub shim.ChaincodeStubInterface, args []string) pb.Response {
   148  	fmt.Println("delete production start.")
   149  	username := args[0]
   150  	production_type := args[1]
   151  	production_serial := args[2]
   152  	user_key := GetUserKey(username)
   153  	// verify weather the user exists
   154  	userAsBytes, err := stub.GetState(user_key)
   155  	if err != nil {
   156  		return shim.Error("Fail to get user: " + err.Error())
   157  	}
   158  	if userAsBytes == nil {
   159  		fmt.Println("This user doesn't exist: " + username)
   160  		return shim.Error("This user doesn't exist: " + username)
   161  	}
   162  	// get user's address
   163  	address, err := stub.GetSender()
   164  	if err != nil {
   165  		return shim.Error("Fail to reveal user's address.")
   166  	}
   167  	address = strings.ToLower(address)
   168  	var userJSON User
   169  	err = json.Unmarshal([]byte(userAsBytes), &userJSON)
   170  	if userJSON.Address != address {
   171  		return shim.Error("The sender's address doesn't correspond with the user's.")
   172  	}
   173  	production_key := GetProductionKey(username, production_type, production_serial)
   174  	// verify weather the production exists
   175  	productionAsBytes, err := stub.GetState(production_key)
   176  	if err != nil {
   177  		return shim.Error("Fail to get production: " + err.Error())
   178  	}
   179  	if productionAsBytes == nil {
   180  		fmt.Println("This production doesn't exist: " + production_key)
   181  		return shim.Error("This production doesn't exist: " + production_key)
   182  	}
   183  	var productionJSON Production
   184  	err = json.Unmarshal([]byte(productionAsBytes), &productionJSON)
   185  	if productionJSON.Username != userJSON.Username {
   186  		return shim.Error("The artist's username doesn't correspond with the user's.")
   187  	}
   188  	// delete production's info
   189  	err = stub.DelState(production_key)
   190  	if err != nil {
   191  		fmt.Println("Fail to delete: " + production_key)
   192  		return shim.Error("Fail to delete" + production_key)
   193  	}
   194  	return shim.Success([]byte("delete production success."))
   195  }
   196  
   197  func (*ProductionInvoke) QueryProduction(stub shim.ChaincodeStubInterface, args []string) pb.Response {
   198  	fmt.Println("query production start.")
   199  	username := args[0]
   200  	production_type := args[1]
   201  	production_serial := args[2]
   202  	production_key := GetProductionKey(username, production_type, production_serial)
   203  	productionAsBytes, err := stub.GetState(production_key)
   204  	if err != nil {
   205  		return shim.Error("Fail to get artist: " + err.Error())
   206  	}
   207  	if productionAsBytes == nil {
   208  		fmt.Println("This production doesn't exist: " + production_key)
   209  		return shim.Error("This production doesn't exist: " + production_key)
   210  	}
   211  	return shim.Success(productionAsBytes)
   212  }
   213  
   214  func (*ProductionInvoke) ListOfProduction(stub shim.ChaincodeStubInterface, args []string) pb.Response {
   215  	fmt.Println("list of production start.")
   216  	username := args[0]
   217  	product_type := args[1]
   218  	state_key := GetStateKey(ProductionPrefix, username, product_type)
   219  	resultsIterator, err := stub.GetStateByRange(state_key+StateStartSymbol, state_key+StateEndSymbol)
   220  	if err != nil {
   221  		return shim.Error(err.Error())
   222  	}
   223  	list, err := GetListResult(resultsIterator)
   224  	if err != nil {
   225  		return shim.Error("getListResult failed")
   226  	}
   227  	return shim.Success(list)
   228  }
   229  
   230  func (*ProductionInvoke) ListOfSupporter(stub shim.ChaincodeStubInterface, args []string) pb.Response {
   231  	fmt.Println("list of supporter start.")
   232  	username := args[0]
   233  	product_type := args[1]
   234  	product_serial := args[2]
   235  	state_key := GetStateKey(ProductionPrefix, username, product_type, product_serial)
   236  	var list []Production
   237  	fmt.Println("state_key:", state_key)
   238  	if product_serial != "" {
   239  		product, err := stub.GetState(state_key)
   240  		if err != nil {
   241  			return shim.Error(err.Error())
   242  		}
   243  		var pro Production
   244  		json.Unmarshal(product, &pro)
   245  		list = append(list, pro)
   246  	} else {
   247  		resultsIterator, err := stub.GetStateByRange(state_key+StateStartSymbol, state_key+StateEndSymbol)
   248  		if err != nil {
   249  			return shim.Error(err.Error())
   250  		}
   251  		list, err = GetListProduction(resultsIterator)
   252  		fmt.Println("list:", list)
   253  		if err != nil {
   254  			return shim.Error("getListResult failed")
   255  		}
   256  	}
   257  	result := make(map[string]string)
   258  	for _, production := range list {
   259  		supporters := production.Supporters
   260  		for k, v := range supporters {
   261  			if _, ok := result[k]; ok {
   262  				result[k] = Add(result[k], v)
   263  			} else {
   264  				result[k] = v
   265  			}
   266  		}
   267  	}
   268  	resultAsBytes, err := json.Marshal(result)
   269  	if err != nil {
   270  		return shim.Error(err.Error())
   271  	}
   272  	if resultAsBytes == nil {
   273  		fmt.Println("This supporters doesn't exist: ")
   274  		return shim.Error("This supporters doesn't exist: ")
   275  	}
   276  	return shim.Success(resultAsBytes)
   277  }
   278  
   279  func (*ProductionInvoke) AddSupporter(stub shim.ChaincodeStubInterface, args []string) pb.Response {
   280  	fmt.Println("add buyer start.")
   281  	username := args[0]
   282  	production_type := args[1]
   283  	production_serial := args[2]
   284  	price_type := args[3]
   285  	price := args[4]
   286  	supporter := args[5]
   287  	user_key := GetUserKey(username)
   288  	// verify weather the user exists
   289  	userAsBytes, err := stub.GetState(user_key)
   290  	if err != nil {
   291  		return shim.Error("Fail to get user: " + err.Error())
   292  	}
   293  	if userAsBytes == nil {
   294  		fmt.Println("This user doesn't exist: " + username)
   295  		return shim.Error("This user doesn't exist: " + username)
   296  	}
   297  
   298  	production_key := GetProductionKey(username, production_type, production_serial)
   299  	// verify weather the production exists
   300  	productionAsBytes, err := stub.GetState(production_key)
   301  	if err != nil {
   302  		return shim.Error("Fail to get artist: " + err.Error())
   303  	}
   304  	if productionAsBytes == nil {
   305  		fmt.Println("This production doesn't exist: " + production_key)
   306  		return shim.Error("This production doesn't exist: " + production_key)
   307  	}
   308  
   309  	var productionJSON Production
   310  	err = json.Unmarshal([]byte(productionAsBytes), &productionJSON)
   311  
   312  	var userJSON User
   313  	err = json.Unmarshal([]byte(userAsBytes), &userJSON)
   314  	if userJSON.Username != productionJSON.Username {
   315  		return shim.Error("The production's username doesn't correspond with the user's.")
   316  	}
   317  
   318  	if price_type != productionJSON.CopyrightPriceType {
   319  		return shim.Error("The production's priceType doesn't correspond with the supporter's.")
   320  	}
   321  
   322  	// step 4: make transfer
   323  	toAddress := userJSON.Address
   324  	amount := big.NewInt(0)
   325  	_, good := amount.SetString(price, 10)
   326  	if !good {
   327  		return shim.Error("Expecting integer value for amount")
   328  	}
   329  
   330  	fmt.Println(toAddress, ", ", price_type, ",", amount)
   331  	err = stub.Transfer(toAddress, price_type, amount)
   332  
   333  	if err != nil {
   334  		return shim.Error("Error when making transfer。")
   335  	}
   336  	if _, ok := productionJSON.Supporters[supporter]; ok {
   337  
   338  		productionJSON.Supporters[supporter] = Add(productionJSON.Supporters[supporter], price)
   339  	} else {
   340  		productionJSON.Supporters = make(map[string]string)
   341  		productionJSON.Supporters[supporter] = price
   342  	}
   343  	productionJSONasBytes, err := json.Marshal(productionJSON)
   344  	if err != nil {
   345  		return shim.Error(err.Error())
   346  	}
   347  
   348  	err = stub.PutState(production_key, productionJSONasBytes)
   349  	if err != nil {
   350  		return shim.Error(err.Error())
   351  	}
   352  
   353  	return shim.Success([]byte("add supporter success."))
   354  }
   355  
   356  func (*ProductionInvoke) ListOfBuyer(stub shim.ChaincodeStubInterface, args []string) pb.Response {
   357  	fmt.Println("list of buyer start.")
   358  	username := args[0]
   359  	product_type := args[1]
   360  	product_serial := args[2]
   361  	state_key := GetStateKey(ProductionPrefix, username, product_type, product_serial)
   362  	resultsIterator, err := stub.GetStateByRange(state_key+StateStartSymbol, state_key+StateEndSymbol)
   363  	if err != nil {
   364  		return shim.Error(err.Error())
   365  	}
   366  	list, err := GetListResult(resultsIterator)
   367  	if err != nil {
   368  		return shim.Error("getListResult failed")
   369  	}
   370  	var listOfProductionJson []Production
   371  	err = json.Unmarshal(list, &listOfProductionJson)
   372  	if err != nil {
   373  		return shim.Error(err.Error())
   374  	}
   375  	result := make(map[string]string)
   376  	for _, production := range listOfProductionJson {
   377  		buyers := production.Buyers
   378  		for k, v := range buyers {
   379  			if _, ok := result[k]; ok {
   380  				result[k] = Add(result[k], v)
   381  			} else {
   382  				result[k] = v
   383  			}
   384  		}
   385  	}
   386  	resultAsBytes, err := json.Marshal(result)
   387  	if err != nil {
   388  		return shim.Error(err.Error())
   389  	}
   390  	if resultAsBytes == nil {
   391  		fmt.Println("This buyers doesn't exist: ")
   392  		return shim.Error("This buyers doesn't exist: ")
   393  	}
   394  	return shim.Success(resultAsBytes)
   395  }
   396  
   397  func (w *ProductionInvoke) AddBuyer(stub shim.ChaincodeStubInterface, args []string) pb.Response {
   398  	fmt.Println("add buyer start.")
   399  	username := args[0]
   400  	production_type := args[1]
   401  	production_serial := args[2]
   402  	price_type := args[3]
   403  	buy_part := args[4]
   404  	buyer := args[5]
   405  	user_key := GetUserKey(username)
   406  	// verify weather the user exists
   407  	userAsBytes, err := stub.GetState(user_key)
   408  	if err != nil {
   409  		return shim.Error("Fail to get user: " + err.Error())
   410  	}
   411  	if userAsBytes == nil {
   412  		fmt.Println("This user doesn't exist: " + username)
   413  		return shim.Error("This user doesn't exist: " + username)
   414  	}
   415  
   416  	production_key := GetProductionKey(username, production_type, production_serial)
   417  	// verify weather the production exists
   418  	productionAsBytes, err := stub.GetState(production_key)
   419  	if err != nil {
   420  		return shim.Error("Fail to get artist: " + err.Error())
   421  	}
   422  	if productionAsBytes == nil {
   423  		fmt.Println("This production doesn't exist: " + production_key)
   424  		return shim.Error("This production doesn't exist: " + production_key)
   425  	}
   426  
   427  	var productionJSON Production
   428  	err = json.Unmarshal([]byte(productionAsBytes), &productionJSON)
   429  
   430  	var userJSON User
   431  	err = json.Unmarshal([]byte(userAsBytes), &userJSON)
   432  	if userJSON.Username != productionJSON.Username {
   433  		return shim.Error("The production's username doesn't correspond with the user's.")
   434  	}
   435  
   436  	if price_type != productionJSON.CopyrightPriceType {
   437  		return shim.Error("The production's priceType doesn't correspond with the supporter's.")
   438  	}
   439  
   440  	// 是否满足购买条件
   441  	total := "0"
   442  	buyers := productionJSON.Buyers
   443  	if buyers != nil {
   444  		for _, value := range buyers {
   445  			total = Add(total, value)
   446  		}
   447  	}
   448  	num1, _ := strconv.Atoi(Add(total, buy_part))
   449  	num2, _ := strconv.Atoi(productionJSON.CopyrightTransferPart)
   450  	if num1 > num2 {
   451  		return shim.Error("buy part too much")
   452  	}
   453  
   454  	// step 4: make transfer
   455  	toAddress := userJSON.Address
   456  	amount := big.NewInt(0)
   457  	_, good := amount.SetString(Mul(productionJSON.CopyrightPrice, buy_part), 10)
   458  	if !good {
   459  		return shim.Error("Expecting integer value for amount")
   460  	}
   461  
   462  	fmt.Println(toAddress, ", ", price_type, ",", amount)
   463  	err = stub.Transfer(toAddress, price_type, amount)
   464  	if err != nil {
   465  		return shim.Error("Error when making transfer。")
   466  	}
   467  	if _, ok := productionJSON.Buyers[buyer]; ok {
   468  		productionJSON.Buyers[buyer] = Add(productionJSON.Buyers[buyer], buy_part)
   469  	} else {
   470  		productionJSON.Buyers = make(map[string]string)
   471  		productionJSON.Buyers[buyer] = buy_part
   472  	}
   473  	productionJSONasBytes, err := json.Marshal(productionJSON)
   474  	if err != nil {
   475  		return shim.Error(err.Error())
   476  	}
   477  
   478  	err = stub.PutState(production_key, productionJSONasBytes)
   479  	if err != nil {
   480  		return shim.Error(err.Error())
   481  	}
   482  
   483  	return shim.Success([]byte("add supporter success."))
   484  }
   485  
   486  func (*ProductionInvoke) ModifyBuyer(stub shim.ChaincodeStubInterface, args []string) pb.Response {
   487  	fmt.Println("modify buyer start.")
   488  	// TODO
   489  	return shim.Success([]byte("modify buyer success."))
   490  }
   491  
   492  func (*ProductionInvoke) DeleteBuyer(stub shim.ChaincodeStubInterface, args []string) pb.Response {
   493  	fmt.Println("delete buyer start.")
   494  	// TODO
   495  	return shim.Success([]byte("delete buyer success."))
   496  }