Transactions
General transaction signing flow
Below you can see the sequence diagram for submitting a transaction to our blockchain.
Several steps are not mandatory, just the most convenient way to do things.
Steps 1-4 can be replaced by a direct call to the appropriate endpoint.
It is also possible to use the SDK to send transactions with one method.
The easy way
You call the sendTransaction
method of the SDK with the transaction data and your certificate/private key combination.
import { BAM, BaseUrl } from 'bam-ticketing-sdk'
const wallet = {
certificate: '-------BEGIN CERTIFICATE------- .....',
privateKey: 'You got this when you enrolled',
}
const bam = await BAM.build({
baseUrl: BaseUrl.Prod, // Change this appropriately
credentials: new WalletCredentials(wallet),
})
// Blockchain function to call
const proposal = {
fcn: "TICKET.INVALIDATE",
args: ['{"seq_num": "12","ticket_config": {"id": "23","event": {"id": "3334"}}}']
}
const txResult = await bam.blockchain.sendTransaction(payload, wallet)
// txResult: {status: "SUCCESS",...}
The more detailed way
This is essentially what the sendTransaction
method does internally.
1. Generate an unsigned transaction proposal
The client calls the POST blockchain/v1/transaction/proposal endpoint of the blockchain service.
The payload of the request should have two fields, fcn and args.
fcn
- is the name of the chaincode function that the transaction should execute.args
- is a list of the arguments passed to the chaincode function.
curl -X POST
--header 'Content-Type: application/json'
-d '{"fcn": "TICKET.INVALIDATE", "certificate":"-------BEGIN CERTIFICATE------- .....", "args": [{"seq_num": 12,"ticket_config": {"id": 23,"event": {"id": "3334"}}}]}'
'https://catapult.api.bam.fan/blockchain/v1/transaction/proposal'
import { BAM } from 'bam-ticketing-sdk'
const bam = await BAM.build({
baseUrl: BaseUrl.Prod, // Change this appropriately
})
const proposal = await bam.blockchain.createProposal({
// Blockchain function to call
fcn: "TICKET.INVALIDATE",
certificate: "-------BEGIN CERTIFICATE------- .....",
args: ['{"seq_num": "12","ticket_config": {"id": "23","event": {"id": "3334"}}}']
})
// proposal = {"digest": "1234567890abcdef1234567890abcdef1234567890abcdef"}
The response's payload has the unsigned transaction proposal digest, which should be signed with the wallet's private key.
2. Send the signed transaction proposal to the endorsers and generate an unsigned transaction
The client calls the [POST blockchain/v1/transaction/proposal/:digest] endpoint of the blockchain service.
The payload of the request should have one field, signature
. The signature field
is a string gotten by signing the unsigned transaction proposal digest.
The response's payload has the unsigned transaction digest, which should be signed with the wallet's private key.
curl -X POST
--header 'Content-Type: application/json'
-d '{"signature": "$proposal_signature"}'
'https://catapult.api.bam.fan/blockchain/v1/transaction/proposal/1234567890abcdef1234567890abcdef1234567890abcdef'
import { signDigest } from 'bam-ticketing-sdk'
const proposalSignature = signDigest("YOUR_PRIVATE_KEY_PEM", proposal.digest)
const transaction = await bam.blockchain.createTransaction({
signature: proposalSignature,
digest: proposal.digest
})
// transaction = {"digest": "AAAAAAAABBBBBBBBCCCCCCCCDDDDDDDDEEEEEEE"}
3. Commit the signed transaction
The client calls the POST blockchain/v1/transaction/:digest endpoint of the blockchain service.
The payload of the request should have one field, signature
. The signature field
is a string gotten by signing the unsigned transaction digest.
The payload of the response has the status field, which is the status of the transaction.
curl -X POST
--header 'Content-Type: application/json'
-d '{"signature": "$tx_signature"}'
'https://catapult.api.bam.fan/blockchain/v1/transaction/AAAAAAAABBBBBBBBCCCCCCCCDDDDDDDDEEEEEEE'
import { signDigest } from 'bam-ticketing-sdk'
const txSignature = signDigest("YOUR_PRIVATE_KEY_PEM", transaction.digest)
const txStatus = await bam.blockchain.commitTransaction({
signature: txSignature,
digest: transaction.digest
})
// txStatus = {"info": "", "status": "OK"}
4. Sending the committed transaction payload to the queue
After every successful committing of the transaction, a message is published to the queue.
The message has the same shape as the unsigned transaction proposal request payload.