Frontend & SDK Integration
Reading Data from Intelligent Contracts

Reading from Intelligent Contracts

Reading from Intelligent Contracts means querying contract state or executing view functions without modifying blockchain state. These read-only operations are free, require no fees, and provide immediate access to contract data.

Understanding View Operations

In GenLayer, functions marked with the @gl.public.view decorator are read-only operations that:

  • Don't modify the contract's state
  • Can be executed without requiring a transaction
  • Return data immediately
  • Don't consume gas
  • Can be called by any account

Basic Contract Reading

Here's how to read from an Intelligent Contract:

import { simulator } from 'genlayer-js/chains';
import { createClient, createAccount } from 'genlayer-js';
 
const account = createAccount();
const client = createClient({
  chain: simulator,
  account: account,
});
 
const result = await client.readContract({
  address: contractAddress,
  functionName: 'get_complete_storage',
  args: [],
});

Parameters Explained

  • address: The deployed contract's address on the GenLayer network
  • functionName: The name of the view function you want to call
  • args: An array of arguments that the function accepts (empty if none required)

Common View Operations

Intelligent Contracts typically include several types of view functions:

State Queries

// Reading a single value
const balance = await client.readContract({
  address: contractAddress,
  functionName: 'get_balance',
  args: [accountAddress],
});
 
// Reading multiple values
const userInfo = await client.readContract({
  address: contractAddress,
  functionName: 'get_user_info',
  args: [userId],
});

Computed Values

// Getting calculated results
const totalSupply = await client.readContract({
  address: contractAddress,
  functionName: 'calculate_total_supply',
  args: [],
});

Validation Checks

// Checking permissions
const hasAccess = await client.readContract({
  address: contractAddress,
  functionName: 'check_user_permission',
  args: [userId, 'ADMIN_ROLE'],
});

Error Handling

When reading from contracts, you should handle potential errors:

try {
  const result = await client.readContract({
    address: contractAddress,
    functionName: 'get_data',
    args: [],
  });
  console.log('Data retrieved:', result);
} catch (error) {
  if (error.message.includes('Contract not found')) {
    console.error('Invalid contract address');
  } else if (error.message.includes('Function not found')) {
    console.error('Invalid function name');
  } else {
    console.error('Error reading contract:', error);
  }
}

Best Practices

  1. Cache Results: For frequently accessed data that doesn't change often, consider caching the results.
  2. Batch Readings: When possible, use functions that return multiple values instead of making multiple separate calls.
  3. Type Safety: Use TypeScript interfaces to ensure type safety when handling returned data: