Nothing
## NOTE: so far as I can see this is not valid json, nor is it
## sensible json schema (the 'required' kw should be an array)
test_that("is-my-json-valid", {
str <- "{
required: true,
type: 'object',
properties: {
hello: {
required: true,
type: 'string'
}
}
}"
v <- json_validator(str, engine = "imjv")
expect_false(v("{}"))
expect_true(v("{hello: 'world'}"))
expect_false(json_validate("{}", str, engine = "imjv"))
expect_true(json_validate("{hello: 'world'}", str, engine = "imjv"))
f <- tempfile()
writeLines(str, f)
v <- json_validator(f, engine = "imjv")
expect_false(v("{}"))
expect_true(v("{hello: 'world'}"))
v <- json_validator("schema.json", engine = "imjv")
expect_error(v("{}", error = TRUE),
"data.hello: is required",
class = "validation_error")
expect_true(v("{hello: 'world'}", error = TRUE))
})
test_that("simple case works", {
schema <- str <- '{
"type": "object",
required: ["hello"],
"properties": {
"hello": {
"type": "string"
}
}
}'
v <- json_validator(str, "ajv")
expect_false(v("{}"))
expect_true(v("{hello: 'world'}"))
expect_false(json_validate("{}", str))
expect_true(json_validate("{hello: 'world'}", str))
f <- tempfile()
writeLines(str, f)
v <- json_validator(f)
expect_false(v("{}"))
expect_true(v("{hello: 'world'}"))
v <- json_validator("schema2.json", "ajv")
expect_error(v("{}", error = TRUE), "hello", class = "validation_error")
expect_true(v("{hello: 'world'}", error = TRUE))
})
test_that("verbose output", {
schema <- str <- '{
"type": "object",
required: ["hello"],
"properties": {
"hello": {
"type": "string"
}
}
}'
v <- json_validator(str, "ajv")
res <- v("{}", verbose = TRUE)
expect_false(res)
expect_s3_class(attr(res, "errors"), "data.frame")
})
test_that("const keyword is supported in draft-06, not draft-04", {
schema <- "{
'$schema': 'http://json-schema.org/draft-04/schema#',
'type': 'object',
'properties': {
'a': {
'const': 'foo'
}
}
}"
expect_true(json_validate("{'a': 'foo'}", schema, engine = "ajv"))
expect_true(json_validate("{'a': 'bar'}", schema, engine = "ajv"))
## Switch to draft-06
schema <- gsub("draft-04", "draft-06", schema)
expect_true(json_validate("{'a': 'foo'}", schema, engine = "ajv"))
expect_false(json_validate("{'a': 'bar'}", schema, engine = "ajv"))
})
test_that("if/then/else keywords are supported in draft-07, not draft-04", {
schema <- "{
'$schema': 'http://json-schema.org/draft-04/schema#',
'type': 'object',
'if': {
'properties': {
'a': {'type': 'number', 'minimum': 1}
}
},
'then': {
'required': ['b']
},
'else': {
'required': ['c']
}
}"
expect_true(json_validate("{'a': 5, 'b': 5}", schema, engine = "ajv"))
expect_true(json_validate("{'a': 0, 'b': 5}", schema, engine = "ajv"))
## Switch to draft-07
schema <- gsub("draft-04", "draft-07", schema)
expect_true(json_validate("{'a': 5, 'b': 5}", schema, engine = "ajv"))
expect_false(json_validate("{'a': 5, 'c': 5}", schema, engine = "ajv"))
})
test_that("subschema validation works", {
schema <- '{
"$schema": "http://json-schema.org/draft-06/schema#",
"definitions": {
"Goodbye": {
type: "object",
properties: {"goodbye": {type: "string"}},
"required": ["goodbye"]
},
"Hello": {
type: "object",
properties: {"hello": {type: "string"}},
"required": ["hello"]
},
"Conversation": {
"anyOf": [
{"$ref": "#/definitions/Hello"},
{"$ref": "#/definitions/Goodbye"},
]
}
},
"$ref": "#/definitions/Conversation"
}'
val_goodbye <- json_validator(schema, "ajv", "#/definitions/Goodbye")
expect_true(val_goodbye("{'goodbye': 'failure'}"))
expect_false(val_goodbye("{'hello': 'failure'}"))
val_hello <- json_validator(schema, "ajv", "#/definitions/Hello")
expect_false(val_hello("{'goodbye': 'failure'}"))
expect_true(val_hello("{'hello': 'failure'}"))
})
test_that("can't use subschema reference with imjv", {
expect_error(json_validator("{}", engine = "imjv",
reference = "definitions/sub"),
"subschema validation only supported with engine 'ajv'")
})
test_that("can't use nested schemas with imjv", {
testthat::skip_if_not_installed("withr")
parent <- c(
'{',
' "type": "object",',
' "properties": {',
' "hello": {',
' "$ref": "child.json"',
' }',
' },',
' "required": ["hello"],',
' "additionalProperties": false',
'}')
child <- c(
'{',
' "type": "string"',
'}')
path <- tempfile()
dir.create(path)
writeLines(parent, file.path(path, "parent.json"))
writeLines(child, file.path(path, "child.json"))
withr::with_options(
list(jsonvalidate.no_note_imjv = FALSE),
expect_message(
v <- json_validator(file.path(path, "parent.json"), engine = "imjv"),
"Schema references are only supported with engine 'ajv'"))
## We incorrectly don't find this invalid, because we never read the
## child schema; the user should have used ajv!
expect_true(v('{"hello": 1}'))
})
test_that("can't use invalid engines", {
expect_error(json_validator("{}", engine = "magic"),
"Unknown engine 'magic'")
})
test_that("can't use new schema versions with imjv", {
testthat::skip_if_not_installed("withr")
schema <- "{
'$schema': 'http://json-schema.org/draft-07/schema#',
'type': 'object',
'properties': {
'a': {
'const': 'foo'
}
}
}"
ct <- jsonvalidate_js()
schema <- read_schema(schema, ct)
withr::with_options(
list(jsonvalidate.no_note_imjv = FALSE),
expect_message(
v <- json_validator_imjv(schema, ct, NULL),
"meta schema version other than 'draft-04' is only supported with"))
## We incorrectly don't find this invalid, because imjv does not
## understand the const keyword.
expect_true(v('{"a": "bar"}'))
})
test_that("Simple file references work", {
parent <- c(
'{',
' "type": "object",',
' "properties": {',
' "hello": {',
' "$ref": "child.json"',
' }',
' },',
' "required": ["hello"],',
' "additionalProperties": false',
'}')
child <- c(
'{',
' "type": "string"',
'}')
path <- tempfile()
dir.create(path)
writeLines(parent, file.path(path, "parent.json"))
writeLines(child, file.path(path, "child.json"))
v <- json_validator(file.path(path, "parent.json"), engine = "ajv")
expect_false(v("{}"))
expect_true(v('{"hello": "world"}'))
})
test_that("Referenced schemas have their ids replaced", {
parent <- c(
'{',
' "type": "object",',
' "properties": {',
' "hello": {',
' "$ref": "child.json"',
' }',
' },',
' "required": ["hello"],',
' "additionalProperties": false',
'}')
child <- c(
'{',
' "id": "child",',
' "type": "string"',
'}')
path <- tempfile()
dir.create(path)
writeLines(parent, file.path(path, "parent.json"))
writeLines(child, file.path(path, "child.json"))
expect_silent(
v <- json_validator(file.path(path, "parent.json"), engine = "ajv"))
expect_false(v("{}"))
expect_true(v('{"hello": "world"}'))
})
test_that("Can validate fraction of a json object", {
schema <- c(
'{',
' "type": "object",',
' "properties": {',
' "x": {',
' type: "string"',
' },',
' },',
' "required": ["x"]',
'}')
data <- c(
'{',
' "a": {',
' "x": "string"',
' },',
' "b": {',
' y: 1',
' }',
'}')
expect_false(json_validate(data, schema, engine = "ajv"))
expect_true(json_validate(data, schema, engine = "ajv", query = "a"))
expect_false(json_validate(data, schema, engine = "ajv", query = "b"))
expect_error(
json_validate(data, schema, engine = "imjv", query = "c"),
"Queries are only supported with engine 'ajv'")
expect_error(
json_validate(data, schema, engine = "ajv", query = "c"),
"Query did not match any element in the data")
expect_error(
json_validate("[]", schema, engine = "ajv", query = "c"),
"Query only supported with object json")
expect_error(
json_validate("null", schema, engine = "ajv", query = "c"),
"Query only supported with object json")
})
test_that("complex jsonpath queries are rejected", {
msg <- "Full json-path support is not implemented"
expect_error(query_validate("foo/bar"), msg)
expect_error(query_validate("foo?"), msg)
expect_error(query_validate("$foo"), msg)
expect_error(query_validate("foo(bar)"), msg)
expect_error(query_validate("foo[0]"), msg)
expect_error(query_validate("foo@bar"), msg)
})
test_that("simple jsonpath is passed along", {
expect_identical(query_validate("foo"), "foo")
expect_identical(query_validate(NULL), V8::JS("null"))
})
test_that("stray null values in a schema are ok", {
## This is stripped down version of the vegalite schema 3.3.0 which
## includes a block
##
## "invalidValues": {
## "description": "Defines how Vega-Lite should handle ...",
## "enum": [
## "filter",
## null
## ],
## "type": [
## "string",
## "null"
## ]
## },
##
## which used to break the reference detection by throwing an error
## when the schema was read.
schema <- '{
"type": "object",
"properties": {
"a": {
"enum": ["value", null]
}
}
}'
ct <- jsonvalidate_js()
expect_error(read_schema(schema, ct), NA)
})
test_that("Referencing definition in another file works", {
parent <- c(
'{',
' "type": "object",',
' "properties": {',
' "hello": {',
' "$ref": "child.json#/definitions/greeting"',
' }',
' },',
' "required": ["hello"],',
' "additionalProperties": false',
'}')
child <- c(
'{',
' "definitions": {',
' "greeting": {',
' "type": "string"',
' }',
' }',
'}')
path <- tempfile()
dir.create(path)
writeLines(parent, file.path(path, "parent.json"))
writeLines(child, file.path(path, "child.json"))
v <- json_validator(file.path(path, "parent.json"), engine = "ajv")
expect_false(v("{}"))
expect_true(v('{"hello": "world"}'))
invalid <- v('{"hello": ["thing"]}', verbose = TRUE)
expect_false(invalid)
error <- attr(invalid, "errors", TRUE)
expect_equal(error$schemaPath, "child.json#/definitions/greeting/type")
expect_equal(error$message, "must be string")
})
test_that("schema can contain IDs", {
schema <- c(
'{',
' "$id": "http://example.com/schemas/thing.json",',
' "type": "object",',
' "properties": {',
' "hello": {',
' "type": "string"',
' }',
' },',
' "required": ["hello"],',
' "additionalProperties": false',
'}')
path <- tempfile()
dir.create(path)
writeLines(schema, file.path(path, "schema.json"))
v <- json_validator(file.path(path, "schema.json"), engine = "ajv")
expect_false(v("{}"))
expect_true(v("{hello: 'world'}"))
})
test_that("Parent schema with URL ID works", {
parent <- c(
'{',
' "$id": "http://example.com/schemas/thing.json",',
' "type": "object",',
' "properties": {',
' "hello": {',
' "$ref": "child.json#/definitions/greeting"',
' }',
' },',
' "required": ["hello"],',
' "additionalProperties": false',
'}')
child <- c(
'{',
' "definitions": {',
' "first": {',
' "type": "string"',
' },',
' "greeting": {',
' "type": "object",',
' "properties": {',
' "name": {',
' "type": "string"',
' },',
' "another_prop": {',
' "type": "number"',
' }',
' }',
' }',
' }',
'}')
path <- tempfile()
dir.create(path)
writeLines(parent, file.path(path, "parent.json"))
writeLines(child, file.path(path, "child.json"))
v <- json_validator(file.path(path, "parent.json"), engine = "ajv")
expect_false(v("{}"))
expect_true(v('{"hello": {"name": "a name", "another_prop": 2}}'))
})
test_that("format keyword works", {
str <- '{
"type": "object",
"required": ["date"],
"properties": {
"date": {
"type": "string",
"format": "date-time"
}
}
}'
v <- json_validator(str, "ajv")
expect_false(v("{'date': '123'}"))
expect_true(v("{'date': '2018-11-13T20:20:39+00:00'}"))
})
test_that("format keyword works in draft-04", {
str <- '{
"$schema": "http://json-schema.org/draft-04/schema#",
"type": "object",
"required": ["date"],
"properties": {
"date": {
"type": "string",
"format": "date-time"
}
}
}'
v <- json_validator(str, "ajv", strict = TRUE)
expect_false(v("{'date': '123'}"))
expect_true(v("{'date': '2018-11-13T20:20:39+00:00'}"))
})
test_that("unknown format type throws an error if in strict mode", {
str <- '{
"type": "object",
"required": ["date"],
"properties": {
"date": {
"type": "string",
"format": "test"
}
}
}'
expect_error(json_validator(str, "ajv", strict = TRUE),
paste0('Error: unknown format "test" ignored in schema at ',
'path "#/properties/date"'))
## Warnings printed in non-strict mode; these include some annoying
## newlines from the V8 engine, so using capture.output to stop
## these messing up testthat output
capture.output(
msg <- capture_warnings(v <- json_validator(str, "ajv", strict = FALSE)))
expect_equal(msg[1], paste0('unknown format "test" ignored in ',
'schema at path "#/properties/date"'))
expect_true(v("{'date': '123'}"))
})
test_that("json_validate can be run in strict mode", {
schema <- "{
'$schema': 'http://json-schema.org/draft-04/schema#',
'type': 'object',
'properties': {
'a': {
'const': 'foo'
}
},
'reference': '1234'
}"
expect_true(json_validate("{'a': 'foo'}", schema, engine = "ajv"))
expect_error(
json_validate("{'a': 'foo'}", schema, engine = "ajv", strict = TRUE),
'Error: strict mode: unknown keyword: "reference"')
})
test_that("validation works with 2019-09 schema version", {
schema <- "{
'$schema': 'http://json-schema.org/draft-07/schema#',
'$defs': {
'toggle': {
'$id': '#toggle',
'type': [ 'boolean', 'null' ],
'default': null
}
},
'type': 'object',
'properties': {
'enabled': {
'$ref': '#toggle',
'default': true
}
}
}"
expect_true(json_validate("{'enabled': true}", schema, engine = "ajv"))
expect_false(json_validate("{'enabled': 'test'}", schema, engine = "ajv"))
## Switch to draft/2019-09
schema <- gsub("http://json-schema.org/draft-07/schema#",
"https://json-schema.org/draft/2019-09/schema#", schema)
## draft/2019-09 doesn't allow #plain-name form of $id
expect_error(json_validator(schema, engine = "ajv"),
"Error: schema is invalid:")
schema <- "{
'$schema': 'https://json-schema.org/draft/2019-09/schema#',
'$defs': {
'toggle': {
'$anchor': 'toggle',
'type': [ 'boolean', 'null' ],
'default': null
}
},
'type': 'object',
'properties': {
'enabled': {
'$ref': '#toggle',
'default': true
}
}
}"
expect_true(json_validate("{'enabled': true}", schema, engine = "ajv"))
expect_false(json_validate("{'enabled': 'test'}", schema, engine = "ajv"))
})
test_that("validation works with 2020-12 schema version", {
schema <- "{
'$schema': 'https://json-schema.org/draft/2020-12/schema#',
'$defs': {
'toggle': {
'$anchor': 'toggle',
'type': [ 'boolean', 'null' ],
'default': null
}
},
'type': 'object',
'properties': {
'enabled': {
'$ref': '#toggle',
'default': true
}
}
}"
expect_true(json_validate("{'enabled': true}", schema, engine = "ajv"))
expect_false(json_validate("{'enabled': 'test'}", schema, engine = "ajv"))
})
test_that("ajv requires a valid meta schema version", {
schema <- "{
'$schema': 'http://json-schema.org/draft-99/schema#',
'type': 'object',
'properties': {
'a': {
'const': 'foo'
}
}
}"
expect_error(
json_validator(schema, engine = "ajv"),
"Unknown meta schema version 'draft-99'")
})
Any scripts or data that you put into this service are public.
Add the following code to your website.
For more information on customizing the embed code, read Embedding Snippets.