sturdy-bulkhead implements middleware to queue compute-intensive requests (such as DuckDB queries) within a Ring API.
It prevents CPU starvation by offloading work to dedicated worker pools using core.async.
Initialize a worker pool when your application starts.
(require '[sturdy.bulkhead :as bulkhead])
(def my-pool
(bulkhead/start-pool! {:num-workers 4 ; 4 concurrent queries max
:queue-size 20})) ; queue up to 20 requests
Use the provided middleware to wrap computationally expensive routes.
(def app
(-> heavy-query-handler
(bulkhead/wrap-compute-bound my-pool {:timeout-ms 10000})))
If you use reitit, you can attach the middleware to specific routes using its vector syntax:
(require '[reitit.ring :as ring])
(def app
(ring/ring-handler
(ring/router
["/api"
["/heavy" {:get {:middleware [[bulkhead/wrap-compute-bound my-pool {:timeout-ms 10000}]]
:handler heavy-query-handler}}]
["/light" {:get {:handler light-query-handler}}]])))
When shutting down your application, clean up the resources:
(bulkhead/stop-pool! my-pool)
This project uses deps.edn aliases for testing and validation.
# Run unit tests
clj -X:test
# Generate code coverage report (in target/coverage/index.html)
clj -X:coverage
# Scan dependencies for known vulnerabilities (clj-watson)
clj -X:vuln
Can you improve this documentation?Edit on GitHub
cljdoc builds & hosts documentation for Clojure/Script libraries
| Ctrl+k | Jump to recent docs |
| ← | Move to previous article |
| → | Move to next article |
| Ctrl+/ | Jump to the search field |