Get Started with the StorageHub SDK¶
The StorageHub SDK is a modular toolkit that makes it easy to build on DataHaven, giving developers direct access to functionalities for managing storage, buckets, and proofs. It simplifies both on-chain and off-chain interactions so you can focus on your application logic rather than low-level integrations.
This guide introduces and compares the functionalities of the StorageHub SDK packages. You can use the StorageHub SDK for every step in the storage request and retrieval process. For more information, see the Workflow Overview.
Workflow Overview¶
A high-level look at how data moves through DataHaven, from storage requests to upload, verification, and retrieval.
Get Started with StorageHub SDK
Set up your development environment, install the StorageHub SDK, and prepare your project to start interacting with the DataHaven network.
Connect your wallet or app identity, select a Main Storage Provider (MSP), and create or reuse a bucket.
Authenticate with SIWE and JWT
Use Sign-In with Ethereum (SIWE) and JSON Web Tokens (JWT) for secure authentication.
Issue a Storage Request, verify it, then upload a file to the connected MSP. Includes steps to verify upload success.
Use your file key to download your file from the MSP client and save it programmatically.
StorageHub SDK Packages¶
The StorageHub SDK contains the following packages:
Package |
Description | When to Use | Environments |
|---|---|---|---|
@storagehub-sdk/core |
Foundational, backend-agnostic building blocks for StorageHub. | Chain-facing interactions | Node.js, Browsers |
@storagehub-sdk/msp-client |
High-level client for interacting with Main Storage Provider (MSP) services. | Provider-facing operations | Node.js, Browsers |
@storagehub-sdk/core
The primary functions of @storagehub-sdk/core are to act as backend-agnostic building blocks including:
- Wallets and signing
- EIP-1193
- Precompile helpers for bridging between Substrate and EVM
- Merkle and WASM utilities
- Low-level HTTP
- Types and constants shared across the SDK.
This package includes EVM account-typed helpers, WASM-backed file utilities, and stable primitives usable without any backend.
@storagehub-sdk/msp-client
The primary functions of @storagehub-sdk/msp-client are as follows:
- Retrieve MSP-specific client information, such as:
- Health
- Authorization nonce/verify
- Upload and download endpoints
- Talk to an MSP backend for authorization and file transfer.
- Includes REST contracts for MSP, token handling, and streaming or multipart upload and download helpers.
This package includes all MSP-tied logic.
Prerequisites¶
Before you begin, ensure you have the following:
- Node.js ≥ 22 installed. LTS version recommended.
- pnpm, npm, or yarn installed for package management
- Testnet network configuration details, including the RPC and WSS endpoints
- Testnet MSP base URL
- Testnet tokens
Need a starter project?
If you don't have an existing project, follow these steps to create a TypeScript project you can use to follow the guides in this section:
-
Create a new project folder by executing the following command in the terminal:
-
Initialize a
package.jsonfile using the correct command for your package manager: -
Add the TypeScript and Node type definitions to your projects using the correct command for your package manager:
-
Create a
tsconfig.jsonfile in the root of your project and paste the following configuration: -
Initialize the
srcdirectory:
Install the StorageHub SDK¶
Add the core and MSP client packages to your project. These libraries provide the APIs and utilities needed to interact with DataHaven’s storage network.
Initialize the StorageHub SDK¶
Follow the steps in this section to set up the clients needed to work with the StorageHub SDK, allowing you to interact with DataHaven and manage your data.
Install Client Dependencies¶
Why do I need these dependencies?
-
@storagehub/types-bundle: Describes DataHaven's custom on-chain types. -
@polkadot/api: The core JavaScript library used to talk to any Substrate-based blockchain, which in our case is DataHaven. -
@storagehub/api-augment: Extends@polkadot/apiwith DataHaven's custom pallets and RPC methods. You will import it in yourindex.tsfile where your main script logic will be executed. -
viem: Lightweight library for building Ethereum-compatible applications.
Set Up Client Service¶
You'll need to set up the necessary clients to connect to the DataHaven network, which runs on a dual-protocol architecture (Substrate for core logic and EVM for compatibility).
-
In the folder where your
index.ts(or main code file) is located, create a new folder calledservices: -
Create a
clientService.tsfile. -
Add the following code:
Note
The code below uses DataHaven testnet configuration values, which include the chain ID RPC URL, WSS URL, MSP URL, and token metadata. If you’re running a local devnet, make sure to replace these with your local configuration parameters. You can find all the relevant local devnet values in the Local Devnet page.
clientService.tsimport { privateKeyToAccount } from 'viem/accounts'; import { Chain, defineChain } from 'viem'; import { createPublicClient, createWalletClient, http, WalletClient, PublicClient, } from 'viem'; import { StorageHubClient } from '@storagehub-sdk/core'; import { ApiPromise, WsProvider } from '@polkadot/api'; import { types } from '@storagehub/types-bundle'; const account = privateKeyToAccount('INSERT_PRIVATE_KEY' as `0x${string}`); const address = account.address; const NETWORKS = { devnet: { id: 181222, name: 'DataHaven Local Devnet', rpcUrl: 'http://127.0.0.1:9666', wsUrl: 'wss://127.0.0.1:9666', mspUrl: 'http://127.0.0.1:8080/', nativeCurrency: { name: 'StorageHub', symbol: 'SH', decimals: 18 }, }, testnet: { id: 55931, name: 'DataHaven Testnet', rpcUrl: 'https://services.datahaven-testnet.network/testnet', wsUrl: 'wss://services.datahaven-testnet.network/testnet', mspUrl: 'https://deo-dh-backend.testnet.datahaven-infra.network/', nativeCurrency: { name: 'Mock', symbol: 'MOCK', decimals: 18 }, }, }; const chain: Chain = defineChain({ id: NETWORKS.testnet.id, name: NETWORKS.testnet.name, nativeCurrency: NETWORKS.testnet.nativeCurrency, rpcUrls: { default: { http: [NETWORKS.testnet.rpcUrl] } }, }); const walletClient: WalletClient = createWalletClient({ chain, account, transport: http(NETWORKS.testnet.rpcUrl), }); const publicClient: PublicClient = createPublicClient({ chain, transport: http(NETWORKS.testnet.rpcUrl), }); // Create StorageHub client const storageHubClient: StorageHubClient = new StorageHubClient({ rpcUrl: NETWORKS.testnet.rpcUrl, chain: chain, walletClient: walletClient, filesystemContractAddress: '0x0000000000000000000000000000000000000404' as `0x${string}`, }); // Create Polkadot API client const provider = new WsProvider(NETWORKS.testnet.wsUrl); const polkadotApi: ApiPromise = await ApiPromise.create({ provider, typesBundle: types, noInitWarn: true, }); export { account, address, publicClient, walletClient, storageHubClient, polkadotApi, };Warning
It is assumed that private keys are securely stored and managed in accordance with standard security practices.
With the above code in place, you now have the following:
walletClient: Used for signing and broadcasting transactions using the derived private key.publicClient: Used for reading general public data from the chain, such as checking transaction receipts or block status.storageHubClient: Used for interacting with the StorageHub network APIs, including creating buckets, issuing storage requests, uploading or deleting files, and managing storage proofs.polkadotApi: Used for reading code chain logic and state data from the underlying DataHaven Substrate node.
Set Up MSP Service¶
To interact with DataHaven's Main Storage Provider (MSP) services, you need to establish a connection using the MspClient from the StorageHub SDK. This involves configuring the HTTP client, setting up session management for authenticated requests, and initializing the MSP client itself.
-
Create a
mspService.tsfile within yourservicesfolder. -
Add the following code:
Note
The code below uses DataHaven testnet configuration values, which include the chain ID, RPC URL, WSS URL, MSP URL, and token metadata. If you’re running a local devnet, make sure to replace these with your local configuration parameters. You can find all the relevant local devnet values in the Local Devnet page.
mspService.tsimport { HealthStatus, InfoResponse, MspClient, UserInfo, } from '@storagehub-sdk/msp-client'; import { HttpClientConfig } from '@storagehub-sdk/core'; import { address, walletClient } from './clientService.js'; const NETWORKS = { devnet: { id: 181222, name: 'DataHaven Local Devnet', rpcUrl: 'http://127.0.0.1:9666', wsUrl: 'wss://127.0.0.1:9666', mspUrl: 'http://127.0.0.1:8080/', nativeCurrency: { name: 'StorageHub', symbol: 'SH', decimals: 18 }, }, testnet: { id: 55931, name: 'DataHaven Testnet', rpcUrl: 'https://services.datahaven-testnet.network/testnet', wsUrl: 'wss://services.datahaven-testnet.network/testnet', mspUrl: 'https://deo-dh-backend.testnet.datahaven-infra.network/', nativeCurrency: { name: 'Mock', symbol: 'MOCK', decimals: 18 }, }, }; // Configure the HTTP client to point to the MSP backend const httpCfg: HttpClientConfig = { baseUrl: NETWORKS.testnet.mspUrl }; // Initialize a session token for authenticated requests (updated after authentication // through SIWE) let sessionToken: string | undefined = undefined; // Provide session information to the MSP client whenever available // Returns a token and user address if authenticated, otherwise undefined const sessionProvider = async () => sessionToken ? ({ token: sessionToken, user: { address: address } } as const) : undefined; // Establish a connection to the Main Storage Provider (MSP) backend const mspClient = await MspClient.connect(httpCfg, sessionProvider); // Retrieve MSP metadata, including its unique ID and version, and log it to the console const getMspInfo = async (): Promise<InfoResponse> => { const mspInfo = await mspClient.info.getInfo(); console.log(`MSP ID: ${mspInfo.mspId}`); return mspInfo; }; // Retrieve and log the MSP’s current health status const getMspHealth = async (): Promise<HealthStatus> => { const mspHealth = await mspClient.info.getHealth(); console.log(`MSP Health: ${mspHealth}`); return mspHealth; }; // Authenticate the user via SIWE (Sign-In With Ethereum) using the connected wallet // Once authenticated, store the returned session token and retrieve the user’s profile const authenticateUser = async (): Promise<UserInfo> => { console.log('Authenticating user with MSP via SIWE...'); // In development domain and uri can be arbitrary placeholders, // but in production they must match your actual frontend origin. const domain = 'localhost'; const uri = 'http://localhost'; const siweSession = await mspClient.auth.SIWE(walletClient, domain, uri); console.log('SIWE Session:', siweSession); sessionToken = (siweSession as { token: string }).token; const profile: UserInfo = await mspClient.auth.getProfile(); return profile; }; // Export initialized client and helper functions for use in other modules export { mspClient, getMspInfo, getMspHealth, authenticateUser };With the above code in place, you now have the following:
mspClient: Used for interacting with a Main Storage Provider (MSP) backend — allowing you to authenticate via SIWE, retrieve MSP information and health status, and perform storage-related actions through REST-like endpoints.getMspInfo: Fetches general MSP metadata such as its unique ID, version, and available endpoints.getMspHealth: Checks the operational health of the MSP and reports whether it’s running normally or facing issues.authenticateUser: Authenticates your wallet with the MSP via Sign-In With Ethereum (SIWE), creates a session token, and returns your user profile.
Next Steps¶
Now that you have the StorageHub SDK packages installed and all the necessary clients set up, you are ready to start building with DataHaven.
-
Create A Bucket
Follow this guide to create your first bucket, DataHaven's storage container for your files. This is the perfect first step on your journey of building on DataHaven.
-
End-to-End Storage Workflow
This tutorial takes you step-by-step through storing a file on DataHaven and retrieving it from the network. Take this step to see how all the pieces fit together in one go.
| Created: September 18, 2025