Getting Started
Decoding Chain Data
Learn how to query and decode blockchain data from storage into human-readable format
When working with blockchain data, all information is stored in an encoded format for efficiency. Polkadart provides powerful tools to decode this data into human-readable formats that your Dart applications can easily work with.
Understanding Storage Encoding
Blockchain storage uses SCALE (Simple Concatenated Aggregate Little-Endian) encoding. This includes:
- Storage keys: Hashed identifiers for storage locations
- Storage values: The actual encoded data
- Account IDs: 32-byte public keys
Querying and Decoding Storage
Complete Example
Create a new file bin/demo.dart with the following code:
demo.dart
Future<void> main(List<String> arguments) async {
final provider = Provider.fromUri(Uri.parse('wss://rpc.polkadot.io'));
final polkadot = Polkadot(provider);
// Step 1: Get the storage key prefix for accounts
final accountMapPrefix = polkadot.query.system.accountMapPrefix();
// Step 2: Query the first 10 account storage keys
final keys = await polkadot.rpc.state.getKeysPaged(
key: accountMapPrefix,
count: 10
);
print("First 10 account storage keys:");
print(keys.map((key) => '0x${hex.encode(key)}').join('\n')));
// Step 3: Decode account IDs from storage keys
// Storage keys are composed of: [pallet_hash(16 bytes) + storage_item_hash(16 bytes) + account_id(32 bytes)]
final accountIds = keys.map((key) =>
const AccountId32Codec().decode(ByteInput(key.sublist(32)))
);
print("\nFirst 10 account public keys:");
print(accountIds.map((account) => '0x${hex.encode(account)}').join('\n')));
// Step 4: Query account information for each account
final accountInfos = await Future.wait(
accountIds.map((account) => polkadot.query.system.account(account))
);
// Step 5: Display decoded account information
print("\nAccount Information:");
for (final (index, accountInfo) in accountInfos.indexed) {
print('Account ${index + 1}:');
print(' Nonce: ${accountInfo.nonce}');
print(' Free Balance: ${accountInfo.data.free}');
print(' Reserved: ${accountInfo.data.reserved}');
print(' Frozen: ${accountInfo.data.frozen}');
print('');
}
}
Running the Example
dart run bin/demo.dart
Understanding the Output
The output shows:
Storage Keys: Long hexadecimal strings that identify storage locations
Account IDs: 32-byte public keys extracted from the storage keys
Account Information: Decoded data including:
nonce: Number of transactions sent from this accountfree: Available balancereserved: Balance locked for specific purposesfrozen: Balance that cannot be transferred
The storage key structure is:
- First 16 bytes: Pallet identifier hash
- Next 16 bytes: Storage item identifier hash
- Remaining bytes: The actual key data (account ID in this case)
Key Concepts
Storage Keys
Every piece of data on the blockchain has a unique storage key. Polkadart helps you:
- Generate the correct storage keys
- Query data using these keys
- Decode the returned values
SCALE Codec
The SCALE codec is used throughout Polkadot for efficient data encoding:
// Decode any SCALE-encoded data
final decoded = SomeTypeCodec().decode(ByteInput(encodedData));
// Encode data to SCALE format
final encoded = SomeTypeCodec().encode(myData);
Type Safety
Generated types ensure you're working with the correct data structures:
// Type-safe query with auto-completion
final balance = await polkadot.query.system.account(accountId);
// balance is strongly typed as AccountInfo
🎉 Congratulations! You've successfully queried and decoded blockchain data!