Skip to content

Latest commit

 

History

History
927 lines (700 loc) · 33.4 KB

index.md

File metadata and controls

927 lines (700 loc) · 33.4 KB

Quick Start

Prerequisites

csx (Chainsight command-line execution envirionment) depends on several tools. Therefore, developers must have these tools installed and available in advance.

  • rust: To generate Canister code to be compiled into Module
  • dfx: To interact with Internet Computer

You can confirm that it has been installed and is in the path by running the following in a terminal.

% rustc --version 
rustc 1.76.0 (07dca489a 2024-02-04)
% dfx --version
dfx 0.15.1

Note

Before you can deploy on your local machine, you need to deploy chainsight-management-canisters to your local dfx environment.

  git clone https://github.com/horizonx-tech/chainsight-management-canisters.git
  cd chainsight-management-canisters/artifacts
  make all port=${YOUR_DFX_PORT}

Install CLI

You can choose between the following two methods of installation.

  • Download the prebuild CLI binaries
  • Build the CLI from source code

Once you have followed either of these steps to install, you can confirm the installation with the following command.

csx --version
# -> csx version: x.y.z

Warning
Currently only macos and linux environments are supported.
This is a limitation of the dfx specification on which it depends.

Download the prebuild CLI binaries

Install and path the binary file according to your terminal from the following

Releases · horizonx-tech/chainsight-cli

Build the CLI from source code

Clone this repository and run cargo build.

cd horizonx-tech/chainsight-cli && cargo build --release && cargo install --path .

Quick Start for your project

A small modification to the Manifest, which is placed when the project is initially generated, is all that is required to create a deployable component.

Let's actually create a project/component with the project name 'initial_project'.
The 'new' command can be used to create a project with a specified project name.

# Create Chainsight project
csx new initial_project

Then modify the manifest. Specifically, modify the rpc_url key to match your project.

Once the manifest is corrected to the correct one, the 'build' command can be executed to generate the module and execution commands to run canister.

# Build project
csx build --path initial_project

If the build command succeeds, deploy with the 'deploy' command.
Remember to have a dfx network in your local area when deploying locally.

# Deploy project
# NOTE: If you deploy in local, dfx network must be started (ex: 'dfx start')
dfx start
csx deploy

When 'deploy' is complete, the 'exec' command sends the actual initialization and start of periodic execution instructions to the component.

# Initialize Components / Start processing
csx exec --path initial_project

Terminology

Manifest

Use Manifest to actually tell Chainsight what the developer wants to customize.

Specifically, this is a YAML file, and the developer's intent can be reflected by having the values set according to the format specified on the Chainsight side.

Currently, the following types of Manifest are available.

  • Component Manifest
  • Project Manifest

Component

A Canister that contains a Module specialized for the data processes managed within the Chainsight Platform.

Chainsight defines several types of canisters specialized for certain applications, allowing users to select the type that best suits their needs and to freely customize items within that type.

The following Components are currently available on the CLI.

  • Snapshot Indexer
    • Select the following types depending on the location of the data you wish to collect
      • Snapshot Indexer EVM: For EVM-based Other chains
      • Snapshot Indexer ICP: Other canisters on Internet Computer
      • Snapshot Indexer HTTPS: Resources available on the general web
  • Event Indexer
  • Algorithm Indexer
  • Algorithm Lens
  • Relayer

Note
See following for all supported Component Types and their purpose.
Data Processing Components - Chainsight Network

Project

Manage one or more Components together.

For example, at least Snapshot Indexer and Relayer are required to take a snapshot of ERC20's totalSupply obtained from Ethereum and flow it to other Chains.

Most objectives require combining multiple Components, and Project is provided to make them easier to manage.

Project consists of the following folders.
However, these are not usually necessary to be aware of.

(project root)
|- artifacts # Artifacts generated by 'build' process
|- components # Place Component Manifest
|- interfaces # Place dependent interfaces (abi etc.)
|- project.yaml # Project Manifest
.chainsight

These are the Internet Computer concepts needed to better understand Chainsight

