# Home

Discover everything you need to know about the platform with our comprehensive documentation.

<table data-view="cards"><thead><tr><th></th><th></th><th></th><th data-hidden data-card-cover data-type="files"></th><th data-hidden data-card-target data-type="content-ref"></th></tr></thead><tbody><tr><td><strong>What is TuumIO Protocol?</strong></td><td>Get an overview of the core components of the protocol.</td><td></td><td></td><td><a href="/pages/X9wjUQOTNolESGmoDwuM#what-is-care.platform">/pages/X9wjUQOTNolESGmoDwuM#what-is-care.platform</a></td></tr><tr><td><strong>Protocol Guide</strong></td><td>Learn how to build and author decentralized applications (dApps).</td><td></td><td></td><td><a href="/pages/Agsdt6kNZGVNAaPtmFoP">/pages/Agsdt6kNZGVNAaPtmFoP</a></td></tr><tr><td><strong>Tutorials</strong></td><td><a href="/pages/ST1y4nqdV7NnZjgwVZ0q">Create an Event Booker</a><br><a href="/pages/sdMci3Ye6TYpv0PIYR2H">Create a Library Explorer</a></td><td></td><td></td><td><a href="/pages/3F07dNYh3e7IjfLOYXYR">/pages/3F07dNYh3e7IjfLOYXYR</a></td></tr></tbody></table>


# Introduction

## What is TuumIO Protocol?

**TuumIO.Protocol** is a secure and decentralized platform that empowers individuals to take control of their data using blockchain technology. It is designed to reduce reliance on centralized IT systems and provides a foundation for Web3 development.

## **Key Components**

**Chains**: Enterprise-level solutions that offer a wide range of products and services categorized by various industries, such as healthcare, finance, gaming, and more.

**dApp**: A decentralized application in Web3 that offers various functionalities, including interactions, data exchanges, and workflows for specific user roles.

**TuumIO Wallet**: A mobile application that allows users to store and manage digital assets, and serves as a gateway to chains and dApps.

## Use Case Examples

### Remote patient monitoring

Facilitates treatment adjustments and supports patients in managing their conditions remotely, without direct intervention from care providers.

<figure><img src="/files/29CUEOBWD9rB3z4AuDrN" alt="remote-patient-monitoring-use-case" width="375"><figcaption><p>Figure 1: Use case diagram for remote patient monitoring</p></figcaption></figure>

### Insurance claims processing

Manages the submission and processing of insurance claims. Patients can submit claims for reimbursement plans, such as vision or dental insurance, ensuring faster and more transparent processing.

<figure><img src="/files/oMwSsSosaR6l0L9vGcMn" alt="insurance-claims-processing-use-case" width="375"><figcaption><p>Figure 2: Use case diagram for insurance claims processing</p></figcaption></figure>

### Employee rewards system

Addresses burnout and high turnover among employees by implementing a rewards system. This can include gift cards, paid time offs, discount vouchers, wellness programs, and more.

<figure><img src="/files/mD3xKWIFoQNmB9Z41wwi" alt="employee-rewards-system-use-case" width="375"><figcaption><p>Figure 3: Use case diagram for an employee rewards system</p></figcaption></figure>


# Architecture

<figure><img src="/files/ElJMwfpzvnSLrVvjR3Lr" alt=""><figcaption><p>Figure 4: High-level Platform Architecture</p></figcaption></figure>

## Application Layer

The **Application Layer** handles configuration, administration, and communication within networks, allowing users to interact with decentralized applications (dApps).

* **TuumIO Wallet**: A mobile app that allows users to store and manage digital assets and serves as a gateway to various industry services and dApps.
* **Journeys**: A sequence of interconnected cards outlining specific workflows for roles such as participants, administrators, managers and employees.
* **TuumIO Card**: An interactive module that combines text, images, buttons, and interoperable functions on the app's user interface.
* **TuumIO Network**: A digital network of various healthcare roles, operating based on the rules defined in the TuumIO Protocol.
* **TuumIO Protocol**: A governance framework that defines the rules for data exchange and communication, facilitating secure transactions and interactions within the network.

## Data Layer

The **Data Layer** provides secure, transparent, decentralized data storage and records management.

