datahike-browser-tests 1.0.0

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 (324) hide show
  1. package/.circleci/config.yml +405 -0
  2. package/.circleci/scripts/gen_ci.clj +194 -0
  3. package/.cirrus.yml +60 -0
  4. package/.clj-kondo/babashka/sci/config.edn +1 -0
  5. package/.clj-kondo/babashka/sci/sci/core.clj +9 -0
  6. package/.clj-kondo/config.edn +95 -0
  7. package/.dir-locals.el +2 -0
  8. package/.github/FUNDING.yml +3 -0
  9. package/.github/ISSUE_TEMPLATE/1-bug-report.yml +68 -0
  10. package/.github/ISSUE_TEMPLATE/2-feature-request.yml +28 -0
  11. package/.github/ISSUE_TEMPLATE/config.yml +6 -0
  12. package/.github/pull_request_template.md +24 -0
  13. package/.github/workflows/native-image.yml +84 -0
  14. package/LICENSE +203 -0
  15. package/README.md +273 -0
  16. package/bb/deps.edn +9 -0
  17. package/bb/resources/github-fingerprints +3 -0
  18. package/bb/resources/native-image-tests/run-bb-pod-tests.clj +162 -0
  19. package/bb/resources/native-image-tests/run-libdatahike-tests +12 -0
  20. package/bb/resources/native-image-tests/run-native-image-tests +74 -0
  21. package/bb/resources/native-image-tests/run-python-tests +22 -0
  22. package/bb/resources/native-image-tests/testconfig.attr-refs.edn +6 -0
  23. package/bb/resources/native-image-tests/testconfig.edn +5 -0
  24. package/bb/resources/template/.settings/org.eclipse.jdt.apt.core.prefs +2 -0
  25. package/bb/resources/template/.settings/org.eclipse.jdt.core.prefs +9 -0
  26. package/bb/resources/template/.settings/org.eclipse.m2e.core.prefs +4 -0
  27. package/bb/resources/template/pom.xml +22 -0
  28. package/bb/src/tools/build.clj +132 -0
  29. package/bb/src/tools/clj_kondo.clj +32 -0
  30. package/bb/src/tools/deploy.clj +26 -0
  31. package/bb/src/tools/examples.clj +19 -0
  32. package/bb/src/tools/npm.clj +100 -0
  33. package/bb/src/tools/python.clj +14 -0
  34. package/bb/src/tools/release.clj +94 -0
  35. package/bb/src/tools/test.clj +148 -0
  36. package/bb/src/tools/version.clj +47 -0
  37. package/bb.edn +269 -0
  38. package/benchmark/src/benchmark/cli.clj +195 -0
  39. package/benchmark/src/benchmark/compare.clj +157 -0
  40. package/benchmark/src/benchmark/config.clj +316 -0
  41. package/benchmark/src/benchmark/measure.clj +187 -0
  42. package/benchmark/src/benchmark/store.clj +190 -0
  43. package/benchmark/test/benchmark/measure_test.clj +156 -0
  44. package/build.clj +30 -0
  45. package/config.edn +49 -0
  46. package/deps.edn +138 -0
  47. package/dev/sandbox.clj +82 -0
  48. package/dev/sandbox.cljs +127 -0
  49. package/dev/sandbox_benchmarks.clj +27 -0
  50. package/dev/sandbox_client.clj +87 -0
  51. package/dev/sandbox_transact_bench.clj +109 -0
  52. package/dev/user.clj +79 -0
  53. package/doc/README.md +96 -0
  54. package/doc/adl/README.md +6 -0
  55. package/doc/adl/adr-000-adr.org +28 -0
  56. package/doc/adl/adr-001-attribute-references.org +15 -0
  57. package/doc/adl/adr-002-build-tooling.org +54 -0
  58. package/doc/adl/adr-003-db-meta-data.md +52 -0
  59. package/doc/adl/adr-004-github-flow.md +40 -0
  60. package/doc/adl/adr-XYZ-template.md +30 -0
  61. package/doc/adl/index.org +3 -0
  62. package/doc/assets/datahike-logo.svg +3 -0
  63. package/doc/assets/datahiking-invoice.org +85 -0
  64. package/doc/assets/hhtree2.png +0 -0
  65. package/doc/assets/network_topology.svg +624 -0
  66. package/doc/assets/perf.png +0 -0
  67. package/doc/assets/schema_mindmap.mm +132 -0
  68. package/doc/assets/schema_mindmap.svg +970 -0
  69. package/doc/assets/temporal_index.mm +74 -0
  70. package/doc/backend-development.md +78 -0
  71. package/doc/bb-pod.md +89 -0
  72. package/doc/benchmarking.md +360 -0
  73. package/doc/bindings/edn-conversion.md +383 -0
  74. package/doc/cli.md +162 -0
  75. package/doc/cljdoc.edn +27 -0
  76. package/doc/cljs-support.md +133 -0
  77. package/doc/config.md +406 -0
  78. package/doc/contributing.md +114 -0
  79. package/doc/datalog-vs-sql.md +210 -0
  80. package/doc/datomic_differences.md +109 -0
  81. package/doc/development/pull-api-ns.md +186 -0
  82. package/doc/development/pull-frame-state-diagram.jpg +0 -0
  83. package/doc/distributed.md +566 -0
  84. package/doc/entity_spec.md +92 -0
  85. package/doc/gc.md +273 -0
  86. package/doc/java-api.md +808 -0
  87. package/doc/javascript-api.md +421 -0
  88. package/doc/libdatahike.md +86 -0
  89. package/doc/logging_and_error_handling.md +43 -0
  90. package/doc/norms.md +66 -0
  91. package/doc/schema-migration.md +85 -0
  92. package/doc/schema.md +287 -0
  93. package/doc/storage-backends.md +363 -0
  94. package/doc/store-id-refactoring.md +596 -0
  95. package/doc/time_variance.md +325 -0
  96. package/doc/unstructured.md +167 -0
  97. package/doc/versioning.md +261 -0
  98. package/examples/basic/README.md +19 -0
  99. package/examples/basic/deps.edn +6 -0
  100. package/examples/basic/docker-compose.yml +13 -0
  101. package/examples/basic/src/examples/core.clj +60 -0
  102. package/examples/basic/src/examples/schema.clj +155 -0
  103. package/examples/basic/src/examples/store.clj +60 -0
  104. package/examples/basic/src/examples/time_travel.clj +185 -0
  105. package/examples/java/.settings/org.eclipse.core.resources.prefs +3 -0
  106. package/examples/java/.settings/org.eclipse.jdt.apt.core.prefs +2 -0
  107. package/examples/java/.settings/org.eclipse.jdt.core.prefs +9 -0
  108. package/examples/java/.settings/org.eclipse.m2e.core.prefs +4 -0
  109. package/examples/java/README.md +162 -0
  110. package/examples/java/pom.xml +62 -0
  111. package/examples/java/src/main/java/examples/QuickStart.java +115 -0
  112. package/examples/java/src/main/java/examples/SchemaExample.java +148 -0
  113. package/examples/java/src/main/java/examples/TimeTravelExample.java +121 -0
  114. package/flake.lock +27 -0
  115. package/flake.nix +27 -0
  116. package/http-server/datahike/http/middleware.clj +75 -0
  117. package/http-server/datahike/http/server.clj +269 -0
  118. package/java/src/datahike/java/Database.java +274 -0
  119. package/java/src/datahike/java/Datahike.java +281 -0
  120. package/java/src/datahike/java/DatahikeGeneratedTest.java +349 -0
  121. package/java/src/datahike/java/DatahikeTest.java +370 -0
  122. package/java/src/datahike/java/EDN.java +170 -0
  123. package/java/src/datahike/java/IEntity.java +11 -0
  124. package/java/src/datahike/java/Keywords.java +161 -0
  125. package/java/src/datahike/java/SchemaFlexibility.java +52 -0
  126. package/java/src/datahike/java/Util.java +219 -0
  127. package/karma.conf.js +19 -0
  128. package/libdatahike/compile-cpp +7 -0
  129. package/libdatahike/src/datahike/impl/LibDatahikeBase.java +203 -0
  130. package/libdatahike/src/datahike/impl/libdatahike.clj +59 -0
  131. package/libdatahike/src/test_cpp.cpp +61 -0
  132. package/npm-package/PUBLISHING.md +140 -0
  133. package/npm-package/README.md +226 -0
  134. package/npm-package/package.template.json +34 -0
  135. package/npm-package/test-isomorphic.ts +281 -0
  136. package/npm-package/test.js +557 -0
  137. package/npm-package/typescript-test.ts +70 -0
  138. package/package.json +16 -0
  139. package/pydatahike/README.md +569 -0
  140. package/pydatahike/pyproject.toml +91 -0
  141. package/pydatahike/setup.py +42 -0
  142. package/pydatahike/src/datahike/__init__.py +134 -0
  143. package/pydatahike/src/datahike/_native.py +250 -0
  144. package/pydatahike/src/datahike/_version.py +2 -0
  145. package/pydatahike/src/datahike/database.py +722 -0
  146. package/pydatahike/src/datahike/edn.py +311 -0
  147. package/pydatahike/src/datahike/py.typed +0 -0
  148. package/pydatahike/tests/conftest.py +17 -0
  149. package/pydatahike/tests/test_basic.py +170 -0
  150. package/pydatahike/tests/test_database.py +51 -0
  151. package/pydatahike/tests/test_edn_conversion.py +299 -0
  152. package/pydatahike/tests/test_query.py +99 -0
  153. package/pydatahike/tests/test_schema.py +55 -0
  154. package/resources/clj-kondo.exports/io.replikativ/datahike/config.edn +5 -0
  155. package/resources/example_server.edn +4 -0
  156. package/shadow-cljs.edn +56 -0
  157. package/src/data_readers.clj +7 -0
  158. package/src/datahike/api/impl.cljc +176 -0
  159. package/src/datahike/api/specification.cljc +633 -0
  160. package/src/datahike/api/types.cljc +261 -0
  161. package/src/datahike/api.cljc +41 -0
  162. package/src/datahike/array.cljc +99 -0
  163. package/src/datahike/cli.clj +166 -0
  164. package/src/datahike/cljs.cljs +6 -0
  165. package/src/datahike/codegen/cli.clj +406 -0
  166. package/src/datahike/codegen/clj_kondo.clj +291 -0
  167. package/src/datahike/codegen/java.clj +403 -0
  168. package/src/datahike/codegen/naming.cljc +33 -0
  169. package/src/datahike/codegen/native.clj +559 -0
  170. package/src/datahike/codegen/pod.clj +488 -0
  171. package/src/datahike/codegen/python.clj +838 -0
  172. package/src/datahike/codegen/report.clj +55 -0
  173. package/src/datahike/codegen/typescript.clj +262 -0
  174. package/src/datahike/codegen/validation.clj +145 -0
  175. package/src/datahike/config.cljc +294 -0
  176. package/src/datahike/connections.cljc +16 -0
  177. package/src/datahike/connector.cljc +265 -0
  178. package/src/datahike/constants.cljc +142 -0
  179. package/src/datahike/core.cljc +297 -0
  180. package/src/datahike/datom.cljc +459 -0
  181. package/src/datahike/db/interface.cljc +119 -0
  182. package/src/datahike/db/search.cljc +305 -0
  183. package/src/datahike/db/transaction.cljc +937 -0
  184. package/src/datahike/db/utils.cljc +338 -0
  185. package/src/datahike/db.cljc +956 -0
  186. package/src/datahike/experimental/unstructured.cljc +126 -0
  187. package/src/datahike/experimental/versioning.cljc +172 -0
  188. package/src/datahike/externs.js +31 -0
  189. package/src/datahike/gc.cljc +69 -0
  190. package/src/datahike/http/client.clj +188 -0
  191. package/src/datahike/http/writer.clj +79 -0
  192. package/src/datahike/impl/entity.cljc +218 -0
  193. package/src/datahike/index/interface.cljc +93 -0
  194. package/src/datahike/index/persistent_set.cljc +469 -0
  195. package/src/datahike/index/utils.cljc +44 -0
  196. package/src/datahike/index.cljc +32 -0
  197. package/src/datahike/js/api.cljs +172 -0
  198. package/src/datahike/js/api_macros.clj +22 -0
  199. package/src/datahike/js.cljs +163 -0
  200. package/src/datahike/json.cljc +209 -0
  201. package/src/datahike/lru.cljc +146 -0
  202. package/src/datahike/migrate.clj +39 -0
  203. package/src/datahike/norm/norm.clj +245 -0
  204. package/src/datahike/online_gc.cljc +252 -0
  205. package/src/datahike/pod.clj +155 -0
  206. package/src/datahike/pull_api.cljc +325 -0
  207. package/src/datahike/query.cljc +1945 -0
  208. package/src/datahike/query_stats.cljc +88 -0
  209. package/src/datahike/readers.cljc +62 -0
  210. package/src/datahike/remote.cljc +218 -0
  211. package/src/datahike/schema.cljc +228 -0
  212. package/src/datahike/schema_cache.cljc +42 -0
  213. package/src/datahike/spec.cljc +101 -0
  214. package/src/datahike/store.cljc +80 -0
  215. package/src/datahike/tools.cljc +308 -0
  216. package/src/datahike/transit.cljc +80 -0
  217. package/src/datahike/writer.cljc +239 -0
  218. package/src/datahike/writing.cljc +362 -0
  219. package/src/deps.cljs +1 -0
  220. package/src-hitchhiker-tree/datahike/index/hitchhiker_tree/insert.cljc +76 -0
  221. package/src-hitchhiker-tree/datahike/index/hitchhiker_tree/upsert.cljc +128 -0
  222. package/src-hitchhiker-tree/datahike/index/hitchhiker_tree.cljc +213 -0
  223. package/test/datahike/backward_compatibility_test/src/backward_test.clj +37 -0
  224. package/test/datahike/integration_test/config_record_file_test.clj +14 -0
  225. package/test/datahike/integration_test/config_record_test.clj +14 -0
  226. package/test/datahike/integration_test/depr_config_uri_test.clj +15 -0
  227. package/test/datahike/integration_test/return_map_test.clj +62 -0
  228. package/test/datahike/integration_test.cljc +67 -0
  229. package/test/datahike/norm/norm_test.clj +124 -0
  230. package/test/datahike/norm/resources/naming-and-sorting-test/001-a1-example.edn +5 -0
  231. package/test/datahike/norm/resources/naming-and-sorting-test/002-a2-example.edn +5 -0
  232. package/test/datahike/norm/resources/naming-and-sorting-test/003-tx-fn-test.edn +1 -0
  233. package/test/datahike/norm/resources/naming-and-sorting-test/004-tx-data-and-tx-fn-test.edn +5 -0
  234. package/test/datahike/norm/resources/naming-and-sorting-test/01-transact-basic-characters.edn +2 -0
  235. package/test/datahike/norm/resources/naming-and-sorting-test/02 add occupation.edn +5 -0
  236. package/test/datahike/norm/resources/naming-and-sorting-test/checksums.edn +12 -0
  237. package/test/datahike/norm/resources/simple-test/001-a1-example.edn +5 -0
  238. package/test/datahike/norm/resources/simple-test/002-a2-example.edn +5 -0
  239. package/test/datahike/norm/resources/simple-test/checksums.edn +4 -0
  240. package/test/datahike/norm/resources/tx-data-and-tx-fn-test/first/001-a1-example.edn +5 -0
  241. package/test/datahike/norm/resources/tx-data-and-tx-fn-test/first/002-a2-example.edn +5 -0
  242. package/test/datahike/norm/resources/tx-data-and-tx-fn-test/first/003-tx-fn-test.edn +1 -0
  243. package/test/datahike/norm/resources/tx-data-and-tx-fn-test/first/checksums.edn +6 -0
  244. package/test/datahike/norm/resources/tx-data-and-tx-fn-test/second/004-tx-data-and-tx-fn-test.edn +5 -0
  245. package/test/datahike/norm/resources/tx-data-and-tx-fn-test/second/checksums.edn +2 -0
  246. package/test/datahike/norm/resources/tx-fn-test/first/001-a1-example.edn +5 -0
  247. package/test/datahike/norm/resources/tx-fn-test/first/002-a2-example.edn +5 -0
  248. package/test/datahike/norm/resources/tx-fn-test/first/checksums.edn +4 -0
  249. package/test/datahike/norm/resources/tx-fn-test/second/003-tx-fn-test.edn +1 -0
  250. package/test/datahike/norm/resources/tx-fn-test/second/checksums.edn +2 -0
  251. package/test/datahike/test/api_test.cljc +895 -0
  252. package/test/datahike/test/array_test.cljc +40 -0
  253. package/test/datahike/test/attribute_refs/datoms_test.cljc +140 -0
  254. package/test/datahike/test/attribute_refs/db_test.cljc +42 -0
  255. package/test/datahike/test/attribute_refs/differences_test.cljc +515 -0
  256. package/test/datahike/test/attribute_refs/entity_test.cljc +89 -0
  257. package/test/datahike/test/attribute_refs/pull_api_test.cljc +320 -0
  258. package/test/datahike/test/attribute_refs/query_find_specs_test.cljc +59 -0
  259. package/test/datahike/test/attribute_refs/query_fns_test.cljc +130 -0
  260. package/test/datahike/test/attribute_refs/query_interop_test.cljc +47 -0
  261. package/test/datahike/test/attribute_refs/query_not_test.cljc +193 -0
  262. package/test/datahike/test/attribute_refs/query_or_test.cljc +137 -0
  263. package/test/datahike/test/attribute_refs/query_pull_test.cljc +156 -0
  264. package/test/datahike/test/attribute_refs/query_rules_test.cljc +176 -0
  265. package/test/datahike/test/attribute_refs/query_test.cljc +241 -0
  266. package/test/datahike/test/attribute_refs/temporal_search.cljc +22 -0
  267. package/test/datahike/test/attribute_refs/transact_test.cljc +220 -0
  268. package/test/datahike/test/attribute_refs/utils.cljc +128 -0
  269. package/test/datahike/test/cache_test.cljc +38 -0
  270. package/test/datahike/test/components_test.cljc +92 -0
  271. package/test/datahike/test/config_test.cljc +158 -0
  272. package/test/datahike/test/core_test.cljc +105 -0
  273. package/test/datahike/test/datom_test.cljc +44 -0
  274. package/test/datahike/test/db_test.cljc +54 -0
  275. package/test/datahike/test/entity_spec_test.cljc +159 -0
  276. package/test/datahike/test/entity_test.cljc +103 -0
  277. package/test/datahike/test/explode_test.cljc +143 -0
  278. package/test/datahike/test/filter_test.cljc +75 -0
  279. package/test/datahike/test/gc_test.cljc +159 -0
  280. package/test/datahike/test/http/server_test.clj +192 -0
  281. package/test/datahike/test/http/writer_test.clj +86 -0
  282. package/test/datahike/test/ident_test.cljc +32 -0
  283. package/test/datahike/test/index_test.cljc +345 -0
  284. package/test/datahike/test/insert.cljc +125 -0
  285. package/test/datahike/test/java_bindings_test.clj +6 -0
  286. package/test/datahike/test/listen_test.cljc +41 -0
  287. package/test/datahike/test/lookup_refs_test.cljc +266 -0
  288. package/test/datahike/test/lru_test.cljc +27 -0
  289. package/test/datahike/test/migrate_test.clj +297 -0
  290. package/test/datahike/test/model/core.cljc +376 -0
  291. package/test/datahike/test/model/invariant.cljc +142 -0
  292. package/test/datahike/test/model/rng.cljc +82 -0
  293. package/test/datahike/test/model_test.clj +217 -0
  294. package/test/datahike/test/nodejs_test.cljs +262 -0
  295. package/test/datahike/test/online_gc_test.cljc +475 -0
  296. package/test/datahike/test/pod_test.clj +369 -0
  297. package/test/datahike/test/pull_api_test.cljc +474 -0
  298. package/test/datahike/test/purge_test.cljc +144 -0
  299. package/test/datahike/test/query_aggregates_test.cljc +101 -0
  300. package/test/datahike/test/query_find_specs_test.cljc +52 -0
  301. package/test/datahike/test/query_fns_test.cljc +523 -0
  302. package/test/datahike/test/query_interop_test.cljc +47 -0
  303. package/test/datahike/test/query_not_test.cljc +189 -0
  304. package/test/datahike/test/query_or_test.cljc +158 -0
  305. package/test/datahike/test/query_pull_test.cljc +147 -0
  306. package/test/datahike/test/query_rules_test.cljc +248 -0
  307. package/test/datahike/test/query_stats_test.cljc +218 -0
  308. package/test/datahike/test/query_test.cljc +984 -0
  309. package/test/datahike/test/schema_test.cljc +424 -0
  310. package/test/datahike/test/specification_test.cljc +30 -0
  311. package/test/datahike/test/store_test.cljc +78 -0
  312. package/test/datahike/test/stress_test.cljc +57 -0
  313. package/test/datahike/test/time_variance_test.cljc +518 -0
  314. package/test/datahike/test/tools_test.clj +134 -0
  315. package/test/datahike/test/transact_test.cljc +518 -0
  316. package/test/datahike/test/tuples_test.cljc +564 -0
  317. package/test/datahike/test/unstructured_test.cljc +291 -0
  318. package/test/datahike/test/upsert_impl_test.cljc +205 -0
  319. package/test/datahike/test/upsert_test.cljc +363 -0
  320. package/test/datahike/test/utils.cljc +110 -0
  321. package/test/datahike/test/validation_test.cljc +48 -0
  322. package/test/datahike/test/versioning_test.cljc +56 -0
  323. package/test/datahike/test.cljc +66 -0
  324. package/tests.edn +24 -0