HTTPS outcalls

HTTPS outcalls in the Internet Computer refer to making HTTP requests from a canister (smart contract) running on the Internet Computer to external HTTPS endpoints. It allows canisters to interact with external services, such as APIs or web servers, over secure HTTPS connections.

HTTPS outcalls are subject to certain limitations and security considerations imposed by the Internet Computer platform. For example, canisters have a set of allowed domains and endpoints they can make requests to, and the response size and request duration may be limited. These restrictions are in place to ensure the security, scalability, and resource efficiency of the Internet Computer network.

For more information, please check here.

HTTPS outcalls: technology overview | Internet Computer

Timer Task

Unlike other blockchains, the Internet Computer can automatically execute canister smart contracts after a specified delay or periodically.

For more information, please check here.

Periodic tasks and timers | Internet Computer

Commands

Several subcommands of csx can be used to advance the development of the component.

The basic syntax is as follows

csx [subcommand] [flag]

You can also check the list of executable commands by specifying the --help flag.

csx new

Create a new project for Chainsight Platform.

This generated project contains several Manifests as templates.
Specify the name of the project to be created, and then generate the project.

csx new --help  
Generates Chainsight project with built-in templates

Usage: csx new [OPTIONS] <PROJECT_NAME>

Arguments:
  <PROJECT_NAME>  Specifies the name of the project to create

Options:
      --no-samples  Skip generation of sample component manifests [short aliases: n]
  -v, --verbose...  Displays detailed information about operations. -vv will generate a very large number of messages and can
                    affect performance
  -q, --quiet...    Suppresses informational messages. -qq limits to errors only; -qqqq disables them all
  -h, --help        Print help

csx add

The 'add' command is used to add a new type of component to your project.

This command will add a Component Manifest of the specified Type and its management settings to the Project Manifest.

If you are familiar with it, you can do manually what this command does.

  • --type: Specify the Component Type
    • A Template Manifest will be generated for the specified Component Type.
  • --path: Select the path of the project to which you want to add the Component.
    • The folder containing the .chainsight file will be recognized as the project.
% csx add --help
Generates component manifest of specified type and adds to your project

Usage: csx add [OPTIONS] --type <TYPE> <COMPONENT_NAME>

Arguments:
  <COMPONENT_NAME>
          Specifies the name of the component to add

Options:
      --type <TYPE>
          Specifies type of the component to add

          Possible values:
          - event-indexer:          To synchronize event data
          - algorithm-indexer:      To get events from other indexer and convert it into another format
          - snapshot-indexer-icp:   To periodically take and store snapshots from other Canisters
          - snapshot-indexer-evm:   To periodically take and store snapshots from Contract
          - snapshot-indexer-https: To periodically take and store snapshots using HTTPS Outcall
          - relayer:                To relay data to other blockchains
          - algorithm-lens:         To calculate using data obtained from the specified Source and process into an arbitrary format

  -v, --verbose...
          Displays detailed information about operations. -vv will generate a very large number of messages and can affect performance

  -p, --path <PATH>
          Specify the path of the project to which the component is to be added. If not specified, the current directory is targeted

  -q, --quiet...
          Suppresses informational messages. -qq limits to errors only; -qqqq disables them all

  -h, --help
          Print help (see a summary with '-h')

csx generate

Generate component code from the manifest in your Chainsight project.

% csx generate --help (or csx gen ...)
Generate codes according to project/component manifests

Usage: csx generate [OPTIONS]

Options:
  -p, --path <PATH>  Specify the path of the project. If not specified, the current directory is targeted
  -v, --verbose...   Displays detailed information about operations. -vv will generate a very large number of messages and can affect performance
  -q, --quiet...     Suppresses informational messages. -qq limits to errors only; -qqqq disables them all
  -h, --help         Print help

csx build

Generate a canister module that runs on the Chainsight Platform from your Chainsight project code. By default, it also includes csx generate, use the -only-build option if you want to generate modules only.

% csx build --help 
Builds your project to generate canisters' modules for Chainsight

