git.iko.soy/typeable/hjsonschema
on db91ca2 help sign in
91 files changed+638−4620
since splitsnapshots
unifiedsplit
.travis.yml+56−67 JSON-Schema-Test-Suite/.travis.yml+2−7 JSON-Schema-Test-Suite/README.md+5−26 JSON-Schema-Test-Suite/bin/jsonschema_suite+27−2 JSON-Schema-Test-Suite/index.js−32 JSON-Schema-Test-Suite/package.json−28 JSON-Schema-Test-Suite/remotes/name.json−11 JSON-Schema-Test-Suite/test-schema.json−28 JSON-Schema-Test-Suite/tests/draft3/optional/format.json+2−2 JSON-Schema-Test-Suite/tests/draft3/ref.json−33 JSON-Schema-Test-Suite/tests/draft3/type.json−15 JSON-Schema-Test-Suite/tests/draft4/additionalItems.json+1−6 JSON-Schema-Test-Suite/tests/draft4/items.json−32 JSON-Schema-Test-Suite/tests/draft4/maximum.json−5 JSON-Schema-Test-Suite/tests/draft4/minimum.json−5 JSON-Schema-Test-Suite/tests/draft4/optional/ecmascript-regex.json−13 JSON-Schema-Test-Suite/tests/draft4/optional/format.json+2−2 JSON-Schema-Test-Suite/tests/draft4/ref.json−139 JSON-Schema-Test-Suite/tests/draft4/refRemote.json+3−100 JSON-Schema-Test-Suite/tests/draft4/required.json−5 JSON-Schema-Test-Suite/tests/draft4/type.json−15 JSON-Schema-Test-Suite/tests/draft6/additionalItems.json−87 JSON-Schema-Test-Suite/tests/draft6/additionalProperties.json−88 JSON-Schema-Test-Suite/tests/draft6/allOf.json−145 JSON-Schema-Test-Suite/tests/draft6/anyOf.json−101 JSON-Schema-Test-Suite/tests/draft6/boolean_schema.json−104 JSON-Schema-Test-Suite/tests/draft6/const.json−65 JSON-Schema-Test-Suite/tests/draft6/contains.json−95 JSON-Schema-Test-Suite/tests/draft6/default.json−49 JSON-Schema-Test-Suite/tests/draft6/definitions.json−32 JSON-Schema-Test-Suite/tests/draft6/dependencies.json−162 JSON-Schema-Test-Suite/tests/draft6/enum.json−72 JSON-Schema-Test-Suite/tests/draft6/exclusiveMaximum.json−30 JSON-Schema-Test-Suite/tests/draft6/exclusiveMinimum.json−30 JSON-Schema-Test-Suite/tests/draft6/items.json−133 JSON-Schema-Test-Suite/tests/draft6/maxItems.json−28 JSON-Schema-Test-Suite/tests/draft6/maxLength.json−33 JSON-Schema-Test-Suite/tests/draft6/maxProperties.json−28 JSON-Schema-Test-Suite/tests/draft6/maximum.json−28 JSON-Schema-Test-Suite/tests/draft6/minItems.json−28 JSON-Schema-Test-Suite/tests/draft6/minLength.json−33 JSON-Schema-Test-Suite/tests/draft6/minProperties.json−28 JSON-Schema-Test-Suite/tests/draft6/minimum.json−28 JSON-Schema-Test-Suite/tests/draft6/multipleOf.json−60 JSON-Schema-Test-Suite/tests/draft6/not.json−117 JSON-Schema-Test-Suite/tests/draft6/oneOf.json−112 JSON-Schema-Test-Suite/tests/draft6/optional/bignum.json−105 JSON-Schema-Test-Suite/tests/draft6/optional/ecmascript-regex.json−13 JSON-Schema-Test-Suite/tests/draft6/optional/format.json−148 JSON-Schema-Test-Suite/tests/draft6/optional/zeroTerminatedFloats.json−15 JSON-Schema-Test-Suite/tests/draft6/pattern.json−34 JSON-Schema-Test-Suite/tests/draft6/patternProperties.json−141 JSON-Schema-Test-Suite/tests/draft6/properties.json−123 JSON-Schema-Test-Suite/tests/draft6/propertyNames.json−68 JSON-Schema-Test-Suite/tests/draft6/ref.json−332 JSON-Schema-Test-Suite/tests/draft6/refRemote.json−171 JSON-Schema-Test-Suite/tests/draft6/required.json−60 JSON-Schema-Test-Suite/tests/draft6/type.json−345 JSON-Schema-Test-Suite/tests/draft6/uniqueItems.json−79 README.md+50−10 changelog.md−54 examples/AlternateSchema.hs+57−86 examples/Simple.hs+5−4 examples/TwoStep.hs+4−3 hjsonschema.cabal+29−25 logo.jpg shell.nix+3−5 src/Import.hs+8−15 src/JSONSchema/Draft4.hs+30−21 src/JSONSchema/Draft4/Failure.hs+2−1 src/JSONSchema/Draft4/Schema.hs+7−6 src/JSONSchema/Draft4/Spec.hs+39−61 src/JSONSchema/Fetch.hs+65−46 src/JSONSchema/Types.hs+1 src/JSONSchema/Validator/Draft4.hs+19−19 src/JSONSchema/Validator/Draft4/Any.hs+59−217 src/JSONSchema/Validator/Draft4/Array.hs+7−8 src/JSONSchema/Validator/Draft4/Number.hs+2−1 src/JSONSchema/Validator/Draft4/Object.hs+10−6 src/JSONSchema/Validator/Draft4/Object/Properties.hs+6−6 src/JSONSchema/Validator/Draft4/String.hs+3−2 src/JSONSchema/Validator/Reference.hs+36−28 src/JSONSchema/Validator/Types.hs+1 src/JSONSchema/Validator/Utils.hs+27−11 stack.yaml−2 test/Local.hs+14−10 test/Local/Failure.hs+7−6 test/Local/Reference.hs+13−12 test/Local/Validation.hs+6−5 test/Remote.hs+11−9 test/Shared.hs+19−18
.travis.yml+56−67
@@ -1,95 +1,84 @@
1−# This Travis job script has been generated by a script via
2−#
3−# make_travis_yml_2.hs 'hjsonschema.cabal'
4−#
5−# For more information, see https://github.com/hvr/multi-ghc-travis
1+# Generated by: https://github.com/hvr/multi-ghc-travis
62#
3+# Removed `cabal check` because I don't want a description field.
4+
75language: c
86sudo: false
97
10−git:
11− submodules: false # whether to recursively clone submodules
12−
138cache:
149 directories:
10+ - $HOME/.cabsnap
1511 - $HOME/.cabal/packages
16− - $HOME/.cabal/store
1712
1813before_cache:
1914 - rm -fv $HOME/.cabal/packages/hackage.haskell.org/build-reports.log
20− # remove files that are regenerated by 'cabal update'
21− - rm -fv $HOME/.cabal/packages/hackage.haskell.org/00-index.*
22− - rm -fv $HOME/.cabal/packages/hackage.haskell.org/*.json
23− - rm -fv $HOME/.cabal/packages/hackage.haskell.org/01-index.cache
24− - rm -fv $HOME/.cabal/packages/hackage.haskell.org/01-index.tar
25− - rm -fv $HOME/.cabal/packages/hackage.haskell.org/01-index.tar.idx
15+ - rm -fv $HOME/.cabal/packages/hackage.haskell.org/00-index.tar
2616
2717matrix:
2818 include:
29− - compiler: "ghc-8.0.2"
30− # env: TEST=--disable-tests BENCH=--disable-benchmarks
31− addons: {apt: {packages: [ghc-ppa-tools,cabal-install-head,ghc-8.0.2], sources: [hvr-ghc]}}
32− - compiler: "ghc-8.2.2"
33− # env: TEST=--disable-tests BENCH=--disable-benchmarks
34− addons: {apt: {packages: [ghc-ppa-tools,cabal-install-head,ghc-8.2.2], sources: [hvr-ghc]}}
35− - compiler: "ghc-8.4.1"
36− # env: TEST=--disable-tests BENCH=--disable-benchmarks
37− addons: {apt: {packages: [ghc-ppa-tools,cabal-install-head,ghc-8.4.1], sources: [hvr-ghc]}}
19+ - env: CABALVER=1.18 GHCVER=7.8.4
20+ compiler: ": #GHC 7.8.4"
21+ addons: {apt: {packages: [cabal-install-1.18,ghc-7.8.4], sources: [hvr-ghc]}}
22+ - env: CABALVER=1.22 GHCVER=7.10.2
23+ compiler: ": #GHC 7.10.2"
24+ addons: {apt: {packages: [cabal-install-1.22,ghc-7.10.2], sources: [hvr-ghc]}}
25+ - env: CABALVER=1.24 GHCVER=8.0.1
26+ compiler: ": #GHC 8.0.1"
27+ addons: {apt: {packages: [cabal-install-1.24,ghc-8.0.1], sources: [hvr-ghc]}}
3828
3929before_install:
40− - HC=${CC}
41− - HCPKG=${HC/ghc/ghc-pkg}
4230 - unset CC
43− - PATH=/opt/ghc/bin:/opt/ghc-ppa-tools/bin:$PATH
44− - PKGNAME='hjsonschema'
31+ - export PATH=/opt/ghc/$GHCVER/bin:/opt/cabal/$CABALVER/bin:$PATH
4532
4633install:
4734 - cabal --version
48− - echo "$(${HC} --version) [$(${HC} --print-project-git-commit-id 2> /dev/null || echo '?')]"
49− - BENCH=${BENCH---enable-benchmarks}
50− - TEST=${TEST---enable-tests}
51− - HADDOCK=${HADDOCK-true}
52− - INSTALLED=${INSTALLED-true}
35+ - echo "$(ghc --version) [$(ghc --print-project-git-commit-id 2> /dev/null || echo '?')]"
36+ - if [ -f $HOME/.cabal/packages/hackage.haskell.org/00-index.tar.gz ];
37+ then
38+ zcat $HOME/.cabal/packages/hackage.haskell.org/00-index.tar.gz >
39+ $HOME/.cabal/packages/hackage.haskell.org/00-index.tar;
40+ fi
5341 - travis_retry cabal update -v
54− - sed -i.bak 's/^jobs:/-- jobs:/' ${HOME}/.cabal/config
55− - rm -fv cabal.project.local
56− - "echo 'packages: .' > cabal.project"
57− - rm -f cabal.project.freeze
58− - cabal new-build -w ${HC} ${TEST} ${BENCH} --dep -j2 all
59− - cabal new-build -w ${HC} --disable-tests --disable-benchmarks --dep -j2 all
42+ - sed -i 's/^jobs:/-- jobs:/' ${HOME}/.cabal/config
43+ - cabal install --only-dependencies --enable-tests --enable-benchmarks --dry -v > installplan.txt
44+ - sed -i -e '1,/^Resolving /d' installplan.txt; cat installplan.txt
45+
46+# check whether current requested install-plan matches cached package-db snapshot
47+ - if diff -u installplan.txt $HOME/.cabsnap/installplan.txt;
48+ then
49+ echo "cabal build-cache HIT";
50+ rm -rfv .ghc;
51+ cp -a $HOME/.cabsnap/ghc $HOME/.ghc;
52+ cp -a $HOME/.cabsnap/lib $HOME/.cabsnap/share $HOME/.cabsnap/bin $HOME/.cabal/;
53+ else
54+ echo "cabal build-cache MISS";
55+ rm -rf $HOME/.cabsnap;
56+ mkdir -p $HOME/.ghc $HOME/.cabal/lib $HOME/.cabal/share $HOME/.cabal/bin;
57+ cabal install --only-dependencies --enable-tests --enable-benchmarks;
58+ fi
59+
60+# snapshot package-db on cache miss
61+ - if [ ! -d $HOME/.cabsnap ];
62+ then
63+ echo "snapshotting package-db to build-cache";
64+ mkdir $HOME/.cabsnap;
65+ cp -a $HOME/.ghc $HOME/.cabsnap/ghc;
66+ cp -a $HOME/.cabal/lib $HOME/.cabal/share $HOME/.cabal/bin installplan.txt $HOME/.cabsnap/;
67+ fi
6068
6169# Here starts the actual work to be performed for the package under test;
6270# any command which exits with a non-zero exit code causes the build to fail.
6371script:
6472 - if [ -f configure.ac ]; then autoreconf -i; fi
65− - rm -rf .ghc.environment.* dist/
66− - cabal sdist # test that a source-distribution can be generated
67− - cd dist/
68− - SRCTAR=(${PKGNAME}-*.tar.gz)
69− - SRC_BASENAME="${SRCTAR/%.tar.gz}"
70− - tar -xvf "./$SRC_BASENAME.tar.gz"
71− - cd "$SRC_BASENAME/"
72−## from here on, CWD is inside the extracted source-tarball
73− - rm -fv cabal.project.local
74− - "echo 'packages: .' > cabal.project"
75− # this builds all libraries and executables (without tests/benchmarks)
76− - rm -f cabal.project.freeze
77− - cabal new-build -w ${HC} --disable-tests --disable-benchmarks all
78− # this builds all libraries and executables (including tests/benchmarks)
79− # - rm -rf ./dist-newstyle
80−
81− # Build with installed constraints for packages in global-db
82− - if $INSTALLED; then
83− echo cabal new-build -w ${HC} --disable-tests --disable-benchmarks $(${HCPKG} list --global --simple-output --names-only | sed 's/\([a-zA-Z0-9-]\{1,\}\) */--constraint="\1 installed" /g') all | sh;
84− else echo "Not building with installed constraints"; fi
85−
86− # build & run tests, build benchmarks
87− - cabal new-build -w ${HC} ${TEST} ${BENCH} all
88− - if [ "x$TEST" = "x--enable-tests" ]; then cabal new-test -w ${HC} ${TEST} all; fi
73+ - cabal configure --enable-tests --enable-benchmarks -v2 # -v2 provides useful information for debugging
74+ - cabal build # this builds all libraries and executables (including tests/benchmarks)
75+ - cabal test
76+ - cabal sdist # tests that a source-distribution can be generated
8977
90− # haddock
91− - rm -rf ./dist-newstyle
92− - if $HADDOCK; then cabal new-haddock -w ${HC} --disable-tests --disable-benchmarks all; else echo "Skipping haddock generation";fi
78+# Check that the resulting source distribution can be built & installed.
79+# If there are no other `.tar.gz` files in `dist`, this can be even simpler:
80+# `cabal install --force-reinstalls dist/*-*.tar.gz`
81+ - SRC_TGZ=$(cabal info . | awk '{print $2;exit}').tar.gz &&
82+ (cd dist && cabal install --force-reinstalls "$SRC_TGZ")
9383
94−# REGENDATA ["hjsonschema.cabal"]
9584# EOF
JSON-Schema-Test-Suite/.travis.yml+2−7
@@ -1,9 +1,4 @@
11language: python
22python: "2.7"
3−node_js: "6"
4−install:
5− - pip install tox
6− - npm install
7−script:
8− - tox
9− - npm test
3+install: pip install tox
4+script: tox
JSON-Schema-Test-Suite/README.md+5−26
@@ -1,4 +1,4 @@
1−JSON Schema Test Suite [![Build Status](https://travis-ci.org/json-schema-org/JSON-Schema-Test-Suite.svg?branch=master)](https://travis-ci.org/json-schema-org/JSON-Schema-Test-Suite)
1+JSON Schema Test Suite [![Build Status](https://travis-ci.org/json-schema/JSON-Schema-Test-Suite.png?branch=develop)](https://travis-ci.org/json-schema/JSON-Schema-Test-Suite)
22======================
33
44This repository contains a set of JSON objects that implementors of JSON Schema
@@ -64,18 +64,10 @@ This suite is being used by:
6464
6565* [jsck](https://github.com/pandastrike/jsck)
6666
67−### C++ ###
68−
69−* [Modern C++ JSON schema validator](https://github.com/pboettch/json-schema-validator)
70−
7167### Dart ###
7268
7369* [json_schema](https://github.com/patefacio/json_schema)
7470
75−### Elixir ###
76−
77−* [ex_json_schema](https://github.com/jonasschmidt/ex_json_schema)
78−
7971### Erlang ###
8072
8173* [jesse](https://github.com/klarna/jesse)
@@ -92,9 +84,7 @@ This suite is being used by:
9284
9385### Java ###
9486
95−* [json-schema-validator](https://github.com/daveclayton/json-schema-validator)
96−* [everit-org/json-schema](https://github.com/everit-org/json-schema)
97−* [networknt/json-schema-validator](https://github.com/networknt/json-schema-validator)
87+* [json-schema-validator](https://github.com/fge/json-schema-validator)
9888
9989### JavaScript ###
10090
@@ -112,25 +102,22 @@ This suite is being used by:
112102* [z-schema](https://github.com/zaggino/z-schema)
113103* [jsen](https://github.com/bugventure/jsen)
114104* [ajv](https://github.com/epoberezkin/ajv)
115−* [djv](https://github.com/korzio/djv)
116105
117106### Node.js ###
118107
119108The JSON Schema Test Suite is also available as an
120109[npm](https://www.npmjs.com/package/json-schema-test-suite) package.
121−Node-specific support is maintained on the [node branch](https://github.com/json-schema-org/JSON-Schema-Test-Suite/tree/node).
122−See [NODE-README.md](https://github.com/json-schema-org/JSON-Schema-Test-Suite/blob/node/NODE-README.md)
110+Node-specific support is maintained on the [node branch](https://github.com/json-schema/JSON-Schema-Test-Suite/tree/node).
111+See [NODE-README.md](https://github.com/json-schema/JSON-Schema-Test-Suite/blob/node/NODE-README.md)
123112for more information.
124113
125114### .NET ###
126115
127116* [Newtonsoft.Json.Schema](https://github.com/JamesNK/Newtonsoft.Json.Schema)
128−* [Manatee.Json](https://github.com/gregsdennis/Manatee.Json)
129117
130118### PHP ###
131119
132120* [json-schema](https://github.com/justinrainbow/json-schema)
133−* [json-guard](https://github.com/thephpleague/json-guard)
134121
135122### Python ###
136123
@@ -148,14 +135,6 @@ for more information.
148135
149136* [JSONSchema](https://github.com/kylef/JSONSchema.swift)
150137
151−### Clojure ###
152−
153−* [json-schema](https://github.com/tatut/json-schema)
154−
155−### PostgreSQL ###
156−
157−* [postgres-json-schema](https://github.com/gavinwahl/postgres-json-schema)
158−
159138If you use it as well, please fork and send a pull request adding yourself to
160139the list :).
161140
@@ -165,5 +144,5 @@ Contributing
165144If you see something missing or incorrect, a pull request is most welcome!
166145
167146There are some sanity checks in place for testing the test suite. You can run
168−them with `bin/jsonschema_suite check && npm test` or `tox && npm test`. They will be run automatically by
147+them with `bin/jsonschema_suite check` or `tox`. They will be run automatically by
169148[Travis CI](https://travis-ci.org/) as well.
JSON-Schema-Test-Suite/bin/jsonschema_suite+27−2
@@ -52,8 +52,33 @@ REMOTES = {
5252}
5353REMOTES_DIR = os.path.join(ROOT_DIR, "remotes")
5454
55−with open(os.path.join(ROOT_DIR, "test-schema.json")) as schema:
56− TESTSUITE_SCHEMA = json.load(schema)
55+TESTSUITE_SCHEMA = {
56+ "$schema": "http://json-schema.org/draft-03/schema#",
57+ "type": "array",
58+ "items": {
59+ "type": "object",
60+ "properties": {
61+ "description": {"type": "string", "required": True},
62+ "schema": {"required": True},
63+ "tests": {
64+ "type": "array",
65+ "items": {
66+ "type": "object",
67+ "properties": {
68+ "description": {"type": "string", "required": True},
69+ "data": {"required": True},
70+ "valid": {"type": "boolean", "required": True}
71+ },
72+ "additionalProperties": False
73+ },
74+ "minItems": 1
75+ }
76+ },
77+ "additionalProperties": False,
78+ "minItems": 1
79+ }
80+}
81+
5782
5883def files(paths):
5984 for path in paths:
JSON-Schema-Test-Suite/index.jsdeleted−32
@@ -1,32 +0,0 @@
1−'use strict';
2−
3−var Ajv = require('ajv');
4−var jsonSchemaTest = require('json-schema-test');
5−var assert = require('assert');
6−
7−var refs = {
8− 'http://localhost:1234/integer.json': require('./remotes/integer.json'),
9− 'http://localhost:1234/subSchemas.json': require('./remotes/subSchemas.json'),
10− 'http://localhost:1234/folder/folderInteger.json': require('./remotes/folder/folderInteger.json'),
11− 'http://localhost:1234/name.json': require('./remotes/name.json')
12−};
13−
14−runTest(4);
15−runTest(6);
16−
17−function runTest(draft) {
18− var opts = {};
19− if (draft == 4) opts.meta = false;
20− var ajv = new Ajv(opts);
21− ajv.addMetaSchema(require('ajv/lib/refs/json-schema-draft-04.json'));
22− if (draft == 4) ajv._opts.defaultMeta = 'http://json-schema.org/draft-04/schema#';
23− for (var uri in refs) ajv.addSchema(refs[uri], uri);
24−
25− jsonSchemaTest(ajv, {
26− description: 'Test suite draft-0' + draft,
27− suites: {tests: './tests/draft' + draft + '/{**/,}*.json'},
28− skip: draft == 4 ? ['optional/zeroTerminatedFloats'] : [],
29− cwd: __dirname,
30− hideFolder: 'tests/'
31− });
32−}
JSON-Schema-Test-Suite/package.jsondeleted−28
@@ -1,28 +0,0 @@
1−{
2− "name": "json-schema-test-suite",
3− "version": "0.1.0",
4− "description": "A language agnostic test suite for the JSON Schema specifications",
5− "main": "index.js",
6− "scripts": {
7− "test": "mocha index.js -R spec"
8− },
9− "repository": {
10− "type": "git",
11− "url": "git+https://github.com/json-schema-org/JSON-Schema-Test-Suite.git"
12− },
13− "keywords": [
14− "json-schema",
15− "tests"
16− ],
17− "author": "http://json-schema.org",
18− "license": "MIT",
19− "bugs": {
20− "url": "https://github.com/json-schema-org/JSON-Schema-Test-Suite/issues"
21− },
22− "homepage": "https://github.com/json-schema-org/JSON-Schema-Test-Suite#readme",
23− "devDependencies": {
24− "ajv": "^5.0.4-beta.0",
25− "json-schema-test": "^1.3.0",
26− "mocha": "^3.2.0"
27− }
28−}
JSON-Schema-Test-Suite/remotes/name.jsondeleted−11
@@ -1,11 +0,0 @@
1−{
2− "definitions": {
3− "orNull": {
4− "anyOf": [
5− {"type": "null"},
6− {"$ref": "#"}
7− ]
8− }
9− },
10− "type": "string"
11−}
JSON-Schema-Test-Suite/test-schema.jsondeleted−28
@@ -1,28 +0,0 @@
1−{
2− "$schema": "http://json-schema.org/draft-04/schema#",
3− "type": "array",
4− "items": {
5− "type": "object",
6− "required": ["description", "schema", "tests"],
7− "properties": {
8− "description": {"type": "string"},
9− "schema": {},
10− "tests": {
11− "type": "array",
12− "items": {
13− "type": "object",
14− "required": ["description", "data", "valid"],
15− "properties": {
16− "description": {"type": "string"},
17− "data": {},
18− "valid": {"type": "boolean"}
19− },
20− "additionalProperties": false
21− },
22− "minItems": 1
23− }
24− },
25− "additionalProperties": false,
26− "minItems": 1
27− }
28−}
JSON-Schema-Test-Suite/tests/draft3/optional/format.json+2−2
@@ -78,9 +78,9 @@
7878 "valid": true
7979 },
8080 {
81− "description": "an invalid protocol-relative URI Reference",
81+ "description": "a valid protocol-relative URI",
8282 "data": "//foo.bar/?baz=qux#quux",
83− "valid": false
83+ "valid": true
8484 },
8585 {
8686 "description": "an invalid URI",
JSON-Schema-Test-Suite/tests/draft3/ref.json−33
@@ -140,39 +140,6 @@
140140 }
141141 ]
142142 },
143− {
144− "description": "ref overrides any sibling keywords",
145− "schema": {
146− "definitions": {
147− "reffed": {
148− "type": "array"
149− }
150− },
151− "properties": {
152− "foo": {
153− "$ref": "#/definitions/reffed",
154− "maxItems": 2
155− }
156− }
157− },
158− "tests": [
159− {
160− "description": "remote ref valid",
161− "data": { "foo": [] },
162− "valid": true
163− },
164− {
165− "description": "remote ref valid, maxItems ignored",
166− "data": { "foo": [ 1, 2, 3] },
167− "valid": true
168− },
169− {
170− "description": "ref invalid",
171− "data": { "foo": "string" },
172− "valid": false
173− }
174− ]
175− },
176143 {
177144 "description": "remote ref, containing refs itself",
178145 "schema": {"$ref": "http://json-schema.org/draft-03/schema#"},
JSON-Schema-Test-Suite/tests/draft3/type.json−15
@@ -18,11 +18,6 @@
1818 "data": "foo",
1919 "valid": false
2020 },
21− {
22− "description": "a string is still not an integer, even if it looks like one",
23− "data": "1",
24− "valid": false
25− },
2621 {
2722 "description": "an object is not an integer",
2823 "data": {},
@@ -64,11 +59,6 @@
6459 "data": "foo",
6560 "valid": false
6661 },
67− {
68− "description": "a string is still not a number, even if it looks like one",
69− "data": "1",
70− "valid": false
71− },
7262 {
7363 "description": "an object is not a number",
7464 "data": {},
@@ -110,11 +100,6 @@
110100 "data": "foo",
111101 "valid": true
112102 },
113− {
114− "description": "a string is still a string, even if it looks like a number",
115− "data": "1",
116− "valid": true
117− },
118103 {
119104 "description": "an object is not a string",
120105 "data": {},
JSON-Schema-Test-Suite/tests/draft4/additionalItems.json+1−6
@@ -40,12 +40,7 @@
4040 },
4141 "tests": [
4242 {
43− "description": "fewer number of items present",
44− "data": [ 1, 2 ],
45− "valid": true
46− },
47− {
48− "description": "equal number of items present",
43+ "description": "no additional items present",
4944 "data": [ 1, 2, 3 ],
5045 "valid": true
5146 },
JSON-Schema-Test-Suite/tests/draft4/items.json−32
@@ -19,14 +19,6 @@
1919 "description": "ignores non-arrays",
2020 "data": {"foo" : "bar"},
2121 "valid": true
22− },
23− {
24− "description": "JavaScript pseudo-array is valid",
25− "data": {
26− "0": "invalid",
27− "length": 1
28− },
29− "valid": true
3022 }
3123 ]
3224 },
@@ -48,30 +40,6 @@
4840 "description": "wrong types",
4941 "data": [ "foo", 1 ],
5042 "valid": false
51− },
52− {
53− "description": "incomplete array of items",
54− "data": [ 1 ],
55− "valid": true
56− },
57− {
58− "description": "array with additional items",
59− "data": [ 1, "foo", true ],
60− "valid": true
61− },
62− {
63− "description": "empty array",
64− "data": [ ],
65− "valid": true
66− },
67− {
68− "description": "JavaScript pseudo-array is valid",
69− "data": {
70− "0": "invalid",
71− "1": "valid",
72− "length": 2
73− },
74− "valid": true
7543 }
7644 ]
7745 }
JSON-Schema-Test-Suite/tests/draft4/maximum.json−5
@@ -8,11 +8,6 @@
88 "data": 2.6,
99 "valid": true
1010 },
11− {
12− "description": "boundary point is valid",
13− "data": 3.0,
14− "valid": true
15− },
1611 {
1712 "description": "above the maximum is invalid",
1813 "data": 3.5,
JSON-Schema-Test-Suite/tests/draft4/minimum.json−5
@@ -8,11 +8,6 @@
88 "data": 2.6,
99 "valid": true
1010 },
11− {
12− "description": "boundary point is valid",
13− "data": 1.1,
14− "valid": true
15− },
1611 {
1712 "description": "below the minimum is invalid",
1813 "data": 0.6,
JSON-Schema-Test-Suite/tests/draft4/optional/ecmascript-regex.jsondeleted−13
@@ -1,13 +0,0 @@
1−[
2− {
3− "description": "ECMA 262 regex non-compliance",
4− "schema": { "format": "regex" },
5− "tests": [
6− {
7− "description": "ECMA 262 has no support for \\Z anchor from .NET",
8− "data": "^\\S(|(.|\\n)*\\S)\\Z",
9− "valid": false
10− }
11− ]
12− }
13−]
JSON-Schema-Test-Suite/tests/draft4/optional/format.json+2−2
@@ -30,9 +30,9 @@
3030 "valid": true
3131 },
3232 {
33− "description": "an invalid protocol-relative URI Reference",
33+ "description": "a valid protocol-relative URI",
3434 "data": "//foo.bar/?baz=qux#quux",
35− "valid": false
35+ "valid": true
3636 },
3737 {
3838 "description": "an invalid URI",
JSON-Schema-Test-Suite/tests/draft4/ref.json−139
@@ -140,39 +140,6 @@
140140 }
141141 ]
142142 },
143− {
144− "description": "ref overrides any sibling keywords",
145− "schema": {
146− "definitions": {
147− "reffed": {
148− "type": "array"
149− }
150− },
151− "properties": {
152− "foo": {
153− "$ref": "#/definitions/reffed",
154− "maxItems": 2
155− }
156− }
157− },
158− "tests": [
159− {
160− "description": "ref valid",
161− "data": { "foo": [] },
162− "valid": true
163− },
164− {
165− "description": "ref valid, maxItems ignored",
166− "data": { "foo": [ 1, 2, 3] },
167− "valid": true
168− },
169− {
170− "description": "ref invalid",
171− "data": { "foo": "string" },
172− "valid": false
173− }
174− ]
175− },
176143 {
177144 "description": "remote ref, containing refs itself",
178145 "schema": {"$ref": "http://json-schema.org/draft-04/schema#"},
@@ -188,111 +155,5 @@
188155 "valid": false
189156 }
190157 ]
191− },
192− {
193− "description": "property named $ref that is not a reference",
194− "schema": {
195− "properties": {
196− "$ref": {"type": "string"}
197− }
198− },
199− "tests": [
200− {
201− "description": "property named $ref valid",
202− "data": {"$ref": "a"},
203− "valid": true
204− },
205− {
206− "description": "property named $ref invalid",
207− "data": {"$ref": 2},
208− "valid": false
209− }
210− ]
211− },
212− {
213− "description": "Recursive references between schemas",
214− "schema": {
215− "description": "tree of nodes",
216− "type": "object",
217− "properties": {
218− "meta": {"type": "string"},
219− "nodes": {
220− "type": "array",
221− "items": {"$ref": "#/definitions/node"}
222− }
223− },
224− "required": ["meta", "nodes"],
225− "definitions": {
226− "node": {
227− "description": "node",
228− "type": "object",
229− "properties": {
230− "value": {"type": "number"},
231− "subtree": {"$ref": "#"}
232− },
233− "required": ["value"]
234− }
235− }
236− },
237− "tests": [
238− {
239− "description": "valid tree",
240− "data": {
241− "meta": "root",
242− "nodes": [
243− {
244− "value": 1,
245− "subtree": {
246− "meta": "child",
247− "nodes": [
248− {"value": 1.1},
249− {"value": 1.2}
250− ]
251− }
252− },
253− {
254− "value": 2,
255− "subtree": {
256− "meta": "child",
257− "nodes": [
258− {"value": 2.1},
259− {"value": 2.2}
260− ]
261− }
262− }
263− ]
264− },
265− "valid": true
266− },
267− {
268− "description": "invalid tree",
269− "data": {
270− "meta": "root",
271− "nodes": [
272− {
273− "value": 1,
274− "subtree": {
275− "meta": "child",
276− "nodes": [
277− {"value": "string is invalid"},
278− {"value": 1.2}
279− ]
280− }
281− },
282− {
283− "value": 2,
284− "subtree": {
285− "meta": "child",
286− "nodes": [
287− {"value": 2.1},
288− {"value": 2.2}
289− ]
290− }
291− }
292− ]
293− },
294− "valid": false
295− }
296− ]
297158 }
298159]
JSON-Schema-Test-Suite/tests/draft4/refRemote.json+3−100
@@ -50,7 +50,7 @@
5050 ]
5151 },
5252 {
53− "description": "base URI change",
53+ "description": "change resolution scope",
5454 "schema": {
5555 "id": "http://localhost:1234/",
5656 "items": {
@@ -60,112 +60,15 @@
6060 },
6161 "tests": [
6262 {
63− "description": "base URI change ref valid",
63+ "description": "changed scope ref valid",
6464 "data": [[1]],
6565 "valid": true
6666 },
6767 {
68− "description": "base URI change ref invalid",
68+ "description": "changed scope ref invalid",
6969 "data": [["a"]],
7070 "valid": false
7171 }
7272 ]
73− },
74− {
75− "description": "base URI change - change folder",
76− "schema": {
77− "id": "http://localhost:1234/scope_change_defs1.json",
78− "type" : "object",
79− "properties": {
80− "list": {"$ref": "#/definitions/baz"}
81− },
82− "definitions": {
83− "baz": {
84− "id": "folder/",
85− "type": "array",
86− "items": {"$ref": "folderInteger.json"}
87− }
88− }
89− },
90− "tests": [
91− {
92− "description": "number is valid",
93− "data": {"list": [1]},
94− "valid": true
95− },
96− {
97− "description": "string is invalid",
98− "data": {"list": ["a"]},
99− "valid": false
100− }
101− ]
102− },
103− {
104− "description": "base URI change - change folder in subschema",
105− "schema": {
106− "id": "http://localhost:1234/scope_change_defs2.json",
107− "type" : "object",
108− "properties": {
109− "list": {"$ref": "#/definitions/baz/definitions/bar"}
110− },
111− "definitions": {
112− "baz": {
113− "id": "folder/",
114− "definitions": {
115− "bar": {
116− "type": "array",
117− "items": {"$ref": "folderInteger.json"}
118− }
119− }
120− }
121− }
122− },
123− "tests": [
124− {
125− "description": "number is valid",
126− "data": {"list": [1]},
127− "valid": true
128− },
129− {
130− "description": "string is invalid",
131− "data": {"list": ["a"]},
132− "valid": false
133− }
134− ]
135− },
136− {
137− "description": "root ref in remote ref",
138− "schema": {
139− "id": "http://localhost:1234/object",
140− "type": "object",
141− "properties": {
142− "name": {"$ref": "name.json#/definitions/orNull"}
143− }
144− },
145− "tests": [
146− {
147− "description": "string is valid",
148− "data": {
149− "name": "foo"
150− },
151− "valid": true
152− },
153− {
154− "description": "null is valid",
155− "data": {
156− "name": null
157− },
158− "valid": true
159− },
160− {
161− "description": "object is invalid",
162− "data": {
163− "name": {
164− "name": null
165− }
166− },
167− "valid": false
168− }
169− ]
17073 }
17174]
JSON-Schema-Test-Suite/tests/draft4/required.json−5
@@ -18,11 +18,6 @@
1818 "description": "non-present required property is invalid",
1919 "data": {"bar": 1},
2020 "valid": false
21− },
22− {
23− "description": "ignores non-objects",
24− "data": 12,
25− "valid": true
2621 }
2722 ]
2823 },
JSON-Schema-Test-Suite/tests/draft4/type.json−15
@@ -18,11 +18,6 @@
1818 "data": "foo",
1919 "valid": false
2020 },
21− {
22− "description": "a string is still not an integer, even if it looks like one",
23− "data": "1",
24− "valid": false
25− },
2621 {
2722 "description": "an object is not an integer",
2823 "data": {},
@@ -64,11 +59,6 @@
6459 "data": "foo",
6560 "valid": false
6661 },
67− {
68− "description": "a string is still not a number, even if it looks like one",
69− "data": "1",
70− "valid": false
71− },
7262 {
7363 "description": "an object is not a number",
7464 "data": {},
@@ -110,11 +100,6 @@
110100 "data": "foo",
111101 "valid": true
112102 },
113− {
114− "description": "a string is still a string, even if it looks like a number",
115− "data": "1",
116− "valid": true
117− },
118103 {
119104 "description": "an object is not a string",
120105 "data": {},
JSON-Schema-Test-Suite/tests/draft6/additionalItems.jsondeleted−87
@@ -1,87 +0,0 @@
1−[
2− {
3− "description": "additionalItems as schema",
4− "schema": {
5− "items": [{}],
6− "additionalItems": {"type": "integer"}
7− },
8− "tests": [
9− {
10− "description": "additional items match schema",
11− "data": [ null, 2, 3, 4 ],
12− "valid": true
13− },
14− {
15− "description": "additional items do not match schema",
16− "data": [ null, 2, 3, "foo" ],
17− "valid": false
18− }
19− ]
20− },
21− {
22− "description": "items is schema, no additionalItems",
23− "schema": {
24− "items": {},
25− "additionalItems": false
26− },
27− "tests": [
28− {
29− "description": "all items match schema",
30− "data": [ 1, 2, 3, 4, 5 ],
31− "valid": true
32− }
33− ]
34− },
35− {
36− "description": "array of items with no additionalItems",
37− "schema": {
38− "items": [{}, {}, {}],
39− "additionalItems": false
40− },
41− "tests": [
42− {
43− "description": "fewer number of items present",
44− "data": [ 1, 2 ],
45− "valid": true
46− },
47− {
48− "description": "equal number of items present",
49− "data": [ 1, 2, 3 ],
50− "valid": true
51− },
52− {
53− "description": "additional items are not permitted",
54− "data": [ 1, 2, 3, 4 ],
55− "valid": false
56− }
57− ]
58− },
59− {
60− "description": "additionalItems as false without items",
61− "schema": {"additionalItems": false},
62− "tests": [
63− {
64− "description":
65− "items defaults to empty schema so everything is valid",
66− "data": [ 1, 2, 3, 4, 5 ],
67− "valid": true
68− },
69− {
70− "description": "ignores non-arrays",
71− "data": {"foo" : "bar"},
72− "valid": true
73− }
74− ]
75− },
76− {
77− "description": "additionalItems are allowed by default",
78− "schema": {"items": [{"type": "integer"}]},
79− "tests": [
80− {
81− "description": "only the first item is validated",
82− "data": [1, "foo", false],
83− "valid": true
84− }
85− ]
86− }
87−]
JSON-Schema-Test-Suite/tests/draft6/additionalProperties.jsondeleted−88
@@ -1,88 +0,0 @@
1−[
2− {
3− "description":
4− "additionalProperties being false does not allow other properties",
5− "schema": {
6− "properties": {"foo": {}, "bar": {}},
7− "patternProperties": { "^v": {} },
8− "additionalProperties": false
9− },
10− "tests": [
11− {
12− "description": "no additional properties is valid",
13− "data": {"foo": 1},
14− "valid": true
15− },
16− {
17− "description": "an additional property is invalid",
18− "data": {"foo" : 1, "bar" : 2, "quux" : "boom"},
19− "valid": false
20− },
21− {
22− "description": "ignores non-objects",
23− "data": [1, 2, 3],
24− "valid": true
25− },
26− {
27− "description": "patternProperties are not additional properties",
28− "data": {"foo":1, "vroom": 2},
29− "valid": true
30− }
31− ]
32− },
33− {
34− "description":
35− "additionalProperties allows a schema which should validate",
36− "schema": {
37− "properties": {"foo": {}, "bar": {}},
38− "additionalProperties": {"type": "boolean"}
39− },
40− "tests": [
41− {
42− "description": "no additional properties is valid",
43− "data": {"foo": 1},
44− "valid": true
45− },
46− {
47− "description": "an additional valid property is valid",
48− "data": {"foo" : 1, "bar" : 2, "quux" : true},
49− "valid": true
50− },
51− {
52− "description": "an additional invalid property is invalid",
53− "data": {"foo" : 1, "bar" : 2, "quux" : 12},
54− "valid": false
55− }
56− ]
57− },
58− {
59− "description":
60− "additionalProperties can exist by itself",
61− "schema": {
62− "additionalProperties": {"type": "boolean"}
63− },
64− "tests": [
65− {
66− "description": "an additional valid property is valid",
67− "data": {"foo" : true},
68− "valid": true
69− },
70− {
71− "description": "an additional invalid property is invalid",
72− "data": {"foo" : 1},
73− "valid": false
74− }
75− ]
76− },
77− {
78− "description": "additionalProperties are allowed by default",
79− "schema": {"properties": {"foo": {}, "bar": {}}},
80− "tests": [
81− {
82− "description": "additional properties are allowed",
83− "data": {"foo": 1, "bar": 2, "quux": true},
84− "valid": true
85− }
86− ]
87− }
88−]
JSON-Schema-Test-Suite/tests/draft6/allOf.jsondeleted−145
@@ -1,145 +0,0 @@
1−[
2− {
3− "description": "allOf",
4− "schema": {
5− "allOf": [
6− {
7− "properties": {
8− "bar": {"type": "integer"}
9− },
10− "required": ["bar"]
11− },
12− {
13− "properties": {
14− "foo": {"type": "string"}
15− },
16− "required": ["foo"]
17− }
18− ]
19− },
20− "tests": [
21− {
22− "description": "allOf",
23− "data": {"foo": "baz", "bar": 2},
24− "valid": true
25− },
26− {
27− "description": "mismatch second",
28− "data": {"foo": "baz"},
29− "valid": false
30− },
31− {
32− "description": "mismatch first",
33− "data": {"bar": 2},
34− "valid": false
35− },
36− {
37− "description": "wrong type",
38− "data": {"foo": "baz", "bar": "quux"},
39− "valid": false
40− }
41− ]
42− },
43− {
44− "description": "allOf with base schema",
45− "schema": {
46− "properties": {"bar": {"type": "integer"}},
47− "required": ["bar"],
48− "allOf" : [
49− {
50− "properties": {
51− "foo": {"type": "string"}
52− },
53− "required": ["foo"]
54− },
55− {
56− "properties": {
57− "baz": {"type": "null"}
58− },
59− "required": ["baz"]
60− }
61− ]
62− },
63− "tests": [
64− {
65− "description": "valid",
66− "data": {"foo": "quux", "bar": 2, "baz": null},
67− "valid": true
68− },
69− {
70− "description": "mismatch base schema",
71− "data": {"foo": "quux", "baz": null},
72− "valid": false
73− },
74− {
75− "description": "mismatch first allOf",
76− "data": {"bar": 2, "baz": null},
77− "valid": false
78− },
79− {
80− "description": "mismatch second allOf",
81− "data": {"foo": "quux", "bar": 2},
82− "valid": false
83− },
84− {
85− "description": "mismatch both",
86− "data": {"bar": 2},
87− "valid": false
88− }
89− ]
90− },
91− {
92− "description": "allOf simple types",
93− "schema": {
94− "allOf": [
95− {"maximum": 30},
96− {"minimum": 20}
97− ]
98− },
99− "tests": [
100− {
101− "description": "valid",
102− "data": 25,
103− "valid": true
104− },
105− {
106− "description": "mismatch one",
107− "data": 35,
108− "valid": false
109− }
110− ]
111− },
112− {
113− "description": "allOf with boolean schemas, all true",
114− "schema": {"allOf": [true, true]},
115− "tests": [
116− {
117− "description": "any value is valid",
118− "data": "foo",
119− "valid": true
120− }
121− ]
122− },
123− {
124− "description": "allOf with boolean schemas, some false",
125− "schema": {"allOf": [true, false]},
126− "tests": [
127− {
128− "description": "any value is invalid",
129− "data": "foo",
130− "valid": false
131− }
132− ]
133− },
134− {
135− "description": "allOf with boolean schemas, all false",
136− "schema": {"allOf": [false, false]},
137− "tests": [
138− {
139− "description": "any value is invalid",
140− "data": "foo",
141− "valid": false
142− }
143− ]
144− }
145−]
JSON-Schema-Test-Suite/tests/draft6/anyOf.jsondeleted−101
@@ -1,101 +0,0 @@
1−[
2− {
3− "description": "anyOf",
4− "schema": {
5− "anyOf": [
6− {
7− "type": "integer"
8− },
9− {
10− "minimum": 2
11− }
12− ]
13− },
14− "tests": [
15− {
16− "description": "first anyOf valid",
17− "data": 1,
18− "valid": true
19− },
20− {
21− "description": "second anyOf valid",
22− "data": 2.5,
23− "valid": true
24− },
25− {
26− "description": "both anyOf valid",
27− "data": 3,
28− "valid": true
29− },
30− {
31− "description": "neither anyOf valid",
32− "data": 1.5,
33− "valid": false
34− }
35− ]
36− },
37− {
38− "description": "anyOf with base schema",
39− "schema": {
40− "type": "string",
41− "anyOf" : [
42− {
43− "maxLength": 2
44− },
45− {
46− "minLength": 4
47− }
48− ]
49− },
50− "tests": [
51− {
52− "description": "mismatch base schema",
53− "data": 3,
54− "valid": false
55− },
56− {
57− "description": "one anyOf valid",
58− "data": "foobar",
59− "valid": true
60− },
61− {
62− "description": "both anyOf invalid",
63− "data": "foo",
64− "valid": false
65− }
66− ]
67− },
68− {
69− "description": "anyOf with boolean schemas, all true",
70− "schema": {"anyOf": [true, true]},
71− "tests": [
72− {
73− "description": "any value is valid",
74− "data": "foo",
75− "valid": true
76− }
77− ]
78− },
79− {
80− "description": "anyOf with boolean schemas, some true",
81− "schema": {"anyOf": [true, false]},
82− "tests": [
83− {
84− "description": "any value is valid",
85− "data": "foo",
86− "valid": true
87− }
88− ]
89− },
90− {
91− "description": "anyOf with boolean schemas, all false",
92− "schema": {"anyOf": [false, false]},
93− "tests": [
94− {
95− "description": "any value is invalid",
96− "data": "foo",
97− "valid": false
98− }
99− ]
100− }
101−]
JSON-Schema-Test-Suite/tests/draft6/boolean_schema.jsondeleted−104
@@ -1,104 +0,0 @@
1−[
2− {
3− "description": "boolean schema 'true'",
4− "schema": true,
5− "tests": [
6− {
7− "description": "number is valid",
8− "data": 1,
9− "valid": true
10− },
11− {
12− "description": "string is valid",
13− "data": "foo",
14− "valid": true
15− },
16− {
17− "description": "boolean true is valid",
18− "data": true,
19− "valid": true
20− },
21− {
22− "description": "boolean false is valid",
23− "data": false,
24− "valid": true
25− },
26− {
27− "description": "null is valid",
28− "data": null,
29− "valid": true
30− },
31− {
32− "description": "object is valid",
33− "data": {"foo": "bar"},
34− "valid": true
35− },
36− {
37− "description": "empty object is valid",
38− "data": {},
39− "valid": true
40− },
41− {
42− "description": "array is valid",
43− "data": ["foo"],
44− "valid": true
45− },
46− {
47− "description": "empty array is valid",
48− "data": [],
49− "valid": true
50− }
51− ]
52− },
53− {
54− "description": "boolean schema 'false'",
55− "schema": false,
56− "tests": [
57− {
58− "description": "number is invalid",
59− "data": 1,
60− "valid": false
61− },
62− {
63− "description": "string is invalid",
64− "data": "foo",
65− "valid": false
66− },
67− {
68− "description": "boolean true is invalid",
69− "data": true,
70− "valid": false
71− },
72− {
73− "description": "boolean false is invalid",
74− "data": false,
75− "valid": false
76− },
77− {
78− "description": "null is invalid",
79− "data": null,
80− "valid": false
81− },
82− {
83− "description": "object is invalid",
84− "data": {"foo": "bar"},
85− "valid": false
86− },
87− {
88− "description": "empty object is invalid",
89− "data": {},
90− "valid": false
91− },
92− {
93− "description": "array is invalid",
94− "data": ["foo"],
95− "valid": false
96− },
97− {
98− "description": "empty array is invalid",
99− "data": [],
100− "valid": false
101− }
102− ]
103− }
104−]
JSON-Schema-Test-Suite/tests/draft6/const.jsondeleted−65
@@ -1,65 +0,0 @@
1−[
2− {
3− "description": "const validation",
4− "schema": {"const": 2},
5− "tests": [
6− {
7− "description": "same value is valid",
8− "data": 2,
9− "valid": true
10− },
11− {
12− "description": "another value is invalid",
13− "data": 5,
14− "valid": false
15− },
16− {
17− "description": "another type is invalid",
18− "data": "a",
19− "valid": false
20− }
21− ]
22− },
23− {
24− "description": "const with object",
25− "schema": {"const": {"foo": "bar", "baz": "bax"}},
26− "tests": [
27− {
28− "description": "same object is valid",
29− "data": {"foo": "bar", "baz": "bax"},
30− "valid": true
31− },
32− {
33− "description": "same object with different property order is valid",
34− "data": {"baz": "bax", "foo": "bar"},
35− "valid": true
36− },
37− {
38− "description": "another object is invalid",
39− "data": {"foo": "bar"},
40− "valid": false
41− },
42− {
43− "description": "another type is invalid",
44− "data": [1, 2],
45− "valid": false
46− }
47− ]
48− },
49− {
50− "description": "const with null",
51− "schema": {"const": null},
52− "tests": [
53− {
54− "description": "null is valid",
55− "data": null,
56− "valid": true
57− },
58− {
59− "description": "not null is invalid",
60− "data": 0,
61− "valid": false
62− }
63− ]
64− }
65−]
JSON-Schema-Test-Suite/tests/draft6/contains.jsondeleted−95
@@ -1,95 +0,0 @@
1−[
2− {
3− "description": "contains keyword validation",
4− "schema": {
5− "contains": {"minimum": 5}
6− },
7− "tests": [
8− {
9− "description": "array with item matching schema (5) is valid",
10− "data": [3, 4, 5],
11− "valid": true
12− },
13− {
14− "description": "array with item matching schema (6) is valid",
15− "data": [3, 4, 6],
16− "valid": true
17− },
18− {
19− "description": "array with two items matching schema (5, 6) is valid",
20− "data": [3, 4, 5, 6],
21− "valid": true
22− },
23− {
24− "description": "array without items matching schema is invalid",
25− "data": [2, 3, 4],
26− "valid": false
27− },
28− {
29− "description": "empty array is invalid",
30− "data": [],
31− "valid": false
32− },
33− {
34− "description": "not array is valid",
35− "data": {},
36− "valid": true
37− }
38− ]
39− },
40− {
41− "description": "contains keyword with const keyword",
42− "schema": {
43− "contains": { "const": 5 }
44− },
45− "tests": [
46− {
47− "description": "array with item 5 is valid",
48− "data": [3, 4, 5],
49− "valid": true
50− },
51− {
52− "description": "array with two items 5 is valid",
53− "data": [3, 4, 5, 5],
54− "valid": true
55− },
56− {
57− "description": "array without item 5 is invalid",
58− "data": [1, 2, 3, 4],
59− "valid": false
60− }
61− ]
62− },
63− {
64− "description": "contains keyword with boolean schema true",
65− "schema": {"contains": true},
66− "tests": [
67− {
68− "description": "any non-empty array is valid",
69− "data": ["foo"],
70− "valid": true
71− },
72− {
73− "description": "empty array is invalid",
74− "data": [],
75− "valid": false
76− }
77− ]
78− },
79− {
80− "description": "contains keyword with boolean schema false",
81− "schema": {"contains": false},
82− "tests": [
83− {
84− "description": "any non-empty array is invalid",
85− "data": ["foo"],
86− "valid": false
87− },
88− {
89− "description": "empty array is invalid",
90− "data": [],
91− "valid": false
92− }
93− ]
94− }
95−]
JSON-Schema-Test-Suite/tests/draft6/default.jsondeleted−49
@@ -1,49 +0,0 @@
1−[
2− {
3− "description": "invalid type for default",
4− "schema": {
5− "properties": {
6− "foo": {
7− "type": "integer",
8− "default": []
9− }
10− }
11− },
12− "tests": [
13− {
14− "description": "valid when property is specified",
15− "data": {"foo": 13},
16− "valid": true
17− },
18− {
19− "description": "still valid when the invalid default is used",
20− "data": {},
21− "valid": true
22− }
23− ]
24− },
25− {
26− "description": "invalid string value for default",
27− "schema": {
28− "properties": {
29− "bar": {
30− "type": "string",
31− "minLength": 4,
32− "default": "bad"
33− }
34− }
35− },
36− "tests": [
37− {
38− "description": "valid when property is specified",
39− "data": {"bar": "good"},
40− "valid": true
41− },
42− {
43− "description": "still valid when the invalid default is used",
44− "data": {},
45− "valid": true
46− }
47− ]
48− }
49−]
JSON-Schema-Test-Suite/tests/draft6/definitions.jsondeleted−32
@@ -1,32 +0,0 @@
1−[
2− {
3− "description": "valid definition",
4− "schema": {"$ref": "http://json-schema.org/draft-04/schema#"},
5− "tests": [
6− {
7− "description": "valid definition schema",
8− "data": {
9− "definitions": {
10− "foo": {"type": "integer"}
11− }
12− },
13− "valid": true
14− }
15− ]
16− },
17− {
18− "description": "invalid definition",
19− "schema": {"$ref": "http://json-schema.org/draft-04/schema#"},
20− "tests": [
21− {
22− "description": "invalid definition schema",
23− "data": {
24− "definitions": {
25− "foo": {"type": 1}
26− }
27− },
28− "valid": false
29− }
30− ]
31− }
32−]
JSON-Schema-Test-Suite/tests/draft6/dependencies.jsondeleted−162
@@ -1,162 +0,0 @@
1−[
2− {
3− "description": "dependencies",
4− "schema": {
5− "dependencies": {"bar": ["foo"]}
6− },
7− "tests": [
8− {
9− "description": "neither",
10− "data": {},
11− "valid": true
12− },
13− {
14− "description": "nondependant",
15− "data": {"foo": 1},
16− "valid": true
17− },
18− {
19− "description": "with dependency",
20− "data": {"foo": 1, "bar": 2},
21− "valid": true
22− },
23− {
24− "description": "missing dependency",
25− "data": {"bar": 2},
26− "valid": false
27− },
28− {
29− "description": "ignores non-objects",
30− "data": "foo",
31− "valid": true
32− }
33− ]
34− },
35− {
36− "description": "dependencies with empty array",
37− "schema": {
38− "dependencies": {"bar": []}
39− },
40− "tests": [
41− {
42− "description": "empty object",
43− "data": {},
44− "valid": true
45− },
46− {
47− "description": "object with one property",
48− "data": {"bar": 2},
49− "valid": true
50− }
51− ]
52− },
53− {
54− "description": "multiple dependencies",
55− "schema": {
56− "dependencies": {"quux": ["foo", "bar"]}
57− },
58− "tests": [
59− {
60− "description": "neither",
61− "data": {},
62− "valid": true
63− },
64− {
65− "description": "nondependants",
66− "data": {"foo": 1, "bar": 2},
67− "valid": true
68− },
69− {
70− "description": "with dependencies",
71− "data": {"foo": 1, "bar": 2, "quux": 3},
72− "valid": true
73− },
74− {
75− "description": "missing dependency",
76− "data": {"foo": 1, "quux": 2},
77− "valid": false
78− },
79− {
80− "description": "missing other dependency",
81− "data": {"bar": 1, "quux": 2},
82− "valid": false
83− },
84− {
85− "description": "missing both dependencies",
86− "data": {"quux": 1},
87− "valid": false
88− }
89− ]
90− },
91− {
92− "description": "multiple dependencies subschema",
93− "schema": {
94− "dependencies": {
95− "bar": {
96− "properties": {
97− "foo": {"type": "integer"},
98− "bar": {"type": "integer"}
99− }
100− }
101− }
102− },
103− "tests": [
104− {
105− "description": "valid",
106− "data": {"foo": 1, "bar": 2},
107− "valid": true
108− },
109− {
110− "description": "no dependency",
111− "data": {"foo": "quux"},
112− "valid": true
113− },
114− {
115− "description": "wrong type",
116− "data": {"foo": "quux", "bar": 2},
117− "valid": false
118− },
119− {
120− "description": "wrong type other",
121− "data": {"foo": 2, "bar": "quux"},
122− "valid": false
123− },
124− {
125− "description": "wrong type both",
126− "data": {"foo": "quux", "bar": "quux"},
127− "valid": false
128− }
129− ]
130− },
131− {
132− "description": "dependencies with boolean subschemas",
133− "schema": {
134− "dependencies": {
135− "foo": true,
136− "bar": false
137− }
138− },
139− "tests": [
140− {
141− "description": "object with property having schema true is valid",
142− "data": {"foo": 1},
143− "valid": true
144− },
145− {
146− "description": "object with property having schema false is invalid",
147− "data": {"bar": 2},
148− "valid": false
149− },
150− {
151− "description": "object with both properties is invalid",
152− "data": {"foo": 1, "bar": 2},
153− "valid": false
154− },
155− {
156− "description": "empty object is valid",
157− "data": {},
158− "valid": true
159− }
160− ]
161− }
162−]
JSON-Schema-Test-Suite/tests/draft6/enum.jsondeleted−72
@@ -1,72 +0,0 @@
1−[
2− {
3− "description": "simple enum validation",
4− "schema": {"enum": [1, 2, 3]},
5− "tests": [
6− {
7− "description": "one of the enum is valid",
8− "data": 1,
9− "valid": true
10− },
11− {
12− "description": "something else is invalid",
13− "data": 4,
14− "valid": false
15− }
16− ]
17− },
18− {
19− "description": "heterogeneous enum validation",
20− "schema": {"enum": [6, "foo", [], true, {"foo": 12}]},
21− "tests": [
22− {
23− "description": "one of the enum is valid",
24− "data": [],
25− "valid": true
26− },
27− {
28− "description": "something else is invalid",
29− "data": null,
30− "valid": false
31− },
32− {
33− "description": "objects are deep compared",
34− "data": {"foo": false},
35− "valid": false
36− }
37− ]
38− },
39− {
40− "description": "enums in properties",
41− "schema": {
42− "type":"object",
43− "properties": {
44− "foo": {"enum":["foo"]},
45− "bar": {"enum":["bar"]}
46− },
47− "required": ["bar"]
48− },
49− "tests": [
50− {
51− "description": "both properties are valid",
52− "data": {"foo":"foo", "bar":"bar"},
53− "valid": true
54− },
55− {
56− "description": "missing optional property is valid",
57− "data": {"bar":"bar"},
58− "valid": true
59− },
60− {
61− "description": "missing required property is invalid",
62− "data": {"foo":"foo"},
63− "valid": false
64− },
65− {
66− "description": "missing all properties is invalid",
67− "data": {},
68− "valid": false
69− }
70− ]
71− }
72−]
JSON-Schema-Test-Suite/tests/draft6/exclusiveMaximum.jsondeleted−30
@@ -1,30 +0,0 @@
1−[
2− {
3− "description": "exclusiveMaximum validation",
4− "schema": {
5− "exclusiveMaximum": 3.0
6− },
7− "tests": [
8− {
9− "description": "below the exclusiveMaximum is valid",
10− "data": 2.2,
11− "valid": true
12− },
13− {
14− "description": "boundary point is invalid",
15− "data": 3.0,
16− "valid": false
17− },
18− {
19− "description": "above the exclusiveMaximum is invalid",
20− "data": 3.5,
21− "valid": false
22− },
23− {
24− "description": "ignores non-numbers",
25− "data": "x",
26− "valid": true
27− }
28− ]
29− }
30−]
JSON-Schema-Test-Suite/tests/draft6/exclusiveMinimum.jsondeleted−30
@@ -1,30 +0,0 @@
1−[
2− {
3− "description": "exclusiveMinimum validation",
4− "schema": {
5− "exclusiveMinimum": 1.1
6− },
7− "tests": [
8− {
9− "description": "above the exclusiveMinimum is valid",
10− "data": 1.2,
11− "valid": true
12− },
13− {
14− "description": "boundary point is invalid",
15− "data": 1.1,
16− "valid": false
17− },
18− {
19− "description": "below the exclusiveMinimum is invalid",
20− "data": 0.6,
21− "valid": false
22− },
23− {
24− "description": "ignores non-numbers",
25− "data": "x",
26− "valid": true
27− }
28− ]
29− }
30−]
JSON-Schema-Test-Suite/tests/draft6/items.jsondeleted−133
@@ -1,133 +0,0 @@
1−[
2− {
3− "description": "a schema given for items",
4− "schema": {
5− "items": {"type": "integer"}
6− },
7− "tests": [
8− {
9− "description": "valid items",
10− "data": [ 1, 2, 3 ],
11− "valid": true
12− },
13− {
14− "description": "wrong type of items",
15− "data": [1, "x"],
16− "valid": false
17− },
18− {
19− "description": "ignores non-arrays",
20− "data": {"foo" : "bar"},
21− "valid": true
22− },
23− {
24− "description": "JavaScript pseudo-array is valid",
25− "data": {
26− "0": "invalid",
27− "length": 1
28− },
29− "valid": true
30− }
31− ]
32− },
33− {
34− "description": "an array of schemas for items",
35− "schema": {
36− "items": [
37− {"type": "integer"},
38− {"type": "string"}
39− ]
40− },
41− "tests": [
42− {
43− "description": "correct types",
44− "data": [ 1, "foo" ],
45− "valid": true
46− },
47− {
48− "description": "wrong types",
49− "data": [ "foo", 1 ],
50− "valid": false
51− },
52− {
53− "description": "incomplete array of items",
54− "data": [ 1 ],
55− "valid": true
56− },
57− {
58− "description": "array with additional items",
59− "data": [ 1, "foo", true ],
60− "valid": true
61− },
62− {
63− "description": "empty array",
64− "data": [ ],
65− "valid": true
66− },
67− {
68− "description": "JavaScript pseudo-array is valid",
69− "data": {
70− "0": "invalid",
71− "1": "valid",
72− "length": 2
73− },
74− "valid": true
75− }
76− ]
77− },
78− {
79− "description": "items with boolean schema (true)",
80− "schema": {"items": true},
81− "tests": [
82− {
83− "description": "any array is valid",
84− "data": [ 1, "foo", true ],
85− "valid": true
86− },
87− {
88− "description": "empty array is valid",
89− "data": [],
90− "valid": true
91− }
92− ]
93− },
94− {
95− "description": "items with boolean schema (false)",
96− "schema": {"items": false},
97− "tests": [
98− {
99− "description": "any non-empty array is invalid",
100− "data": [ 1, "foo", true ],
101− "valid": false
102− },
103− {
104− "description": "empty array is valid",
105− "data": [],
106− "valid": true
107− }
108− ]
109− },
110− {
111− "description": "items with boolean schemas",
112− "schema": {
113− "items": [true, false]
114− },
115− "tests": [
116− {
117− "description": "array with one item is valid",
118− "data": [ 1 ],
119− "valid": true
120− },
121− {
122− "description": "array with two items is invalid",
123− "data": [ 1, "foo" ],
124− "valid": false
125− },
126− {
127− "description": "empty array is valid",
128− "data": [],
129− "valid": true
130− }
131− ]
132− }
133−]
JSON-Schema-Test-Suite/tests/draft6/maxItems.jsondeleted−28
@@ -1,28 +0,0 @@
1−[
2− {
3− "description": "maxItems validation",
4− "schema": {"maxItems": 2},
5− "tests": [
6− {
7− "description": "shorter is valid",
8− "data": [1],
9− "valid": true
10− },
11− {
12− "description": "exact length is valid",
13− "data": [1, 2],
14− "valid": true
15− },
16− {
17− "description": "too long is invalid",
18− "data": [1, 2, 3],
19− "valid": false
20− },
21− {
22− "description": "ignores non-arrays",
23− "data": "foobar",
24− "valid": true
25− }
26− ]
27− }
28−]
JSON-Schema-Test-Suite/tests/draft6/maxLength.jsondeleted−33
@@ -1,33 +0,0 @@
1−[
2− {
3− "description": "maxLength validation",
4− "schema": {"maxLength": 2},
5− "tests": [
6− {
7− "description": "shorter is valid",
8− "data": "f",
9− "valid": true
10− },
11− {
12− "description": "exact length is valid",
13− "data": "fo",
14− "valid": true
15− },
16− {
17− "description": "too long is invalid",
18− "data": "foo",
19− "valid": false
20− },
21− {
22− "description": "ignores non-strings",
23− "data": 100,
24− "valid": true
25− },
26− {
27− "description": "two supplementary Unicode code points is long enough",
28− "data": "\uD83D\uDCA9\uD83D\uDCA9",
29− "valid": true
30− }
31− ]
32− }
33−]
JSON-Schema-Test-Suite/tests/draft6/maxProperties.jsondeleted−28
@@ -1,28 +0,0 @@
1−[
2− {
3− "description": "maxProperties validation",
4− "schema": {"maxProperties": 2},
5− "tests": [
6− {
7− "description": "shorter is valid",
8− "data": {"foo": 1},
9− "valid": true
10− },
11− {
12− "description": "exact length is valid",
13− "data": {"foo": 1, "bar": 2},
14− "valid": true
15− },
16− {
17− "description": "too long is invalid",
18− "data": {"foo": 1, "bar": 2, "baz": 3},
19− "valid": false
20− },
21− {
22− "description": "ignores non-objects",
23− "data": "foobar",
24− "valid": true
25− }
26− ]
27− }
28−]
JSON-Schema-Test-Suite/tests/draft6/maximum.jsondeleted−28
@@ -1,28 +0,0 @@
1−[
2− {
3− "description": "maximum validation",
4− "schema": {"maximum": 3.0},
5− "tests": [
6− {
7− "description": "below the maximum is valid",
8− "data": 2.6,
9− "valid": true
10− },
11− {
12− "description": "boundary point is valid",
13− "data": 3.0,
14− "valid": true
15− },
16− {
17− "description": "above the maximum is invalid",
18− "data": 3.5,
19− "valid": false
20− },
21− {
22− "description": "ignores non-numbers",
23− "data": "x",
24− "valid": true
25− }
26− ]
27− }
28−]
JSON-Schema-Test-Suite/tests/draft6/minItems.jsondeleted−28
@@ -1,28 +0,0 @@
1−[
2− {
3− "description": "minItems validation",
4− "schema": {"minItems": 1},
5− "tests": [
6− {
7− "description": "longer is valid",
8− "data": [1, 2],
9− "valid": true
10− },
11− {
12− "description": "exact length is valid",
13− "data": [1],
14− "valid": true
15− },
16− {
17− "description": "too short is invalid",
18− "data": [],
19− "valid": false
20− },
21− {
22− "description": "ignores non-arrays",
23− "data": "",
24− "valid": true
25− }
26− ]
27− }
28−]
JSON-Schema-Test-Suite/tests/draft6/minLength.jsondeleted−33
@@ -1,33 +0,0 @@
1−[
2− {
3− "description": "minLength validation",
4− "schema": {"minLength": 2},
5− "tests": [
6− {
7− "description": "longer is valid",
8− "data": "foo",
9− "valid": true
10− },
11− {
12− "description": "exact length is valid",
13− "data": "fo",
14− "valid": true
15− },
16− {
17− "description": "too short is invalid",
18− "data": "f",
19− "valid": false
20− },
21− {
22− "description": "ignores non-strings",
23− "data": 1,
24− "valid": true
25− },
26− {
27− "description": "one supplementary Unicode code point is not long enough",
28− "data": "\uD83D\uDCA9",
29− "valid": false
30− }
31− ]
32− }
33−]
JSON-Schema-Test-Suite/tests/draft6/minProperties.jsondeleted−28
@@ -1,28 +0,0 @@
1−[
2− {
3− "description": "minProperties validation",
4− "schema": {"minProperties": 1},
5− "tests": [
6− {
7− "description": "longer is valid",
8− "data": {"foo": 1, "bar": 2},
9− "valid": true
10− },
11− {
12− "description": "exact length is valid",
13− "data": {"foo": 1},
14− "valid": true
15− },
16− {
17− "description": "too short is invalid",
18− "data": {},
19− "valid": false
20− },
21− {
22− "description": "ignores non-objects",
23− "data": "",
24− "valid": true
25− }
26− ]
27− }
28−]
JSON-Schema-Test-Suite/tests/draft6/minimum.jsondeleted−28
@@ -1,28 +0,0 @@
1−[
2− {
3− "description": "minimum validation",
4− "schema": {"minimum": 1.1},
5− "tests": [
6− {
7− "description": "above the minimum is valid",
8− "data": 2.6,
9− "valid": true
10− },
11− {
12− "description": "boundary point is valid",
13− "data": 1.1,
14− "valid": true
15− },
16− {
17− "description": "below the minimum is invalid",
18− "data": 0.6,
19− "valid": false
20− },
21− {
22− "description": "ignores non-numbers",
23− "data": "x",
24− "valid": true
25− }
26− ]
27− }
28−]
JSON-Schema-Test-Suite/tests/draft6/multipleOf.jsondeleted−60
@@ -1,60 +0,0 @@
1−[
2− {
3− "description": "by int",
4− "schema": {"multipleOf": 2},
5− "tests": [
6− {
7− "description": "int by int",
8− "data": 10,
9− "valid": true
10− },
11− {
12− "description": "int by int fail",
13− "data": 7,
14− "valid": false
15− },
16− {
17− "description": "ignores non-numbers",
18− "data": "foo",
19− "valid": true
20− }
21− ]
22− },
23− {
24− "description": "by number",
25− "schema": {"multipleOf": 1.5},
26− "tests": [
27− {
28− "description": "zero is multiple of anything",
29− "data": 0,
30− "valid": true
31− },
32− {
33− "description": "4.5 is multiple of 1.5",
34− "data": 4.5,
35− "valid": true
36− },
37− {
38− "description": "35 is not multiple of 1.5",
39− "data": 35,
40− "valid": false
41− }
42− ]
43− },
44− {
45− "description": "by small number",
46− "schema": {"multipleOf": 0.0001},
47− "tests": [
48− {
49− "description": "0.0075 is multiple of 0.0001",
50− "data": 0.0075,
51− "valid": true
52− },
53− {
54− "description": "0.00751 is not multiple of 0.0001",
55− "data": 0.00751,
56− "valid": false
57− }
58− ]
59− }
60−]
JSON-Schema-Test-Suite/tests/draft6/not.jsondeleted−117
@@ -1,117 +0,0 @@
1−[
2− {
3− "description": "not",
4− "schema": {
5− "not": {"type": "integer"}
6− },
7− "tests": [
8− {
9− "description": "allowed",
10− "data": "foo",
11− "valid": true
12− },
13− {
14− "description": "disallowed",
15− "data": 1,
16− "valid": false
17− }
18− ]
19− },
20− {
21− "description": "not multiple types",
22− "schema": {
23− "not": {"type": ["integer", "boolean"]}
24− },
25− "tests": [
26− {
27− "description": "valid",
28− "data": "foo",
29− "valid": true
30− },
31− {
32− "description": "mismatch",
33− "data": 1,
34− "valid": false
35− },
36− {
37− "description": "other mismatch",
38− "data": true,
39− "valid": false
40− }
41− ]
42− },
43− {
44− "description": "not more complex schema",
45− "schema": {
46− "not": {
47− "type": "object",
48− "properties": {
49− "foo": {
50− "type": "string"
51− }
52− }
53− }
54− },
55− "tests": [
56− {
57− "description": "match",
58− "data": 1,
59− "valid": true
60− },
61− {
62− "description": "other match",
63− "data": {"foo": 1},
64− "valid": true
65− },
66− {
67− "description": "mismatch",
68− "data": {"foo": "bar"},
69− "valid": false
70− }
71− ]
72− },
73− {
74− "description": "forbidden property",
75− "schema": {
76− "properties": {
77− "foo": {
78− "not": {}
79− }
80− }
81− },
82− "tests": [
83− {
84− "description": "property present",
85− "data": {"foo": 1, "bar": 2},
86− "valid": false
87− },
88− {
89− "description": "property absent",
90− "data": {"bar": 1, "baz": 2},
91− "valid": true
92− }
93− ]
94− },
95− {
96− "description": "not with boolean schema true",
97− "schema": {"not": true},
98− "tests": [
99− {
100− "description": "any value is invalid",
101− "data": "foo",
102− "valid": false
103− }
104− ]
105− },
106− {
107− "description": "not with boolean schema false",
108− "schema": {"not": false},
109− "tests": [
110− {
111− "description": "any value is valid",
112− "data": "foo",
113− "valid": true
114− }
115− ]
116− }
117−]
JSON-Schema-Test-Suite/tests/draft6/oneOf.jsondeleted−112
@@ -1,112 +0,0 @@
1−[
2− {
3− "description": "oneOf",
4− "schema": {
5− "oneOf": [
6− {
7− "type": "integer"
8− },
9− {
10− "minimum": 2
11− }
12− ]
13− },
14− "tests": [
15− {
16− "description": "first oneOf valid",
17− "data": 1,
18− "valid": true
19− },
20− {
21− "description": "second oneOf valid",
22− "data": 2.5,
23− "valid": true
24− },
25− {
26− "description": "both oneOf valid",
27− "data": 3,
28− "valid": false
29− },
30− {
31− "description": "neither oneOf valid",
32− "data": 1.5,
33− "valid": false
34− }
35− ]
36− },
37− {
38− "description": "oneOf with base schema",
39− "schema": {
40− "type": "string",
41− "oneOf" : [
42− {
43− "minLength": 2
44− },
45− {
46− "maxLength": 4
47− }
48− ]
49− },
50− "tests": [
51− {
52− "description": "mismatch base schema",
53− "data": 3,
54− "valid": false
55− },
56− {
57− "description": "one oneOf valid",
58− "data": "foobar",
59− "valid": true
60− },
61− {
62− "description": "both oneOf valid",
63− "data": "foo",
64− "valid": false
65− }
66− ]
67− },
68− {
69− "description": "oneOf with boolean schemas, all true",
70− "schema": {"oneOf": [true, true, true]},
71− "tests": [
72− {
73− "description": "any value is invalid",
74− "data": "foo",
75− "valid": false
76− }
77− ]
78− },
79− {
80− "description": "oneOf with boolean schemas, one true",
81− "schema": {"oneOf": [true, false, false]},
82− "tests": [
83− {
84− "description": "any value is valid",
85− "data": "foo",
86− "valid": true
87− }
88− ]
89− },
90− {
91− "description": "oneOf with boolean schemas, more than one true",
92− "schema": {"oneOf": [true, true, false]},
93− "tests": [
94− {
95− "description": "any value is invalid",
96− "data": "foo",
97− "valid": false
98− }
99− ]
100− },
101− {
102− "description": "oneOf with boolean schemas, all false",
103− "schema": {"oneOf": [false, false, false]},
104− "tests": [
105− {
106− "description": "any value is invalid",
107− "data": "foo",
108− "valid": false
109− }
110− ]
111− }
112−]
JSON-Schema-Test-Suite/tests/draft6/optional/bignum.jsondeleted−105
@@ -1,105 +0,0 @@
1−[
2− {
3− "description": "integer",
4− "schema": {"type": "integer"},
5− "tests": [
6− {
7− "description": "a bignum is an integer",
8− "data": 12345678910111213141516171819202122232425262728293031,
9− "valid": true
10− }
11− ]
12− },
13− {
14− "description": "number",
15− "schema": {"type": "number"},
16− "tests": [
17− {
18− "description": "a bignum is a number",
19− "data": 98249283749234923498293171823948729348710298301928331,
20− "valid": true
21− }
22− ]
23− },
24− {
25− "description": "integer",
26− "schema": {"type": "integer"},
27− "tests": [
28− {
29− "description": "a negative bignum is an integer",
30− "data": -12345678910111213141516171819202122232425262728293031,
31− "valid": true
32− }
33− ]
34− },
35− {
36− "description": "number",
37− "schema": {"type": "number"},
38− "tests": [
39− {
40− "description": "a negative bignum is a number",
41− "data": -98249283749234923498293171823948729348710298301928331,
42− "valid": true
43− }
44− ]
45− },
46− {
47− "description": "string",
48− "schema": {"type": "string"},
49− "tests": [
50− {
51− "description": "a bignum is not a string",
52− "data": 98249283749234923498293171823948729348710298301928331,
53− "valid": false
54− }
55− ]
56− },
57− {
58− "description": "integer comparison",
59− "schema": {"maximum": 18446744073709551615},
60− "tests": [
61− {
62− "description": "comparison works for high numbers",
63− "data": 18446744073709551600,
64− "valid": true
65− }
66− ]
67− },
68− {
69− "description": "float comparison with high precision",
70− "schema": {
71− "exclusiveMaximum": 972783798187987123879878123.18878137
72− },
73− "tests": [
74− {
75− "description": "comparison works for high numbers",
76− "data": 972783798187987123879878123.188781371,
77− "valid": false
78− }
79− ]
80− },
81− {
82− "description": "integer comparison",
83− "schema": {"minimum": -18446744073709551615},
84− "tests": [
85− {
86− "description": "comparison works for very negative numbers",
87− "data": -18446744073709551600,
88− "valid": true
89− }
90− ]
91− },
92− {
93− "description": "float comparison with high precision on negative numbers",
94− "schema": {
95− "exclusiveMinimum": -972783798187987123879878123.18878137
96− },
97− "tests": [
98− {
99− "description": "comparison works for very negative numbers",
100− "data": -972783798187987123879878123.188781371,
101− "valid": false
102− }
103− ]
104− }
105−]
JSON-Schema-Test-Suite/tests/draft6/optional/ecmascript-regex.jsondeleted−13
@@ -1,13 +0,0 @@
1−[
2− {
3− "description": "ECMA 262 regex non-compliance",
4− "schema": { "format": "regex" },
5− "tests": [
6− {
7− "description": "ECMA 262 has no support for \\Z anchor from .NET",
8− "data": "^\\S(|(.|\\n)*\\S)\\Z",
9− "valid": false
10− }
11− ]
12− }
13−]
JSON-Schema-Test-Suite/tests/draft6/optional/format.jsondeleted−148
@@ -1,148 +0,0 @@
1−[
2− {
3− "description": "validation of date-time strings",
4− "schema": {"format": "date-time"},
5− "tests": [
6− {
7− "description": "a valid date-time string",
8− "data": "1963-06-19T08:30:06.283185Z",
9− "valid": true
10− },
11− {
12− "description": "an invalid date-time string",
13− "data": "06/19/1963 08:30:06 PST",
14− "valid": false
15− },
16− {
17− "description": "only RFC3339 not all of ISO 8601 are valid",
18− "data": "2013-350T01:01:01",
19− "valid": false
20− }
21− ]
22− },
23− {
24− "description": "validation of URIs",
25− "schema": {"format": "uri"},
26− "tests": [
27− {
28− "description": "a valid URI",
29− "data": "http://foo.bar/?baz=qux#quux",
30− "valid": true
31− },
32− {
33− "description": "an invalid protocol-relative URI Reference",
34− "data": "//foo.bar/?baz=qux#quux",
35− "valid": false
36− },
37− {
38− "description": "an invalid URI",
39− "data": "\\\\WINDOWS\\fileshare",
40− "valid": false
41− },
42− {
43− "description": "an invalid URI though valid URI reference",
44− "data": "abc",
45− "valid": false
46− }
47− ]
48− },
49− {
50− "description": "validation of e-mail addresses",
51− "schema": {"format": "email"},
52− "tests": [
53− {
54− "description": "a valid e-mail address",
55− "data": "joe.bloggs@example.com",
56− "valid": true
57− },
58− {
59− "description": "an invalid e-mail address",
60− "data": "2962",
61− "valid": false
62− }
63− ]
64− },
65− {
66− "description": "validation of IP addresses",
67− "schema": {"format": "ipv4"},
68− "tests": [
69− {
70− "description": "a valid IP address",
71− "data": "192.168.0.1",
72− "valid": true
73− },
74− {
75− "description": "an IP address with too many components",
76− "data": "127.0.0.0.1",
77− "valid": false
78− },
79− {
80− "description": "an IP address with out-of-range values",
81− "data": "256.256.256.256",
82− "valid": false
83− },
84− {
85− "description": "an IP address without 4 components",
86− "data": "127.0",
87− "valid": false
88− },
89− {
90− "description": "an IP address as an integer",
91− "data": "0x7f000001",
92− "valid": false
93− }
94− ]
95− },
96− {
97− "description": "validation of IPv6 addresses",
98− "schema": {"format": "ipv6"},
99− "tests": [
100− {
101− "description": "a valid IPv6 address",
102− "data": "::1",
103− "valid": true
104− },
105− {
106− "description": "an IPv6 address with out-of-range values",
107− "data": "12345::",
108− "valid": false
109− },
110− {
111− "description": "an IPv6 address with too many components",
112− "data": "1:1:1:1:1:1:1:1:1:1:1:1:1:1:1:1",
113− "valid": false
114− },
115− {
116− "description": "an IPv6 address containing illegal characters",
117− "data": "::laptop",
118− "valid": false
119− }
120− ]
121− },
122− {
123− "description": "validation of host names",
124− "schema": {"format": "hostname"},
125− "tests": [
126− {
127− "description": "a valid host name",
128− "data": "www.example.com",
129− "valid": true
130− },
131− {
132− "description": "a host name starting with an illegal character",
133− "data": "-a-host-name-that-starts-with--",
134− "valid": false
135− },
136− {
137− "description": "a host name containing illegal characters",
138− "data": "not_a_valid_host_name",
139− "valid": false
140− },
141− {
142− "description": "a host name with a component too long",
143− "data": "a-vvvvvvvvvvvvvvvveeeeeeeeeeeeeeeerrrrrrrrrrrrrrrryyyyyyyyyyyyyyyy-long-host-name-component",
144− "valid": false
145− }
146− ]
147− }
148−]
JSON-Schema-Test-Suite/tests/draft6/optional/zeroTerminatedFloats.jsondeleted−15
@@ -1,15 +0,0 @@
1−[
2− {
3− "description": "some languages do not distinguish between different types of numeric value",
4− "schema": {
5− "type": "integer"
6− },
7− "tests": [
8− {
9− "description": "a float is not an integer even without fractional part",
10− "data": 1.0,
11− "valid": true
12− }
13− ]
14− }
15−]
JSON-Schema-Test-Suite/tests/draft6/pattern.jsondeleted−34
@@ -1,34 +0,0 @@
1−[
2− {
3− "description": "pattern validation",
4− "schema": {"pattern": "^a*$"},
5− "tests": [
6− {
7− "description": "a matching pattern is valid",
8− "data": "aaa",
9− "valid": true
10− },
11− {
12− "description": "a non-matching pattern is invalid",
13− "data": "abc",
14− "valid": false
15− },
16− {
17− "description": "ignores non-strings",
18− "data": true,
19− "valid": true
20− }
21− ]
22− },
23− {
24− "description": "pattern is not anchored",
25− "schema": {"pattern": "a+"},
26− "tests": [
27− {
28− "description": "matches a substring",
29− "data": "xxaayy",
30− "valid": true
31− }
32− ]
33− }
34−]
JSON-Schema-Test-Suite/tests/draft6/patternProperties.jsondeleted−141
@@ -1,141 +0,0 @@
1−[
2− {
3− "description":
4− "patternProperties validates properties matching a regex",
5− "schema": {
6− "patternProperties": {
7− "f.*o": {"type": "integer"}
8− }
9− },
10− "tests": [
11− {
12− "description": "a single valid match is valid",
13− "data": {"foo": 1},
14− "valid": true
15− },
16− {
17− "description": "multiple valid matches is valid",
18− "data": {"foo": 1, "foooooo" : 2},
19− "valid": true
20− },
21− {
22− "description": "a single invalid match is invalid",
23− "data": {"foo": "bar", "fooooo": 2},
24− "valid": false
25− },
26− {
27− "description": "multiple invalid matches is invalid",
28− "data": {"foo": "bar", "foooooo" : "baz"},
29− "valid": false
30− },
31− {
32− "description": "ignores non-objects",
33− "data": 12,
34− "valid": true
35− }
36− ]
37− },
38− {
39− "description": "multiple simultaneous patternProperties are validated",
40− "schema": {
41− "patternProperties": {
42− "a*": {"type": "integer"},
43− "aaa*": {"maximum": 20}
44− }
45− },
46− "tests": [
47− {
48− "description": "a single valid match is valid",
49− "data": {"a": 21},
50− "valid": true
51− },
52− {
53− "description": "a simultaneous match is valid",
54− "data": {"aaaa": 18},
55− "valid": true
56− },
57− {
58− "description": "multiple matches is valid",
59− "data": {"a": 21, "aaaa": 18},
60− "valid": true
61− },
62− {
63− "description": "an invalid due to one is invalid",
64− "data": {"a": "bar"},
65− "valid": false
66− },
67− {
68− "description": "an invalid due to the other is invalid",
69− "data": {"aaaa": 31},
70− "valid": false
71− },
72− {
73− "description": "an invalid due to both is invalid",
74− "data": {"aaa": "foo", "aaaa": 31},
75− "valid": false
76− }
77− ]
78− },
79− {
80− "description": "regexes are not anchored by default and are case sensitive",
81− "schema": {
82− "patternProperties": {
83− "[0-9]{2,}": { "type": "boolean" },
84− "X_": { "type": "string" }
85− }
86− },
87− "tests": [
88− {
89− "description": "non recognized members are ignored",
90− "data": { "answer 1": "42" },
91− "valid": true
92− },
93− {
94− "description": "recognized members are accounted for",
95− "data": { "a31b": null },
96− "valid": false
97− },
98− {
99− "description": "regexes are case sensitive",
100− "data": { "a_x_3": 3 },
101− "valid": true
102− },
103− {
104− "description": "regexes are case sensitive, 2",
105− "data": { "a_X_3": 3 },
106− "valid": false
107− }
108− ]
109− },
110− {
111− "description": "patternProperties with boolean schemas",
112− "schema": {
113− "patternProperties": {
114− "f.*": true,
115− "b.*": false
116− }
117− },
118− "tests": [
119− {
120− "description": "object with property matching schema true is valid",
121− "data": {"foo": 1},
122− "valid": true
123− },
124− {
125− "description": "object with property matching schema false is invalid",
126− "data": {"bar": 2},
127− "valid": false
128− },
129− {
130− "description": "object with both properties is invalid",
131− "data": {"foo": 1, "bar": 2},
132− "valid": false
133− },
134− {
135− "description": "empty object is valid",
136− "data": {},
137− "valid": true
138− }
139− ]
140− }
141−]
JSON-Schema-Test-Suite/tests/draft6/properties.jsondeleted−123
@@ -1,123 +0,0 @@
1−[
2− {
3− "description": "object properties validation",
4− "schema": {
5− "properties": {
6− "foo": {"type": "integer"},
7− "bar": {"type": "string"}
8− }
9− },
10− "tests": [
11− {
12− "description": "both properties present and valid is valid",
13− "data": {"foo": 1, "bar": "baz"},
14− "valid": true
15− },
16− {
17− "description": "one property invalid is invalid",
18− "data": {"foo": 1, "bar": {}},
19− "valid": false
20− },
21− {
22− "description": "both properties invalid is invalid",
23− "data": {"foo": [], "bar": {}},
24− "valid": false
25− },
26− {
27− "description": "doesn't invalidate other properties",
28− "data": {"quux": []},
29− "valid": true
30− },
31− {
32− "description": "ignores non-objects",
33− "data": [],
34− "valid": true
35− }
36− ]
37− },
38− {
39− "description":
40− "properties, patternProperties, additionalProperties interaction",
41− "schema": {
42− "properties": {
43− "foo": {"type": "array", "maxItems": 3},
44− "bar": {"type": "array"}
45− },
46− "patternProperties": {"f.o": {"minItems": 2}},
47− "additionalProperties": {"type": "integer"}
48− },
49− "tests": [
50− {
51− "description": "property validates property",
52− "data": {"foo": [1, 2]},
53− "valid": true
54− },
55− {
56− "description": "property invalidates property",
57− "data": {"foo": [1, 2, 3, 4]},
58− "valid": false
59− },
60− {
61− "description": "patternProperty invalidates property",
62− "data": {"foo": []},
63− "valid": false
64− },
65− {
66− "description": "patternProperty validates nonproperty",
67− "data": {"fxo": [1, 2]},
68− "valid": true
69− },
70− {
71− "description": "patternProperty invalidates nonproperty",
72− "data": {"fxo": []},
73− "valid": false
74− },
75− {
76− "description": "additionalProperty ignores property",
77− "data": {"bar": []},
78− "valid": true
79− },
80− {
81− "description": "additionalProperty validates others",
82− "data": {"quux": 3},
83− "valid": true
84− },
85− {
86− "description": "additionalProperty invalidates others",
87− "data": {"quux": "foo"},
88− "valid": false
89− }
90− ]
91− },
92− {
93− "description": "properties with boolean schema",
94− "schema": {
95− "properties": {
96− "foo": true,
97− "bar": false
98− }
99− },
100− "tests": [
101− {
102− "description": "no property present is valid",
103− "data": {},
104− "valid": true
105− },
106− {
107− "description": "only 'true' property present is valid",
108− "data": {"foo": 1},
109− "valid": true
110− },
111− {
112− "description": "only 'false' property present is invalid",
113− "data": {"bar": 2},
114− "valid": false
115− },
116− {
117− "description": "both properties present is invalid",
118− "data": {"foo": 1, "bar": 2},
119− "valid": false
120− }
121− ]
122− }
123−]
JSON-Schema-Test-Suite/tests/draft6/propertyNames.jsondeleted−68
@@ -1,68 +0,0 @@
1−[
2− {
3− "description": "propertyNames validation",
4− "schema": {
5− "propertyNames": {"maxLength": 3}
6− },
7− "tests": [
8− {
9− "description": "all property names valid",
10− "data": {
11− "f": {},
12− "foo": {}
13− },
14− "valid": true
15− },
16− {
17− "description": "some property names invalid",
18− "data": {
19− "foo": {},
20− "foobar": {}
21− },
22− "valid": false
23− },
24− {
25− "description": "object without properties is valid",
26− "data": {},
27− "valid": true
28− },
29− {
30− "description": "non-object is valid",
31− "data": [],
32− "valid": true
33− }
34− ]
35− },
36− {
37− "description": "propertyNames with boolean schema true",
38− "schema": {"propertyNames": true},
39− "tests": [
40− {
41− "description": "object with any properties is valid",
42− "data": {"foo": 1},
43− "valid": true
44− },
45− {
46− "description": "empty object is valid",
47− "data": {},
48− "valid": true
49− }
50− ]
51− },
52− {
53− "description": "propertyNames with boolean schema false",
54− "schema": {"propertyNames": false},
55− "tests": [
56− {
57− "description": "object with any properties is invalid",
58− "data": {"foo": 1},
59− "valid": false
60− },
61− {
62− "description": "empty object is valid",
63− "data": {},
64− "valid": true
65− }
66− ]
67− }
68−]
JSON-Schema-Test-Suite/tests/draft6/ref.jsondeleted−332
@@ -1,332 +0,0 @@
1−[
2− {
3− "description": "root pointer ref",
4− "schema": {
5− "properties": {
6− "foo": {"$ref": "#"}
7− },
8− "additionalProperties": false
9− },
10− "tests": [
11− {
12− "description": "match",
13− "data": {"foo": false},
14− "valid": true
15− },
16− {
17− "description": "recursive match",
18− "data": {"foo": {"foo": false}},
19− "valid": true
20− },
21− {
22− "description": "mismatch",
23− "data": {"bar": false},
24− "valid": false
25− },
26− {
27− "description": "recursive mismatch",
28− "data": {"foo": {"bar": false}},
29− "valid": false
30− }
31− ]
32− },
33− {
34− "description": "relative pointer ref to object",
35− "schema": {
36− "properties": {
37− "foo": {"type": "integer"},
38− "bar": {"$ref": "#/properties/foo"}
39− }
40− },
41− "tests": [
42− {
43− "description": "match",
44− "data": {"bar": 3},
45− "valid": true
46− },
47− {
48− "description": "mismatch",
49− "data": {"bar": true},
50− "valid": false
51− }
52− ]
53− },
54− {
55− "description": "relative pointer ref to array",
56− "schema": {
57− "items": [
58− {"type": "integer"},
59− {"$ref": "#/items/0"}
60− ]
61− },
62− "tests": [
63− {
64− "description": "match array",
65− "data": [1, 2],
66− "valid": true
67− },
68− {
69− "description": "mismatch array",
70− "data": [1, "foo"],
71− "valid": false
72− }
73− ]
74− },
75− {
76− "description": "escaped pointer ref",
77− "schema": {
78− "tilda~field": {"type": "integer"},
79− "slash/field": {"type": "integer"},
80− "percent%field": {"type": "integer"},
81− "properties": {
82− "tilda": {"$ref": "#/tilda~0field"},
83− "slash": {"$ref": "#/slash~1field"},
84− "percent": {"$ref": "#/percent%25field"}
85− }
86− },
87− "tests": [
88− {
89− "description": "slash invalid",
90− "data": {"slash": "aoeu"},
91− "valid": false
92− },
93− {
94− "description": "tilda invalid",
95− "data": {"tilda": "aoeu"},
96− "valid": false
97− },
98− {
99− "description": "percent invalid",
100− "data": {"percent": "aoeu"},
101− "valid": false
102− },
103− {
104− "description": "slash valid",
105− "data": {"slash": 123},
106− "valid": true
107− },
108− {
109− "description": "tilda valid",
110− "data": {"tilda": 123},
111− "valid": true
112− },
113− {
114− "description": "percent valid",
115− "data": {"percent": 123},
116− "valid": true
117− }
118− ]
119− },
120− {
121− "description": "nested refs",
122− "schema": {
123− "definitions": {
124− "a": {"type": "integer"},
125− "b": {"$ref": "#/definitions/a"},
126− "c": {"$ref": "#/definitions/b"}
127− },
128− "$ref": "#/definitions/c"
129− },
130− "tests": [
131− {
132− "description": "nested ref valid",
133− "data": 5,
134− "valid": true
135− },
136− {
137− "description": "nested ref invalid",
138− "data": "a",
139− "valid": false
140− }
141− ]
142− },
143− {
144− "description": "ref overrides any sibling keywords",
145− "schema": {
146− "definitions": {
147− "reffed": {
148− "type": "array"
149− }
150− },
151− "properties": {
152− "foo": {
153− "$ref": "#/definitions/reffed",
154− "maxItems": 2
155− }
156− }
157− },
158− "tests": [
159− {
160− "description": "ref valid",
161− "data": { "foo": [] },
162− "valid": true
163− },
164− {
165− "description": "ref valid, maxItems ignored",
166− "data": { "foo": [ 1, 2, 3] },
167− "valid": true
168− },
169− {
170− "description": "ref invalid",
171− "data": { "foo": "string" },
172− "valid": false
173− }
174− ]
175− },
176− {
177− "description": "remote ref, containing refs itself",
178− "schema": {"$ref": "http://json-schema.org/draft-04/schema#"},
179− "tests": [
180− {
181− "description": "remote ref valid",
182− "data": {"minLength": 1},
183− "valid": true
184− },
185− {
186− "description": "remote ref invalid",
187− "data": {"minLength": -1},
188− "valid": false
189− }
190− ]
191− },
192− {
193− "description": "property named $ref that is not a reference",
194− "schema": {
195− "properties": {
196− "$ref": {"type": "string"}
197− }
198− },
199− "tests": [
200− {
201− "description": "property named $ref valid",
202− "data": {"$ref": "a"},
203− "valid": true
204− },
205− {
206− "description": "property named $ref invalid",
207− "data": {"$ref": 2},
208− "valid": false
209− }
210− ]
211− },
212− {
213− "description": "$ref to boolean schema true",
214− "schema": {
215− "$ref": "#/definitions/bool",
216− "definitions": {
217− "bool": true
218− }
219− },
220− "tests": [
221− {
222− "description": "any value is valid",
223− "data": "foo",
224− "valid": true
225− }
226− ]
227− },
228− {
229− "description": "$ref to boolean schema false",
230− "schema": {
231− "$ref": "#/definitions/bool",
232− "definitions": {
233− "bool": false
234− }
235− },
236− "tests": [
237− {
238− "description": "any value is invalid",
239− "data": "foo",
240− "valid": false
241− }
242− ]
243− },
244− {
245− "description": "Recursive references between schemas",
246− "schema": {
247− "$id": "http://localhost:1234/tree",
248− "description": "tree of nodes",
249− "type": "object",
250− "properties": {
251− "meta": {"type": "string"},
252− "nodes": {
253− "type": "array",
254− "items": {"$ref": "node"}
255− }
256− },
257− "required": ["meta", "nodes"],
258− "definitions": {
259− "node": {
260− "$id": "http://localhost:1234/node",
261− "description": "node",
262− "type": "object",
263− "properties": {
264− "value": {"type": "number"},
265− "subtree": {"$ref": "tree"}
266− },
267− "required": ["value"]
268− }
269− }
270− },
271− "tests": [
272− {
273− "description": "valid tree",
274− "data": {
275− "meta": "root",
276− "nodes": [
277− {
278− "value": 1,
279− "subtree": {
280− "meta": "child",
281− "nodes": [
282− {"value": 1.1},
283− {"value": 1.2}
284− ]
285− }
286− },
287− {
288− "value": 2,
289− "subtree": {
290− "meta": "child",
291− "nodes": [
292− {"value": 2.1},
293− {"value": 2.2}
294− ]
295− }
296− }
297− ]
298− },
299− "valid": true
300− },
301− {
302− "description": "invalid tree",
303− "data": {
304− "meta": "root",
305− "nodes": [
306− {
307− "value": 1,
308− "subtree": {
309− "meta": "child",
310− "nodes": [
311− {"value": "string is invalid"},
312− {"value": 1.2}
313− ]
314− }
315− },
316− {
317− "value": 2,
318− "subtree": {
319− "meta": "child",
320− "nodes": [
321− {"value": 2.1},
322− {"value": 2.2}
323− ]
324− }
325− }
326− ]
327− },
328− "valid": false
329− }
330− ]
331− }
332−]
JSON-Schema-Test-Suite/tests/draft6/refRemote.jsondeleted−171
@@ -1,171 +0,0 @@
1−[
2− {
3− "description": "remote ref",
4− "schema": {"$ref": "http://localhost:1234/integer.json"},
5− "tests": [
6− {
7− "description": "remote ref valid",
8− "data": 1,
9− "valid": true
10− },
11− {
12− "description": "remote ref invalid",
13− "data": "a",
14− "valid": false
15− }
16− ]
17− },
18− {
19− "description": "fragment within remote ref",
20− "schema": {"$ref": "http://localhost:1234/subSchemas.json#/integer"},
21− "tests": [
22− {
23− "description": "remote fragment valid",
24− "data": 1,
25− "valid": true
26− },
27− {
28− "description": "remote fragment invalid",
29− "data": "a",
30− "valid": false
31− }
32− ]
33− },
34− {
35− "description": "ref within remote ref",
36− "schema": {
37− "$ref": "http://localhost:1234/subSchemas.json#/refToInteger"
38− },
39− "tests": [
40− {
41− "description": "ref within ref valid",
42− "data": 1,
43− "valid": true
44− },
45− {
46− "description": "ref within ref invalid",
47− "data": "a",
48− "valid": false
49− }
50− ]
51− },
52− {
53− "description": "base URI change",
54− "schema": {
55− "$id": "http://localhost:1234/",
56− "items": {
57− "$id": "folder/",
58− "items": {"$ref": "folderInteger.json"}
59− }
60− },
61− "tests": [
62− {
63− "description": "base URI change ref valid",
64− "data": [[1]],
65− "valid": true
66− },
67− {
68− "description": "base URI change ref invalid",
69− "data": [["a"]],
70− "valid": false
71− }
72− ]
73− },
74− {
75− "description": "base URI change - change folder",
76− "schema": {
77− "$id": "http://localhost:1234/scope_change_defs1.json",
78− "type" : "object",
79− "properties": {
80− "list": {"$ref": "#/definitions/baz"}
81− },
82− "definitions": {
83− "baz": {
84− "$id": "folder/",
85− "type": "array",
86− "items": {"$ref": "folderInteger.json"}
87− }
88− }
89− },
90− "tests": [
91− {
92− "description": "number is valid",
93− "data": {"list": [1]},
94− "valid": true
95− },
96− {
97− "description": "string is invalid",
98− "data": {"list": ["a"]},
99− "valid": false
100− }
101− ]
102− },
103− {
104− "description": "base URI change - change folder in subschema",
105− "schema": {
106− "$id": "http://localhost:1234/scope_change_defs2.json",
107− "type" : "object",
108− "properties": {
109− "list": {"$ref": "#/definitions/baz/definitions/bar"}
110− },
111− "definitions": {
112− "baz": {
113− "$id": "folder/",
114− "definitions": {
115− "bar": {
116− "type": "array",
117− "items": {"$ref": "folderInteger.json"}
118− }
119− }
120− }
121− }
122− },
123− "tests": [
124− {
125− "description": "number is valid",
126− "data": {"list": [1]},
127− "valid": true
128− },
129− {
130− "description": "string is invalid",
131− "data": {"list": ["a"]},
132− "valid": false
133− }
134− ]
135− },
136− {
137− "description": "root ref in remote ref",
138− "schema": {
139− "$id": "http://localhost:1234/object",
140− "type": "object",
141− "properties": {
142− "name": {"$ref": "name.json#/definitions/orNull"}
143− }
144− },
145− "tests": [
146− {
147− "description": "string is valid",
148− "data": {
149− "name": "foo"
150− },
151− "valid": true
152− },
153− {
154− "description": "null is valid",
155− "data": {
156− "name": null
157− },
158− "valid": true
159− },
160− {
161− "description": "object is invalid",
162− "data": {
163− "name": {
164− "name": null
165− }
166− },
167− "valid": false
168− }
169− ]
170− }
171−]
JSON-Schema-Test-Suite/tests/draft6/required.jsondeleted−60
@@ -1,60 +0,0 @@
1−[
2− {
3− "description": "required validation",
4− "schema": {
5− "properties": {
6− "foo": {},
7− "bar": {}
8− },
9− "required": ["foo"]
10− },
11− "tests": [
12− {
13− "description": "present required property is valid",
14− "data": {"foo": 1},
15− "valid": true
16− },
17− {
18− "description": "non-present required property is invalid",
19− "data": {"bar": 1},
20− "valid": false
21− },
22− {
23− "description": "ignores non-objects",
24− "data": 12,
25− "valid": true
26− }
27− ]
28− },
29− {
30− "description": "required default validation",
31− "schema": {
32− "properties": {
33− "foo": {}
34− }
35− },
36− "tests": [
37− {
38− "description": "not required by default",
39− "data": {},
40− "valid": true
41− }
42− ]
43− },
44− {
45− "description": "required with empty array",
46− "schema": {
47− "properties": {
48− "foo": {}
49− },
50− "required": []
51− },
52− "tests": [
53− {
54− "description": "property not required",
55− "data": {},
56− "valid": true
57− }
58− ]
59− }
60−]
JSON-Schema-Test-Suite/tests/draft6/type.jsondeleted−345
@@ -1,345 +0,0 @@
1−[
2− {
3− "description": "integer type matches integers",
4− "schema": {"type": "integer"},
5− "tests": [
6− {
7− "description": "an integer is an integer",
8− "data": 1,
9− "valid": true
10− },
11− {
12− "description": "a float is not an integer",
13− "data": 1.1,
14− "valid": false
15− },
16− {
17− "description": "a string is not an integer",
18− "data": "foo",
19− "valid": false
20− },
21− {
22− "description": "a string is still not an integer, even if it looks like one",
23− "data": "1",
24− "valid": false
25− },
26− {
27− "description": "an object is not an integer",
28− "data": {},
29− "valid": false
30− },
31− {
32− "description": "an array is not an integer",
33− "data": [],
34− "valid": false
35− },
36− {
37− "description": "a boolean is not an integer",
38− "data": true,
39− "valid": false
40− },
41− {
42− "description": "null is not an integer",
43− "data": null,
44− "valid": false
45− }
46− ]
47− },
48− {
49− "description": "number type matches numbers",
50− "schema": {"type": "number"},
51− "tests": [
52− {
53− "description": "an integer is a number",
54− "data": 1,
55− "valid": true
56− },
57− {
58− "description": "a float is a number",
59− "data": 1.1,
60− "valid": true
61− },
62− {
63− "description": "a string is not a number",
64− "data": "foo",
65− "valid": false
66− },
67− {
68− "description": "a string is still not a number, even if it looks like one",
69− "data": "1",
70− "valid": false
71− },
72− {
73− "description": "an object is not a number",
74− "data": {},
75− "valid": false
76− },
77− {
78− "description": "an array is not a number",
79− "data": [],
80− "valid": false
81− },
82− {
83− "description": "a boolean is not a number",
84− "data": true,
85− "valid": false
86− },
87− {
88− "description": "null is not a number",
89− "data": null,
90− "valid": false
91− }
92− ]
93− },
94− {
95− "description": "string type matches strings",
96− "schema": {"type": "string"},
97− "tests": [
98− {
99− "description": "1 is not a string",
100− "data": 1,
101− "valid": false
102− },
103− {
104− "description": "a float is not a string",
105− "data": 1.1,
106− "valid": false
107− },
108− {
109− "description": "a string is a string",
110− "data": "foo",
111− "valid": true
112− },
113− {
114− "description": "a string is still a string, even if it looks like a number",
115− "data": "1",
116− "valid": true
117− },
118− {
119− "description": "an object is not a string",
120− "data": {},
121− "valid": false
122− },
123− {
124− "description": "an array is not a string",
125− "data": [],
126− "valid": false
127− },
128− {
129− "description": "a boolean is not a string",
130− "data": true,
131− "valid": false
132− },
133− {
134− "description": "null is not a string",
135− "data": null,
136− "valid": false
137− }
138− ]
139− },
140− {
141− "description": "object type matches objects",
142− "schema": {"type": "object"},
143− "tests": [
144− {
145− "description": "an integer is not an object",
146− "data": 1,
147− "valid": false
148− },
149− {
150− "description": "a float is not an object",
151− "data": 1.1,
152− "valid": false
153− },
154− {
155− "description": "a string is not an object",
156− "data": "foo",
157− "valid": false
158− },
159− {
160− "description": "an object is an object",
161− "data": {},
162− "valid": true
163− },
164− {
165− "description": "an array is not an object",
166− "data": [],
167− "valid": false
168− },
169− {
170− "description": "a boolean is not an object",
171− "data": true,
172− "valid": false
173− },
174− {
175− "description": "null is not an object",
176− "data": null,
177− "valid": false
178− }
179− ]
180− },
181− {
182− "description": "array type matches arrays",
183− "schema": {"type": "array"},
184− "tests": [
185− {
186− "description": "an integer is not an array",
187− "data": 1,
188− "valid": false
189− },
190− {
191− "description": "a float is not an array",
192− "data": 1.1,
193− "valid": false
194− },
195− {
196− "description": "a string is not an array",
197− "data": "foo",
198− "valid": false
199− },
200− {
201− "description": "an object is not an array",
202− "data": {},
203− "valid": false
204− },
205− {
206− "description": "an array is an array",
207− "data": [],
208− "valid": true
209− },
210− {
211− "description": "a boolean is not an array",
212− "data": true,
213− "valid": false
214− },
215− {
216− "description": "null is not an array",
217− "data": null,
218− "valid": false
219− }
220− ]
221− },
222− {
223− "description": "boolean type matches booleans",
224− "schema": {"type": "boolean"},
225− "tests": [
226− {
227− "description": "an integer is not a boolean",
228− "data": 1,
229− "valid": false
230− },
231− {
232− "description": "a float is not a boolean",
233− "data": 1.1,
234− "valid": false
235− },
236− {
237− "description": "a string is not a boolean",
238− "data": "foo",
239− "valid": false
240− },
241− {
242− "description": "an object is not a boolean",
243− "data": {},
244− "valid": false
245− },
246− {
247− "description": "an array is not a boolean",
248− "data": [],
249− "valid": false
250− },
251− {
252− "description": "a boolean is a boolean",
253− "data": true,
254− "valid": true
255− },
256− {
257− "description": "null is not a boolean",
258− "data": null,
259− "valid": false
260− }
261− ]
262− },
263− {
264− "description": "null type matches only the null object",
265− "schema": {"type": "null"},
266− "tests": [
267− {
268− "description": "an integer is not null",
269− "data": 1,
270− "valid": false
271− },
272− {
273− "description": "a float is not null",
274− "data": 1.1,
275− "valid": false
276− },
277− {
278− "description": "a string is not null",
279− "data": "foo",
280− "valid": false
281− },
282− {
283− "description": "an object is not null",
284− "data": {},
285− "valid": false
286− },
287− {
288− "description": "an array is not null",
289− "data": [],
290− "valid": false
291− },
292− {
293− "description": "a boolean is not null",
294− "data": true,
295− "valid": false
296− },
297− {
298− "description": "null is null",
299− "data": null,
300− "valid": true
301− }
302− ]
303− },
304− {
305− "description": "multiple types can be specified in an array",
306− "schema": {"type": ["integer", "string"]},
307− "tests": [
308− {
309− "description": "an integer is valid",
310− "data": 1,
311− "valid": true
312− },
313− {
314− "description": "a string is valid",
315− "data": "foo",
316− "valid": true
317− },
318− {
319− "description": "a float is invalid",
320− "data": 1.1,
321− "valid": false
322− },
323− {
324− "description": "an object is invalid",
325− "data": {},
326− "valid": false
327− },
328− {
329− "description": "an array is invalid",
330− "data": [],
331− "valid": false
332− },
333− {
334− "description": "a boolean is invalid",
335− "data": true,
336− "valid": false
337− },
338− {
339− "description": "null is invalid",
340− "data": null,
341− "valid": false
342− }
343− ]
344− }
345−]
JSON-Schema-Test-Suite/tests/draft6/uniqueItems.jsondeleted−79
@@ -1,79 +0,0 @@
1−[
2− {
3− "description": "uniqueItems validation",
4− "schema": {"uniqueItems": true},
5− "tests": [
6− {
7− "description": "unique array of integers is valid",
8− "data": [1, 2],
9− "valid": true
10− },
11− {
12− "description": "non-unique array of integers is invalid",
13− "data": [1, 1],
14− "valid": false
15− },
16− {
17− "description": "numbers are unique if mathematically unequal",
18− "data": [1.0, 1.00, 1],
19− "valid": false
20− },
21− {
22− "description": "unique array of objects is valid",
23− "data": [{"foo": "bar"}, {"foo": "baz"}],
24− "valid": true
25− },
26− {
27− "description": "non-unique array of objects is invalid",
28− "data": [{"foo": "bar"}, {"foo": "bar"}],
29− "valid": false
30− },
31− {
32− "description": "unique array of nested objects is valid",
33− "data": [
34− {"foo": {"bar" : {"baz" : true}}},
35− {"foo": {"bar" : {"baz" : false}}}
36− ],
37− "valid": true
38− },
39− {
40− "description": "non-unique array of nested objects is invalid",
41− "data": [
42− {"foo": {"bar" : {"baz" : true}}},
43− {"foo": {"bar" : {"baz" : true}}}
44− ],
45− "valid": false
46− },
47− {
48− "description": "unique array of arrays is valid",
49− "data": [["foo"], ["bar"]],
50− "valid": true
51− },
52− {
53− "description": "non-unique array of arrays is invalid",
54− "data": [["foo"], ["foo"]],
55− "valid": false
56− },
57− {
58− "description": "1 and true are unique",
59− "data": [1, true],
60− "valid": true
61− },
62− {
63− "description": "0 and false are unique",
64− "data": [0, false],
65− "valid": true
66− },
67− {
68− "description": "unique heterogeneous types are valid",
69− "data": [{}, [1], true, null, 1],
70− "valid": true
71− },
72− {
73− "description": "non-unique heterogeneous types are invalid",
74− "data": [{}, [1], true, null, {}, 1],
75− "valid": false
76− }
77− ]
78− }
79−]
README.md+50−10
@@ -1,25 +1,65 @@
1−# DEPRECATION NOTICE
1+![hjsonschema logo](./logo.jpg)
22
3−`hjsonschema` was an attempt to build a very modular JSON Schema library. Validators have [a concrete type](src/JSONSchema/Validator/Types.hs) and can be mixed and matched into new [Specs](src/JSONSchema/Types.hs).
3+A Haskell implementation of the most commonly used [JSON Schema](http://json-schema.org/) specification ([Draft 4](https://github.com/json-schema-org/json-schema-spec/wiki/Specification-Links#draft-4)).
44
5−However this flexibility came at the price of complicating the code. I don't think it was the right tradeoff, especially since situations where you'd want to change what validators make up a `Spec` at runtime seem rare.
5+[Hackage](https://hackage.haskell.org/package/hjsonschema) / [GitHub](https://github.com/seagreen/hjsonschema) / [Travis CI](https://travis-ci.org/seagreen/hjsonschema)
66
7−Also, there are many parts of JSON Schema that `hjsonschema` doesn't implement properly (as you can see from the issue tracker). I'm hoping that a new JSON Schema library will come along that handles these correctly. In the meantime I'm happy to merge working fixes into here.
7+# Notes
88
9−# Links
9++ As of 2017 [json-schema-org](https://github.com/json-schema-org/json-schema-spec) has begun releasing new drafts of the standard. Once this work stabilizes `hjsonschema` will add coverage for the latest draft.
1010
11−[Hackage](https://hackage.haskell.org/package/hjsonschema) / [GitHub](https://github.com/seagreen/hjsonschema) / [Travis CI](https://travis-ci.org/seagreen/hjsonschema)
11++ Requires [pcre](http://www.pcre.org/) (`pkgs.pcre` in Nixpkgs).
12+
13++ Schemas with circular references can cause infinite loops. hjsonschema does loop detection but it may not be solid yet -- please open an issue if you find a situation where it fails.
1214
1315# Example
1416
1517See [here](https://github.com/seagreen/hjsonschema/blob/master/examples/Simple.hs).
1618
17−# System dependencies
19+# Tests
1820
19−+ Requires [pcre](http://www.pcre.org/) (`pkgs.pcre` in Nixpkgs).
21+Run all tests:
22+
23+`stack test`
24+
25+Run only local tests:
26+
27+`stack test hjsonschema:local`
28+
29+Run remote tests (makes GETs to json-schema.org, also temporarily starts an HTTP server on port 1234):
30+
31+`stack test hjsonschema:remote`
32+
33+# Details
34+
35+## Goals
36+
37++ Be a correct and fast implementation of the spec.
38+
39++ Be a useful reference for implementers in other languages. Haskell's high level nature, expressive type system and referential transparency suit this purpose well.
40+
41+## Good Parts
42+
43++ Passes all the required tests in the [language agnostic test suite](https://github.com/json-schema/JSON-Schema-Test-Suite).
44+
45++ Very modular, which should make it easy to support future versions of the specification.
46+
47+## Bad Parts
48+
49++ Uses the [pcre-heavy](https://hackage.haskell.org/package/pcre-heavy) regular expression library for the "pattern" validator. It should use a library based on the ECMA 262 regex dialect, which the [spec](http://json-schema.org/latest/json-schema-validation.html#anchor33) requires.
50+
51++ Currently doesn't support the optional `"format"` validators.
2052
2153## Vendoring
2254
23−+ `JSON-Schema-Test-Suite` is vendored from commit # c1b12bf699f29a04b4286711c6e3bbfba66f21e5 [here](https://github.com/json-schema-org/JSON-Schema-Test-Suite).
55++ `JSON-Schema-Test-Suite` is vendored from commit # aabcb3427745ade7a0b4d49ff016ad7eda8b898b [here](https://github.com/json-schema-org/JSON-Schema-Test-Suite).
56+
57++ `src/draft4.json` is from commit # f3d5aeb5ffbe9d9a5a0ceb761dc47c7c4c2efa68 [here](https://github.com/json-schema/json-schema).
58+
59+## Credits
60+
61+[TJ Weigel](http://tjweigel.com/) created the logo.
62+
63+[Tim Baumann](https://github.com/timjb) wrote [aeson-schema](https://hackage.haskell.org/package/aeson-schema), on which hjsonschema's test code and its implementation of `SchemaGraph` were based.
2464
25−+ `src/draft4.json` is from commit # c1b12bf699f29a04b4286711c6e3bbfba66f21e5 [here](https://github.com/json-schema/json-schema). The [root ref in remote ref](./JSON-Schema-Test-Suite/tests/draft4/refRemote.json) test has been modified to fix [#175](https://github.com/json-schema-org/JSON-Schema-Test-Suite/issues/175).
65+[Julian Berman](https://github.com/Julian) maintains the fantastic [language agnostic test suite](https://github.com/json-schema/JSON-Schema-Test-Suite).
changelog.md−54
@@ -1,57 +1,3 @@
1−# 1.8.0
2−
3−+ Add GHC 8.4 support (thanks @4e6 !).
4−+ Drop GHC 7.10 support.
5−+ Fix JSON Pointer resolution error.
6−
7−# 1.8.0
8−
9−+ Allow HTTPS references (thanks @creichert!).
10−+ Use `safe-exceptions` to eliminate the risk of catching asynchronous exceptions.
11−
12−# 1.7.2
13−
14−+ Remove upper bounds.
15−
16−# 1.7.1
17−
18−+ Bump http-types.
19−
20−# 1.7.0
21−
22−+ Test with GHC 8.2. Drop GHC 7.8.
23−+ Rework `allUniqueValues` related utility functions.
24−
25−# 1.6.3
26−
27−+ Bump hjsonpointer and QuickCheck.
28−
29−# 1.6.2
30−
31−+ Bump aeson.
32−
33−# 1.6.1
34−
35−+ Fix Haddocks.
36−
37−# 1.6.0
38−
39−+ Fix defect where validators alongside "$ref" weren't ignored.
40−
41−+ Fix defect where local references would fail if an "id" key had set resolution scope to start from a different document.
42−
43−+ Vendor latest tests.
44−
45−+ Remove `ReferencedSchemas`.
46−
47−+ Create `Scope` to hold information that changes during validation.
48−
49−+ Use a sum type for "type" values. Thanks to Philip Weaver (GitHub @pheaver).
50−
51−# 1.5.0.1
52−
53−+ Raise test dep upper bounds.
54−
551# 1.5.0.0
562
573+ Report details of `"required"` validator failure.
examples/AlternateSchema.hs+57−86
@@ -5,24 +5,27 @@
55-- to copy this module instead of the 'JSONSchema.Draft4'. While it's
66-- less convenient to write schemas in Haskell without a record type, you
77-- can get the implementation finished with far fewer lines of code.
8+
89module AlternateSchema where
910
1011import Protolude
1112
12−import Data.Aeson (FromJSON(..), Value(..), decodeStrict)
13−import qualified Data.Aeson as AE
14−import qualified Data.HashMap.Strict as HM
15−import Data.Maybe (fromMaybe)
16−import Data.Profunctor (Profunctor(..))
17−
18−import JSONSchema.Draft4 (ValidatorFailure(..), metaSchemaBytes)
19−import JSONSchema.Fetch (SchemaWithURI(..), URISchemaMap(..))
20−import qualified JSONSchema.Fetch as FE
21−import JSONSchema.Types (Schema(..), Spec(..))
22−import qualified JSONSchema.Types as JT
23−import qualified JSONSchema.Validator.Draft4 as D4
24−import JSONSchema.Validator.Reference (BaseURI(..), Scope(..),
25− updateResolutionScope)
13+import Data.Aeson (FromJSON(..), Value(..),
14+ decodeStrict)
15+import qualified Data.Aeson as AE
16+import qualified Data.HashMap.Strict as HM
17+import Data.Maybe (fromMaybe)
18+import Data.Profunctor (Profunctor (..))
19+
20+import JSONSchema.Draft4 (ValidatorFailure(..),
21+ metaSchemaBytes)
22+import JSONSchema.Fetch (ReferencedSchemas(..),
23+ SchemaWithURI(..))
24+import qualified JSONSchema.Fetch as FE
25+import JSONSchema.Types (Schema(..), Spec(..))
26+import qualified JSONSchema.Types as JT
27+import qualified JSONSchema.Validator.Draft4 as D4
28+import JSONSchema.Validator.Reference (updateResolutionScope)
2629
2730--------------------------------------------------
2831-- * Basic fetching tools
@@ -42,38 +45,22 @@ draft4FetchInfo = FE.FetchInfo embedded (lookup "id") (lookup "$ref")
4245 Just (String t) -> Just t
4346 _ -> Nothing
4447
45−-- | An implementation of 'JT.embedded'.
4648embedded :: Schema -> ([Schema], [Schema])
47−embedded s =
48− JT.embedded (d4Spec mempty mempty (Scope s Nothing (BaseURI Nothing))) s
49+embedded s = JT.embedded (d4Spec (ReferencedSchemas s mempty) mempty Nothing) s
4950
5051--------------------------------------------------
5152-- * Main API
5253--------------------------------------------------
5354
5455validate
55− :: URISchemaMap Schema
56− -> SchemaWithURI Schema
56+ :: ReferencedSchemas Schema
57+ -> Maybe Text
58+ -> Schema
5759 -> Value
5860 -> [ValidatorFailure]
59−validate schemaMap sw =
60− JT.validate (d4Spec schemaMap visited scope) (_swSchema sw)
61− where
62− visited :: D4.VisitedSchemas
63− visited = D4.VisitedSchemas [(Nothing, Nothing)]
61+validate rs = continueValidating rs (D4.VisitedSchemas [(Nothing, Nothing)])
6462
65− schemaId :: Maybe Text
66− schemaId = FE._fiId draft4FetchInfo (_swSchema sw)
67−
68− scope :: Scope Schema
69− scope = Scope
70− { _topLevelDocument = _swSchema sw
71− , _documentURI = _swURI sw
72− , _currentBaseURI = updateResolutionScope (BaseURI (_swURI sw))
73− schemaId
74− }
75−
76−-- | A schema for schemas themselves. Uses @src/draft4.json@ which is loaded
63+-- A schema for schemas themselves, using @src/draft4.json@ which is loaded
7764-- at compile time.
7865metaSchema :: Schema
7966metaSchema =
@@ -82,57 +69,47 @@ metaSchema =
8269 $ metaSchemaBytes
8370
8471checkSchema :: Schema -> [ValidatorFailure]
85−checkSchema = validate schemaMap (SchemaWithURI metaSchema Nothing)
86− . Object
87− . _unSchema
72+checkSchema = validate referenced Nothing metaSchema . Object . _unSchema
8873 where
89− schemaMap :: URISchemaMap Schema
90− schemaMap =
91− URISchemaMap (HM.singleton "http://json-schema.org/draft-04/schema"
74+ referenced :: ReferencedSchemas Schema
75+ referenced = ReferencedSchemas
76+ metaSchema
77+ (HM.singleton "http://json-schema.org/draft-04/schema"
9278 metaSchema)
9379
9480--------------------------------------------------
9581-- * Spec
9682--------------------------------------------------
9783
98−validateSubschema
99− :: URISchemaMap Schema
84+continueValidating
85+ :: ReferencedSchemas Schema
10086 -> D4.VisitedSchemas
101− -> Scope Schema
87+ -> Maybe Text
10288 -> Schema
10389 -> Value
10490 -> [ValidatorFailure]
105−validateSubschema schemaMap visited scope schema =
106− JT.validate (d4Spec schemaMap visited newScope) schema
91+continueValidating referenced visited mURI sc =
92+ JT.validate (d4Spec referenced visited newScope) sc
10793 where
10894 schemaId :: Maybe Text
109− schemaId = FE._fiId draft4FetchInfo schema
95+ schemaId = case HM.lookup "id" (_unSchema sc) of
96+ Just (String t) -> Just t
97+ _ -> Nothing
11098
111− newScope :: Scope Schema
112− newScope = scope
113− { _currentBaseURI = updateResolutionScope (_currentBaseURI scope)
114− schemaId
115− }
99+ newScope :: Maybe Text
100+ newScope = updateResolutionScope mURI schemaId
116101
117102d4Spec
118− :: URISchemaMap Schema
103+ :: ReferencedSchemas Schema
119104 -> D4.VisitedSchemas
120− -> Scope Schema
105+ -> Maybe Text
121106 -> Spec Schema ValidatorFailure
122107 -- ^ Here we reuses 'ValidatorFailure' from
123108 -- 'JSONSchema.Draft4.Failure'. If your validators have different
124109 -- failure possibilities you'll need to create your own validator
125110 -- failure type.
126−d4Spec schemaMap visited scope =
127− Spec $
128− [ dimap
129− f
130− FailureRef
131− (D4.refValidator (FE.getReference schemaMap) updateScope
132− valRef visited scope)
133− ]
134−
135− <> fmap (lmap disableIfRefPresent)
111+d4Spec referenced visited scope =
112+ Spec
136113 [ dimap f FailureMultipleOf D4.multipleOfValidator
137114 , dimap f FailureMaximum D4.maximumValidator
138115 , dimap f FailureMinimum D4.minimumValidator
@@ -150,7 +127,6 @@ d4Spec schemaMap visited scope =
150127 D4.IRInvalidItems e -> FailureItems e
151128 D4.IRInvalidAdditional e -> FailureAdditionalItems e)
152129 (D4.itemsRelatedValidator descend)
153− , lmap f D4.definitionsEmbedded
154130
155131 , dimap f FailureMaxProperties D4.maxPropertiesValidator
156132 , dimap f FailureMinProperties D4.minPropertiesValidator
@@ -161,6 +137,10 @@ d4Spec schemaMap visited scope =
161137 FailurePropertiesRelated
162138 (D4.propertiesRelatedValidator descend)
163139
140+ , dimap
141+ f
142+ FailureRef
143+ (D4.refValidator visited scope (FE.getReference referenced) getRef)
164144 , dimap f FailureEnum D4.enumValidator
165145 , dimap f FailureType D4.typeValidator
166146 , dimap f FailureAllOf (D4.allOfValidator lateral)
@@ -170,31 +150,22 @@ d4Spec schemaMap visited scope =
170150 ]
171151 where
172152 f :: FromJSON a => Schema -> Maybe a
173− f (Schema a) =
174− case AE.fromJSON (Object a) of
175− AE.Error _ -> Nothing
176− AE.Success b -> Just b
177−
178− disableIfRefPresent :: Schema -> Schema
179− disableIfRefPresent schema =
180− case FE._fiRef draft4FetchInfo schema of
181− Nothing -> schema
182− Just _ -> Schema mempty
183−
184− updateScope :: BaseURI -> Schema -> BaseURI
185− updateScope uri schema =
186− updateResolutionScope uri (FE._fiId draft4FetchInfo schema)
187−
188− valRef
153+ f (Schema a) = case AE.fromJSON (Object a) of
154+ AE.Error _ -> Nothing
155+ AE.Success b -> Just b
156+
157+ -- 'Maybe Text' is the URI the referenced schema is fetched from,
158+ -- this probably needs a 'newtype' wrapper.
159+ getRef
189160 :: D4.VisitedSchemas
190− -> Scope Schema
161+ -> Maybe Text
191162 -> Schema
192163 -> Value
193164 -> [ValidatorFailure]
194− valRef vis sc = JT.validate (d4Spec schemaMap vis sc)
165+ getRef = continueValidating referenced
195166
196167 descend :: Schema -> Value -> [ValidatorFailure]
197− descend = validateSubschema schemaMap mempty scope
168+ descend = continueValidating referenced mempty scope
198169
199170 lateral :: Schema -> Value -> [ValidatorFailure]
200− lateral = validateSubschema schemaMap visited scope
171+ lateral = continueValidating referenced visited scope
examples/Simple.hs+5−4
@@ -1,13 +1,14 @@
1+
12module Simple where
23
34import Protolude
45
5−import Data.Aeson (Value(..), decodeStrict, toJSON)
6−import qualified Data.ByteString as BS
6+import Data.Aeson (Value(..), decodeStrict, toJSON)
7+import qualified Data.ByteString as BS
78import qualified Data.List.NonEmpty as NE
8−import Data.Maybe (fromMaybe)
9+import Data.Maybe (fromMaybe)
910
10−import qualified JSONSchema.Draft4 as D4
11+import qualified JSONSchema.Draft4 as D4
1112
1213badData :: Value
1314badData = toJSON [True, True]
examples/TwoStep.hs+4−3
@@ -10,14 +10,15 @@
1010-- 'fetchHTTPAndValidate' which fetched references over HTTP (though it
1111-- didn't matter because the last schema didn't actually have any).
1212-- This time we need to get them from the filesystem.
13+
1314module TwoStep where
1415
1516import Protolude
1617
17−import Data.Aeson (Value(..), toJSON)
18−import qualified Data.List.NonEmpty as NE
18+import Data.Aeson (Value (..), toJSON)
19+import qualified Data.List.NonEmpty as NE
1920
20−import qualified JSONSchema.Draft4 as D4
21+import qualified JSONSchema.Draft4 as D4
2122import qualified JSONSchema.Validator.Draft4 as VAL
2223
2324schema :: D4.Schema
hjsonschema.cabal+29−25
@@ -1,5 +1,5 @@
11name: hjsonschema
2−version: 1.9.0
2+version: 1.5.0.0
33synopsis: JSON Schema library
44homepage: https://github.com/seagreen/hjsonschema
55license: MIT
@@ -9,8 +9,6 @@ maintainer: ian@housejeffries.com
99category: Data
1010build-type: Simple
1111cabal-version: >=1.10
12−-- Rerun multi-ghc-travis (executable make-travis-yml-2) after changing:
13−Tested-With: GHC == 8.0.2, GHC == 8.2.2, GHC == 8.4.1
1412extra-source-files:
1513 changelog.md
1614 JSON-Schema-Test-Suite/remotes/*.json
@@ -34,6 +32,7 @@ library
3432 NoImplicitPrelude
3533 OverloadedStrings
3634 ScopedTypeVariables
35+ TupleSections
3736 if impl(ghc >= 8)
3837 default-extensions: StrictData
3938 ghc-options:
@@ -58,28 +57,27 @@ library
5857 JSONSchema.Validator.Draft4.Object.Properties
5958 , Import
6059 build-depends:
61− base >= 4.7 && < 5
60+ base >= 4.7 && < 4.10
6261 -- 0.11 is for `.:!`:
63− , aeson >= 0.11
64− , bytestring >= 0.10
65− , containers >= 0.5
66− , file-embed >= 0.0.8
67− , filepath >= 1.3
68− , hashable >= 1.2
69− , hjsonpointer >= 1.1
62+ , aeson >= 0.11 && < 1.2
63+ , bytestring >= 0.10 && < 0.11
64+ , containers >= 0.5 && < 0.6
65+ , file-embed >= 0.0.8 && < 0.1
66+ , filepath >= 1.3 && < 1.5
67+ , hashable >= 1.2 && < 1.3
68+ , hjsonpointer >= 1.1 && < 1.2
7069 -- 0.4.30 is for parseUrlThrow:
71− , http-client >= 0.4.30
72− , http-client-tls >= 0.3
73− , http-types >= 0.8
74− , pcre-heavy >= 1.0
75− , profunctors >= 5.0
76− , protolude >= 0.1.10
77− , QuickCheck >= 2.8
78− , safe-exceptions >= 0.1.6
79− , scientific >= 0.3
80− , unordered-containers >= 0.2
81− , text >= 1.1
82− , vector >= 0.10
70+ , http-client >= 0.4.30 && < 0.6
71+ , http-types >= 0.8 && < 0.10
72+ , pcre-heavy >= 1.0 && < 1.1
73+ , profunctors >= 5.0 && < 5.3
74+ , protolude >= 0.1.10 && < 1.2
75+ , QuickCheck >= 2.8 && < 2.10
76+ , scientific >= 0.3 && < 0.4
77+ , semigroups >= 0.18 && < 0.19
78+ , unordered-containers >= 0.2 && < 0.3
79+ , text >= 1.1 && < 1.3
80+ , vector >= 0.10 && < 1.0
8381
8482test-suite local
8583 hs-source-dirs:
@@ -114,14 +112,15 @@ test-suite local
114112 , hjsonschema
115113 , profunctors
116114 , protolude
115+ , semigroups
117116 , text
118117 , QuickCheck
119118 , unordered-containers
120119 , vector
121120
122121 -- directory-1.2.5 required for `listDirectory`:
123− , directory >= 1.2.5
124− , hspec >= 2.2
122+ , directory >= 1.2.5 && < 1.4
123+ , hspec >= 2.2 && < 2.4
125124
126125test-suite remote
127126 hs-source-dirs:
@@ -152,6 +151,7 @@ test-suite remote
152151 , hjsonschema
153152 , profunctors
154153 , protolude
154+ , semigroups
155155 , text
156156 , unordered-containers
157157 , vector
@@ -160,3 +160,7 @@ test-suite remote
160160 , hspec
161161 , wai-app-static
162162 , warp
163+
164+source-repository head
165+ type: git
166+ location: git://github.com/seagreen/hjsonschema.git
logo.jpgnew file

Binary file not shown.

shell.nix+3−5
@@ -1,15 +1,13 @@
1−{ghc}:
21with (import <nixpkgs> {});
32
43haskell.lib.buildStackProject {
54 name = "none";
65 inherit ghc;
76 buildInputs = [
7+ pkgconfig
88 pcre
99
10− git # for `git:` references in stack.yml.
11− ncurses # for intero
12− pkgconfig
13− zlib
10+ # for `git:` references in stack.yml:
11+ git
1412 ];
1513}
src/Import.hs+8−15
@@ -1,19 +1,12 @@
11
2−module Import (module Export, fromJSONEither) where
2+module Import (module Export) where
33
4−import Protolude as Export
4+import Protolude as Export
55
6−import Data.Aeson as Export
6+import Data.Aeson as Export
77import Data.HashMap.Strict as Export (HashMap)
8−import Data.List.NonEmpty as Export (NonEmpty)
9−import Data.Vector as Export (Vector)
10−import Test.QuickCheck as Export hiding (Failure, Result, Success,
11− (.&.))
12−
13−import qualified Data.Text as T
14−
15−fromJSONEither :: FromJSON a => Value -> Either Text a
16−fromJSONEither a =
17− case fromJSON a of
18− Error e -> Left (T.pack e)
19− Success b -> Right b
8+import Data.List as Export (length, null) -- for older GHCs
9+import Data.List.NonEmpty as Export (NonEmpty)
10+import Data.Vector as Export (Vector)
11+import Test.QuickCheck as Export hiding ((.&.), Failure,
12+ Result, Success)
src/JSONSchema/Draft4.hs+30−21
@@ -22,7 +22,8 @@ module JSONSchema.Draft4
2222 , ValidatorFailure(..)
2323
2424 -- * Fetching tools
25− , URISchemaMap(..)
25+ , ReferencedSchemas(..)
26+ , FE.URISchemaMap(..)
2627 , referencesViaHTTP
2728 , referencesViaFilesystem
2829
@@ -37,19 +38,23 @@ module JSONSchema.Draft4
3738
3839import Import
3940
40−import qualified Data.ByteString as BS
41−import Data.FileEmbed (embedFile, makeRelativeToProject)
42−import qualified Data.HashMap.Strict as HM
43−import qualified Data.List.NonEmpty as NE
44−import Data.Maybe (fromMaybe)
41+import Control.Arrow (left)
42+import qualified Data.ByteString as BS
43+import Data.FileEmbed (embedFile,
44+ makeRelativeToProject)
45+import qualified Data.HashMap.Strict as HM
46+import qualified Data.List.NonEmpty as NE
47+import Data.Maybe (fromMaybe)
4548
46−import JSONSchema.Draft4.Failure (Invalid(..), SchemaInvalid(..),
49+import JSONSchema.Draft4.Failure (Invalid(..),
50+ SchemaInvalid(..),
4751 ValidatorFailure(..))
48−import JSONSchema.Draft4.Schema (Schema)
49−import qualified JSONSchema.Draft4.Schema as SC
50−import qualified JSONSchema.Draft4.Spec as Spec
51−import JSONSchema.Fetch (SchemaWithURI(..), URISchemaMap(..))
52−import qualified JSONSchema.Fetch as FE
52+import JSONSchema.Draft4.Schema (Schema)
53+import qualified JSONSchema.Draft4.Schema as SC
54+import qualified JSONSchema.Draft4.Spec as Spec
55+import JSONSchema.Fetch (ReferencedSchemas(..),
56+ SchemaWithURI(..))
57+import qualified JSONSchema.Fetch as FE
5358
5459data HTTPValidationFailure
5560 = HVRequest FE.HTTPFailure
@@ -65,11 +70,11 @@ fetchHTTPAndValidate
6570 -> IO (Either HTTPValidationFailure ())
6671fetchHTTPAndValidate sw v = do
6772 res <- referencesViaHTTP sw
68− pure (g =<< f =<< first HVRequest res)
73+ pure (g =<< f =<< left HVRequest res)
6974 where
7075 f :: FE.URISchemaMap Schema
7176 -> Either HTTPValidationFailure (Value -> [ValidatorFailure])
72− f references = first HVSchema (checkSchema references sw)
77+ f references = left HVSchema (checkSchema references sw)
7378
7479 g :: (Value -> [ValidatorFailure]) -> Either HTTPValidationFailure ()
7580 g val = case NE.nonEmpty (val v) of
@@ -95,11 +100,11 @@ fetchFilesystemAndValidate
95100 -> IO (Either FilesystemValidationFailure ())
96101fetchFilesystemAndValidate sw v = do
97102 res <- referencesViaFilesystem sw
98− pure (g =<< f =<< first FVRead res)
103+ pure (g =<< f =<< left FVRead res)
99104 where
100105 f :: FE.URISchemaMap Schema
101106 -> Either FilesystemValidationFailure (Value -> [ValidatorFailure])
102− f references = first FVSchema (checkSchema references sw)
107+ f references = left FVSchema (checkSchema references sw)
103108
104109 g :: (Value -> [ValidatorFailure]) -> Either FilesystemValidationFailure ()
105110 g val = case NE.nonEmpty (val v) of
@@ -138,7 +143,10 @@ checkSchema
138143checkSchema sm sw =
139144 case NE.nonEmpty failures of
140145 Just fs -> Left (SchemaInvalid fs)
141− Nothing -> Right (Spec.specValidate sm sw)
146+ Nothing -> Right (Spec.specValidate
147+ (ReferencedSchemas (_swSchema sw)
148+ (FE._unURISchemaMap sm))
149+ sw)
142150 where
143151 failures :: [(Maybe Text, NonEmpty ValidatorFailure)]
144152 failures =
@@ -161,11 +169,12 @@ metaSchemaBytes =
161169-- (if so the returned list will be empty).
162170schemaValidity :: Schema -> [ValidatorFailure]
163171schemaValidity =
164− Spec.specValidate schemaMap (SchemaWithURI metaSchema Nothing) . toJSON
172+ Spec.specValidate referenced (SchemaWithURI metaSchema Nothing) . toJSON
165173 where
166− schemaMap :: URISchemaMap Schema
167− schemaMap =
168− URISchemaMap (HM.singleton "http://json-schema.org/draft-04/schema"
174+ referenced :: ReferencedSchemas Schema
175+ referenced = ReferencedSchemas
176+ metaSchema
177+ (HM.singleton "http://json-schema.org/draft-04/schema"
169178 metaSchema)
170179
171180-- | Check that a set of referenced schemas are valid
src/JSONSchema/Draft4/Failure.hs+2−1
@@ -1,8 +1,9 @@
1+
12module JSONSchema.Draft4.Failure where
23
34import Import
45
5−import JSONSchema.Draft4.Schema (Schema)
6+import JSONSchema.Draft4.Schema (Schema)
67import qualified JSONSchema.Validator.Draft4 as VAL
78
89-- | Used to report an entire instance being invalidated, as opposed
src/JSONSchema/Draft4/Schema.hs+7−6
@@ -1,13 +1,14 @@
1+
12module JSONSchema.Draft4.Schema where
23
3−import Import hiding (mapMaybe)
4+import Import hiding (mapMaybe)
45
5−import qualified Data.HashMap.Strict as HM
6−import Data.List.NonEmpty (NonEmpty)
7−import Data.Maybe (fromJust, isJust)
6+import qualified Data.HashMap.Strict as HM
7+import Data.List.NonEmpty (NonEmpty)
8+import Data.Maybe (fromJust, isJust)
89import Data.Scientific
9−import qualified Data.Set as Set
10−import qualified Data.Text as T
10+import qualified Data.Set as Set
11+import qualified Data.Text as T
1112
1213import qualified JSONSchema.Validator.Draft4 as D4
1314import JSONSchema.Validator.Utils
src/JSONSchema/Draft4/Spec.hs+39−61
@@ -1,73 +1,53 @@
1+
12module JSONSchema.Draft4.Spec where
23
34import Import
45
5−import Data.Maybe (fromMaybe)
6−import Data.Profunctor (Profunctor(..))
6+import Data.Maybe (fromMaybe)
7+import Data.Profunctor (Profunctor(..))
78
89import JSONSchema.Draft4.Failure
9−import JSONSchema.Draft4.Schema (Schema(..), emptySchema)
10−import JSONSchema.Fetch (SchemaWithURI(..), URISchemaMap(..))
11−import qualified JSONSchema.Fetch as FE
12−import JSONSchema.Types (Spec(..))
13−import qualified JSONSchema.Types as JT
10+import JSONSchema.Draft4.Schema (Schema(..))
11+import JSONSchema.Fetch (ReferencedSchemas(..),
12+ SchemaWithURI(..))
13+import qualified JSONSchema.Fetch as FE
14+import JSONSchema.Types (Spec(..))
15+import qualified JSONSchema.Types as JT
1416import JSONSchema.Validator.Draft4
15−import JSONSchema.Validator.Reference (BaseURI(..), Scope(..),
16− updateResolutionScope)
17+import JSONSchema.Validator.Reference (updateResolutionScope)
1718
18−-- | An implementation of 'JT.embedded'.
1919embedded :: Schema -> ([Schema], [Schema])
20−embedded s =
21− JT.embedded (d4Spec mempty mempty (Scope s Nothing (BaseURI Nothing))) s
20+embedded s = JT.embedded (d4Spec (ReferencedSchemas s mempty) mempty Nothing) s
2221
2322specValidate
24− :: URISchemaMap Schema
23+ :: ReferencedSchemas Schema
2524 -> SchemaWithURI Schema
2625 -> Value
2726 -> [ValidatorFailure]
28−specValidate schemaMap sw =
29− JT.validate (d4Spec schemaMap visited scope) (_swSchema sw)
30− where
31− visited :: VisitedSchemas
32− visited = VisitedSchemas [(Nothing, Nothing)]
33−
34− scope :: Scope Schema
35− scope = Scope
36− { _topLevelDocument = _swSchema sw
37− , _documentURI = _swURI sw
38− , _currentBaseURI = updateResolutionScope (BaseURI (_swURI sw))
39− (_schemaId (_swSchema sw))
40− }
27+specValidate rs =
28+ continueValidating rs (VisitedSchemas [(Nothing, Nothing)])
4129
42−validateSubschema
43− :: URISchemaMap Schema
30+continueValidating
31+ :: ReferencedSchemas Schema
4432 -> VisitedSchemas
45− -> Scope Schema
46− -> Schema
33+ -> SchemaWithURI Schema
4734 -> Value
4835 -> [ValidatorFailure]
49−validateSubschema schemaMap visited scope schema =
50− JT.validate (d4Spec schemaMap visited newScope) schema
36+continueValidating referenced visited sw =
37+ JT.validate (d4Spec referenced visited currentScope)
38+ (_swSchema sw)
5139 where
52− newScope :: Scope Schema
53− newScope = scope
54− { _currentBaseURI = updateResolutionScope (_currentBaseURI scope)
55− (_schemaId schema)
56− }
40+ currentScope :: Maybe Text
41+ currentScope = updateResolutionScope
42+ (_swURI sw)
43+ (_schemaId (_swSchema sw))
5744
5845d4Spec
59− :: URISchemaMap Schema
46+ :: ReferencedSchemas Schema
6047 -> VisitedSchemas
61− -> Scope Schema
48+ -> Maybe Text
6249 -> Spec Schema ValidatorFailure
63−d4Spec schemaMap visited scope = Spec $
64− [ dimap
65− (fmap Ref . _schemaRef)
66− FailureRef
67− (refValidator (FE.getReference schemaMap) updateScope valRef visited scope)
68− ]
69−
70− <> fmap (lmap disableIfRefPresent)
50+d4Spec referenced visited scope = Spec
7151 [ dimap (fmap MultipleOf . _schemaMultipleOf) FailureMultipleOf multipleOfValidator
7252 , dimap
7353 (\s -> Maximum (fromMaybe False (_schemaExclusiveMaximum s)) <$> _schemaMaximum s)
@@ -118,6 +98,10 @@ d4Spec schemaMap visited scope = Spec $
11898 FailurePropertiesRelated
11999 (propertiesRelatedValidator descend)
120100
101+ , dimap
102+ (\s -> Ref <$> _schemaRef s)
103+ FailureRef
104+ (refValidator visited scope (FE.getReference referenced) getRef)
121105 , dimap (fmap EnumValidator . _schemaEnum) FailureEnum enumValidator
122106 , dimap (fmap TypeContext . _schemaType) FailureType typeValidator
123107 , dimap (fmap AllOf . _schemaAllOf) FailureAllOf (allOfValidator lateral)
@@ -126,25 +110,19 @@ d4Spec schemaMap visited scope = Spec $
126110 , dimap (fmap NotValidator . _schemaNot) FailureNot (notValidator lateral)
127111 ]
128112 where
129− disableIfRefPresent :: Schema -> Schema
130− disableIfRefPresent schema =
131− case _schemaRef schema of
132− Nothing -> schema
133− Just _ -> emptySchema
134−
135− updateScope :: BaseURI -> Schema -> BaseURI
136− updateScope uri schema = updateResolutionScope uri (_schemaId schema)
137−
138− valRef
113+ getRef
139114 :: VisitedSchemas
140− -> Scope Schema
115+ -> Maybe Text
141116 -> Schema
142117 -> Value
143118 -> [ValidatorFailure]
144− valRef vis sc = JT.validate (d4Spec schemaMap vis sc)
119+ getRef newVisited newScope schema =
120+ continueValidating referenced newVisited (SchemaWithURI schema newScope)
145121
146122 descend :: Schema -> Value -> [ValidatorFailure]
147− descend = validateSubschema schemaMap mempty scope
123+ descend schema =
124+ continueValidating referenced mempty (SchemaWithURI schema scope)
148125
149126 lateral :: Schema -> Value -> [ValidatorFailure]
150− lateral = validateSubschema schemaMap visited scope
127+ lateral schema =
128+ continueValidating referenced visited (SchemaWithURI schema scope)
src/JSONSchema/Fetch.hs+65−46
@@ -1,18 +1,18 @@
1+
12module JSONSchema.Fetch where
23
34import Import
45
5−import qualified Control.Exception.Safe as Safe
6−import Control.Monad (foldM)
7−import qualified Data.ByteString as BS
8−import qualified Data.ByteString.Lazy as LBS
9−import qualified Data.HashMap.Strict as HM
10−import qualified Data.Semigroup as S
11−import qualified Data.Text as T
12−import qualified Network.HTTP.Client as NC
13−import qualified Network.HTTP.Client.TLS as NCTLS
14−
15−import JSONSchema.Validator.Reference (BaseURI(..), resolveReference,
6+import Control.Arrow (left)
7+import Control.Exception (IOException, catch)
8+import Control.Monad (foldM)
9+import qualified Data.ByteString as BS
10+import qualified Data.ByteString.Lazy as LBS
11+import qualified Data.HashMap.Strict as HM
12+import qualified Data.Text as T
13+import qualified Network.HTTP.Client as NC
14+
15+import JSONSchema.Validator.Reference (resolveReference,
1616 updateResolutionScope)
1717
1818--------------------------------------------------
@@ -27,22 +27,49 @@ data FetchInfo schema = FetchInfo
2727 , _fiRef :: schema -> Maybe Text
2828 }
2929
30+data ReferencedSchemas schema = ReferencedSchemas
31+ { _rsStarting :: !schema
32+ -- ^ Used to resolve relative references when we don't know what the scope
33+ -- of the current schema is. This only happens with starting schemas
34+ -- because if we're using a remote schema we had to know its URI in order
35+ -- to fetch it.
36+ --
37+ -- Tracking the starting schema (instead of just resolving the reference to
38+ -- the current schema being used for validation) is necessary for cases
39+ -- where schemas are embedded inside one another. For instance in this
40+ -- case not distinguishing the starting and "foo" schemas sends the code
41+ -- into an infinite loop:
42+ --
43+ -- {
44+ -- "additionalProperties": false,
45+ -- "properties": {
46+ -- "foo": {
47+ -- "$ref": "#"
48+ -- }
49+ -- }
50+ -- }
51+ , _rsSchemaMap :: !(HashMap Text schema)
52+ -- ^ Map of URIs to schemas.
53+ } deriving (Eq, Show)
54+
3055-- | Keys are URIs (without URI fragments).
3156newtype URISchemaMap schema
3257 = URISchemaMap { _unURISchemaMap :: HashMap Text schema }
33− deriving (Eq, Show, S.Semigroup, Monoid)
58+ deriving (Eq, Show)
3459
35−-- | A top-level schema along with its location.
3660data SchemaWithURI schema = SchemaWithURI
3761 { _swSchema :: !schema
3862 , _swURI :: !(Maybe Text)
39− -- ^ This is the URI from which the document was originally fetched.
63+ -- ^ This is the URI identifying the document containing the schema.
4064 -- It's different than the schema's "id" field, which controls scope
4165 -- when resolving references contained in the schema.
66+
67+ -- TODO: Make the no URI fragment requirement unnecessary.
4268 } deriving (Eq, Show)
4369
44−getReference :: URISchemaMap schema -> Text -> Maybe schema
45−getReference schemaMap t = HM.lookup t (_unURISchemaMap schemaMap)
70+getReference :: ReferencedSchemas schema -> Maybe Text -> Maybe schema
71+getReference referenced Nothing = Just (_rsStarting referenced)
72+getReference referenced (Just t) = HM.lookup t (_rsSchemaMap referenced)
4673
4774--------------------------------------------------
4875-- * Fetch via HTTP
@@ -61,9 +88,9 @@ referencesViaHTTP'
6188 -> SchemaWithURI schema
6289 -> IO (Either HTTPFailure (URISchemaMap schema))
6390referencesViaHTTP' info sw = do
64− manager <- NC.newManager NCTLS.tlsManagerSettings
91+ manager <- NC.newManager NC.defaultManagerSettings
6592 let f = referencesMethodAgnostic (getURL manager) info sw
66− Safe.catch (first HTTPParseFailure <$> f) handler
93+ catch (left HTTPParseFailure <$> f) handler
6794 where
6895 getURL :: NC.Manager -> Text -> IO BS.ByteString
6996 getURL man url = do
@@ -89,8 +116,7 @@ referencesViaFilesystem'
89116 => FetchInfo schema
90117 -> SchemaWithURI schema
91118 -> IO (Either FilesystemFailure (URISchemaMap schema))
92−referencesViaFilesystem' info sw =
93− Safe.catch (first FSParseFailure <$> f) handler
119+referencesViaFilesystem' info sw = catch (left FSParseFailure <$> f) handler
94120 where
95121 f :: IO (Either Text (URISchemaMap schema))
96122 f = referencesMethodAgnostic (BS.readFile . T.unpack) info sw
@@ -129,33 +155,27 @@ getRecursiveReferences fetchRef info referenced sw =
129155 f :: Either Text (URISchemaMap schema)
130156 -> SchemaWithURI schema
131157 -> IO (Either Text (URISchemaMap schema))
132− f (Left e) _ = pure (Left e)
133− f (Right (URISchemaMap schemaMap)) (SchemaWithURI schema mURI) =
158+ f (Left e) _ = pure (Left e)
159+ f (Right (URISchemaMap usm)) (SchemaWithURI schema mUri) =
134160 case newRef of
135− Nothing -> pure (Right (URISchemaMap schemaMap))
161+ Nothing -> pure (Right (URISchemaMap usm))
136162 Just uri -> do
137163 bts <- fetchRef uri
138164 case eitherDecodeStrict bts of
139− Left e -> pure . Left . T.pack $ e
140− Right s -> getRecursiveReferences
141− fetchRef
142− info
143− (URISchemaMap (HM.insert uri s schemaMap))
144− (SchemaWithURI s (Just uri))
165+ Left e -> pure . Left . T.pack $ e
166+ Right schm -> getRecursiveReferences
167+ fetchRef
168+ info
169+ (URISchemaMap (HM.insert uri schm usm))
170+ (SchemaWithURI schm (Just uri))
145171 where
146172 newRef :: Maybe Text
147− newRef = do
148− ref <- _fiRef info schema
149−
150− -- Consider the reference before updating the scope.
151− -- If it's a only a fragment this isn't referencing
152− -- a new document.
153− void (fst (resolveReference (BaseURI Nothing) ref))
154−
155− uri <- fst (resolveReference (BaseURI mURI) ref)
156− case HM.lookup uri schemaMap of
157− Nothing -> Just uri
158− Just _ -> Nothing
173+ newRef
174+ | Just (Just uri,_) <- resolveReference mUri <$> _fiRef info schema
175+ = case HM.lookup uri usm of
176+ Nothing -> Just uri
177+ Just _ -> Nothing
178+ | otherwise = Nothing
159179
160180-- | Return the schema passed in as an argument, as well as every
161181-- subschema contained within it.
@@ -164,12 +184,11 @@ includeSubschemas
164184 FetchInfo schema
165185 -> SchemaWithURI schema
166186 -> [SchemaWithURI schema]
167−includeSubschemas info (SchemaWithURI schema mURI) =
168− SchemaWithURI schema mURI
187+includeSubschemas info (SchemaWithURI schema mUri) =
188+ SchemaWithURI schema mUri
169189 : (includeSubschemas info =<< subSchemas)
170190 where
171191 subSchemas :: [SchemaWithURI schema]
172192 subSchemas =
173− let newScope = updateResolutionScope (BaseURI mURI) (_fiId info schema)
174− updateScope s = SchemaWithURI s (_unBaseURI newScope)
175− in updateScope <$> uncurry (<>) (_fiEmbedded info schema)
193+ (\a -> SchemaWithURI a (updateResolutionScope mUri (_fiId info schema)))
194+ <$> uncurry (<>) (_fiEmbedded info schema)
src/JSONSchema/Types.hs+1
@@ -1,3 +1,4 @@
1+
12module JSONSchema.Types where
23
34import Import
src/JSONSchema/Validator/Draft4.hs+19−19
@@ -1,7 +1,5 @@
11-- | Turn the validation functions into actual 'Validator's.
2−--
3−-- This is frankly a lot of busywork. It can perhaps be moved into the
4−-- validator modules themselves once we're sure this is the right design.
2+
53module JSONSchema.Validator.Draft4
64 ( module JSONSchema.Validator.Draft4
75 , module Export
@@ -9,16 +7,18 @@ module JSONSchema.Validator.Draft4
97
108import Import
119
12−import qualified Data.HashMap.Strict as HM
13−import qualified Data.List.NonEmpty as NE
10+import qualified Data.HashMap.Strict as HM
11+import qualified Data.List.NonEmpty as NE
12+import Data.Maybe (catMaybes, maybe, maybeToList)
13+import Data.Text (Text)
1414
15−import JSONSchema.Validator.Draft4.Any as Export
16−import JSONSchema.Validator.Draft4.Array as Export
15+import JSONSchema.Validator.Draft4.Any as Export
16+import JSONSchema.Validator.Draft4.Array as Export
1717import JSONSchema.Validator.Draft4.Number as Export
1818import JSONSchema.Validator.Draft4.Object as Export
1919import JSONSchema.Validator.Draft4.String as Export
20−import JSONSchema.Validator.Reference (BaseURI(..), Scope(..))
21−import JSONSchema.Validator.Types (Validator(..))
20+import JSONSchema.Validator.Types (Validator(..))
21+import JSONSchema.Validator.Utils (fromJSONEither)
2222
2323-- | For internal use.
2424--
@@ -75,8 +75,6 @@ minItemsValidator = Validator noEmbedded (run minItemsVal)
7575uniqueItemsValidator :: Validator a (Maybe UniqueItems) UniqueItemsInvalid
7676uniqueItemsValidator = Validator noEmbedded (run uniqueItemsVal)
7777
78−-- TODO: Add tests to the language agnostic test suite to
79−-- make sure @"additionalItems"@ subschemas are embedded correctly.
8078itemsRelatedValidator
8179 :: (schema -> Value -> [err])
8280 -> Validator schema (ItemsRelated schema) (ItemsRelatedInvalid err)
@@ -147,7 +145,7 @@ propertiesRelatedValidator f =
147145 <> HM.elems (fromMaybe mempty (_propPattern a))
148146 <> case _propAdditional a of
149147 Just (AdditionalPropertiesObject b) -> [b]
150− _ -> mempty
148+ _ -> mempty
151149 ))
152150 (\a b -> case fromJSONEither b of
153151 Left _ -> mempty
@@ -161,6 +159,9 @@ instance FromJSON schema => FromJSON (Definitions schema) where
161159 parseJSON = withObject "Definitions" $ \o ->
162160 Definitions <$> o .: "definitions"
163161
162+-- TODO: Add tests to the language agnostic test suite to
163+-- make sure these schemas are embedded correctly
164+-- (and do so for @"additionalItems"@ as well).
164165definitionsEmbedded
165166 :: Validator
166167 schema
@@ -179,16 +180,15 @@ definitionsEmbedded =
179180
180181refValidator
181182 :: (FromJSON schema, ToJSON schema)
182− => (Text -> Maybe schema)
183− -> (BaseURI -> schema -> BaseURI)
184− -> (VisitedSchemas -> Scope schema -> schema -> Value -> [err])
185− -> VisitedSchemas
186− -> Scope schema
183+ => VisitedSchemas
184+ -> Maybe Text
185+ -> (Maybe Text -> Maybe schema)
186+ -> (VisitedSchemas -> Maybe Text -> schema -> Value -> [err])
187187 -> Validator a (Maybe Ref) (RefInvalid err)
188−refValidator getRef updateScope f visited scope =
188+refValidator visited scope getRef f =
189189 Validator
190190 noEmbedded
191− (run (refVal getRef updateScope f visited scope))
191+ (run (refVal visited scope getRef f))
192192
193193enumValidator :: Validator a (Maybe EnumValidator) EnumInvalid
194194enumValidator = Validator noEmbedded (run enumVal)
src/JSONSchema/Validator/Draft4/Any.hs+59−217
@@ -1,24 +1,20 @@
1+
12module JSONSchema.Validator.Draft4.Any where
23
3−import Import hiding ((<>))
4−
5−import Data.Aeson.TH (constructorTagModifier)
6−import Data.Char (toLower)
7−import qualified Data.HashMap.Strict as HM
8−import Data.List.NonEmpty (NonEmpty((:|)))
9−import qualified Data.List.NonEmpty as NE
10−import qualified Data.Scientific as SCI
11−import Data.Semigroup
12−import Data.Set (Set)
13−import qualified Data.Set as Set
14−import Data.Text.Encoding.Error (UnicodeException)
15−import qualified JSONPointer as JP
16−import Network.HTTP.Types.URI (urlDecode)
17−
18−import JSONSchema.Validator.Reference (BaseURI(..), Scope(..),
19− URIAndFragment,
4+import Import
5+
6+import Data.List.NonEmpty (NonEmpty((:|)))
7+import qualified Data.List.NonEmpty as NE
8+import qualified Data.Scientific as SCI
9+import Data.Semigroup (Semigroup) -- for older GHCs
10+import Data.Set (Set)
11+import qualified Data.Set as S
12+import qualified JSONPointer as JP
13+
14+import qualified JSONSchema.Validator.Utils as UT
15+import JSONSchema.Validator.Reference (URIBaseAndFragment,
16+ resolveFragment,
2017 resolveReference)
21−import qualified JSONSchema.Validator.Utils as UT
2218
2319--------------------------------------------------
2420-- * $ref
@@ -43,156 +39,42 @@ data RefInvalid err
4339 -- Also note that ideally we would enforce in the type system that any
4440 -- failing references be dealt with before valididation. Then this could
4541 -- be removed entirely.
46− | RefPointerResolution JSONPointerError
47− | RefLoop Text VisitedSchemas URIAndFragment
42+ | RefPointerResolution Text
43+ | RefLoop Text VisitedSchemas URIBaseAndFragment
4844 | RefInvalid Text Value (NonEmpty err)
4945 -- ^ 'Text' is the URI and 'Value' is the linked schema.
5046 deriving (Eq, Show)
5147
5248newtype VisitedSchemas
53− = VisitedSchemas { _unVisited :: [URIAndFragment] }
49+ = VisitedSchemas { _unVisited :: [URIBaseAndFragment] }
5450 deriving (Eq, Show, Semigroup, Monoid)
5551
5652refVal
5753 :: forall err schema. (FromJSON schema, ToJSON schema)
58− => (Text -> Maybe schema)
59− -- ^ Look up a schema.
60− -> (BaseURI -> schema -> BaseURI)
61− -- ^ Update scope (needed after moving deeper into nested schemas).
62− -> (VisitedSchemas -> Scope schema -> schema -> Value -> [err])
63− -- ^ Validate data.
64− -> VisitedSchemas
65− -> Scope schema
54+ => VisitedSchemas
55+ -> Maybe Text
56+ -> (Maybe Text -> Maybe schema)
57+ -> (VisitedSchemas -> Maybe Text -> schema -> Value -> [err])
6658 -> Ref
6759 -> Value
6860 -> Maybe (RefInvalid err)
69−refVal getRef updateScope val visited scope (Ref reference) x
61+refVal visited scope getRef f (Ref reference) x
7062 | (mURI, mFragment) `elem` _unVisited visited =
7163 Just (RefLoop reference visited (mURI, mFragment))
72− | otherwise = leftToMaybe $ do
73−
74− -- Get the referenced document
75−
76− (newScope, doc) <- first RefResolution
77− $ getDocument getRef updateScope scope mURI reference
78−
79− -- Get the correct subschema within that document.
80−
81− res <- case mFragment of
82− Nothing -> Right (newScope, doc)
83− Just fragment -> first RefPointerResolution
84− $ resolveFragment updateScope newScope fragment
85− let (finalScope, schema) = res
86−
87− -- Check if that schema is valid.
88−
89− let newVisited = VisitedSchemas [(_documentURI newScope, mFragment)]
90− <> visited
91− failures = val newVisited finalScope schema x
92− first (RefInvalid reference (toJSON schema))
93− . maybeToLeft ()
94− $ NE.nonEmpty failures
64+ | otherwise =
65+ case getRef mURI of
66+ Nothing -> Just (RefResolution reference)
67+ Just schema ->
68+ case resolveFragment mFragment schema of
69+ Nothing -> Just (RefPointerResolution reference)
70+ Just s ->
71+ let newVisited = (VisitedSchemas [(mURI, mFragment)]
72+ <> visited)
73+ errs = f newVisited mURI s x
74+ in RefInvalid reference (toJSON schema)
75+ <$> NE.nonEmpty errs
9576 where
96− mURI :: Maybe Text
97− mFragment :: Maybe Text
98− (mURI, mFragment) = resolveReference (_currentBaseURI scope) reference
99−
100−getDocument
101− :: forall schema. (Text -> Maybe schema)
102− -> (BaseURI -> schema -> BaseURI)
103− -> Scope schema
104− -> Maybe Text
105− -> Text
106− -> Either Text (Scope schema, schema)
107− -- ^ 'Left' is the URI of the document we failed to resolve.
108−getDocument getRef updateScope scope mURI reference =
109− case mURI <* fst (resolveReference (BaseURI Nothing) reference) of
110− Nothing -> Right topOfThisDoc
111− Just uri ->
112− case getRef uri of
113− Nothing -> Left uri
114− Just s -> Right ( Scope s mURI (updateScope (BaseURI mURI) s)
115− , s
116− )
117− where
118− topOfThisDoc :: (Scope schema, schema)
119− topOfThisDoc =
120− ( scope { _currentBaseURI =
121− updateScope (BaseURI (_documentURI scope))
122− (_topLevelDocument scope)
123− }
124− , _topLevelDocument scope
125− )
126−
127−data JSONPointerError
128− = URLDecodingError UnicodeException
129− -- ^ Aspirationally internal.
130− | FormatError JP.FormatError
131− | ResolutionError JP.ResolutionError
132− | SubschemaDecodingError Text
133− -- ^ Aspirationally internal.
134− deriving (Eq, Show)
135−
136−resolveFragment
137− :: (FromJSON schema, ToJSON schema)
138− => (BaseURI -> schema -> BaseURI)
139− -> Scope schema
140− -> Text
141− -> Either JSONPointerError (Scope schema, schema)
142−resolveFragment updateScope scope fragment = do
143− urlDecoded <- first URLDecodingError
144− . decodeUtf8'
145− . urlDecode True
146− . encodeUtf8
147− $ fragment
148− JP.Pointer tokens <- first FormatError (JP.unescape urlDecoded)
149− let acc = (toJSON (_topLevelDocument scope), _currentBaseURI scope)
150− (schemaVal, base) <- foldM go acc tokens
151− schema <- first SubschemaDecodingError (fromJSONEither schemaVal)
152− pure (scope { _currentBaseURI = base }, schema)
153− where
154− -- We have to step through the document JSON Pointer token
155− -- by JSON Pointer token so that we can update the scope
156− -- based on each @"id"@ we encounter.
157− --
158− -- TODO: Do we need specialized code to skip @"id"@s such
159− -- as property keys that aren't meant to change scope?
160− -- Perhaps this should be added to the language agnostic
161− -- test suite as well.
162− --
163− -- In the meantime 'newBaseURIFromFragment' drops all keys
164− -- from JSON objects except "id", which at least prevents
165− -- SubschemaDecodingError in a situation where one of the
166− -- values we step through isn't a valid schema.
167− go :: (Value, BaseURI)
168− -> JP.Token
169− -> Either JSONPointerError (Value, BaseURI)
170− go (lastVal, baseURI) tok = do
171− v <- first ResolutionError (JP.resolveToken tok lastVal)
172− newBase <- newBaseURIFromFragment updateScope baseURI v
173− Right (v, newBase)
174−
175−-- | Update the 'BaseURI' (the store of the current "id" value)
176−-- after resolving one token of a JSON Pointer and stepping into
177−-- a new 'Value'.
178−newBaseURIFromFragment
179− :: FromJSON schema
180− => (BaseURI -> schema -> BaseURI)
181− -> BaseURI
182− -> Value
183− -> Either JSONPointerError BaseURI
184−newBaseURIFromFragment updateScope baseURI v =
185− case v of
186− Object hm -> do
187− let hmWithOnlyId = case HM.lookup idKey hm of
188− Nothing -> mempty
189− Just idVal -> HM.singleton idKey idVal
190− schema <- first SubschemaDecodingError (fromJSONEither (Object hmWithOnlyId))
191− Right (updateScope baseURI schema)
192− _ -> Right baseURI
193− where
194− idKey :: Text
195− idKey = "id"
77+ (mURI, mFragment) = resolveReference scope reference
19678
19779--------------------------------------------------
19880-- * enum
@@ -227,10 +109,7 @@ instance Arbitrary EnumValidator where
227109 Just ne -> pure (EnumValidator ne)
228110 where
229111 toUnique :: [Value] -> [Value]
230− toUnique = fmap UT._unOrdValue
231− . Set.toList
232− . Set.fromList
233− . fmap UT.OrdValue
112+ toUnique = fmap UT._unOrdValue . S.toList . S.fromList . fmap UT.OrdValue
234113
235114data EnumInvalid
236115 = EnumInvalid EnumValidator Value
@@ -238,9 +117,9 @@ data EnumInvalid
238117
239118enumVal :: EnumValidator -> Value -> Maybe EnumInvalid
240119enumVal a@(EnumValidator vs) x
241− | not (UT.allUniqueValues vs) = Nothing
242− | x `elem` vs = Nothing
243− | otherwise = Just $ EnumInvalid a x
120+ | not (UT.allUniqueValues' vs) = Nothing
121+ | x `elem` vs = Nothing
122+ | otherwise = Just $ EnumInvalid a x
244123
245124--------------------------------------------------
246125-- * type
@@ -258,25 +137,10 @@ instance FromJSON TypeContext where
258137 TypeContext <$> o .: "type"
259138
260139data TypeValidator
261− = TypeValidatorString SchemaType
262− | TypeValidatorArray (Set SchemaType)
140+ = TypeValidatorString Text
141+ | TypeValidatorArray (Set Text)
263142 deriving (Eq, Show)
264143
265−instance Semigroup TypeValidator where
266− (<>) x y
267− | isEmpty x = x
268− | isEmpty y = y
269− | x == y = x
270− | otherwise = TypeValidatorArray (setFromTypeValidator x
271− `Set.union`
272− setFromTypeValidator y)
273− where
274− isEmpty :: TypeValidator -> Bool
275− isEmpty (TypeValidatorString _) = False
276− isEmpty (TypeValidatorArray ts) = Set.null ts
277−
278− stimes = stimesIdempotent
279−
280144instance FromJSON TypeValidator where
281145 parseJSON v = fmap TypeValidatorString (parseJSON v)
282146 <|> fmap TypeValidatorArray (parseJSON v)
@@ -286,63 +150,40 @@ instance ToJSON TypeValidator where
286150 toJSON (TypeValidatorArray ts) = toJSON ts
287151
288152instance Arbitrary TypeValidator where
289− arbitrary = oneof [ TypeValidatorString <$> arbitrary
290− , TypeValidatorArray <$> arbitrary
153+ arbitrary = oneof [ TypeValidatorString <$> UT.arbitraryText
154+ , TypeValidatorArray <$> UT.arbitrarySetOfText
291155 ]
292156
293−data SchemaType
294− = SchemaObject
295− | SchemaArray
296− | SchemaString
297− | SchemaNumber
298− | SchemaInteger
299− | SchemaBoolean
300− | SchemaNull
301− deriving (Eq, Ord, Show, Bounded, Enum, Generic)
302−
303−instance FromJSON SchemaType where
304− parseJSON = genericParseJSON
305− defaultOptions
306− { constructorTagModifier = fmap toLower . drop 6 }
307−
308−instance ToJSON SchemaType where
309− toJSON = genericToJSON
310− defaultOptions
311− { constructorTagModifier = fmap toLower . drop 6 }
312−
313−instance Arbitrary SchemaType where
314− arbitrary = arbitraryBoundedEnum
315−
316157data TypeValidatorInvalid
317158 = TypeValidatorInvalid TypeValidator Value
318159 deriving (Eq, Show)
319160
320161typeVal :: TypeContext -> Value -> Maybe TypeValidatorInvalid
321162typeVal (TypeContext tv) x
322− | Set.null matches = Just (TypeValidatorInvalid tv x)
323− | otherwise = Nothing
163+ | S.null matches = Just (TypeValidatorInvalid tv x)
164+ | otherwise = Nothing
324165 where
325166 -- There can be more than one match because a 'Value' can be both a
326167 -- @"number"@ and an @"integer"@.
327− matches :: Set SchemaType
328− matches = Set.intersection okTypes (setFromTypeValidator tv)
168+ matches :: Set Text
169+ matches = S.intersection okTypes (setFromTypeValidator tv)
329170
330− okTypes :: Set SchemaType
171+ okTypes :: Set Text
331172 okTypes =
332173 case x of
333− Null -> Set.singleton SchemaNull
334− (Array _) -> Set.singleton SchemaArray
335− (Bool _) -> Set.singleton SchemaBoolean
336− (Object _) -> Set.singleton SchemaObject
337− (String _) -> Set.singleton SchemaString
174+ Null -> S.singleton "null"
175+ (Array _) -> S.singleton "array"
176+ (Bool _) -> S.singleton "boolean"
177+ (Object _) -> S.singleton "object"
178+ (String _) -> S.singleton "string"
338179 (Number y) ->
339180 if SCI.isInteger y
340− then Set.fromList [SchemaNumber, SchemaInteger]
341− else Set.singleton SchemaNumber
181+ then S.fromList ["number", "integer"]
182+ else S.singleton "number"
342183
343184-- | Internal.
344−setFromTypeValidator :: TypeValidator -> Set SchemaType
345−setFromTypeValidator (TypeValidatorString t) = Set.singleton t
185+setFromTypeValidator :: TypeValidator -> Set Text
186+setFromTypeValidator (TypeValidatorString t) = S.singleton t
346187setFromTypeValidator (TypeValidatorArray ts) = ts
347188
348189--------------------------------------------------
@@ -399,7 +240,8 @@ anyOfVal
399240 -> Value
400241 -> Maybe (AnyOfInvalid err)
401242anyOfVal f (AnyOf subSchemas) x
402− | any (null . snd) perhapsFailures = Nothing
243+ -- Replace with @null@ once we drop GHC 7.8:
244+ | any (((==) 0 . length) . snd) perhapsFailures = Nothing
403245 | otherwise = AnyOfInvalid <$> NE.nonEmpty failures
404246 where
405247 perhapsFailures :: [(JP.Index, [err])]
src/JSONSchema/Validator/Draft4/Array.hs+7−8
@@ -1,10 +1,11 @@
1+
12module JSONSchema.Validator.Draft4.Array where
23
34import Import
45
5−import qualified Data.List.NonEmpty as NE
6−import qualified Data.Vector as V
7−import qualified JSONPointer as JP
6+import qualified Data.List.NonEmpty as NE
7+import qualified Data.Vector as V
8+import qualified JSONPointer as JP
89
910import JSONSchema.Validator.Utils (allUniqueValues)
1011
@@ -66,7 +67,7 @@ instance FromJSON UniqueItems where
6667 parseJSON = withObject "UniqueItems" $ \o ->
6768 UniqueItems <$> o .: "uniqueItems"
6869
69−newtype UniqueItemsInvalid
70+data UniqueItemsInvalid
7071 = UniqueItemsInvalid (Vector Value)
7172 deriving (Eq, Show)
7273
@@ -173,8 +174,7 @@ itemsVal f a xs =
173174 :: schema
174175 -> (JP.Index, Value)
175176 -> Maybe (JP.Index, NonEmpty err)
176− validateElem schema (index,x) =
177− (\v -> (index, v)) <$> NE.nonEmpty (f schema x)
177+ validateElem schema (index,x) = (index,) <$> NE.nonEmpty (f schema x)
178178
179179--------------------------------------------------
180180-- * additionalItems
@@ -219,7 +219,6 @@ additionalItemsVal _ (AdditionalBool False) xs =
219219 AdditionalItemsBoolInvalid <$> NE.nonEmpty xs
220220additionalItemsVal f (AdditionalObject subSchema) xs =
221221 let res = mapMaybe
222− (\(index,x) -> (\v -> (index, v))
223− <$> NE.nonEmpty (f subSchema x))
222+ (\(index,x) -> (index,) <$> NE.nonEmpty (f subSchema x))
224223 xs
225224 in AdditionalItemsObjectInvalid <$> NE.nonEmpty res
src/JSONSchema/Validator/Draft4/Number.hs+2−1
@@ -1,8 +1,9 @@
1+
12module JSONSchema.Validator.Draft4.Number where
23
34import Import
45
5−import Data.Fixed (mod')
6+import Data.Fixed (mod')
67import Data.Scientific (Scientific)
78
89--------------------------------------------------
src/JSONSchema/Validator/Draft4/Object.hs+10−6
@@ -1,3 +1,4 @@
1+
12module JSONSchema.Validator.Draft4.Object
23 ( module JSONSchema.Validator.Draft4.Object
34 , module JSONSchema.Validator.Draft4.Object.Properties
@@ -5,11 +6,11 @@ module JSONSchema.Validator.Draft4.Object
56
67import Import
78
8−import qualified Data.HashMap.Strict as HM
9−import qualified Data.List.NonEmpty as NE
10−import Data.Set (Set)
11−import qualified Data.Set as Set
12−import qualified Data.Text as T
9+import qualified Data.HashMap.Strict as HM
10+import qualified Data.List.NonEmpty as NE
11+import Data.Set (Set)
12+import qualified Data.Set as Set
13+import qualified Data.Text as T
1314
1415import JSONSchema.Validator.Draft4.Object.Properties
1516import JSONSchema.Validator.Utils
@@ -95,6 +96,9 @@ data RequiredInvalid
9596
9697requiredVal :: Required -> HashMap Text Value -> Maybe RequiredInvalid
9798requiredVal r@(Required ts) x
99+ -- NOTE: When we no longer need to support GHCs before 7.10
100+ -- we can use null from Prelude throughout the library
101+ -- instead of specialized versions.
98102 | Set.null ts = Nothing
99103 | Set.null leftovers = Nothing
100104 | otherwise = Just (RequiredInvalid r leftovers x)
@@ -141,7 +145,7 @@ data DependencyMemberInvalid err
141145 | PropertyDepInvalid (Set Text) (HashMap Text Value)
142146 deriving (Eq, Show)
143147
144−newtype DependenciesInvalid err
148+data DependenciesInvalid err
145149 = DependenciesInvalid (HashMap Text (DependencyMemberInvalid err))
146150 deriving (Eq, Show)
147151
src/JSONSchema/Validator/Draft4/Object/Properties.hs+6−6
@@ -1,17 +1,17 @@
1+
12module JSONSchema.Validator.Draft4.Object.Properties where
23
34import Import
45
5−import qualified Data.Hashable as HA
6−import qualified Data.HashMap.Strict as HM
7−import qualified Data.List.NonEmpty as NE
8−import Data.Text.Encoding (encodeUtf8)
9−import qualified JSONPointer as JP
6+import qualified Data.Hashable as HA
7+import qualified Data.HashMap.Strict as HM
8+import qualified Data.List.NonEmpty as NE
9+import Data.Text.Encoding (encodeUtf8)
10+import qualified JSONPointer as JP
1011import qualified Text.Regex.PCRE.Heavy as RE
1112
1213data PropertiesRelated schema = PropertiesRelated
1314 { _propProperties :: Maybe (HashMap Text schema)
14− -- ^ 'Maybe' is used to distinguish whether the key is present or not.
1515 , _propPattern :: Maybe (HashMap Text schema)
1616 , _propAdditional :: Maybe (AdditionalProperties schema)
1717 } deriving (Eq, Show)
src/JSONSchema/Validator/Draft4/String.hs+3−2
@@ -1,9 +1,10 @@
1+
12module JSONSchema.Validator.Draft4.String where
23
34import Import
45
5−import qualified Data.Text as T
6−import Data.Text.Encoding (encodeUtf8)
6+import qualified Data.Text as T
7+import Data.Text.Encoding (encodeUtf8)
78import qualified Text.Regex.PCRE.Heavy as RE
89
910--------------------------------------------------
src/JSONSchema/Validator/Reference.hs+36−28
@@ -3,34 +3,42 @@
33--
44-- And is extended for JSON Schema here:
55-- <http://json-schema.org/latest/json-schema-core.html#anchor26>
6+
67module JSONSchema.Validator.Reference where
78
89import Import
910
10−import qualified Data.Text as T
11−import System.FilePath (dropFileName, (</>))
12−
13−data Scope schema = Scope
14− { _topLevelDocument :: schema
15− , _documentURI :: Maybe Text
16− , _currentBaseURI :: BaseURI
17− } deriving (Eq, Show)
11+import qualified Data.Text as T
12+import Data.Text.Encoding (decodeUtf8, encodeUtf8)
13+import qualified JSONPointer as JP
14+import Network.HTTP.Types.URI (urlDecode)
15+import System.FilePath ((</>), dropFileName)
1816
19−newtype BaseURI
20− = BaseURI { _unBaseURI :: Maybe Text }
21− deriving (Eq, Show)
17+-- | TODO: Replace these with actual URI data types.
18+type URIBase = Maybe Text
19+type URIBaseAndFragment = (Maybe Text, Maybe Text)
2220
23−-- | TODO: no `type`s.
24−type URIAndFragment = (Maybe Text, Maybe Text)
21+updateResolutionScope :: URIBase -> Maybe Text -> URIBase
22+updateResolutionScope mScope idKeyword
23+ | Just t <- idKeyword = fst . baseAndFragment $ resolveScopeAgainst mScope t
24+ | otherwise = mScope
2525
26−updateResolutionScope :: BaseURI -> Maybe Text -> BaseURI
27−updateResolutionScope base idKeyword =
28− case idKeyword of
29− Just t -> BaseURI . fst . baseAndFragment $ resolveScopeAgainst base t
30− Nothing -> base
26+resolveReference :: URIBase -> Text -> URIBaseAndFragment
27+resolveReference mScope t = baseAndFragment $ resolveScopeAgainst mScope t
3128
32−resolveReference :: BaseURI -> Text -> URIAndFragment
33−resolveReference base t = baseAndFragment (resolveScopeAgainst base t)
29+resolveFragment
30+ :: (FromJSON schema, ToJSON schema)
31+ => Maybe Text
32+ -> schema
33+ -> Maybe schema
34+resolveFragment Nothing schema = Just schema
35+resolveFragment (Just pointer) schema = do
36+ let urlDecoded = decodeUtf8 . urlDecode True . encodeUtf8 $ pointer
37+ p <- either (const Nothing) Just (JP.unescape urlDecoded)
38+ x <- either (const Nothing) Just (JP.resolve p (toJSON schema))
39+ case fromJSON x of
40+ Error _ -> Nothing
41+ Success schema' -> Just schema'
3442
3543--------------------------------------------------
3644-- * Helpers
@@ -39,10 +47,10 @@ resolveReference base t = baseAndFragment (resolveScopeAgainst base t)
3947isRemoteReference :: Text -> Bool
4048isRemoteReference = T.isInfixOf "://"
4149
42−baseAndFragment :: Text -> URIAndFragment
50+baseAndFragment :: Text -> URIBaseAndFragment
4351baseAndFragment = f . T.splitOn "#"
4452 where
45− f :: [Text] -> URIAndFragment
53+ f :: [Text] -> URIBaseAndFragment
4654 f [x] = (g x, Nothing)
4755 f [x,y] = (g x, g y)
4856 f _ = (Nothing, Nothing)
@@ -50,9 +58,9 @@ baseAndFragment = f . T.splitOn "#"
5058 g "" = Nothing
5159 g x = Just x
5260
53−resolveScopeAgainst :: BaseURI -> Text -> Text
54−resolveScopeAgainst (BaseURI Nothing) t = t
55−resolveScopeAgainst (BaseURI (Just base)) t
61+resolveScopeAgainst :: Maybe Text -> Text -> Text
62+resolveScopeAgainst Nothing t = t
63+resolveScopeAgainst (Just scope) t
5664 | isRemoteReference t = t
5765 | otherwise = smartAppend
5866 where
@@ -61,11 +69,11 @@ resolveScopeAgainst (BaseURI (Just base)) t
6169 -- to cut it off before appending.
6270 smartAppend :: Text
6371 smartAppend =
64− case baseAndFragment base of
65− (Just uri,_) ->
72+ case baseAndFragment scope of
73+ (Just base,_) ->
6674 case T.unpack t of
6775 -- We want "/foo" and "#/bar" to combine into
6876 -- "/foo#/bar" not "/foo/#/bar".
6977 '#':_ -> base <> t
70− _ -> T.pack (dropFileName (T.unpack uri) </> T.unpack t)
78+ _ -> T.pack (dropFileName (T.unpack base) </> T.unpack t)
7179 _ -> t
src/JSONSchema/Validator/Types.hs+1
@@ -1,3 +1,4 @@
1+
12module JSONSchema.Validator.Types where
23
34import Import
src/JSONSchema/Validator/Utils.hs+27−11
@@ -1,15 +1,16 @@
1+
12module JSONSchema.Validator.Utils where
23
34import Import
45
5−import Control.Monad (fail)
6+import Control.Monad (fail)
67import qualified Data.HashMap.Strict as HM
7−import qualified Data.List.NonEmpty as NE
8−import Data.Scientific (Scientific, fromFloatDigits)
9−import Data.Set (Set)
10−import qualified Data.Set as S
11−import qualified Data.Text as T
12−import qualified Data.Vector as V
8+import qualified Data.List.NonEmpty as NE
9+import Data.Scientific (Scientific, fromFloatDigits)
10+import Data.Set (Set)
11+import qualified Data.Set as S
12+import qualified Data.Text as T
13+import qualified Data.Vector as V
1314
1415--------------------------------------------------
1516-- * QuickCheck
@@ -82,11 +83,16 @@ instance Arbitrary a => Arbitrary (NonEmpty' a) where
8283-- * allUniqueValues
8384--------------------------------------------------
8485
85−allUniqueValues :: (Foldable f, Functor f) => f Value -> Bool
86−allUniqueValues = allUnique . fmap OrdValue
86+allUniqueValues :: Vector Value -> Bool
87+allUniqueValues = allUnique . fmap OrdValue . V.toList
88+
89+-- NOTE: When we no longer support GHC 7.8 we can generalize
90+-- allUnique to work on any Foldable and remove this function.
91+allUniqueValues' :: NonEmpty Value -> Bool
92+allUniqueValues' = allUnique . fmap OrdValue . NE.toList
8793
88−allUnique :: (Foldable f, Ord a) => f a -> Bool
89−allUnique xs = S.size (S.fromList (toList xs)) == length xs
94+allUnique :: (Ord a) => [a] -> Bool
95+allUnique xs = S.size (S.fromList xs) == length xs
9096
9197-- | OrdValue's Ord instance needs benchmarking, but it allows us to
9298-- use our 'allUnique' function instead of O(n^2) nub, so it's probably
@@ -117,3 +123,13 @@ instance Ord OrdValue where
117123
118124 (OrdValue (Object x)) `compare` (OrdValue (Object y)) =
119125 HM.toList (OrdValue <$> x) `compare` HM.toList (OrdValue <$> y)
126+
127+--------------------------------------------------
128+-- * other
129+--------------------------------------------------
130+
131+fromJSONEither :: FromJSON a => Value -> Either Text a
132+fromJSONEither a =
133+ case fromJSON a of
134+ Error e -> Left (T.pack e)
135+ Success b -> Right b
stack.yamldeleted−2
@@ -1,2 +0,0 @@
1−resolver: lts-10.8
2−pvp-bounds: upper-revision
test/Local.hs+14−10
@@ -1,18 +1,21 @@
1+
12module Main where
23
34import Protolude
45
56import Data.Aeson
67import qualified Data.List.NonEmpty as NE
7−import qualified System.Timeout as TO
8+import qualified System.Timeout as TO
89import Test.Hspec
9−import Test.QuickCheck (property)
10+import Test.QuickCheck (property)
1011
11−import qualified JSONSchema.Draft4 as D4
12−import qualified JSONSchema.Types as JT
12+import qualified JSONSchema.Draft4 as D4
13+import JSONSchema.Fetch (ReferencedSchemas(..),
14+ URISchemaMap(..))
15+import qualified JSONSchema.Types as JT
1316import qualified Local.Failure
14−import qualified Local.Reference
1517import qualified Local.Validation
18+import qualified Local.Reference
1619import Shared
1720
1821-- Examples
@@ -32,10 +35,12 @@ main = do
3235 -- Language agnostic tests
3336 ts <- readSchemaTests
3437 dir
35− (\a -> not (isHTTPTest a || skipTest a))
38+ (\a -> not (isHTTPTest a || skipOptional a))
3639
3740 -- Custom supplements to the language agnostic tests
38− supplementTs <- readSchemaTests supplementDir (not . isHTTPTest)
41+ supplementTs <- readSchemaTests
42+ supplementDir
43+ (\a -> not (isHTTPTest a || skipOptional a))
3944
4045 hspec $ do
4146 describe "Examples" exampleTests
@@ -79,9 +84,8 @@ main = do
7984 Left e -> panic ("Local.validateExample error: " <> show e)
8085 Right schemaMap -> do
8186 let failures = AlternateSchema.validate
82− schemaMap
83− (D4.SchemaWithURI s Nothing)
84− (_scData sc)
87+ (ReferencedSchemas s (_unURISchemaMap schemaMap))
88+ Nothing s (_scData sc)
8589 assertResult sc failures
8690
8791quickCheckTests :: Spec
test/Local/Failure.hs+7−6
@@ -1,14 +1,15 @@
1+
12module Local.Failure where
23
34import Protolude
45
56import Data.Aeson
6−import qualified Data.Vector as V
7−import qualified JSONPointer as JP
87import Test.Hspec
8+import qualified Data.Vector as V
9+import qualified JSONPointer as JP
910
1011import JSONSchema.Draft4
11−import qualified JSONSchema.Draft4.Spec as Spec
12+import qualified JSONSchema.Draft4.Spec as Spec
1213import qualified JSONSchema.Validator.Draft4 as VAL
1314
1415spec :: Spec
@@ -30,7 +31,7 @@ itemsArray =
3031 ]
3132 where
3233 failures :: [ValidatorFailure]
33− failures = Spec.specValidate mempty sw badData
34+ failures = Spec.specValidate (ReferencedSchemas schema mempty) sw badData
3435
3536 schema :: Schema
3637 schema = emptySchema
@@ -60,7 +61,7 @@ itemsObject =
6061 ]
6162 where
6263 failures :: [ValidatorFailure]
63− failures = Spec.specValidate mempty sw badData
64+ failures = Spec.specValidate (ReferencedSchemas schema mempty) sw badData
6465
6566 schema :: Schema
6667 schema = emptySchema
@@ -88,7 +89,7 @@ loopRef =
8889 ]
8990 where
9091 failures :: [ValidatorFailure]
91− failures = Spec.specValidate mempty sw badData
92+ failures = Spec.specValidate (ReferencedSchemas schema mempty) sw badData
9293
9394 schema :: Schema
9495 schema = emptySchema
test/Local/Reference.hs+13−12
@@ -1,3 +1,4 @@
1+
12module Local.Reference where
23
34import Protolude
@@ -9,28 +10,28 @@ import JSONSchema.Validator.Reference
910spec :: Spec
1011spec = do
1112 it "updateResolutionScope gives correct results" $ do
12− updateResolutionScope (BaseURI Nothing) Nothing
13− `shouldBe` BaseURI Nothing
13+ updateResolutionScope Nothing Nothing
14+ `shouldBe` Nothing
1415
15− updateResolutionScope (BaseURI Nothing) (Just "#")
16− `shouldBe` BaseURI Nothing
16+ updateResolutionScope Nothing (Just "#")
17+ `shouldBe` Nothing
1718
18− updateResolutionScope (BaseURI Nothing) (Just "foo")
19− `shouldBe` BaseURI (Just "foo")
19+ updateResolutionScope Nothing (Just "foo")
20+ `shouldBe` Just "foo"
2021
2122 -- TODO: Normalize after updateResolutionScope:
22− updateResolutionScope (BaseURI (Just "/foo")) (Just "./bar")
23− `shouldBe` BaseURI (Just "/./bar")
23+ updateResolutionScope (Just "/foo") (Just "./bar")
24+ `shouldBe` Just "/./bar"
2425
2526 it "resolveReference gives correct results" $ do
26− resolveReference (BaseURI (Just "/foo")) "bar"
27+ resolveReference (Just "/foo") "bar"
2728 `shouldBe` (Just "/bar", Nothing)
2829
29− resolveReference (BaseURI (Just "/foo/bar")) "/baz"
30+ resolveReference (Just "/foo/bar") "/baz"
3031 `shouldBe` (Just "/baz", Nothing)
3132
32− resolveReference (BaseURI Nothing) "#/bar"
33+ resolveReference Nothing "#/bar"
3334 `shouldBe` (Nothing, Just "/bar")
3435
35− resolveReference (BaseURI (Just "/foo")) "#/bar"
36+ resolveReference (Just "/foo") "#/bar"
3637 `shouldBe` (Just "/foo", Just "/bar")
test/Local/Validation.hs+6−5
@@ -1,16 +1,17 @@
1+
12module Local.Validation where
23
3−import Protolude
4+import Protolude hiding (msg)
45
56import Data.Aeson
6−import qualified Data.Aeson as AE
7+import qualified Data.Aeson as AE
78import qualified Data.HashMap.Strict as HM
8−import Data.String (String)
9+import Data.String (String)
910import Test.Hspec
1011
11−import qualified AlternateSchema as AS
1212import JSONSchema.Draft4
13−import qualified JSONSchema.Types as JT
13+import qualified JSONSchema.Types as JT
14+import qualified AlternateSchema as AS
1415
1516spec :: Spec
1617spec = do
test/Remote.hs+11−9
@@ -1,16 +1,19 @@
1+
12module Main where
23
34import Protolude
45
5−import Control.Concurrent.Async (withAsync)
6−import qualified Data.List.NonEmpty as NE
6+import Control.Concurrent.Async (withAsync)
7+import qualified Data.List.NonEmpty as NE
78import Network.Wai.Application.Static (defaultFileServerSettings,
89 staticApp)
9−import qualified Network.Wai.Handler.Warp as Warp
10+import Network.Wai.Handler.Warp (run)
1011import Test.Hspec
1112
12−import qualified JSONSchema.Draft4 as D4
13−import qualified JSONSchema.Types as JT
13+import qualified JSONSchema.Draft4 as D4
14+import JSONSchema.Fetch (ReferencedSchemas(..),
15+ URISchemaMap(..))
16+import qualified JSONSchema.Types as JT
1417import Shared
1518
1619-- Examples
@@ -45,13 +48,12 @@ main = withAsync serve $ \_ -> do
4548 Left e -> panic ("Remote.validateExample error: " <> show e)
4649 Right schemaMap -> do
4750 let failures = AlternateSchema.validate
48− schemaMap
49− (D4.SchemaWithURI s Nothing)
50− (_scData sc)
51+ (ReferencedSchemas s (_unURISchemaMap schemaMap))
52+ Nothing s (_scData sc)
5153 assertResult sc failures
5254
5355serve :: IO ()
54−serve = Warp.run 1234
56+serve = run 1234
5557 . staticApp
5658 . defaultFileServerSettings
5759 $ "JSON-Schema-Test-Suite/remotes"
test/Shared.hs+19−18
@@ -1,29 +1,19 @@
1+
12module Shared where
23
34import Protolude
45
5−import Control.Monad (fail)
6+import Control.Monad (fail)
67import Data.Aeson
7−import Data.Aeson.TH (fieldLabelModifier)
8−import qualified Data.ByteString as BS
9−import Data.Char (toLower)
10−import Data.List (stripPrefix, unlines)
11−import qualified Data.Text as T
8+import Data.Aeson.TH (fieldLabelModifier)
9+import qualified Data.ByteString as BS
10+import Data.Char (toLower)
11+import Data.List (stripPrefix, unlines)
12+import qualified Data.Text as T
1213import qualified System.Directory as SD
13−import System.FilePath ((</>))
14+import System.FilePath ((</>))
1415import Test.Hspec
1516
16−skipTest :: FilePath -> Bool
17−skipTest file = (file == "optional/format.json") -- Optional
18− || (file == "optional/zeroTerminatedFloats.json")
19− || (file == "optional/ecmascript-regex.json")
20−
21−
22−isHTTPTest :: FilePath -> Bool
23−isHTTPTest file = (file == "definitions.json")
24− || (file == "ref.json")
25− || (file == "refRemote.json")
26−
2717-- Recursively return the contents of a directory
2818-- (or return itself if given a file as an argument).
2919--
@@ -47,6 +37,17 @@ listFilesFullPath path = do
4737 fs <- fmap (path </>) <$> SD.listDirectory path
4838 concat <$> traverse listFilesFullPath fs
4939
40+isHTTPTest :: FilePath -> Bool
41+isHTTPTest file = (file == "definitions.json")
42+ || (file == "ref.json")
43+ || (file == "refRemote.json")
44+
45+-- | We may never support the @"format"@ keywords, and
46+-- are currently failing the zeroTerminatedFloats test.
47+skipOptional :: FilePath -> Bool
48+skipOptional file = (file == "optional/format.json")
49+ || (file == "optional/zeroTerminatedFloats.json")
50+
5051data SchemaTest = SchemaTest
5152 { _stDescription :: Text
5253 , _stSchema :: Value