IBM-Blockchain-Archive / fabric-boilerplate

Get up and running quickly with your own blockchain application!
Apache License 2.0
79 stars 150 forks source link

Trying to add thing for a user, but the thing is not reflected for the user #32

Closed salshyn closed 7 years ago

salshyn commented 7 years ago

Hi All,

I am trying to add a thing for a user, but can't. Here's what log shows:

screen shot 2017-01-31 at 3 13 15 pm

The height is getting changed (incremented each time I add something), which means it is getting added to blockchain.

screen shot 2017-01-31 at 3 14 25 pm

As you see here, the number of things still stay the same (2 things), while I would suppose it should be 3 things.

Here's the method I added and it is working:

screen shot 2017-01-31 at 3 15 43 pm

How to reflect the added thing for the user?

marcusvcs commented 7 years ago

You have to look at the smart contract code in the src folder: query.go and invoke.go. The add_thing method put a thing in the blockchain, but when you call get_all_things the contract is reading the things associated with the users, meaning that bold part of the JSON below.

"users": [ { "id": "marcus", "password": "passw0rd", "firstName": "Marcus Vinicius", "lastName": "LTDA", "things": [ "12345678", "87654321" ], "affiliation": "Banco_A", "address": "Dam 1, 1012 JS Amsterdam, The Netherlands", "phoneNumber": "0900 0048", "emailAddress": "xxx@gmail.com", "role": 0 }

So to correct this behavior you have to change the smart contract code to somehow associate the new thing created with an user.

salshyn commented 7 years ago

Right, I figured out already. I associated it.

That's how it looked before:

func add_thing(stub shim.ChaincodeStubInterface, args []string) ([]byte, error) {
    var item data.Thing
    err := json.Unmarshal([]byte(args[1]), &item)
    if err != nil { return nil, err }
    return nil, data.Save(stub, item)
}

And now:

func add_thing(stub shim.ChaincodeStubInterface, args []string) ([]byte, error) {
    // Unmarshal JSON to Thing model
    var item data.Thing
    err := json.Unmarshal([]byte(args[1]), &item)
    if err != nil { return nil, err }

    // Save new thing
    err = data.Save(stub, item)
    if err != nil { return nil, err }

    // Fetch user
    var user data.User
    err = utils.Get(stub, &user, args[2])
    if err != nil {
        return nil, errors.Wrap(err, "Could not get user "+args[2])
    }

    // Attach thing id to user's Things
    user.Things = append(user.Things, item.Id)

    // Save user
    return nil, data.Save(stub, user)
}
sitomani commented 7 years ago

I'm experimenting with the same on top of the boilerplate implementation; somehow it seems tho that modifying the user object upon add_thing will cause the chainnode go bad, and I can no longer authenticate or get the list of things for an user. Surprisingly though the add_thing still functions (using Postman to execute the API calls).

The error I get after once running into add_thing is Error:Failed to launch chaincode spec(Could not get deployment transaction for 13ceda62ab205bf012ac017caea6ed377f7bcd7fa807a607bb4830d00a02e802 - LedgerError - ResourceNotFound: ledger: resource not found)

I'm running the fabric local install in a mac (MacOS Sierra).

@salshyn did you do additional changes in the go implementation in addition to what is listed above?