Usage: csx build [OPTIONS]

Options:
  -p, --path <PATH>  Specify the path of the project to build. If not specified, the current directory is targeted
  -v, --verbose...   Displays detailed information about operations. -vv will generate a very large number of messages and can affect performance
      --only-build   Only perform build. Perform this steps with code already generated
  -q, --quiet...     Suppresses informational messages. -qq limits to errors only; -qqqq disables them all
  -h, --help         Print help

csx deploy

This command is used to deploy a built module of your own Project to a specified network (local or IC).

It is built by wrapping the operations performed by the dfx deploy command, plus Identity and Wallet checks.

  • --path: Specify the path of the project to deploy. If not specified, the current directory is targeted
  • --network: Specify the network to deploy to.
    • Currently, you can choose between the following options.
      • local ... localhost
      • ic ... mainnet of Internet Computer
  • --component: Only specified components can be targeted.
    • Without this option, all components declared in the project are executed as targets.
% csx deploy --help
Deploy the components of your project. If you want to operate on a local network, you need to build a local dfx network in advance

Usage: csx deploy [OPTIONS]

Options:
  -p, --path <PATH>                Specify the path of the project to deploy. If not specified, the current directory is targeted
  -v, --verbose...                 Displays detailed information about operations. -vv will generate a very large number of messages and can affect performance
  -c, --component <COMPONENT>      Specify the component to deploy. If this option is not specified, the command will be given to all components managed by the project
  -q, --quiet...                   Suppresses informational messages. -qq limits to errors only; -qqqq disables them all
      --network <NETWORK>          Specify the network to execute on [default: local] [possible values: local, ic]
      --port <PORT>                Specifies the port to call. This option is used only if the target is localhost
      --with-cycles <WITH_CYCLES>  Specify the initial number of cycles for canister. Used as a parameter for `dfx canister create`
  -h, --help                       Print help

csx exec

Executes commands that prepare the deployed project's Components for correct operation. The commands executed here are built from the information in the Component Manifest.

It is currently implemented to perform the following commands.

  1. Setup: Set parameters for the Component to operate as intended.
  2. Start timer task: kick periodic execution of data acquisition/processing/storage.
% csx exec --help  
Calls for component processing. Currently supports initialization and task start instructions

Usage: csx exec [OPTIONS]

Options:
  -p, --path <PATH>            Specify the path of the project that manages the component to be called. Refer to the manifest of this project to build the commands that should be executed
  -v, --verbose...             Displays detailed information about operations. -vv will generate a very large number of messages and can affect performance
  -c, --component <COMPONENT>  Specify the name of the component you want to execute. If this option is not specified, the command will be given to all components managed by the project
  -q, --quiet...               Suppresses informational messages. -qq limits to errors only; -qqqq disables them all
      --network <NETWORK>      Specify the network to execute on [default: local] [possible values: local, ic]
      --only-generate-cmds     Only generate commands
      --only-execute-cmds      Only execute commands. Perform this steps with commands already generated
  -h, --help                   Print help

csx delete

Remove already deployed components included in the project.

% csx delete --help
Delete your Chainsight component. This command deletes the component with sidecars and allows you to recover the remaining cycles

Usage: csx delete [OPTIONS] --component <COMPONENT>

Options:
  -p, --path <PATH>            Specify the path of the project to be deleted. If not specified, the current directory is targeted
  -v, --verbose...             Displays detailed information about operations. -vv will generate a very large number of messages and can affect performance
  -c, --component <COMPONENT>  Specify the component name or canister id to delete
  -q, --quiet...               Suppresses informational messages. -qq limits to errors only; -qqqq disables them all
      --network <NETWORK>      Specify the network to execute on [default: local] [possible values: local, ic]
      --port <PORT>            Specifies the port to call. This option is used only if the target is localhost
  -h, --help                   Print help

csx remove

Used to remove resources related to a specified component from your project.

Warning
Stopping a deployed Component (Canister) is currently not part of the process, so you will need to stop/delete the Component, canister, manually.

dfx remove --path sample_project

