field development

sample

//! 
//! Copyright (c) 2015, The casual project
//!
//! This software is licensed under the MIT license, https://opensource.org/licenses/MIT
//!


/*
 * Disclaimer: This might not be a valid C-function
 *
 * Disclaimer: A lot of error handling is missing
 */

#include "xatmi.h"
#include "casual/buffer/field.h"

#include <cstddef>
#include <cstdio>


/*
 * Just for this sample (see casual_field_make_header)
 */
#define FLD_ID       (CASUAL_FIELD_STRING * CASUAL_FIELD_TYPE_BASE + 1)
#define FLD_COUNT    (CASUAL_FIELD_LONG   * CASUAL_FIELD_TYPE_BASE + 1)
#define FLD_NAME     (CASUAL_FIELD_STRING * CASUAL_FIELD_TYPE_BASE + 2)
#define FLD_COST     (CASUAL_FIELD_DOUBLE * CASUAL_FIELD_TYPE_BASE + 1)


int call_with_field()
{
   char* buffer;
   long length;

   const char* name;
   double cost;

   int result;

   /*
    * The buffer auto-resizes, so we do not need to give it a size
    */

   length = 0;

   buffer = tpalloc( CASUAL_FIELD, nullptr, length);

   result = CASUAL_FIELD_SUCCESS;

   result |= casual_field_add_string( &buffer, FLD_ID, "123");
   result |= casual_field_add_long( &buffer, FLD_COUNT, 2);


   tpcall( "some_service", buffer, length, &buffer, &length, TPSIGRSTRT);

   result |= casual_field_get_string( buffer, FLD_NAME, 0, &name);
   result |= casual_field_get_double( buffer, FLD_COST, 0, &cost);

   if( result)
   {
      /* something went wrong */
   }


   printf( "name %s", name);
   printf( "cost %f", cost);


   tpfree( buffer);

   return 0;
}

remarks

  • No encoding of strings occurs

  • The buffer is automatically resized and therefore might update the buffer-handle

  • Don’t manipulate the buffer in other ways (such as memcpy()) than by casual_field-functions, because the internal index will then be out of sync

  • A field-repository might be needed for certain functionality

tools

casual_field_make_header

The tool is to provide something like mkfldhdr

Keys (id:s) to use most of the casual_field-functions can be provided in any way by the application it self, as long as their ranges match their types, and the repository is just needed for certain casual_field-functions where some mapping from the id (long) to some string-name (like casual_field_name_of_id() etc) is needed.

If there is a repository, casual_field_make_header can be used to create a header-file with defines where user-provided id:s are transformed to match it’s type-range.

usage: casual_field_make_header [repository]

If the repository-file is not provided, the environment-variable CASUAL_FIELD_TABLE is used

Layout of the repository should conform to a structure described in this:

json-schema

{
  "$schema": "http://json-schema.org/draft-04/schema#",
  "type": "object",
  "required": [ "groups"],
  "properties": {
    "groups": {
      "type": "array",
      "items": [{
        "type": "object",
        "optional": [ "base"],
        "properties": {
          "base": { "type": "integer"},
          "fields": {
            "type": "array",
            "items": [{
              "type": "object",
              "required": [ "id", "name", "type"],
              "properties": {
                "id": { "type": "integer"},
                "name": { "type": "string"},
                "type": { "type": "string"}
              }
            }]
          }
        }
      }]
    }
  }
}

json-sample

