luposlip / json-schema

Clojure library JSON Schema validation and generation - Draft-07 compatible
Apache License 2.0
72 stars 7 forks source link

Allow relative file resolution in $ref fields #9

Closed jurgiskg closed 3 years ago

jurgiskg commented 3 years ago

Made one more improvement with schema reusability. With this PR relative $refs will be supported - that will allow to keep the schema files cleaner.

Went back and forth on parameter passing to prepare-schema.

(prepare-schema input :classpath-aware "classpath://schemas/")

vs

(prepare-schema input {:classpath-aware? true :default-resolution-scope "classpath://schemas/"})

Decided to go with the latter as more explicit felt clearer, but let me know @luposlip if that should be changed.

jurgiskg commented 3 years ago

@luposlip Could you please review this?:)

luposlip commented 3 years ago

Haven't had the time to dig into the changes, but to me the original interface was simpler, and the classpath://schemas/ URI is more difficult to remember, and seems relevant only because of the particular underlying Java library.

I thought the same with regards to naming the :classpath-aware flag in your original PR, but couldn't immediately think of a better term.

Does your change @jurgiskg have functional differences, or only a more explicit interface?

jurgiskg commented 3 years ago

Yes, there are functional differences - now relative $refs are supported, while previously they did not work. Meaning that if you have a file testSchema.json in directory resources/schemas with this

{
  "$ref": "relativeSchema.json"
}

it will resolve the relativeSchema.json file, which sits in the same resources/schemas directory. Values like ../upperSchema.json, nested/childSchema.json are also supported. Previously, it only worked with an absolute URI in the schema file:

{
  "$ref": "classpath://relativeSchema.json"
}

That allows to keep the schema JSON files cleaner (especially when the schemas have lots of references, then there's no need to prefix all of them with the "classpath://"). I introduced the explicit interface because a default resolution scope must be provided in order for the relative refs to work.

jurgiskg commented 3 years ago

As for the naming - agree, I'm not really happy with :classpath-aware either:( But could not think of a better one and decided to go with it, as local file resolution is not very clearly defined in the JSON Schema drafts and is still heavily dependant on the underlying libraries.