How to customize

About Manifest

The developer must update the manifest to meet his/her own objectives and communicate his/her intentions to the component.

This section describes how to define and modify Manifest.

Project Manifest

This section describes the manifest of the component managed by your project.

The version is currently fixed at "v1" only.

example)

version: v1
label: sample
components:
- component_path: components/sample_algorithm_indexer.yaml
- component_path: components/sample_algorithm_lens.yaml
- component_path: components/sample_event_indexer.yaml
- component_path: components/sample_relayer.yaml
- component_path: components/sample_snapshot_indexer_evm.yaml
- component_path: components/sample_snapshot_indexer_icp.yaml
- component_path: components/sample_snapshot_indexer_https.yaml

Component Manifest

The description of each component type is different, but the following is a description of the common parts.

version: Like the project manifest, currently fixed at “v1”.

metadata: These are the places where the meta-information of the Component, which can be any Type, is stored, and are set in the custom attributes of WASM according to the specification of Internet Computer.

Of particular importance is the type, which determines the Component Type, so be sure to check and set it.

  • label: String / Component name
  • type: Enum / Component Type (ex: snapshot_indexer_icp)
  • description: String / Component description field
  • tags: Array(String) / Tags for component elements

example)

version: v1
metadata:
  label: sample_snapshot_indexer_evm
  type: snapshot_indexer_evm
  description: ''
  tags: ...
...

The differences between components are presented in the "Components" section below.

Note: Working with .env

If you want to use environment variables or secret values in the manifest, you can use the following syntax.

version: v1
metadata:
  label: sample_snapshot_indexer_evm
  type: snapshot_indexer_evm
  description: ''
  tags: ...
datasource:
  type: contract
  location:
    id: "${CHAIN_CONTRACT_ID}"
    args:
      network_id: ${CHAIN_NETWORK_ID}
      rpc_url: https://alchemy.com/v2/${CHAIN_ALCHEMY_KEY}
...

And then, you can set the environment variables in the .env file on the project root.

CHAIN_CONTRACT_ID=0x1234567890
CHAIN_NETWORK_ID=1
CHAIN_ALCHEMY_KEY=abcde12345

Components

About Snapshot Indexer

As mentioned earlier, there are multiple types of Snapshot Indexer, and each datasource has different logic and external connection methods, so there are differences in the way manifest is written.

These Snapshot Indexer types are also specified in metadata.type.

  • snapshot_indexer_evm
  • snapshot_indexer_icp
  • snapshot_indexer_https

This section also briefly introduces the manifest items that commonly exist in Snapshot Indexer.

  • datasource specifies the data source to be collected
    • The method of description varies slightly from component to component. See individual component sections for details.
  • interval specifies the interval between acquiring and storing data at the destination specified by datasource
    • Number / Interval between data acquisition and storage.
    • Set in seconds.
datasource: ...
...
interval: 3600

Snapshot Indexer EVM

Select this type if you want to build a data snapshot using HTTPS outcalls from an EVM-compliant blockchain.

In datasource, specify the destination network, contract address, and contract function.

  • datasource.location ... Specify destination network, contract
    • id: String / Contract address
    • args.network_id: Number / chain_id of the target network
    • args.rpc_url: String / rpc endpoint url to connect to the target network
  • datasource.method ... Specify the function of the contract to be called.
    • identifier: String / Interface of the function to be called.
    • interface: Name of the ABI file containing the interface to the above function.
      • Placed under (project folder)/interfaces
      • ERC20.json is buildin to the CLI.
    • args: String, Number / If the function has arguments, set their values.
      • The value entered is always used in HTTPS outcalls as a fixed value.
        • Snapshot stores function calls with the same conditions as a Snapshot, so it is not possible to calculate the input value each time.

example)

version: v1
metadata:
  label: sample_snapshot_indexer_evm
  type: snapshot_indexer_evm
  description: ''
  tags: ...
