Compare commits

..

1 commit

Author SHA1 Message Date
Daw-Ran Liou
c953d9c82a
Merge a3c64baeba into 7520d20f12 2025-06-24 09:07:11 -05:00
68 changed files with 1366 additions and 710 deletions

View file

@ -1,26 +0,0 @@
name: Release
on:
release:
types:
- published # reacts to releases and prereleases, but not their drafts
jobs:
build-and-release:
runs-on: ubuntu-latest
steps:
- uses: actions/checkout@v5
- name: "Setup Java"
uses: actions/setup-java@v5
with:
distribution: zulu
java-version: 11
- name: "Setup Clojure"
uses: DeLaGuardo/setup-clojure@master
with:
lein: 2.9.5
- name: Deploy to Clojars
run: ./scripts/lein-modules do clean, deploy clojars
env:
CLOJARS_USERNAME: metosinci
CLOJARS_PASSWORD: "${{ secrets.CLOJARS_DEPLOY_TOKEN }}"

View file

@ -12,26 +12,6 @@ We use [Break Versioning][breakver]. The version numbers follow a `<major>.<mino
[breakver]: https://github.com/ptaoussanis/encore/blob/master/BREAK-VERSIONING.md [breakver]: https://github.com/ptaoussanis/encore/blob/master/BREAK-VERSIONING.md
## 0.9.2-rc1 (2025-10-24)
* Allow multimethods as handlers when validating [#755](https://github.com/metosin/reitit/pull/755)
* Improve error reporting when generating OpenAPI fails [#754](https://github.com/metosin/reitit/pull/754)
* Allow middleware registry to be used when defining middleware in `ring-handler`. See [docs](./doc/ring/middleware_registry.md). [#739](https://github.com/metosin/reitit/pull/739)
* Allow passing options (eg. `:malli.transform/add-optional-keys`) to malli's `default-value-transformer`. See [docs](./doc/coercion/malli_coercion.md). [#756](https://github.com/metosin/reitit/pull/756)
* **FIX**: `match-by-name!` returning `nil` instead of throwing an exception for some partial matches [#758](https://github.com/metosin/reitit/issues/758)
* Updated dependencies:
```
[com.fasterxml.jackson.core/jackson-core "2.20.0"] is available but we use "2.18.2"
[com.fasterxml.jackson.core/jackson-databind "2.20.0"] is available but we use "2.18.2"
[compojure "1.7.2"] is available but we use "1.7.1"
[fipp "0.6.29"] is available but we use "0.6.27"
[metosin/malli "0.19.2"] is available but we use "0.18.0"
[ring "1.15.3"] is available but we use "1.14.1"
[ring/ring-core "1.15.3"] is available but we use "1.14.1"
[ring/ring-defaults "0.7.0"] is available but we use "0.6.0"
```
## 0.9.1 (2025-05-27) ## 0.9.1 (2025-05-27)
* **FIX**: response coercion threw an exception for unlisted HTTP status codes if there was no `:default`. Broken in 0.9.0. [#742](https://github.com/metosin/reitit/issues/742) * **FIX**: response coercion threw an exception for unlisted HTTP status codes if there was no `:default`. Broken in 0.9.0. [#742](https://github.com/metosin/reitit/issues/742)

View file

@ -66,7 +66,7 @@ modules will continue to be released under `metosin` for compatibility purposes.
All main modules bundled: All main modules bundled:
```clj ```clj
[metosin/reitit "0.9.2-rc1"] [metosin/reitit "0.9.1"]
``` ```
Optionally, the parts can be required separately. Optionally, the parts can be required separately.

View file

@ -41,7 +41,7 @@ There is [#reitit](https://clojurians.slack.com/messages/reitit/) in [Clojurians
All bundled: All bundled:
```clj ```clj
[metosin/reitit "0.9.2-rc1"] [metosin/reitit "0.9.1"]
``` ```
Optionally, the parts can be required separately. Optionally, the parts can be required separately.

View file

@ -22,7 +22,7 @@ The default exception formatting uses `reitit.exception/exception`. It produces
## Pretty Errors ## Pretty Errors
```clj ```clj
[metosin/reitit-dev "0.9.2-rc1"] [metosin/reitit-dev "0.9.1"]
``` ```
For human-readable and developer-friendly exception messages, there is `reitit.dev.pretty/exception` (in the `reitit-dev` module). It is inspired by the lovely errors messages of [ELM](https://elm-lang.org/blog/compiler-errors-for-humans) and [ETA](https://twitter.com/jyothsnasrin/status/1037703436043603968) and uses [fipp](https://github.com/brandonbloom/fipp), [expound](https://github.com/bhb/expound) and [spell-spec](https://github.com/bhauman/spell-spec) for most of heavy lifting. For human-readable and developer-friendly exception messages, there is `reitit.dev.pretty/exception` (in the `reitit-dev` module). It is inspired by the lovely errors messages of [ELM](https://elm-lang.org/blog/compiler-errors-for-humans) and [ETA](https://twitter.com/jyothsnasrin/status/1037703436043603968) and uses [fipp](https://github.com/brandonbloom/fipp), [expound](https://github.com/bhb/expound) and [spell-spec](https://github.com/bhauman/spell-spec) for most of heavy lifting.

View file

@ -73,10 +73,9 @@ Using `create` with options to create the coercion instead of `coercion`:
{:transformers {:body {:default reitit.coercion.malli/default-transformer-provider {:transformers {:body {:default reitit.coercion.malli/default-transformer-provider
:formats {"application/json" reitit.coercion.malli/json-transformer-provider}} :formats {"application/json" reitit.coercion.malli/json-transformer-provider}}
:string {:default reitit.coercion.malli/string-transformer-provider} :string {:default reitit.coercion.malli/string-transformer-provider}
:response {:default reitit.coercion.malli/default-transformer-provider :response {:default reitit.coercion.malli/default-transformer-provider}}
:formats {"application/json" reitit.coercion.malli/json-transformer-provider}}}
;; set of keys to include in error messages ;; set of keys to include in error messages
:error-keys #{:type :coercion :in #_:schema :value #_:errors :humanized #_:transformed} :error-keys #{:type :coercion :in :schema :value :errors :humanized #_:transformed}
;; support lite syntax? ;; support lite syntax?
:lite true :lite true
;; schema identity function (default: close all map schemas) ;; schema identity function (default: close all map schemas)
@ -88,11 +87,7 @@ Using `create` with options to create the coercion instead of `coercion`:
;; strip-extra-keys (affects only predefined transformers) ;; strip-extra-keys (affects only predefined transformers)
:strip-extra-keys true :strip-extra-keys true
;; add/set default values ;; add/set default values
;; Can be false, true or a map of options to pass to malli.transform/default-value-transformer,
;; for example {:malli.transform/add-optional-keys true}
:default-values true :default-values true
;; encode-error
:encode-error nil
;; malli options ;; malli options
:options nil}) :options nil})
``` ```

View file

@ -25,14 +25,6 @@ clojure-lsp clean-ns
The documentation lives under `doc` and it is hosted on [cljdoc](https://cljdoc.org). See their The documentation lives under `doc` and it is hosted on [cljdoc](https://cljdoc.org). See their
documentation for [library authors](https://github.com/cljdoc/cljdoc/blob/master/doc/userguide/for-library-authors.adoc) documentation for [library authors](https://github.com/cljdoc/cljdoc/blob/master/doc/userguide/for-library-authors.adoc)
## Updating deps
* `lein ancient upgrade`
* Mention non-dev non-test dep upgrades in CHANGELOG.md
* `npm update --save`
* Make a PR, run CI
## Making a release ## Making a release
We use [Break Versioning][breakver]. Remember our promise: patch-level bumps never include breaking changes! We use [Break Versioning][breakver]. Remember our promise: patch-level bumps never include breaking changes!
@ -40,20 +32,25 @@ We use [Break Versioning][breakver]. Remember our promise: patch-level bumps nev
[breakver]: https://github.com/ptaoussanis/encore/blob/master/BREAK-VERSIONING.md [breakver]: https://github.com/ptaoussanis/encore/blob/master/BREAK-VERSIONING.md
```bash ```bash
# create a release commit # new version
./scripts/set-version "1.0.0" ./scripts/set-version "1.0.0"
# !!! update the changelog # create a release commit and a tag
git add -u
git add -u
git commit -m "Release 1.0.0" git commit -m "Release 1.0.0"
git tag 1.0.0
# push the commit # works
./scripts/lein-modules install
lein test
# deploy to clojars
CLOJARS_USERNAME=*** CLOJARS_PASSWORD=*** ./scripts/lein-modules do clean, deploy clojars
# push the commit and the tag
git push git push
git push --tags
# !!! check that tests pass on CI
``` ```
* Create a new release on github at <https://github.com/metosin/reitit/releases> * Remembor to update the changelog!
* This will trigger the automated release workflow <https://github.com/metosin/reitit/actions/workflows/release.yml>
* Announce the release at least on #reitit in Clojurians. * Announce the release at least on #reitit in Clojurians.

View file

@ -1,7 +1,7 @@
# Default Interceptors # Default Interceptors
```clj ```clj
[metosin/reitit-interceptors "0.9.2-rc1"] [metosin/reitit-interceptors "0.9.1"]
``` ```
Just like the [ring default middleware](../ring/default_middleware.md), but for interceptors. Just like the [ring default middleware](../ring/default_middleware.md), but for interceptors.

View file

@ -5,7 +5,7 @@ Reitit has also support for [interceptors](http://pedestal.io/reference/intercep
## Reitit-http ## Reitit-http
```clj ```clj
[metosin/reitit-http "0.9.2-rc1"] [metosin/reitit-http "0.9.1"]
``` ```
A module for http-routing using interceptors instead of middleware. Builds on top of the [`reitit-ring`](../ring/ring.md) module having all the same features. A module for http-routing using interceptors instead of middleware. Builds on top of the [`reitit-ring`](../ring/ring.md) module having all the same features.

View file

@ -3,7 +3,7 @@
[Pedestal](http://pedestal.io/) is a backend web framework for Clojure. `reitit-pedestal` provides an alternative routing engine for Pedestal. [Pedestal](http://pedestal.io/) is a backend web framework for Clojure. `reitit-pedestal` provides an alternative routing engine for Pedestal.
```clj ```clj
[metosin/reitit-pedestal "0.9.2-rc1"] [metosin/reitit-pedestal "0.9.1"]
``` ```
Why should one use reitit instead of the Pedestal [default routing](http://pedestal.io/reference/routing-quick-reference)? Why should one use reitit instead of the Pedestal [default routing](http://pedestal.io/reference/routing-quick-reference)?
@ -26,8 +26,8 @@ A minimalistic example on how to to swap the default-router with a reitit router
```clj ```clj
; [io.pedestal/pedestal.service "0.5.5"] ; [io.pedestal/pedestal.service "0.5.5"]
; [io.pedestal/pedestal.jetty "0.5.5"] ; [io.pedestal/pedestal.jetty "0.5.5"]
; [metosin/reitit-pedestal "0.9.2-rc1"] ; [metosin/reitit-pedestal "0.9.1"]
; [metosin/reitit "0.9.2-rc1"] ; [metosin/reitit "0.9.1"]
(require '[io.pedestal.http :as server]) (require '[io.pedestal.http :as server])
(require '[reitit.pedestal :as pedestal]) (require '[reitit.pedestal :as pedestal])

View file

@ -1,7 +1,7 @@
# Sieppari # Sieppari
```clj ```clj
[metosin/reitit-sieppari "0.9.2-rc1"] [metosin/reitit-sieppari "0.9.1"]
``` ```
[Sieppari](https://github.com/metosin/sieppari) is a new and fast interceptor implementation for Clojure, with pluggable async supporting [core.async](https://github.com/clojure/core.async), [Manifold](https://github.com/ztellman/manifold) and [Promesa](http://funcool.github.io/promesa/latest). [Sieppari](https://github.com/metosin/sieppari) is a new and fast interceptor implementation for Clojure, with pluggable async supporting [core.async](https://github.com/clojure/core.async), [Manifold](https://github.com/ztellman/manifold) and [Promesa](http://funcool.github.io/promesa/latest).

View file

@ -65,7 +65,7 @@ There is an extra option in http-router (actually, in the underlying interceptor
### Printing Context Diffs ### Printing Context Diffs
```clj ```clj
[metosin/reitit-interceptors "0.9.2-rc1"] [metosin/reitit-interceptors "0.9.1"]
``` ```
Using `reitit.http.interceptors.dev/print-context-diffs` transformation, the context diffs between each interceptor are printed out to the console. To use it, add the following router option: Using `reitit.http.interceptors.dev/print-context-diffs` transformation, the context diffs between each interceptor are printed out to the console. To use it, add the following router option:

View file

@ -1,7 +1,7 @@
# Default Middleware # Default Middleware
```clj ```clj
[metosin/reitit-middleware "0.9.2-rc1"] [metosin/reitit-middleware "0.9.1"]
``` ```
Any Ring middleware can be used with `reitit-ring`, but using data-driven middleware is preferred as they are easier to manage and in many cases yield better performance. `reitit-middleware` contains a set of common ring middleware, lifted into data-driven middleware. Any Ring middleware can be used with `reitit-ring`, but using data-driven middleware is preferred as they are easier to manage and in many cases yield better performance. `reitit-middleware` contains a set of common ring middleware, lifted into data-driven middleware.

View file

@ -1,7 +1,7 @@
# Exception Handling with Ring # Exception Handling with Ring
```clj ```clj
[metosin/reitit-middleware "0.9.2-rc1"] [metosin/reitit-middleware "0.9.1"]
``` ```
Exceptions thrown in router creation can be [handled with custom exception handler](../basics/error_messages.md). By default, exceptions thrown at runtime from a handler or a middleware are not caught by the `reitit.ring/ring-handler`. A good practice is to have a top-level exception handler to log and format errors for clients. Exceptions thrown in router creation can be [handled with custom exception handler](../basics/error_messages.md). By default, exceptions thrown at runtime from a handler or a middleware are not caught by the `reitit.ring/ring-handler`. A good practice is to have a top-level exception handler to log and format errors for clients.

View file

@ -2,7 +2,7 @@
The `:middleware` syntax in `reitit-ring` also supports Keywords. Keywords are looked up from the Middleware Registry, which is a map of `keyword => IntoMiddleware`. Middleware registry should be stored under key `:reitit.middleware/registry` in the router options. If a middleware keyword isn't found in the registry, router creation fails fast with a descriptive error message. The `:middleware` syntax in `reitit-ring` also supports Keywords. Keywords are looked up from the Middleware Registry, which is a map of `keyword => IntoMiddleware`. Middleware registry should be stored under key `:reitit.middleware/registry` in the router options. If a middleware keyword isn't found in the registry, router creation fails fast with a descriptive error message.
## Examples ## Examples
Application using middleware defined in the Middleware Registry: Application using middleware defined in the Middleware Registry:
@ -52,20 +52,6 @@ Router creation fails fast if the registry doesn't contain the middleware:
;| :bonus | reitit.ring_test$wrap_bonus@59fddabb | ;| :bonus | reitit.ring_test$wrap_bonus@59fddabb |
``` ```
Middleware defined in the registry can also be used on the `ring-handler` level:
```clj
(def app
(ring/ring-handler
(ring/router
["/api"
["/bonus" {:get (fn [{:keys [bonus]}]
{:status 200, :body {:bonus bonus}})}]]
{::middleware/registry {:bonus wrap-bonus}})
nil
{:middleware [[:bonus 15]]}))
```
## When to use the registry? ## When to use the registry?
Middleware as Keywords helps to keep the routes (all but handlers) as literal data (i.e. data that evaluates to itself), enabling the routes to be persisted in external formats like EDN-files and databases. Duct is a good example, where the [middleware can be referenced from EDN-files](https://github.com/duct-framework/duct/wiki/Configuration). It should be easy to make Duct configuration a Middleware Registry in `reitit-ring`. Middleware as Keywords helps to keep the routes (all but handlers) as literal data (i.e. data that evaluates to itself), enabling the routes to be persisted in external formats like EDN-files and databases. Duct is a good example, where the [middleware can be referenced from EDN-files](https://github.com/duct-framework/duct/wiki/Configuration). It should be easy to make Duct configuration a Middleware Registry in `reitit-ring`.

View file

@ -5,7 +5,7 @@
Read more about the [Ring Concepts](https://github.com/ring-clojure/ring/wiki/Concepts). Read more about the [Ring Concepts](https://github.com/ring-clojure/ring/wiki/Concepts).
```clj ```clj
[metosin/reitit-ring "0.9.2-rc1"] [metosin/reitit-ring "0.9.1"]
``` ```
## `reitit.ring/router` ## `reitit.ring/router`

View file

@ -1,7 +1,7 @@
# Swagger Support # Swagger Support
``` ```
[metosin/reitit-swagger "0.9.2-rc1"] [metosin/reitit-swagger "0.9.1"]
``` ```
Reitit supports [Swagger2](https://swagger.io/) documentation, thanks to [schema-tools](https://github.com/metosin/schema-tools) and [spec-tools](https://github.com/metosin/spec-tools). Documentation is extracted from route definitions, coercion `:parameters` and `:responses` and from a set of new documentation keys. Reitit supports [Swagger2](https://swagger.io/) documentation, thanks to [schema-tools](https://github.com/metosin/schema-tools) and [spec-tools](https://github.com/metosin/spec-tools). Documentation is extracted from route definitions, coercion `:parameters` and `:responses` and from a set of new documentation keys.
@ -47,7 +47,7 @@ If you need to post-process the generated spec, just wrap the handler with a cus
[Swagger-ui](https://github.com/swagger-api/swagger-ui) is a user interface to visualize and interact with the Swagger specification. To make things easy, there is a pre-integrated version of the swagger-ui as a separate module. [Swagger-ui](https://github.com/swagger-api/swagger-ui) is a user interface to visualize and interact with the Swagger specification. To make things easy, there is a pre-integrated version of the swagger-ui as a separate module.
``` ```
[metosin/reitit-swagger-ui "0.9.2-rc1"] [metosin/reitit-swagger-ui "0.9.1"]
``` ```
`reitit.swagger-ui/create-swagger-ui-handler` can be used to create a ring-handler to serve the swagger-ui. It accepts the following options: `reitit.swagger-ui/create-swagger-ui-handler` can be used to create a ring-handler to serve the swagger-ui. It accepts the following options:

View file

@ -59,7 +59,7 @@ There is an extra option in the Ring router (actually, in the underlying middlew
### Printing Request Diffs ### Printing Request Diffs
```clj ```clj
[metosin/reitit-middleware "0.9.2-rc1"] [metosin/reitit-middleware "0.9.1"]
``` ```
Using `reitit.ring.middleware.dev/print-request-diffs` transformation, the request diffs between each middleware are printed out to the console. To use it, add the following router option: Using `reitit.ring.middleware.dev/print-request-diffs` transformation, the request diffs between each middleware are printed out to the console. To use it, add the following router option:

View file

@ -2,6 +2,6 @@
:description "Reitit Buddy Auth App" :description "Reitit Buddy Auth App"
:dependencies [[org.clojure/clojure "1.11.2"] :dependencies [[org.clojure/clojure "1.11.2"]
[ring/ring-jetty-adapter "1.12.1"] [ring/ring-jetty-adapter "1.12.1"]
[metosin/reitit "0.9.2-rc1"] [metosin/reitit "0.9.1"]
[buddy "2.0.0"]] [buddy "2.0.0"]]
:repl-options {:init-ns example.server}) :repl-options {:init-ns example.server})

View file

@ -10,9 +10,9 @@
[ring "1.12.1"] [ring "1.12.1"]
[hiccup "1.0.5"] [hiccup "1.0.5"]
[org.clojure/clojurescript "1.11.132"] [org.clojure/clojurescript "1.11.132"]
[metosin/reitit "0.9.2-rc1"] [metosin/reitit "0.9.1"]
[metosin/reitit-schema "0.9.2-rc1"] [metosin/reitit-schema "0.9.1"]
[metosin/reitit-frontend "0.9.2-rc1"] [metosin/reitit-frontend "0.9.1"]
[cljsjs/react "17.0.2-0"] [cljsjs/react "17.0.2-0"]
[cljsjs/react-dom "17.0.2-0"] [cljsjs/react-dom "17.0.2-0"]
;; Just for pretty printting the match ;; Just for pretty printting the match

View file

@ -10,9 +10,9 @@
[ring "1.12.1"] [ring "1.12.1"]
[hiccup "1.0.5"] [hiccup "1.0.5"]
[org.clojure/clojurescript "1.11.132"] [org.clojure/clojurescript "1.11.132"]
[metosin/reitit "0.9.2-rc1"] [metosin/reitit "0.9.1"]
[metosin/reitit-schema "0.9.2-rc1"] [metosin/reitit-schema "0.9.1"]
[metosin/reitit-frontend "0.9.2-rc1"] [metosin/reitit-frontend "0.9.1"]
[cljsjs/react "17.0.2-0"] [cljsjs/react "17.0.2-0"]
[cljsjs/react-dom "17.0.2-0"] [cljsjs/react-dom "17.0.2-0"]
;; Just for pretty printting the match ;; Just for pretty printting the match

View file

@ -10,9 +10,9 @@
[ring "1.12.1"] [ring "1.12.1"]
[hiccup "1.0.5"] [hiccup "1.0.5"]
[org.clojure/clojurescript "1.10.520"] [org.clojure/clojurescript "1.10.520"]
[metosin/reitit "0.9.2-rc1"] [metosin/reitit "0.9.1"]
[metosin/reitit-spec "0.9.2-rc1"] [metosin/reitit-spec "0.9.1"]
[metosin/reitit-frontend "0.9.2-rc1"] [metosin/reitit-frontend "0.9.1"]
[cljsjs/react "17.0.2-0"] [cljsjs/react "17.0.2-0"]
[cljsjs/react-dom "17.0.2-0"] [cljsjs/react-dom "17.0.2-0"]
;; Just for pretty printting the match ;; Just for pretty printting the match

View file

@ -10,9 +10,9 @@
[ring "1.12.1"] [ring "1.12.1"]
[hiccup "1.0.5"] [hiccup "1.0.5"]
[org.clojure/clojurescript "1.11.132"] [org.clojure/clojurescript "1.11.132"]
[metosin/reitit "0.9.2-rc1"] [metosin/reitit "0.9.1"]
[metosin/reitit-malli "0.9.2-rc1"] [metosin/reitit-malli "0.9.1"]
[metosin/reitit-frontend "0.9.2-rc1"] [metosin/reitit-frontend "0.9.1"]
[cljsjs/react "17.0.2-0"] [cljsjs/react "17.0.2-0"]
[cljsjs/react-dom "17.0.2-0"] [cljsjs/react-dom "17.0.2-0"]
;; Just for pretty printting the match ;; Just for pretty printting the match

View file

@ -10,9 +10,9 @@
[ring "1.12.1"] [ring "1.12.1"]
[hiccup "1.0.5"] [hiccup "1.0.5"]
[org.clojure/clojurescript "1.11.132"] [org.clojure/clojurescript "1.11.132"]
[metosin/reitit "0.9.2-rc1"] [metosin/reitit "0.9.1"]
[metosin/reitit-spec "0.9.2-rc1"] [metosin/reitit-spec "0.9.1"]
[metosin/reitit-frontend "0.9.2-rc1"] [metosin/reitit-frontend "0.9.1"]
[cljsjs/react "17.0.2-0"] [cljsjs/react "17.0.2-0"]
[cljsjs/react-dom "17.0.2-0"] [cljsjs/react-dom "17.0.2-0"]
;; Just for pretty printting the match ;; Just for pretty printting the match

View file

@ -1,7 +1,7 @@
(defproject frontend-re-frame "0.1.0-SNAPSHOT" (defproject frontend-re-frame "0.1.0-SNAPSHOT"
:dependencies [[org.clojure/clojure "1.11.2"] :dependencies [[org.clojure/clojure "1.11.2"]
[org.clojure/clojurescript "1.11.132"] [org.clojure/clojurescript "1.11.132"]
[metosin/reitit "0.9.2-rc1"] [metosin/reitit "0.9.1"]
[reagent "1.2.0"] [reagent "1.2.0"]
[re-frame "0.10.6"] [re-frame "0.10.6"]
[cljsjs/react "17.0.2-0"] [cljsjs/react "17.0.2-0"]

View file

@ -10,9 +10,9 @@
[ring "1.12.1"] [ring "1.12.1"]
[hiccup "1.0.5"] [hiccup "1.0.5"]
[org.clojure/clojurescript "1.11.132"] [org.clojure/clojurescript "1.11.132"]
[metosin/reitit "0.9.2-rc1"] [metosin/reitit "0.9.1"]
[metosin/reitit-spec "0.9.2-rc1"] [metosin/reitit-spec "0.9.1"]
[metosin/reitit-frontend "0.9.2-rc1"] [metosin/reitit-frontend "0.9.1"]
[cljsjs/react "17.0.2-0"] [cljsjs/react "17.0.2-0"]
[cljsjs/react-dom "17.0.2-0"] [cljsjs/react-dom "17.0.2-0"]
;; Just for pretty printting the match ;; Just for pretty printting the match

View file

@ -3,6 +3,6 @@
:dependencies [[org.clojure/clojure "1.11.2"] :dependencies [[org.clojure/clojure "1.11.2"]
[ring/ring-jetty-adapter "1.12.1"] [ring/ring-jetty-adapter "1.12.1"]
[aleph "0.7.1"] [aleph "0.7.1"]
[metosin/reitit "0.9.2-rc1"] [metosin/reitit "0.9.1"]
[metosin/ring-swagger-ui "5.9.0"]] [metosin/ring-swagger-ui "5.9.0"]]
:repl-options {:init-ns example.server}) :repl-options {:init-ns example.server})

View file

@ -5,5 +5,5 @@
[funcool/promesa "11.0.678"] [funcool/promesa "11.0.678"]
[manifold "0.4.2"] [manifold "0.4.2"]
[ring/ring-jetty-adapter "1.12.1"] [ring/ring-jetty-adapter "1.12.1"]
[metosin/reitit "0.9.2-rc1"]] [metosin/reitit "0.9.1"]]
:repl-options {:init-ns example.server}) :repl-options {:init-ns example.server})

View file

@ -2,4 +2,4 @@
:description "Reitit coercion with vanilla ring" :description "Reitit coercion with vanilla ring"
:dependencies [[org.clojure/clojure "1.11.2"] :dependencies [[org.clojure/clojure "1.11.2"]
[ring/ring-jetty-adapter "1.12.1"] [ring/ring-jetty-adapter "1.12.1"]
[metosin/reitit "0.9.2-rc1"]]) [metosin/reitit "0.9.1"]])

View file

@ -3,7 +3,7 @@
:dependencies [[org.clojure/clojure "1.11.2"] :dependencies [[org.clojure/clojure "1.11.2"]
[metosin/jsonista "0.3.8"] [metosin/jsonista "0.3.8"]
[ring/ring-jetty-adapter "1.12.1"] [ring/ring-jetty-adapter "1.12.1"]
[metosin/reitit "0.9.2-rc1"] [metosin/reitit "0.9.1"]
[metosin/ring-swagger-ui "5.9.0"]] [metosin/ring-swagger-ui "5.9.0"]]
:repl-options {:init-ns example.server} :repl-options {:init-ns example.server}
:profiles {:dev {:dependencies [[ring/ring-mock "0.4.0"]]}}) :profiles {:dev {:dependencies [[ring/ring-mock "0.4.0"]]}})

View file

@ -3,7 +3,7 @@
:dependencies [[org.clojure/clojure "1.11.2"] :dependencies [[org.clojure/clojure "1.11.2"]
[io.pedestal/pedestal.service "0.6.3"] [io.pedestal/pedestal.service "0.6.3"]
[io.pedestal/pedestal.jetty "0.6.3"] [io.pedestal/pedestal.jetty "0.6.3"]
[metosin/reitit-malli "0.9.2-rc1"] [metosin/reitit-malli "0.9.1"]
[metosin/reitit-pedestal "0.9.2-rc1"] [metosin/reitit-pedestal "0.9.1"]
[metosin/reitit "0.9.2-rc1"]] [metosin/reitit "0.9.1"]]
:repl-options {:init-ns server}) :repl-options {:init-ns server})

View file

@ -3,6 +3,6 @@
:dependencies [[org.clojure/clojure "1.11.2"] :dependencies [[org.clojure/clojure "1.11.2"]
[io.pedestal/pedestal.service "0.6.3"] [io.pedestal/pedestal.service "0.6.3"]
[io.pedestal/pedestal.jetty "0.6.3"] [io.pedestal/pedestal.jetty "0.6.3"]
[metosin/reitit-pedestal "0.9.2-rc1"] [metosin/reitit-pedestal "0.9.1"]
[metosin/reitit "0.9.2-rc1"]] [metosin/reitit "0.9.1"]]
:repl-options {:init-ns example.server}) :repl-options {:init-ns example.server})

View file

@ -3,6 +3,6 @@
:dependencies [[org.clojure/clojure "1.11.2"] :dependencies [[org.clojure/clojure "1.11.2"]
[io.pedestal/pedestal.service "0.6.3"] [io.pedestal/pedestal.service "0.6.3"]
[io.pedestal/pedestal.jetty "0.6.3"] [io.pedestal/pedestal.jetty "0.6.3"]
[metosin/reitit-pedestal "0.9.2-rc1"] [metosin/reitit-pedestal "0.9.1"]
[metosin/reitit "0.9.2-rc1"]] [metosin/reitit "0.9.1"]]
:repl-options {:init-ns example.server}) :repl-options {:init-ns example.server})

View file

@ -2,5 +2,5 @@
:description "Reitit Ring App" :description "Reitit Ring App"
:dependencies [[org.clojure/clojure "1.11.2"] :dependencies [[org.clojure/clojure "1.11.2"]
[ring/ring-jetty-adapter "1.12.1"] [ring/ring-jetty-adapter "1.12.1"]
[metosin/reitit "0.9.2-rc1"]] [metosin/reitit "0.9.1"]]
:repl-options {:init-ns example.server}) :repl-options {:init-ns example.server})

View file

@ -2,7 +2,7 @@
:description "Reitit Ring App with Integrant" :description "Reitit Ring App with Integrant"
:dependencies [[org.clojure/clojure "1.11.2"] :dependencies [[org.clojure/clojure "1.11.2"]
[ring/ring-jetty-adapter "1.12.1"] [ring/ring-jetty-adapter "1.12.1"]
[metosin/reitit "0.9.2-rc1"] [metosin/reitit "0.9.1"]
[integrant "0.8.1"]] [integrant "0.8.1"]]
:main example.server :main example.server
:repl-options {:init-ns user} :repl-options {:init-ns user}

View file

@ -3,6 +3,6 @@
:dependencies [[org.clojure/clojure "1.11.2"] :dependencies [[org.clojure/clojure "1.11.2"]
[metosin/jsonista "0.3.8"] [metosin/jsonista "0.3.8"]
[ring/ring-jetty-adapter "1.12.1"] [ring/ring-jetty-adapter "1.12.1"]
[metosin/reitit "0.9.2-rc1"]] [metosin/reitit "0.9.1"]]
:repl-options {:init-ns example.server} :repl-options {:init-ns example.server}
:profiles {:dev {:dependencies [[ring/ring-mock "0.4.0"]]}}) :profiles {:dev {:dependencies [[ring/ring-mock "0.4.0"]]}})

View file

@ -3,7 +3,7 @@
:dependencies [[org.clojure/clojure "1.11.2"] :dependencies [[org.clojure/clojure "1.11.2"]
[metosin/jsonista "0.3.8"] [metosin/jsonista "0.3.8"]
[ring/ring-jetty-adapter "1.12.1"] [ring/ring-jetty-adapter "1.12.1"]
[metosin/reitit "0.9.2-rc1"] [metosin/reitit "0.9.1"]
[metosin/ring-swagger-ui "5.9.0"]] [metosin/ring-swagger-ui "5.9.0"]]
:repl-options {:init-ns example.server} :repl-options {:init-ns example.server}
:profiles {:dev {:dependencies [[ring/ring-mock "0.4.0"]]}}) :profiles {:dev {:dependencies [[ring/ring-mock "0.4.0"]]}})

View file

@ -2,7 +2,7 @@
:description "Reitit Ring App with Swagger" :description "Reitit Ring App with Swagger"
:dependencies [[org.clojure/clojure "1.11.2"] :dependencies [[org.clojure/clojure "1.11.2"]
[ring/ring-jetty-adapter "1.12.1"] [ring/ring-jetty-adapter "1.12.1"]
[metosin/reitit "0.9.2-rc1"] [metosin/reitit "0.9.1"]
[metosin/ring-swagger-ui "5.9.0"]] [metosin/ring-swagger-ui "5.9.0"]]
:repl-options {:init-ns example.server} :repl-options {:init-ns example.server}
:profiles {:dev {:dependencies [[ring/ring-mock "0.4.0"]]}}) :profiles {:dev {:dependencies [[ring/ring-mock "0.4.0"]]}})

View file

@ -1,4 +1,4 @@
(defproject metosin/reitit-core "0.9.2-rc1" (defproject metosin/reitit-core "0.9.1"
:description "Snappy data-driven router for Clojure(Script)" :description "Snappy data-driven router for Clojure(Script)"
:url "https://github.com/metosin/reitit" :url "https://github.com/metosin/reitit"
:license {:name "Eclipse Public License" :license {:name "Eclipse Public License"

View file

@ -198,8 +198,9 @@
(:path route))) (:path route)))
(defn throw-on-missing-path-params [template required path-params] (defn throw-on-missing-path-params [template required path-params]
(let [missing (set (remove #(get path-params %) required))] (when-not (every? #(contains? path-params %) required)
(when-not (empty? missing) (let [defined (-> path-params keys set)
missing (set/difference required defined)]
(ex/fail! (ex/fail!
(str "missing path-params for route " template " -> " missing) (str "missing path-params for route " template " -> " missing)
{:path-params path-params, :required required})))) {:path-params path-params, :required required}))))

View file

@ -37,11 +37,8 @@
;; Default data ;; Default data
;; ;;
(defn -multi? [x]
(instance? #?(:clj clojure.lang.MultiFn :cljs cljs.core.MultiFn) x))
(s/def ::name keyword?) (s/def ::name keyword?)
(s/def ::handler (s/or :fn fn? :var var? :multi -multi?)) (s/def ::handler (s/or :fn fn? :var var?))
(s/def ::no-doc boolean?) (s/def ::no-doc boolean?)
(s/def ::conflicting boolean?) (s/def ::conflicting boolean?)
(s/def ::default-data (s/def ::default-data

View file

@ -1,4 +1,4 @@
(defproject metosin/reitit-dev "0.9.2-rc1" (defproject metosin/reitit-dev "0.9.1"
:description "Snappy data-driven router for Clojure(Script)" :description "Snappy data-driven router for Clojure(Script)"
:url "https://github.com/metosin/reitit" :url "https://github.com/metosin/reitit"
:license {:name "Eclipse Public License" :license {:name "Eclipse Public License"

View file

@ -1,4 +1,4 @@
(defproject metosin/reitit-frontend "0.9.2-rc1" (defproject metosin/reitit-frontend "0.9.1"
:description "Reitit: Clojurescript frontend routing core" :description "Reitit: Clojurescript frontend routing core"
:url "https://github.com/metosin/reitit" :url "https://github.com/metosin/reitit"
:license {:name "Eclipse Public License" :license {:name "Eclipse Public License"

View file

@ -1,4 +1,4 @@
(defproject metosin/reitit-http "0.9.2-rc1" (defproject metosin/reitit-http "0.9.1"
:description "Reitit: HTTP routing with interceptors" :description "Reitit: HTTP routing with interceptors"
:url "https://github.com/metosin/reitit" :url "https://github.com/metosin/reitit"
:license {:name "Eclipse Public License" :license {:name "Eclipse Public License"

View file

@ -1,4 +1,4 @@
(defproject metosin/reitit-interceptors "0.9.2-rc1" (defproject metosin/reitit-interceptors "0.9.1"
:description "Reitit, common interceptors bundled" :description "Reitit, common interceptors bundled"
:url "https://github.com/metosin/reitit" :url "https://github.com/metosin/reitit"
:license {:name "Eclipse Public License" :license {:name "Eclipse Public License"

View file

@ -1,4 +1,4 @@
(defproject metosin/reitit-malli "0.9.2-rc1" (defproject metosin/reitit-malli "0.9.1"
:description "Reitit: Malli coercion" :description "Reitit: Malli coercion"
:url "https://github.com/metosin/reitit" :url "https://github.com/metosin/reitit"
:license {:name "Eclipse Public License" :license {:name "Eclipse Public License"

View file

@ -9,7 +9,8 @@
[malli.swagger :as swagger] [malli.swagger :as swagger]
[malli.transform :as mt] [malli.transform :as mt]
[malli.util :as mu] [malli.util :as mu]
[reitit.coercion :as coercion])) [reitit.coercion :as coercion]
[clojure.string :as string]))
;; ;;
;; coercion ;; coercion
@ -30,7 +31,7 @@
(mt/transformer (mt/transformer
(if strip-extra-keys (mt/strip-extra-keys-transformer)) (if strip-extra-keys (mt/strip-extra-keys-transformer))
transformer transformer
(if default-values (mt/default-value-transformer (if (map? default-values) default-values {}))))))) (if default-values (mt/default-value-transformer))))))
(def string-transformer-provider (-provider (mt/string-transformer))) (def string-transformer-provider (-provider (mt/string-transformer)))
(def json-transformer-provider (-provider (mt/json-transformer))) (def json-transformer-provider (-provider (mt/json-transformer)))
@ -115,9 +116,7 @@
:enabled true :enabled true
;; strip-extra-keys (affects only predefined transformers) ;; strip-extra-keys (affects only predefined transformers)
:strip-extra-keys true :strip-extra-keys true
;; add/set default values. ;; add/set default values
;; Can be false, true or a map of options to pass to malli.transform/default-value-transformer,
;; for example {:malli.transform/add-optional-keys true}
:default-values true :default-values true
;; encode-error ;; encode-error
:encode-error nil :encode-error nil

View file

@ -1,4 +1,4 @@
(defproject metosin/reitit-middleware "0.9.2-rc1" (defproject metosin/reitit-middleware "0.9.1"
:description "Reitit, common middleware bundled" :description "Reitit, common middleware bundled"
:url "https://github.com/metosin/reitit" :url "https://github.com/metosin/reitit"
:license {:name "Eclipse Public License" :license {:name "Eclipse Public License"

View file

@ -58,10 +58,7 @@
"Creates a Middleware to handle the multipart params, based on "Creates a Middleware to handle the multipart params, based on
ring.middleware.multipart-params, taking same options. Mounts only ring.middleware.multipart-params, taking same options. Mounts only
if endpoint has `[:parameters :multipart]` defined. Publishes coerced if endpoint has `[:parameters :multipart]` defined. Publishes coerced
parameters into `[:parameters :multipart]` under request. parameters into `[:parameters :multipart]` under request."
Note! You want to have multipart-middleware after coerce-request-middleware,
because coerce-request-middleware overwrites `:parameters`."
([] ([]
(create-multipart-middleware nil)) (create-multipart-middleware nil))
([options] ([options]
@ -72,8 +69,5 @@
"Middleware to handle the multipart params, based on "Middleware to handle the multipart params, based on
ring.middleware.multipart-params, taking same options. Mounts only ring.middleware.multipart-params, taking same options. Mounts only
if endpoint has `[:parameters :multipart]` defined. Publishes coerced if endpoint has `[:parameters :multipart]` defined. Publishes coerced
parameters into `[:parameters :multipart]` under request. parameters into `[:parameters :multipart]` under request."
Note! You want to have multipart-middleware after coerce-request-middleware,
because coerce-request-middleware overwrites `:parameters`."
(create-multipart-middleware)) (create-multipart-middleware))

View file

@ -1,4 +1,4 @@
(defproject fi.metosin/reitit-openapi "0.9.2-rc1" (defproject fi.metosin/reitit-openapi "0.9.1"
:description "Reitit: OpenAPI-support" :description "Reitit: OpenAPI-support"
:url "https://github.com/metosin/reitit" :url "https://github.com/metosin/reitit"
:license {:name "Eclipse Public License" :license {:name "Eclipse Public License"

View file

@ -206,23 +206,20 @@
accept-route (fn [route] accept-route (fn [route]
(-> route second :openapi :id (or ::default) (trie/into-set) (set/intersection ids) seq)) (-> route second :openapi :id (or ::default) (trie/into-set) (set/intersection ids) seq))
definitions (volatile! {}) definitions (volatile! {})
transform-endpoint (fn [path [method {{:keys [coercion no-doc openapi] :as data} :data transform-endpoint (fn [[method {{:keys [coercion no-doc openapi] :as data} :data
middleware :middleware middleware :middleware
interceptors :interceptors}]] interceptors :interceptors}]]
(try (if (and data (not no-doc))
(if (and data (not no-doc)) [method
[method (meta-merge
(meta-merge (apply meta-merge (keep (comp :openapi :data) middleware))
(apply meta-merge (keep (comp :openapi :data) middleware)) (apply meta-merge (keep (comp :openapi :data) interceptors))
(apply meta-merge (keep (comp :openapi :data) interceptors)) (if coercion
(if coercion (-get-apidocs-openapi coercion data definitions))
(-get-apidocs-openapi coercion data definitions)) (select-keys data [:tags :summary :description])
(select-keys data [:tags :summary :description]) (strip-top-level-keys openapi))]))
(strip-top-level-keys openapi))])
(catch Throwable t
(throw (ex-info "While building openapi docs" {:path path :method method} t)))))
transform-path (fn [[p _ c]] transform-path (fn [[p _ c]]
(if-let [endpoint (some->> c (keep (partial transform-endpoint p)) (seq) (into {}))] (if-let [endpoint (some->> c (keep transform-endpoint) (seq) (into {}))]
[(openapi-path p (r/options router)) endpoint])) [(openapi-path p (r/options router)) endpoint]))
map-in-order #(->> % (apply concat) (apply array-map)) map-in-order #(->> % (apply concat) (apply array-map))
paths (->> router (r/compiled-routes) (filter accept-route) (map transform-path) map-in-order)] paths (->> router (r/compiled-routes) (filter accept-route) (map transform-path) map-in-order)]

View file

@ -1,4 +1,4 @@
(defproject metosin/reitit-pedestal "0.9.2-rc1" (defproject metosin/reitit-pedestal "0.9.1"
:description "Reitit + Pedestal Integration" :description "Reitit + Pedestal Integration"
:url "https://github.com/metosin/reitit" :url "https://github.com/metosin/reitit"
:license {:name "Eclipse Public License" :license {:name "Eclipse Public License"

View file

@ -1,4 +1,4 @@
(defproject metosin/reitit-ring "0.9.2-rc1" (defproject metosin/reitit-ring "0.9.1"
:description "Reitit: Ring routing" :description "Reitit: Ring routing"
:url "https://github.com/metosin/reitit" :url "https://github.com/metosin/reitit"
:license {:name "Eclipse Public License" :license {:name "Eclipse Public License"

View file

@ -370,7 +370,7 @@
([router default-handler {:keys [middleware inject-match? inject-router?] ([router default-handler {:keys [middleware inject-match? inject-router?]
:or {inject-match? true, inject-router? true}}] :or {inject-match? true, inject-router? true}}]
(let [default-handler (or default-handler (fn ([_]) ([_ respond _] (respond nil)))) (let [default-handler (or default-handler (fn ([_]) ([_ respond _] (respond nil))))
wrap (if middleware #(middleware/chain middleware % nil (r/options router)) identity) wrap (if middleware (partial middleware/chain middleware) identity)
enrich-request (create-enrich-request inject-match? inject-router?) enrich-request (create-enrich-request inject-match? inject-router?)
enrich-default-request (create-enrich-default-request inject-router?)] enrich-default-request (create-enrich-default-request inject-router?)]
(with-meta (with-meta

View file

@ -1,4 +1,4 @@
(defproject metosin/reitit-schema "0.9.2-rc1" (defproject metosin/reitit-schema "0.9.1"
:description "Reitit: Plumatic Schema coercion" :description "Reitit: Plumatic Schema coercion"
:url "https://github.com/metosin/reitit" :url "https://github.com/metosin/reitit"
:license {:name "Eclipse Public License" :license {:name "Eclipse Public License"

View file

@ -1,4 +1,4 @@
(defproject metosin/reitit-sieppari "0.9.2-rc1" (defproject metosin/reitit-sieppari "0.9.1"
:description "Reitit: Sieppari Interceptors" :description "Reitit: Sieppari Interceptors"
:url "https://github.com/metosin/reitit" :url "https://github.com/metosin/reitit"
:license {:name "Eclipse Public License" :license {:name "Eclipse Public License"

View file

@ -1,4 +1,4 @@
(defproject metosin/reitit-spec "0.9.2-rc1" (defproject metosin/reitit-spec "0.9.1"
:description "Reitit: clojure.spec coercion" :description "Reitit: clojure.spec coercion"
:url "https://github.com/metosin/reitit" :url "https://github.com/metosin/reitit"
:license {:name "Eclipse Public License" :license {:name "Eclipse Public License"

View file

@ -1,4 +1,4 @@
(defproject metosin/reitit-swagger-ui "0.9.2-rc1" (defproject metosin/reitit-swagger-ui "0.9.1"
:description "Reitit: Swagger-ui support" :description "Reitit: Swagger-ui support"
:url "https://github.com/metosin/reitit" :url "https://github.com/metosin/reitit"
:license {:name "Eclipse Public License" :license {:name "Eclipse Public License"

View file

@ -1,4 +1,4 @@
(defproject metosin/reitit-swagger "0.9.2-rc1" (defproject metosin/reitit-swagger "0.9.1"
:description "Reitit: Swagger-support" :description "Reitit: Swagger-support"
:url "https://github.com/metosin/reitit" :url "https://github.com/metosin/reitit"
:license {:name "Eclipse Public License" :license {:name "Eclipse Public License"

View file

@ -1,4 +1,4 @@
(defproject metosin/reitit "0.9.2-rc1" (defproject metosin/reitit "0.9.1"
:description "Snappy data-driven router for Clojure(Script)" :description "Snappy data-driven router for Clojure(Script)"
:url "https://github.com/metosin/reitit" :url "https://github.com/metosin/reitit"
:license {:name "Eclipse Public License" :license {:name "Eclipse Public License"

1607
package-lock.json generated

File diff suppressed because it is too large Load diff

View file

@ -2,13 +2,13 @@
"name": "reitit", "name": "reitit",
"private": true, "private": true,
"devDependencies": { "devDependencies": {
"@seriousme/openapi-schema-validator": "^2.7.0", "@seriousme/openapi-schema-validator": "^2.4.0",
"karma": "^6.4.4", "karma": "^6.4.4",
"karma-chrome-launcher": "^3.2.0", "karma-chrome-launcher": "^3.2.0",
"karma-cli": "^2.0.0", "karma-cli": "^2.0.0",
"karma-cljs-test": "^0.1.0" "karma-cljs-test": "^0.1.0"
}, },
"dependencies": { "dependencies": {
"shadow-cljs": "^3.2.1" "shadow-cljs": "^2.28.22"
} }
} }

View file

@ -1,4 +1,4 @@
(defproject metosin/reitit-parent "0.9.2-rc1" (defproject metosin/reitit-parent "0.9.1"
:description "Snappy data-driven router for Clojure(Script)" :description "Snappy data-driven router for Clojure(Script)"
:url "https://github.com/metosin/reitit" :url "https://github.com/metosin/reitit"
:license {:name "Eclipse Public License" :license {:name "Eclipse Public License"
@ -6,8 +6,7 @@
:test-paths ["test/clj" "test/cljc"] :test-paths ["test/clj" "test/cljc"]
:deploy-repositories [["clojars" {:url "https://repo.clojars.org" :deploy-repositories [["clojars" {:url "https://repo.clojars.org"
:username :env/clojars_username :username :env/clojars_username
:password :env/clojars_password :password :env/clojars_password}]]
:sign-releases false}]]
:repositories [["clojars" {:url "https://repo.clojars.org" :repositories [["clojars" {:url "https://repo.clojars.org"
:username :env/clojars_username :username :env/clojars_username
:password :env/clojars_password}]] :password :env/clojars_password}]]
@ -16,47 +15,48 @@
:metadata {:doc/format :markdown}} :metadata {:doc/format :markdown}}
:scm {:name "git" :scm {:name "git"
:url "https://github.com/metosin/reitit"} :url "https://github.com/metosin/reitit"}
;; TODO: need to verify that the code actually worked with Java1.8, see #242
;; Ring 1.13.1 drops support for Java 1.8 so lets target 11 ;; Ring 1.13.1 drops support for Java 1.8 so lets target 11
:javac-options ["-Xlint:unchecked" "-target" "11" "-source" "11"] :javac-options ["-Xlint:unchecked" "-target" "11" "-source" "11"]
:managed-dependencies [[metosin/reitit "0.9.2-rc1"] :managed-dependencies [[metosin/reitit "0.9.1"]
[metosin/reitit-core "0.9.2-rc1"] [metosin/reitit-core "0.9.1"]
[metosin/reitit-dev "0.9.2-rc1"] [metosin/reitit-dev "0.9.1"]
[metosin/reitit-spec "0.9.2-rc1"] [metosin/reitit-spec "0.9.1"]
[metosin/reitit-malli "0.9.2-rc1"] [metosin/reitit-malli "0.9.1"]
[metosin/reitit-schema "0.9.2-rc1"] [metosin/reitit-schema "0.9.1"]
[metosin/reitit-ring "0.9.2-rc1"] [metosin/reitit-ring "0.9.1"]
[metosin/reitit-middleware "0.9.2-rc1"] [metosin/reitit-middleware "0.9.1"]
[metosin/reitit-http "0.9.2-rc1"] [metosin/reitit-http "0.9.1"]
[metosin/reitit-interceptors "0.9.2-rc1"] [metosin/reitit-interceptors "0.9.1"]
[metosin/reitit-swagger "0.9.2-rc1"] [metosin/reitit-swagger "0.9.1"]
[fi.metosin/reitit-openapi "0.9.2-rc1"] [fi.metosin/reitit-openapi "0.9.1"]
[metosin/reitit-swagger-ui "0.9.2-rc1"] [metosin/reitit-swagger-ui "0.9.1"]
[metosin/reitit-frontend "0.9.2-rc1"] [metosin/reitit-frontend "0.9.1"]
[metosin/reitit-sieppari "0.9.2-rc1"] [metosin/reitit-sieppari "0.9.1"]
[metosin/reitit-pedestal "0.9.2-rc1"] [metosin/reitit-pedestal "0.9.1"]
[metosin/ring-swagger-ui "5.20.0"] [metosin/ring-swagger-ui "5.20.0"]
[metosin/spec-tools "0.10.7"] [metosin/spec-tools "0.10.7"]
[metosin/schema-tools "0.13.1"] [metosin/schema-tools "0.13.1"]
[metosin/muuntaja "0.6.11"] [metosin/muuntaja "0.6.11"]
[metosin/jsonista "0.3.13"] [metosin/jsonista "0.3.13"]
[metosin/sieppari "0.0.0-alpha13"] [metosin/sieppari "0.0.0-alpha13"]
[metosin/malli "0.19.2"] [metosin/malli "0.18.0"]
;; https://clojureverse.org/t/depending-on-the-right-versions-of-jackson-libraries/5111 ;; https://clojureverse.org/t/depending-on-the-right-versions-of-jackson-libraries/5111
[com.fasterxml.jackson.core/jackson-core "2.20.0"] [com.fasterxml.jackson.core/jackson-core "2.18.2"]
[com.fasterxml.jackson.core/jackson-databind "2.20.0"] [com.fasterxml.jackson.core/jackson-databind "2.18.2"]
[meta-merge "1.0.0"] [meta-merge "1.0.0"]
[fipp "0.6.29" :exclusions [org.clojure/core.rrb-vector]] [fipp "0.6.27" :exclusions [org.clojure/core.rrb-vector]]
;; Deep-diff uses this version, override olders versiom from fipp. ;; Deep-diff uses this version, override olders versiom from fipp.
[org.clojure/core.rrb-vector "0.2.0"] [org.clojure/core.rrb-vector "0.2.0"]
[expound "0.9.0"] [expound "0.9.0"]
[lambdaisland/deep-diff "0.0-47"] [lambdaisland/deep-diff "0.0-47"]
[com.bhauman/spell-spec "0.1.2"] [com.bhauman/spell-spec "0.1.2"]
[mvxcvi/arrangement "2.1.0"] [mvxcvi/arrangement "2.1.0"]
[ring/ring-core "1.15.3"] [ring/ring-core "1.14.1"]
[io.pedestal/pedestal.service "0.6.4" :upgrade false]] [io.pedestal/pedestal.service "0.6.4"]]
:plugins [[jonase/eastwood "1.4.3"] :plugins [[jonase/eastwood "1.4.3"]
;[lein-virgil "0.1.7"] ;[lein-virgil "0.1.7"]
@ -90,8 +90,8 @@
:java-source-paths ["modules/reitit-core/java-src"] :java-source-paths ["modules/reitit-core/java-src"]
:dependencies [[org.clojure/clojure "1.11.4"] :dependencies [[org.clojure/clojure "1.11.4"]
[thheller/shadow-cljs "3.2.1"] [thheller/shadow-cljs "2.28.22"]
[org.clojure/clojurescript "1.12.42"] [org.clojure/clojurescript "1.11.132"]
;; modules dependencies ;; modules dependencies
[metosin/schema-tools "0.13.1"] [metosin/schema-tools "0.13.1"]
@ -99,16 +99,16 @@
[metosin/muuntaja "0.6.11"] [metosin/muuntaja "0.6.11"]
[metosin/sieppari "0.0.0-alpha13"] [metosin/sieppari "0.0.0-alpha13"]
[metosin/jsonista "0.3.13"] [metosin/jsonista "0.3.13"]
[metosin/malli "0.19.2"] [metosin/malli "0.18.0"]
[lambdaisland/deep-diff "0.0-47"] [lambdaisland/deep-diff "0.0-47"]
[meta-merge "1.0.0"] [meta-merge "1.0.0"]
[com.bhauman/spell-spec "0.1.2"] [com.bhauman/spell-spec "0.1.2"]
[expound "0.9.0"] [expound "0.9.0"]
[fipp "0.6.29"] [fipp "0.6.27"]
[orchestra "2021.01.01-1"] [orchestra "2021.01.01-1"]
[ring "1.15.3"] [ring "1.14.1"]
[ikitommi/immutant-web "3.0.0-alpha1"] [ikitommi/immutant-web "3.0.0-alpha1"]
[metosin/ring-http-response "0.9.5"] [metosin/ring-http-response "0.9.5"]
[metosin/ring-swagger-ui "5.20.0"] [metosin/ring-swagger-ui "5.20.0"]
@ -117,17 +117,16 @@
[criterium "0.4.6"] [criterium "0.4.6"]
[org.clojure/test.check "1.1.1"] [org.clojure/test.check "1.1.1"]
[org.clojure/tools.namespace "1.5.0"] [org.clojure/tools.namespace "1.5.0"]
[com.gfredericks/test.chuck "0.2.15"] [com.gfredericks/test.chuck "0.2.14"]
[nubank/matcher-combinators "3.9.2"] [nubank/matcher-combinators "3.9.1"]
;; TODO: adapt to breaking changes in pedestal 0.7 and 0.8 [io.pedestal/pedestal.service "0.6.4"]
[io.pedestal/pedestal.service "0.6.4" :upgrade false]
[org.clojure/core.async "1.8.741"] [org.clojure/core.async "1.7.701"]
[manifold "0.4.3"] [manifold "0.4.3"]
[funcool/promesa "11.0.678"] [funcool/promesa "11.0.678"]
[com.clojure-goes-fast/clj-async-profiler "1.6.2"] [com.clojure-goes-fast/clj-async-profiler "1.6.1"]
[ring-cors "0.1.13"] [ring-cors "0.1.13"]
[com.bhauman/rebel-readline "0.1.5"]]} [com.bhauman/rebel-readline "0.1.5"]]}
@ -136,18 +135,18 @@
"-Xmx4096m" "-Xmx4096m"
"-Dclojure.compiler.direct-linking=true"] "-Dclojure.compiler.direct-linking=true"]
:test-paths ["perf-test/clj"] :test-paths ["perf-test/clj"]
:dependencies [[compojure "1.7.2"] :dependencies [[compojure "1.7.1"]
[ring/ring-defaults "0.7.0"] [ring/ring-defaults "0.6.0"]
[ikitommi/immutant-web "3.0.0-alpha1"] [ikitommi/immutant-web "3.0.0-alpha1"]
[io.pedestal/pedestal.service "0.6.4" :upgrade false] [io.pedestal/pedestal.service "0.6.4"]
[io.pedestal/pedestal.jetty "0.6.4" :upgrade false] [io.pedestal/pedestal.jetty "0.6.4"]
[calfpath "0.8.1"] [calfpath "0.8.1"]
[org.clojure/core.async "1.8.741"] [org.clojure/core.async "1.7.701"]
[manifold "0.4.3"] [manifold "0.4.3"]
[funcool/promesa "11.0.678"] [funcool/promesa "11.0.678"]
[metosin/sieppari] [metosin/sieppari]
[yada "1.2.16"] [yada "1.2.16"]
[aleph "0.9.3"] [aleph "0.8.3"]
[ataraxy "0.4.3"] [ataraxy "0.4.3"]
[bidi "2.1.6"] [bidi "2.1.6"]
[janus "1.3.2"]]} [janus "1.3.2"]]}

View file

@ -140,36 +140,6 @@
(let [m (r/match-by-path r "/none/kikka/abba")] (let [m (r/match-by-path r "/none/kikka/abba")]
(is (= nil (coercion/coerce! m)))))))) (is (= nil (coercion/coerce! m))))))))
(deftest malli-query-parameter-coercion-test
(let [router (fn [coercion]
(r/router ["/test"
{:coercion coercion
:parameters {:query [:map
[:a [:string {:default "a"}]]
[:x {:optional true} [:keyword {:default :a}]]]}}]
{:compile coercion/compile-request-coercers}))]
(testing "default values for :optional query keys do not get added"
(is (= {:query {:a "a"}}
(-> (r/match-by-path (router reitit.coercion.malli/coercion) "/test")
(assoc :query-params {})
(coercion/coerce!)))))
(testing "default values for :optional query keys get added when :malli.transform/add-optional-keys is set"
(is (= {:query {:a "a" :x :a}}
(-> (r/match-by-path (router (reitit.coercion.malli/create
(assoc reitit.coercion.malli/default-options
:default-values {:malli.transform/add-optional-keys true}))) "/test")
(assoc :query-params {})
(coercion/coerce!)))))
(testing "default values can be disabled"
(is (thrown-with-msg?
ExceptionInfo
#"Request coercion failed"
(-> (r/match-by-path (router (reitit.coercion.malli/create
(assoc reitit.coercion.malli/default-options
:default-values false))) "/test")
(assoc :query-params {})
(coercion/coerce!)))))))
(defn match-by-path-and-coerce! [router path] (defn match-by-path-and-coerce! [router path]
(if-let [match (r/match-by-path router path)] (if-let [match (r/match-by-path router path)]
(assoc match :parameters (coercion/coerce! match)))) (assoc match :parameters (coercion/coerce! match))))

View file

@ -13,7 +13,8 @@
(testing "routers handling wildcard paths" (testing "routers handling wildcard paths"
(are [r name] (are [r name]
(testing (str name) (testing "wild"
(testing "simple" (testing "simple"
(let [router (r/router ["/api" ["/ipa" ["/:size" ::beer]]] {:router r})] (let [router (r/router ["/api" ["/ipa" ["/:size" ::beer]]] {:router r})]
(is (= name (r/router-name router))) (is (= name (r/router-name router)))
@ -51,17 +52,10 @@
:path-params nil}) :path-params nil})
(r/match-by-name router ::beer))) (r/match-by-name router ::beer)))
(is (r/partial-match? (r/match-by-name router ::beer))) (is (r/partial-match? (r/match-by-name router ::beer)))
(is (r/partial-match? (r/match-by-name router ::beer {:size nil}))
"nil counts as missing")
(is (thrown-with-msg? (is (thrown-with-msg?
ExceptionInfo ExceptionInfo
#"^missing path-params for route /api/ipa/:size -> \#\{:size\}$" #"^missing path-params for route /api/ipa/:size -> \#\{:size\}$"
(r/match-by-name! router ::beer))) (r/match-by-name! router ::beer))))))
(is (thrown-with-msg?
ExceptionInfo
#"^missing path-params for route /api/ipa/:size -> \#\{:size\}$"
(r/match-by-name! router ::beer {:size nil}))
"nil counts as missing"))))
(testing "decode %-encoded path params" (testing "decode %-encoded path params"
(let [router (r/router [["/one-param-path/:param1" ::one] (let [router (r/router [["/one-param-path/:param1" ::one]

View file

@ -901,11 +901,13 @@
:request {:description "body description" :request {:description "body description"
:content {"application/json" {:schema {:x int?, :y int?} :content {"application/json" {:schema {:x int?, :y int?}
:examples {"1+1" {:value {:x 1, :y 1}} :examples {"1+1" {:value {:x 1, :y 1}}
"1+2" {:value {:x 1, :y 2}}}}}} "1+2" {:value {:x 1, :y 2}}}
:openapi {:example {:x 2, :y 2}}}}}
:responses {200 {:description "success" :responses {200 {:description "success"
:content {"application/json" {:schema {:total int?} :content {"application/json" {:schema {:total int?}
:examples {"2" {:value {:total 2}} :examples {"2" {:value {:total 2}}
"3" {:value {:total 3}}}}}}} "3" {:value {:total 3}}}
:openapi {:example {:total 4}}}}}}
:handler (fn [request] :handler (fn [request]
(let [{:keys [x y]} (-> request :parameters :body)] (let [{:keys [x y]} (-> request :parameters :body)]
{:status 200, :body {:total (+ x y)}}))}}]]] {:status 200, :body {:total (+ x y)}}))}}]]]
@ -923,14 +925,16 @@
:required [:x :y], :required [:x :y],
:additionalProperties false}, :additionalProperties false},
:examples {"1+1" {:value {:x 1, :y 1}} :examples {"1+1" {:value {:x 1, :y 1}}
"1+2" {:value {:x 1, :y 2}}}}}}, "1+2" {:value {:x 1, :y 2}}},
:example {:x 2, :y 2}}}},
:responses {200 {:description "success", :responses {200 {:description "success",
:content {"application/json" {:schema {:type "object", :content {"application/json" {:schema {:type "object",
:properties {:total {:type "integer"}}, :properties {:total {:type "integer"}},
:required [:total], :required [:total],
:additionalProperties false}, :additionalProperties false},
:examples {"2" {:value {:total 2}}, :examples {"2" {:value {:total 2}},
"3" {:value {:total 3}}}}}}}, "3" {:value {:total 3}}},
:example {:total 4}}}}},
:summary "plus with body"}}} :summary "plus with body"}}}
(:paths spec))) (:paths spec)))
(is (nil? (validate spec)))) (is (nil? (validate spec))))

View file

@ -12,9 +12,6 @@
(s/def ::role #{:admin :user}) (s/def ::role #{:admin :user})
(s/def ::roles (s/and (s/coll-of ::role :into #{}) set?)) (s/def ::roles (s/and (s/coll-of ::role :into #{}) set?))
(defmulti my-multi (constantly :default))
(defmethod my-multi :default [x] x)
(deftest route-data-validation-test (deftest route-data-validation-test
(testing "validation is turned off by default" (testing "validation is turned off by default"
(is (r/router? (is (r/router?
@ -88,12 +85,6 @@
(ring/router (ring/router
["/api" {:handler identity ["/api" {:handler identity
:middleware '()}] :middleware '()}]
{:validate rrs/validate}))))
(testing "handler can be a multimethod"
(is (r/router?
(ring/router
["/api" {:get {:handler my-multi}}]
{:validate rrs/validate}))))) {:validate rrs/validate})))))
(deftest coercion-spec-test (deftest coercion-spec-test

View file

@ -114,25 +114,6 @@
(is (= {:status 200, :body [:top :api :ok]} (is (= {:status 200, :body [:top :api :ok]}
(app {:uri "/api/get" :request-method :get})))))) (app {:uri "/api/get" :request-method :get}))))))
(testing "middleware from registry"
(let [router (ring/router
["/api" {:middleware [:mw-foo]}
["/get" {:middleware [[:mw :inner]]
:get handler}]]
{::middleware/registry {:mw mw
:mw-foo #(mw % :foo)}})
app (ring/ring-handler router nil {:middleware [[:mw :top]]})]
(testing "router can be extracted"
(is (= router (ring/get-router app))))
(testing "not found"
(is (= nil (app {:uri "/favicon.ico"}))))
(testing "on match"
(is (= {:status 200, :body [:top :foo :inner :ok]}
(app {:uri "/api/get" :request-method :get}))))))
(testing "named routes" (testing "named routes"
(let [router (ring/router (let [router (ring/router
[["/api" [["/api"
@ -762,7 +743,7 @@
(is (= (redirect "/docs/index.html") response))) (is (= (redirect "/docs/index.html") response)))
(let [response (app (request "/foobar"))] (let [response (app (request "/foobar"))]
(is (= 404 (:status response))))))) (is (= 404 (:status response)))))))
(testing "with additional mime types" (testing "with additional mime types"
(let [app (ring/ring-handler (let [app (ring/ring-handler
(ring/router (ring/router