* **MainNet**: Holds the core registry service that maps TuumIO Wallet users to their respective TuumIO Networks, such as the country matrix for region-based services.
* **Node Vault**: A secure and decentralized storage of data for TuumIO Nodes, with backups stored in [Storj](https://www.storj.io/).
* **Event Ledger**: A decentralized, immutable record of event logs from sender and recipient node addresses, including payload data.
* **TuumIO Data Node (CDN)**: A specialized node created for each network. It manages data storage, processing, and exchanges with external systems.

## Compute Layer

The **Compute Layer** manages core operations and node management, ensuring secure data and event transmission across the network.

* **TuumIO Node**: An entity that manages data storage and event handling across the network. It is a secure, versatile object deployable in any environment.
* **Network Onboarding Manager (NOM)**: Facilitates the initial creation and assignments of TuumIO Nodes upon joining the network.
* **Node Lifecycle Manager (NLM)**: Manages the creation and lifecycle states of TuumIO Nodes, including active, start, stop, and hibernate states.
* **Base Node Services (BNS)**: Ensures secure transmission of events and data through the blockchain.


# Get Started

**TuumIO** **Protocol** defines the rules governing information communication and data exchange. It employs an event-driven architecture and utilizes JSON files to represent configurations for roles, relationships, journeys, events, and interactions. By using standard data structures, it reduces complexity and enables interoperability between systems.

In this guide, you'll learn how to manually author TuumIO Protocol using provided examples.

### Structure of files and folders

<pre><code>├── sample-network/
     ├── definitions/
     │    ├── card/
<strong>     │    ├── ddf/     
</strong>     │    ├── event/
     │    ├── event-handler/
     │    ├── python-event-handler/
     │    ├── resources/
     │    └── td/
     └── input.json 
</code></pre>

### Prerequisites

Before you begin, ensure you have the following:

* An Integrated Development Environment (IDE) or a text editor to manually author files.
* The required Python packages to configure and run Python event handlers.
* Postman API platform and the network environment details for publishing.
* BrowserStack, a cloud web and mobile testing platform, for testing the application.


# Components

This section describes the structured files and modules that can be configured in TuumIO Protocol.

### `input.json`

The `input.json` file is a hierarchical structure of objects defined within a network. It contains information about the network, roles, journeys, cards, events, event handlers, and TuumIO ledgers.

### TuumIO Data Node

The TuumIO Data Node (TDN) serves as the network's central database for storing and processing data files. It facilitates data exchange with external client systems, including electronic medical records, claims systems, member systems, and payment systems.

### TuumIO Card definitions

A TuumIO Card is an interactive module encapsulating multiple data types, user interface elements, and interoperable functions. The TuumIO Card definition structure includes card data, layout, card footer, and UI actions.

### Event definitions

Events define the interactions and communication between roles or nodes in the network, such as sending and receiving information. Events are chained together in a time series on a blockchain, creating a secure, transparent, and immutable record of transactions within the network.

### Event handlers

An event handler is a set of instructions that execute tasks based on specific events. These tasks include updating records, transforming data, and identifying recipients for the next event.

### Python event handlers

Python event handlers are designed to execute complex events and transactions that require data processing, analysis, import, and export. They can fetch external data in HL7, X12 EDI, XML, JSON, or CSV formats.

### Resources

Resources contain predefined data that is inserted or updated automatically during initialization.

### Transactional data

Transactional data consists of configurable data that can be referenced from roles, cards, or events within the network.


# Definition of Terms

This section provides definitions for the key terms used throughout this documentation.

<table><thead><tr><th width="242">Term</th><th>Definition</th></tr></thead><tbody><tr><td>TuumIO Card (Card)</td><td>An interactive module encapsulating multiple data types, user interface elements, and interoperable functions. "TuumIO Card" and "Card" are used interchangeably in this document.</td></tr><tr><td>TuumIO Data Node (TDN)</td><td>A specialized node that acts as a database, facilitating secure data storage, retrieval, and exchange with external systems.</td></tr><tr><td>TuumIO Ledger</td><td>A decentralized record of events or transactions within a network, as defined by the protocol.</td></tr><tr><td>TuumIO Network (Network)</td><td>A digital network of various healthcare roles, operating based on rules defined in a TuumIO Protocol. "TuumIO Network" and "Network" are used interchangeably in this document.</td></tr><tr><td>TuumIO Node (Node)</td><td>A secure digital entity that enables secure data exchange and event handling. "TuumIO Node" and "Node" are used interchangeably in this document.</td></tr><tr><td>TuumIO Protocol (Protocol)</td><td>A governance framework that defines the rules for data exchange and communication in networks. "TuumIO Protocol" and "Protocol" are used interchangeably in this document.</td></tr><tr><td>TuumIO Wallet (Wallet)</td><td>A mobile app that serves as a gateway to various industry services and dApps. It provides a secure way to store and manage digital assets and records. "TuumIO Wallet" and "Wallet" are used interchangeably in this document.</td></tr><tr><td>TuumIO Vault (Vault)</td><td>A decentralized storage, facilitating secure data management and storage.</td></tr><tr><td>Chain </td><td>An enterprise-level solution that offers various industry services.</td></tr><tr><td>dApps</td><td>A decentralized application in Web3 that offers various functionalities, including interactions, data exchanges, and workflows for specific user roles.</td></tr><tr><td>Data definition file (DDF)</td><td>A JSON file specifying the structure of data stored within the TuumIO Data Node, defining data elements, data types, and validation rules.</td></tr><tr><td>Event</td><td>A message or record signifying an occurrence within a network or journey. Events define interactions and communications between roles and nodes.</td></tr><tr><td>Event Handler</td><td>A set of instructions that execute tasks based on specific events. These tasks include updating records, transforming data, and identifying recipients for the next event.</td></tr><tr><td>Journeys</td><td>A sequence of interconnected TuumIO Cards, defining functionalities, including interactions, data exchanges, and workflows for specific user roles.</td></tr><tr><td>Role</td><td>A fundamental element in the protocol that defines a specific participant type, such as patient, physician, admins, etc. Each role is associated with corresponding consents and cards within the protocol.</td></tr><tr><td>SOLVE</td><td>A cryptocurrency utility token used throughout the platform to facilitate payments and transactions.</td></tr><tr><td>Tile</td><td>A modular component in a card user interface that displays data or provides functionality.</td></tr></tbody></table>


# Build a dApp

This section outlines the steps involved in authoring the protocol for building decentralized applications (dApps).

{% hint style="warning" %}
**Note:** Ensure that all fields and values adhere strictly to the protocol structure and specifications.
{% endhint %}

## Understand the structure of the `input.json` file

* Open the `input.json` file in a text editor.
* View or modify the [network details](/protocol-guide/build-a-dapp/network-configuration#network-metadata).
* In the network settings, fill in the [author details](/protocol-guide/build-a-dapp/network-configuration#author-details-and-countries) and specify the [supported countries](/protocol-guide/build-a-dapp/network-configuration#author-details-and-countries).
* Configure the [join network settings](/protocol-guide/build-a-dapp/network-configuration#join-network-settings) and set up [solve token usage](/protocol-guide/build-a-dapp/network-configuration#solve-token-settings).
* Define the [roles](/protocol-guide/build-a-dapp/roles-and-journeys#roles) and [journeys](/protocol-guide/build-a-dapp/roles-and-journeys#journeys).
* Declare the included [cards](/protocol-guide/build-a-dapp/card-definitions#cards), [events](/protocol-guide/build-a-dapp/events-and-event-handlers#events), and [event handlers](/protocol-guide/build-a-dapp/events-and-event-handlers#event-handlers).
* If necessary, include details about [tuumIO ledgers](/protocol-guide/build-a-dapp/tuumio-ledgers).
* Save and validate the `input.json` file.

## Define the data structure

* Create a [data definition file](/protocol-guide/build-a-dapp/tuumio-data-node#data-definition-file) based on how you want to organize data.
* Define the structure of the [transactional data](/protocol-guide/build-a-dapp/transactional-data).

## Create the definitions for cards&#x20;

* Define the [card structure](/protocol-guide/build-a-dapp/card-definitions#card-definition-structure), including [tiles](/protocol-guide/build-a-dapp/card-definitions/tiles) and [functions](/protocol-guide/build-a-dapp/card-definitions/functions).

## Create events and event handler definitions

* Configure the [events](/protocol-guide/build-a-dapp/events-and-event-handlers#events) and [event handlers](/protocol-guide/build-a-dapp/events-and-event-handlers#event-handlers).
* Configure [node event handlers](/protocol-guide/build-a-dapp/node-event-handlers).

## Configure Python event handlers

* Understand the predefined functions in the [Python template](/protocol-guide/build-a-dapp/python-event-handlers#python-event-handler-template).
* Perform the steps to configure an event based on the [use case example](/protocol-guide/build-a-dapp/python-event-handlers#use-case-example).


# Network Configuration

This section describes the overall network specifications, including author details, countries, join network settings, and solve token settings.

## Network metadata

<table><thead><tr><th width="213">Field Name</th><th width="174">Value Type</th><th>Description</th></tr></thead><tbody><tr><td>network_id</td><td>string</td><td>The unique ID associated with the network.</td></tr><tr><td>node_url</td><td>string</td><td>The URL of the network node where it is deployed.</td></tr><tr><td>name</td><td>string</td><td>The unique name of the network.</td></tr><tr><td>version</td><td>number</td><td>The version number of the network protocol.</td></tr><tr><td>description</td><td>string</td><td>The short description of the network.</td></tr><tr><td>publish_date</td><td>string</td><td>The date when the network protocol is published.</td></tr><tr><td>effective_date</td><td>string</td><td>The date when the protocol is effective or operational within the network.</td></tr></tbody></table>

{% code title="Example:" %}

```json
{
    "tuumIO_protocol": {
        "network_id": "dev-network-xxx",
        "node_url": "https://site000.abc.net",
        "name": "My TuumIO Network",
        "version": 1,
        "description": "This is a sample TuumIO network.",
        "publish_date": "2024-03-27",
        "effective_date": "2024-03-27",
```

{% endcode %}

## Author details and countries

<table><thead><tr><th width="212">Field Name</th><th width="172">Value Type</th><th>Description</th></tr></thead><tbody><tr><td>author_name</td><td>string</td><td>The name of the network protocol's author (entity or person).</td></tr><tr><td>author_website</td><td>string</td><td>The website URL of the author.</td></tr><tr><td>author_address1</td><td>string</td><td>The address of the author (line1).</td></tr><tr><td>author_address2</td><td>string</td><td>The address of the author (line2).</td></tr><tr><td>geo_fence_countries</td><td>string</td><td>The list of countries that can join the network.</td></tr></tbody></table>

{% code title="Example:" %}

```json
        "network_settings": {
                    "author_details": {
                        "author_name": "John Carter",
                        "author_address1": "127 Goyette River, Lake Audreanne",
                        "author_website": "www.abc-company.net",
                        "author_address2": "Arizona"
                    },
                    "geo_fence_countries": [
                        "US",
                        "IN",
                        "UA"
                    ]
                },
```

{% endcode %}

## Join network settings

<table><thead><tr><th width="211">Field Name</th><th width="169">Value Type</th><th>Description</th></tr></thead><tbody><tr><td>role</td><td>string</td><td>The ID of the role joining the network.</td></tr><tr><td>join_method</td><td>string</td><td>The method of joining the network.</td></tr><tr><td>required_consents</td><td>array</td><td>The cards which you allow other users in the network to access.</td></tr><tr><td>terms_and_conditions_checksum</td><td>string</td><td>The terms and conditions for joining the network.</td></tr></tbody></table>

{% code title="Example:" %}

```json
                    "join_network_settings": {
                      "join_roles": [
                        {
                          "role": "rl-patient",
                          "join_method": "DEFAULT",
                          "required_consents": ["WALLET", "PHONE"],
                          "terms_and_conditions_checksum": "d61c0c428b88a19c1d0b9e10dae816fe"
                        },
                        {
                          "role": "rl-doctor",
                          "join_method": "INVITE",
                          "required_consents": ["WALLET"],
                          "terms_and_conditions_checksum": "6dadacb7b61860d446c5ebdffcc2be54"
                        }
                      ]
                    },
```

{% endcode %}

## SOLVE token usage

<table><thead><tr><th width="205">Field Name</th><th width="150">Value Type</th><th>Description</th></tr></thead><tbody><tr><td>deposit_value</td><td>string</td><td>The deposit value of SOLVE tokens.</td></tr><tr><td>redemption_value</td><td>string</td><td>The redemption value of SOLVE tokens.</td></tr><tr><td>solve_gas_setting</td><td>JSON</td><td>The SOLVE gas usage setting.</td></tr><tr><td>event_wise_cost</td><td>array</td><td>The event and the cost in SOLVE token.</td></tr><tr><td>event</td><td>string</td><td>The event used for transactions in the network.</td></tr><tr><td>cost</td><td>integer</td><td>The cost in SOLVE gas for each event transaction.</td></tr></tbody></table>

{% code title="Example:" %}

```json
            "solve_token_usage": {
                "deposit_value": "Market",
                "redemption_value": "Deposit",
                "solve_gas_setting": {
                    "event_wise_cost": [
                        {
                            "event": "e-booking-appointment",
                            "cost": 1000
                        }
                    ]
                },
                "custom_payments": {
                    "event_wise_cost": []
                }
            }
        }, 
```

{% endcode %}


# TuumIO Data Node

## How TuumIO Data Node works?

The TuumIO Data Node (TDN) is responsible for storing and exchanging data files within the TuumIO Network. It can convert external data files into events, and events into external data files. When receiving data files, the TuumIO Data Node extracts and transforms the data, and then creates events. Event handlers can be created in TuumIO Protocol to manage the events generated by the TuumIO Data Node.

## Data definition file

The data definition file (DDF) defines the model and structure for organizing data in the TDN. This file is used in TDN to process incoming data files and generate events for distribution to TuumIO Nodes. The DDF and raw CSV files are uploaded to the environment repository for processing. For more information, see [Updating TDN](/protocol-guide/test-and-publish/publishing-the-protocol#update-cdn).

The following example shows data definition in `ddf/us-doctors-sample.json`.

{% code title="Example:" %}

```json
{
    "ddf_type": "us-doctors-sample",
    "meta_data": {
        "description": "Sample"
    },
    "messages": [
        {
            "message_category": "CSV",
            "message_type": "Doctors",
            "meta_data": {
                "description": "Sample",
                "indices": "us-doctors-sample"
            },
            "events": [
                {
                    "to_role": "rl-patient",
                    "event": "ev-cdn-broadcast"
                }
            ],
            "attributes": [
                {
                    "name": "Provider",
                    "description": "Provider",
                    "required": false,
                    "index_field": true,
                    "type": "integer",
                    "data_location": "Provider"
                },
                {
                    "name": "License",
                    "description": "License",
                    "required": false,
                    "index_field": true,
                    "type": "string",
                    "data_location": "License"
                },
                {
                    "name": "Specialization",
                    "description": "Specialization",
                    "required": false,
                    "index_field": true,
                    "type": "string",
                    "data_location": "Specialization"
                },
                {
                    "name": "Address",
                    "description": "Address",
                    "required": false,
                    "index_field": true,
                    "type": "string",
                    "data_location": "Address"
                }
            ]
        }
    ]
}
```

{% endcode %}


# TuumIO Ledgers

## TuumIO Ledger specifications

A TuumIO ledger is used to store and manage data related to events or transactions within the network. If necessary, include details about `tuumIO_ledgers` and `tuumIO_ledger_tags` in your protocol.

Use tags to categorize data within TuumIO ledgers, such as Appointments, Prescriptions, Results, and others.

| Field Name | Value  | Description                             |
| ---------- | ------ | --------------------------------------- |
| id         | string | The unique ID of the TuumIO ledger tag. |
| name       | string | The name of the TuumIO ledger tag.      |

{% code title="Example:" %}

```json
        "care_ledger_tags": [            
            {
                "id": "clt-Answer-QA",
                "name": "Answer QA"
            },
            {
                "id": "clt-Request-Appointment",
                "name": "Request Appointment"
            }
        ],
```

{% endcode %}

Declare the attributes and values for the TuumIO ledgers.

| Field Name           | Value  | Description                                                                       |
| -------------------- | ------ | --------------------------------------------------------------------------------- |
| id                   | string | The unique ID of the tuumIO ledger.                                               |
| name                 | string | The name of the tuumIO ledger.                                                    |
| description          | string | The description of the tuumIO ledger.                                             |
| event\_id            | string | The reference ID of the event to be recorded in the tuumIO ledger.                |
| private\_cards       | array  | The cards with consent to view.                                                   |
| public\_cards        | array  | The cards associated to the event record, which can be shared across the network. |
| tuumIO\_ledger\_tags | array  | The reference IDs of the tuumIO ledger tags.                                      |

{% code title="Example:" %}

```json
        "care_ledgers": [
            {
                "id": "cl-e-PSbUgucq4Z8zCSemaBiuSyc2uijm8",
                "name": "Answer QA",
                "description": "Answer QA",
                "event_id": "e-w-broad-sendqa-next",
                "private_cards": [],
                "public_cards": [
                    "cd-wv129h6n1lr1ognzepj2abp1iqvp"
                ],
                "care_ledger_tags": [
                    "clt-Answer-QA"
                ]
            },
            {
                "id": "cl-e-PSbUgucq4Z8zCSemaBiuSyc2jXg4",
                "name": "Request Appointment from Patient to Doctor",
                "description": "Request Appointment from Patient to Doctor",
                "event_id": "e-w-broad-shareAppt-next",
                "private_cards": [],
                "public_cards": [
                    "cd-mwlyle6o9ko65ojdorbrg259g761"
                ],
                "care_ledger_tags": [
                    "clt-Request-Appointment"
                ]
            }
        ]    
```

{% endcode %}


# Roles and Journeys

This section describes the definition structure of user roles and journeys in a network.

## Roles

A role is a fundamental element of TuumIO Protocol that represents a specific participant type, such as patients or doctors. Each role is defined with the corresponding cards and events.

<table><thead><tr><th width="185">Field Name</th><th width="148">Value Type</th><th>Description</th></tr></thead><tbody><tr><td>id</td><td>string</td><td>The unique ID of the role.</td></tr><tr><td>name</td><td>string</td><td>The name of the role.</td></tr><tr><td>description</td><td>string</td><td>The description of the role.</td></tr><tr><td>type</td><td>string</td><td>The role type is defined in the platform.</td></tr><tr><td>status</td><td>string</td><td>The status of the role is set to Active.</td></tr><tr><td>version</td><td>number</td><td>The role's version number is updated when the role metadata value changes.</td></tr><tr><td>td_collections</td><td>array</td><td>The transactional data records are linked to the role.</td></tr><tr><td>allow_events_with_role</td><td>array</td><td>The events allowed for the role.</td></tr><tr><td>home_card_ref_id</td><td>string</td><td>The reference ID to the home card for the role.</td></tr></tbody></table>

{% code title="Example:" %}

```json
        "roles": [
            {
                "id": "rl-patient",
                "name": "PATIENT",
                "description": "The patient user role.",
                "type": "Wallet",
                "status": "Active",
                "version": 1,
                "allow_events_with_role": [],
                "home_card_ref_id": "cd-h-patient"
            },
            {
                "id": "rl-doctor",
                "name": "DOCTOR",
                "description": "The Doctor user role.",
                "type": "Wallet",
                "status": "Active",
                "version": 1,
                "allow_events_with_role": [],
                "home_card_ref_id": "cd-h-doctor"
            }
            
        ],
```

{% endcode %}

## Journeys

A journey is a sequence of interconnected cards, defining a specific workflow for a role or network.

<table><thead><tr><th width="189">Field Name</th><th width="165">Value Type</th><th>Description</th></tr></thead><tbody><tr><td>id</td><td>string</td><td>The unique ID of the journey.</td></tr><tr><td>icon</td><td>string</td><td>The path to the icon image file.</td></tr><tr><td>name</td><td>string</td><td>The name of the journey.</td></tr><tr><td>description</td><td>string</td><td>The description of the journey.</td></tr><tr><td>status</td><td>string</td><td>The status of the journey is set to Active.</td></tr><tr><td>start_card_ref_id</td><td>string</td><td>The reference ID of the journey starting card.</td></tr><tr><td>roles</td><td>string</td><td>The roles involved in the journey.</td></tr><tr><td>journey_data</td><td>array</td><td>The data model for synchronizing across multiple roles or nodes, triggered by events. See <a href="#journey-data-model">Journey data model</a>.</td></tr><tr><td>journey_type</td><td>string</td><td>The journey type is defined in the platform.</td></tr></tbody></table>

### Journey definitions

The following example shows the "Get Started" and the "Join as Doctor" journeys.

{% code title="Example:" %}

```json
        "journeys": [
            {
                "id": "jn-start-journey",
                "icon": "",
                "name": "Get Started",
                "description": "Start journey for Patient",
                "status": "Active",
                "start_card_ref_id": "cd-start-rl-patient",
                "roles": ["rl-patient"],
                "journey_data": [],
                "journey_type": "STANDARD_JOURNEY"
            },
            {
                "id": "jn-rl-doctor",
                "icon": "",
                "name": "Join as Doctor",
                "description": "Join as Doctor",
                "status": "Active",
                "start_card_ref_id": "cd-invite-rl-doctor",
                "roles": ["rl-doctor"],
                "journey_data": [],
                "journey_type": "JOIN_NETWORK_JOURNEY"
            },
```

{% endcode %}

### Journey data model

Here is another example of a "Book Appointment" journey that defines the events, roles, and permissions for synchronizing data across multiple nodes.

<table><thead><tr><th>Field Name</th><th width="170">Value Type</th><th>Description</th></tr></thead><tbody><tr><td>name</td><td>string</td><td>The unique name of the journey data model.</td></tr><tr><td>start_event_ids</td><td>array</td><td>The IDs of start events that trigger data sharing and synchronization. <br><strong>Note:</strong> Only the user role with OWNER access can submit the start (init) event.</td></tr><tr><td>stop_event_ids</td><td>array</td><td>The IDs of stop events with shared data in the payload, completing the synchronization to all nodes.</td></tr><tr><td>affected_collections</td><td>array</td><td>The data collections where payload data is saved.</td></tr><tr><td>expire_in</td><td>string</td><td>The number of days (d), weeks (w), or years (y) from initialization until synchronization is stopped.</td></tr><tr><td>permissions</td><td>array</td><td>The list of roles and corresponding access permissions.</td></tr><tr><td>role</td><td>string</td><td>The reference ID of each role defined in the journey.</td></tr><tr><td>access</td><td>string</td><td>The access level permission set for each role.</td></tr></tbody></table>

{% code title="Example:" %}

```json
{
        "id": "book-appointment-journey",
        "name": "Book Appointment",
        "description": "Book Appointment",
        "status": "Active",
        "start_card_ref_id": "get-records-list-card",
        "roles": ["patient", "doctor", "nurse"],
        "journey_data": [
          {
            "name": "jdm-001-data-01",
            "start_event_ids": [
              "e-w-broad-patient-to-rl-xxx",
              "e-w-pt-confirm-appt"
            ],
            "stop_event_ids": [
              "e-w-pt-confirm-appt-fee"
            ],
            "affected_collections": [
              "td/td-BOOKING.json"
            ],
            "expire_in": "1d",
            "permissions": [
              {
                "role": "rl-PATIENT",
                "access": "OWNER"
              },
              {
                "role": "rl-DOCTOR",
                "access": "READ"
              },
              {
                "role": "rl-NURSE",
                "access": "DELEGATION"
              }
            ]
          }
        ],
        "journey_type": "STANDARD_JOURNEY"
      }
```

{% endcode %}


# Card Definitions

This section describes the structure of card definitions, including card data, card layout, card footer, and card UI actions.

{% hint style="info" %}
All card definitions must be included in the `input.json` file.
{% endhint %}

## Cards

A card contains multiple data types, user interface elements, and interactive functions triggered by events.

<table><thead><tr><th width="230">Field Name</th><th width="158">Value Type</th><th>Description</th></tr></thead><tbody><tr><td>id</td><td>string</td><td>The unique ID of the card.</td></tr><tr><td>name</td><td>string</td><td>The name of the card.</td></tr><tr><td>description</td><td>string</td><td>The description of the card.</td></tr><tr><td>status</td><td>string</td><td>The status of the card is set to Active.</td></tr><tr><td>card_definition_ref</td><td>string</td><td>The reference to the UI component of the card.</td></tr><tr><td>side</td><td>string</td><td>The side on which data is presented.</td></tr><tr><td>role</td><td>string</td><td>The role ID is referenced in the card.</td></tr><tr><td>transaction_data_ref</td><td>string</td><td>The reference to the transaction data used upon initialization.</td></tr><tr><td>journey</td><td>string</td><td>The journey to which the card belongs.</td></tr><tr><td>outgoing_events</td><td>array</td><td>The events or actions triggered by the card.</td></tr><tr><td>pre_rendering_events</td><td>array</td><td>The events or actions used to initialize the card.</td></tr></tbody></table>

{% code title="Example:" %}

```json
    "cards": [
      {
        "id": "cd-start-rl-patient",
        "name": "Patient start card",
        "description": "Start card for patient",
        "status": "Active",
        "card_definition_ref": "card/cd-start-rl-patient.json",
        "side": "PUBLIC",
        "role": "rl-patient",
        "transaction_data_ref": "td/td-default.json",
        "private_card": "",
        "base_card": "",
        "journey": "jn-start-journey",
        "outgoing_events": ["ev-patient-nav-to-cd-next"],
        "pre_rendering_events": [],
        "post_rendering_events": []
      }
    ],
```

{% endcode %}

## Card definition structure

{% hint style="info" %}
Each card definition is located in the `/definitions/card/` folder.
{% endhint %}

* **Card data** - The information or data displayed within the card, such as texts, images, and links.
* **Card layout** - The arrangement and organization of elements within the card, including body content style, and footer menus.
* **Card footer** - The additional options, navigation buttons, or menus at the bottom of the card for user interaction and navigation.
* **Card UI actions** - The actions triggered by user interactions within the card, such as navigation, form submissions, or data updates.&#x20;

### Card data

Card data can include text, images, links or different types of information relevant to a healthcare journey.

{% code title="Example:" %}

```json
{
    "id": "cd-start-rl-patient",
    "name": "Get started",
    "cardData": {
        "Tile11000vtext": "Welcome to my TuumIO network!",
        "Tile11000vsubText": "This is an example.",
        "Tile11000vsubText1": "This is another example.",
        "imgUrlpjbx": "https://123.abc.net/media/Intro.png",
        "EN01BottomButton1002vtext": "Get Started"
    },
```

{% endcode %}

### Card layout

The card body displays the card's content, which includes tiles, texts, images, and interactive functions. For information on supported tiles, see [Tiles](/protocol-guide/build-a-dapp/card-definitions/tiles). For details on supported functions, see [Functions](/protocol-guide/build-a-dapp/card-definitions/functions).

{% code title="Example:" %}

```json
    "cardLayout": {
        "body": [
            {
                "id": "00tc01",
                "tileComponent": [
                    {
                        "id": "Tile0",
                        "subView": [
                            {
                                "title": {
                                    "text": "Tile11000vtext",
                                    "style": "bold"
                                }
                            }
                        ],
                        "align": "START",
                        "type": "CONTAINER",
                        "uiAction": "",
                        "order": 1
                    },
                    {
                        "id": "Tile11",
                        "subView": [
                            {
                                "title": {
                                    "text": "Tile11000vsubText"
                                },
                                "subTitle": {
                                    "text": "Tile11000vsubText1"
                                }
                            }
                        ],
                        "align": "START",
                        "type": "CONTAINER",
                        "uiAction": "",
                        "order": 1
                    },
                    {
                        "id": "Tile16",
                        "subView": [
                            {
                                "img": {
                                    "text": "imgUrlpjbx",
                                    "isUrl": true,
                                    "height": "250",
                                    "width": "250"
                                }
                            }
                        ],
                        "align": "START",
                        "textColor": "#212121",
                        "borderColor": "#1a1a1a",
                        "type": "CONTAINER",
                        "uiAction": "",
                        "order": 1
                    }
                ],
                "tileType": "WRAP",
                "uiAction": "",
                "order": 1
            }
        ],
```

{% endcode %}

### Card footer

The card footer includes buttons or actions used to interact with the card itself or navigate to other related cards. These buttons or actions can perform specific tasks like submitting information, saving changes, or going back to previous screens.

{% code title="Example:" %}

```json
        "footer": {
            "menu": [
                {
                    "id": "EN01BottomButtonBack",
                    "subView": [
                        {
                            "title": {
                                "text": ""
                            }
                        }
                    ],
                    "align": "START",
                    "type": "BACK_BUTTON",
                    "uiAction": "${action1}",
                    "order": 1
                },
                {
                    "id": "EN01BottomButton1",
                    "subView": [
                        {
                            "title": {
                                "text": "EN01BottomButton1002vtext"
                            }
                        }
                    ],
                    "align": "END",
                    "type": "BUTTON",
                    "uiAction": "${action2}",
                    "order": 2
                }
            ],
            "orientation": "HORIZONTAL"
        }
    },
```

{% endcode %}

### Card UI actions

The card UI actions define user interactions within the card's content. These actions trigger functionalities like navigation, data updates, input validation, or external function calls.

{% code title="Example:" %}

```json
    "cardUIAction": {
        "action1": {
            "action": ""
        }, "action2": {
            "action": "ev-patient-nav-to-cd-next"
        }
    }
}
```

{% endcode %}


# Tiles

This section describes the supported configurations and examples of tiles used in card definitions.

Use tiles to display card data in a specific layout or to provide functionality to texts, buttons, and images.

### Tile0: Text Label

This tile represents a text label in a single row.

<table><thead><tr><th width="324">Configurations</th><th>Preview</th></tr></thead><tbody><tr><td><ul><li>style: Regular or Bold</li><li>align: START (left), CENTER, END (right) or JUSTIFY</li><li>border color: hex value</li><li>text color: hex value</li></ul></td><td><img src="/files/w0WhIBRC1sPZ0sgL3yUi" alt=""><br></td></tr></tbody></table>

{% code title="Example:" %}

```json
{
            "id": "Tile0",
            "subView": [
              {
                "title": {
                  "text": "00t1v0",
                  "style": "bold"
                }
              }
            ],
            "align":"START",
            "type": "CONTAINER",
            "uiAction": "",
            "order": 1
          }
```

{% endcode %}

### Tile0a: Two Text Labels

This tile represents two texts labels in a single row.

| Configurations                                                                                                                                             | Preview                          |
| ---------------------------------------------------------------------------------------------------------------------------------------------------------- | -------------------------------- |
| <ul><li>style: Regular or Bold</li><li>align: START (left), END (right) or JUSTIFY</li><li>border color: hex value</li><li>text color: hex value</li></ul> | ![](/files/teGOXPX2Ij63Q34bZ1eF) |

{% code title="Example:" %}

```json
 {
            "id": "Tile0a",
            "subView": [
              {
                "title": {
                  "text": "00t1v36",
                  "style": "bold"
                },
                "subTitle": {
                  "text": "00t1v37",
                  "style": "bold"
                }
              }
            ],
            "align":"START",
            "type": "CONTAINER",
            "uiAction": "",
            "order": 1
          }
```

{% endcode %}

### Tile1: Text Input

This tile represents a text input for a specific key.

<table><thead><tr><th width="370">Configurations</th><th>Preview</th></tr></thead><tbody><tr><td><ul><li>align: START (left), END (right) or JUSTIFY</li><li>keyboard: text or number</li><li>min and max: character length</li><li>hint: placeholder for text input</li><li>key: <code>{*sugarLevel}</code>- The text input is set to key <code>sugarlevel</code> that will be used and sent through an event.</li><li>border color: hex value</li><li>text color: hex value</li></ul></td><td><img src="/files/e6ps67zqdqYM5k2kW19x" alt=""></td></tr></tbody></table>

{% code title="Example:" %}

```json
{
            "id": "Tile1",
            "subView": [
              {
                "title": {
                  "text": "00t1v25"
                },
                "subTitle": {
                  "text": "{*sugarLevel}",
                  "hint": "00t1v26",
                  "keyboard": "text",
                  "min":"1",
                  "max":"30"
                }
              }
            ],
            "align":"START",
            "type": "CONTAINER",
            "uiAction": "",
            "order": 1
          }
```

{% endcode %}

### Tile1a: Two Rows with Text Input

This tile represents two rows: the first containing a text label and the second containing a text input for a specific key.

| Configurations                                                                                                                                                                                                                                                                                                                                                                                                 | Preview                          |
| -------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------- | -------------------------------- |
| <ul><li>Title text is displayed on the first row</li><li>Subtitle text is displayed on the second row as an input field</li><li>text color: hex value</li><li>border color: hex value</li><li>align: START, CENTER, END and JUSTIFY</li><li>hint: placeholder for text input</li><li>keyboard: text or number</li><li>min and max length</li><li>validation: optional or required, and error message</li></ul> | ![](/files/x9m5qwR9eMiM0pasF0vs) |

{% code title="Example:" %}

```json
{
                        "id": "Tile1a",
                        "subView": [
                            {
                                "title": {
                                    "text": "1tile1iitextiiixo",
                                    "titleTextColor": "#000080",
                                    "titleAlign": "JUSTIFY"
                                },
                                "subTitle": {
                                    "text": "{$ReferralCode}",
                                    "hint": "1tile1iihintii6km",
                                    "subTitleTextColor": "#000080",
                                    "subTitleAlign": "START",
                                    "keyboard": "text",
                                    "min": "1",
                                    "max": "1000",
                                    "validation": [
                                        {
                                            "name": "OPTIONAL",
                                            "error": "1tile1iierrorii6se"
                                        }
                                    ]
                                }
                            }
                        ],
                        "borderColor": "#87ceeb",
                        "type": "CONTAINER",
                        "uiAction": "",
                        "order": 4
                    }
```

{% endcode %}

### Tile2: Text Input with Tooltip

This tile represents a text input for a specific key with tooltip.

| Configurations                                                                                                                                                                                                                                                                                                                                                                                                                                              | Preview                          |
| ----------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------- | -------------------------------- |
| <ul><li>align: START (fixed left)</li><li>keyboard: text or number</li><li>min and max: character length</li><li>hint: placeholder for text input</li><li>key: <code>{\*age}</code> - The text input is set to <code>age</code> that will be used and sent through an event.</li><li>tip: text shows when a user clicks the question mark icon</li><li>border color: hex value</li><li>text color: hex value</li><li>icon image: height and width</li></ul> | ![](/files/cKh0Z3VrgvLsdq2O5HW6) |

{% code title="Example:" %}

```json
{
            "id": "Tile2",
            "subView": [
              {
                "title": {
                  "text": "00t1v23"
                },
                "subTitle": {
                  "text": "{*age}",
                  "hint": "00t1v24",
                  "keyboard": "text",
                  "min":"1",
                  "max":"30",
                  "tip": "00t1v22"
                }
              }
            ],
            "align":"START",
            "type": "CONTAINER",
            "uiAction": "",
            "order": 1
          }
```

{% endcode %}

### Tile3: Date Selector

This tile represents a date selector for a specific key.

| Configurations                                                                                                                                                                                                                                                                                                                                                                                      | Preview                          |
| --------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------- | -------------------------------- |
| <ul><li>title label (left)</li><li>min and max: date values</li><li>align: START (fixed left)</li><li>hint: placeholder for date input</li><li>key: <code>{\*dateSelected}</code> - The date input is set to key <code>dateSelected</code>that will be used and sent through an event.</li><li>border color: hex value</li><li>text color: hex value</li><li>icon image: height and width</li></ul> | ![](/files/M8RX0qlovRG0Wlf4EyUn) |

{% code title="Example:" %}

```json
{
            "id": "Tile3",
            "subView": [
              {
                "title": {
                  "text": "00t1v19"
                },
                "subTitle": {
                  "text": "{*dateSelected}",
                  "hint": "00t1v20",
                  "min" : "12/01/2022",
                  "max" : "14/01/2022"
                }
              }
            ],
            "align":"START",
            "type": "CONTAINER",
            "uiAction": "",
            "order": 1
          }
```

{% endcode %}

### Tile5: Stepper

This tile represents a stepper to adjust the value for a specific key.

| Configurations                                                                                                                                                                                                                                                                                                                                                                | Preview                          |
| ----------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------- | -------------------------------- |
| <ul><li>title label (left)</li><li>start: the start number of the stepper</li><li>end: the end number of the stepper</li><li>align: START (fixed left), JUSTIFY</li><li>key: <code>{status}</code> - The selected value is set to key <code>status</code>that will be used and sent through an event.</li><li>border color: hex value</li><li>text color: hex value</li></ul> | ![](/files/W8Z3Ci5Z5VEVUbAMUFel) |

{% code title="Example:" %}

```json
{
            "id":"Tile5",
            "subView":[
              {
                "title":{
                  "text":"00t1v18"
                },
                "subTitle":{
                  "text":"{status}",
                  "start": 0,
                  "end": 100,
                  "count":10
                }
              }
            ],
            "align":"START",
            "type":"CONTAINER",
            "uiAction":"",
            "order":1
          }
```

{% endcode %}

### Tile6: Horizontal Radio Buttons

This tile represents option selectors as radio buttons in horizontal format.

| Configurations                                                                                                                                                                                                                                                                                                                            | Preview                          |
| ----------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------- | -------------------------------- |
| <ul><li>title label (left)</li><li>align: START, JUSTIFY</li><li>options: key and list</li><li>key: <code>{answer}</code> - The selected option is set to key <code>answer</code> that will be used and sent through an event.</li><li>list: dynamic options list</li><li>border color: hex value</li><li>text color: hex value</li></ul> | ![](/files/DKgXVYmN5ZEIwURmR29e) |

{% code title="Example:" %}

```json
{
            "id": "Tile6",
            "subView": [
              {
                "title": {
                  "text": "00t1v5"
                },
                "options": {
                  "key":{
                    "name":"{answer}"
                  },
                  "list":[
                    
                    {
                      "label": "00t1v11"
                    },
                    {
                      "label": "00t1v12"
                    },
                    {
                      "label": "00t1v13"
                    }
                  ]
                  
                }
                
              }
            ],
            "align":"START",
            "type": "CONTAINER",
            "uiAction": "",
            "order": 1
          }
```

{% endcode %}

### Tile6a: Vertical Radio Buttons

This tile represents option selectors as radio buttons in vertical format.

| Configurations                                                                                                                                                                                                                                                                                                                            | Preview                                                             |
| ----------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------- | ------------------------------------------------------------------- |
| <ul><li>title label (left)</li><li>align: START, JUSTIFY</li><li>options: key and list</li><li>key: <code>{answer}</code> - The selected option is set to key <code>answer</code> that will be used and sent through an event.</li><li>list: dynamic options list</li><li>border color: hex value</li><li>text color: hex value</li></ul> | <img src="/files/nXxu5RUE6fiZLJnl9VAQ" alt="" data-size="original"> |

{% code title="Example:" %}

```json
{
            "id": "Tile6",
            "subView": [
              {
                "title": {
                  "text": "00t1v5"
                },
                "options": {
                  "key":{
                    "name":"{answer5}"
                  },
                  "list":[
                    
                    {
                      "label": "00t1v11"
                    },
                    {
                      "label": "00t1v12"
                    },
                    {
                      "label": "00t1v13"
                    }
                  ]
                  
                }
                
              }
            ],
            "align":"START",
            "type": "CONTAINER",
            "uiAction": "",
            "order": 1
          }
```

{% endcode %}

### Tile7: Horizontal Checkboxes

This tile represents a multi-option selector as checkboxes in horizontal format.

| Configurations                                                                                                                                                                                                                                                                                              | Preview                          |
| ----------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------- | -------------------------------- |
| <ul><li>title label (left)</li><li>options: key and list</li><li>key: <code>{answer}</code> - The selected option is set to key <code>answer</code> that will be used and sent through an event.</li><li>list: dynamic options list</li><li>border color: hex value</li><li>text color: hex value</li></ul> | ![](/files/460guHzADzwfkVZVHJjJ) |

{% code title="Example:" %}

```json
{
            "id": "Tile7",
            "subView": [
              {
                "title": {
                  "text": "00t1v5"
                },
                "options": {
                  
                  "key":{
                    "name":"{answer}"
                  },
                  "list":[
                    
                    {
                      "label": "00t1v11"
                    },
                    {
                      "label": "00t1v12"
                    },
                    {
                      "label": "00t1v13"
                    }
                  ]
                  
                }
                
              }
            ],
            "align":"START",
            "type": "CONTAINER",
            "uiAction": "",
            "order": 1
          }
```

{% endcode %}

### Tile7a: Vertical Checkboxes

This tile represents a multi-option selector as checkboxes in vertical format.

| Configurations                                                                                                                                                                                                                                                           | Preview                          |
| ------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------ | -------------------------------- |
| <ul><li>title label (left)</li><li>options: key and list</li><li>key: <code>{answer}</code> - The selected option is set to key <code>answer</code> that will be used and sent through an event.</li><li>border color: hex value</li><li>text color: hex value</li></ul> | ![](/files/pR8g2uzKEV7MaVlJXhb0) |

{% code title="Example:" %}

```json
{
            "id": "Tile7a",
            "subView": [
              {
                "title": {
                  "text": "00t1v5"
                },
                "options": {
                  
                  "key":{
                    "name":"{answer}"
                  },
                  "list":[
                    
                    {
                      "label": "00t1v11"
                    },
                    {
                      "label": "00t1v12"
                    },
                    {
                      "label": "00t1v13"
                    }
                  ]
                  
                }
                
              }
            ],
            "align":"START",
            "type": "CONTAINER",
            "uiAction": "",
            "order": 1
          }
```

{% endcode %}

### Tile7b: Vertical Checkboxes with Subtitle

This tile is the same as [Tile7a](#tile7a) with an extra option for a subtitle label, such as displaying the count in numbers.&#x20;

| Configurations                                                                                                                                                                              | Preview                          |
| ------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------- | -------------------------------- |
| <p>For subtitle color handling:</p><ul><li>border color: hex value</li><li>text color: hex value</li></ul><p>In the example, the subtitle is shown as a number next to the title label.</p> | ![](/files/Wb4DRiJJb0nurERFrjRJ) |

{% code title="Example:" %}

```json
{
            "id": "Tile7b",
            "subView": [
              {
                "title": {
                  "text": "00t1v5"
                },
                "options": {
                  
                  "key":{
                    "name":"{answer}"
                  },
                  "list":[
                    
                    {
                      "label": "00t1v11",
                      "subTitle":{
                        "text": "{00t1v11}",
                        "colorCode": "00FF00"
                    },
                    {
                      "label": "00t1v12"
                      "subTitle":{
                        "text": "{00t1v12}",
                        "colorCode": "00FF00"                
                    },
                    {
                      "label": "00t1v13"
                      "subTitle":{
                        "text": "{00t1v13}",
                        "colorCode": "00FF00"
                    }
                  ]
                  
                }
                
              }
            ],
            "align":"START",
            "type": "CONTAINER",
            "uiAction": "",
            "order": 1
          }
```

{% endcode %}

### Tile8: Scrollable Table

This tile represents a scrollable table grid.

| Configurations                                                                                                                                                                                                                                                                                                         | Preview                                                             |
| ---------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------- | ------------------------------------------------------------------- |
| <ul><li>title label (left)</li><li>options: key and list</li><li>key: <code>{answer}</code> - The selected option is set to key <code>answer</code> that will be used and sent through an event.</li><li>list: label and data</li><li>label: the header title</li><li>data: the list of data for each header</li></ul> | <img src="/files/diBQqTz1H3cx4bqWo9vU" alt="" data-size="original"> |

{% code title="Example:" %}

```json
{
              "id": "Tile8",
              "subView": [
                {
                  "title": {
                    "text": "00t1v10"
                  },
                  "options": {
                    
                    "key":{
                      "name":"{answer}"
                    },
                    "list":[
                      {
                        "label": "00t1v11",
                        "data" : "00t1v14"
                      },
                      {
                        "label": "00t1v12",
                        "data" : "00t1v15"
                      },
                      {
                        "label": "00t1v13",
                        "data" : "00t1v16"
                      }
                    ]
                  }
                }
              ],
              "align":"START",
              "type": "CONTAINER",
              "uiAction": "",
              "order": 1
            }
```

{% endcode %}

### Tile9: Scrollable Table without Title Label

This tile is the same as [Tile8](#tile8), with no title.

| Configurations                          | Preview                                                             |
| --------------------------------------- | ------------------------------------------------------------------- |
| See configurations for [Tile8](#tile8). | <img src="/files/IF65Gem1gStyeqAYFgWO" alt="" data-size="original"> |

{% code title="Example:" %}

```json
{
              "id": "Tile9",
              "subView": [
                {
                  "options": {
                    
                    "key":{
                      "name":"{answer}"
                    },
                    "list":[
                      {
                        "label": "00t1v11",
                        "data" : "00t1v14"
                      },
                      {
                        "label": "00t1v12",
                        "data" : "00t1v15"
                      },
                      {
                        "label": "00t1v13",
                        "data" : "00t1v16"
                      }
                    ]
                  }
                }
              ],
              "align":"START",
              "type": "CONTAINER",
              "uiAction": "",
              "order": 1
            }
```

{% endcode %}

### Tile10: Option Selector

This tile represents an option selector.

| Configurations                                                                                                                                                                                                                                                                                              | Preview                                                             |
| ----------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------- | ------------------------------------------------------------------- |
| <ul><li>title label (left)</li><li>options: key and list</li><li>key: <code>{answer</code>} - The selected option is set to key <code>answer</code> that will be used and sent through an event.</li><li>list: dynamic options list</li><li>border color: hex value</li><li>text color: hex value</li></ul> | <img src="/files/opIFwpHhYm988JY26JIr" alt="" data-size="original"> |

{% code title="Example:" %}

```json
{
            "id": "Tile10",
            "subView": [
              {
                "title": {
                  "text": "00t1v4"
                },
                "options": {
                  
                  "key":{
                    "name":"{answer}"
                  },
                  "list":[
                    
                    {
                      "label": "00t1v16"
                    },
                    {
                      "label": "00t1v17"
                    }
                  ]
                  
                }
                
              }
            ],
            "align":"START",
            "type": "CONTAINER",
            "uiAction": "",
            "order": 1
          }
```

{% endcode %}

### Tile10a: Toggle Switch

This tile represents a toggle switching button, such as "on" or "off".

| Configurations                                                                                                                                                                                                                                                                                                              | Preview                                                             |
| --------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------- | ------------------------------------------------------------------- |
| <ul><li>title label (left)</li><li>options: key and list</li><li>key: <code>{answer}</code> - The selected option is set to key <code>answer</code> that will be used and sent through an event.</li><li>list: dynamic options to toggle on and off</li><li>border color: hex value</li><li>text color: hex value</li></ul> | <img src="/files/fVC29zzMmzjKufSIqX6Y" alt="" data-size="original"> |

{% code title="Example:" %}

```json
{
            "id": "Tile10a",
            "subView": [
              {
                "title": {
                  "text": "00t1v4"
                },
                "options": {
                  
                  "key":{
                    "name":"{answer}"
                  },
                  "list":[
                    
                    {
                      "label": "00t1v16"
                    },
                    {
                      "label": "00t1v17"
                    }
                  ]
                  
                }
                
              }
            ],
            "align":"START",
            "type": "CONTAINER",
            "uiAction": "",
            "order": 1
          }
```

{% endcode %}

### Tile11: Title and Text

This tile represents two rows with a title and a subtitle text.

| Configurations                                                                                                                                              | Preview                                                             |
| ----------------------------------------------------------------------------------------------------------------------------------------------------------- | ------------------------------------------------------------------- |
| <ul><li>title label (left) on first row</li><li>subtitle label (left) on second row</li><li>border color: hex value</li><li>text color: hex value</li></ul> | <img src="/files/rCgKHUODX5gUWEGQVcE3" alt="" data-size="original"> |

{% code title="Example:" %}

```json
{
            "id": "Tile11",
            "subView": [
              {
                "title": {
                  "text": "00t1v27"
                },"subTitle":{
                  "text":"00t1v28"
                }
              }
            ],
            "align":"START",
            "type": "CONTAINER",
            "uiAction": "",
            "order": 1
            
          }
```

{% endcode %}

### Tile11a: Title and Scrollable Text

This tile is the same as [Tile11](#tile11) with a scrollable subtitle text.

| Configurations                                                                                                                                                                                                             | Preview                                                             |
| -------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------- | ------------------------------------------------------------------- |
| <p>For subtitle view:</p><ul><li>heightMultiplier: "1" - This value is calculated according the screen ratio.</li><li>text includes JUSTIFY option</li><li>border color: hex value</li><li>text color: hex value</li></ul> | <img src="/files/oGfy21w2UNnGTrXdGO1t" alt="" data-size="original"> |

{% code title="Example:" %}

```json
{
            "id": "Tile11",
            "subView": [
              {
                "title": {
                  "text": "00t1v27"
                },"subTitle":{
                  "text":"00t1v28",
                  "heightMultiplier":"1"
                }
              }
            ],
            "align":"START",
            "type": "CONTAINER",
            "uiAction": "",
            "order": 1
            
          }
```

{% endcode %}

### Tile12: Dropdown Option Selector

This tile represents a dropdown selector for a list of options.

| Configurations                                                                                                                                                                                                                                                                                                                                                                                                                                                                                    | Preview                                                             |
| ------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------- | ------------------------------------------------------------------- |
| <ul><li>title label (left)</li><li>subtitle: key, hint, and data</li><li>key: {\*patient} - The selected option is set to key patient that will be used and sent through an event.</li><li>hint: placeholder for the selected option</li><li>data: an array of options loaded from cardData, for example: \["option 1", "option 2", "option 3"]</li><li>text includes JUSTIFY option</li><li>border color: hex value</li><li>text color: hex value</li><li>icon image: height and width</li></ul> | <img src="/files/7m6Ajr70f8NPMqAgWhke" alt="" data-size="original"> |

{% code title="Example:" %}

```json
{
            "id": "Tile12",
            "subView": [
              {
                "title": {
                  "text": "00t1v29"
                },
                
                "subTitle": {
                  "text": "{*patient}",
                  "hint": "00t1v30",
                  "keyboard": "text",
                  "data" : "00t1v14"
                }
              }
            ],
            "align":"START",
            "type": "CONTAINER",
            "uiAction": "",
            "order": 1
          }
```

{% endcode %}

### Tile14: Clickable Tile

This tile represents a clickable tile that triggers an action.

| Configurations                                                                                                                                                                                                                                         | Preview                                                             |
| ------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------ | ------------------------------------------------------------------- |
| <ul><li>title label</li><li>uiAction: "${action1}" - This value is correlated with an event handler.</li><li>text includes JUSTIFY option</li><li>border color: hex value</li><li>text color: hex value</li><li>icon image: height and width</li></ul> | <img src="/files/3I6ZmikKgkvmtIm9ZK6D" alt="" data-size="original"> |

{% code title="Example:" %}

```json
 {
            "id":"Tile14",
            "subView":[
              {
                "title":{
                  "text":"00t1v21"
                }
                
              }
            ],
            "align":"START",
            "type":"CONTAINER",
            "uiAction":"${action1}",
            "order":1
          }
```

{% endcode %}

### Tile14a: Clickable Tile with Subtitle

This tile is the same as [Tile14](#tile14) with a subtitle.

| Configurations                                                                                                                                                        | Preview                                                             |
| --------------------------------------------------------------------------------------------------------------------------------------------------------------------- | ------------------------------------------------------------------- |
| <ul><li>style: bold</li><li>text includes JUSTIFY option</li><li>border color: hex value</li><li>text color: hex value</li><li>icon image: height and width</li></ul> | <img src="/files/NAq6piOtcy3LxfEoHNXF" alt="" data-size="original"> |

{% code title="Example:" %}

```json
 {
            "id":"Tile14a",
            "subView":[
              {
                "title":{
                  "text":"00t1v21",
                  "style":"bold"
                },
                "subTitle":{
                  "text":"00t1v21",
                  "style":"bold"
                },
                "img":{
                  "text":"00t1v35"
              }
            ],
            "align":"START",
            "type":"CONTAINER",
            "uiAction":"${action1}",
            "order":1
          }
```

{% endcode %}

### Tile16: Image Tile

This tile represents an image that can be loaded locally or from a URL.

| Configurations                                                                                                                                                                                         | Preview                                                             |
| ------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------ | ------------------------------------------------------------------- |
| <ul><li>image: text, isURL, height and width</li><li>text: the source of the image (link or image name) loaded from the cardData</li><li>isURL: true or false</li><li>size: height and width</li></ul> | <img src="/files/jPylGaBMWNQACkaMJgCz" alt="" data-size="original"> |

{% code title="Example:" %}

```json
{
            "id":"Tile16",
            "subView":[
              {
                "img":{
                  "text":"00t1v35",
                  "isUrl":true
                }
              }
            ],
            "align":"START",
            "type":"CONTAINER",
            "uiAction":"",
            "order":1
          }
```

{% endcode %}

### Tile17: Clickable Image Grid

This tile represents clickable images to select an option or trigger an action.

| Configurations                                                                                                                                                                                                                                             | Preview                                                             |
| ---------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------- | ------------------------------------------------------------------- |
| <ul><li>options: key and list</li><li>key: <code>{answer5}</code> - The selected option from the list is set to key <code>answer5</code> that will be used and sent through an event.</li><li>image: text and isURL</li><li>isURL: true or false</li></ul> | <img src="/files/tNV2gxdQk5obEaWx9Smx" alt="" data-size="original"> |

{% code title="Example:" %}

```json
{
            "id":"Tile17",
            "subView":[
              {
                "options":{
                  "key":{
                    "name":"{answer5}"
                    },
                  "list":[
                    {
                    "label":"00t1v44",
                    "img":{
                      "text":"00t1v43",
                      "isURL":false
                    }
                  },
                    {
                    "label":"00t1v45",
                    "img":{
                      "text":"00t1v48",
                      "isURL":false
                    }
                  },
                    {
                    "label":"00t1v46",
                    "img":{
                      "text":"00t1v49",
                      "isURL":false
                    }
                  },
                    {
                    "label":"00t1v47",
                    "img":{
                      "text":"00t1v50",
                      "isURL":false
                    }
                  }
                ]
              }
                    
                "img":{
                  "text":"00t1v35",
                  "isUrl":true
                }
              }
            ],
            "order":1
            "type":"CONTAINER",
            "uiAction":""
          }
```

{% endcode %}

### Tile17a: Clickable Image Row

This tile represents clickable images in a single row. Clicking the image navigates the user to a target location.

| Configurations                                                                                                                                                                                                                       | Preview                                                             |
| ------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------ | ------------------------------------------------------------------- |
| <ul><li>subtitle text: reference to the title that displays below the image</li><li>align: START, CENTER, or END</li><li>text color: hex value</li><li>border color: hex value</li><li>uiAction: for example, "action17a2"</li></ul> | <img src="/files/l0nBsn5bZnP0wzRJOVW0" alt="" data-size="original"> |

{% code title="Tile definition example:" %}

```json
{
                        "id": "Tile17a",
                        "subView": [
                            {
                                "options": {
                                    "list": [
                                        {
                                            "subTitle": {
                                                "text": "10tile17aiitextiizxq",
                                                "subtitleAlign": "CENTER",
                                                "colorCode": "#000080",
                                                "style": "REGULAR"
                                            },
                                            "img": {
                                                "text": "imageUrlo9w7y"
                                            },
                                            "uiAction": ""
                                        },
                                        {
                                            "subTitle": {
                                                "text": "9tile17aiitextii0ak",
                                                "subtitleAlign": "CENTER",
                                                "colorCode": "#000080",
                                                "style": "REGULAR"
                                            },
                                            "img": {
                                                "text": "imageUrlynopr"
                                            },
                                            "uiAction": "action17a2"
                                        },
                                        {
                                            "subTitle": {
                                                "text": "8tile17aiitextiimyk",
                                                "subtitleAlign": "END",
                                                "colorCode": "#000080",
                                                "style": "REGULAR"
                                            },
                                            "img": {
                                                "text": "imageUrlk6cem"
                                            },
                                            "uiAction": "action17a1"
                                        }
                                        
                                    ]
                                }
                            }
                        ],
                        "borderColor": "#ffffff",
                        "type": "CONTAINER",
                        "uiAction": "",
                        "order": 5
                    }
```

{% endcode %}

{% code title="cardUIAction example:" %}

```json
"action17a2": {
            "action": [
                {
                    "name": "Function.Navigate",
                    "cardId":"cd-vwgot7h4rlhwnzjf24aqa37ezz4"
                    
                }
            ]
        }
```

{% endcode %}

### SmartTile1: Input Validation Tile

This tile is an input field that is used to implement checks, such as "field format" and "field value".

| Configurations                                                                                                                                                                                                                                                                                                                                                                                  | Preview                          |
| ----------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------- | -------------------------------- |
| <ul><li>title text</li><li>subtitle text</li><li>text color: hex value</li><li>font size: number value</li><li>border color: hex value</li><li>align: START, CENTER, END or JUSTIFY</li><li>hint: placeholder for text input</li><li>min and max length</li><li>fieldFormat: Any supported field format, such as "email".</li><li>validation: optional or required, and error message</li></ul> | ![](/files/2yQLmGl8tiMZxSBLywDK) |

{% code title="Example:" %}

```json
                    {
                        "id": "SmartTile1",
                        "subView": [
                            {
                                "title": {
                                    "text": "2tile1iitextii5gb",
                                    "titleTextColor": "#000080",
                                    "titleAlign": "START",
                                    "fontSize": 16
                                },
                                "subTitle": {
                                    "text": "{$email}",
                                    "hint": "2tile1iihintiid8l",
                                    "subTitleTextColor": "#000080",
                                    "subTitleAlign": "START",
                                    "tip": "2tile2iitipii3m6",
                                    "fieldFormat": "email",
                                    "validation": [
                                        {
                                            "name": "REQUIRED_FIELD",
                                            "error": "2tile1iierrorii0uj"
                                        }
                                    ]
                                }
                            }
                        ],
                        "borderColor": "#C5C3C8",
                        "type": "CONTAINER",
                        "uiAction": "",
                        "order": 2
                    }
```

{% endcode %}


# Functions

This section provides information about the functions that are supported within card definitions.

Use the functions to link cards to event handlers, execute operations to fetch data, validate data input, navigate between cards, and manage other interactions.

## Fetching data

### Function.SOLVE.getTokenBalance&#x20;

Fetches the available SOLVE token balance after joining a network.

#### Parameter

| Field      | Value  | Description                                                                |
| ---------- | ------ | -------------------------------------------------------------------------- |
| name       | string | The name of the function: `Function.SOLVE.getTokenBalance`                 |
| sourceKeys | array  | Not required                                                               |
| totalKey   | string | Not required                                                               |
| resultKey  | string | The key name in which you want to store the final outcome of the function. |

{% code title="Example:" %}

```json
    "prerenderingFunctions": [
        {
            "name": "Function.SOLVE.getTokenBalance",
            "sourceKeys": [],
            "totalKey": "",
            "resultKey": "solveBalance"
        }
    ]
```

{% endcode %}

### Function.SOLVE.getExchangeRate

Fetches the exchange value of SOLVE from USD.

#### Parameter

| Field      | Value  | Description                                                                       |
| ---------- | ------ | --------------------------------------------------------------------------------- |
| name       | string | The name of the function: `Function.SOLVE.getExchangeRate`                        |
| sourceKeys | array  | The key name, which has a value in USD and is passed as an input to the function. |
| resultKey  | string | The key name in which you want to store the final outcome of the function.        |

{% code title="Example:" %}

```json
"prerenderingFunctions": [
    {
        "name": "Function.SOLVE.getExchangeRate",
        "sourceKeys": [ "totalUsdCost" ],
        "resultKey": "totalSolveCost"
    }
]
```

{% endcode %}

### Function.Profile.key

Shows user profile data inside the network.

#### Parameter

| Field | Value  | Description                                                                                                                                                                                                                                                                                                 |
| ----- | ------ | ----------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------- |
| text  | string | <p>The name of the function: <code>Function.Profile.key</code></p><p>The following keys can be used as input:</p><ul><li>name (nickname)</li><li>cw\_id</li><li>phone</li><li>country (get user's country code, such as "US")</li><li>first\_name</li><li>last\_name</li><li>ssn</li><li>language</li></ul> |

{% code title="Example 1:" %}

```json
{
    "id": "Tile0",
    "subView": [
        {
        "title": {
        "text": "Function.Profile.first_name"
        }
    }
]
}
```

{% endcode %}

{% code title="Example 2:" %}

```json
{
    "id": "Tile14a",
    "subView": [
     {
       "title": {
       "text": "2tile14aiitextiihsb",
       "titleTextColor": "#000080",
       "style": "BOLD"
      },
       "subTitle": {
       "text": "Function.Profile.cw_id",
       "subTitleTextColor": "#000080",
       "style": "REGULAR"
      },
   }
]
}
```

{% endcode %}

### Function.PROTOCOL.preLoadData

Executes a GET request to the user node.

#### Parameter

| Field | Value  | Description                                               |
| ----- | ------ | --------------------------------------------------------- |
| name  | string | The name of the function: `Function.PROTOCOL.preLoadData` |
| url   | string | The URL path where the data is stored.                    |

{% code title="Example:" %}

```json
    "prerenderingFunctions": [
            {
                "name": "Function.PROTOCOL.preLoadData",
                "url": "/transactions/H_QUESTIONS"
            }
```

{% endcode %}

### Function.getGPSLocation

Fetches user's current location latitude and longitude.

#### Parameter

| Field      | Value  | Description                                                                                |
| ---------- | ------ | ------------------------------------------------------------------------------------------ |
| name       | string | The name of the function: `Function.getGPSLocation`                                        |
| sourceKeys | array  | The key names that correspond to the user's location coordinates (latitude and longitude). |

{% code title="Example:" %}

```json
    "prerenderingFunctions": [
        {
            "name": "Function.getGPSLocation",
            "sourceKeys": [ "userLocationLatitude", "userLocationLongitude" ]
        }
```

{% endcode %}

### Function.Preference.language

Shows user preference data such as language preference.

#### Parameter

<table><thead><tr><th width="218">Field</th><th>Value</th><th>Description</th></tr></thead><tbody><tr><td>text</td><td>string</td><td>The name of the function: <code>Function.Preference.language</code><br>This function is used only inside Tiles.</td></tr></tbody></table>

{% code title="Example:" %}

```json
{
    "id": "Tile0",
    "subView": [
        {
            "title": {
                "text": "Function.Preference.language"
            }
        }
    ],
}
```

{% endcode %}

## Performing calculations

### Function.data.totalCount

Shows the total count of fetched data.

#### Parameter

| Field | Value  | Description                                          |
| ----- | ------ | ---------------------------------------------------- |
| text  | string | The name of the function: `Function.data.totalCount` |

{% code title="Example:" %}

```json
{
    "id": "Tile0a",
    "subView": [
        {
            "title": {
                "text": "0tile0aiitextiizsx",
                "style": "BOLD",
                "titleTextColor": "#000080",
                "titleAlign": "START"
            },
            "subTitle": {
                "text": "Function.data.totalCount",
                "style": "REGULAR",
                "subTitleTextColor": "#000080",
                "subTitleAlign": "END"
            }
        }
    ],
    "borderColor": "#87ceeb",
    "type": "CONTAINER",
    "uiAction": "",
    "order": 2
}
```

{% endcode %}

### Function.calculateSum

Calculates the total sum of all input value.

#### Parameter

| Field      | Value  | Description                                                                                                                                                              |
| ---------- | ------ | ------------------------------------------------------------------------------------------------------------------------------------------------------------------------ |
| name       | string | The name of the function: `Function.calculateSum`                                                                                                                        |
| sourceKeys | array  | The names of the keys on which you want to calculate the sum.                                                                                                            |
| resultKey  | string | The key name in which you want to store the final outcome of the function.                                                                                               |
| NAVIGATE   | string | The value of the card ID where you want to navigate after getting the result from the function. If you want to show results on the same card, then use the same card ID. |

{% code title="Example:" %}

```json
"cardUIAction": {
     "action1": {
        "action": [
        {
          "name": "Function.calculateSum",
          "url": "",
          "sourceKeys":["keyName1","keyName2","keyName3"],
          "sourceKey":"",
          "resultKey" : "KeyName3",
          "NAVIGATE":"cd-cost-preview"
         }
       ]
     }
   }
```

{% endcode %}

### Function.calculateSubtract

Calculates the subtraction of the input value.

#### Parameter

| Field     | Value  | Description                                                                                                                                                              |
| --------- | ------ | ------------------------------------------------------------------------------------------------------------------------------------------------------------------------ |
| name      | string | The name of the function: `Function.calculateSubtract`                                                                                                                   |
| sourceKey | string | The key name that you want to subtract from the totalKey.                                                                                                                |
| totalKey  | string | The key name from which the source key value gets subtracted.                                                                                                            |
| resultKey | string | The key name in which you want to store the final outcome of the function.                                                                                               |
| NAVIGATE  | string | The value of the card ID where you want to navigate after getting the result from the function. If you want to show results on the same card, then use the same card ID. |

{% code title="Example:" %}

```json
"cardUIAction": {
     "action1": {
        "action": [
        {
          "name": "Function.calculateSubtract",
          "url": "",
          "sourceKeys":[],
          "sourceKey":"keyName1",
          "totalKey":"keyName2"
          "resultKey" : "KeyName3",
          "NAVIGATE":"cd-cost-preview"
         }
       ]
     }
   }
```

{% endcode %}

### Function.calculateMultiply

Calculates the multiplication of all input values.

#### Parameter

| Field      | Value  | Description                                                                                                                                                              |
| ---------- | ------ | ------------------------------------------------------------------------------------------------------------------------------------------------------------------------ |
| name       | string | The name of the function: `Function.calculateMultiply`                                                                                                                   |
| sourceKeys | array  | The key names on which you want to calculate multiplication.                                                                                                             |
| resultKey  | string | The key name in which you want to store the final outcome of the function.                                                                                               |
| NAVIGATE   | string | The value of the card ID where you want to navigate after getting the result from the function. If you want to show results on the same card, then use the same card ID. |

{% code title="Example:" %}

```json
"cardUIAction": {
     "action1": {
        "action": [
        {
          "name": "Function.calculateMultiply",
          "url": "",
          "sourceKeys":["keyName1","keyName2","keyName3"],
          "sourceKey":"",
          "resultKey" : "KeyName3",
          "NAVIGATE":"cd-cost-preview"
         }
       ]
     }
   }
```

{% endcode %}

### Function.calculateDivide

Calculates the division of the input value.

#### Parameter

| Field     | Value  | Description                                                                |
| --------- | ------ | -------------------------------------------------------------------------- |
| name      | string | The name of the function: `Function.calculateDivision`                     |
| sourceKey | string | The key name that you want to get divided from the totalKey.               |
| totalKey  | string | The key name from which the source key value gets divided.                 |
| resultKey | string | The key name in which you want to store the final outcome of the function. |

{% code title="Example:" %}

```json
"cardUIAction": {
     "action1": {
        "action": [
        {
           "name": "Function.calculateDivide",
           "url": "",
           "sourceKeys":[],
           "sourceKey":"keyName1",
           "totalKey":"keyName2"
           "resultKey" : "KeyName3",
           "NAVIGATE":"cd-cost-preview"  
         }
       ]
     }
   }
```

{% endcode %}

### Function.calculatePercentage

Calculates the percentage of the input value.

#### Parameter

| Field     | Value  | Description                                                                                                                                                                                                   |
| --------- | ------ | ------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------- |
| name      | string | The name of the function: `Function.calculatePercentage`                                                                                                                                                      |
| sourceKey | string | The key name that has the percentage value, like 10% should be used as 10, 20% should be used as 20.                                                                                                          |
| totalKey  | string | The key name on which sourceKey will be applied. For example, if sourceKey has a key name with a value of 10 and totalKey has a key name with a total value of 200, the outcome will be 10 \* 200 / 100 = 20. |
| resultKey | string | The key name on which the final outcome of the function is stored.                                                                                                                                            |
| NAVIGATE  | string | The value of the card ID where you want to navigate after getting the result from the function. If you want to show results on the same card, then use the same card ID.                                      |

{% code title="Example:" %}

```json
"cardUIAction": {
     "action1": {
        "action": [
        {
           "name": "Function.calculatePercentage",
           "url": "",
           "sourceKeys":[],
           "sourceKey":"keyName1",
           "totalKey":"keyName2"
           "resultKey" : "KeyName3",
           "NAVIGATE":"cd-cost-preview"
          }
        ]
      }
    }
```

{% endcode %}

## Validating data input

### Function.validateReferralCode

Validates if the referral code entered is a valid TuumIO Wallet ID.

#### Parameter

| Field     | Value  | Description                                                     |
| --------- | ------ | --------------------------------------------------------------- |
| name      | string | The name of the function: `Function.validateReferralCode`       |
| resultKey | string | The input key for referral code. For example: `{$ReferralCode}` |

{% code title="Example:" %}

```json
        "action2":{
            "action": [
                {
                    "name": "Function.validateReferralCode",
                    "resultKey": "{recipientPublicKey}"
                },
                {
                    "name": "e-w-parti-refer-trial"
                }
            ]
        } 
```

{% endcode %}

### Check field format and field value

Validates field format and value. This function is used in [SmartTile1](/protocol-guide/build-a-dapp/card-definitions/tiles#smarttile1-input-validation-tile).

#### Parameter

| Field       | Value  | Description                                                                                                                                                                                                                                                          |
| ----------- | ------ | -------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------- |
| fieldFormat | string | <p>The name of the field value to be validated. The supported fieldFormat values are:</p><ul><li>age</li><li>email</li><li>pin</li><li>year</li><li>date</li><li>phone</li><li>country</li><li>ssn</li><li>otp</li><li>text</li><li>number</li><li>trialId</li></ul> |
| min         | string | The minimum length of the field value.                                                                                                                                                                                                                               |
| max         | string | The maximum length of the field value.                                                                                                                                                                                                                               |
| validation  | string | The validation whether field is required and the error message.                                                                                                                                                                                                      |
| name        | string | The validation whether field is required.                                                                                                                                                                                                                            |
| error       | string | The error message that shows when the value entered in invalid.                                                                                                                                                                                                      |

{% code title="Example:" %}

```json
{
    "id": "SmartTile1",
    "subView": [
        {
            "title": {
                "text": "5tile2iitextii7g0",
                "titleTextColor": "#000000",
                "titleAlign": "START"
            },
            "subTitle": {
                "text": "{$phoneValue}",
                "hint": "5tile2iihintiij3r",
                "subTitleTextColor": "#000000",
                "subTitleAlign": "START",
                "tip": "5tile2iitipiivqw",
                "fieldFormat": "phone",
                "min": "1",
                "max": "30",
                "validation": [
                    {
                        "name": "REQUIRED_FIELD",
                        "error": "5tile2iierroriinaz"
                    }
                ]
            },
            "img": {
                "text": "imageUrlktoxk",
                "isUrl": true,
                "height": "24",
                "width": "24"
            }
        }
    ],
    "borderColor": "#afafaf",
    "type": "CONTAINER",
    "uiAction": "",
    "order": 5
}
```

{% endcode %}

## Linking and navigation

### Function.When.Condition.Navigate

Shows a default empty card when no data is fetched, otherwise it moves to a specific card based on the `whenConditionKey` value within the data. This function allows displaying different cards based on various conditions.

#### Parameter

| Field            | Value  | Description                                                                 |
| ---------------- | ------ | --------------------------------------------------------------------------- |
| name             | string | The name of the function: `Function.When.Condition.preLoad`                 |
| method           | string | The method used to fetch data: `GET`                                        |
| url              | string | The path of the transaction data collection.                                |
| cardId           | string | The reference ID of the current card.                                       |
| whenConditionKey | string | The key name which represents the condition values, such as `recordStatus`. |
| whenConditions   | array  | The list of condition values and card IDs.                                  |
| conditionValue   | string | The value of the condition.                                                 |
| conditionCardId  | string | The card ID reference of the destination card.                              |

{% code title="Example:" %}

```json
    "cardUIAction": {
        "action253": {
            "action": [
                      {
                          "name": "Function.When.Condition.Navigate",
                          "cardId": "cd-xb8kw63u8rpge76l5mngcpkt36v1",
                          "whenConditionKey": "recordStatus",
                          "whenConditions": [
                            {
                                  "conditionValue": "empty",
                                  "conditionCardId": "cd-7w2t7slwuxjxojbu8n1qdvps-sg6"
                            },
                            {
                                "conditionValue": "rejected",
                                "conditionCardId": "cd-7w2t7slwuxjxojbu8n1qdvps-sg8"
                            },
                            {
                                "conditionValue": "verified",
                                "conditionCardId": "cd-7w2t7slwuxjxojbu8n1qdvps-sg7"
                            },
                            {
                                "conditionValue": "submitted",
                                "conditionCardId": "cd-7w2t7slwuxjxojbu8n1qdvps-sg9"
                            },
                            {
                                "conditionValue": "Pending review",
                                "conditionCardId": "cd-7w2t7slwuxjxojbu8n1qdvps-sg10"
                            }
                          ]
                        }
                    ]
          },
```

{% endcode %}

### Function.When.Condition.PreLoad

Shows a default empty card when no data is fetched, otherwise it stays on the current card. For the description of parameters, see [Function.When.Condition.Navigate](#function.when.condition.navigate).

{% code title="Example:" %}

```json
    "prerenderingFunctions": [
        {
          "name": "Function.When.Condition.preLoad",
          "method": "GET",
          "url": "/transactions/RECORD_DATA",
          "cardId": "cd-xb8kw63u8rpge76l5mngcpkt36v1",
          "whenConditionKey": "recordStatus",
          "whenConditions": [
            {
              "conditionValue": "empty",
              "conditionCardId": "cd-7w2t7slwuxjxojbu8n1qdvps-sg6"
            }
          ]
        }
      ],
```

{% endcode %}

### Function.Navigate

Moves to the destination card without calling events or event handlers. This function also supports calculating and comparing values.

#### Parameter

| Field  | Value  | Description                                    |
| ------ | ------ | ---------------------------------------------- |
| name   | string | The name of the function: `Function.Navigate`  |
| cardId | string | The card ID reference of the destination card. |

{% code title="Example 1:" %}

```json
    "cardUIAction": {
        "action1": {
            "action": "HOME"
        },
        "action17d1": {
            "action": [
                {
                    "name": "Function.Navigate",
                    "cardId": "cd-bpmho1x359gohn1rw6xdppzkzu11"
                }
            ]
        },
        "action17d2": {
            "action": [
                {
                    "name": "Function.Navigate",
                    "cardId": ""
                }
            ]
        },
        "action17d3": {
            "action": [
                {
                    "name": "Function.Navigate",
                    "cardId": ""
                }
            ]
        }
    }
```

{% endcode %}

{% code title="Example 2:" %}

```json
"cardUIAction": {
    "action1": {
        "action": "BACK"
    },
    "action337": {
        "action": [
            {
                "name": "Function.calculateSum",
                "sourceKeys": [
                    "patientAge",
                    "patientSugarLevel",
                    "patientSleepingTime"
                ],
                "resultKey": "resultSum1"
            },
            {
                "name": "Function.Navigate",
                "compareKey": "resultSum1",
                "compareValue": 60,
                "cardIdForGreaterValue": "cd-40yoxo205nu4sippxzmzj22mnn0",
                "cardIdForLessValue": "cd-34fdshqildm8ojse2tzu7jd85qj",
                "cardId": "cd-40yoxo205nu4sippxzmzj22mnn0"
            }
        ]
    }
}
```

{% endcode %}

### Function.ChangeCard

Pushes to a new view after comparing the compareKey values.

#### Parameter

| Field                 | Value   | Description                                                                                               |
| --------------------- | ------- | --------------------------------------------------------------------------------------------------------- |
| name                  | string  | The name of the function: `Function.ChangeCard`                                                           |
| compareKey            | string  | The dynamic value based on results from another function.                                                 |
| compareValue          | integer | The fixed value to which the compareKey value is compared to.                                             |
| cardIdForGreaterValue | string  | The card ID that is viewed when the compareKey value is greater than the fixed value set in compareValue. |
| cardIdForLessValue    | string  | The card ID that is viewed when the compareKey value is less than the fixed value set in compareValue.    |
| cardId                | string  | The card ID of the current view.                                                                          |

{% code title="Example:" %}

```json
{
    "name": "Function.ChangeCard",
    "compareKey": "resultSum1",
    "compareValue": 60,
    "cardIdForGreaterValue": "cd-40yoxo205nu4sippxzmzj22mnn0",
    "cardIdForLessValue": "cd-34fdshqildm8ojse2tzu7jd85qj",
    "cardId": "cd-40yoxo205nu4sippxzmzj22mnn0"
}
```

{% endcode %}

### Function.deposit.SOLVE

Navigates from any card to the "SOLVE" tab view.

#### Parameter

| Field    | Value  | Description                                        |
| -------- | ------ | -------------------------------------------------- |
| uiAction | string | The name of the function: `Function.deposit.SOLVE` |

{% code title="Example:" %}

```json
{
    "id": "Tile14",
    "subView": [
        {
            "title": {
                "text": "2tile14iitextii8ek"
            },
            "img": {
                "text": "imageUrl8i1kh",
                "isUrl": true,
                "height": "25",
                "width": "25"
            }
        }
    ],
    "borderColor": "#afafaf",
    "type": "CONTAINER",
    "uiAction": "Function.deposit.SOLVE",
    "order": 2
}
```

{% endcode %}

### Multiple selection

Allows multiple item selection for [Tile12: Dropdown Option Selector](/protocol-guide/build-a-dapp/card-definitions/tiles#tile12-dropdown-option-selector).

#### Parameter

| Field       | Value  | Description                                                        |
| ----------- | ------ | ------------------------------------------------------------------ |
| fieldFormat | string | The value that allows selecting multiple items in a dropdown list. |

{% code title="Example:" %}

```json
{
    "id": "Tile12",
    "subView": [
        {
            "title": {
                "text": "4tile12iitextii0xr",
                "style": "REGULAR",
                "titleTextColor": "#000000",
                "titleAlign": "START",
                "fontSize": 16
            },
            "subTitle": {
                "text": "4tile12iitextii1w4",
                "fontSize": 16,
                "data": "4tile12iidataii9pw",
                "hint": "4tile12iihintiigmm",
                "keyboard": "text",
                "subTitleTextColor": "#000000",
                "subTitleAlign": "START",
                "fieldFormat": "multiple"
            },
            "img": {
                "text": "imageUrlltc9e",
                "isUrl": true,
                "height": "25",
                "width": "25"
            }
        }
    ],
    "borderColor": "#afafaf",
    "backgroundColor": "#ffffff",
    "borderWidth": 1,
    "type": "CONTAINER",
    "uiAction": "",
    "order": 4
}
```

{% endcode %}

### isLink or isUrl

Adds links inside the text of a tile, such as [Tile0: Text Label](/protocol-guide/build-a-dapp/card-definitions/tiles#tile0-text-label).

#### Parameter

| Field           | Value  | Description                                                                                       |
| --------------- | ------ | ------------------------------------------------------------------------------------------------- |
| isLink or isURL | string | To enable the link features in a tile, the value is set to `"true"`.                              |
| urls            | array  | The list of labels and URLs. If isLink or isURL is set to "true", then this property is required. |
| label           | string | The title or subtitle text that will be clickable from the tile.                                  |
| url             | string | The URL that opens when the label text is clicked.                                                |

{% code title="Example:" %}

```json
{
  "id": "Tile0",
  "subView": [
      {
          "title": {
              "text": "6tile0aiitextiicqd",
              "style": "REGULAR",
              "titleTextColor": "#000000",
              "titleAlign": "START",
              "isUrl": true,
              "urls": [
                  { 
                    "label":"Terms",
                    "url":"https://solve.care/tuumiowallet-terms-and-conditions/" 
                  },
                  {
                    "label":"Privacy",
                    "url":"https://solve.care/tuumiowallet-privacy-policy/" 
                  }
              ]
          }
      }
  ],
  "borderColor": "#afafaf",
  "type": "CONTAINER",
  "uiAction": "",
  "order": 7
},
```

{% endcode %}

### Function.CallEventHandler

Executes other functions to pass user input to the next card.

#### Parameter

| Field  | Value  | Description                                           |
| ------ | ------ | ----------------------------------------------------- |
| name   | string | The name of the function: `Function.CallEventHandler` |
| method | string | The user input data to pass to the next card.         |

{% code title="Example:" %}

```json
        "action3": {
            "action": {
                "name": "Function.CallEventHandler",
                "method": "DETAILS",
                "NAVIGATION": "cd-participants-terms"
            }
        }
```

{% endcode %}

### Function.COPY.TEXT

Copies the subtitle or title text from specific tiles.

#### Parameter

| Field    | Value  | Description                                    |
| -------- | ------ | ---------------------------------------------- |
| uiAction | string | The name of the function: `Function.COPY.TEXT` |

{% code title="Example:" %}

```json
{
    "id": "Tile0a",
    "subView": [
        {
            "title": {
                "text": "0tile0aiitextiictl",
                "style": "BOLD",
                "titleTextColor": "#000000",
                "titleAlign": "START"
            },
            "subTitle": {
                "text": "0tile0aiitextiiocy",
                "style": "REGULAR",
                "subTitleTextColor": "#000000",
                "subTitleAlign": "END"
            }
        }
    ],
    "borderColor": "#afafaf",
    "type": "CONTAINER",
    "uiAction": "Function.COPY.TEXT",
    "order": 1
}
```

{% endcode %}

### Function.camera\_selfie

Captures a selfie or selects from the gallery.

#### Parameter

| Field     | Value  | Description                                                                                                      |
| --------- | ------ | ---------------------------------------------------------------------------------------------------------------- |
| name      | string | The name of the function: `Function.camera_selfie`                                                               |
| resultKey | string | The key name which will save the image in base64 format and will be added to the payload to be sent to the node. |

{% code title="Example:" %}

```json
"cardUIAction": {
     "action1": {
        "action":[
        {
          "name": "Function.camera_selfie",
          "resultKey" : "KeyName",
          "NAVIGATE":"cd-cost-preview"
         }
       ]
     }
   }
```

{% endcode %}

### Function.uploadFiles

Uploads multiple files in `AttachmentUploadTile`.

#### Parameter

| Field        | Value  | Description                                                                                                                             |
| ------------ | ------ | --------------------------------------------------------------------------------------------------------------------------------------- |
| name         | string | The name of the function: `Function.uploadFiles`                                                                                        |
| sourceKeys   | array  | The input key of the AttachmentUploadTile. For example, for input key `{$attachingFiles}`, the value for sourceKey is "attachingFiles". |
| resultKey    | string | The final submit key for storing data.                                                                                                  |
| timestampKey | string | The time in milliseconds when the file is successfully uploaded.                                                                        |

{% code title="Example:" %}

```json
{
  "id": "AttachmentUploadTile",
  "subView": [
      {
          "title": {
              "text": "1tile13iitextiiacf",
              "style": "REGULAR",
              "titleTextColor": "#000000",
              "titleAlign": "START",
              "fontSize": 16
          },
          "subTitle": {
              "text": "{$attachingFiles}",
              "fontSize": 16,
              "fileType": "PDF,PNG,JPG",
              "hint": "1tile13iihintii9rf",
              "subTitleTextColor": "#000000",
              "subTitleAlign": "START"
          }
      }
  ],
  "borderColor": "#afafaf",
  "backgroundColor": "#ffffff",
  "borderWidth": 1,
  "type": "CONTAINER",
  "uiAction": "",
  "order": 2
}
```

{% endcode %}

{% code title="Example:" %}

```json
"cardUIAction": {
    "action394": {
        "action": [
            {
                "name": "Function.uploadFiles",
                "sourceKeys": ["attachingFiles"],
                "resultKey": "record_folder_ref",
                "timestampKey": "createdAt"
            },
            {
                "name": "e-w-pt-save-pt_da-ms3o"
            }
        ]
    }
}
```

{% endcode %}


# Events and Event Handlers

This section describes the structure of event and event handler definitions, and some examples for the different types of events and event handlers.

{% hint style="info" %}
All event and event handler definitions must be included in the `input.json` file.
{% endhint %}

## Events

An event represents the actions that occur based on user interactions within a network. It defines the data used to communicate between roles or nodes in the network, such as sending and receiving information.&#x20;

### Types of events

* `WALLET_LOCAL` — A local event within TuumIO Wallet, such as sending data from one card to another.
* `WALLET_FROM_NODE` — An event that gets data from a specific node, such as retrieving a list of records in TuumIO Wallet.
* `WALLET_TO_NODE` — An event that sends data from TuumIO Wallet to a specific node, such as submitting records.
* `NODE_TO_NODE` — An event that sends data from one node to another node, such as a patient booking an appointment with a doctor.
* `NODE_TO_ROLE` — An event that sends data to all nodes with a designated role in a network, such as a patient searching for the nearest pediatrician among all doctors in the network.

<table><thead><tr><th width="235">Field Name</th><th width="166">Value Type</th><th>Description</th></tr></thead><tbody><tr><td>id</td><td>string</td><td>The unique ID of the event.</td></tr><tr><td>name</td><td>string</td><td>The name of the event.</td></tr><tr><td>description</td><td>string</td><td>The description of the event.</td></tr><tr><td>code</td><td>string</td><td>The same as the event name.</td></tr><tr><td>status</td><td>string</td><td>The status of the event is set to Active.</td></tr><tr><td>type</td><td>string</td><td>The type of event. The possible values are WALLET_LOCAL, WALLET_FROM_NODE, WALLET_TO_NODE, NODE_TO_NODE and NODE_TO_ROLE.</td></tr><tr><td>event_definition_ref</td><td>string</td><td>The reference path and ID of the event definition.</td></tr><tr><td>submit_event_handler</td><td>string</td><td>The ID of the event handler used for submitting the event.</td></tr><tr><td>node_event_handlers</td><td>array</td><td>The list of outgoing event handlers for node events.</td></tr><tr><td>card</td><td>string</td><td>The reference ID of the card associated to the event.</td></tr></tbody></table>

The following example represents an event that lets users navigate from one card to another, as defined in the `input.json` file.

{% code title="Example:" %}

```json
        "events": [
            {
                "id": "ev-patient-nav-to-cd-next",
                "name": "W.PATIENT.NAV.CD-NEXT",
                "description": "Event to navigate from start card to next card",
                "code": "W.PATIENT.NAV.CD-NEXT",
                "status": "Active",
                "type": "WALLET_LOCAL",
                "event_definition_ref": "event/ev-patient-nav-to-cd-next.json",
                "submit_event_handler": "eh-w-ev-patient-nav-to-cd-next",
                "node_event_handlers": [],
                "card": "cd-start-rl-patient"
            },
```

{% endcode %}

The following example defines an event containing user details: `event/ev-patient-nav-to-cd-next.json`.

{% code title="Example:" %}

```json
{
  "definition": {
    "description": "Get started",
    "name": "GET_STARTED",
    "resource": "GET_STARTED",
    "type": "EVENT_DATA"
  },
  "structure": {
    "attributes": [
      {
        "code": "answer",
        "name": "answer",
        "type_definition": {
          "type": "number"
        },
        "order": 3,
        "system": false,
        "required": false
      },

      {
        "code": "memberId",
        "name": "memberId",
        "type_definition": {
          "type": "string"
        },
        "order": 1,
        "system": false,
        "required": false
      }
    ]
  }
}
```

{% endcode %}

## Event handlers

The event handler defines the instructions that execute tasks based on specific events, such as navigation and data manipulation.

### Types of event handlers

* `WALLET_EVENT_HANDLER` — This event handler is defined in JSON and can be used to navigate between cards, submit data, or retrieve data.
* `NODE_EVENT_HANDLER` — This event handler is defined in either JSON or Python and can be used to search, retrieve, update, or save data. To learn more about the different types of node event handlers, see [Node Event Handlers](/protocol-guide/build-a-dapp/node-event-handlers) and [Python Event Handlers](/protocol-guide/build-a-dapp/python-event-handlers).

| Field Name                      | Value Type | Description                                                                                         |
| ------------------------------- | ---------- | --------------------------------------------------------------------------------------------------- |
| id                              | string     | The unique ID of the event handler.                                                                 |
| name                            | string     | The name of the event handler.                                                                      |
| description                     | string     | The description of the event handler.                                                               |
| status                          | string     | The status of the event handler is set to Active.                                                   |
| event                           | string     | The event which the event handler executes.                                                         |
| type                            | string     | The type of event handler. The possible values are: WALLET\_EVENT\_HANDLER and NODE\_EVENT\_HANDLER |
| event\_handler\_definition\_ref | string     | The reference path and ID of the event handler definition.                                          |

The following example is the wallet event handler for navigating to the next card, as defined in the `input.json` file.

{% code title="Example:" %}

```json
        "event_handlers": [
            {
                "id": "eh-w-patient-nav-to-cd-next",
                "name": "W.PATIENT.NAV.CD-NEXT",
                "description": "Wallet Event Handler to Navigate from Start to cd-next",
                "status": "Active",
                "event": "ev-patient-nav-to-cd-next",
                "type": "WALLET_EVENT_HANDLER",
                "event_handler_definition_ref": "event-handler/eh-w-ev-patient-nav-to-cd-next.json"
            },
```

{% endcode %}

The following example is an event handler definition in a JSON file that sends the details to the next card in the sequence: `event-handler/eh-w-ev-patient-nav-to-cd-next1.json`.&#x20;

{% code title="Example:" %}

```json
{
    "walletEventHandler": [
        {
            "refId": "ev-patient-nav-to-cd-next",
            "walletEvents": [
                {
                    "actions": [
                        {
                            "name": "submit",
                            "order": 1,
                            "parameter": [
                                {
                                    "method": "POST",
                                    "url": "/events"
                                }
                            ]
                        }
                    ],
                    "postAction": "cd-next",
                    "refId": "ev-patient-nav-to-cd-next"
                }
            ]
        }
    ]
}
```

{% endcode %}

## Use case examples

### Submitting health questions

In this example, a patient submits answers from the health questions card and the data is saved in a collection.

1. Define the events in the `input.json` file. Here, we have two events:

{% code title="Example:" %}

```json
            {
                "id": "ev-w-broad-health-questions",
                "name": "W.BROAD.H.QUESTIONS",
                "description": "Submit health questions",
                "code": "W.BROAD.H.QUESTIONS",
                "status": "Active",
                "type": "WALLET_TO_NODE",
                "event_definition_ref": "event/ev-w-broad-health-questions.json",
                "submit_event_handler": "eh-ev-w-broad-health-questions",
                "next_event": "ev-w-broad-health-questions-na",
                "node_event_handlers": [
                    "eh-n-ev-w-broad-health-questions", "eh-n-patient-process-py"
                ],
                "card": "cd-health-questions"
            },
            {
                "id": "ev-w-broad-health-questions-na",
                "name": "W.BROAD.H.QUESTIONS.NA",
                "description": "Broadcast health questions from Patients to rl-netadmin",
                "code": "W.BROAD.H.QUESTIONS.NA",
                "status": "Active",
                "type": "NODE_TO_ROLE",
                "event_definition_ref": "event/ev-w-broad-health-questions-na.json",
                "from_role": "rl-patient",
                "to_role": "rl-netadmin",
                "node_event_handlers": [
                    "eh-n-ev-w-broad-health-questions-na"
                ],
                "card": "cd-health-questions"
            },
```

{% endcode %}

2. Create the event definition for the submit event that contains the data used in the patient health questions: `event/ev-w-broad-health-questions.json`.

{% code title="Example:" %}

```json
{
    "definition": {
        "description": "Save H_QUESTIONS at Patients",
        "name": "W-BROAD-H-QUESTIONS",
        "resource": "W-BROAD-H-QUESTIONS",
        "type": "EVENT_DATA"
    },
    "structure": {
        "attributes": [
            {
                "name": "Symptoms",
                "type_definition": {
                    "type": "string"
                },
                "required": false,
                "system": false,
                "code": "Symptoms",
                "order": 1
            },
            {
                "name": "History",
                "type_definition": {
                    "type": "string"
                },
                "required": false,
                "system": false,
                "code": "History",
                "order": 2
            },
            {
                "name": "Gender",
                "type_definition": {
                    "type": "string"
                },
                "required": true,
                "system": false,
                "code": "Gender",
                "order": 3
            },
            {
                "name": "Age",
                "type_definition": {
                    "type": "number"
                },
                "required": true,
                "system": false,
                "times": 1,
                "code": "Age",
                "order": 4
            },
            {
                "code": "transactionalGuid",
                "name": "transactionalGuid",
                "type_definition": {
                    "type": "string"
                },
                "required": false,
                "system": false,
                "times": 1,
                "order": 5
            },
            {
                "code": "createdAt",
                "name": "createdAt",
                "type_definition": {
                    "type": "timestamp"
                },
                "required": false,
                "system": false,
                "times": 1,
                "order": 6
            },
            {
                "name": "senderNodeAddress",
                "code": "senderNodeAddress",
                "type_definition": {
                    "type": "string"
                },
                "required": false,
                "system": false,
                "order": 7
            }
        ],
        "primary_key": "false"
    }
}
```

{% endcode %}

3. Define the event handlers for the submit event in the `input.json` file. Here, the submit event has two event handlers: `eh-ev-w-broad-health-questions.json` and `eh-n-ev-w-broad-health-questions.json`.&#x20;

{% code title="Example:" %}

```json
            {
                "id": "eh-ev-w-broad-health-questions",
                "name": "eh-ev-w-broad-health-questions",
                "description": "Submit H_Questions",
                "status": "Active",
                "event": "ev-w-broad-health-questions",
                "type": "WALLET_EVENT_HANDLER",
                "event_handler_definition_ref": "event-handler/eh-ev-w-broad-health-questions.json"
            },
            {
                "id": "eh-n-ev-w-broad-health-questions",
                "name": "eh-n-ev-w-broad-health-questions",
                "description": "Broadcast H_QUESTIONS from Patients to rl-netadmin",
                "status": "Active",
                "event": "ev-w-broad-health-questions",
                "type": "NODE_EVENT_HANDLER",
                "event_handler_definition_ref": "event-handler/eh-n-ev-w-broad-health-questions.json"
            },
```

{% endcode %}

4. Create the wallet event handler definition for submitting the event data: `event-handler/eh-ev-w-broad-health-questions.json`.

{% code title="Example:" %}

```json
{
    "walletEventHandler": [
        {
            "refId": "ev-w-broad-health-questions",
            "walletEvents": [
                {
                    "actions": [
                        {
                            "name": "submit",
                            "order": 1,
                            "parameter": [
                                {
                                    "method": "POST",
                                    "url": "/events"
                                }
                            ]
                        }
                    ],
                    "postAction": "cd-health-questions-done",
                    "refId": "ev-w-broad-health-questions"
                } 
            ]
        }
    ]
}
```

{% endcode %}

5. Create the node event handler definition for saving the event payload: `eh-n-ev-w-broad-health-questions.json`.

{% code title="Example:" %}

```json
{
    "nodeEventHandlers": [
        {
            "type": "MAPPER",
            "name": "Append or Exclude attributes to H_QUESTIONS payload",
            "order": 1,
            "dataSource": "EVENT_PAYLOAD",
            "additionalAttributes": {
                "createdAt": {
                    "source": "GENERATED",
                    "value": "CURRENT_TIMESTAMP"
                },
                "transactionalGuid": {
                    "source": "GENERATED",
                    "value": "UUID"
                },
                "senderNodeAddress": {
                    "source": "EVENT",
                    "value": "SENDER"
                }
            },
            "excludedAttributes": []
        },
        {
            "type": "VAULT_INSERT",
            "name": "H_QUESTIONS",
            "order": 2,
            "collection": "H_QUESTIONS",
            "collectionVersion": 1,
            "dataSource": "HANDLER_ARGUMENTS",
            "handlerOutput": "PERSISTED_ENTITY"
        },
        {
            "type": "MAPPER",
            "name": "Append or Exclude attributes in the result",
            "order": 3,
            "dataSource": "EVENT_PAYLOAD",
            "additionalAttributes": {
                "createdAt": {
                    "source": "HANDLER_ARGUMENTS",
                    "value": "createdAt"
                },
                "transactionalGuid": {
                    "source": "HANDLER_ARGUMENTS",
                    "value": "transactionalGuid"
                },
                "senderNodeAddress": {
                    "source": "EVENT",
                    "value": "SENDER"
                }
            },
            "excludedAttributes": []
        }
    ]
}
```

{% endcode %}

6. Create the event definition for the next event: `ev-w-broad-health-questions-na.json`.

```json
{
    "definition": {
        "description": "Save H_QUESTIONS at PATIENT_ANSWERS",
        "name": "W-BROAD-H-QUESTIONS",
        "resource": "W-BROAD-H-QUESTIONS",
        "type": "EVENT_DATA"
    },
    "structure": {
        "attributes": [
            {
                "name": "Symptoms",
                "type_definition": {
                    "type": "string"
                },
                "required": false,
                "system": false,
                "code": "Symptoms",
                "order": 1
            },
            {
                "name": "History",
                "type_definition": {
                    "type": "string"
                },
                "required": false,
                "system": false,
                "code": "History",
                "order": 2
            },
            {
                "name": "Gender",
                "type_definition": {
                    "type": "string"
                },
                "required": true,
                "system": false,
                "code": "Gender",
                "order": 3
            },
            {
                "name": "Age",
                "type_definition": {
                    "type": "number"
                },
                "required": true,
                "system": false,
                "times": 1,
                "code": "Age",
                "order": 4
            },
            {
                "code": "transactionalGuid",
                "name": "transactionalGuid",
                "type_definition": {
                    "type": "string"
                },
                "required": false,
                "system": false,
                "times": 1,
                "order": 5
            },
            {
                "code": "createdAt",
                "name": "createdAt",
                "type_definition": {
                    "type": "timestamp"
                },
                "required": false,
                "system": false,
                "times": 1,
                "order": 6
            },
            {
                "name": "senderNodeAddress",
                "code": "senderNodeAddress",
                "type_definition": {
                    "type": "string"
                },
                "required": false,
                "system": false,
                "order": 7
            }
        ],
        "primary_key": "false"
    }
}
```

7. Define the event handler for the next event in the `input.json` file. The next event has one event handler: `eh-n-ev-w-broad-health-questions-na.json`.

```json
            {
                "id": "eh-n-ev-w-broad-health-questions-na",
                "name": "eh-n-ev-w-broad-health-questions-na",
                "description": "Broadcast H_QUESTIONS from Patients to rl-netadmin",
                "status": "Active",
                "event": "ev-w-broad-health-questions-na",
                "type": "NODE_EVENT_HANDLER",
                "event_handler_definition_ref": "event-handler/eh-n-ev-w-broad-health-questions-na.json"
            }
```

8. Create the node event handler definition that saves the event data to the collection: `event-handler/eh-ev-n-broad-health-questions-na.json`. Here, the data is saved to the `PATIENT_ANSWERS` collection based on the defined search criteria.

```json
{
    "nodeEventHandlers": [
        {
            "type": "MAPPER",
            "name": "Append or Exclude attributes to H_QUESTIONS payload",
            "order": 1,
            "dataSource": "EVENT_PAYLOAD",
            "additionalAttributes": {},
            "excludedAttributes": []
        },
        {
            "type": "VAULT_UPDATE",
            "name": "PATIENT_ANSWERS",
            "order": 2,
            "collection": "PATIENT_ANSWERS",
            "collectionVersion": 1,
            "dataSource": "HANDLER_ARGUMENTS",
            "insertIfAbsent": true,
            "searchCriteria": [
                {
                    "queryMatcher": "EQUAL",
                    "fieldName": "senderNodeAddress",
                    "dynamicValue": {
                        "source": "EVENT_PAYLOAD",
                        "value": "senderNodeAddress"
                    }
                }
            ],
            "handlerOutput": "PERSISTED_ENTITY"
        }
    ]
}
```

### Viewing records history

In this example, the wallet retrieves the history of records from a data collection and displays it on the card.

1. Define the event in the `input.json` file.

{% code title="Example:" %}

```json
            {
                "id": "ev-get-records-history",
                "name": "W.GET.RECORDS.HIST",
                "code": "W.GET.RECORDS.HIST",
                "description": "Get Records History",
                "status": "Active",
                "type": "WALLET_FROM_NODE",
                "event_definition_ref": "event/ev-get-records-history.json",
                "submit_event_handler": "eh-ev-get-records-history",
                "node_event_handlers": [],
                "card": "cd-view-records"
            }
```

{% endcode %}

2. Create the event definition with the source of data: `event/ev-get-records-history.json`. To retrieve data, this event uses the unique ID of the `transactionalGuid` generated from a submit event.

{% code title="Example:" %}

```json
{
    "definition": {
        "description": "Get Records History",
        "name": "Get Records History",
        "resource": "Get Records History",
        "type": "EVENT_DATA"
    },
    "structure": {
        "attributes": [
            {
                "code": "transactionalGuid",
                "name": "transactionalGuid",
                "type_definition": {
                    "type": "string"
                },
                "order": 1,
                "system": false,
                "required": false
            }
        ]
    }
}
```

{% endcode %}

3. Define the event handler in the `input.json` file.

{% code title="Example:" %}

```json
            {
                "id": "eh-ev-get-records-history",
                "name": "eh-ev-get-records-history",
                "description": "eh-ev-get-records-history",
                "status": "Active",
                "event": "ev-get-records-history",
                "type": "WALLET_EVENT_HANDLER",
                "event_handler_definition_ref": "event-handler/eh-ev-get-records-history.json"
            }   
```

{% endcode %}

4. Create the wallet event handler definition that gets the records history data from the collection: `event-handler/eh-ev-get-records-history.json`. This event handler uses the GET method to retrieve record data based on the filter query.

{% code title="Example:" %}

```json
{
    "walletEventHandler": [
        {
            "refId": "ev-get-records-history",
            "walletEvents": [
                {
                    "actions": [
                        {
                            "name": "",
                            "order": 1,
                            "parameter": [
                                {
                                    "method": "GET",
                                    "url": "/transactions/RECORD_DATA?filter=[{\"queryMatcher\":\"EQUAL\",\"fieldName\":\"senderNodeAddress\",\"value\":\"${senderNodeAddress}\"}]"
                                }
                            ]
                        }
                    ],
                    "postAction": "",
                    "refId": "ev-get-records-history"
                }
            ]
        }
    ]
}
```

{% endcode %}


# Node Event Handlers

This section describes the different types of node event handlers, their definitions, parameters, and examples.

## Types of node event handlers

* `VAULT_INSERT` — This event handler is used to insert a record into a specific collection in the vault.
* `VAULT_UPDATE` — This event handler is used to update a record in a specific collection in the vault based on the dynamic search criteria.
* `MAPPER` — This event handler is used for data transformation, such as excluding, appending, or generating data in the execution chain.
* `NEXT_EVENT_RECIPIENT` — This event handler is used to identify the recipient for the next event.
* `EXPRESSION_LANGUAGE` — This event handler allows writing data manipulation expressions to easily access, filter, and calculate values.
* `CUSTOM` — This event handler is used to specify a specific Java class that implements a legacy JAR (Java Archive) handler.

## Handler definition constants

### Handler data source (`GenericHandlerDataSource`)

* `EMPTY`— An empty source or collection.
* `EVENT_PAYLOAD` — The payload source of events processed in the handlers chain.
* `HANDLER_ARGUMENTS` — The response value from the previous handler in the chain.
* `PERSISTED_ENTITY` — For vault-related handlers, it is the state of inserted or updated documents in a collection.

### Dynamic handler value (`DynamicHandlerValue`)

It uses "source" and "value" fields to link data. The actual value can be determined dynamically based on the information in the "source" field. Here are the possible values:

| Source              | Possible values                                              | Description                                                                                    |
| ------------------- | ------------------------------------------------------------ | ---------------------------------------------------------------------------------------------- |
| `CONSTANT`          | Any value                                                    | The constant propagates the value field as a result.                                           |
| `GENERATED`         | `UUID`, `CURRENT_TIMESTAMP`                                  | It generates a UUID or timestamp.                                                              |
| `EVENT`             | `SENDER`, `RECIPIENT`, `CODE`, `TIMESTAMP`, `CORRELATION_ID` | It gets the value of the original event sender, recipient, code, timestamp, or correlation ID. |
| `EVENT_PAYLOAD`     | Attribute name                                               | It gets the value of the attribute in the event payload.                                       |
| `HANDLER_ARGUMENTS` | Attribute name                                               | It gets the value of the attribute in the handler arguments.                                   |

## Handler definition examples

### Vault Insert handler

| Parameters        | Data type / Values                                              | Description                                                                |
| ----------------- | --------------------------------------------------------------- | -------------------------------------------------------------------------- |
| type              | `VAULT_INSERT`                                                  | The handler type.                                                          |
| order             | Integer                                                         | The order of the handler in the execution chain.                           |
| name              | String                                                          | The name of the handler which is used for logging.                         |
| collection        | String                                                          | The name of the vault collection.                                          |
| collectionVersion | Integer                                                         | The version of the vault collection.                                       |
| dataSource        | `EMPTY`, `EVENT_PAYLOAD`, `HANDLER_ARGUMENTS`                   | The data source of the record which will be inserted into the collection.  |
| handlerOutput     | `EMPTY`, `EVENT_PAYLOAD`, `HANDLER_ARGUMENTS, PERSISTED_ENTITY` | The handler output that will be passed as an argument to the next handler. |

{% code title="Example:" %}

```json
    {
      "type": "VAULT_INSERT",
      "name": "Insert SAMPLE record",
      "order": 2,
      "collection": "SAMPLE",
      "collectionVersion": 1,
      "dataSource": "HANDLER_ARGUMENTS",
      "handlerOutput": "PERSISTED_ENTITY"
    }
```

{% endcode %}

### Vault Update handler

| Parameters        | Data type / Values                                                | Description                                                                                                                                            |
| ----------------- | ----------------------------------------------------------------- | ------------------------------------------------------------------------------------------------------------------------------------------------------ |
| type              | `VAULT_UPDATE`                                                    | The handler type.                                                                                                                                      |
| order             | Integer                                                           | The order of the handler in the execution chain.                                                                                                       |
| name              | String                                                            | The name of the handler which is used for logging.                                                                                                     |
| collection        | String                                                            | The name of the vault collection.                                                                                                                      |
| collectionVersion | Integer                                                           | The version of the vault collection.                                                                                                                   |
| dataSource        | `EMPTY`, `EVENT_PAYLOAD`, `HANDLER_ARGUMENTS`                     | The data source from which the record changes (diffs) will be retrieved.                                                                               |
| handlerOutput     | `EMPTY`, `EVENT_PAYLOAD`, `HANDLER_ARGUMENTS`, `PERSISTED_ENTITY` | The handler output that will be passed as an argument to the next handler.                                                                             |
| insertIfAbsent    | Boolean                                                           | It defines a flag that inserts the document if it does not exist in the collection based on the search criteria. The value is set to false by default. |
| searchCriteria    | Array of `SearchQueryFilter`                                      | The search criteria to find the document to be updated.                                                                                                |

{% code title="Example:" %}

```json
    {
      "type": "VAULT_UPDATE",
      "name": "Answer SAMPLE question",
      "order": 1,
      "collection": "SAMPLE",
      "collectionVersion": 1,
      "dataSource": "EVENT_PAYLOAD",
      "searchCriteria": [
        {
          "queryMatcher": "EQUAL",
          "fieldName": "transactionalGuid",
          "dynamicValue": {
            "source": "EVENT_PAYLOAD",
            "value": "transactionalGuid"
          }
        }
      ],
      "handlerOutput": "PERSISTED_ENTITY"
    }
```

{% endcode %}

### Data Transformation handler

| Parameters           | Data type / Values                                                                                                                        | Description                                                                |
| -------------------- | ----------------------------------------------------------------------------------------------------------------------------------------- | -------------------------------------------------------------------------- |
| type                 | `MAPPER`                                                                                                                                  | The handler type.                                                          |
| order                | Integer                                                                                                                                   | The order of the handler in the execution chain.                           |
| name                 | String                                                                                                                                    | The name of the handler which is used for logging.                         |
| dataSource           | `EMPTY`, `EVENT_PAYLOAD`, `HANDLER_ARGUMENTS`                                                                                             | The data source for the unmapped data.                                     |
| handlerOutput        | `EMPTY`, `EVENT_PAYLOAD`, `HANDLER_ARGUMENTS`, `PERSISTED_ENTITY`                                                                         | The handler output that will be passed as an argument to the next handler. |
| excludedAttributes   | Array of strings                                                                                                                          | A set of attributes to be excluded from the input data.                    |
| additionalAttributes | <p>Map of <code>DynamicHandlerValue</code></p><p>(see <a href="#dynamic-handler-value-dynamichandlervalue">Dynamic handler value</a>)</p> | A map of attributes with dynamic values calculated at runtime.             |

{% code title="Example:" %}

```json
    {
      "type": "MAPPER",
      "name": "Append SAMPLE payload",
      "order": 1,
      "dataSource": "EVENT_PAYLOAD",
      "additionalAttributes": {
        "createdAt": {
          "source": "GENERATED",
          "value": "CURRENT_TIMESTAMP"
        },
        "transactionalGuid": {
          "source": "GENERATED",
          "value": "UUID"
        },
        "doctorNodeAddress": {
          "source": "EVENT",
          "value": "SENDER"
        }
      },
      "excludedAttributes": [
        "correlationId"
      ]
    }
```

{% endcode %}

### Next Event Recipient handler

| Parameters       | Data type / Values                                                                                                                 | Description                                                                |
| ---------------- | ---------------------------------------------------------------------------------------------------------------------------------- | -------------------------------------------------------------------------- |
| type             | `NEXT_EVENT_RECIPIENT`                                                                                                             | The handler type.                                                          |
| order            | Integer                                                                                                                            | The order of the handler in the execution chain.                           |
| name             | String                                                                                                                             | The name of the handler which is used for logging.                         |
| handlerOutput    | `EMPTY`, `EVENT_PAYLOAD`, `HANDLER_ARGUMENTS`                                                                                      | The handler output that will be passed as an argument to the next handler. |
| recipientAddress | <p><code>DynamicHandlerValue</code></p><p>(see <a href="#dynamic-handler-value-dynamichandlervalue">Dynamic handler value</a>)</p> | The dynamic value represents the recipient of the next event.              |

{% code title="Example:" %}

```json
    {
      "type": "NEXT_EVENT_RECIPIENT",
      "name": "Fetch SAMPLE target doctor",
      "order": 2,
      "recipientAddress": {
        "source": "HANDLER_ARGUMENTS",
        "value": "doctorNodeAddress"
      },
      "handlerOutput": "HANDLER_ARGUMENTS"
    }
```

{% endcode %}

### Expression Language handler

The expression language used for this handler type is based on Spring Expression Language (SpEL). For more information, see the documentation for [Spring Expression Language (SpEL)](https://docs.spring.io/spring-framework/docs/3.0.x/reference/expressions.html).&#x20;

Here are the operators supported in the language:

| Type        | Operators                                    |
| ----------- | -------------------------------------------- |
| Arithmetic  | +, -, \*, /, %, ^, div, mod                  |
| Relational  | <, >, ==, !=, <=, >=, lt, gt, eq, ne, le, ge |
| Logical     | and, or, not, &&, \|\|, !                    |
| Conditional | ?:                                           |
| Regex       | matches                                      |

Here are the parameters in the event handler definition:

| Parameter          | Data type / Values                                                                            | Description                                                                           |
| ------------------ | --------------------------------------------------------------------------------------------- | ------------------------------------------------------------------------------------- |
| type               | `EXPRESSION_LANGUAGE`                                                                         | The handler type.                                                                     |
| order              | Integer                                                                                       | The order of the handler in the execution chain.                                      |
| name               | String                                                                                        | The name of the handler which is used for logging.                                    |
| dataSource         | `EMPTY`, `EVENT_PAYLOAD`, `HANDLER_ARGUMENTS`                                                 | The data source of the record which will be inserted into the collection.             |
| computedAttributes | Map of expressions, where the key is a variable name, and the value is the expression itself. | The handler executes the expression and puts the value inside the specified variable. |

{% code title="Example 1:" %}

```json
    {
      "type": "EXPRESSION_LANGUAGE",
      "name": "Calc",
      "order": 2,
      "dataSource": "EMPTY",
      "computedAttributes": {
        "c": "arguments['a']+arguments['b']"
      }
    }
```

{% endcode %}

In Example 1, let's assume that the `HANDLER_ARGUMENTS` has variables `a` and `b`. If the variables represent numeric values, such as `a=1` and `b=2`, then the result will be `1+2=3`.  If the variables represent string values, such as `a='1'` and `b='2`', then the result will be `'1'+'2'='12'`.

{% code title="Example 2:" %}

```json
    {
      "type": "EXPRESSION_LANGUAGE",
      "name": "Calc",
      "order": 2,
      "dataSource": "EMPTY",
      "computedAttributes": {
        "res": "arguments[users].?[country=='USA'].size()"
      }
    }
```

{% endcode %}

In Example 2, let's assume that the `HANDLER_ARGUMENTS` has a variable `user`, which represent a list with the following value:

```json
    [
      {
        "name": "John",
        "country": "USA"
      },
      {
        "name": "Sam",
        "country": "Canada"
      },
    ]
```

The expression `arguments[users].?[country=='USA'].size()` will filter the items which has the country value set to `"USA"`.  Then it calculates the size, which returns the count. In this case, the result will be `1`.

{% code title="Example 3:" %}

```json
    {
      "type": "EXPRESSION_LANGUAGE",
      "name": "Calc",
      "order": 2,
      "dataSource": "EMPTY",
      "computedAttributes": {
        "res": "arguments[users].?[country=='USA'].size() > 0 ? 'USA_PRESENT' : 'USA_NOT_PRESENT'"
      }
    }
```

{% endcode %}

In Example 3, let's assume that the `HANDLER_ARGUMENTS` has a variable `user`, which represent a list with the following value:

```json
    [
      {
        "name": "John",
        "country": "USA"
      },
      {
        "name": "Sam",
        "country": "Canada"
      },
    ]
```

The expression `arguments[users].?[country=='USA'].size() > 0 ? 'USA_PRESENT' : 'USA_NOT_PRESENT'` will filter the items which has the country value set to `"USA"`. Then it calculates the size, which returns the count. In this case, the count is `1`. If the count is greater than 0, then the result will be `'USA_PRESENT'`.

### Custom (JAR) handler

| Parameter | Data type / Values | Description                                                           |
| --------- | ------------------ | --------------------------------------------------------------------- |
| type      | CUSTOM             | The handler type.                                                     |
| order     | Integer            | The order of the handler in the execution chain.                      |
| jarUrl    | String             | The URL where the JAR file with the handler implementation is stored. |
| className | String             | The full Java class name that implements the corresponding interface. |

{% code title="Example:" %}

```json
  {
    "type": "CUSTOM",
    "order": 2,
    "jarUrl": "https://a.solvecare.net/artifactory/libs-snapshot-local/care/solve/generic/node/hello-world-handler/1.0.4-SNAPSHOT/hello-world-handler-1.0.4-20220406.133327-6.jar",
    "className": "care.solve.node.handler.demo.patient.PatientComputeBmiHandler"
  }
```

{% endcode %}


# Python Event Handlers

This section provides examples on how to configure Python event handlers.

The Python event handler contains a set of base classes that provide an interface to the platform's core components, such as Vault, Wallet, Node, and TuumIO Data Node (TDN). The following template includes base classes and functions that provide features to retrieve, search, update, and save data.

## Python template

{% code title="Example:" fullWidth="false" %}

```python
class TDN:
    def __init__(self, index: str):
        self.context = context
        self.index = index
    def find_all(self, parameters: SearchRequest) -> List:
        return self.context.getCareDataNodeProvider().findAll(self.index, parameters)
    def find_first(self, parameters: SearchRequest) -> SearchResponse:
        return self.context.getCareDataNodeProvider().findFirst(self.index, parameters)
    def raw_search(self, from_row, num_rows, search_request) -> List:
        return self.context.getCareDataNodeProvider().rawSearch(self.index, from_row, num_rows, search_request)

class Wallet:
    def __init__(self):
        self.context = context
    def get_wallet_profile(self) -> WalletProfile:
        return self.context.getMainNetNodeProvider().getMainNetProfile(ProfileType.WALLET)
    def get_phone_profile(self) -> PhoneProfile:
        return self.context.getMainNetNodeProvider().getMainNetProfile(ProfileType.PHONE)
    def get_contact_profile(self) -> ContactProfile:
        return self.context.getMainNetNodeProvider().getMainNetProfile(ProfileType.CONTACT)
    def update_wallet_profile(self, data: Map, attribute_mapping: Map) -> Map:
        self.context.getMainNetNodeProvider().updateWalletProfile(data, attribute_mapping)
        return data
    def update_phone_profile(self, data: Map, attribute_mapping: Map) -> Map:
        self.context.getMainNetNodeProvider().updatePhoneProfile(data, attribute_mapping)
        return data
    def update_contact_profile(self, data: Map, attribute_mapping: Map) -> Map:
        self.context.getMainNetNodeProvider().updateContactProfile(data, attribute_mapping)
        return data

class Vault:
    def __init__(self):
        self.context = context
    def save(self, collection: str, data: Map) -> Map:
        vault = self.context.getVaultStorage(collection)
        guid = vault.save(data)
        return vault.getByGuid(guid)
    def update(self, collection: str, criteria: List, data: Map, insert_if_absent: bool) -> Map:
        vault = self.context.getVaultStorage(collection)
        guid = vault.update(criteria, data, insert_if_absent)
        return vault.getByGuid(guid)
    def search(self, collection: str, filters: List) -> List:
        vault = self.context.getVaultStorage(collection)
        return vault.search(filters)

class Node:
    def __init__(self, context: HandlerExecutionContext):
        self.context = context

    def info(self) -> NodeInfo:
        return self.context.getNodeInfo()


def execute(ctx: HandlerExecutionContext) -> Map:
    result = HashMap(arguments())
    # PUT YOUR CODE HERE
    return result
```

{% endcode %}

## Use case example

1. Define the event in the `input.json` file.

{% code title="Example:" %}

```json
{
    "id": "ev-tdn-broadcast",
    "name": "N.TDN.BROADCAST.MESSAGE",
    "code": "N.TDN.BROADCAST.MESSAGE",
    "description": "TDN broadcast message",
    "status": "Active",
    "type": "NODE_TO_ROLE",
    "from_role": "DATA_NODE",
    "to_role": "PATIENT",
    "event_definition_ref": "event/ev-cdn-broadcast.json",
    "node_event_handlers": [
      "eh-n-patient-process-py"
    ]
  }
```

{% endcode %}

2. Create the event definition: `event/ev-cdn-broadcast.json`*.*

{% code title="Example:" %}

```json
{
  "definition": {
    "description": "Broadcast TDN message",
    "name": "N_TDN_BROADCAST_MESSAGE",
    "resource": "N_TDN_BROADCAST_MESSAGE",
    "type": "EVENT_DATA"
  },
  "structure": {
    "attributes": [
      {
        "code": "transactionalGuid",
        "name": "transactionalGuid",
        "type_definition": {
          "type": "string"
        },
        "order": 1,
        "system": false
      },
      {
        "code": "indexName",
        "name": "indexName",
        "type_definition": {
          "type": "string"
        },
        "order": 2,
        "system": false
      },
      {
        "code": "ddfType",
        "name": "ddfType",
        "type_definition": {
          "type": "string"
        },
        "order": 3,
        "system": false
      },
      {
        "code": "msgType",
        "name": "msgType",
        "type_definition": {
          "type": "string"
        },
        "order": 4,
        "system": false
      },
      {
        "code": "attributes",
        "name": "attributes",
        "type_definition": {
          "type": "collection",
          "item_type_definition": {
            "type": "string"
          }  
        },
        "order": 5,
        "system": false
      }
    ]
  }
}
```

{% endcode %}

3. Define the event handler in the `input.json` file.

{% code title="Example:" %}

```json
 {
    "id": "eh-n-patient-process-py",
    "name": "N.TDN.BROADCAST.MESSAGE",
    "description": "N.TDN.BROADCAST.MESSAGE",
    "status": "Active",
    "event": "ev-tdn-broadcast",
    "type": "NODE_EVENT_HANDLER",
    "python_event_handler_ref": "python-event-handler/eh-n-patient-process.py"
  }
```

{% endcode %}

4. Create a Python event handler definition that saves the data.

{% code title="Example:" %}

```python
def execute(ctx: HandlerExecutionContext) -> Map:
    result = HashMap(arguments())
    # PUT YOUR CODE HERE
    start_row = 0
    num_rows = 10
    query = {
      "match_all": {}
    }
    page = CDN('DOCTORS').search(start_row, num_rows, query)
    Vault('MY_DATA').save(page.getContent())
    return result
```

{% endcode %}


# Transactional Data

This section shows the structure and attributes of transactional data.

Transactional data contains configurable data that can be referenced from roles, cards, or events within the network. The following example shows the definition of transactional data in `td/td-default.json`.

{% code title="Example:" %}

```json
{
    "id": "td-default",
    "path": "td/td-default.json",
    "definition": {
        "collection": "DEFAULT",
        "description": "DEFAULT",
        "name": "DEFAULT",
        "resource": "DEFAULT",
        "status": "RELEASED",
        "type": "TRANSACTIONAL_DATA"
    },
    "structure": {
        "attributes": [
            {
                "code": "transactionalGuid",
                "name": "transactionalGuid",
                "type_definition": {
                    "type": "string"
                },
                "order": 1,
                "required": false,
                "system": false
            },
            {
                "code": "createdAt",
                "name": "createdAt",
                "type_definition": {
                    "type": "timestamp"
                },
                "order": 2,
                "required": false,
                "system": false
            },
            {
                "code": "answer",
                "name": "answer",
                "type_definition": {
                    "type": "string"
                },
                "order": 3,
                "required": false,
                "system": false
            },
            {
                "name": "senderNodeAddress",
                "code": "senderNodeAddress",
                "type_definition": {
                    "type": "string"
                },
                "required": false,
                "system": false,
                "order": 4
            }
        ]
    }
}
```

{% endcode %}


# Test and Publish

### Deployment readiness checklist

Before testing and publishing the network, make sure that:

* [ ] All files and data are correctly referenced in the `input.json` file.
* [ ] There are no logical errors in the referenced data.
* [ ] The `/definitions` folder and `input.json` file are packaged into one zip file.
* [ ] The DDF and CSV files are ready for upload.
* [ ] You have the test environment details where you want to publish the protocol. For more information, see [Publishing the protocol](/protocol-guide/test-and-publish/publishing-the-protocol).


# Publishing the protocol

{% hint style="info" %}
Use Postman to perform the steps for publishing. To get the authorization and environment details, contact [tuumio.support@solve.care](mailto:care.support@solve.care)*.*
{% endhint %}

## Fetch MainNet authorization token

Initiate a request with the appropriate details for your environment.

<mark style="color:orange;">**POST**</mark>

{% code overflow="wrap" %}

```
https://{{abc-care-env}}/core-registry-service/oauth/token?grant_type=password&username=%2B{{networkAuthorPhone}}&password={{networkAuthorPassword}}&blockchainAddress={{networkAuthorWalletId}}
```

{% endcode %}

Pre-request script:

{% code title="Example:" %}

```javascript
pm.globals.set("abc-care-env", "dev.env.abc.net");
pm.globals.set("xxx-env", "site000.abc.net/sample-net");


pm.globals.set("networkAuthorPhone", "91888888888");
pm.globals.set("networkAuthorWalletId", "0xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx");
pm.globals.set("networkAuthorPassword", "999999");
pm.globals.set("networkId", "dev-network-xxx");
```

{% endcode %}

## Fetch network authorization token

<mark style="color:orange;">**POST**</mark>

{% code overflow="wrap" %}

```
https://{{eks-env}}/nom/oauth/token?grant_type=exchange_token&exchange_token={{networkAuthorMainNetToken}}
```

{% endcode %}

## Get sponsor address

<mark style="color:green;">**GET**</mark>

```url
https://{{eks-env}}/nom/v2/holders/me
```

Post-request script:

{% code title="Example:" overflow="wrap" %}

```javascript
const jsonData = pm.response.json().nodes;
const networkId = pm.globals.get("networkId");
const node = jsonData.filter(r => r.networkId === networkId && r.roleId === 'NETWORK_SPONSOR')[0];
pm.globals.set("sponsorWalletAddress", node.scAddress);
```

{% endcode %}

## Upload the protocol package

<mark style="color:orange;">**POST**</mark>

{% code overflow="wrap" %}

```url
https://{{eks-env}}/generic-protocol-service/v2/packaging/{{networkId}}/restore/zip
```

{% endcode %}

## Publish the protocol package

<mark style="color:orange;">**POST**</mark>

{% code overflow="wrap" %}

```url
https://{{eks-env}}/generic-protocol-service/v2/packaging/{{networkId}}/publish
```

{% endcode %}

{% code title="Example:" overflow="wrap" %}

```bash
curl --location --globoff 'https://{{eks-env}}/generic-protocol-service/v2/packaging/{{networkId}}/publish' \
--header 'Content-Type: application/json' \
--header 'Authorization: Bearer {{networkAuthorCANToken}}' \
--data '{
    "certificates":"CERT-12345-2022",
    "effectiveDate": "20-05-2022",
    "sponsorWalletAddress": "{{sponsorWalletAddress}}"
    
    

}'
```

{% endcode %}

## Get publishing state

<mark style="color:green;">**GET**</mark>

```
https://{{eks-env}}/generic-protocol-service/v2/packaging/{{networkId}}/{{networkVersion}}
```

{% code title="Example:" overflow="wrap" %}

```bash
curl --location --globoff 'https://{{eks-env}}/generic-protocol-service/v2/packaging/{{networkId}}/{{networkVersion}}' \
--header 'Authorization: Bearer {{networkAuthorCANToken}}'
```

{% endcode %}

## Update TDN

Upload the CSV file with the same attributes as the uploaded DDF in the input folder of the Amazon S3 bucket. If necessary, delete existing data.

### Uploading data definition file (DDF)

The data definition file contains the model and structure for organizing data in TDN.

<mark style="color:orange;">**POST**</mark>

{% code overflow="wrap" %}

```url
https://{{eks-env}}/{{network-id}}/data-node/v1/ddf
```

{% endcode %}

{% code title="Example:" %}

```bash
curl --location 'https://data-node/v1/ddf?status=ACTIVE' \
--header 'Authorization: Basic Y2FyZS1iYWNrZW5kOnNlY3JldA==' \
--header 'Content-Type: application/json' \
--data '{
    "ddf_type": "us-doctors-sample",
    "meta_data": {
        "description": "Sample"
    },
    "messages": [
        {
            "message_category": "CSV",
            "message_type": "Doctors",
            "meta_data": {
                "description": "Sample",
                "indices": "us-doctors-sample"
            },
            "events": [
                {
                    "to_role": "rl-patient",
                    "event": "ev-cdn-broadcast"
                }
            ],
            "attributes": [
                {
                    "name": "Provider",
                    "description": "Provider",
                    "required": false,
                    "index_field": true,
                    "type": "integer",
                    "data_location": "Provider"
                },
                {
                    "name": "License",
                    "description": "License",
                    "required": false,
                    "index_field": true,
                    "type": "string",
                    "data_location": "License"
                },
                {
                    "name": "Specialization",
                    "description": "Specialization",
                    "required": false,
                    "index_field": true,
                    "type": "string",
                    "data_location": "Specialization"
                },
                {
                    "name": "Address",
                    "description": "Address",
                    "required": false,
                    "index_field": true,
                    "type": "string",
                    "data_location": "Address"
                }
            ]
        }
    ]
}'
```

{% endcode %}

### Searching data

<mark style="color:orange;">**POST**</mark>

```
https://{{eks-env}}/{{network-id}}/elasticsearch/us-doctors-sample/_search
```

{% code title="Example:" %}

```bash
curl --location 'https://elasticsearch/us-doctors-sample/_search' \
--header 'Content-Type: application/json' \
--header 'Authorization: Basic ZWxhc3RpYzpweFkwMXNQTXMyZTRTdFp3M2U1MjU5N3U=' \
--data '{

"query": {

"match_all": {}

}

}'
```

{% endcode %}

### Deleting existing data from TDN

<mark style="color:orange;">**POST**</mark>

```
https://{{eks-env}}/{{network-id}}/elasticsearch/us-doctors-sample/_delete_by_query
```

{% code title="Example:" %}

```bash
curl --location 'https://{{eks-env}}/{{network-id}}/elasticsearch/us-doctors-sample/_delete_by_query' \
--header 'Content-Type: application/json' \
--header 'Authorization: Basic ZWxhc3RpYzpweFkwMXNQTXMyZTRTdFp3M2U1MjU5N3U=' \
--data '{

"query": {

"match_all": {}

}

}'
```

{% endcode %}

### Checking the count

<mark style="color:orange;">**POST**</mark>

```
https://{{eks-env}}/{{network-id}}/elasticsearch/us-doctors-sample/_count
```

{% code title="Example:" %}

```bash
curl --location --globoff 'https://{{eks-env}}/{{network-id}}/elasticsearch/us-doctors-sample/_count' \
--header 'Content-Type: application/json' \
--header 'Authorization: Basic ZWxhc3RpYzo5UlBJMTMzNFNydHBOMzI1NFNRcjd4clI=' \
--data '{

"query": {

"match_all": {}

}

}'
```

{% endcode %}


# Testing the app using BrowserStack

1. Open a web browser, and then go to <https://www.browserstack.com/>.
2. Sign in to your account.
3. From the homepage, navigate to **App Live**.
4. Upload the app.
5. Select the operating system and device model.&#x20;
6. Wait for the app to load on the device, then start testing.\
   \
   **Note:** To view event payload and analyze data flow, select the **Network** tab **>** **Enable for all traffic**, and then save the configuration.

{% hint style="info" %}
For more information on testing mobile apps in App Live, see the [BrowserStack documentation](https://www.browserstack.com/docs/app-live).
{% endhint %}


# About TuumIO Wallet

**TuumIO Wallet**\
Your all-in-one companion for managing health, finance, and beyond. TuumIO Wallet connects you to a wide range of app networks, including the powerful Care.Trials, giving you complete control over the healthcare services you choose to use.

Powered by blockchain technology, TuumIO Wallet ensures your data remains secure and private. With no ads and total privacy protection, your information is never accessed, aggregated, brokered, or sold without your consent. Only you can see what's in your TuumIO Wallet—not even TuumIO has access.

**Care.Trials**\
Join groundbreaking clinical trials with TuumIO Wallet. Care.Trials connects you to the latest medical research studies, seeking participants for conditions like cancer, diabetes, mental health, and more. Find local wellness and prevention studies, and take part in the journey toward better medicine.

**Buy SOLVE**\
Easily purchase SOLVE tokens directly in your TuumIO Wallet using traditional payment methods. Choose the amount you want in SOLVE or USD.

**Track Your SOLVE**\
Keep an eye on your SOLVE activity with the SOLVE Transaction Statement, tracking all your interactions within the app network.


# User Access

### Signing up to TuumIO Wallet

1. Open the TuumIO Wallet app from your mobile device.
2. Tap **Create a new TuumIO Wallet**.\
   ![](/files/OJs1d0aiLvcvFQAyCOVy)
3. Allow the app to access your device's location.\
   ![](/files/8QFmrfitO7Z2oPfD2cY6)
4. Choose a method for signing up. Do one of the following:\
   ![](/files/ntnhdfEfehjXpc7udrMq)
   * Choose 'Receive a code via email' to sign up via your email address.\
     ![](/files/71JwxCAVsd1fVdhuIYLI)
   * Choose 'Receive a code on your phone' to sign up via your phone number.\
     ![](/files/iWhUCozO4DicDwha0gmz)
   * Choose 'Continue with Facebook' to sign up using your Facebook account.
5. If necessary, enter the one-time code sent to you, and then proceed.\
   ![](/files/tSen4EnrMoOWLbEc1GGV)
6. Set up a 6-digit Wallet PIN, and then proceed.\
   ![](/files/d0RnSHDXuPch4ZwK1wwh)
7. Allow the app to use biometrics for added security when accessing your account.
8. Use fingerprint scan or facial recognition.
9. Wait a few seconds for your account to be created.

{% hint style="info" %}
Save your recovery phrase and keep it in a safe place. For complete instructions, see Saving your recovery phrase.
{% endhint %}

### Signing up to TuumIO Wallet using Apple ID on iOS device

1. Open the TuumIO Wallet app from your mobile device.
2. Tap **Create a new TuumIO Wallet**.
3. Allow the app to access your device's location.
4. Choose **'Continue with Apple'** method for signing up.\
   ![](/files/2IqqDWJzWhmK1j6Int29)
5. Authorise the app to create account using your Apple ID.
6. Set up a 6-digit Wallet PIN, and then proceed.
7. Wait a few seconds for your account to be created.

### Signing in to TuumIO Wallet

1. Open the TuumIO Wallet app from your mobile device.
2. Tap '**I already have a TuumIO Wallet'**.\
   ![](/files/aIp3Z0zxXQ9dO52Eji8F)
3. Enter your 6-digit PIN, and then proceed.\
   ![](/files/Hj3WoD13vlLlyDj3XduI)
4. If biometrics is enabled, use fingerprint scan or facial recognition.
5. Wait a few seconds for the home screen to load.

### Resetting your passcode

1. Open your TuumIO Wallet app.
2. From the "Login using PIN" screen, tap "**Forgot PIN?**".\
   \
   ![](/files/M8LIk2bME0E3XScWfLjt)\\
3. Enter the one-time code sent to you, and then proceed.\
   ![](/files/TsRRLDPcrez7ee9IMaj3)
4. Set up a new Wallet PIN for your account.\
   ![](/files/X7AkX6Qs5XXeykGtxvoz)

### Saving your recovery phrase

1. Sign in to your TuumIO Wallet app.
2. From the Side Menu screen, tap **Backup**.\
   ![](/files/SHeb21Fgkks3sDcB7d76)
3. Allow access to view the recovery phrase.\
   ![](/files/uRfRfOuY0leGd6Nzdri2)
4. Enter your Wallet PIN, then tap **Next**.
5. Copy the phrase or write it down.\
   ![](/files/31kDYTrRNPAzBXoE8eXu)

{% hint style="info" %}
If you lose your mobile device or uninstall the app, you can use the recovery phrase to restore your access to TuumIO Wallet.
{% endhint %}

### Recovering the access

1. Open the TuumIO Wallet app from your mobile device.
2. Tap '**I already have a TuumIO Wallet'**.
3. Enter your recovery phrase.\
   ![](/files/cM0mplArhU1a6GCTzBkv)
4. Enter your Wallet PIN, and then proceed.\
   ![](/files/oAqh5Gfav42W3JXaO888)
5. Allow the app to use biometrics for added security when accessing your account.
6. Use fingerprint scan or facial recognition.
7. Wait a few seconds for the home screen to load.


# SOLVE Tokens

## Buying SOLVE

1. Sign in to the TuumIO Wallet app.
2. From the bottom navigation bar, tap **FUNDS**.\
   ![](/files/tj8jzvPUc9viZapFFWRv)
3. Select **Buy SOLVE**.\
   ![](/files/B7QHPIqPK1lGqnjhWG3M)
4. Enter the amount in USD.
5. The equivalent amount in SOLVE is calculated automatically.
6. Select the payment method and enter details.\
   ![](/files/qCf9041Fm79kFb8rGXRn)
7. Tap **Buy**.

## Depositing SOLVE

1. Sign in to the TuumIO Wallet app.
2. From the bottom navigation bar, tap **FUNDS**.
3. Select **Deposit SOLVE**.\
   ![](/files/Dlc0LramzjvZvWr2HjnT)
4. Scan the QR code or copy the deposit address.\
   ![](/files/2DFbimI395M8rHY6NvYw)

## Transferring SOLVE

1. Sign in to the TuumIO Wallet app.
2. From the bottom navigation bar, tap **FUNDS**.
3. Select **Transfer/Gift SOLVE**.\
   ![](/files/LAYkRuKG7Q7SCZwROtoW)
4. Enter the amount in SOLVE.
5. Enter the Wallet ID or Scan the QR code of receiver.\
   ![](/files/dbaGjB1u5BDcMhxXkVMo)
6. Tap **Transfer**.
7. Enter your PIN code.\
   ![](/files/IQ0cQzw0Xqn6p9ipAeZw)
8. Tap **Confirm**.

## Paying bills

1. Sign in to the TuumIO Wallet app.
2. From the bottom navigation bar, tap **FUNDS**.
3. Select **Pay Bills**.\
   ![](/files/AeGujtBy64IDtxM3C9KL)
4. Select the bill you want to pay.
5. Send your payment.

## Viewing transactions history

1. Sign in to the TuumIO Wallet app.
2. From the bottom navigation bar, tap **FUNDS**.
3. Select **Transactions History**.\
   ![](/files/2iVKfZHvteyzYBOQDDsC)
4. Select a transaction to view the details.\
   ![](/files/iiJse2PZt4IivNyafONr)


# Caira - AI Assistant

**Caira** is an AI Patient AIdvocate here to provide you with a "wow" experience on Care.Trials. Caira is focused on helping you understand clinical trials and the benefits they offer. Whether it's discovering new opportunities for improving your health or meeting people from different walks of life, Caira is here to assist you with all the information you need about becoming a part of Care.Trials. If you have any questions, feel free to ask!

#### Using Caira Assistant

1. Sign in to the TuumIO Wallet app.
2. From the bottom navigation bar, tap **Caira**.\
   ![](/files/U2fwc3URPTfifS333JAy)\
   \
   ![](/files/JycadH6w5sKsKFOnTlbm)
3. Allow the app to access your device's microphone.\
   ![](/files/yR0NG0y08yfdNfZzxG6j)
4. Share your query to Caira.
5. You will see the result to your requested query.\
   ![](/files/lW9PGNRLvGn77Oi3CS8H)


# User Profile

The Profile screen allows users to view the details they have saved in the application. The following information is displayed:

1. Wallet ID
2. Nickname
3. Country
4. Verification method
5. Financial information

The information is clearly labeled so users understand which details are public, private, or shared only with us. Users can update their nickname and financial information; however, other details cannot be changed.

Users can also view detailed descriptions of each field and learn how their data is being securely stored.

Additionally, users have the option to delete their wallet account if they no longer wish to use the service.

To open the profile screen, tap 'Profile' from the bottom navigation bar.\
![](/files/Kc292ZKqaq7YHJ1yiieP)\
\
![](/files/XYNoWd6NHiPdrTYE6Upm)\
\
![](/files/qsMJePWx5yIKndFB4qLo)


# Care.Trials


# Overview

## Getting started

Participate in clinical trials to help discover new treatments and contribute to medical advancements. Join Care.Trials and search for clinical trials near you.

## Types of roles in Care.Trials

* **Participants** — When you join Care.Trials as a participant, you will have access to available trials that match your profile. Use swiping to like or skip matched trials.
* **Physician** — The physician, also known as principal investigator, helps connect patients to relevant clinical trials. In Care.Trials, the physician can browse trials, refer patients and search for trial sponsors.
* **Site Admin** — The site admin helps coordinate clinical trials in a specific site location. In Care.Trials, the site admin can view leads and interact with the participants.
* **Trial Admin** — The trial admin oversees the clinical trials in all sites. In Care.Trials, the trial admin can activate trials and set the budget for a trial site.
* **Nurse** — The nurse in Care.Trials can review medical records and verify the eligibility of participants.

## Joining the Care.Trials network

1. Sign in to the TuumIO Wallet app.
2. From the CTN Home screen, select the role you want to join.\
   ![](/files/8cyxku7NcZXXGBMlSCQz)
3. Tap any card of the role.\
   ![](/files/OrSxB56mAuCl8d5BvsbA)
4. Please review the terms and conditions.
5. Tap the join button.
6. Wait up to 5 minutes to connect your TuumIO Wallet to the network.


# Participant

### Getting matched for clinical trials

1. Sign in to the TuumIO Wallet app.
2. From the Manage Networks screen, tap **Care.Trials**.
3. Tap **Start Here**.\
   ![](/files/zlW82T9zNQDTrrb2sTI7)
4. To get an overview of the next steps, watch the video. To read the FAQs, tap **Learn more**.\
   ![](/files/smExZPrN2WuLCQW1VC2q)
5. Tap **Start** to proceed\*\*.\*\*
6. Answer the 5 questions to create your profile for matching clinical trials.\
   ![](/files/FRO4rrDiyqJvZQKvgOiw)
7. Agree to the terms and conditions and privacy policy.\
   ![](/files/6EUeTemtb7YoY11BfOhU)
8. Tap **Submit**.
9. Wait up to 5 minutes to search for available trials near you.

### Swiping matched trials

1. Sign in to the TuumIO Wallet app.
2. From the Manage Networks screen, tap **Care.Trials**.
3. Tap **See Trials Near You**.\
   ![](/files/XY5NWoIZ3HBmSI5fnUwB)
4. Swipe left or right to browse through available trials.\
   ![](/files/X3xe7RaR5iDCKGeXBiiQ)
5. Like the trial you want to participate in. You can also skip or go back to the previous trial.

### Uploading your medical records and ID

1. Sign in to the TuumIO Wallet app.
2. From the Manage Networks screen, tap **Care.Trials**.
3. Tap **Records and ID**.\
   ![](/files/wFZL4AFwQLvF6sGGRwOI)
4. Select **Upload records and ID**.\
   ![](/files/fr6wYhIHS5E1DaazLwED)
5. Select the type of attachment you want to upload.\
   ![](/files/IS8LhNrHDuUTEyc1hgHS)
6. Select a file from your device or take a photo.
7. Tap **Upload**.

### Submitting records for review or verification

1. Sign in to the TuumIO Wallet app.
2. From the Manage Networks screen, tap **Care.Trials**.
3. Tap **Records Review and ID Verification**.
4. Select **Records Review and ID Verification**.\
   ![](/files/21e296Bikj7AP0igZZ49)
5. Select the record or ID you want to submit.\
   ![](/files/181HeLgx9wNg8sA6JxhZ)
6. Attach the file, then select your payment option.\
   ![](/files/3Us9HIsRMKYdMrwahK1S)
7. Confirm your payment.

### Viewing records history

1. Sign in to the TuumIO Wallet app.
2. From the Manage Networks screen, tap **Care.Trials**.
3. Tap **Records Review and ID Verification**.
4. Select **Records & ID History**.\
   ![](/files/t9Vw1DuIBzfFbXWmDI39)
5. Select the record or ID that you want to view.\
   ![](/files/2ZyE1MurF8M9Xmr1MOnH)\\

### Managing liked trials

1. Sign in to the TuumIO Wallet app.
2. From the Manage Networks screen, tap **Care.Trials**.
3. Tap **See your Likes and Matches**.\
   ![](/files/V0jDV2uWVYFM595OEfhH)
4. In the "**Trials you liked**" screen, select any of the following:\
   ![](/files/4T27FcgWiXFAlPEkqiH5)
   * **Matched** — View the clinical trials you liked that the site admin has responded to.
   * **No response** — View the clinical trials you liked that the site admin has not yet responded to.
   * **Not a fit** — View trials you liked but don't match your profile.


# Site Admin

### Activating a site

1. Sign in to the TuumIO Wallet app.
2. From the Manage Networks screen, tap **Care.Trials**.
3. Tap **Activate your site**.\
   ![](/files/QULrVP6UHTafY4cXLFEN)
4. Tap **Activate Site**.
5. Tap **Step 1: Request site code.**\
   ![](/files/yi61qVpTmEbWwqACeakv)
6. Enter the Trial ID and the email address where you want the activation code to be sent.\
   ![](/files/0BvHI6tERh55kWAKnMXC)
7. Tap **Request code**. Wait for the activation code to be sent to your email.
8. Tap **Step 2: Activate site role**.\
   ![](/files/TBeuV5c2ETxaAxhZqsEQ)
9. Enter the activation code sent to your email.\
   ![](/files/JX6OZoofe4YbagTr7FH5)
10. Tap **Activate Site**.

### Buying leads

{% hint style="info" %}
In TuumIO Trials, a lead is a potential participant in clinical trials. Make sure you have enough SOLVE balance to buy a lead. For instructions on how to buy SOLVE, see Buying SOLVE tokens.
{% endhint %}

1. Sign in to the TuumIO Wallet app.
2. From the Manage Networks screen, tap **Care.Trials**.
3. Tap **See Your Matches**.\
   ![](/files/5jNqNNJ5f3xoOfZvuhYd)
4. Tap Previous or Skip to browse through matched leads.\
   ![](/files/RDoOpAGnq4kqdHmPYLzt)
5. Tap Buy the lead you want to buy.

### Updating trial info

1. Sign in to the TuumIO Wallet app.
2. From the Manage Networks screen, tap **Care.Trials**.
3. Tap **Activate your site**.\
   ![](/files/1cImBjTQBVhq5i2ra4WH)
4. In the "Active site" list, select the trial you want to update.\
   ![](/files/E3Hh3b2vHgddFyZ3Xcey)
5. Select **Update trial info**.\
   ![](/files/0B8CNNSqvwj32ApdddE3)
6. Fill in the details you want to modify.\
   ![](/files/HepaSNGu9A96JvZ6gQJV)
7. Tap **Update**.

### Upgrade your plan

1. Sign in to the TuumIO Wallet app.
2. From the Manage Networks screen, tap **Care.Trials**.
3. Tap **Activate your site**.\
   ![](/files/c7GtZPiVmdjnrnSopdab)
4. In the "Active site" list, select the trial you want to upgrade plan.\
   ![](/files/AeIDu3Ng7Oj46n5zWoEe)
5. Tap **Upgrade plan**.\
   ![](/files/VpxvHYMJm6gtL26EXNL2)
6. From Explore Plans screen, tap on **Upgrade Plan** button.\
   ![](/files/3WmEQ87kV66dY7piQM9O)
7. Tap on **Confirm** to confirm your payment.\
   ![](/files/huyo1vfjFREuZU2AxA3q)
8. Your plan will be subscribed.\
   ![](/files/fFMCbSylMQr3kgSwmglu)

### Buying campaigns

{% hint style="info" %}
You must upgrade your plan in order to buy campaigns.
{% endhint %}

1. Sign in to the TuumIO Wallet app.
2. From the Manage Networks screen, tap **Care.Trials**.
3. Tap **Activate your site**.\
   ![](/files/cwERH2vtBUdsT4OGhfGm)
4. In the "Active site" list, select the trial you want to update.
5. Tap **Buy campaign**.\
   ![](/files/JQxORhP9RWlEZ98qPmBr)
6. View each campaign card to see more details.\
   ![](/files/8SJRS6oFoRCaV61x5hEz)
7. Tap **Buy Now**, then confirm your payment.

### Requesting budget

1. Sign in to the TuumIO Wallet app.
2. From the Manage Networks screen, tap **Care.Trials**.
3. Tap **Activate your site**.\
   ![](/files/U1eJ84vpetXMu9sGKmNa)
4. In the "Active site" list, select the trial you want to update.
5. Tap **Track Budget > Request budget**.\
   ![](/files/5o0CPwvSyL8lbOouJkdg)\
   \
   ![](/files/iYuJdvAFl2iQUCiVLoO2)
6. Enter the amount, then add a comment.\
   ![](/files/QEla38REXu0jF5ZV9OlL)
7. Tap **Request**.

### Checking statistics

1. Sign in to the TuumIO Wallet app.
2. From the Manage Networks screen, tap **Care.Trials**.
3. Tap **Activate your site**.\
   ![](/files/QtS0DQLtvVKFFLQukdh4)
4. In the "Active site" list, select a trial.
5. Tap **Check statistics > Update data.**\
   ![](/files/pU9WLuioLUhFSdqip79e)\
   \
   ![](/files/iJbi5hGKtuJtAPKQI5sr)

### Connecting with the lead

1. Sign in to the TuumIO Wallet app.
2. From the Manage Networks screen, tap **Care.Trials**.
3. Tap **Connect and Engage**.\
   ![](/files/QqOFS9Wz1AMe8UZRAsm1)
4. In Purchased Leads, select the lead you want to connect with.\
   ![](/files/fMJKMyzD4oVF3lW5LbS6)
5. In the "Connect with the Lead" section, do any of the following:\
   ![](/files/8PGUjDfBdPNDkQTLY0NW)
   * **Share trial info** — Share the details about the trial with the participant.
   * **Participant records & ID** — Request records and ID from the participant.
   * **Ask a question** — Send questions to the participant.
   * **Set an appointment** — Send an appointment request to the participant containing the trial facility details.

### Submitting records to Nurse for review and verification

1. Sign in to the TuumIO Wallet app.
2. From the Manage Networks screen, tap **Care.Trials**.
3. Tap **Connect and Engage**.\
   ![](/files/JhN2biA1hIlKAlehw3rs)
4. In Purchased Leads, select the lead you want to connect with.
5. In the "Connect with the Lead" section, tap **Participant records & ID**.\
   ![](/files/iC7HCeNB6Sk1dAiyfiR4)
6. Tap **Submit for review & verification**.\
   ![](/files/u7HxF2PJO7n9AYWJJzqx)
7. Select the record you want to submit for review or verification.
8. Tap **Submit to Nurse**.\
   ![](/files/hZl7GHf4m679vXzYPyMO)


# Trial Admin

### Activating a trial

1. Sign in to the TuumIO Wallet app.
2. From the Manage Networks screen, tap **Care.Trials**.
3. Tap **Start Here**.\
   ![](/files/tIVmqZpA4P4zO9Eft8Fc)
4. Tap **Activate Trial**.
5. Tap **Step 1: Request admin code.**\
   ![](/files/ELQ7NQY8CEGOKh4y8kc3)
6. Enter the Trial ID and the email address where you want the activation code to be sent.\
   ![](/files/aGzw9I3axhxxgTnU3TDw)
7. Tap **Request code**. Wait for the activation code to be sent to your email.
8. Tap **Step 2: Activate admin role**.\
   ![](/files/swQNGKZart0zl3wuFIun)
9. Enter the activation code you received in Step 1.\
   ![](/files/rKWb94UDuM6rzfsUYsxQ)
10. Tap **Activate**.

### Updating trial info

1. Sign in to the TuumIO Wallet app.
2. From the Manage Networks screen, tap **Care.Trials**.
3. Tap **Start Here**.\
   ![](/files/q8duJ1fnuNgizsNoRm7a)
4. In the "Active trials" list, select the trial you want to update.\
   ![](/files/Kk9FOxRSBx5CN8DUPnyD)
5. Select **Update trial info**.\
   ![](/files/QlMlIawdDzAXZ6ZyKMz8)
6. Fill in the details you want to modify.\
   ![](/files/53Q6DJflZgPELtxtcxmo)
7. Tap **Update**.

### Setting the budget

1. Sign in to the TuumIO Wallet app.
2. From the Manage Networks screen, tap **Care.Trials**.
3. Tap **Manage Sites**.\
   ![](/files/i09KboW8Ck6BLPhA52Pr)
4. Select the site you want to update.
5. Tap **View budget requests**.\
   ![](/files/aYnD8u9RbsVijKUzJbof)
6. Select the site and the budget request you want to view.\
   ![](/files/9jp05tCj1TzDgVMvfMmU)\
   \
   ![](/files/rJOCdg5e1LkxFOzPt8ku)
7. To approve the request, tap **Set Budget**.\
   ![](/files/Gf5UEdhlOIZ0byNUu4jM)
8. Enter the amount in SOLVE, then add a comment.\
   ![](/files/QykvmZNwIZ4H4HEq0V2c)
9. Tap **Submit**.

### Checking the site statistics

1. Sign in to the TuumIO Wallet app.
2. From the Manage Networks screen, tap **Care.Trials**.
3. Tap **Manage Sites**.\
   ![](/files/Yl35EWqknO6FjLeW6qLi)
4. Select the site you want to update.
5. Tap **Check site statistics > Update**.\
   ![](/files/HBHSBm7HR6XBLRaJRsLm)\
   \
   ![](/files/sAhqMjxYz0cZmsxQx71y)


# Physician

### Verifying ID and medical license

1. Sign in to the TuumIO Wallet app.
2. From the Manage Networks screen, tap **Care.Trials**.
3. Tap **Verify your identity > Verify your identity**.\
   ![](/files/4sC5UJ9xrbYc0IiuSeJ8)\
   \
   ![](/files/dFxgvUTuRitVP4QFy2YH)
4. Enter your full name, then upload your ID or medical license.\
   ![](/files/Q0ju39Em1VTRoIsUzdO0)
5. Tap **Submit**.

### Viewing history of submitted IDs

1. Sign in to the TuumIO Wallet app.
2. From the Manage Networks screen, tap **Care.Trials**.
3. Tap **Verify your identity > ID history**.\
   ![](/files/Hcu69OlJfFufJqaqvD24)
4. Select the ID record details that you want to view.\
   ![](/files/YTxBe5N7lNnEQeGUpsbb)\
   \
   ![](/files/CmwthwwPViy3b8RYyuCs)


# Nurse

### Reviewing ID and medical records

1. Sign in to the TuumIO Wallet app.
2. From the Manage Networks screen, tap **Care.Trials**.\
   ![](/files/HvxI45YPjbAE2RtxFh9t)
3. Tap **Manage the Records > Pending record review**.\
   ![](/files/cqV4PSGGuy6djqmSTgRT)\
   \
   ![](/files/9ZKUJcB1Wxbuk2Ablsmm)
4. Review the attached records, then fill in the participant details.\
   ![](/files/ZU08mZuBUvs77ABUdQuz)\
   \
   ![](/files/0fyYQjnhIwuzUAv9RgVW)
5. Approve or reject the records.

### Viewing history of reviewed records

1. Sign in to the TuumIO Wallet app.
2. From the Manage Networks screen, tap **Care.Trials**.
3. Tap **Record** **> Reviewed records**.\
   ![](/files/jKFLTtxGBdIQ0YTNQWbl)
4. Select the record details you want to view.\
   ![](/files/ckNmidog3JqB3nhvaqOQ)\
   \
   ![](/files/8K7ZZq3HKqCpgcCDOUSd)

### Reviewing lead eligibility

1. Sign in to the TuumIO Wallet app.
2. From the Manage Networks screen, tap **Care.Trials**.
3. Tap **Review Trials Liked by Leads > Pending Review**.\
   ![](/files/y0yMG5JBjHPei3pnHVCv)\
   \
   ![](/files/Vcc4GfrBPXGvvW99r6e7)
4. Select the lead you want to review.
5. Do either of the following:\
   ![](/files/A0kknZpGoryWwedhk40a)
   * View the details of the trial
   * Ask a question to the lead
6. Approve or reject the lead.

### Viewing lead verification details

1. Sign in to the TuumIO Wallet app.
2. From the Manage Networks screen, tap **Care.Trials**.
3. Tap **Review Trials Liked by Leads > Reviewed Leads**.\
   ![](/files/Z3PJBeeYVlEvUwAJN7iv)
4. Select the lead verification details that you want to view.\
   ![](/files/wltqOMArAJArChGvMaPD)\
   \
   ![](/files/1lwrXcnKoYO0pzkeEDd2)


# Create an Event Booker

## Overview

Welcome to the Event Booker example, a simple booking app for events or appointments. The underlying structure can be adapted for Web3 integration, allowing you to extend the app's functionality such as using tokens to pay booking fees for exclusive events.\
\
Here’s how the app works:

1. Launch the app to book an event or appointment.
2. Fill in the details of the event or appointment.
3. Confirm and submit your booking details.

## Steps

Ready to create your own booking app? Follow these steps:

### 1. Define the structure&#x20;

Open the `input.json` file in a text editor, then add the journey definition:

{% code title="input.json" overflow="wrap" %}

```json
            {
                "id": "jn-event-booker",
                "icon": "https://i.ibb.co/7N134gb/booking.png",
                "name": "Book an Event",
                "description": "Book an Event",
                "status": "Active",
                "start_card_ref_id": "cd-book-an-event",
                "roles": [
                    "rl-member"
                ],
                "journey_type": "STANDARD_JOURNEY"
            }
```

{% endcode %}

Define the included [cards](/protocol-guide/build-a-dapp/card-definitions#cards):

{% code title="input.json" overflow="wrap" %}

```json
            {
                "id": "cd-book-an-event",
                "name": "Book an Event",
                "description": "Book an Event",
                "status": "Active",
                "card_definition_ref": "card/cd-book-an-event.json",
                "side": "PUBLIC",
                "role": "rl-member",
                "transaction_data_ref": "td/td-BOOKING-DETAILS.json",
                "private_card": "",
                "base_card": "base-card-1",
                "journey": "jn-event-booker",
                "outgoing_events": [
                    "e-w-navig-to-details"   
                ],
                "pre_rendering_events": [],
                "post_rendering_events": []
            },
            {
                "id": "cd-set-booking-details",
                "name": "Booking Details",
                "description": "Booking Details",
                "status": "Active",
                "card_definition_ref": "card/cd-set-booking-details.json",
                "side": "PUBLIC",
                "role": "rl-member",
                "transaction_data_ref": "td/td-BOOKING-DETAILS.json",
                "private_card": "",
                "base_card": "base-card-1",
                "journey": "jn-event-booker",
                "outgoing_events": [
                    "e-w-broad-shareAppt",
                    "e-w-navig-to-book-1"
                ],
                "pre_rendering_events": [],
                "post_rendering_events": []
            }
```

{% endcode %}

Define the included [events](/protocol-guide/build-a-dapp/events-and-event-handlers#events):

{% code title="input.json" %}

```json
            {
                "id": "e-w-navig-to-details",
                "name": "W-NAVIG-TO-SET",
                "description": "Event to Navigate from Book an Event to next card",
                "code": "W-NAVIG-TO-SET",
                "status": "Active",
                "type": "WALLET_LOCAL",
                "event_definition_ref": "event/e-w-navig-to-details.json",
                "submit_event_handler": "eh-w-navig-to-details",
                "node_event_handlers": [],
                "card": "cd-book-an-event"                
            },            
			{
                "id": "e-w-navig-to-book-1",
                "name": "W-NAVIG-TO-BOOK-EVT",
                "description": "Event to Navigate from Set Booking to first card",
                "code": "W-NAVIG-TO-BOOK-EVT",
                "status": "Active",
                "type": "WALLET_LOCAL",
                "event_definition_ref": "event/e-w-navig-to-book-1.json",
                "submit_event_handler": "eh-w-navig-to-book-1",
                "node_event_handlers": [],
                "card": "cd-set-booking-details"
            },
            {
                "id": "e-w-broad-shareAppt",
                "name": "W-BROAD-SHAREAPPT",
                "description": "Submit UDETAILS",
                "code": "W-BROAD-SHAREAPPT",
                "status": "Active",
                "type": "WALLET_TO_NODE",
                "event_definition_ref": "event/e-w-broad-shareAppt.json",
                "submit_event_handler": "eh-w-e-w-broad-shareAppt",
                "node_event_handlers": [
                    "eh-h-e-w-broad-shareAppt"
                ],
                "card": "cd-set-booking-details"
            }
```

{% endcode %}

Define the included [event handlers](/protocol-guide/build-a-dapp/events-and-event-handlers#event-handlers):

{% code title="input.json" %}

```json
            {
                "id": "eh-w-navig-to-details",
                "name": "W-NAVIG-TO-SET",
                "description": "Wallet Event Handler to Navigate from Book an Event to next card",
                "status": "Active",
                "event": "e-w-navig-to-details",
                "type": "WALLET_EVENT_HANDLER",
                "event_handler_definition_ref": "event-handler/eh-w-navig-to-details.json"
            },
            {
                "id": "eh-w-navig-to-book-1",
                "name": "W-NAVIG-TO-BOOK-EVT",
                "description": "Wallet Event Handler to Navigate from Set Booking Details to first card",
                "status": "Active",
                "event": "e-w-navig-to-book-1",
                "type": "WALLET_EVENT_HANDLER",
                "event_handler_definition_ref": "event-handler/eh-w-navig-to-book-1.json"
            },
            {
                "id": "eh-h-e-w-broad-shareAppt",
                "name": "eh-h-e-w-broad-shareAppt",
                "description": "Broadcast UDETAILS",
                "status": "Active",
                "event": "e-w-broad-shareAppt",
                "type": "NODE_EVENT_HANDLER",
                "event_handler_definition_ref": "event-handler/eh-h-e-w-broad-shareAppt.json"
            }     
```

{% endcode %}

### 2. Create the card definitions

Create the definitions for the start card: `cd-book-an-event.json` and the next card: `cd-set-booking-details.json`.

{% code title="cd-book-an-event.json" %}

```json
{
    "id": "cd-book-an-event",
    "name": "Book an Event",
    "cardData": {
        "textforbookevent": "Book an event",
        "imageUrlzkk3n12": "https://abc-rep.net/arrow-right blue.png",

    }, 
    "cardLayout": {
        "body": [
            {
                "id": "000t1",
                "tileComponent": [
                    {
                        "id": "Tile14",
                        "subView": [
                            {
                                "title": {
                                    "text": "textforbookevent",
                                    "fontSize": 16,
                                    "titleTextColor": "#000080",
                                    "style": "REGULAR"
                                },
                                "img": {
                                    "text": "imageUrlzkk3n12",
                                    "isUrl": true,
                                    "height": "25",
                                    "width": "25"
                                }
                            }
                        ],
                        "borderColor": "#C5C3C8",
                        "backgroundColor": "#ffffff",
                        "borderWidth": 3,
                        "type": "CONTAINER",
                        "uiAction": "${action502}",
                        "order": 3
                    }
                ],
                "tileType": "WRAP",
                "uiAction": "",
                "order": 1
            }
        ],
        "style": {
            "fontSize": 16,
            "bgColor": "#ffffff",
            "borderWidth": 1
        },
        "footer": {
            "menu": [
                {
                    "id": "EN01BottomButtonBack",
                    "subView": [
                        {
                            "title": {
                                "text": ""
                            }
                        }
                    ],
                    "align": "START",
                    "type": "BACK_BUTTON",
                    "uiAction": "${action478}",
                    "order": 1
                }
            ],
            "orientation": "HORIZONTAL"
        }
    },
    "cardUIAction": {
        "action478": {
            "action": ""
        },
        "action502": {
            "action": "e-w-navig-to-details" 
        }
    }
}   
```

{% endcode %}

{% code title="cd-set-booking-details.json" %}

```json
{
    "id": "cd-set-booking-details",
    "name": "Booking Details",
    "cardData": {
        "0tile0iitextiiiw8": "Enter the details for your booking.",
        "2en01bottombutton1iitextiilor": "Send",
        "1tile1iitextiiixo1": "Location",
        "1tile1iihintii6km1": "e.g. London, UK",
        "1tile1iierrorii6se1": "",
        "1tile1iitextiiixo2": "Date",
        "1tile1iihintii6km2": "e.g. Day 1, Day 2",
        "1tile1iierrorii6se2": "",
        "1tile1iitextiiixo3": "Time",
        "1tile1iihintii6km3": "e.g. 2 p.m. EST",
        "1tile1iierrorii6se3": "",
        "tile1iitextiiixop": "Purpose",
        "1tile1iihintii6kmp": "e.g. Comic Convention",
        "1tile1iierrorii6sep": "" 
    }, 
    "cardLayout": {
        "body": [
            {
                "id": "000t1",
                "tileComponent": [
                    {
                        "id": "Tile0",
                        "subView": [
                            {
                                "title": {
                                    "text": "0tile0iitextiiiw8",
                                    "style": "BOLD",
                                    "titleTextColor": "#000080",
                                    "titleAlign": "START",
                                    "fontSize": 16
                                }
                            }
                        ],
                        "borderColor": "#C5C3C8",
                        "backgroundColor": "#ffffff",
                        "borderWidth": 1,
                        "type": "CONTAINER",
                        "uiAction": "",
                        "order": 1
                    },
                    {
                        "id": "Tile1a",
                        "subView": [
                            {
                                "title": {
                                    "text": "1tile1iitextiiixo",
                                    "titleTextColor": "#000080",
                                    "titleAlign": "JUSTIFY"
                                },
                                "subTitle": {
                                    "text": "{$apptInfo}",
                                    "hint": "1tile1iihintii6km",
                                    "subTitleTextColor": "#000080",
                                    "subTitleAlign": "START",
                                    "keyboard": "text",
                                    "min": "1",
                                    "max": "1000",
                                    "validation": [
                                        {
                                            "name": "REQUIRED_FIELD",
                                            "error": "1tile1iierrorii6se"
                                        }
                                    ]
                                }
                            }
                        ],
                        "borderColor": "#C5C3C8",
                        "type": "CONTAINER",
                        "uiAction": "",
                        "order": 4
                    },
                    {
                        "id": "Tile1a",
                        "subView": [
                            {
                                "title": {
                                    "text": "tile1iitextiiixop",
                                    "titleTextColor": "#000080",
                                    "titleAlign": "JUSTIFY"
                                },
                                "subTitle": {
                                    "text": "{$apptPurpose}",
                                    "hint": "1tile1iihintii6kmp",
                                    "subTitleTextColor": "#000080",
                                    "subTitleAlign": "START",
                                    "keyboard": "text",
                                    "min": "1",
                                    "max": "1000",
                                    "validation": [
                                        {
                                            "name": "REQUIRED_FIELD",
                                            "error": "1tile1iierrorii6sep"
                                        }
                                    ]
                                }
                            }
                        ],
                        "borderColor": "#C5C3C8",
                        "type": "CONTAINER",
                        "uiAction": "",
                        "order": 4
                    },
                    {
                        "id": "Tile1a",
                        "subView": [
                            {
                                "title": {
                                    "text": "1tile1iitextiiixo1",
                                    "titleTextColor": "#000080",
                                    "titleAlign": "JUSTIFY"
                                },
                                "subTitle": {
                                    "text": "{$apptLocation}",
                                    "hint": "1tile1iihintii6km1",
                                    "subTitleTextColor": "#000080",
                                    "subTitleAlign": "START",
                                    "keyboard": "text",
                                    "min": "1",
                                    "max": "1000",
                                    "validation": [
                                        {
                                            "name": "REQUIRED_FIELD",
                                            "error": "1tile1iierrorii6se1"
                                        }
                                    ]
                                }
                            }
                        ],
                        "borderColor": "#C5C3C8",
                        "type": "CONTAINER",
                        "uiAction": "",
                        "order": 4
                    },
                    {
                        "id": "Tile1a",
                        "subView": [
                            {
                                "title": {
                                    "text": "1tile1iitextiiixo2",
                                    "titleTextColor": "#000080",
                                    "titleAlign": "JUSTIFY"
                                },
                                "subTitle": {
                                    "text": "{$apptDays}",
                                    "hint": "1tile1iihintii6km2",
                                    "subTitleTextColor": "#000080",
                                    "subTitleAlign": "START",
                                    "keyboard": "text",
                                    "min": "1",
                                    "max": "1000",
                                    "validation": [
                                        {
                                            "name": "REQUIRED_FIELD",
                                            "error": "1tile1iierrorii6se2"
                                        }
                                    ]
                                }
                            }
                        ],
                        "borderColor": "#C5C3C8",
                        "type": "CONTAINER",
                        "uiAction": "",
                        "order": 4
                    },
                    {
                        "id": "Tile1a",
                        "subView": [
                            {
                                "title": {
                                    "text": "1tile1iitextiiixo3",
                                    "titleTextColor": "#000080",
                                    "titleAlign": "JUSTIFY"
                                },
                                "subTitle": {
                                    "text": "{$apptTime}",
                                    "hint": "1tile1iihintii6km3",
                                    "subTitleTextColor": "#000080",
                                    "subTitleAlign": "START",
                                    "keyboard": "text",
                                    "min": "1",
                                    "max": "1000",
                                    "validation": [
                                        {
                                            "name": "REQUIRED_FIELD",
                                            "error": "1tile1iierrorii6se3"
                                        }
                                    ]
                                }
                            }
                        ],
                        "borderColor": "#C5C3C8",
                        "type": "CONTAINER",
                        "uiAction": "",
                        "order": 4
                    }
                ],
                "tileType": "WRAP",
                "uiAction": "",
                "order": 1
            }
        ],
        "style": {
            "fontSize": 16,
            "bgColor": "#ffffff",
            "borderWidth": 1
        },
        "footer": {
            "menu": [
                {
                    "id": "EN01BottomButtonBack",
                    "subView": [
                        {
                            "title": {
                                "text": ""
                            }
                        }
                    ],
                    "align": "START",
                    "type": "BACK_BUTTON",
                    "uiAction": "${action461}",
                    "order": 1
                },
                {
                    "id": "EN01BottomButton1",
                    "subView": [
                        {
                            "title": {
                                "text": "2en01bottombutton1iitextiilor"
                            }
                        }
                    ],
                    "align": "START",
                    "type": "BUTTON",
                    "uiAction": "${action420}",
                    "order": 2
                }
            ],
            "orientation": "HORIZONTAL"
        }
    },
    "cardUIAction": {
        "action461": {
            "action": "e-w-navig-to-book-1"
        },
        "action420": {
            "action": "e-w-broad-shareAppt" 
        }
    }
}   
```

{% endcode %}

### 3. Create the event definitions

Create the definition for the event to navigate from start card to the next card: `e-w-navig-to-details.json`.

{% code title="e-w-navig-to-details.json" %}

```json
{
    "definition": {
        "description": "Event to Navigate from Book an Event to next card",
        "name": "W-NAVIG-TO-SET",
        "resource": "W-NAVIG-TO-SET",
        "type": "EVENT_DATA"
    },
    "structure": {
        "attributes": [
            {
                "code": "transactionalGuid",
                "name": "transactionalGuid",
                "type_definition": {
                    "type": "string"
                },
                "order": 1,
                "system": false,
                "required": false
            }
        ]
    }
}
```

{% endcode %}

Create the definition for the submit event that contains the data for the booking details: `e-w-broad-shareAppt.json`.

{% code title="e-w-broad-shareAppt.json" %}

```json
{
    "definition": {
        "description": "Submit Booking Details",
        "name": "W-BROAD-SHAREAPPT",
        "resource": "W-BROAD-SHAREAPPT",
        "type": "EVENT_DATA"
    },
    "structure": {
        "attributes": [
            {
                "name": "apptInfo",
                "code": "apptInfo",
                "type_definition": {
                    "type": "string"
                },
                "required": true,
                "system": false,
                "order": 1
            },
            {
                "name": "apptPurpose",
                "code": "apptPurpose",
                "type_definition": {
                    "type": "string"
                },
                "required": true,
                "system": false,
                "order": 2
            },
            {
                "name": "apptLocation",
                "code": "apptLocation",
                "type_definition": {
                    "type": "string"
                },
                "required": true,
                "system": false,
                "order": 3
            }, 
            {
                "name": "apptDays",
                "code": "apptDays",
                "type_definition": {
                    "type": "string"
                },
                "required": true,
                "system": false,
                "order": 4
            },
            {
                "name": "apptTime",
                "code": "apptTime",
                "type_definition": {
                    "type": "string"
                },
                "required": true,
                "system": false,
                "order": 5
            },
            {
                "name": "senderNodeAddress",
                "code": "senderNodeAddress",
                "type_definition": {
                    "type": "string"
                },
                "required": true,
                "system": false,
                "order": 7
            }
        ]
    }
}
```

{% endcode %}

Create the definition for the next navigation event after submitting details: `e-w-navig-to-book-1.json`.

{% code title="e-w-navig-to-book-1.json" %}

```json
{
  "definition": {
    "description": "Event to Navigate from Set Booking Details to first card",
    "name": "W-NAVIG-TO-BOOK-EVT",
    "resource": "W-NAVIG-TO-BOOK-EVT",
    "type": "EVENT_DATA"
  },
  "structure": {
    "attributes": [
      {
        "code": "transactionalGuid",
        "name": "transactionalGuid",
        "type_definition": { "type": "string" },
        "order": 1,
        "system": false,
        "required": false
      }
    ]
  }
}

```

{% endcode %}

### 4. Create the event handler definitions

Create the event handler definition for the navigation event with booking details: `eh-w-navig-to-details.json`.

{% code title="" %}

```json
{
    "walletEventHandler": [
        {
            "refId": "e-w-navig-to-details",
            "walletEvents": [
                {
                    "actions": [
                        {
                            "name": "submit",
                            "order": 1,
                            "parameter": [
                                {
                                    "method": "DETAILS",
                                    "url": ""
                                }
                            ]
                        }
                    ],
                    "postAction": "cd-set-event-details",
                    "refId": "e-w-navig-to-details"
                }
            ]
        }
    ]
}
```

{% endcode %}

Create the event handler definition for saving data to the `BOOKING_DETAILS` collection: `eh-h-e-w-broad-shareAppt.json`. This node event handler also appends attributes to the payload.

{% code title="eh-h-e-w-broad-shareAppt.json" %}

```json
{
    "nodeEventHandlers": [
        {
            "type": "MAPPER",
            "name": "Append attributes",
            "order": 1,
            "dataSource": "EVENT_PAYLOAD",
            "additionalAttributes": {
                "transactionalGuid": {
                    "source": "GENERATED",
                    "value": "UUID" 
                },
                "leadNodeAddress": {
                    "source": "EVENT_PAYLOAD",
                    "value": "senderNodeAddress"
                },
                "apptInfo": {
                    "source": "EVENT_PAYLOAD",
                    "value": "apptInfo"
                },
                "apptPurpose": {
                    "source": "EVENT_PAYLOAD",
                    "value": "apptPurpose"
                },
                "apptLocation": {
                    "source": "EVENT_PAYLOAD",
                    "value": "apptLocation"
                },
                "apptWorkDays": {
                    "source": "EVENT_PAYLOAD",
                    "value": "apptDays"
                },
                "apptWorkHours": {
                    "source": "EVENT_PAYLOAD",
                    "value": "apptTime"
                },
                "createdAt": {
                    "source": "GENERATED",
                    "value": "CURRENT_TIMESTAMP"
                },
                "updatedAt": {
                    "source": "GENERATED",
                    "value": "CURRENT_TIMESTAMP"
                }
            },
            "excludedAttributes": [
                "senderNodeAddress"
            ]
        },
        {
            "type": "EXPRESSION_LANGUAGE",
            "name": "Append attributes",
            "order": 2,
            "dataSource": "HANDLER_ARGUMENTS",
            "computedAttributes": {
                "submittedAt": "\"Received on: \" + new java.text.SimpleDateFormat(\"dd/MM/yyyy\").format(new java.util.Date(arguments['createdAt']))"            }
        },
        {
            "type": "VAULT_INSERT",
            "name": "BOOKING_DETAILS",
            "order": 3,
            "collection": "BOOKING_DETAILS",
            "collectionVersion": 1,
            "dataSource": "HANDLER_ARGUMENTS",
            "handlerOutput": "PERSISTED_ENTITY"
        },
        {
            "type": "NEXT_EVENT_RECIPIENT",
            "name": "Fetch sender address",
            "order": 4,
            "recipientAddress": {
                "source": "EVENT_PAYLOAD",
                "value": "senderNodeAddress"
            },
            "handlerOutput": "HANDLER_ARGUMENTS"
        },
        {
            "type": "MAPPER",
            "name": "Append and Exclude attributes in the result",
            "order": 5,
            "dataSource": "EVENT_PAYLOAD",
            "additionalAttributes": {
                "transactionalGuid": {
                    "source": "HANDLER_ARGUMENTS",
                    "value": "transactionalGuid"
                },
                "submittedAt": {
                    "source": "HANDLER_ARGUMENTS",
                    "value": "submittedAt"
                },
                "apptInfo": {
                    "source": "EVENT_PAYLOAD",
                    "value": "apptInfo"
                },
                "apptPurpose": {
                    "source": "EVENT_PAYLOAD",
                    "value": "apptPurpose"
                },
                "apptLocation": {
                    "source": "EVENT_PAYLOAD",
                    "value": "apptLocation"
                },
                "apptWorkDays": {
                    "source": "EVENT_PAYLOAD",
                    "value": "apptDays"
                },
                "apptWorkHours": {
                    "source": "EVENT_PAYLOAD",
                    "value": "apptTime"
                }
            },
            "excludedAttributes": [
                "createdAt",
                "updatedAt",
                "leadNodeAddress",
                "senderNodeAddress"
            ]
        }
    ]
}
```

{% endcode %}

Create the event handler definition for the navigation event after submitting booking details: `eh-w-navig-to-book-1.json`. The booking details are fetched from the data collection: `td/td-BOOKING_DETAILS`.

{% code title="eh-w-navig-to-book-1.json" %}

```json
{
    "walletEventHandler": [
        {
            "refId": "e-w-navig-to-book-1",
            "walletEvents": [
                {
                    "actions": [
                        {
                            "name": "submit",
                            "order": 1,
                            "parameter": [
                                {
                                    "method": "GET",
                                    "url": "/transactions/BOOKING_DETAILS"
                                }
                            ]
                        }
                    ],
                    "postAction": "cd-book-an-event",
                    "refId": "e-w-navig-to-book-1" 
                }
            ]
        }
    ]
}
```

{% endcode %}


# Create a Library Explorer

## Overview

Welcome to the Library Explorer example, an app designed for exploring educational materials in a digital library. The underlying structure can be adapted for Web3 integration, allowing you to extend the app's functionality such as minting non-fungible tokens (NFTs) for digital content like e-books.

Here's how the app works:

1. Launch the app.
2. Fill in the details of the material that match your interest (title, author, subject).
3. Browse the catalog of recommended materials.

## Steps


# Support

## :e-mail: Need Help?

Our support team is here for you! Reach out at <SupportTeam@tuumio.com>.

## :robot: Ask the Community

Join the conversation:

* [Telegram](https://t.me/TuumIO)
* [Discord](https://discord.gg/Bh52GthxX4)