datasource:
  type: contract
  location:
    id: 6b175474e89094c44da98b954eedeac495271d0f
    args:
      network_id: 1
      rpc_url: https://eth-mainnet.g.alchemy.com/v2/<YOUR_KEY>
  method:
    identifier: totalSupply():(uint256)
    interface: ERC20.json
    args: []
interval: 3600
cycles: null

Snapshot Indexer ICP

Select this type if you want to use cross canister calls within Internet Computer to build a snapshot of data that can be retrieved from other canisters.

Set the function for the canister to be acquired at datasource.

  • datasource.location ... Specify the canister to retrieve from.
    • id: String / Target canister name or id
  • datasource.method ... Specify the Canister function to call.
    • method.identifier: String / interface of the function to be called.
      • Refer to the interface definition in the candid file and enter.
        • NOTE: Exclude "query" in the query call.
    • method.interface: Current status "null" fixed.
    • method.args: String, Number / If the function has arguments, set their values
      • The value entered is always used in cross contract calls as a fixed value.

is_target_component specifies whether the data source is a canister in the Chainsight Platform.

  • is_target_component: Whether the data source is a Chainsight Component or not
    • If this is not set, the target will act as if it were a Chainsight Component.

example)

version: v1
metadata:
  label: sample_snapshot_indexer_icp
  type: snapshot_indexer_icp
  description: ''
  tags: ...
datasource:
  type: canister
  location:
    id: sample_snapshot_indexer_evm
  method:
    identifier: 'get_last_snapshot : () -> (record { value : text; timestamp : nat64 })'
    interface: null
    args: []
is_target_component: null
interval: 3600

Snapshot Indexer HTTPS

Select this type if you want to collect data from a general web, such as a public API server.

The datasource specifies the data location to be collected.

  • datasource.url: String / Specify the URL from which to retrieve data
  • datasource.headers: Object / Specifies the request header
  • datasource.queries: Object / Specify request data
    • type: "static" or "dynamic"
      • "static" will set it statically in the subsequent value field in the manifest
      • "dynamic", where the user writes the logic to calculate parameters in the generated component code
    • value: Object / Set the request body in key-value format

example)

version: v1
metadata:
  label: Sample Snapshot Indexer Https
  type: snapshot_indexer_https
  description: ''
  tags: ...
datasource:
  url: https://api.coingecko.com/api/v3/simple/price
  headers:
    Content-Type: application/json
  queries:
    type: static
    value:
      ids: dai
      vs_currencies: usd
interval: 3600
cycles: null

Event Indexer

Event Indexer subscribes to Ethereum Contract events and stores them as data in the component.

Specify the contract to be subscribed to and its events in datasource. The specification of chains and contracts is the same as in the Snapshot Indexer EVM.

  • datasource.id: String / Contract address
  • datasource.event: Specify the target Event
    • identifier: event name / identifier
    • interface: Name of the ABI file containing the interface to the above event.
  • datasource.network: Network to which the contract for the specified event belongs
    • chain_id: Number / chain_id of the target network
    • rpc_url: String / rpc endpoint url to connect to the target
  • datasource.from: Number / Specifies the block number to start subscribing to
    • Block numbers before the specified number are skipped.
  • datasource.contract_type: String / Specify the contract type
  • datasource.batch_size: Optional(Number) / Specify the size of the block to be subscribed at a time.

example)

version: v1
metadata:
  label: Event Indexer
  type: event_indexer
  description: ''
  tags: ...
datasource:
  id: 0x6B175474E89094C44Da98b954EedeAC495271d0F
  event:
    identifier: Transfer
    interface: ERC20.json
  network:
    rpc_url: https://eth-mainnet.g.alchemy.com/v2/${ALCHEMY_KEY}
    chain_id: 1
  from: 17660942
  contract_type: ERC-20
  batch_size: null
interval: 3600
cycles: null

Algorithm Indexer

The Algorithm Indexer subscribes to data from the Event Indexer and other Algorithm Indexers and allows them to be processed with arbitrary logic.

The datasource determines what data source is used as input, and the output determines the format of the data produced by the logic.

  • datasource: Identification of computation source information
    • datasource.principal: Component to call
    • datasource.input: Type of data to be collected
      • datasource.input.name: String / Name of type
      • datasource.input.fields: Optional(Object) / Specify the field information of the type, any key name and value type.
        • If it is not set up, code it yourself.
      • datasource.method: String / Function name to call
      • datasource.source_type: String / Select the data source format
        • event_indexer ... Event Indexer Component
        • key_value,key_values ... Algorithm Indexer Component, More details to follow.
      • The following are similar to Event Indexer
        • datasource.from, datasource.batch_size
  • output: Array(Object) / Specify the format of calculation results
    • output[i].output_type: Specify the type of storage where the calculation results are to be stored
      • key_value ... Store one data in one key.
      • key_values ... Store multiple data in one key. That is, it stores an array of data.
    • The following is the same as for datasource.input
      • output[i].name, output[i].field
version: v1
metadata:
  label: Algorithm Indexer
  type: algorithm_indexer
  description: ''
  tags: ...
datasource:
  principal: event_indexer_component
  input:
    name: Transfer
    fields:
      from: String
      to: String
      value: chainsight_cdk::core::U256
  from: 17660942
  method: proxy_call
  source_type: event_indexer
  batch_size: null
output:
- name: Account
  fields:
    address: String
  output_type: key_value
- name: AccountBalance
  fields:
    address: String
    balance: u64
  output_type: key_values
interval: 3600
cycles: null

Relayer

Relayer is a component for propagating data computed and maintained by Chainsight Platform to other blockchains.

Therefore, datasource and interval are the same as Snapshot Indexer ICP, and a new destination must be specified to specify the propagation destination.

  • destination.network_id: Number / chain_id of the target network
  • destination.type: Enum / Oracle Type
    • To send data to the destination chain, Chainsight provides several Oracle types according to a defined standard, and the developer specifies the type
  • destination.oracle_address: String / Oracle address
  • destination.rpc_url: String / rpc endpoint url to call the target network

example)

version: v1
metadata:
  label: sample_relayer
  type: relayer
  description: ''
  tags: ...
datasource:
  type: canister
  location:
    id: sample_snapshot_indexer_evm
  method:
    identifier: 'get_last_snapshot_value : () -> (text)'
    interface: null
    args: []
destination:
  network_id: 80001
  type: uint256
  oracle_address: 0539a0EF8e5E60891fFf0958A059E049e43020d9
  rpc_url: https://polygon-mumbai.g.alchemy.com/v2/<YOUR_KEY>
interval: 3600

The above description is only a minimal setup. Further customization is possible.

  • To change the caller's contract interface...
    • destination.method_name: identifier of the function to call
    • destination.interface: ABI of the contract to be called
  • conversion_parameter allows simple processing of the data to be propagated
    • extracted_field: String / Specify the field to propagate
    • destination_type_to_convert: String / Specify the type you want to convert
    • exponent_of_power10: Number / Use for digit up

example)

destination:
  ...
  interface: IProposalSynchronizer.json
  method_name: batchSynchronize
conversion_parameter:
  extracted_field: value.dai.usd
  destination_type_to_convert: U256
  exponent_of_power10: 2

What is Oracle?

When Relayer propagates data to other blockchains, Chainsight provides Oracle Contract as the target.

It has only a state that stores the specified type in key/value format, where the key is an address constructed from the sender's Canister secret information, allowing the sender to be identified.

There is a specific code below.

horizonx-tech/chainsight-management-oracle: Oracles supported by Chainsight

Check the README in the above repository for the addresses of available oracle contracts that have been deployed. If you have a network you would like to add, please use that repository or send us an add request.

Algorithm Lens

Users can define arbitrary logic using Algorithm Lens. All data sources on Chainsight can be used as inputs for the calculations.

