Skip to main content

HDF5 Datasets

HDF5 (Hierarchical Data Format version 5) organizes hierarchical data in groups and datasets. The platform exports annotated recording data as HDF5 for training frameworks outside the platform to read.

Definitions​

ItemDescription
Storage unitA single .hdf5 file; inside the file is a tree of groups and datasets
ChunkingRaw files are grouped by the export parameters, and each group is written to one chunk_NNN.hdf5
episodeAn annotation task corresponds to one group under /data
Frame alignmentDatasets within the same episode correspond one to one by frame index

Rules and Workflow​

Ingestion and Import​

During preprocessing, the platform converts HDF5 recordings from the following sources to MCAP and then ingests them. After ingestion, the data can be viewed and annotated in the platform and exported as HDF5 again.

SourcePreprocessing action
Agilexio_hdf5agilex2mcap
Realmanio_hdf5realman2mcap
Dobotio_hdf5dobot2mcap
Limxio_hdf5limx2mcap
Unixio_hdf5unix2mcap

Export Rules​

RuleDescription
ChunkingEvery chunk_size raw files go into one chunk file; chunk numbering starts at 1 and is zero-padded to three digits
SamplingBefore writing, each message channel is sampled at equal intervals by hz
episode divisionEach subtasks entry in the sidecar JSON is written to one data/episode_NNN group; without a sidecar JSON, the whole recording is written as one episode
Conversion sourceMCAP input goes through io_mcap2hdf5; the Agibot extracted directory goes through io_agibot2hdf5
MergingThe conversion output is merged by merge_chunks.py according to chunk_size, and chunk numbering stays continuous
ArchivingAll chunk files are packed into one archive, tar.gz by default

Export Result​

After an export task finishes, the status can be viewed and the archive downloaded in the export records.

Export task status

Export archive download

Parameters and Fields​

Export Parameters​

The export page provides the following parameters, written according to the --chunk_size and --hz options of the conversion command.

ParameterTypeRequiredDefaultValue rangeDescription
chunk_size (group count)IntegerYes101–100Number of raw files each HDF5 file contains; when set to 1, raw files and chunk files correspond one to one
hz (data refresh rate per second)IntegerYes301–60Each message channel is sampled at equal intervals before writing; the sampling frame grid is fixed at 30 Hz, and the sampling rate only changes the message taken for each frame

The figure below shows the data selection and parameter panel.

Select data on the export page

Directory Structure​

chunk_001.hdf5
├── data/
│ ├── episode_001/
│ │ ├── action
│ │ ├── observation.gripper
│ │ ├── observation.images.<camera>
│ │ └── observation.state
│ └── episode_002/
└── meta/

Under each episode group, datasets are written by field, and the shape starts with the frame count T.

DatasetShapeContent
action(T, D)Issued joint command
observation.state(T, D)Joint observation values
observation.gripper(T, 2)Gripper observation values, by convention [right_gripper, left_gripper]
observation.images.<camera>(T,)One JPEG-encoded image per frame, with elements as uint8 variable-length arrays

Each episode group carries the following attributes.

AttributeTypeDescription
taskStringAnnotated natural language task description
task_zhStringChinese text of the task description
scoreNumberAction quality score, -1 by default

The content of the /meta group differs by input source.

meta contentSourceDescription
Feature metadataio_mcap2hdf5The dtype, shape, and names of each field are written to the meta group attributes
Robot model and URDFio_agibot2hdf5The meta.robot_type attribute and meta/urdf
Camera intrinsics and extrinsicsio_agibot2hdf5meta/camera/<camera>/intrinsic and extrinsic (JSON text)

Reading Method​

h5py can read chunk files directly.

import h5py

with h5py.File("chunk_001.hdf5", "r") as f:
episodes = list(f["data"].keys()) # episode_001, episode_002, ...
episode = f["data/episode_001"]
task = episode.attrs["task"].decode() # natural language task
score = episode.attrs["score"] # action quality score
actions = episode["action"][:] # (T, D)
state = episode["observation.state"][:] # (T, D)
frames = episode["observation.images.camera_01"][:] # JPEG bytes per frame

Basis and Sources​

ItemValueSource
Chunk namingchunk_NNN.hdf5tools/mcap2hdf5/mcap2hdf5.py, tools/agibot2hdf5/convert_to_hdf5.py
chunk_size default10tools/mcap2hdf5/mcap2hdf5.py (--chunk_size)
hz default30tools/mcap2hdf5/mcap2hdf5.py (--hz)
UI value rangechunk_size 1–100, hz 1–60app/app/(dashboard)/(data)/export/hdf5/HDF5ExportClient.tsx
episode naming and attributesepisode_NNN, attributes task, task_zh, scoretools/mcap2hdf5/mcap2hdf5.py, tools/agibot2hdf5/convert_to_hdf5.py
Image encodingJPEG, uint8 variable-length arraytools/mcap2hdf5/mcap2hdf5.py, tools/agibot2hdf5/convert_to_hdf5.py
Archive formattar.gzworker/src/workers/export.ts
Conversion imagesio_mcap2hdf5, io_agibot2hdf5worker/src/docker-check.ts

Limitations​

The import and export of HDF5 data are constrained by the existing boundaries below.

ItemLimitDescription
Ingestion sourcesAgilex, Realman, Dobot, Limx, UnixOnly these sources have an HDF5-to-MCAP converter; other HDF5 recordings cannot be imported
Group count1–100Number of raw files each chunk file contains, as provided by the UI value range
Sampling rate1–60 HzThe sampling frame grid is fixed at 30 Hz, and sampling only changes the message taken for each frame
episode divisionOne episode per subtasks entryWithout a sidecar JSON, the whole recording is a single episode
Missing decodable messagesFile conversion failsWhen both image and joint messages are missing, the file reports an error and is skipped
Image encodingJPEG onlyEach frame is written as JPEG, and the encoding cannot be changed
Archive formattar.gzAll chunks are packed into one archive