VersatIL 0.3.0__py3-none-any.whl

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (349) hide show
  1. versatil/__init__.py +85 -0
  2. versatil/common/__init__.py +1 -0
  3. versatil/common/argparse_compat.py +50 -0
  4. versatil/common/dict_of_tensor_mixin.py +48 -0
  5. versatil/common/logging.py +16 -0
  6. versatil/common/module_attr_mixin.py +17 -0
  7. versatil/common/omegaconf_ops.py +33 -0
  8. versatil/common/set_cache_dir.py +21 -0
  9. versatil/common/tensor_ops.py +126 -0
  10. versatil/configs/__init__.py +1047 -0
  11. versatil/configs/data/__init__.py +0 -0
  12. versatil/configs/data/augmentations.py +134 -0
  13. versatil/configs/data/dataloader.py +60 -0
  14. versatil/configs/data/metadata.py +130 -0
  15. versatil/configs/data/raw/__init__.py +8 -0
  16. versatil/configs/data/raw/schema.py +57 -0
  17. versatil/configs/data/raw/zarr_meta.py +24 -0
  18. versatil/configs/data/task.py +66 -0
  19. versatil/configs/data/tokenizer.py +45 -0
  20. versatil/configs/decoding/__init__.py +0 -0
  21. versatil/configs/decoding/action_head.py +101 -0
  22. versatil/configs/decoding/algorithm.py +124 -0
  23. versatil/configs/decoding/decoder.py +414 -0
  24. versatil/configs/decoding/latent.py +228 -0
  25. versatil/configs/encoding/__init__.py +0 -0
  26. versatil/configs/encoding/encoder.py +196 -0
  27. versatil/configs/encoding/fusion.py +45 -0
  28. versatil/configs/encoding/pipeline.py +18 -0
  29. versatil/configs/experiment.py +33 -0
  30. versatil/configs/inference.py +15 -0
  31. versatil/configs/loss.py +293 -0
  32. versatil/configs/main.py +33 -0
  33. versatil/configs/policy.py +28 -0
  34. versatil/configs/post_training_compression.py +97 -0
  35. versatil/configs/quantization.py +67 -0
  36. versatil/configs/training.py +195 -0
  37. versatil/data/__init__.py +0 -0
  38. versatil/data/constants.py +279 -0
  39. versatil/data/dataloader.py +286 -0
  40. versatil/data/episodic_dataset.py +376 -0
  41. versatil/data/metadata.py +673 -0
  42. versatil/data/normalization/__init__.py +0 -0
  43. versatil/data/normalization/image_normalizer.py +458 -0
  44. versatil/data/normalization/normalizer.py +647 -0
  45. versatil/data/preprocessing/__init__.py +0 -0
  46. versatil/data/preprocessing/codecs.py +96 -0
  47. versatil/data/preprocessing/create_zarr_arrays.py +126 -0
  48. versatil/data/preprocessing/create_zarr_from_csv.py +68 -0
  49. versatil/data/preprocessing/create_zarr_from_hdf5.py +71 -0
  50. versatil/data/preprocessing/create_zarr_from_lerobot.py +57 -0
  51. versatil/data/preprocessing/create_zarr_from_synthetic.py +136 -0
  52. versatil/data/preprocessing/replay_buffer.py +1094 -0
  53. versatil/data/preprocessing/sampler.py +282 -0
  54. versatil/data/processing/__init__.py +0 -0
  55. versatil/data/processing/action_processor.py +354 -0
  56. versatil/data/processing/image_processor.py +102 -0
  57. versatil/data/processing/transform.py +240 -0
  58. versatil/data/processing/transform_builder.py +605 -0
  59. versatil/data/raw/__init__.py +0 -0
  60. versatil/data/raw/schemas/__init__.py +3 -0
  61. versatil/data/raw/schemas/base.py +118 -0
  62. versatil/data/raw/schemas/csv.py +52 -0
  63. versatil/data/raw/schemas/custom/__init__.py +3 -0
  64. versatil/data/raw/schemas/custom/libero.py +184 -0
  65. versatil/data/raw/schemas/custom/synthetic.py +170 -0
  66. versatil/data/raw/schemas/custom/tso.py +321 -0
  67. versatil/data/raw/schemas/hdf5.py +62 -0
  68. versatil/data/raw/schemas/lerobot.py +546 -0
  69. versatil/data/raw/zarr_meta.py +213 -0
  70. versatil/data/sample_builder.py +242 -0
  71. versatil/data/synthetic/__init__.py +3 -0
  72. versatil/data/synthetic/assets/RobotoSerif.ttf +0 -0
  73. versatil/data/synthetic/constants.py +121 -0
  74. versatil/data/synthetic/generators.py +865 -0
  75. versatil/data/synthetic/renderer.py +145 -0
  76. versatil/data/synthetic/task_layout.py +164 -0
  77. versatil/data/synthetic/visualization.py +416 -0
  78. versatil/data/task.py +410 -0
  79. versatil/data/tokenization/__init__.py +17 -0
  80. versatil/data/tokenization/action_tokenizer.py +576 -0
  81. versatil/data/tokenization/binning_tokenizer.py +187 -0
  82. versatil/data/tokenization/fast.py +89 -0
  83. versatil/data/tokenization/observation_tokenizer.py +388 -0
  84. versatil/data/tokenization/tokenizer.py +148 -0
  85. versatil/endpoints/__init__.py +1 -0
  86. versatil/endpoints/explain.py +334 -0
  87. versatil/endpoints/post_training_compress.py +37 -0
  88. versatil/endpoints/test.py +193 -0
  89. versatil/endpoints/train.py +53 -0
  90. versatil/explain/__init__.py +23 -0
  91. versatil/explain/constants.py +11 -0
  92. versatil/explain/explainer.py +526 -0
  93. versatil/inference/__init__.py +1 -0
  94. versatil/inference/action_postprocessor.py +183 -0
  95. versatil/inference/inference_client.py +479 -0
  96. versatil/inference/observation_buffer.py +68 -0
  97. versatil/inference/observation_preprocessor.py +206 -0
  98. versatil/inference/policy_loading/__init__.py +1 -0
  99. versatil/inference/policy_loading/base.py +285 -0
  100. versatil/inference/policy_loading/compressed_loader.py +365 -0
  101. versatil/inference/policy_loading/float_loader.py +130 -0
  102. versatil/inference/protocol.py +69 -0
  103. versatil/inference/socket_transport.py +116 -0
  104. versatil/inference/synthetic_rollout.py +459 -0
  105. versatil/inference/temporal_aggregation.py +112 -0
  106. versatil/metrics/__init__.py +1 -0
  107. versatil/metrics/accumulators.py +391 -0
  108. versatil/metrics/base.py +237 -0
  109. versatil/metrics/components.py +2541 -0
  110. versatil/metrics/composite.py +92 -0
  111. versatil/metrics/constants.py +112 -0
  112. versatil/metrics/kernels.py +278 -0
  113. versatil/metrics/ot_loss.py +457 -0
  114. versatil/metrics/synthetic_metrics.py +302 -0
  115. versatil/models/__init__.py +0 -0
  116. versatil/models/decoding/__init__.py +5 -0
  117. versatil/models/decoding/action_heads/__init__.py +35 -0
  118. versatil/models/decoding/action_heads/base.py +73 -0
  119. versatil/models/decoding/action_heads/blocks.py +180 -0
  120. versatil/models/decoding/action_heads/gaussian.py +62 -0
  121. versatil/models/decoding/action_heads/moe.py +265 -0
  122. versatil/models/decoding/action_heads/single_output.py +27 -0
  123. versatil/models/decoding/action_masking.py +142 -0
  124. versatil/models/decoding/algorithm/__init__.py +1 -0
  125. versatil/models/decoding/algorithm/base.py +115 -0
  126. versatil/models/decoding/algorithm/behavior_cloning.py +73 -0
  127. versatil/models/decoding/algorithm/diffusion.py +249 -0
  128. versatil/models/decoding/algorithm/flow_matching.py +333 -0
  129. versatil/models/decoding/algorithm/variational.py +310 -0
  130. versatil/models/decoding/constants.py +121 -0
  131. versatil/models/decoding/decoders/__init__.py +10 -0
  132. versatil/models/decoding/decoders/base.py +295 -0
  133. versatil/models/decoding/decoders/factory/__init__.py +25 -0
  134. versatil/models/decoding/decoders/factory/act.py +209 -0
  135. versatil/models/decoding/decoders/factory/action_transformer.py +160 -0
  136. versatil/models/decoding/decoders/factory/conditional_action_unet.py +342 -0
  137. versatil/models/decoding/decoders/factory/diffusion_action_transformer.py +335 -0
  138. versatil/models/decoding/decoders/factory/discrete_detr_action_transformer.py +276 -0
  139. versatil/models/decoding/decoders/factory/dit_block_action_transformer.py +295 -0
  140. versatil/models/decoding/decoders/factory/free_action_transformer.py +428 -0
  141. versatil/models/decoding/decoders/factory/gpt_action_transformer.py +541 -0
  142. versatil/models/decoding/decoders/factory/lact.py +263 -0
  143. versatil/models/decoding/decoders/factory/mode_act.py +673 -0
  144. versatil/models/decoding/decoders/factory/moe_free_action_transformer.py +305 -0
  145. versatil/models/decoding/decoders/factory/phase_act.py +172 -0
  146. versatil/models/decoding/decoders/factory/pi0.py +508 -0
  147. versatil/models/decoding/decoders/factory/smolvla.py +667 -0
  148. versatil/models/decoding/decoders/moe.py +174 -0
  149. versatil/models/decoding/decoders/timestep_conditioning.py +143 -0
  150. versatil/models/decoding/latent/__init__.py +41 -0
  151. versatil/models/decoding/latent/posterior/__init__.py +0 -0
  152. versatil/models/decoding/latent/posterior/base_posterior.py +72 -0
  153. versatil/models/decoding/latent/posterior/transformer_encoder.py +273 -0
  154. versatil/models/decoding/latent/posterior/vq_encoder.py +244 -0
  155. versatil/models/decoding/latent/prior/__init__.py +0 -0
  156. versatil/models/decoding/latent/prior/base_prior.py +104 -0
  157. versatil/models/decoding/latent/prior/codebook_prior.py +323 -0
  158. versatil/models/decoding/latent/prior/dit_prior.py +555 -0
  159. versatil/models/decoding/latent/prior/gaussian_prior.py +82 -0
  160. versatil/models/decoding/latent/prior/latent_standardizer.py +127 -0
  161. versatil/models/decoding/latent/prior/state_condition_pool.py +72 -0
  162. versatil/models/decoding/latent/prior/transformer_encoder.py +218 -0
  163. versatil/models/decoding/latent/prior/uniform_codebook_prior.py +190 -0
  164. versatil/models/decoding/latent/prior/vamp_prior.py +339 -0
  165. versatil/models/decoding/latent/protocols.py +23 -0
  166. versatil/models/decoding/latent/reparametrize.py +16 -0
  167. versatil/models/decoding/latent/vq/__init__.py +7 -0
  168. versatil/models/decoding/latent/vq/euclidean_codebook.py +180 -0
  169. versatil/models/decoding/latent/vq/residual_vq.py +148 -0
  170. versatil/models/decoding/latent/vq/vector_quantize.py +99 -0
  171. versatil/models/decoding/mixture_of_experts.py +250 -0
  172. versatil/models/decoding/transformer_input_builder.py +369 -0
  173. versatil/models/decoding/unet_input_builder.py +107 -0
  174. versatil/models/encoding/__init__.py +4 -0
  175. versatil/models/encoding/encoders/__init__.py +0 -0
  176. versatil/models/encoding/encoders/base.py +183 -0
  177. versatil/models/encoding/encoders/conditional.py +157 -0
  178. versatil/models/encoding/encoders/constants.py +171 -0
  179. versatil/models/encoding/encoders/cross_modal/__init__.py +1 -0
  180. versatil/models/encoding/encoders/cross_modal/rgbd/__init__.py +1 -0
  181. versatil/models/encoding/encoders/cross_modal/rgbd/dformerv2.py +424 -0
  182. versatil/models/encoding/encoders/cross_modal/rgbd/geometric_rgbd.py +250 -0
  183. versatil/models/encoding/encoders/cross_modal/vision_language/__init__.py +1 -0
  184. versatil/models/encoding/encoders/cross_modal/vision_language/generative_vlm.py +452 -0
  185. versatil/models/encoding/encoders/cross_modal/vision_language/paligemma.py +109 -0
  186. versatil/models/encoding/encoders/cross_modal/vision_language/smolvlm.py +129 -0
  187. versatil/models/encoding/encoders/cross_modal/vision_language/two_tower_vlm.py +301 -0
  188. versatil/models/encoding/encoders/depth/__init__.py +1 -0
  189. versatil/models/encoding/encoders/depth/spatial.py +249 -0
  190. versatil/models/encoding/encoders/image_mixin.py +161 -0
  191. versatil/models/encoding/encoders/language/__init__.py +5 -0
  192. versatil/models/encoding/encoders/language/language.py +235 -0
  193. versatil/models/encoding/encoders/language_mixin.py +157 -0
  194. versatil/models/encoding/encoders/proprioceptive/__init__.py +5 -0
  195. versatil/models/encoding/encoders/proprioceptive/base.py +148 -0
  196. versatil/models/encoding/encoders/rgb/__init__.py +5 -0
  197. versatil/models/encoding/encoders/rgb/conditional_cnn.py +372 -0
  198. versatil/models/encoding/encoders/rgb/flat.py +199 -0
  199. versatil/models/encoding/encoders/rgb/spatial.py +249 -0
  200. versatil/models/encoding/encoders/unconditional.py +138 -0
  201. versatil/models/encoding/fusion/__init__.py +12 -0
  202. versatil/models/encoding/fusion/attention.py +94 -0
  203. versatil/models/encoding/fusion/base.py +119 -0
  204. versatil/models/encoding/fusion/concat.py +44 -0
  205. versatil/models/encoding/fusion/constants.py +9 -0
  206. versatil/models/encoding/fusion/mlp.py +70 -0
  207. versatil/models/encoding/pipeline.py +399 -0
  208. versatil/models/exportable_policy.py +128 -0
  209. versatil/models/feature_meta.py +58 -0
  210. versatil/models/layers/__init__.py +51 -0
  211. versatil/models/layers/activation.py +50 -0
  212. versatil/models/layers/conditional_unet.py +304 -0
  213. versatil/models/layers/constants.py +35 -0
  214. versatil/models/layers/convert_layers.py +98 -0
  215. versatil/models/layers/convolution/__init__.py +0 -0
  216. versatil/models/layers/convolution/conv1d.py +35 -0
  217. versatil/models/layers/convolution/depthwise_conv2d.py +29 -0
  218. versatil/models/layers/denoising/__init__.py +1 -0
  219. versatil/models/layers/denoising/conditional_flow_matching.py +127 -0
  220. versatil/models/layers/denoising/diffusion_process.py +194 -0
  221. versatil/models/layers/denoising/ode_solvers.py +142 -0
  222. versatil/models/layers/denoising/timestep_sampling.py +195 -0
  223. versatil/models/layers/detr_transformer/__init__.py +20 -0
  224. versatil/models/layers/detr_transformer/attention.py +97 -0
  225. versatil/models/layers/detr_transformer/transformer.py +131 -0
  226. versatil/models/layers/detr_transformer/transformer_decoder.py +208 -0
  227. versatil/models/layers/detr_transformer/transformer_encoder.py +149 -0
  228. versatil/models/layers/diffusion_transformer/__init__.py +45 -0
  229. versatil/models/layers/diffusion_transformer/cross_attention_dit.py +174 -0
  230. versatil/models/layers/diffusion_transformer/dit_block_transformer.py +253 -0
  231. versatil/models/layers/diffusion_transformer/final_prediction_layer.py +68 -0
  232. versatil/models/layers/diffusion_transformer/mmdit_transformer.py +156 -0
  233. versatil/models/layers/drop_path.py +24 -0
  234. versatil/models/layers/dynamic_feature_embedding.py +70 -0
  235. versatil/models/layers/feature_projection.py +233 -0
  236. versatil/models/layers/free_transformer/__init__.py +0 -0
  237. versatil/models/layers/free_transformer/binary_mapper.py +161 -0
  238. versatil/models/layers/free_transformer/free_transformer.py +646 -0
  239. versatil/models/layers/frozen_batchnorm.py +52 -0
  240. versatil/models/layers/gated_linear_unit.py +74 -0
  241. versatil/models/layers/geometric_attention/__init__.py +13 -0
  242. versatil/models/layers/geometric_attention/depth_decay.py +107 -0
  243. versatil/models/layers/geometric_attention/geometric_attention.py +255 -0
  244. versatil/models/layers/geometric_attention/geometric_attention_encoder.py +131 -0
  245. versatil/models/layers/geometric_attention/geometric_bias.py +113 -0
  246. versatil/models/layers/geometric_attention/spatial_decay.py +119 -0
  247. versatil/models/layers/mlp.py +49 -0
  248. versatil/models/layers/modulation/__init__.py +0 -0
  249. versatil/models/layers/modulation/conditional_modulation.py +170 -0
  250. versatil/models/layers/modulation/conditional_residual_block.py +75 -0
  251. versatil/models/layers/modulation/film_residual_block.py +70 -0
  252. versatil/models/layers/normalization/__init__.py +6 -0
  253. versatil/models/layers/normalization/ada_norm.py +62 -0
  254. versatil/models/layers/normalization/constants.py +8 -0
  255. versatil/models/layers/normalization/factory.py +141 -0
  256. versatil/models/layers/normalization/rms_norm.py +61 -0
  257. versatil/models/layers/normalization/typedefs.py +6 -0
  258. versatil/models/layers/normalization/unconditioned_norm.py +25 -0
  259. versatil/models/layers/patch_embedding.py +185 -0
  260. versatil/models/layers/pooling/__init__.py +0 -0
  261. versatil/models/layers/pooling/attention_pooling.py +142 -0
  262. versatil/models/layers/pooling/pooling_head.py +301 -0
  263. versatil/models/layers/pooling/spatial_softmax.py +54 -0
  264. versatil/models/layers/positional_encoding/__init__.py +0 -0
  265. versatil/models/layers/positional_encoding/base.py +205 -0
  266. versatil/models/layers/positional_encoding/learned.py +101 -0
  267. versatil/models/layers/positional_encoding/rotary.py +223 -0
  268. versatil/models/layers/positional_encoding/sinusoidal.py +299 -0
  269. versatil/models/layers/transformer/__init__.py +1 -0
  270. versatil/models/layers/transformer/attention/__init__.py +1 -0
  271. versatil/models/layers/transformer/attention/cached_attention.py +314 -0
  272. versatil/models/layers/transformer/attention/joint_attention.py +193 -0
  273. versatil/models/layers/transformer/attention/joint_attention_base.py +206 -0
  274. versatil/models/layers/transformer/attention/precomputed_joint_attention.py +178 -0
  275. versatil/models/layers/transformer/attention/query_key_norm.py +54 -0
  276. versatil/models/layers/transformer/autoregressive_decoder.py +241 -0
  277. versatil/models/layers/transformer/bidirectional_decoder.py +185 -0
  278. versatil/models/layers/transformer/block/__init__.py +1 -0
  279. versatil/models/layers/transformer/block/base.py +37 -0
  280. versatil/models/layers/transformer/block/cross_attention.py +79 -0
  281. versatil/models/layers/transformer/block/dual_stream_attention.py +98 -0
  282. versatil/models/layers/transformer/block/dual_stream_base.py +30 -0
  283. versatil/models/layers/transformer/block/feedforward.py +87 -0
  284. versatil/models/layers/transformer/block/precomputed_cross_attention.py +79 -0
  285. versatil/models/layers/transformer/block/precomputed_dual_stream_attention.py +91 -0
  286. versatil/models/layers/transformer/block/self_attention.py +60 -0
  287. versatil/models/layers/transformer/cache/__init__.py +16 -0
  288. versatil/models/layers/transformer/cache/conditioning.py +78 -0
  289. versatil/models/layers/transformer/cache/generation.py +103 -0
  290. versatil/models/layers/transformer/conditional_bidirectional_decoder.py +220 -0
  291. versatil/models/layers/transformer/dual_stream_decoder.py +184 -0
  292. versatil/models/layers/transformer/encoder.py +131 -0
  293. versatil/models/layers/transformer/layer/__init__.py +1 -0
  294. versatil/models/layers/transformer/layer/decoder_layer.py +222 -0
  295. versatil/models/layers/transformer/layer/dual_stream_layer.py +163 -0
  296. versatil/models/layers/transformer/layer/encoder_layer.py +136 -0
  297. versatil/models/layers/transformer/layer/precomputed_dual_stream_layer.py +167 -0
  298. versatil/models/layers/transformer/layer/precomputed_kv_layer.py +146 -0
  299. versatil/models/layers/transformer/masking.py +103 -0
  300. versatil/models/layers/transformer/positional_encoding.py +117 -0
  301. versatil/models/layers/transformer/transformer_mixin.py +193 -0
  302. versatil/models/policy.py +507 -0
  303. versatil/post_training_compression/__init__.py +1 -0
  304. versatil/post_training_compression/compression_target.py +53 -0
  305. versatil/post_training_compression/compressor.py +315 -0
  306. versatil/post_training_compression/constants.py +61 -0
  307. versatil/post_training_compression/export.py +122 -0
  308. versatil/post_training_compression/preparation/__init__.py +25 -0
  309. versatil/post_training_compression/preparation/batchnorm.py +141 -0
  310. versatil/post_training_compression/preparation/fusion.py +84 -0
  311. versatil/post_training_compression/pruning/__init__.py +11 -0
  312. versatil/post_training_compression/pruning/base.py +38 -0
  313. versatil/post_training_compression/pruning/structured.py +98 -0
  314. versatil/post_training_compression/pruning/unstructured.py +81 -0
  315. versatil/post_training_compression/report.py +249 -0
  316. versatil/post_training_compression/serialization.py +156 -0
  317. versatil/quantization/__init__.py +13 -0
  318. versatil/quantization/backends/__init__.py +6 -0
  319. versatil/quantization/backends/base.py +62 -0
  320. versatil/quantization/backends/x86_inductor.py +125 -0
  321. versatil/quantization/calibration.py +58 -0
  322. versatil/quantization/constants.py +43 -0
  323. versatil/quantization/quantize.py +102 -0
  324. versatil/quantization/strategies.py +39 -0
  325. versatil/quantization/torch_patches.py +264 -0
  326. versatil/training/__init__.py +1 -0
  327. versatil/training/callbacks/__init__.py +5 -0
  328. versatil/training/callbacks/confusion_matrix.py +103 -0
  329. versatil/training/callbacks/early_stopping.py +14 -0
  330. versatil/training/callbacks/ema.py +206 -0
  331. versatil/training/callbacks/expert_usage.py +92 -0
  332. versatil/training/callbacks/gradient_norm.py +159 -0
  333. versatil/training/callbacks/latent_visualization.py +480 -0
  334. versatil/training/callbacks/prior_target_standardization.py +323 -0
  335. versatil/training/callbacks/provider.py +20 -0
  336. versatil/training/callbacks/reduce_lr_on_plateau.py +106 -0
  337. versatil/training/callbacks/synthetic_rollout.py +214 -0
  338. versatil/training/callbacks/training_stage.py +651 -0
  339. versatil/training/callbacks/wandb_figure.py +26 -0
  340. versatil/training/constants.py +104 -0
  341. versatil/training/lightning_policy.py +332 -0
  342. versatil/training/stage.py +106 -0
  343. versatil/validation.py +453 -0
  344. versatil/workspace.py +660 -0
  345. versatil-0.3.0.dist-info/METADATA +56 -0
  346. versatil-0.3.0.dist-info/RECORD +349 -0
  347. versatil-0.3.0.dist-info/WHEEL +4 -0
  348. versatil-0.3.0.dist-info/entry_points.txt +2 -0
  349. versatil-0.3.0.dist-info/licenses/LICENSE +21 -0
