Input Specification File

The Blockchain App Builder initialization command reads the input specification file and generates the scaffolded project with several tools to assist in the chaincode development process.

With the specification file you can specify multiple asset definitions and behavior, CRUD and non-CRUD method declaration, custom methods, validation of arguments, auto marshalling/unmarshalling, transparent persistence capability, and invoking rich data queries using SQL SELECTs or CouchDB Query Language. These features will be generated for you.

The specification file can be written in either yaml or json. You can see sample specification files in both formats in the Blockchain App Builder package download:
  • Fabcar-Typescript.yml
  • Marbles-Go.yml

Note:

As per Go conventions, exported names begin with a capital letter. Therefore all the asset properties and methods must have names starting with capital letters in the specification file.

Structure of the Specification File

Typically, you structure a specification file in the following way:

assets: 
    name:
    type:
    properties:
        name:
        type:
        id:
        derived:
           strategy:
           algorithm:
           format:
        mandatory:
        default:
        validate:
    methods:
        crud:
        others:
customMethods:

Blockchain App Builder supports two special asset types, embedded assets and token assets, in addition to generic assets with no specified type. The special assets are defined as type: embedded or type: token under the assets: section of the specification file.

Table 7-2 Specification File Parameter Descriptions and Examples

Entry Description Examples
assets:

This property takes the definition and behavior of the asset. You can give multiple asset definitions here.

 
name:

The name of the asset.

The following names are reserved. Do not use these names for assets.
  • account
  • role
  • hold
  • token
  • authorization
  • tokenAdmin
  • Account
  • Role
  • Hold
  • Token
  • Authorization
  • TokenAdmin
name: owner # Information about the owner
type:

Asset types

The following special asset types are supported:
  • embedded
  • token

If you do not specify a type parameter in the assets section, the asset is of the generic type.

 
type:

type: embedded

If this property is set to embedded the asset is defined as an embedded asset. Embedded assets do not have CRUD methods and have to be part of another asset to store in the ledger.

In the example, the property address is embedded, and is defined in another asset.

Embedded assets do not support circular references. For instance, in the previous example the address asset cannot contain a reference to the employee asset.

Asset: employee
name: employee
  properties:
     name: employeeId
     type: string
     mandatory: true
     id: true

     name: firstName
     type: string
     validate: max(30)
     mandatory: true

     name: lastName
     type: string
     validate: max(30)
     mandatory: true

     name: age
     type: number
     validate: positive(),min(18)

     name: address
     type: address
Asset: address
name: address

type: embedded

properties:
   name: street
   type: string

   name: city
   type: string

   name: state
   type: string

   name: country
   type: string
properties:

Describe all the properties of an asset.

 
name:

The name of the property.

name: ownerId # Unique ID for each owner
id:
  • true

This specifies the identifier of this asset. This property is mandatory.

name: owner            # Information about the owner
properties:
     name: ownerId    # Unique ID for each owner
     type: string
     mandatory: true
     id: true
     name: name        # Name of the owner
     type: string
     mandatory: true
type:

Property types

The following basic property types are supported:
  • number
  • float
  • string
  • boolean
  • date
  • array
For Go chaincodes, number is mapped to int and float is mapped to float64. Other types are not currently supported, including the following types:
  • complex
  • unsigned/signed int
  • 8/16/32/64 bits
name: year        # Model year
                    type: number
                    mandatory: true
                    validate: min(1910),max(2020)
                    name: color       # Color - no validation as color names are innumerable
                    type: string
                    mandatory: true
derived:

This property specifies that the id property is derived from other keys. Dependent properties should be string datatype and not an embedded asset.

This property has two mandatory parameters:
  • strategy: takes values of concat or hash.
  • format: takes an array of specification strings and values to be used by the strategy.
Example 1:
  • The property employeeID is dependent on the firstName and lastName properties.
  • This property is a concatenation of the values listed in the format array.
  • IND%1#%2%tIND is the 0th index in the array and describes the final format.
  • %n is a position specifier that takes its values from the other indexes in the array.
  • %t indicates the value should be stub.timestamp from the channel header.
  • If you need to use the character % in the format string, it should be escaped with another %.
  • The final format in this example would be: INDfirstName#lastName1606885454916IND
Example 2:
  • When using hash, you must also use the algorithm parameter. The default is sha256; md5 is also supported.
  • IND%1#%2%t is the 0th index in the array and describes the final format.
  • %n is a position specifier that takes its values from the other indexes in the array.
  • %t indicates the value should be stub.timestamp from the channel header.
  • If you need to use the character % in the format string, it should be escaped with another %.
Example 1
name: employee
  properties:
     name: employeeId
     type: string
     mandatory: true
     id: true
     derived:
         strategy: concat
         format: ["IND%1#%2%tIND","firstName","lastName"]

     name: firstName
     type: string
     validate: max(30)
     mandatory: true

     name: lastName
     type: string
     validate: max(30)
     mandatory: true

     name: age
     type: number
     validate: positive(),min(18)