{
  "groups": [
    {
      "base": 1000,
      "fields": [
        {
          "id": 1,
          "name": "FLD_SHORT1",
          "type": "short"
        },
        {
          "id": 2,
          "name": "FLD_SHORT2",
          "type": "short"
        },
        {
          "id": 3,
          "name": "FLD_SHORT3",
          "type": "short"
        },
        {
          "id": 1,
          "name": "FLD_LONG1",
          "type": "long"
        },
        {
          "id": 2,
          "name": "FLD_LONG2",
          "type": "long"
        },
        {
          "id": 3,
          "name": "FLD_LONG3",
          "type": "long"
        },
        {
          "id": 1,
          "name": "FLD_CHAR1",
          "type": "char"
        },
        {
          "id": 2,
          "name": "FLD_CHAR2",
          "type": "char"
        },
        {
          "id": 3,
          "name": "FLD_CHAR3",
          "type": "char"
        }
      ]
    },
    {
      "base": 2000,
      "fields": [
        {
          "id": 1,
          "name": "FLD_FLOAT1",
          "type": "float"
        },
        {
          "id": 2,
          "name": "FLD_FLOAT2",
          "type": "float"
        },
        {
          "id": 3,
          "name": "FLD_FLOAT3",
          "type": "float"
        },
        {
          "id": 1,
          "name": "FLD_DOUBLE1",
          "type": "double"
        },
        {
          "id": 2,
          "name": "FLD_DOUBLE2",
          "type": "double"
        },
        {
          "id": 3,
          "name": "FLD_DOUBLE3",
          "type": "double"
        },
        {
          "id": 1,
          "name": "FLD_STRING1",
          "type": "string"
        },
        {
          "id": 2,
          "name": "FLD_STRING2",
          "type": "string"
        },
        {
          "id": 3,
          "name": "FLD_STRING3",
          "type": "string"
        },
        {
          "id": 1,
          "name": "FLD_BINARY1",
          "type": "binary"
        },
        {
          "id": 2,
          "name": "FLD_BINARY2",
          "type": "binary"
        },
        {
          "id": 3,
          "name": "FLD_BINARY3",
          "type": "binary"
        }
      ]
    }
  ]
}

xml-schema

<?xml version="1.0" encoding="UTF-8"?>
<xsd:schema xmlns:xsd="http://www.w3.org/2001/XMLSchema">

<xsd:element name="groups">
  <xsd:complexType>
    <xsd:sequence>
      <xsd:element name="element" maxOccurs="unbounded">
        <xsd:complexType>
          <xsd:sequence>
            <xsd:element name="base" type="xsd:integer" minOccurs="0"/>
            <xsd:element name="fields" maxOccurs="unbounded">
              <xsd:complexType>
                <xsd:sequence>
                  <xsd:element name="element" maxOccurs="unbounded">
                    <xsd:complexType>
                      <xsd:sequence>
                        <xsd:element name="id" type="xsd:integer"/>
                        <xsd:element name="name" type="xsd:string"/>
                        <xsd:element name="type" type="xsd:string"/>
                      </xsd:sequence>
                    </xsd:complexType>
                  </xsd:element>
                </xsd:sequence>
              </xsd:complexType>
            </xsd:element>
          </xsd:sequence>
        </xsd:complexType>
      </xsd:element>
    </xsd:sequence>
  </xsd:complexType>
</xsd:element>

</xsd:schema>

xml-sample

<?xml version="1.0" encoding="UTF-8"?>
<groups>
   <element>
      <base>1000</base>
      <fields>
         <element>
            <id>1</id>
            <name>FLD_SHORT1</name>
            <type>short</type>
         </element>
         <element>
            <id>2</id>
            <name>FLD_SHORT2</name>
            <type>short</type>
         </element>
         <element>
            <id>3</id>
            <name>FLD_SHORT3</name>
            <type>short</type>
         </element>

         <element>
            <id>1</id>
            <name>FLD_LONG1</name>
            <type>long</type>
         </element>
         <element>
            <id>2</id>
            <name>FLD_LONG2</name>
            <type>long</type>
         </element>
         <element>
            <id>3</id>
            <name>FLD_LONG3</name>
            <type>long</type>
         </element>

         <element>
            <id>1</id>
            <name>FLD_CHAR1</name>
            <type>char</type>
         </element>
         <element>
            <id>2</id>
            <name>FLD_CHAR2</name>
            <type>char</type>
         </element>
         <element>
            <id>3</id>
            <name>FLD_CHAR3</name>
            <type>char</type>
         </element>
      </fields>
   </element>
   <element>
      <base>2000</base>
      <fields>
         <element>
            <id>1</id>
            <name>FLD_FLOAT1</name>
            <type>float</type>
         </element>
         <element>
            <id>2</id>
            <name>FLD_FLOAT2</name>
            <type>float</type>
         </element>
         <element>
            <id>3</id>
            <name>FLD_FLOAT3</name>
            <type>float</type>
         </element>

         <element>
            <id>1</id>
            <name>FLD_DOUBLE1</name>
            <type>double</type>
         </element>
         <element>
            <id>2</id>
            <name>FLD_DOUBLE2</name>
            <type>double</type>
         </element>
         <element>
            <id>3</id>
            <name>FLD_DOUBLE3</name>
            <type>double</type>
         </element>

         <element>
            <id>1</id>
            <name>FLD_STRING1</name>
            <type>string</type>
         </element>
         <element>
            <id>2</id>
            <name>FLD_STRING2</name>
            <type>string</type>
         </element>
         <element>
            <id>3</id>
            <name>FLD_STRING3</name>
            <type>string</type>
         </element>

         <element>
            <id>1</id>
            <name>FLD_BINARY1</name>
            <type>binary</type>
         </element>
         <element>
            <id>2</id>
            <name>FLD_BINARY2</name>
            <type>binary</type>
         </element>
         <element>
            <id>3</id>
            <name>FLD_BINARY3</name>
            <type>binary</type>
         </element>
      </fields>
   </element>