versatil/__init__.py ADDED
@@ -0,0 +1,85 @@
1
+ """VersatIL library."""
2
+
3
+ import logging
4
+ import os
5
+ import warnings
6
+ from pathlib import Path
7
+
8
+ from dotenv import load_dotenv
9
+
10
+ load_dotenv()
11
+
12
+ # Set cache dirs before importing transformers/timm — they read
13
+ CACHE_DIR = Path(os.environ["VERSATIL_CACHE_DIR"])
14
+
15
+
16
+ def setup_cache_directories():
17
+ """Configure cache directories for model downloads."""
18
+ os.environ["HF_HOME"] = str(CACHE_DIR / "huggingface")
19
+ os.environ["HF_HUB_CACHE"] = str(CACHE_DIR / "huggingface" / "hub")
20
+ os.environ["TORCH_HOME"] = str(CACHE_DIR / "torch")
21
+ for cache_path in [
22
+ CACHE_DIR / "huggingface" / "transformers",
23
+ CACHE_DIR / "huggingface" / "hub",
24
+ CACHE_DIR / "torch" / "hub",
25
+ ]:
26
+ cache_path.mkdir(parents=True, exist_ok=True)
27
+
28
+
29
+ setup_cache_directories()
30
+
31
+ import transformers
32
+
33
+ from versatil.quantization.torch_patches import patch_pt2e_python314
34
+
35
+ patch_pt2e_python314()
36
+
37
+ logging.getLogger("timm").setLevel(logging.ERROR)
38
+ logging.getLogger("huggingface_hub").setLevel(logging.ERROR)
39
+ logging.getLogger("httpx").setLevel(logging.WARNING)
40
+ transformers.logging.set_verbosity_error()
41
+
42
+ warnings.filterwarnings(
43
+ "ignore",
44
+ category=UserWarning,
45
+ module="pydantic._internal._generate_schema",
46
+ )
47
+ warnings.filterwarnings("ignore", category=FutureWarning, module="transformers")
48
+ warnings.filterwarnings("ignore", category=UserWarning, module="transformers")
49
+ warnings.filterwarnings("ignore", category=FutureWarning, module="timm")
50
+ warnings.filterwarnings("ignore", category=UserWarning, module="timm")
51
+ warnings.filterwarnings("ignore", category=UserWarning, module="albumentations")
52
+ warnings.filterwarnings("ignore", category=UserWarning, module="hydra")
53
+ warnings.filterwarnings("ignore", message="Trying to infer the `batch_size`")
54
+ warnings.filterwarnings("ignore", category=SyntaxWarning, module="geomloss")
55
+ warnings.filterwarnings("ignore", category=SyntaxWarning, module="torchao")
56
+ warnings.filterwarnings(
57
+ "ignore",
58
+ message="The given buffer is not writable",
59
+ category=UserWarning,
60
+ )
61
+ warnings.filterwarnings(
62
+ "ignore",
63
+ message=".*self.log.*self.trainer.*not registered.*",
64
+ module="pytorch_lightning",
65
+ )
66
+ warnings.filterwarnings(
67
+ "ignore",
68
+ message=".*tensorboardX.*has been removed.*",
69
+ module="pytorch_lightning",
70
+ )
71
+ warnings.filterwarnings(
72
+ "ignore",
73
+ message=".*isinstance.*LeafSpec.*is deprecated.*",
74
+ module="pytorch_lightning",
75
+ )
76
+ warnings.filterwarnings(
77
+ "ignore",
78
+ message="Checkpoint directory.*exists and is not empty",
79
+ module="pytorch_lightning",
80
+ )
81
+ warnings.filterwarnings(
82
+ "ignore",
83
+ message="crc32c usage is deprecated",
84
+ module="numcodecs.*",
85
+ )
@@ -0,0 +1 @@
1
+ """Common functionalities and utilities shared across the codebase."""
@@ -0,0 +1,50 @@
1
+ """Python 3.14 argparse compatibility shim for Hydra 1.3.2.
2
+
3
+ Python 3.14 added ``_ActionsContainer._check_help`` which eagerly validates
4
+ ``help=`` arguments at ``add_argument`` time by calling
5
+ ``formatter._expand_help(action)``. That path performs ``'%' in help_string``,
6
+ which assumes ``help`` is a ``str``. Hydra 1.3.2 passes a
7
+ ``LazyCompletionHelp`` instance (defined inside
8
+ ``hydra._internal.utils.get_args_parser``) that only implements ``__repr__``,
9
+ so the eager check raises ``ValueError('badly formed help string')`` and
10
+ prevents any Hydra endpoint from starting on Python 3.14.
11
+
12
+ This module restores the pre-3.14 deferred behavior only for non-string
13
+ ``help`` values: string help strings still go through the stock check, so
14
+ genuinely malformed strings are still caught.
15
+
16
+ Import this module once before ``import hydra``.
17
+
18
+ Upstream status
19
+ ---------------
20
+ - Hydra issue: https://github.com/facebookresearch/hydra/issues/3121
21
+ (open, same traceback, unresolved in 1.3.2)
22
+ - Hydra fix: https://github.com/facebookresearch/hydra/pull/3090
23
+ (merged 2025-10-28 into ``main``, targets ``1.4.0.dev``, not on PyPI).
24
+ The upstream fix uses the same approach — temporarily disabling
25
+ ``argparse.ArgumentParser._check_help``.
26
+ - Release tracker: https://github.com/facebookresearch/hydra/issues/3125
27
+ (asking for a 1.4 release; no release yet)
28
+ - CPython: the eager ``_check_help`` was added in CPython PR #141940 and is
29
+ not flagged as a breaking change in the Python 3.14 "What's New" notes.
30
+
31
+ This shim can be removed once ``hydra-core >= 1.4`` is released on PyPI
32
+ and the project bumps the pin in ``pyproject.toml``.
33
+ """
34
+
35
+ import argparse
36
+
37
+
38
+ def _install() -> None:
39
+ original_check_help = argparse._ActionsContainer._check_help
40
+
41
+ def _check_help_string_only(
42
+ self: argparse._ActionsContainer, action: argparse.Action
43
+ ) -> None:
44
+ if action.help is None or isinstance(action.help, str):
45
+ original_check_help(self, action)
46
+
47
+ argparse._ActionsContainer._check_help = _check_help_string_only # type: ignore[method-assign]
48
+
49
+
50
+ _install()
@@ -0,0 +1,48 @@
1
+ """Mixin for nn.Module that stores and loads nested ParameterDict state."""
2
+
3
+ import torch
4
+ import torch.nn as nn
5
+
6
+
7
+ class DictOfTensorMixin(nn.Module):
8
+ def __init__(self, params_dict=None):
9
+ super().__init__()
10
+ if params_dict is None:
11
+ params_dict = nn.ParameterDict()
12
+ self.params_dict = params_dict
13
+ self.register_buffer("_device_tracker", torch.zeros(1))
14
+
15
+ @property
16
+ def device(self):
17
+ return self._device_tracker.device
18
+
19
+ def _load_from_state_dict(
20
+ self,
21
+ state_dict,
22
+ prefix,
23
+ local_metadata,
24
+ strict,
25
+ missing_keys,
26
+ unexpected_keys,
27
+ error_msgs,
28
+ ):
29
+ def dfs_add(dest, keys, value: torch.Tensor):
30
+ if len(keys) == 1:
31
+ dest[keys[0]] = value
32
+ return
33
+
34
+ if keys[0] not in dest:
35
+ dest[keys[0]] = nn.ParameterDict()
36
+ dfs_add(dest[keys[0]], keys[1:], value)
37
+
38
+ def load_dict(state_dict, prefix):
39
+ out_dict = nn.ParameterDict()
40
+ for key, value in state_dict.items():
41
+ if key.startswith(prefix):
42
+ param_keys = key[len(prefix) :].split(".")[1:]
43
+ dfs_add(out_dict, param_keys, value.clone())
44
+ return out_dict
45
+
46
+ self.params_dict = load_dict(state_dict, prefix + "params_dict")
47
+ self.params_dict.requires_grad_(False)
48
+ return
@@ -0,0 +1,16 @@
1
+ """Logging utilities for VersatIL endpoints."""
2
+
3
+ import logging
4
+
5
+ LOG_FORMAT = "%(asctime)s %(module)s %(levelname)s %(message)s"
6
+
7
+
8
+ def override_log_format() -> None:
9
+ """Replace the log formatter on all root handlers.
10
+
11
+ Call after Hydra's ``@hydra.main`` has configured logging,
12
+ so the format shows the source module instead of ``root``.
13
+ """
14
+ formatter = logging.Formatter(LOG_FORMAT)
15
+ for handler in logging.root.handlers:
16
+ handler.setFormatter(formatter)
@@ -0,0 +1,17 @@
1
+ """Mixin for nn.Module that exposes device and dtype properties."""
2
+
3
+ import torch.nn as nn
4
+
5
+
6
+ class ModuleAttrMixin(nn.Module):
7
+ def __init__(self):
8
+ super().__init__()
9
+ self._dummy_variable = nn.Parameter()
10
+
11
+ @property
12
+ def device(self):
13
+ return next(iter(self.parameters())).device
14
+
15
+ @property
16
+ def dtype(self):
17
+ return next(iter(self.parameters())).dtype
@@ -0,0 +1,33 @@
1
+ """OmegaConf utility operations."""
2
+
3
+ from collections.abc import Mapping
4
+ from typing import Any
5
+
6
+ from omegaconf import OmegaConf
7
+
8
+
9
+ def resolve_dict_keys(d: Mapping[Any, Any]) -> dict[Any, Any]:
10
+ """Resolve any OmegaConf interpolations in dictionary keys recursively.
11
+
12
+ OmegaConf doesn't resolve interpolations in dict keys by default.
13
+ This function resolves keys like '${cameras:AGENTVIEW}' to 'agentview_rgb'.
14
+
15
+ Args:
16
+ d: Dictionary with potentially unresolved interpolation keys.
17
+
18
+ Returns:
19
+ New dictionary with resolved keys.
20
+ """
21
+ resolved = {}
22
+ for key, value in d.items():
23
+ if isinstance(key, str) and key.startswith("${") and key.endswith("}"):
24
+ temp_cfg = OmegaConf.create({"_key": key})
25
+ OmegaConf.resolve(temp_cfg)
26
+ resolved_key = OmegaConf.select(temp_cfg, "_key")
27
+ else:
28
+ resolved_key = key
29
+ resolved_value = (
30
+ resolve_dict_keys(value) if isinstance(value, Mapping) else value
31
+ )
32
+ resolved[resolved_key] = resolved_value
33
+ return resolved
@@ -0,0 +1,21 @@
1
+ """Configuration of HuggingFace and Torch cache directories."""
2
+
3
+ import os
4
+ from pathlib import Path
5
+
6
+
7
+ def setup_cache_directories(cache_dir: str | Path):
8
+ """Configure cache directories for model downloads before any run."""
9
+ # Convert to Path for consistent handling
10
+ cache_path = Path(cache_dir)
11
+
12
+ os.environ["HF_HOME"] = str(cache_path / "huggingface")
13
+ os.environ["HF_HUB_CACHE"] = str(cache_path / "huggingface" / "hub")
14
+ os.environ["TORCH_HOME"] = str(cache_path / "torch")
15
+
16
+ for dir_path in [
17
+ cache_path / "huggingface" / "transformers",
18
+ cache_path / "huggingface" / "hub",
19
+ cache_path / "torch" / "hub",
20
+ ]:
21
+ dir_path.mkdir(parents=True, exist_ok=True)
@@ -0,0 +1,126 @@
1
+ """Tensor container utilities used across VersatIL."""
2
+
3
+ from collections import OrderedDict
4
+ from collections.abc import Callable
5
+
6
+ import torch
7
+
8
+ type NestedDictionary[Leaf] = dict[str, Leaf | NestedDictionary[Leaf]]
9
+ type TensorTree = (
10
+ torch.Tensor
11
+ | str
12
+ | None
13
+ | dict[str, TensorTree]
14
+ | OrderedDict[str, TensorTree]
15
+ | list[TensorTree]
16
+ | tuple[TensorTree, ...]
17
+ )
18
+ type TensorTreeHandlerMap = dict[type, Callable[[TensorTree], TensorTree]]
19
+
20
+
21
+ def dict_apply[LeafInput, LeafOutput](
22
+ data: NestedDictionary[LeafInput],
23
+ transform: Callable[[LeafInput], LeafOutput],
24
+ ) -> NestedDictionary[LeafOutput]:
25
+ """Apply a transform to every leaf in a nested dictionary.
26
+
27
+ Args:
28
+ data: Nested dictionary whose leaves should be transformed.
29
+ transform: Function applied to each leaf value.
30
+
31
+ Returns:
32
+ Nested dictionary with the same keys and transformed leaf values.
33
+ """
34
+ result = {}
35
+ for key, value in data.items():
36
+ if isinstance(value, dict):
37
+ result[key] = dict_apply(data=value, transform=transform)
38
+ else:
39
+ result[key] = transform(value)
40
+ return result
41
+
42
+
43
+ def tensor_to_str(tensor: torch.Tensor) -> str:
44
+ """Format a tensor as a compact numeric list for logs.
45
+
46
+ Args:
47
+ tensor: Tensor to format. Scalars are treated as one-element tensors.
48
+
49
+ Returns:
50
+ String with each value formatted to three significant digits.
51
+ """
52
+ flat_tensor = tensor.flatten()
53
+ return "[" + ", ".join([f"{value.item():.3g}" for value in flat_tensor]) + "]"
54
+
55
+
56
+ def recursive_dict_list_tuple_apply(
57
+ data: TensorTree,
58
+ type_handler_map: TensorTreeHandlerMap,
59
+ ) -> TensorTree:
60
+ """Apply type-specific handlers to leaves inside nested containers.
61
+
62
+ Args:
63
+ data: Tensor tree containing dictionaries, sequences, and supported leaves.
64
+ type_handler_map: Mapping from leaf type to its transform function.
65
+
66
+ Returns:
67
+ Tensor tree with handlers applied to matching leaves.
68
+
69
+ Raises:
70
+ ValueError: If a container type is passed as a leaf handler.
71
+ NotImplementedError: If a leaf value has no matching handler.
72
+ """
73
+ if isinstance(data, (dict, OrderedDict)):
74
+ if dict in type_handler_map:
75
+ raise ValueError("dict cannot be handled by type_func_dict")
76
+ return OrderedDict(
77
+ [
78
+ (
79
+ key,
80
+ recursive_dict_list_tuple_apply(
81
+ data=value,
82
+ type_handler_map=type_handler_map,
83
+ ),
84
+ )
85
+ for key, value in data.items()
86
+ ]
87
+ )
88
+
89
+ if isinstance(data, (list, tuple)):
90
+ if list in type_handler_map or tuple in type_handler_map:
91
+ raise ValueError("list/tuple cannot be handled by type_func_dict")
92
+ return type(data)(
93
+ [
94
+ recursive_dict_list_tuple_apply(
95
+ data=value,
96
+ type_handler_map=type_handler_map,
97
+ )
98
+ for value in data
99
+ ]
100
+ )
101
+
102
+ for leaf_type, handler in type_handler_map.items():
103
+ if isinstance(data, leaf_type):
104
+ return handler(data)
105
+
106
+ raise NotImplementedError(f"Unsupported type: {type(data)}")
107
+
108
+
109
+ def to_device(data: TensorTree, device: torch.device | str) -> TensorTree:
110
+ """Move every tensor in a nested container to a device.
111
+
112
+ Args:
113
+ data: Tensor tree containing tensors and pass-through string or None leaves.
114
+ device: Destination device.
115
+
116
+ Returns:
117
+ Tensor tree with all tensor leaves moved to the destination device.
118
+ """
119
+ return recursive_dict_list_tuple_apply(
120
+ data=data,
121
+ type_handler_map={
122
+ torch.Tensor: lambda tensor: tensor.to(device),
123
+ str: lambda value: value,
124
+ type(None): lambda value: value,
125
+ },
126
+ )