I'm using Node.js to pretty-print a JSON object.
This line
obj = JSON.stringify(obj, null, 1);
results in:
{
"name": "Member",
"type": "object",
"properties": {
"Id": {
"type": "GUID",
"description": "Unique identifier"
},
"Name": {
"type": "string",
"description": "Members name"
}
}
}
But I want it to look this way:
{
"name": "Member",
"type": "object",
"properties": {
"Id": {"type": "GUID", "description": "Unique identifier"},
"Name": {"type": "string", "description": "Members name"}
}
}
How can I do this?
Use JSON.stringify, then use some regular expressions on the resulting string.
First strip the top level braces, then replace every newline within a {...} group with blank.
Related
I'm making a Discord bot in Python that reacts to certain keywords in messages and my script uses a JSON file that might for example look like this:
{
"characters": {
"john": {
"name": "Johnny",
"hex_colour": "0xC61B1B"
},
"marc": {
"name": "Marcus",
"hex_colour": "0x8AC0FF"
}
},
"reactions": [
{
"keywords": ["Hi", "Hello"],
"quotes": {
"john": ["Hello my name is Johnny"]
"marc": [
"Hi there. I'm Marcus.",
"Not now, I'm looking for John, have you seen him?"
]
}
},
{
"keywords": ["Bye"],
"quotes": {
"john": ["See you later!"]
}
}
]
}
As you can see the structure is quite complex, so I decide to make a schema for it so vscode could point out any issues. It currently looks like this:
{
"title": "Quotes data",
"description": "Quotes bot data file",
"type": "object",
"properties": {
"characters": {
"title": "Character collection",
"description": "A collection of the available characters.",
"type": "object",
"additionalProperties":{
"title": "Character tag",
"description": "A tag that represents the character as a short string",
"type": "object",
"properties": {
"name": {
"title": "Character name",
"description": "The name of the character.",
"type": "string"
},
"hex_colour": {
"title": "Character colour",
"description": "The hex code of the colour in 0x000000 format.",
"type": "string"
},
"image_url": {
"title": "Character image",
"description": "An url to an image of the character.",
"type": "string"
}
},
"required": ["name"],
"additionalProperties": false
}
},
"reactions": {
"title": "Reaction collection",
"description": "A list of the reactions",
"type": "array",
"items": {
"type": "object",
"properties": {
"keywords": {
"title": "Keyword list",
"description": "A list of keywords for the bot to react to.",
"type": "array",
"items": {
"title": "Keyword",
"type": "string",
"minItems": 1,
"uniqueItems": true
}
},
"quotes": {
"title": "Quotes collection",
"description": "A collection of characters with quotes.",
"type": "object",
"additionalProperties":{
"title":"Character tag",
"description": "A tag that matches a character above.",
"type": "array",
"items": {
"title": "Quote",
"description": "A quote to react with.",
"type": "string",
"minItems": 1,
"uniqueItems": true
}
}
}
},
"required": ["keywords", "quotes"],
"additionalProperties": false
}
}
},
"required": ["characters", "reactions"],
"additionalProperties": true,
"allowTrailingCommas": true
}
So for the properties of the "characters" object, any property name is allowed, therefore I use "additionalProperties". Later on, for the "quotes" object, I did the same. But in this case, not any property should be allowed. Only those that match one of the properties of the "characters" object is allowed. Is there any way to make the schema check for matching properties?
This is a very specific semantic check and not possible using the standard specification of JSON Schema. Validation can't access an arbitrary set of property names and also can't look up the validation path. You would need to add this as application code.
I have a JSON object like:
{
"result": [
{
"name" : "abc",
"email": "abc.test#mail.com"
},
{
"name": "def",
"email": "def.test#mail.com"
},
{
"name": "xyz",
"email": "abc.test#mail.com"
}
]
}
and schema for this:
{
"definitions": {},
"$schema": "http://json-schema.org/draft-07/schema#",
"$id": "https://example.com/object1607582431.json",
"title": "Root",
"type": "object",
"required": [
"result"
],
"properties": {
"result": {
"$id": "#root/result",
"title": "Result",
"type": "array",
"default": [],
"uniqueItems": true,
"items": {
"$id": "#root/result/items",
"title": "Items",
"type": "object",
"required": [
"name",
"email"
],
"properties": {
"name": {
"$id": "#root/result/items/name",
"title": "Name",
"type": "string"
},
"email": {
"$id": "#root/result/items/email",
"title": "Email",
"type": "string"
}
}
}
}
}
}
I am looking for an option to check uniqueness for email irrespective of name. How I can validate that every email should be unique?
You can't. There are no keywords that let you compare one particular data value against another, other than uniqueItems, which compares an array element in toto against another.
The JsonSchema specification does not currently support this.
You can see the active GitHub issue here: https://github.com/json-schema-org/json-schema-vocabularies/issues/22
However, there are various extensions of JsonSchema that do validate unique fields within lists of objects.
If you happen to be using Python you can use the package (I created) JsonVL. It can be installed with pip install jsonvl and then run with jsonvl data.json schema.json.
Code examples in the GitHub repo: https://github.com/gregorybchris/jsonvl
I am trying to validate JSON file against this schema including dateTime regex pattern:
{
"$schema": "http://json-schema.org/draft-07/schema#",
"$id": "http://example.com/product.schema.json",
"title": "title",
"type": "object",
"properties": {
"entries": {
"description": "date time entries",
"type": "array",
"contains": {
"type": "object"
},
"items": {
"type": "object",
"properties": {
"dateTime": {
"description": "UTC timestamp in format \"YYYY-MM-DDThh:mm:ssTZD\" according to ISO 8601",
"type": "string",
"pattern": "^(-?(?:[1-9][0-9]*)?[0-9]{4})-(1[0-2]|0[1-9])-(3[01]|0[1-9]|[12][0-9])T(2[0-3]|[01][0-9]):([0-5][0-9]):([0-5][0-9])(.[0-9]{3})?(?:Z|[+-][01][0-9]:[0-5][0-9])?$"
}
}
}
}
}
}
When I try to validate this JSON file:
{
"description": "date time entries",
"entries": [
{
"dateTime": "2020-10-09T08:48:41.348+02:00"
},
{
"dateTime": "2020-10-09T08:48:52.240+02:00"
}
]
}
I get the following error regarding second entry in the array:
String '2020-10-09T06:48:52.24+00:00' does not match regex pattern '^(-?(?:[1-9][0-9]*)?[0-9]{4})-(1[0-2]|0[1-9])-(3[01]|0[1-9]|[12][0-9])T(2[0-3]|[01][0-9]):([0-5][0-9]):([0-5][0-9])(.[0-9]{3})?(?:Z|[+-][01][0-9]:[0-5][0-9])?$'.
Please note, that the validator correctly validated 1st entry: "2020-10-09T08:48:41.348+02:00".
What I noticed is that the problem is with entries containing milliseconds with "0" at the end, like: ".240"
I have following schema:
{
"$schema": "http://json-schema.org/draft-07/schema#",
"description": "Bulk Create Entity",
"title": "Bulk Create Entity",
"type": "object",
"properties": {
"idempotence_key": {
"description": "Idempotence Key",
"type": "string"
},
"requested_by": {
"description": "Requested By",
"type": "string"
},
"updated_by_process_id": {
"description": "Process id which is creating this entity.",
"type": "string"
},
"entity_creation_requests": {
"description": "Entity creation requests.",
"type": "array",
"minItems": 1,
"items": {
"title": "Entity Creation Request",
"type": "object",
"properties": {
"type": {
"description": "Entity Type",
"type": "string"
},
"taxonomies": {
"description": "Entity Taxonomies",
"type": "array",
"items": {
"title": "Taxonomy",
"type": "object",
"properties": {
"name": {
"description": "Taxonomy Name",
"type": "string"
},
"value": {
"description": "Taxonomy Value",
"type": "string"
}
}
}
}
}
}
}
},
"required": [
"idempotence_key",
"requested_by",
"updated_by_process_id",
"entity_creation_requests"
]
}
Here, the root level payload is an object which has a key "entity_creation_requests" which is an array of objects which in turn have an array property "taxonomies" which contains a list of key-value pairs.
Now depending on the "type" of the request under "entity_creation_requests", I want to validate the presence of certain keys in the taxonomies list.
For example, for the creation request of type "product", I want keys "MRP", "seller" etc. to be present in the taxonomies list.
Can we achieve this using JSON schema validator?
{Here is something I have created: https://codebeautify.org/jsonviewer/cb80c728}
Are there any other alternatives?
I am using this in an spring boot application (Java).
I need to create a JSON schema for object that will include java Properties object as one of its properties.
The nested Properties object will be simply list of key=value. Both key and value are of type string.
I failed to find any docs that describe how to define the schema that includes 2 new types.
shall it be something like:
{
"type": "object",
"name": "MyObj",
"properties": {
"prop1": {
"type": "string",
"description": "prop1",
"required": true
},
"props": {
"type": "array",
"items": {
"type": "object"
"properties": {
"key": {
"type": "string",
"description": "key",
"required": true
},
"value": {
"type": "string",
"description": "the value",
"required": true
}
}
"description": "the value",
"required": true
}
}
}
}
The schema you have written (assuming the commas are fixed) describes data of the form:
{
"prop1": "Some string property goes here",
"props": [
{"key": "foo", "value": "bar"},
{"key": "foo2", "value": "bar2"},
...
]
}
If this is what you wanted, then you are already finished.
However, I do wonder why you are using key/value pairs in an array, when you could use a JSON object with string keys instead. Using the additionalProperties keyword, you could have a schema:
{
"type": "object",
"name": "MyObj",
"properties": {
"prop1": {
"type": "string",
"description": "prop1"
},
"props": {
"type": "object",
"additionalProperties": {
"type": "string",
"description": "string values"
}
}
}
}
This describes a data format like:
{
"prop1": "Some string property goes here",
"props": {
"foo": "bar",
"foo2": "bar2"
}
}
At W3 schools (JSON Syntax) you can read how the array should be defined.
There is no schema like the xsd for xml, however i've found an approach on json-schema.org. If you are able to, i'll advice to youse google-GSON library for JSON. You could Store key Value as "id" : "value" and build only one object, containing all requieed pairs:
{ "lang" : "EN" , "color" : "red" }
Your posted model is incorect, you can check it on jsonlint.com
Here is a working version, i'm not sure if the modell is as expected.
{
"type": "object",
"name": "MyObj",
"properties": [
{
"prop1": {
"type": "string",
"description": "prop1",
"required": true
},
"props": {
"type": "array",
"items": {
"type": "object",
"properties": {
"key": {
"type": "string",
"description": "key",
"required": true
},
"value": {
"type": "string",
"description": "the value",
"required": true
}
},
"description": "the value",
"required": true
}
}
}
]
}