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.
- package/.circleci/config.yml +405 -0
- package/.circleci/scripts/gen_ci.clj +194 -0
- package/.cirrus.yml +60 -0
- package/.clj-kondo/babashka/sci/config.edn +1 -0
- package/.clj-kondo/babashka/sci/sci/core.clj +9 -0
- package/.clj-kondo/config.edn +95 -0
- package/.dir-locals.el +2 -0
- package/.github/FUNDING.yml +3 -0
- package/.github/ISSUE_TEMPLATE/1-bug-report.yml +68 -0
- package/.github/ISSUE_TEMPLATE/2-feature-request.yml +28 -0
- package/.github/ISSUE_TEMPLATE/config.yml +6 -0
- package/.github/pull_request_template.md +24 -0
- package/.github/workflows/native-image.yml +84 -0
- package/LICENSE +203 -0
- package/README.md +273 -0
- package/bb/deps.edn +9 -0
- package/bb/resources/github-fingerprints +3 -0
- package/bb/resources/native-image-tests/run-bb-pod-tests.clj +162 -0
- package/bb/resources/native-image-tests/run-libdatahike-tests +12 -0
- package/bb/resources/native-image-tests/run-native-image-tests +74 -0
- package/bb/resources/native-image-tests/run-python-tests +22 -0
- package/bb/resources/native-image-tests/testconfig.attr-refs.edn +6 -0
- package/bb/resources/native-image-tests/testconfig.edn +5 -0
- package/bb/resources/template/.settings/org.eclipse.jdt.apt.core.prefs +2 -0
- package/bb/resources/template/.settings/org.eclipse.jdt.core.prefs +9 -0
- package/bb/resources/template/.settings/org.eclipse.m2e.core.prefs +4 -0
- package/bb/resources/template/pom.xml +22 -0
- package/bb/src/tools/build.clj +132 -0
- package/bb/src/tools/clj_kondo.clj +32 -0
- package/bb/src/tools/deploy.clj +26 -0
- package/bb/src/tools/examples.clj +19 -0
- package/bb/src/tools/npm.clj +100 -0
- package/bb/src/tools/python.clj +14 -0
- package/bb/src/tools/release.clj +94 -0
- package/bb/src/tools/test.clj +148 -0
- package/bb/src/tools/version.clj +47 -0
- package/bb.edn +269 -0
- package/benchmark/src/benchmark/cli.clj +195 -0
- package/benchmark/src/benchmark/compare.clj +157 -0
- package/benchmark/src/benchmark/config.clj +316 -0
- package/benchmark/src/benchmark/measure.clj +187 -0
- package/benchmark/src/benchmark/store.clj +190 -0
- package/benchmark/test/benchmark/measure_test.clj +156 -0
- package/build.clj +30 -0
- package/config.edn +49 -0
- package/deps.edn +138 -0
- package/dev/sandbox.clj +82 -0
- package/dev/sandbox.cljs +127 -0
- package/dev/sandbox_benchmarks.clj +27 -0
- package/dev/sandbox_client.clj +87 -0
- package/dev/sandbox_transact_bench.clj +109 -0
- package/dev/user.clj +79 -0
- package/doc/README.md +96 -0
- package/doc/adl/README.md +6 -0
- package/doc/adl/adr-000-adr.org +28 -0
- package/doc/adl/adr-001-attribute-references.org +15 -0
- package/doc/adl/adr-002-build-tooling.org +54 -0
- package/doc/adl/adr-003-db-meta-data.md +52 -0
- package/doc/adl/adr-004-github-flow.md +40 -0
- package/doc/adl/adr-XYZ-template.md +30 -0
- package/doc/adl/index.org +3 -0
- package/doc/assets/datahike-logo.svg +3 -0
- package/doc/assets/datahiking-invoice.org +85 -0
- package/doc/assets/hhtree2.png +0 -0
- package/doc/assets/network_topology.svg +624 -0
- package/doc/assets/perf.png +0 -0
- package/doc/assets/schema_mindmap.mm +132 -0
- package/doc/assets/schema_mindmap.svg +970 -0
- package/doc/assets/temporal_index.mm +74 -0
- package/doc/backend-development.md +78 -0
- package/doc/bb-pod.md +89 -0
- package/doc/benchmarking.md +360 -0
- package/doc/bindings/edn-conversion.md +383 -0
- package/doc/cli.md +162 -0
- package/doc/cljdoc.edn +27 -0
- package/doc/cljs-support.md +133 -0
- package/doc/config.md +406 -0
- package/doc/contributing.md +114 -0
- package/doc/datalog-vs-sql.md +210 -0
- package/doc/datomic_differences.md +109 -0
- package/doc/development/pull-api-ns.md +186 -0
- package/doc/development/pull-frame-state-diagram.jpg +0 -0
- package/doc/distributed.md +566 -0
- package/doc/entity_spec.md +92 -0
- package/doc/gc.md +273 -0
- package/doc/java-api.md +808 -0
- package/doc/javascript-api.md +421 -0
- package/doc/libdatahike.md +86 -0
- package/doc/logging_and_error_handling.md +43 -0
- package/doc/norms.md +66 -0
- package/doc/schema-migration.md +85 -0
- package/doc/schema.md +287 -0
- package/doc/storage-backends.md +363 -0
- package/doc/store-id-refactoring.md +596 -0
- package/doc/time_variance.md +325 -0
- package/doc/unstructured.md +167 -0
- package/doc/versioning.md +261 -0
- package/examples/basic/README.md +19 -0
- package/examples/basic/deps.edn +6 -0
- package/examples/basic/docker-compose.yml +13 -0
- package/examples/basic/src/examples/core.clj +60 -0
- package/examples/basic/src/examples/schema.clj +155 -0
- package/examples/basic/src/examples/store.clj +60 -0
- package/examples/basic/src/examples/time_travel.clj +185 -0
- package/examples/java/.settings/org.eclipse.core.resources.prefs +3 -0
- package/examples/java/.settings/org.eclipse.jdt.apt.core.prefs +2 -0
- package/examples/java/.settings/org.eclipse.jdt.core.prefs +9 -0
- package/examples/java/.settings/org.eclipse.m2e.core.prefs +4 -0
- package/examples/java/README.md +162 -0
- package/examples/java/pom.xml +62 -0
- package/examples/java/src/main/java/examples/QuickStart.java +115 -0
- package/examples/java/src/main/java/examples/SchemaExample.java +148 -0
- package/examples/java/src/main/java/examples/TimeTravelExample.java +121 -0
- package/flake.lock +27 -0
- package/flake.nix +27 -0
- package/http-server/datahike/http/middleware.clj +75 -0
- package/http-server/datahike/http/server.clj +269 -0
- package/java/src/datahike/java/Database.java +274 -0
- package/java/src/datahike/java/Datahike.java +281 -0
- package/java/src/datahike/java/DatahikeGeneratedTest.java +349 -0
- package/java/src/datahike/java/DatahikeTest.java +370 -0
- package/java/src/datahike/java/EDN.java +170 -0
- package/java/src/datahike/java/IEntity.java +11 -0
- package/java/src/datahike/java/Keywords.java +161 -0
- package/java/src/datahike/java/SchemaFlexibility.java +52 -0
- package/java/src/datahike/java/Util.java +219 -0
- package/karma.conf.js +19 -0
- package/libdatahike/compile-cpp +7 -0
- package/libdatahike/src/datahike/impl/LibDatahikeBase.java +203 -0
- package/libdatahike/src/datahike/impl/libdatahike.clj +59 -0
- package/libdatahike/src/test_cpp.cpp +61 -0
- package/npm-package/PUBLISHING.md +140 -0
- package/npm-package/README.md +226 -0
- package/npm-package/package.template.json +34 -0
- package/npm-package/test-isomorphic.ts +281 -0
- package/npm-package/test.js +557 -0
- package/npm-package/typescript-test.ts +70 -0
- package/package.json +16 -0
- package/pydatahike/README.md +569 -0
- package/pydatahike/pyproject.toml +91 -0
- package/pydatahike/setup.py +42 -0
- package/pydatahike/src/datahike/__init__.py +134 -0
- package/pydatahike/src/datahike/_native.py +250 -0
- package/pydatahike/src/datahike/_version.py +2 -0
- package/pydatahike/src/datahike/database.py +722 -0
- package/pydatahike/src/datahike/edn.py +311 -0
- package/pydatahike/src/datahike/py.typed +0 -0
- package/pydatahike/tests/conftest.py +17 -0
- package/pydatahike/tests/test_basic.py +170 -0
- package/pydatahike/tests/test_database.py +51 -0
- package/pydatahike/tests/test_edn_conversion.py +299 -0
- package/pydatahike/tests/test_query.py +99 -0
- package/pydatahike/tests/test_schema.py +55 -0
- package/resources/clj-kondo.exports/io.replikativ/datahike/config.edn +5 -0
- package/resources/example_server.edn +4 -0
- package/shadow-cljs.edn +56 -0
- package/src/data_readers.clj +7 -0
- package/src/datahike/api/impl.cljc +176 -0
- package/src/datahike/api/specification.cljc +633 -0
- package/src/datahike/api/types.cljc +261 -0
- package/src/datahike/api.cljc +41 -0
- package/src/datahike/array.cljc +99 -0
- package/src/datahike/cli.clj +166 -0
- package/src/datahike/cljs.cljs +6 -0
- package/src/datahike/codegen/cli.clj +406 -0
- package/src/datahike/codegen/clj_kondo.clj +291 -0
- package/src/datahike/codegen/java.clj +403 -0
- package/src/datahike/codegen/naming.cljc +33 -0
- package/src/datahike/codegen/native.clj +559 -0
- package/src/datahike/codegen/pod.clj +488 -0
- package/src/datahike/codegen/python.clj +838 -0
- package/src/datahike/codegen/report.clj +55 -0
- package/src/datahike/codegen/typescript.clj +262 -0
- package/src/datahike/codegen/validation.clj +145 -0
- package/src/datahike/config.cljc +294 -0
- package/src/datahike/connections.cljc +16 -0
- package/src/datahike/connector.cljc +265 -0
- package/src/datahike/constants.cljc +142 -0
- package/src/datahike/core.cljc +297 -0
- package/src/datahike/datom.cljc +459 -0
- package/src/datahike/db/interface.cljc +119 -0
- package/src/datahike/db/search.cljc +305 -0
- package/src/datahike/db/transaction.cljc +937 -0
- package/src/datahike/db/utils.cljc +338 -0
- package/src/datahike/db.cljc +956 -0
- package/src/datahike/experimental/unstructured.cljc +126 -0
- package/src/datahike/experimental/versioning.cljc +172 -0
- package/src/datahike/externs.js +31 -0
- package/src/datahike/gc.cljc +69 -0
- package/src/datahike/http/client.clj +188 -0
- package/src/datahike/http/writer.clj +79 -0
- package/src/datahike/impl/entity.cljc +218 -0
- package/src/datahike/index/interface.cljc +93 -0
- package/src/datahike/index/persistent_set.cljc +469 -0
- package/src/datahike/index/utils.cljc +44 -0
- package/src/datahike/index.cljc +32 -0
- package/src/datahike/js/api.cljs +172 -0
- package/src/datahike/js/api_macros.clj +22 -0
- package/src/datahike/js.cljs +163 -0
- package/src/datahike/json.cljc +209 -0
- package/src/datahike/lru.cljc +146 -0
- package/src/datahike/migrate.clj +39 -0
- package/src/datahike/norm/norm.clj +245 -0
- package/src/datahike/online_gc.cljc +252 -0
- package/src/datahike/pod.clj +155 -0
- package/src/datahike/pull_api.cljc +325 -0
- package/src/datahike/query.cljc +1945 -0
- package/src/datahike/query_stats.cljc +88 -0
- package/src/datahike/readers.cljc +62 -0
- package/src/datahike/remote.cljc +218 -0
- package/src/datahike/schema.cljc +228 -0
- package/src/datahike/schema_cache.cljc +42 -0
- package/src/datahike/spec.cljc +101 -0
- package/src/datahike/store.cljc +80 -0
- package/src/datahike/tools.cljc +308 -0
- package/src/datahike/transit.cljc +80 -0
- package/src/datahike/writer.cljc +239 -0
- package/src/datahike/writing.cljc +362 -0
- package/src/deps.cljs +1 -0
- package/src-hitchhiker-tree/datahike/index/hitchhiker_tree/insert.cljc +76 -0
- package/src-hitchhiker-tree/datahike/index/hitchhiker_tree/upsert.cljc +128 -0
- package/src-hitchhiker-tree/datahike/index/hitchhiker_tree.cljc +213 -0
- package/test/datahike/backward_compatibility_test/src/backward_test.clj +37 -0
- package/test/datahike/integration_test/config_record_file_test.clj +14 -0
- package/test/datahike/integration_test/config_record_test.clj +14 -0
- package/test/datahike/integration_test/depr_config_uri_test.clj +15 -0
- package/test/datahike/integration_test/return_map_test.clj +62 -0
- package/test/datahike/integration_test.cljc +67 -0
- package/test/datahike/norm/norm_test.clj +124 -0
- package/test/datahike/norm/resources/naming-and-sorting-test/001-a1-example.edn +5 -0
- package/test/datahike/norm/resources/naming-and-sorting-test/002-a2-example.edn +5 -0
- package/test/datahike/norm/resources/naming-and-sorting-test/003-tx-fn-test.edn +1 -0
- package/test/datahike/norm/resources/naming-and-sorting-test/004-tx-data-and-tx-fn-test.edn +5 -0
- package/test/datahike/norm/resources/naming-and-sorting-test/01-transact-basic-characters.edn +2 -0
- package/test/datahike/norm/resources/naming-and-sorting-test/02 add occupation.edn +5 -0
- package/test/datahike/norm/resources/naming-and-sorting-test/checksums.edn +12 -0
- package/test/datahike/norm/resources/simple-test/001-a1-example.edn +5 -0
- package/test/datahike/norm/resources/simple-test/002-a2-example.edn +5 -0
- package/test/datahike/norm/resources/simple-test/checksums.edn +4 -0
- package/test/datahike/norm/resources/tx-data-and-tx-fn-test/first/001-a1-example.edn +5 -0
- package/test/datahike/norm/resources/tx-data-and-tx-fn-test/first/002-a2-example.edn +5 -0
- package/test/datahike/norm/resources/tx-data-and-tx-fn-test/first/003-tx-fn-test.edn +1 -0
- package/test/datahike/norm/resources/tx-data-and-tx-fn-test/first/checksums.edn +6 -0
- package/test/datahike/norm/resources/tx-data-and-tx-fn-test/second/004-tx-data-and-tx-fn-test.edn +5 -0
- package/test/datahike/norm/resources/tx-data-and-tx-fn-test/second/checksums.edn +2 -0
- package/test/datahike/norm/resources/tx-fn-test/first/001-a1-example.edn +5 -0
- package/test/datahike/norm/resources/tx-fn-test/first/002-a2-example.edn +5 -0
- package/test/datahike/norm/resources/tx-fn-test/first/checksums.edn +4 -0
- package/test/datahike/norm/resources/tx-fn-test/second/003-tx-fn-test.edn +1 -0
- package/test/datahike/norm/resources/tx-fn-test/second/checksums.edn +2 -0
- package/test/datahike/test/api_test.cljc +895 -0
- package/test/datahike/test/array_test.cljc +40 -0
- package/test/datahike/test/attribute_refs/datoms_test.cljc +140 -0
- package/test/datahike/test/attribute_refs/db_test.cljc +42 -0
- package/test/datahike/test/attribute_refs/differences_test.cljc +515 -0
- package/test/datahike/test/attribute_refs/entity_test.cljc +89 -0
- package/test/datahike/test/attribute_refs/pull_api_test.cljc +320 -0
- package/test/datahike/test/attribute_refs/query_find_specs_test.cljc +59 -0
- package/test/datahike/test/attribute_refs/query_fns_test.cljc +130 -0
- package/test/datahike/test/attribute_refs/query_interop_test.cljc +47 -0
- package/test/datahike/test/attribute_refs/query_not_test.cljc +193 -0
- package/test/datahike/test/attribute_refs/query_or_test.cljc +137 -0
- package/test/datahike/test/attribute_refs/query_pull_test.cljc +156 -0
- package/test/datahike/test/attribute_refs/query_rules_test.cljc +176 -0
- package/test/datahike/test/attribute_refs/query_test.cljc +241 -0
- package/test/datahike/test/attribute_refs/temporal_search.cljc +22 -0
- package/test/datahike/test/attribute_refs/transact_test.cljc +220 -0
- package/test/datahike/test/attribute_refs/utils.cljc +128 -0
- package/test/datahike/test/cache_test.cljc +38 -0
- package/test/datahike/test/components_test.cljc +92 -0
- package/test/datahike/test/config_test.cljc +158 -0
- package/test/datahike/test/core_test.cljc +105 -0
- package/test/datahike/test/datom_test.cljc +44 -0
- package/test/datahike/test/db_test.cljc +54 -0
- package/test/datahike/test/entity_spec_test.cljc +159 -0
- package/test/datahike/test/entity_test.cljc +103 -0
- package/test/datahike/test/explode_test.cljc +143 -0
- package/test/datahike/test/filter_test.cljc +75 -0
- package/test/datahike/test/gc_test.cljc +159 -0
- package/test/datahike/test/http/server_test.clj +192 -0
- package/test/datahike/test/http/writer_test.clj +86 -0
- package/test/datahike/test/ident_test.cljc +32 -0
- package/test/datahike/test/index_test.cljc +345 -0
- package/test/datahike/test/insert.cljc +125 -0
- package/test/datahike/test/java_bindings_test.clj +6 -0
- package/test/datahike/test/listen_test.cljc +41 -0
- package/test/datahike/test/lookup_refs_test.cljc +266 -0
- package/test/datahike/test/lru_test.cljc +27 -0
- package/test/datahike/test/migrate_test.clj +297 -0
- package/test/datahike/test/model/core.cljc +376 -0
- package/test/datahike/test/model/invariant.cljc +142 -0
- package/test/datahike/test/model/rng.cljc +82 -0
- package/test/datahike/test/model_test.clj +217 -0
- package/test/datahike/test/nodejs_test.cljs +262 -0
- package/test/datahike/test/online_gc_test.cljc +475 -0
- package/test/datahike/test/pod_test.clj +369 -0
- package/test/datahike/test/pull_api_test.cljc +474 -0
- package/test/datahike/test/purge_test.cljc +144 -0
- package/test/datahike/test/query_aggregates_test.cljc +101 -0
- package/test/datahike/test/query_find_specs_test.cljc +52 -0
- package/test/datahike/test/query_fns_test.cljc +523 -0
- package/test/datahike/test/query_interop_test.cljc +47 -0
- package/test/datahike/test/query_not_test.cljc +189 -0
- package/test/datahike/test/query_or_test.cljc +158 -0
- package/test/datahike/test/query_pull_test.cljc +147 -0
- package/test/datahike/test/query_rules_test.cljc +248 -0
- package/test/datahike/test/query_stats_test.cljc +218 -0
- package/test/datahike/test/query_test.cljc +984 -0
- package/test/datahike/test/schema_test.cljc +424 -0
- package/test/datahike/test/specification_test.cljc +30 -0
- package/test/datahike/test/store_test.cljc +78 -0
- package/test/datahike/test/stress_test.cljc +57 -0
- package/test/datahike/test/time_variance_test.cljc +518 -0
- package/test/datahike/test/tools_test.clj +134 -0
- package/test/datahike/test/transact_test.cljc +518 -0
- package/test/datahike/test/tuples_test.cljc +564 -0
- package/test/datahike/test/unstructured_test.cljc +291 -0
- package/test/datahike/test/upsert_impl_test.cljc +205 -0
- package/test/datahike/test/upsert_test.cljc +363 -0
- package/test/datahike/test/utils.cljc +110 -0
- package/test/datahike/test/validation_test.cljc +48 -0
- package/test/datahike/test/versioning_test.cljc +56 -0
- package/test/datahike/test.cljc +66 -0
- package/tests.edn +24 -0
package/bb.edn
ADDED
|
@@ -0,0 +1,269 @@
|
|
|
1
|
+
{:min-bb-version "0.8.0"
|
|
2
|
+
:pods {org.babashka/tools-deps-native {:version "0.1.7"}
|
|
3
|
+
clj-kondo/clj-kondo {:version "2025.07.28"}}
|
|
4
|
+
:deps {datahike/bb {:local/root "bb"}
|
|
5
|
+
org.babashka/http-client {:mvn/version "0.4.22"}}
|
|
6
|
+
:tasks {:requires [[babashka.fs :as fs]
|
|
7
|
+
[babashka.process :as process]
|
|
8
|
+
[clojure.edn :as edn]
|
|
9
|
+
[clojure.string :as str]
|
|
10
|
+
[pod.borkdude.clj-kondo :as clj-kondo]
|
|
11
|
+
[tools.build :as build]
|
|
12
|
+
[tools.clj-kondo :as clj-kondo-tools]
|
|
13
|
+
[tools.deploy :as deploy]
|
|
14
|
+
[tools.examples :as examples]
|
|
15
|
+
[tools.npm :as npm]
|
|
16
|
+
[tools.python :as python]
|
|
17
|
+
[tools.release :as release]
|
|
18
|
+
[tools.test :as test]
|
|
19
|
+
[tools.version :as version]]
|
|
20
|
+
:init (do (def config-file "config.edn")
|
|
21
|
+
(def config (edn/read-string (slurp config-file))))
|
|
22
|
+
|
|
23
|
+
; tools
|
|
24
|
+
|
|
25
|
+
bench {:doc "Run benchmarks"
|
|
26
|
+
:depends [prep]
|
|
27
|
+
:task (clojure "-M:benchmark" "measure")}
|
|
28
|
+
|
|
29
|
+
ffix {:doc "Format source files"
|
|
30
|
+
:depends [prep]
|
|
31
|
+
:task (clojure "-M:ffix")}
|
|
32
|
+
|
|
33
|
+
; checks
|
|
34
|
+
|
|
35
|
+
format {:doc "Test formatting"
|
|
36
|
+
:depends [prep]
|
|
37
|
+
:task (clojure "-M:format")}
|
|
38
|
+
|
|
39
|
+
lint {:doc "Run clj-kondo linter"
|
|
40
|
+
:require [[pod.borkdude.clj-kondo :as clj-kondo]]
|
|
41
|
+
:task (clj-kondo/print! (clj-kondo/run! {:lint "."}))}
|
|
42
|
+
|
|
43
|
+
test {:doc "Run all tests or restrict to 'native-image', 'back-compat' or a kaocha test id (see tests.edn)"
|
|
44
|
+
:depends [jcompile]
|
|
45
|
+
:task (apply test/-main config *command-line-args*)}
|
|
46
|
+
|
|
47
|
+
kaocha {:doc "Run kaocha with arbitrary arguments"
|
|
48
|
+
:task (apply test/kaocha *command-line-args*)}
|
|
49
|
+
|
|
50
|
+
|
|
51
|
+
outdated {:doc "Find outdated libraries"
|
|
52
|
+
:depends [prep]
|
|
53
|
+
:task (clojure "-M:outdated")}
|
|
54
|
+
|
|
55
|
+
; build and release
|
|
56
|
+
|
|
57
|
+
inc {:doc "Increment the project version: [major|minor] <version>"
|
|
58
|
+
:task (apply version/inc config-file *command-line-args*)}
|
|
59
|
+
|
|
60
|
+
tag {:doc "Return current version as a tag"
|
|
61
|
+
:task (println (version/as-tag config))}
|
|
62
|
+
|
|
63
|
+
clean {:doc "Remove build files"
|
|
64
|
+
:task (build/clean (-> config :build :clj))}
|
|
65
|
+
|
|
66
|
+
prep {:doc "Prepare git dependencies (compile Java sources)"
|
|
67
|
+
:task (clojure "-X:deps prep")}
|
|
68
|
+
|
|
69
|
+
codegen-java {:doc "Generate Java API bindings from specification"
|
|
70
|
+
:depends [prep]
|
|
71
|
+
:task (let [cp (str/trim (:out (shell {:out :string} "clojure" "-Spath")))]
|
|
72
|
+
;; First compile Java dependencies (Util, IEntity) so Clojure can load them
|
|
73
|
+
(println "Compiling Java dependencies...")
|
|
74
|
+
(shell "javac" "-cp" cp "-d" "target/classes"
|
|
75
|
+
"java/src/datahike/java/IEntity.java"
|
|
76
|
+
"java/src/datahike/java/Util.java")
|
|
77
|
+
;; Now generate the Java API
|
|
78
|
+
(println "Generating Java API from specification...")
|
|
79
|
+
(clojure "-M" "-m" "datahike.codegen.java" "java/src-generated"))}
|
|
80
|
+
|
|
81
|
+
codegen-ts {:doc "Generate TypeScript type definitions from specification"
|
|
82
|
+
:task (npm/generate-typescript-definitions! "npm-package/index.d.ts")}
|
|
83
|
+
|
|
84
|
+
codegen-native {:doc "Generate native C entry points from specification"
|
|
85
|
+
:depends [prep]
|
|
86
|
+
:task (clojure "-M" "-m" "datahike.codegen.native" "libdatahike/src")}
|
|
87
|
+
|
|
88
|
+
python-version {:doc "Update Python package version from config.edn"
|
|
89
|
+
:task (python/update-python-version! config "pydatahike")}
|
|
90
|
+
|
|
91
|
+
codegen-python {:doc "Generate Python bindings from specification"
|
|
92
|
+
:depends [prep python-version]
|
|
93
|
+
:task (clojure "-M" "-m" "datahike.codegen.python" "pydatahike/src/datahike")}
|
|
94
|
+
|
|
95
|
+
java-examples-version {:doc "Update Java examples pom.xml version to match current version"
|
|
96
|
+
:task (examples/update-java-examples-version! config)}
|
|
97
|
+
|
|
98
|
+
codegen-clj-kondo {:doc "Generate clj-kondo config from API specification"
|
|
99
|
+
:depends [prep]
|
|
100
|
+
:task (clj-kondo-tools/generate-clj-kondo-config!
|
|
101
|
+
"resources/clj-kondo.exports/io.replikativ/datahike/config.edn"
|
|
102
|
+
".clj-kondo/datahike/datahike/config.edn"
|
|
103
|
+
".clj-kondo/config.edn")}
|
|
104
|
+
|
|
105
|
+
codegen-all {:doc "Generate all language bindings (TypeScript, Java, Native, Python)"
|
|
106
|
+
:depends [codegen-ts codegen-java codegen-native codegen-python]}
|
|
107
|
+
|
|
108
|
+
codegen-report {:doc "Show code generation coverage across all bindings"
|
|
109
|
+
:depends [prep]
|
|
110
|
+
:task (clojure "-M" "-m" "datahike.codegen.report")}
|
|
111
|
+
|
|
112
|
+
jcompile {:doc "Compile java classes"
|
|
113
|
+
:depends [clean codegen-java]
|
|
114
|
+
:task (build/compile-java (-> config :build :clj))}
|
|
115
|
+
|
|
116
|
+
javadoc {:doc "Generate Javadoc for Java API (published to javadoc.io)"
|
|
117
|
+
:task (build/javadoc {})}
|
|
118
|
+
|
|
119
|
+
ccompile {:doc "Compile clojure namespaces"
|
|
120
|
+
:task (build/compile-clojure (-> config :build :clj))}
|
|
121
|
+
|
|
122
|
+
version-resource {:doc "Generate version resource file for embedding in builds"
|
|
123
|
+
:task (build/write-version-resource config)}
|
|
124
|
+
|
|
125
|
+
pom {:doc "Create pom file"
|
|
126
|
+
:task (build/pom config (-> config :build :clj))}
|
|
127
|
+
|
|
128
|
+
jar {:doc "Build jar"
|
|
129
|
+
:depends [jcompile pom version-resource]
|
|
130
|
+
:task (build/jar config (-> config :build :clj))}
|
|
131
|
+
|
|
132
|
+
install {:doc "Install jar locally"
|
|
133
|
+
:task (deploy/local config (-> config :build :clj))}
|
|
134
|
+
|
|
135
|
+
clojars {:doc "Install jar to clojars"
|
|
136
|
+
:task (deploy/remote config (-> config :build :clj))}
|
|
137
|
+
|
|
138
|
+
release {:doc "Build and release jar to GitHub"
|
|
139
|
+
:task (release/-main config *command-line-args*)}
|
|
140
|
+
|
|
141
|
+
|
|
142
|
+
;; http server build and release
|
|
143
|
+
|
|
144
|
+
http-server-clean {:doc "Remove build files"
|
|
145
|
+
:task (build/clean (-> config :build :http-server-clj))}
|
|
146
|
+
|
|
147
|
+
http-server-jcompile {:doc "Compile java classes"
|
|
148
|
+
:depends [http-server-clean]
|
|
149
|
+
:task (build/compile-java (-> config :build :http-server-clj))}
|
|
150
|
+
|
|
151
|
+
http-server-ccompile {:doc "Compile clojure namespaces for http-server"
|
|
152
|
+
:task (build/compile-clojure (-> config :build :http-server-clj))}
|
|
153
|
+
|
|
154
|
+
http-server-pom {:doc "Create pom file"
|
|
155
|
+
:task (build/pom config (-> config :build :http-server-clj))}
|
|
156
|
+
|
|
157
|
+
http-server-uber {:doc "Build jar"
|
|
158
|
+
:depends [http-server-jcompile http-server-pom http-server-ccompile version-resource]
|
|
159
|
+
:task (build/uber config (-> config :build :http-server-clj))}
|
|
160
|
+
|
|
161
|
+
http-server-install {:doc "Install uber jar locally"
|
|
162
|
+
:task (deploy/local config (-> config :build :http-server-clj))}
|
|
163
|
+
|
|
164
|
+
http-server-release {:doc "Build and release jar to GitHub"
|
|
165
|
+
:depends [http-server-uber]
|
|
166
|
+
:task (let [jar (build/jar-path config (-> config :build :http-server-clj))]
|
|
167
|
+
(release/gh-release jar config))}
|
|
168
|
+
|
|
169
|
+
;; native image
|
|
170
|
+
|
|
171
|
+
ni-check {:doc "Check for 'native-image' program"
|
|
172
|
+
:task (try (shell "which" "native-image")
|
|
173
|
+
(println "Program native-image found!")
|
|
174
|
+
(catch Exception _
|
|
175
|
+
(println "PATH does not contain native-image! Make sure to add your GraalVM to it.")
|
|
176
|
+
(System/exit 1)))}
|
|
177
|
+
|
|
178
|
+
ni-cli {:doc "Build native image cli"
|
|
179
|
+
:depends [jcompile ni-check version-resource]
|
|
180
|
+
:task (clojure "-M:native-cli")}
|
|
181
|
+
|
|
182
|
+
ni-ccompile {:doc "Compile clojure namespaces for native-image"
|
|
183
|
+
:depends [jcompile]
|
|
184
|
+
:task (build/compile-clojure (-> config :build :native))}
|
|
185
|
+
|
|
186
|
+
ni-uber {:doc "Build native image uber jar"
|
|
187
|
+
:depends [jcompile ni-ccompile version-resource]
|
|
188
|
+
:task (build/uber config (-> config :build :native))}
|
|
189
|
+
|
|
190
|
+
ni-compile {:doc "Create native cpp library"
|
|
191
|
+
:depends [codegen-native ni-uber]
|
|
192
|
+
:task (build/native-compile config (-> config :build :native))}
|
|
193
|
+
|
|
194
|
+
;; npm package
|
|
195
|
+
|
|
196
|
+
npm-version {:doc "Update npm package.json version from config.edn"
|
|
197
|
+
:task (npm/update-package-json-version! config "npm-package")}
|
|
198
|
+
|
|
199
|
+
npm-clean {:doc "Clean compiled files from npm package directory"
|
|
200
|
+
:task (npm/clean-npm-package! "npm-package")}
|
|
201
|
+
|
|
202
|
+
npm-build {:doc "Build npm package (clean, update version, generate types, compile ClojureScript)"
|
|
203
|
+
:depends [prep]
|
|
204
|
+
:task (npm/build-npm-package! config "npm-package")}
|
|
205
|
+
|
|
206
|
+
npm-test {:doc "Run npm package JavaScript tests"
|
|
207
|
+
:task (do
|
|
208
|
+
(println "Running npm package tests...")
|
|
209
|
+
(let [result (shell {:dir "npm-package"
|
|
210
|
+
:out :inherit
|
|
211
|
+
:err :inherit}
|
|
212
|
+
"node test.js")]
|
|
213
|
+
(when-not (zero? (:exit result))
|
|
214
|
+
(System/exit 1))))}
|
|
215
|
+
|
|
216
|
+
node-cljs-test {:doc "Compile and run ClojureScript tests on Node.js"
|
|
217
|
+
:depends [prep]
|
|
218
|
+
:task (do
|
|
219
|
+
(println "Compiling CLJS node tests...")
|
|
220
|
+
(shell "npx shadow-cljs compile node-test")
|
|
221
|
+
(println "Running CLJS node tests...")
|
|
222
|
+
(shell "node target/out/node-test.js"))}
|
|
223
|
+
|
|
224
|
+
browser-test {:doc "Run browser integration tests with Karma (headless Chrome)"
|
|
225
|
+
:depends [prep]
|
|
226
|
+
:task (let [;; Auto-detect Chrome binary
|
|
227
|
+
chrome-bin (or (System/getenv "CHROME_BIN")
|
|
228
|
+
(when (fs/exists? "/usr/bin/chromium-browser") "/usr/bin/chromium-browser")
|
|
229
|
+
(when (fs/exists? "/usr/bin/chromium") "/usr/bin/chromium")
|
|
230
|
+
(when (fs/exists? "/usr/bin/google-chrome") "/usr/bin/google-chrome"))]
|
|
231
|
+
(when-not chrome-bin
|
|
232
|
+
(println "ERROR: Chrome not found. Set CHROME_BIN environment variable.")
|
|
233
|
+
(System/exit 1))
|
|
234
|
+
|
|
235
|
+
;; Start JVM test server in background
|
|
236
|
+
(println "Starting Kabel test server on ws://localhost:47296...")
|
|
237
|
+
(let [server-proc (process/process
|
|
238
|
+
["clojure" "-M:test" "-e"
|
|
239
|
+
"(require 'datahike.kabel.browser-test-server) (datahike.kabel.browser-test-server/start-test-server!) (Thread/sleep Long/MAX_VALUE)"]
|
|
240
|
+
{:out :inherit :err :inherit})]
|
|
241
|
+
(try
|
|
242
|
+
;; Wait for server to start
|
|
243
|
+
(println "Waiting for server startup (10s)...")
|
|
244
|
+
(Thread/sleep 10000)
|
|
245
|
+
|
|
246
|
+
;; Compile browser tests
|
|
247
|
+
(println "Compiling browser tests...")
|
|
248
|
+
(shell "npx shadow-cljs compile browser-ci")
|
|
249
|
+
|
|
250
|
+
;; Run Karma
|
|
251
|
+
(println "Running tests with Karma...")
|
|
252
|
+
(shell {:extra-env {"CHROME_BIN" chrome-bin}} "npx karma start --single-run")
|
|
253
|
+
|
|
254
|
+
(finally
|
|
255
|
+
;; Kill the server process
|
|
256
|
+
(println "Stopping test server...")
|
|
257
|
+
(process/destroy-tree server-proc)))))}
|
|
258
|
+
|
|
259
|
+
browser-watch {:doc "Start browser test dev server (open http://localhost:8022)"
|
|
260
|
+
:depends [prep]
|
|
261
|
+
:task (do
|
|
262
|
+
(println "Starting browser test dev server...")
|
|
263
|
+
(println "Open http://localhost:8022 in your browser")
|
|
264
|
+
(shell "npx shadow-cljs watch browser-integration-test"))}
|
|
265
|
+
|
|
266
|
+
;; aggregate tasks
|
|
267
|
+
|
|
268
|
+
ci {:doc "Run CI checks (Clojure/ClojureScript + npm tests)"
|
|
269
|
+
:depends [test npm-test format lint]}}}
|
|
@@ -0,0 +1,195 @@
|
|
|
1
|
+
(ns benchmark.cli
|
|
2
|
+
(:require [clojure.tools.cli :as cli]
|
|
3
|
+
[benchmark.measure :refer [get-measurements time-statistics]]
|
|
4
|
+
[benchmark.compare :refer [compare-benchmarks]]
|
|
5
|
+
[benchmark.config :as c]
|
|
6
|
+
[benchmark.store :refer [save]]
|
|
7
|
+
[clojure.string :refer [join]]
|
|
8
|
+
[datahike.store :as ds]
|
|
9
|
+
[datahike.config :as dc]
|
|
10
|
+
[datahike.index :as di]))
|
|
11
|
+
|
|
12
|
+
(def output-formats (set (keys (methods save))))
|
|
13
|
+
(def config-names (set (map :config-name c/named-db-configs)))
|
|
14
|
+
(def implemented-queries #{:simple-query
|
|
15
|
+
:e-join-query :e-join-query-first-fixed :e-join-query-second-fixed
|
|
16
|
+
:a-join-query
|
|
17
|
+
:v-join-query
|
|
18
|
+
:equals-query :equals-query-1-fixed
|
|
19
|
+
:less-than-query :less-than-query-1-fixed
|
|
20
|
+
:scalar-arg-query :scalar-arg-query-with-join
|
|
21
|
+
:vector-arg-query
|
|
22
|
+
:limit-query
|
|
23
|
+
:stddev-query :variance-query :max-query :median-query :avg-query})
|
|
24
|
+
(def implemented-functions #{:connection :transaction :query})
|
|
25
|
+
(def implemented-data-types #{:int :str})
|
|
26
|
+
|
|
27
|
+
(def index-names (-> (methods di/default-index-config) keys set (disj :default)))
|
|
28
|
+
(def backend-names (-> (methods ds/default-config) keys set (disj :default)))
|
|
29
|
+
(def time-stats (-> (time-statistics [0]) keys set))
|
|
30
|
+
|
|
31
|
+
(def cli-options ;; TODO: use default values from datahike.config when available
|
|
32
|
+
[;; CMD run
|
|
33
|
+
["-u" "--db-server-url URL" "Base URL for datahike server, e.g. http://localhost:3000"
|
|
34
|
+
:default nil]
|
|
35
|
+
["-n" "--db-name DBNAME" "Database name for datahike server" :default nil]
|
|
36
|
+
["-g" "--db-token TOKEN" "Token for datahike server" :default nil]
|
|
37
|
+
|
|
38
|
+
["-t" "--tag TAG" "Add tag to measurements"
|
|
39
|
+
:default #{}
|
|
40
|
+
:assoc-fn (fn [m k v] (assoc m k (conj (get m k) v)))]
|
|
41
|
+
["-o" "--output-format FORMAT"
|
|
42
|
+
(str "Determines how the results will be processed. "
|
|
43
|
+
"Available are " output-formats " "
|
|
44
|
+
"Currently only edn format is supported for comparisons.")
|
|
45
|
+
:default "edn"
|
|
46
|
+
:validate [output-formats #(str "Format " % " has not been implemented. "
|
|
47
|
+
"Available formats are " output-formats)]]
|
|
48
|
+
["-e" "--statistics VECTOR"
|
|
49
|
+
(str "Statistic columns shown in the printed comparison summary. "
|
|
50
|
+
"Available are: " time-stats)
|
|
51
|
+
:default [:median :mean :std]
|
|
52
|
+
:parse-fn read-string
|
|
53
|
+
:validate [vector? (str "Must be a vector of cell names. Available are: " time-stats)
|
|
54
|
+
#(every? time-stats %) #(str "Must be a vector of cell names. Available are: " time-stats)]]
|
|
55
|
+
|
|
56
|
+
["-c" "--config-name CONFIGNAME"
|
|
57
|
+
(str "Name of preset database configuration to use. Available are: " config-names)
|
|
58
|
+
:validate [config-names #(str "A configuration named " % " has not been implemented. "
|
|
59
|
+
"Available configurations are: " config-names)]]
|
|
60
|
+
|
|
61
|
+
["-a" "--index INDEXNAME"
|
|
62
|
+
(str "Name of index to use. Available are " index-names)
|
|
63
|
+
:default :all
|
|
64
|
+
:parse-fn read-string
|
|
65
|
+
:validate [index-names #(str "An index named " % " has not been implemented. "
|
|
66
|
+
"Available indices are: " index-names)]]
|
|
67
|
+
["-l" "--history BOOLEAN"
|
|
68
|
+
(str "Boolean indication if measured databases use temporal indices")
|
|
69
|
+
:default false
|
|
70
|
+
:parse-fn read-string
|
|
71
|
+
:validate [#(contains? #{true false :all} %) "Must be a boolean value or keyword :all"]]
|
|
72
|
+
["-b" "--backend BACKEND"
|
|
73
|
+
(str "Keyword for backend that is going to be used")
|
|
74
|
+
:default :all
|
|
75
|
+
:parse-fn read-string
|
|
76
|
+
:validate [(conj backend-names :all) #(str "A backend named " % " has not been implemented. "
|
|
77
|
+
"Available backends are: " backend-names)]]
|
|
78
|
+
["-k" "--search-caches SIZES"
|
|
79
|
+
(str "Search cache sizes for which measurements should be done")
|
|
80
|
+
:default [dc/*default-search-cache-size*]
|
|
81
|
+
:parse-fn read-string
|
|
82
|
+
:validate [vector? "Must be a vector of non-negative integers."
|
|
83
|
+
#(every? nat-int? %) "Vector must consist of non-negative integers."]]
|
|
84
|
+
["-m" "--store-caches SIZES"
|
|
85
|
+
(str "Store cache sizes for which measurements should be done")
|
|
86
|
+
:default [dc/*default-store-cache-size*]
|
|
87
|
+
:parse-fn read-string
|
|
88
|
+
:validate [vector? "Must be a vector of positive integers."
|
|
89
|
+
#(every? pos-int? %) "Vector must consist of non-negative integers."]]
|
|
90
|
+
["-j" "--schema VALUE"
|
|
91
|
+
(str "Schema flexibility configuration. Available are: " #{:read :write})
|
|
92
|
+
:default :write
|
|
93
|
+
:parse-fn read-string
|
|
94
|
+
:validate [#{:read :write :all} #(str "A schema-flexibility named " % " has not been implemented. "
|
|
95
|
+
"Available values are: " #{:read :write})]]
|
|
96
|
+
|
|
97
|
+
["-d" "--db-entity-counts VECTOR"
|
|
98
|
+
(str "Numbers of entities in database for which benchmarks should be run. "
|
|
99
|
+
"Must be given as a clojure vector of non-negative integers like '[0 10 100 1000]'.")
|
|
100
|
+
:default [0 1000]
|
|
101
|
+
:parse-fn read-string
|
|
102
|
+
:validate [vector? "Must be a vector of non-negative integers."
|
|
103
|
+
#(every? nat-int? %) "Vector must consist of non-negative integers."]]
|
|
104
|
+
["-x" "--tx-entity-counts VECTOR"
|
|
105
|
+
(str "Numbers of entities in transaction for which benchmarks should be run. "
|
|
106
|
+
"Must be given as a clojure vector of non-negative integers like '[0 10 100 1000]'.")
|
|
107
|
+
:default [0 1000]
|
|
108
|
+
:parse-fn read-string
|
|
109
|
+
:validate [vector? "Must be a vector of non-negative integers."
|
|
110
|
+
#(every? nat-int? %) "Vector must consist of non-negative integers."]]
|
|
111
|
+
["-y" "--data-types VECTOR"
|
|
112
|
+
(str "Vector of datatypes to test queries on. Available are: " implemented-data-types ".")
|
|
113
|
+
:default [:int :str]
|
|
114
|
+
:parse-fn read-string
|
|
115
|
+
:validate [vector? (str "Must be a vector of data type keywords. Available are " implemented-data-types)
|
|
116
|
+
#(every? implemented-data-types %) (str "Vector must consist of keywords for datatypes. "
|
|
117
|
+
"Available are: " implemented-data-types)]]
|
|
118
|
+
["-z" "--data-found-opts BOOLEAN"
|
|
119
|
+
(str "Boolean indicating if query is run for existent or nonexistent values in the database.")
|
|
120
|
+
:default true
|
|
121
|
+
:parse-fn read-string
|
|
122
|
+
:validate [#{true false :all} "Must be a boolean value or keyword :all."]]
|
|
123
|
+
["-i" "--iterations ITERATIONS"
|
|
124
|
+
(str "Number of measurements for each setting taken on the same database.")
|
|
125
|
+
:default 10
|
|
126
|
+
:parse-fn read-string
|
|
127
|
+
:validate [nat-int? "Must be a non-negative integer."]]
|
|
128
|
+
["-s" "--db-samples DB-SAMPLES"
|
|
129
|
+
(str "Number of database instances on which the full measurements are run.")
|
|
130
|
+
:default 1
|
|
131
|
+
:parse-fn read-string
|
|
132
|
+
:validate [nat-int? "Must be a non-negative integer."]]
|
|
133
|
+
["-q" "--query QUERYNAME"
|
|
134
|
+
(str "Name of query to test. Available are " implemented-queries)
|
|
135
|
+
:default :all
|
|
136
|
+
:parse-fn read-string
|
|
137
|
+
:validate [(conj implemented-queries :all) (str "Must be a keyword for a implemented database query "
|
|
138
|
+
"Available are: " implemented-queries)]]
|
|
139
|
+
["-f" "--function FUNCTIONNAME"
|
|
140
|
+
(str "Name of function to test. Available are " implemented-functions)
|
|
141
|
+
:default :all
|
|
142
|
+
:parse-fn read-string
|
|
143
|
+
:validate [(conj implemented-functions :all) (str "Must be a keyword for implemented database function. "
|
|
144
|
+
"Available are: " implemented-functions)]]
|
|
145
|
+
|
|
146
|
+
;; CMD compare
|
|
147
|
+
|
|
148
|
+
["-p" "--[no-]plots" "Output comparison as plots."]
|
|
149
|
+
|
|
150
|
+
["-h" "--help"]])
|
|
151
|
+
|
|
152
|
+
|
|
153
|
+
(defn print-usage-info [summary]
|
|
154
|
+
(println (str "Usage: clj -M:benchmark CMD [OPTIONS] [FILEPATHS] \n\n Options for command 'run':\n" summary)))
|
|
155
|
+
|
|
156
|
+
(defmulti run-command (fn [cmd _paths _options] cmd))
|
|
157
|
+
|
|
158
|
+
(defmethod run-command :default [cmd _paths _options]
|
|
159
|
+
(throw (Exception. (str "Command '" cmd "' does not exist. Valid commands are 'measure' and 'compare'"))))
|
|
160
|
+
|
|
161
|
+
(defmethod run-command "compare" [_cmd paths {:keys [plots statistics]}]
|
|
162
|
+
(compare-benchmarks paths plots statistics))
|
|
163
|
+
|
|
164
|
+
|
|
165
|
+
(defmethod run-command "measure" [_cmd paths {:keys [tag output-format] :as options}]
|
|
166
|
+
(let [server-description (select-keys options [:db-server-url :db-token :db-name])]
|
|
167
|
+
(if (and (= "remote-db" output-format)
|
|
168
|
+
(some nil? (vals server-description)))
|
|
169
|
+
(do (println (str "Only partial information for remote connection has been given: " server-description))
|
|
170
|
+
(println "Please, define URL, database name, and token to save the data on a remote datahike server."))
|
|
171
|
+
(let [measurements (cond->> (get-measurements options)
|
|
172
|
+
(seq tag) (map (fn [entity] (assoc entity :tag (join " " tag))))
|
|
173
|
+
true vec) ]
|
|
174
|
+
(save options paths measurements)))))
|
|
175
|
+
|
|
176
|
+
(defn -main [& args]
|
|
177
|
+
(let [{:keys [arguments options errors summary]} (cli/parse-opts args cli-options)
|
|
178
|
+
[cmd & paths] arguments]
|
|
179
|
+
(cond
|
|
180
|
+
(some? errors)
|
|
181
|
+
(do (println "Errors:" errors)
|
|
182
|
+
(print-usage-info summary))
|
|
183
|
+
|
|
184
|
+
(:help options)
|
|
185
|
+
(print-usage-info summary)
|
|
186
|
+
|
|
187
|
+
:else (run-command cmd paths options)))
|
|
188
|
+
|
|
189
|
+
(shutdown-agents))
|
|
190
|
+
|
|
191
|
+
(comment
|
|
192
|
+
(-main "measure" "-x" "[0 10000 5000]" "-t" "test-bench" "-o" "edn" "bench.edn")
|
|
193
|
+
)
|
|
194
|
+
|
|
195
|
+
;TIMBRE_LEVEL=":info" clj -M:benchmark measure --backend :file --index :datahike.index/persistent-set -t pss -o edn pss.edn --schema :write --history false
|
|
@@ -0,0 +1,157 @@
|
|
|
1
|
+
(ns benchmark.compare
|
|
2
|
+
(:require [clojure.edn :as edn]
|
|
3
|
+
[clojure.string :refer [join]]
|
|
4
|
+
[incanter.core :as ic]
|
|
5
|
+
[incanter.charts :as charts]
|
|
6
|
+
[benchmark.config :as c]
|
|
7
|
+
[taoensso.timbre :as log]
|
|
8
|
+
[clojure.java.io :as io])
|
|
9
|
+
(:import [java.awt Color]))
|
|
10
|
+
|
|
11
|
+
(defn comparison-table [group filenames time-stats]
|
|
12
|
+
(let [col-mapping (zipmap (map :name c/csv-cols)
|
|
13
|
+
c/csv-cols)
|
|
14
|
+
grouped (group-by :context group)
|
|
15
|
+
context-sort-fn (fn [context]
|
|
16
|
+
(mapv #(get-in context (vec (rest (:path (% col-mapping))))) ;; rest since already in :context
|
|
17
|
+
c/comparison-context-cell-order))
|
|
18
|
+
sorted-contexts (sort-by context-sort-fn (keys grouped))
|
|
19
|
+
unique-context-key-spaces (map (fn [k]
|
|
20
|
+
(let [{:keys [title path]} (k col-mapping)]
|
|
21
|
+
(->> sorted-contexts
|
|
22
|
+
(map (fn [context]
|
|
23
|
+
(let [x (get-in context (vec (rest path)))]
|
|
24
|
+
(count (str (if (keyword? x)
|
|
25
|
+
(name x)
|
|
26
|
+
x))))))
|
|
27
|
+
(cons (count title))
|
|
28
|
+
(apply max))))
|
|
29
|
+
c/comparison-context-cell-order)
|
|
30
|
+
num-space 8
|
|
31
|
+
col-width (+ (* 3 (- (count time-stats) 1))
|
|
32
|
+
(* (count time-stats) num-space))
|
|
33
|
+
titles (concat (map #(get-in col-mapping [% :title])
|
|
34
|
+
c/comparison-context-cell-order)
|
|
35
|
+
filenames)
|
|
36
|
+
title-spaces (concat unique-context-key-spaces (repeat (count filenames) col-width))
|
|
37
|
+
subtitles (concat (repeat (count c/comparison-context-cell-order) "")
|
|
38
|
+
(apply concat (repeat (count filenames) time-stats)))
|
|
39
|
+
subtitle-spaces (concat unique-context-key-spaces
|
|
40
|
+
(repeat (* (count time-stats) (count filenames))
|
|
41
|
+
num-space))
|
|
42
|
+
dbl-fmt (str "%" num-space ".2f")
|
|
43
|
+
str-fmt (fn [cw] (str "%-" cw "s"))]
|
|
44
|
+
(str " | " (join " | " (map #(format (str-fmt %2) %1) titles title-spaces)) " |\n"
|
|
45
|
+
" |-" (join "-+-" (map (fn [s] (apply str (repeat s "-"))) title-spaces)) "-|\n"
|
|
46
|
+
" | " (join " | " (map #(format (str-fmt %2) %1) subtitles subtitle-spaces)) " |\n"
|
|
47
|
+
" |-" (join "-+-" (map (fn [s] (apply str (repeat s "-"))) subtitle-spaces)) "-|\n"
|
|
48
|
+
(join "\n" (for [[context results] (sort-by #(context-sort-fn (key %)) grouped)]
|
|
49
|
+
(let [times (map (fn [filename] (->> results (filter #(= (:source %) filename)) first :time))
|
|
50
|
+
filenames)
|
|
51
|
+
context-cells (map (fn [context-key col-width]
|
|
52
|
+
(let [context-val (get-in context (vec (rest (:path (context-key col-mapping)))) "")]
|
|
53
|
+
(format (str-fmt col-width)
|
|
54
|
+
(if (keyword? context-val)
|
|
55
|
+
(name context-val)
|
|
56
|
+
context-val))))
|
|
57
|
+
c/comparison-context-cell-order
|
|
58
|
+
unique-context-key-spaces)
|
|
59
|
+
measurement-cells (map (fn [measurements] (join " | " (map (fn [stat] (format dbl-fmt (stat measurements)))
|
|
60
|
+
time-stats)))
|
|
61
|
+
times)]
|
|
62
|
+
(str " | " (join " | " (concat context-cells measurement-cells)) " |"))))
|
|
63
|
+
"\n")))
|
|
64
|
+
|
|
65
|
+
|
|
66
|
+
(defn check-file-format [filename]
|
|
67
|
+
(when-not (.endsWith filename ".edn")
|
|
68
|
+
(throw (Exception. (str "File " filename "has an unsupported file type. Supported are only edn files.")))))
|
|
69
|
+
|
|
70
|
+
(defn report [benchmarks filenames time-stats]
|
|
71
|
+
(let [grouped-benchmarks (group-by #(get-in % [:context :function]) benchmarks)
|
|
72
|
+
output (str (when-let [conn-benchmarks (:connection grouped-benchmarks)]
|
|
73
|
+
(str "Connection Measurements (in s):\n"
|
|
74
|
+
(comparison-table conn-benchmarks filenames time-stats)
|
|
75
|
+
"\n"))
|
|
76
|
+
(when-let [tx-benchmarks (:transaction grouped-benchmarks)]
|
|
77
|
+
(str "Transaction Measurements (in s):\n"
|
|
78
|
+
(comparison-table tx-benchmarks filenames time-stats)
|
|
79
|
+
"\n"))
|
|
80
|
+
(when-let [query-benchmarks (->> (dissoc grouped-benchmarks :connection :transaction)
|
|
81
|
+
vals
|
|
82
|
+
(apply concat))]
|
|
83
|
+
(str "Query Measurements (in s):\n"
|
|
84
|
+
(comparison-table query-benchmarks filenames time-stats))))]
|
|
85
|
+
(println output)))
|
|
86
|
+
|
|
87
|
+
(defn create-plots [data] ;; 1 plot per function and context
|
|
88
|
+
(let [tags (join "," (distinct (map :tag data)))
|
|
89
|
+
colors [Color/red Color/blue Color/green Color/cyan Color/magenta Color/orange Color/yellow]
|
|
90
|
+
directory (str "plots-" tags)]
|
|
91
|
+
|
|
92
|
+
(doall (for [function (distinct (map #(get-in % [:context :function]) data))
|
|
93
|
+
config (distinct (map #(get-in % [:context :dh-config]) data))
|
|
94
|
+
execution-details (distinct (map #(get-in % [:context :execution]) data))]
|
|
95
|
+
(let [_ (log/debug (str "Processing " function " " config " " execution-details))
|
|
96
|
+
{:keys [tx-entities data-type data-in-db?]} execution-details
|
|
97
|
+
filename (str (name function)
|
|
98
|
+
"_config-" config
|
|
99
|
+
(when tx-entities
|
|
100
|
+
(str "_tx-ents-" tx-entities))
|
|
101
|
+
(when data-type
|
|
102
|
+
(str "_type-" (name data-type)))
|
|
103
|
+
(when data-in-db?
|
|
104
|
+
(str "_found-" data-in-db?))
|
|
105
|
+
"_tags-" tags
|
|
106
|
+
".png")
|
|
107
|
+
|
|
108
|
+
plot-data (->> data
|
|
109
|
+
(filter #(and (= (get-in % [:context :function]) function)
|
|
110
|
+
(= (get-in % [:context :dh-config]) config)
|
|
111
|
+
(= (get-in % [:context :execution]) execution-details)))
|
|
112
|
+
(map #(assoc % :x (get-in % [:context :db-entities]))))]
|
|
113
|
+
(when (seq plot-data)
|
|
114
|
+
(let [filepath (str directory "/" filename)
|
|
115
|
+
all-y (apply concat (map #(get-in % [:time :observations]) plot-data))
|
|
116
|
+
ymin 0
|
|
117
|
+
ymax (apply max all-y)
|
|
118
|
+
; ymax (quantile all-y :probs 0.9)
|
|
119
|
+
plot (charts/scatter-plot nil nil
|
|
120
|
+
:title (str "Execution time of function " function "\n"
|
|
121
|
+
"for configuration " (name config) " and\n"
|
|
122
|
+
"execution parameters " execution-details)
|
|
123
|
+
:y-label "Time (s)"
|
|
124
|
+
:x-label (str "Entities in database (1 entity = " (count c/schema) " datoms)")
|
|
125
|
+
:legend true
|
|
126
|
+
:series-label "")]
|
|
127
|
+
(charts/set-stroke-color plot (Color. 0 0 0 0) :dataset 0)
|
|
128
|
+
(charts/set-y-range plot ymin ymax)
|
|
129
|
+
(doall (map-indexed (fn [idx [tag group]]
|
|
130
|
+
(let [sorted (sort-by :x group)
|
|
131
|
+
entities (map :x sorted)
|
|
132
|
+
time (map :time sorted)
|
|
133
|
+
time-obs (apply concat (map :observations time))
|
|
134
|
+
entities-rep (apply concat (map #(repeat (count (:observations %2)) %1) entities time))]
|
|
135
|
+
|
|
136
|
+
(charts/add-points plot entities-rep time-obs :series-label tag)
|
|
137
|
+
(charts/set-stroke-color plot (get colors idx) :dataset (+ 1 (* idx 2)))
|
|
138
|
+
(charts/add-lines plot entities (map :median time) :series-label (str tag " median")))
|
|
139
|
+
(charts/set-stroke-color plot (get colors idx) :dataset (+ 2 (* idx 2))))
|
|
140
|
+
(group-by :tag plot-data)))
|
|
141
|
+
(when-not (.exists (io/file directory))
|
|
142
|
+
(.mkdir (io/file directory)))
|
|
143
|
+
(ic/save plot filepath
|
|
144
|
+
:width 800
|
|
145
|
+
:height 600))))))))
|
|
146
|
+
|
|
147
|
+
(defn compare-benchmarks [filenames plots? time-stats]
|
|
148
|
+
(run! check-file-format filenames)
|
|
149
|
+
|
|
150
|
+
(let [benchmarks (->> filenames
|
|
151
|
+
(map (fn [filename]
|
|
152
|
+
(map #(assoc % :source filename)
|
|
153
|
+
(edn/read-string (slurp filename)))))
|
|
154
|
+
(apply concat))]
|
|
155
|
+
(if plots?
|
|
156
|
+
(create-plots benchmarks)
|
|
157
|
+
(report benchmarks filenames time-stats))))
|