Example 2
name: account
  properties:
     name: accountId
     type: string
     mandatory: true
     id: true
     derived:
         strategy: hash
         algorithm: 'sha256'
         format: ["IND%1#%2%t","bankName","ifsccode"]

     name: bankName
     type: string
     validate: max(30)
     mandatory: true

     name: ifsccode
     type: string
     mandatory: true
mandatory:
  • true
  • false

The corresponding property is mandatory and cannot be skipped while creating an asset.

name: phone       # Phone number - validate as (ddd)-ddd-dddd where dashes could also be periods or spaces
type: string
mandatory: true
validate: /^\(?([0-9]{3})\)?[-. ]?([0-9]{3})[-. ]?([0-9]{4})$/
name: cars        # The list of car VINs owned by this owner
type: string[]
mandatory: false
default:

This gives you the default value of this property.

 
validate:

The given property is validated against some of the out-of-box validations provided by Blockchain App Builder. You can chain validations if you ensure that the chain is valid.

If the validate property is not provided, then the validation is done against only the property type.

 
validate:

type: number

  • positive()
  • negative()
  • min()
  • max()

These validations can be chained together separated by commas.

name: offerApplied
type: number
validate: negative(),min(-4)
name: year  # Model year
type: number
mandatory: true
validate: min(1910),max(2020)
validate:

type: string

  • min()
  • max()
  • email()
  • url()
  • /regex/ - supports PHP regex

For Go chaincodes, regular expressions which contain certain reserved characters or whitespace characters should be properly escaped.

name: website 
type: string
mandatory: false
validate: url()
name: phone  # Phone number - validate as (ddd)-ddd-dddd where dashes could also be periods or spaces
type: string
mandatory: true
validate: /^\(?([0-9]{3})\)?[-. ]?([0-9]{3})[-. ]?([0-9]{4})$/
name: Color #Color can be red, blue, or green
type: string
mandatory: true
validate: /^\\s*(red|blue|green)\\s*$/
validate:

type: boolean

  • true
  • false

In the example, the validation of property active is by the type itself (boolean)

name: active
type: boolean
validate:

type: array

By type itself, in the form of type: number[], this conveys that the array is of type number.

You can enter limits to the array in the format number[1:5] which means minimum length is 1, maximum is 5. If either one is avoided, only min/max is considered.

name: items
type: number[:5]
validate:

type: date

  • min()
  • max()
Date should be one of these formats:
  • YYYY-MM-DD
  • YYYY-MM-DDTHH:MM:SSZ, where T separates the date from the time, and the Z indicates UTC. Timezone offsets can replace the Z as in -05:00 for Central Daylight Savings Time.
name: expiryDate
type: date
validate: max('2020-06-26')
name: completionDate
type: date
validate: min('2020-06-26T02:30:55Z')
methods:

Use this to state which of the CRUD (Create/Read/Update/Delete) or additional methods are to be generated.

By default, if nothing is entered, all CRUD and other methods are generated.

methods:
    crud: [create, getById, update, delete]
    others: [getHistoryById, getByRange]
crud:
  • create
  • getByID (read)
  • update
  • delete

If this array is left empty, no CRUD methods will be created.

If the crud parameter is not used at all, all four methods will be created by default.

The crud parameter is not applicable to token and embedded assets.

methods:
    crud: [create, getById, delete]
    others: [] # no other methods will be created
others:
  • getHistoryById
  • getByRange

getHistoryById returns the history of the asset in a list.

getByRange returns all the assets in a given range. For more information, see "getByRange" (TypeScript) and "GetByRange" (Go).

If this array is left empty, no other methods will be created.

If the others parameter is not used at all, both methods will be created by default.

The others parameter is not applicable to token and embedded assets.

methods:
    crud: [create, delete]
    others: [] # no other methods will be created
      methods:
        crud: [create, getById, update, delete]
        others: [getHistoryById, getByRange]
customMethods:

This property creates invokable custom method templates in the main controller file. It takes the method signature and creates the function declaration in the controller file.

You can provide language specific function declarations here.

We provide a custom method named executeQuery. If it's added to the specification file, it details how Berkeley DB SQL and CouchDB rich queries can be executed. This method can be invoked only when you are connected to Oracle Blockchain Platform Cloud or Enterprise Edition.

TypeScript

customMethods:
    - executeQuery
    - "buyCar(vin: string, buyerId: string, sellerId: string, price: number, date: Date)"
    - "addCar(vin: string, dealerId: string, price: number, date: Date)"

Go

customMethods:
    - executeQuery
    - "BuyCar(vin string, buyerId string, sellerId string, price int)"
    - "AddCar(vin string, dealerId string, price int)"