-
Notifications
You must be signed in to change notification settings - Fork 0
Json Methods
Along side the ability to traverse and work with JSON documents using the Laravel style arrow selectors. We also have a collection of JSON helper methods, these allow for more complex functionality, while increasing readability.
if you wish to access these methods, please call
jsonBuilder()
before defining your query.
It is possible to select single values (either inner object/array or just values) from within JSON documents.
/**
* @param string|Raw $column The Database column holding JSON document
* @param string|string[]|Raw $nodes Either single node, array of nodes or raw expression
* @param string $alias Sets the 'AS Alias'
* @return QueryBuildHandler
*/
public function selectJson($column, $nodes, $alias): QueryBuilderHandler
DB Table
id | title | authorData |
---|---|---|
1 | 5 Easy Rules Of Tree | {"data":{"author_id":12, "author_name":"Sam"}} |
2 | The Death Of Lard | {"data":{"author_id":42, "author_name":"James"}} |
3 | Is Bacon Still Relevant? | {"data":{"author_id":12, "author_name":"Sam"}} |
4 | The Miracle Of Sponge | {"data":{"author_id":24, "author_name":"Jane"}} |
Usage
$builder->jsonBuilder()
->table('foo')
->select('id', 'title')
->selectJson('authorData',['data','author_name'], 'author')
->get()
0 => {id: 1, title: "5 Easy Rules Of Tree", author: "Sam"},
1 => {id: 2, title: "The Death Of Lard", author: "James"},
2 => {id: 3, title: "Is Bacon Still Relevant?", author: "Sam"},
3 => {id: 4, title: "The Miracle Of Sponge", author: "Jane"}
Also includes
orWhereJson()
It is possible to select single values (either inner object/array or just values) from within JSON documents.
- whereJson() - joins multiple Where Statements with 'AND'
- orWhereJson() - joins multiple Where Statements with 'OR'
/**
* @param string|Raw $column The database column which holds the JSON value
* @param string|string[]|Raw $nodes Either single node, array of nodes or raw expression
* @param string|mixed|null $operator Can be used as value, if 3rd arg not passed
* @param mixed|null $value The value to match to the JSON value
* @return QueryBuilderHandler
*/
public function whereJson($column, $nodes, $operator, $value ): QueryBuilderHandler
It is possible to omit the
$operator
value and it assumed as=
DB Table
id | title | authorData |
---|---|---|
1 | 5 Easy Rules Of Tree | {"data":{"id":12, "name":"Sam"}} |
2 | The Death Of Lard | {"data":{"id":42, "name":"James"}} |
3 | Is Bacon Still Relevant? | {"data":{"id":12, "name":"Sam"}} |
4 | The Miracle Of Sponge | {"data":{"id":24, "name":"Jane"}} |
Usage
$builder->jsonBuilder()
->table('foo')
->whereJson('authorData',['data','id'], 12)
->orWhereJson('authorData',['data','id'], 24)
->get()
Results
0 => {id: 1, title: "5 Easy Rules Of Tree", authorData: {"data":{"id":12, "name":"Sam"}}},
1 => {id: 3, title: "Is Bacon Still Relevant?", authorData: {"data":{"id":12, "name":"Sam"}}}
2 => {id: 4, title: "The Miracle Of Sponge", authorData: {"data":{"id":24, "name":"Jane"}}}
Also includes
orWhereNotJson()
It is possible to create a `Where value inside JSON document doesn't match the operator and value defined.
- whereNotJson() - joins multiple Where Statements with 'AND'
- orWhereNotJson() - joins multiple Where Statements with 'OR'
/**
* @param string|Raw $column The database column which holds the JSON value
* @param string|string[]|Raw $nodes Either single node, array of nodes or raw expression
* @param string|mixed|null $operator Can be used as value, if 3rd arg not passed
* @param mixed|null $value The value to match to the JSON value
* @return QueryBuilderHandler
*/
public function whereNotJson($column, $nodes, $operator, $value ): QueryBuilderHandler
It is possible to omit the
$operator
value and it assumed as=
DB Table
id | title | authorData |
---|---|---|
1 | 5 Easy Rules Of Tree | {"data":{"id":12, "name":"Sam"}} |
2 | The Death Of Lard | {"data":{"id":42, "name":"James"}} |
3 | Is Bacon Still Relevant? | {"data":{"id":12, "name":"Sam"}} |
4 | The Miracle Of Sponge | {"data":{"id":24, "name":"Jane"}} |
Usage
$builder->jsonBuilder()
->table('foo')
->whereNotJson('authorData',['data','id'], 24)
->orWhereNotJson('authorData',['data','id'], 42)
->get()
Results
0 => {id: 1, title: "5 Easy Rules Of Tree", authorData: {"data":{"id":12, "name":"Sam"}}},
1 => {id: 3, title: "Is Bacon Still Relevant?", authorData: {"data":{"id":12, "name":"Sam"}}}
Also includes
orWhereInJson()
It is possible to create a `Where value inside JSON document doesn't match the operator and value defined.
- whereInJson() - joins multiple WhereInJson Statements with 'AND'
- orWhereInJson() - joins multiple WhereInJson Statements with 'OR'
/**
* @param string|Raw $column The database column which holds the JSON value
* @param string|string[]|Raw $nodes Either single node, array of nodes or raw expression
* @param mixed[] $values Array of values to look for a match in
* @return QueryBuilderHandler
*/
public function whereInJson($column, $nodes, $values ): QueryBuilderHandler
DB Table
id | name | choices |
---|---|---|
1 | Glynn | {"data":{"colour":"red", "flavour":"apple"}} |
2 | Oliver | {"data":{"colour":"red", "flavour":"berry"}} |
3 | Dexter | {"data":{"colour":"green", "flavour":"cream"}} |
4 | Mary | {"data":{"colour":"blue", "flavour":"bacon"}} |
Usage
$builder->jsonBuilder()
->table('foo')
->whereInJson('choices',['data','colour'], ['green', 'yellow'])
->orWhereInJson('choices',['data','flavour'], ['bacon', 'cheese', 'pear'])
->get()
Results
0 => {id: 3, name: "Dexter", choices: {"data":{"colour":"green", "flavour":"cream"}}},
1 => {id: 4, name: "Mary", choices: {"data":{"colour":"blue", "flavour":"bacon"}}}
❗ Don't forget you can use bindings to help avoid XSS injection
->whereJson('column', ['json','object'], [Bindings::asString($variable1), Bindings::asString($variable2)]);
Also includes
orWhereNotInJson()
It is possible to create a `Where value inside JSON document doesn't match the operator and value defined.
- whereNotInJson() - joins multiple WhereNotInJson Statements with 'AND'
- orWhereNotInJson() - joins multiple WhereNotInJson Statements with 'OR'
/**
* @param string|Raw $column The database column which holds the JSON value
* @param string|string[]|Raw $nodes Either single node, array of nodes or raw expression
* @param mixed[] $values Array of values to look for a match NOT in
* @return QueryBuilderHandler
*/
public function whereNotInJson($column, $nodes, $values ): QueryBuilderHandler
DB Table
id | name | choices |
---|---|---|
1 | Glynn | {"data":{"colour":"red", "flavour":"apple"}} |
2 | Oliver | {"data":{"colour":"red", "flavour":"berry"}} |
3 | Dexter | {"data":{"colour":"green", "flavour":"cream"}} |
4 | Mary | {"data":{"colour":"blue", "flavour":"bacon"}} |
Usage
$builder->jsonBuilder()
->table('foo')
->whereNotInJson('choices',['data','colour'], ['green', 'yellow'])
->orWhereNotInJson('choices',['data','flavour'], ['bacon', 'cheese', 'pear'])
->get()
Results
0 => {id: 1, name: "Glynn", choices: {"colour":"red", "flavour":"apple"}}},
1 => {id: 2, name: "Oliver", choices: {"data":{"colour":"red", "flavour":"berry"}}}
Also includes
orWhereBetweenJson()
It is possible to create a `Where value inside JSON document doesn't match the operator and value defined.
- whereBetweenJson() - joins multiple whereBetweenJson Statements with 'AND'
- orWhereBetweenJson() - joins multiple whereBetweenJson Statements with 'OR'
/**
* @param string|Raw $column The database column which holds the JSON value
* @param string|string[]|Raw $nodes Either single node, array of nodes or raw expression
* @param int|float|Raw $valueFrom The min value
* @param int|float|Raw $valueTo The max value
* @return QueryBuilderHandler
*/
public function whereBetweenJson($column, $nodes, $valueFrom, $valueTo ): QueryBuilderHandler
DB Table
id | name | results |
---|---|---|
1 | Glynn | {"data":{"step1":2, "step2":8}} |
2 | Oliver | {"data":{"step1":4, "step2":3}} |
3 | Dexter | {"data":{"step1":3, "step2":2}} |
4 | Mary | {"data":{"step1":9, "step2":7}} |
Usage
$builder->jsonBuilder()
->table('foo')
->whereBetweenJson('choices',['data','step1'], 7, 9)
->orWhereBetweenJson('choices',['data','step2'], 7, 9)
->get()
Results
0 => {id: 1, name: "Glynn", results: {"data":{"step1":2, "step2":8}}},
1 => {id: 4, name: "Mary", results: {"data":{"step1":9, "step2":7}}}
It is possible to order a query by a single or multiple values. The basic arrow selectors
will not do any casting of the data value and treat as a basic string value. This can be controlled using the following flags.
/**
* @param string|Raw $column The Database column holding JSON document
* @param string|string[]|Raw $nodes Either single node, array of nodes or raw expression
* @param string $direction Direction 'ASC' or 'DESC'.
* @return QueryBuildHandler
*/
public function orderByJson($column, $nodes, $direction='ASC'): QueryBuilderHandler
DB Table
id | title | metaData |
---|---|---|
1 | Some Tile | {"stats":{"likes":450, "dislikes":5}} |
2 | Foo Bar | {"stats":{"likes":45, "dislikes":500}} |
3 | Words | {"stats":{"likes":85463, "dislikes":785}} |
4 | Examples | {"stats":{"likes":45, "dislikes":14}} |
Usage |
$builder->jsonBuilder()
->table('foo')
->orderByJson('metaData',['stats','likes'], 'DESC')
->orderByJson('metaData',['stats','dislikes'], 'ASC')
->get()
Results
0 => {id: 3, string: "Words", metaData:{stats:{likes:85463, dislikes:785}}},
1 => {id: 1, string: "Some Tile", metaData: {stats:{likes:450,dislikes:5}}},
2 => {id: 4, string: "Examples", metaData: {stats:{likes:45,dislikes:14}}}},
3 => {id: 2, string: "Foo Bar", metaData: {stats:{likes:45,dislikes:500}}}