Skip to content
Discussions/App Development/Using the @daml/ledger library without the @daml/react libraryForum ↗

Using the @daml/ledger library without the @daml/react library

App Development6 posts204 views1 likesLast activity Apr 2023
GY
gyorgybalazsiOP
Apr 2023

Does anybody use the @daml/ledger library without the @daml/react library?

I would appreciate a small example to help me get started.

The docs don’t elaborate on this, advising users to check out how the @daml/react library uses the @daml/ledger library, but it’s not straightforward to separate out the non React specific parts of the code.

CO
cocreature
Apr 2023

Is there something in particular that you are struggling with?

GY
gyorgybalazsi
Apr 2023

I started with looking at this piece of code and I can see that already the type of the DamlLedger object uses React: DamlLedger: React.FC<LedgerProps>;

import React from "react";
import { ContractId, Party, Template, TemplateOrInterface } from "@daml/types";
import Ledger, { CreateEvent, Query, StreamCloseEvent, QueryResult, User } from "@daml/ledger";
export { QueryResult } from "@daml/ledger";
/**
 * React props to initiate a connect to a Daml ledger.
 */
export declare type LedgerProps = {
    token: string;
    httpBaseUrl?: string;
    wsBaseUrl?: string;
    user?: User;
    party: Party;
    reconnectThreshold?: number;
};
/**
 * The result of a ``fetch`` against the ledger.
 *
 * @typeparam T The contract template type of the query.
 * @typeparam K The contract key type of the query.
 * @typeparam I The template id type.
 */
export declare type FetchResult<T extends object, K, I extends string> = {
    /** Contracts of the given contract template and key. */
    contract: CreateEvent<T, K, I> | null;
    /** Indicator for whether the fetch is executing. */
    loading: boolean;
};
/**
 * The result of a streaming ``fetchByKeys`` against the ledger.
 *
 * @typeparam T The contract template type of the query.
 * @typeparam K The contract key type of the query.
 * @typeparam I The template id type.
 */
export declare type FetchByKeysResult<T extends object, K, I extends string> = {
    /** Contracts of the given contract template and key. */
    contracts: (CreateEvent<T, K, I> | null)[];
    /** Indicator for whether the fetch is executing. */
    loading: boolean;
};
/**
 * A LedgerContext is a React context that stores information about a Daml Ledger
 * and hooks necessary to use it.
 */
export declare type LedgerContext = {
    DamlLedger: React.FC<LedgerProps>;
    useParty: () => Party;
    useUser: () => User;
    useLedger: () => Ledger;
    useQuery: <T extends object, K, I extends string>(template: TemplateOrInterface<T, K, I>, queryFactory?: () => Query<T>, queryDeps?: readonly unknown[]) => QueryResult<T, K, I>;
    useFetch: <T extends object, K, I extends string>(template: TemplateOrInterface<T, K, I>, contractId: ContractId<T>) => FetchResult<T, K, I>;
    useFetchByKey: <T extends object, K, I extends string>(template: Template<T, K, I>, keyFactory: () => K, keyDeps: readonly unknown[]) => FetchResult<T, K, I>;
    useStreamQuery: <T extends object, K, I extends string>(template: TemplateOrInterface<T, K, I>, queryFactory?: () => Query<T>, queryDeps?: readonly unknown[], closeHandler?: (e: StreamCloseEvent) => void) => QueryResult<T, K, I>;
    useStreamQueries: <T extends object, K, I extends string>(template: TemplateOrInterface<T, K, I>, queryFactory?: () => Query<T>[], queryDeps?: readonly unknown[], closeHandler?: (e: StreamCloseEvent) => void) => QueryResult<T, K, I>;
    useStreamFetchByKey: <T extends object, K, I extends string>(template: Template<T, K, I>, keyFactory: () => K, keyDeps: readonly unknown[], closeHandler?: (e: StreamCloseEvent) => void) => FetchResult<T, K, I>;
    useStreamFetchByKeys: <T extends object, K, I extends string>(template: Template<T, K, I>, keyFactory: () => K[], keyDeps: readonly unknown[], closeHandler?: (e: StreamCloseEvent) => void) => FetchByKeysResult<T, K, I>;
    useReload: () => () => void;
};
/**
 * Create a [[LedgerContext]]. One should use this function, instead of the default [[DamlLedger]],
 * where one needs to be able to nest ledger interactions, by different parties or connections, within
 * one React application.
 *
 * @param contextName Used to refer to a context in case of errors.
 */
export declare function createLedgerContext(contextName?: string): LedgerContext;
CO
cocreature
Apr 2023

Right, you need to instead use the methods from default |.

Roughly something like this:

import Ledger, { CreateEvent, LedgerOptions } from '@daml/ledger';
const ledger = new Ledger(yourLedgerOptions)
await ledger.create(…)
GY
gyorgybalazsi
Apr 2023

This looks good, thank you!

GY
gyorgybalazsi
Apr 2023

Recording for posterity, this is my first working nodejs program using the the @daml/ledger library, thanks again:

import Ledger, { CreateEvent, LedgerOptions } from '@daml/ledger';

var jwt = require('jwt-simple');

var loginName = "Alice";
var ledgerId = "sandbox";

var payload = {
    "https://daml.com/ledger-api": {
      "ledgerId": ledgerId,
      "applicationId": 'create-daml-app',
      "actAs": [loginName]
    }
}
var secret = 'xxx';
var token = jwt.encode(payload, secret);

let ledgerOptions: LedgerOptions = {
    httpBaseUrl: "http://127.0.0.1:7575/",
    token:token
}
const ledger = new Ledger(ledgerOptions);
// await ledger.create(…)

async function printAlice() {
    var alice = await ledger.getUser("alice");
    console.log(alice);
}

printAlice()

The result:

{
  userId: 'alice',
  primaryParty: 'Alice::122020032b4df0224c7c3003ace3ba4e3bcf3c49083638fbdbbb6663c95ea02192d3'
}
← Back to Discussions