</groups>

yaml-sample

groups:
  - base: 1000
    fields:
      - id: 1
        name: FLD_SHORT1
        type: short

      - id: 2
        name: FLD_SHORT2
        type: short

      - id: 3
        name: FLD_SHORT3
        type: short

      - id: 1
        name: FLD_LONG1
        type: long

      - id: 2
        name: FLD_LONG2
        type: long

      - id: 3
        name: FLD_LONG3
        type: long

      - id: 1
        name: FLD_CHAR1
        type: char

      - id: 2
        name: FLD_CHAR2
        type: char

      - id: 3
        name: FLD_CHAR3
        type: char



  - base: 2000
    fields:
      - id: 1
        name: FLD_FLOAT1
        type: float

      - id: 2
        name: FLD_FLOAT2
        type: float

      - id: 3
        name: FLD_FLOAT3
        type: float

      - id: 1
        name: FLD_DOUBLE1
        type: double

      - id: 2
        name: FLD_DOUBLE2
        type: double

      - id: 3
        name: FLD_DOUBLE3
        type: double

      - id: 1
        name: FLD_STRING1
        type: string

      - id: 2
        name: FLD_STRING2
        type: string

      - id: 3
        name: FLD_STRING3
        type: string

      - id: 1
        name: FLD_BINARY1
        type: binary

      - id: 2
        name: FLD_BINARY2
        type: binary

      - id: 3
        name: FLD_BINARY3
        type: binary

ini-sample

[groups]
base=1000

[groups.fields]
id=1
name=FLD_SHORT1
type=short

[groups.fields]
id=2
name=FLD_SHORT2
type=short

[groups.fields]
id=3
name=FLD_SHORT3
type=short

[groups.fields]
id=1
name=FLD_LONG1
type=long

[groups.fields]
id=2
name=FLD_LONG2
type=long

[groups.fields]
id=3
name=FLD_LONG3
type=long

[groups.fields]
id=1
name=FLD_CHAR1
type=char

[groups.fields]
id=2
name=FLD_CHAR2
type=char

[groups.fields]
id=3
name=FLD_CHAR3
type=char

[groups]
base=2000

[groups.fields]
id=1
name=FLD_FLOAT1
type=float

[groups.fields]
id=2
name=FLD_FLOAT2
type=float

[groups.fields]
id=3
name=FLD_FLOAT3
type=float

[groups.fields]
id=1
name=FLD_DOUBLE1
type=double

[groups.fields]
id=2
name=FLD_DOUBLE2
type=double

[groups.fields]
id=3
name=FLD_DOUBLE3
type=double

[groups.fields]
id=1
name=FLD_STRING1
type=string

[groups.fields]
id=2
name=FLD_STRING2
type=string

[groups.fields]
id=3
name=FLD_STRING3
type=string

[groups.fields]
id=1
name=FLD_BINARY1
type=binary

[groups.fields]
id=2
name=FLD_BINARY2
type=binary

[groups.fields]
id=3
name=FLD_BINARY3
type=binary