@@ -0,0 +1,363 @@
1
+ # Storage Backends
2
+
3
+ Datahike provides pluggable storage through [konserve](https://github.com/replikativ/konserve), allowing you to choose the backend that best fits your deployment model and performance requirements.
4
+
5
+ ## Quick Reference
6
+
7
+ | Backend | Best For | Distribution | Durability | Write Throughput |
8
+ |---------|----------|--------------|------------|------------------|
9
+ | **File** | Unix tools, rsync, git-like workflows | Single machine | High | Good |
10
+ | **LMDB** | High-performance single machine | Single filesystem | High | Excellent |
11
+ | **Memory** | Testing, ephemeral data | Single process | None | Excellent |
12
+ | **JDBC** | Existing SQL infrastructure | Multi-machine | High | Good |
13
+ | **Redis** | High write throughput | Multi-machine | Medium | Excellent |
14
+ | **S3** | Distributed scale-out, cost-effective | Multi-region | Very high | Good |
15
+ | **GCS** | Google Cloud scale-out | Multi-region | Very high | Good |
16
+ | **DynamoDB** | Low latency, AWS-native | Multi-region | Very high | Excellent (expensive) |
17
+ | **IndexedDB** | Browser persistence | Browser | Medium | Good |
18
+
19
+ ## Local Backends
20
+
21
+ ### File Backend
22
+
23
+ **Use when**: You want to use Unix tools (rsync, git, backup scripts) to manage your database.
24
+
25
+ **Key advantage**: Deltas in persistent data structures translate directly into individual file deltas, making incremental backups and synchronization highly efficient.
26
+
27
+ ```clojure
28
+ {:store {:backend :file
29
+ :path "/var/lib/myapp/db"}}
30
+ ```
31
+
32
+ **Characteristics**:
33
+ - Each immutable index fragment stored as an individual file
34
+ - Efficient incremental backups with rsync
35
+ - Can version database directories similar to or with git
36
+ - Good for single-machine deployments
37
+ - Extensively tested and reliable without external dependencies
38
+ - Not ideal for databases with a lot of churn
39
+
40
+ ### LMDB Backend
41
+
42
+ **Use when**: You need maximum performance on a single machine within a single filesystem.
43
+
44
+ **Key advantage**: Lightning-fast memory-mapped database with ACID transactions, optimized for read-heavy workloads.
45
+
46
+ ```clojure
47
+ ;; Requires: org.replikativ/datahike-lmdb
48
+ {:store {:backend :lmdb
49
+ :path "/var/lib/myapp/db"}}
50
+ ```
51
+
52
+ **Characteristics**:
53
+ - Memory-mapped for zero-copy reads
54
+ - Single filesystem only (not distributed)
55
+ - Excellent read performance
56
+ - Lower memory overhead than file backend
57
+ - Well suited for very high churn of small changes
58
+ - Very low latency
59
+ - Large file blob that cannot be as efficiently synched a the file store
60
+
61
+ **Note**: The LMDB backend is available as a separate library: [datahike-lmdb](https://github.com/replikativ/datahike-lmdb), extending [konserve-lmdb](https://github.com/replikativ/lmdb).
62
+
63
+ ### Memory Backend
64
+
65
+ **Use when**: Testing, development, or ephemeral data that doesn't need to survive process restarts.
66
+
67
+ ```clojure
68
+ {:store {:backend :memory
69
+ :id #uuid "550e8400-e29b-41d4-a716-446655440030"}}
70
+ ```
71
+
72
+ **Characteristics**:
73
+ - No persistence - data lost on process exit
74
+ - Fastest possible performance
75
+ - Ideal for unit tests and REPL development
76
+ - Multiple databases distinguished by `:id`
77
+
78
+ ## Distributed Backends
79
+
80
+ All distributed backends support **Distributed Index Space (DIS)**: multiple reader processes can directly access shared storage without database connections, enabling massive read scalability.
81
+
82
+ **Important**: Datahike uses a single-writer model. Multiple readers can access indices concurrently, but only one writer process should transact at a time. This is the same model used by Datomic, Datalevin, and XTDB.
83
+
84
+ ### JDBC Backend
85
+
86
+ **Use when**: You already have PostgreSQL or another JDBC database in your infrastructure.
87
+
88
+ **Key advantage**: Leverage existing SQL database skills, backup procedures, and monitoring tools.
89
+
90
+ ```clojure
91
+ ;; Requires: org.replikativ/datahike-jdbc
92
+ {:store {:backend :jdbc
93
+ :dbtype "postgresql"
94
+ :host "db.example.com"
95
+ :port 5432
96
+ :dbname "datahike"
97
+ :user "datahike"
98
+ :password "..."}}
99
+ ```
100
+
101
+ **Characteristics**:
102
+ - Use familiar SQL database operations
103
+ - Existing backup/restore procedures work
104
+ - Read scaling via DIS (readers don't interfere with writer in database's MVCC)
105
+ - Good for teams already operating PostgreSQL
106
+ - Available for: PostgreSQL, MySQL, H2, and others
107
+
108
+ **Note**: Available as separate library: [datahike-jdbc](https://github.com/replikativ/datahike-jdbc)
109
+
110
+ ### Redis Backend
111
+
112
+ **Use when**: You need high write throughput and can tolerate weaker durability guarantees.
113
+
114
+ **Key advantage**: Excellent write performance with in-memory speed.
115
+
116
+ ```clojure
117
+ ;; Requires: org.replikativ/konserve-redis
118
+ {:store {:backend :redis
119
+ :host "redis.example.com"
120
+ :port 6379}}
121
+ ```
122
+
123
+ **Characteristics**:
124
+ - Very high write throughput
125
+ - Durability depends on Redis persistence settings (RDB/AOF)
126
+ - Can lose recent writes on Redis crash
127
+ - Good for high-traffic applications where some data loss is acceptable
128
+ - Distributed reads via DIS
129
+
130
+ ### S3 Backend
131
+
132
+ **Use when**: You want cost-effective distributed storage that scales to massive datasets.
133
+
134
+ **Key advantage**: Extremely scalable, pay-per-use pricing, natural fit for cloud-native architectures.
135
+
136
+ ```clojure
137
+ ;; Requires: org.replikativ/konserve-s3
138
+ {:store {:backend :s3
139
+ :bucket "my-datahike-bucket"
140
+ :region "us-east-1"}}
141
+ ```
142
+
143
+ **Characteristics**:
144
+ - Unlimited scalability
145
+ - Very low storage costs (compared to databases)
146
+ - High durability (11 nines)
147
+ - Eventually consistent (may have slight read lag)
148
+ - Ideal for read-heavy workloads with occasional writes
149
+ - Can have high latency
150
+ - Works well with AWS Lambda deployments
151
+
152
+ **Performance note**: Higher latency than local storage, but cost-effective for billions of datoms.
153
+
154
+ ### Google Cloud Storage (GCS) Backend
155
+
156
+ **Use when**: You're on Google Cloud Platform and want distributed storage.
157
+
158
+ **Key advantage**: Similar to S3 but optimized for GCP infrastructure.
159
+
160
+ ```clojure
161
+ ;; Requires: org.replikativ/konserve-gcs
162
+ {:store {:backend :gcs
163
+ :bucket "my-datahike-bucket"
164
+ :project-id "my-project"}}
165
+ ```
166
+
167
+ **Characteristics**:
168
+ - Similar to S3 in characteristics
169
+ - Native GCP integration
170
+ - Good latency within GCP regions
171
+ - Cost-effective for large datasets
172
+
173
+ ### DynamoDB Backend
174
+
175
+ **Use when**: You need low-latency distributed storage and are willing to pay premium pricing.
176
+
177
+ **Key advantage**: Single-digit millisecond latency with strong consistency options.
178
+
179
+ ```clojure
180
+ ;; Requires: org.replikativ/konserve-dynamodb
181
+ {:store {:backend :dynamodb
182
+ :table "datahike"
183
+ :region "us-east-1"}}
184
+ ```
185
+
186
+ **Characteristics**:
187
+ - Very low latency
188
+ - Strong consistency available
189
+ - Higher costs than S3
190
+ - Good for latency-sensitive applications
191
+ - On-demand or provisioned capacity modes
192
+
193
+ ## Browser Backend
194
+
195
+ ### IndexedDB Backend
196
+
197
+ **Use when**: Building offline-capable browser applications with persistent local storage.
198
+
199
+ **Key advantage**: Durable browser-local storage with ClojureScript support.
200
+
201
+ ```clojure
202
+ ;; ClojureScript only
203
+ {:store {:backend :indexeddb
204
+ :id "my-app-db"}}
205
+ ```
206
+
207
+ **Characteristics**:
208
+ - Persistent across browser sessions
209
+ - ~50MB-unlimited quota (browser-dependent)
210
+ - Asynchronous API
211
+ - Often paired with TieredStore for performance
212
+
213
+ ## Advanced: TieredStore
214
+
215
+ **TieredStore** creates memory hierarchies by layering backends, with faster storage in front of slower, more durable storage.
216
+
217
+ **Use cases**:
218
+ - **Browser**: Memory (fast) → IndexedDB (persistent)
219
+ - **Server**: Memory → LMDB → S3 (hot → warm → cold)
220
+ - **AWS**: LMDB (fast local) → S3 (distributed backup)
221
+
222
+ ```clojure
223
+ ;; Example: Fast memory cache backed by S3
224
+ {:store {:backend :tiered
225
+ :id #uuid "550e8400-e29b-41d4-a716-446655440031"
226
+ :frontend-config {:backend :memory
227
+ :id #uuid "550e8400-e29b-41d4-a716-446655440031"}
228
+ :backend-config {:backend :s3
229
+ :bucket "persistent-store"
230
+ :region "us-east-1"
231
+ :id #uuid "550e8400-e29b-41d4-a716-446655440031"}
232
+ :write-policy :write-through
233
+ :read-policy :frontend-first}}
234
+ ```
235
+
236
+ **How it works**:
237
+ - Reads check tiers in order (cache-first)
238
+ - Writes go to all tiers
239
+ - Stacking multiple tiers supported but rarely needed
240
+ - Provided by konserve's tiered store implementation
241
+
242
+ **Common patterns**:
243
+
244
+ **Browser with offline support**:
245
+ ```clojure
246
+ {:store {:backend :tiered
247
+ :id #uuid "550e8400-e29b-41d4-a716-446655440032"
248
+ :frontend-config {:backend :memory
249
+ :id #uuid "550e8400-e29b-41d4-a716-446655440032"}
250
+ :backend-config {:backend :indexeddb
251
+ :id #uuid "550e8400-e29b-41d4-a716-446655440032"}
252
+ :write-policy :write-through}}
253
+ ```
254
+
255
+ **AWS Lambda with S3 backing**:
256
+ ```clojure
257
+ {:store {:backend :tiered
258
+ :id #uuid "550e8400-e29b-41d4-a716-446655440033"
259
+ :frontend-config {:backend :lmdb
260
+ :path "/tmp/cache"
261
+ :id #uuid "550e8400-e29b-41d4-a716-446655440033"}
262
+ :backend-config {:backend :s3
263
+ :bucket "lambda-data"
264
+ :region "us-east-1"
265
+ :id #uuid "550e8400-e29b-41d4-a716-446655440033"}}}
266
+ ```
267
+
268
+ ## Backend-Specific Configuration
269
+
270
+ Each backend may have additional configuration options. See the konserve backend documentation for details:
271
+
272
+ - [konserve](https://github.com/replikativ/konserve) - Core abstraction
273
+ - [konserve-lmdb](https://github.com/replikativ/lmdb) - LMDB implementation
274
+ - [datahike-lmdb](https://github.com/replikativ/datahike-lmdb) - Datahike LMDB integration
275
+ - [datahike-jdbc](https://github.com/replikativ/datahike-jdbc) - JDBC backends
276
+ - [konserve-s3](https://github.com/replikativ/konserve-s3) - S3 backend
277
+ - [konserve-redis](https://github.com/replikativ/konserve-redis) - Redis backend
278
+
279
+ ## Choosing a Backend
280
+
281
+ ### For Development
282
+ → **Memory** or **File** backend for simplicity
283
+
284
+ ### For Single-Machine Production
285
+ → **LMDB** for best performance
286
+ → **File** if you need Unix tool integration
287
+
288
+ ### For Distributed Production (Read Scaling)
289
+ → **S3/GCS** for cost-effective scale
290
+ → **DynamoDB** for low latency (higher cost)
291
+ → **JDBC** if you already operate PostgreSQL
292
+
293
+ ### For High Write Throughput
294
+ → **Redis** if you can tolerate some data loss
295
+ → **LMDB** for durable local writes
296
+ → **DynamoDB** for distributed writes (expensive)
297
+
298
+ ### For Browser Applications
299
+ → **IndexedDB** for persistence
300
+ → **TieredStore** (Memory → IndexedDB) for speed + durability
301
+
302
+ ### For Cost Optimization
303
+ → **File** backend with rsync for cheap backups
304
+ → **S3** for large datasets (pennies per GB)
305
+ → **TieredStore** to minimize expensive tier access
306
+
307
+ ## Migration Between Backends
308
+
309
+ To migrate from one backend to another:
310
+
311
+ 1. Export from source database:
312
+ ```clojure
313
+ (require '[datahike.migrate :refer [export-db import-db]])
314
+ (export-db source-conn "/tmp/datoms-export")
315
+ ```
316
+
317
+ 2. Create destination database with new backend:
318
+ ```clojure
319
+ (d/create-database new-config)
320
+ (def dest-conn (d/connect new-config))
321
+ ```
322
+
323
+ 3. Import into destination:
324
+ ```clojure
325
+ (import-db dest-conn "/tmp/datoms-export")
326
+ ```
327
+
328
+ The export format (CBOR) preserves all data types including binary data.
329
+
330
+ ## Performance Considerations
331
+
332
+ ### Read Performance
333
+ - **Fastest**: Memory, LMDB (memory-mapped)
334
+ - **Fast**: File (SSD), Redis
335
+ - **Good**: JDBC, S3 (with tiering)
336
+ - **Variable**: DynamoDB (provisioned vs on-demand)
337
+
338
+ ### Write Performance
339
+ - **Fastest**: Memory, Redis
340
+ - **Fast**: LMDB, DynamoDB (provisioned)
341
+ - **Good**: File, JDBC, S3
342
+ - **Slower**: S3 (especially small writes)
343
+
344
+ ### Distribution
345
+ - **No distribution**: Memory, File, LMDB (single filesystem)
346
+ - **Distributed reads**: All cloud backends via DIS
347
+ - **Single writer**: All backends (architectural constraint)
348
+
349
+ ### Durability
350
+ - **None**: Memory (ephemeral)
351
+ - **Medium**: Redis (depends on persistence settings), IndexedDB
352
+ - **High**: File, LMDB, JDBC
353
+ - **Very high**: S3, GCS, DynamoDB (11 nines)
354
+
355
+ ## Custom Backends
356
+
357
+ Datahike can use any konserve backend. To create a custom backend:
358
+
359
+ 1. Implement the [konserve protocols](https://github.com/replikativ/konserve/blob/main/src/konserve/protocols.cljc)
360
+ 2. Register your backend with konserve
361
+ 3. Use it in Datahike configuration
362
+
363
+ See the [konserve documentation](https://github.com/replikativ/konserve) for details on implementing custom backends.