datasource specifies the source data source for the calculation. You can specify data sources by canister in Chainsight and their endpoints (e.g. functions). Multiple data sources can be specified.

  • datasource.methods: Array / Specifies the components from which the data originates.
    • id: String / Specify the Component to be the data source
      • If in the same project, specify the "component name"
      • Otherwise, specify the canister ID.
        • ex: thiw2-paaaa-aaaag-qc53a-cai
    • identifier: String / Candid format interface to call to for data source acquisition
    • candid_file_path: Optional(String) / Path to the .did file that contains the function interface for the canister that will be the data source
    • func_name_alias: Optional(String) / Function name generated in the logic file generated from this data source definition

example)

version: v1
metadata:
  label: sample_algorithm_lens
  type: algorithm_lens
  description: ''
  tags: ...
datasource:
  methods:
  - id: sample_snapshot_indexer_evm
    identifier: 'get_last_snapshot_value : () -> (record { nat; text })'
    candid_file_path: interfaces/sample_snapshot_indexer_evm.did
  - id: sample_snapshot_indexer_icp
    identifier: 'get_last_snapshot_value : () -> (nat)'
    candid_file_path: interfaces/sample_snapshot_indexer_icp.did
cycles: null

Sources for Component Modules

"csx generate" can be run to generate code for a component module from your project manifest. The codes is generated in the following configuration.

pj_root/src
|- __interface // ABI and Candid used in the codes
|- accessors // External communication logic
|- bindings // Types for external communication
|- canisters // Core canister codes
|- logics // User-specific customization
|- Cargo.lock
L Cargo.toml

Some components can be customized by the user by editing the component-specific lib.rs in the logics folder.

logics
|- (component_name)
|  |- src
|  |  L lib.rs
|  L Cargo.toml
...

Case for Snapshot Indexer HTTPS

Snapshot Indexer HTTPS allows filtering on response data that can be retrieved from a specified destination. It can be reflected by updating the field in the rust structure that represents the response data type.

example)

use candid::{Decode, Encode};
#[derive(Debug, Clone, candid::CandidType, candid::Deserialize, serde::Serialize, chainsight_cdk_macros::StableMemoryStorable)]
pub struct SnapshotValue {
    pub dai: Dai,
}

#[derive(Debug, Clone, candid::CandidType, candid::Deserialize, serde::Serialize, chainsight_cdk_macros::StableMemoryStorable)]
pub struct Dai {
    pub usd: f64,
-    pub usd_market_cap: f64,
-    pub usd_24h_vol: f64,
-    pub usd_24h_change: f64,
-    pub last_updated_at: f64
}

Case for Algorithm Lens

With respect to Algorithm Lens, it is up to the user to decide how to process data from the specified data source. This logic must be implemented here.

Codes is automatically generated to retrieve data from the specified data source.

example)

#[derive(Clone, Debug, Default, candid :: CandidType, serde :: Deserialize, serde :: Serialize)]
pub struct LensValue {
    pub dummy: f64,
}
pub async fn calculate(targets: Vec<String>) -> LensValue {
    let _result = get_eth_1(targets.get(0usize).unwrap().clone()).await;
    let _result = get_eth_2(targets.get(1usize).unwrap().clone()).await;
    let _result = get_eth_3(targets.get(2usize).unwrap().clone()).await;

    todo!();
}

From the template code as above, update the code as follows, taking into account your own logic. This is an example of calculating an average.

example)

#[derive(Clone, Debug, Default, candid :: CandidType, serde :: Deserialize, serde :: Serialize)]
pub struct LensValue {
    pub value: f64,
}
pub async fn calculate(targets: Vec<String>) -> LensValue {
    let eth_1 = get_eth_1(targets.get(0usize).unwrap().clone()).await.unwrap();
    let eth_2 = get_eth_2(targets.get(1usize).unwrap().clone()).await.unwrap();
    let eth_3 = get_eth_3(targets.get(2usize).unwrap().clone()).await.unwrap();

    let prices = vec![eth_1, eth_2, eth_3];
    LensValue { value: (prices.iter().sum::<f64>() / prices.len() as f64) }
}

References

Medium's official account introduces various implementation examples and the technology behind them.

Chainsight – Medium

The Showcase repository also publishes actual code for a variety of use case examples.

horizonx-tech/chainsight-showcase