Class: Query

Query


new Query(collection)

A class used by the Collection class to build queries to be executed against the collection's data. An instance of Query is returned by Collection#query. Query instances are typically short-lived, and you shouldn't have to create them yourself. Just use Collection#query.

import {Query} from 'js-data'
Method parameters:
Name Type Description
collection Collection

The collection on which this query operates.

Details
Since Source
3.0.0 Query.js, line 25
Example
const store = new JSData.DataStore()
store.defineMapper('post')
const posts = [
  { author: 'John', age: 30, status: 'published', id: 1 },
  { author: 'Sally', age: 31, status: 'draft', id: 2 },
  { author: 'Mike', age: 32, status: 'draft', id: 3 },
  { author: 'Adam', age: 33, status: 'deleted', id: 4 },
  { author: 'Adam', age: 33, status: 'draft', id: 5 }
]
store.add('post', posts)
const drafts = store.query('post').filter({ status: 'draft' }).limit(2).run()
console.log(drafts)

Extends

This class extends the Component class.

Members


<static> ops

The filtering operators supported by Query#filter, and which are implemented by adapters (for the most part).

Details
Type Since Source
Object 3.0.0 Query.js, line 860
Properties:
Name Type Description
== Function

Equality operator.

!= Function

Inequality operator.

> Function

Greater than operator.

>= Function

Greater than (inclusive) operator.

< Function

Less than operator.

<= Function

Less than (inclusive) operator.

isectEmpty Function

Operator that asserts that the intersection between two arrays is empty.

isectNotEmpty Function

Operator that asserts that the intersection between two arrays is not empty.

in Function

Operator that asserts whether a value is in an array.

notIn Function

Operator that asserts whether a value is not in an array.

contains Function

Operator that asserts whether an array contains a value.

notContains Function

Operator that asserts whether an array does not contain a value.

Examples

const store = new JSData.DataStore()
store.defineMapper('post')
const posts = [
  { author: 'John', age: 30, status: 'published', id: 1 },
  { author: 'Sally', age: 31, status: 'published', id: 2 },
  { author: 'Mike', age: 32, status: 'published', id: 3 },
  { author: 'Adam', age: 33, status: 'deleted', id: 4 },
  { author: 'Adam', age: 33, status: 'published', id: 5 }
]
store.add('post', posts)

const publishedPosts = store.filter('post', {
  status: 'published',
  limit: 2
})

console.log(publishedPosts)

const store = new JSData.DataStore()
store.defineMapper('post')
const posts = [
  { author: 'John', age: 30, status: 'published', id: 1 },
  { author: 'Sally', age: 31, status: 'published', id: 2 },
  { author: 'Mike', age: 32, status: 'published', id: 3 },
  { author: 'Adam', age: 33, status: 'deleted', id: 4 },
  { author: 'Adam', age: 33, status: 'published', id: 5 }
]
store.add('post', posts)

const publishedPosts = store.filter('post', {
  where: {
    status: {
      '==': 'published'
    }
  },
  limit: 2
})

console.log(publishedPosts)

const store = new JSData.DataStore()
store.defineMapper('post')
const posts = [
  { author: 'John', age: 30, status: 'published', id: 1 },
  { author: 'Sally', age: 31, status: 'published', id: 2 },
  { author: 'Mike', age: 32, status: 'published', id: 3 },
  { author: 'Adam', age: 33, status: 'deleted', id: 4 },
  { author: 'Adam', age: 33, status: 'published', id: 5 }
]
store.add('post', posts)

const publishedPosts = store.query('post').filter({
  status: 'published'
}).limit(2).run()

console.log(publishedPosts)

const store = new JSData.DataStore()
store.defineMapper('post')
const posts = [
  { author: 'John', age: 30, status: 'published', id: 1 },
  { author: 'Sally', age: 31, status: 'published', id: 2 },
  { author: 'Mike', age: 32, status: 'published', id: 3 },
  { author: 'Adam', age: 33, status: 'deleted', id: 4 },
  { author: 'Adam', age: 33, status: 'published', id: 5 }
]
store.add('post', posts)

const publishedPosts = store.query('post').filter({
  where: {
    status: {
      '==': 'published'
    }
  }
}).limit(2).run()

console.log(publishedPosts)

const store = new JSData.DataStore()
store.defineMapper('post')
const posts = [
  { author: 'John', age: 30, status: 'published', id: 1 },
  { author: 'Sally', age: 31, status: 'published', id: 2 },
  { author: 'Mike', age: 32, status: 'published', id: 3 },
  { author: 'Adam', age: 33, status: 'deleted', id: 4 },
  { author: 'Adam', age: 33, status: 'published', id: 5 }
]
store.add('post', posts)

const myPublishedPosts = store.filter('post', {
  where: {
    status: {
      '==': 'published'
    },
    user_id: {
      '==': currentUser.id
    }
  }
})

console.log(myPublishedPosts)

collection

The Collection on which this query operates.

Details
Type Since Source
Collection 3.0.0 Query.js, line 57

data

The current data result of this query.

Details
Type Since Source
Array 3.0.0 Query.js, line 66

debug

Whether to enable debug-level logs for this component. Anything that extends Component inherits this option and the corresponding logging functionality.

Details
Type Since Default value Source
Boolean 3.0.0
false
Component.js, line 28
Inherited From:
Example

// Normally you would do: import {Component} from 'js-data'
const JSData = require('js-data@3.0.0-rc.4')
const {Component} = JSData
console.log('Using JSData v' + JSData.version.full)

const component = new Component()
component.log('debug', 'some message') // nothing gets logged
// Display debug logs:
component.debug = true
component.log('debug', 'other message') // this DOES get logged

Methods


<static> extend(props, classProps)

Create a subclass of this Query:

Method parameters:
Name Type Argument Default Description
props Object <optional>
{}

Properties to add to the prototype of the subclass.

Properties
Name Type Argument Description
constructor Object <optional>

Provide a custom constructor function to be used as the subclass itself.

classProps Object <optional>
{}

Static properties to add to the subclass.

Return value:
Type Description
Constructor

Subclass of this Query class.

Details
Since Source
3.0.0 Query.js, line 1048
Example

// Normally you would do: import {Query} from 'js-data'
const JSData = require('js-data@3.0.0-rc.4')
const {Query} = JSData
console.log('Using JSData v' + JSData.version.full)

// Extend the class using ES2015 class syntax.
class CustomQueryClass extends Query {
  foo () { return 'bar' }
  static beep () { return 'boop' }
}
const customQuery = new CustomQueryClass()
console.log(customQuery.foo())
console.log(CustomQueryClass.beep())

// Extend the class using alternate method.
const OtherQueryClass = Query.extend({
  foo () { return 'bar' }
}, {
  beep () { return 'boop' }
})
const otherQuery = new OtherQueryClass()
console.log(otherQuery.foo())
console.log(OtherQueryClass.beep())

// Extend the class, providing a custom constructor.
function AnotherQueryClass (collection) {
  Query.call(this, collection)
  this.created_at = new Date().getTime()
}
Query.extend({
  constructor: AnotherQueryClass,
  foo () { return 'bar' }
}, {
  beep () { return 'boop' }
})
const anotherQuery = new AnotherQueryClass()
console.log(anotherQuery.created_at)
console.log(anotherQuery.foo())
console.log(AnotherQueryClass.beep())

between(leftKeys, rightKeys, opts)

Find all entities between two boundaries.

Method parameters:
Name Type Argument Description
leftKeys Array

Keys defining the left boundary.

rightKeys Array

Keys defining the right boundary.

opts Object <optional>

Configuration options.

Properties
Name Type Argument Default Description
index String <optional>

Name of the secondary index to use in the query. If no index is specified, the main index is used.

leftInclusive Boolean <optional>
true

Whether to include entities on the left boundary.

rightInclusive Boolean <optional>
false

Whether to include entities on the left boundary.

limit Boolean <optional>

Limit the result to a certain number.

offset Boolean <optional>

The number of resulting entities to skip.

Return value:
Type Description
Query

A reference to itself for chaining.

Details
Since Source
3.0.0 Query.js, line 160
Examples

const store = new JSData.DataStore()
store.defineMapper('user')
const users = [
  { name: 'Peter', age: 25, id: 1 },
  { name: 'Jim', age: 19, id: 2 },
  { name: 'Mike', age: 17, id: 3 },
  { name: 'Alan', age: 29, id: 4 },
  { name: 'Katie', age: 33, id: 5 }
]
store.add('post', posts)
const filteredUsers = store.query('user').between(18, 30, { index: 'age' }).run()
console.log(filteredUsers)

const store = new JSData.DataStore()
store.defineMapper('user')
const users = [
  { name: 'Peter', age: 25, id: 1 },
  { name: 'Jim', age: 19, id: 2 },
  { name: 'Mike', age: 17, id: 3 },
  { name: 'Alan', age: 29, id: 4 },
  { name: 'Katie', age: 33, id: 5 }
]
store.add('post', posts)
const filteredUsers = store.query('user').between([18], [30], { index: 'age' }).run()
console.log(filteredUsers)

compare(orderBy, index, a, b)

The comparison function used by the Query class.

Method parameters:
Name Type Description
orderBy Array

An orderBy clause used for sorting and sub-sorting.

index Number

The index of the current orderBy clause being used.

a *

The first item in the comparison.

b *

The second item in the comparison.

Return value:
Type Description
Number

-1 if b should preceed a. 0 if a and b are equal. 1 if a should preceed b.

Details
Since Source
3.0.0 Query.js, line 215

dbg(args)

Log the provided values at the "debug" level. Debug-level logs are only logged if Component#debug is true.

.dbg(...) is shorthand for .log('debug', ...).

Method parameters:
Name Type Argument Description
args * <optional>
<repeatable>

Values to log.

Details
Since Source
3.0.0 Component.js, line 124
Inherited From:

emit(event, args)

Trigger an event on this Component.

Method parameters:
Name Type Argument Description
event String

Name of event to emit.

args * <optional>
<repeatable>

Arguments to pass to any listeners.

Details
Since Source
3.0.0 Component.js, line 202
Inherited From:
Example

// import {Collection, DataStore} from 'js-data'
const JSData = require('js-data@3.0.0-rc.4')
const {Collection, DataStore} = JSData

const collection = new Collection()
collection.on('foo', function (msg) {
  console.log(msg)
})
collection.emit('foo', 'bar')

const store = new DataStore()
store.on('beep', function (msg) {
  console.log(msg)
})
store.emit('beep', 'boop')

evaluate(value, op, predicate)

Predicate evaluation function used by the Query class.

Method parameters:
Name Type Description
value *

The value to evaluate.

op String

The operator to use in this evaluation.

predicate *

The predicate to use in this evaluation.

Return value:
Type Description
Boolean

Whether the value passed the evaluation or not.

Details
Since Source
3.0.0 Query.js, line 261

filter(queryOrFn, thisArg)

Find the record or records that match the provided query or are accepted by the provided filter function.

Method parameters:
Name Type Argument Default Description
queryOrFn Object | Function <optional>
{}

Selection query or filter function.

thisArg Function <optional>

Context to which to bind queryOrFn if queryOrFn is a function.

Return value:
Type Description
Query

A reference to itself for chaining.

Details
Since Source
3.0.0 Query.js, line 283
Examples

const store = new JSData.DataStore()
store.defineMapper('post')
const posts = [
  { author: 'John', age: 30, status: 'published', id: 1 },
  { author: 'Sally', age: 31, status: 'published', id: 2 },
  { author: 'Mike', age: 32, status: 'draft', id: 3 },
  { author: 'Adam', age: 33, status: 'deleted', id: 4 },
  { author: 'Adam', age: 33, status: 'published', id: 5 }
  { author: 'Peter', age: 25, status: 'deleted', id: 6 },
  { author: 'Sally', age: 21, status: 'draft', id: 7 },
  { author: 'Jim', age: 27, status: 'draft', id: 8 },
  { author: 'Jim', age: 27, status: 'published', id: 9 },
  { author: 'Jason', age: 55, status: 'published', id: 10 }
]
store.add('post', posts)
let results = store.query('post').filter({
  where: {
    status: {
      '==': 'draft'
    },
    age: {
      '<': 30
    }
  }
}).run()
console.log(results)

const posts = query.filter(function (post) {
  return post.isReady()
}).run()

forEach(forEachFn, thisArg)

Iterate over all entities.

Method parameters:
Name Type Argument Description
forEachFn Function

Iteration function.

thisArg * <optional>

Context to which to bind forEachFn.

Return value:
Type Description
Query

A reference to itself for chaining.

Details
Since Source
3.0.0 Query.js, line 602

get(keyList, opts)

Find the entity or entities that match the provided key.

Method parameters:
Name Type Argument Description
keyList Array

Key(s) defining the entity to retrieve. If keyList is not an array (i.e. for a single-value key), it will be wrapped in an array.

opts Object <optional>

Configuration options.

Properties
Name Type Argument Description
string String <optional>

Name of the secondary index to use in the query. If no index is specified, the main index is used.

Return value:
Type Description
Query

A reference to itself for chaining.

Details
Since Source
3.0.0 Query.js, line 616
Examples

const entities = query.get(25).run()

const entities = query.get([25]).run()

const activeAdmins = query.get(['active', 'admin'], {
  index: 'activityAndRoles'
}).run()

const niceDays = query.get(['sunny', 'humid', 'calm'], {
  index: 'weatherConditions'
}).run()

getAll(keyList, opts)

Find the entity or entities that match the provided keyLists.

Method parameters:
Name Type Argument Description
keyList Array <optional>
<repeatable>

Provide one or more keyLists, and all entities matching each keyList will be retrieved. If no keyLists are provided, all entities will be returned.

opts Object <optional>

Configuration options.

Properties
Name Type Argument Description
index String <optional>

Name of the secondary index to use in the query. If no index is specified, the main index is used.

Return value:
Type Description
Query

A reference to itself for chaining.

Details
Since Source
3.0.0 Query.js, line 662
Examples

const posts = query.getAll('draft', 'inReview', { index: 'status' }).run()

const posts = query.getAll(['draft'], ['inReview'], { index: 'status' }).run()

getData()

Return the current data result of this query.

Return value:
Type Description
Array

The data in this query.

Details
Since Source
3.0.0 Query.js, line 702

like(pattern, flags)

Implementation used by the like operator. Takes a pattern and flags and returns a RegExp instance that can test strings.

Method parameters:
Name Type Description
pattern String

Testing pattern.

flags String

Flags for the regular expression.

Return value:
Type Description
RegExp

Regular expression for testing strings.

Details
Since Source
3.0.0 Query.js, line 716

limit(num)

Limit the result.

Method parameters:
Name Type Description
num Number

The maximum number of entities to keep in the result.

Return value:
Type Description
Query

A reference to itself for chaining.

Details
Since Source
3.0.0 Query.js, line 730
Example

const store = new JSData.DataStore()
store.defineMapper('post')
const posts = [
  { author: 'John', age: 30, status: 'published', id: 1 },
  { author: 'Sally', age: 31, status: 'draft', id: 2 },
  { author: 'Mike', age: 32, status: 'draft', id: 3 },
  { author: 'Adam', age: 33, status: 'deleted', id: 4 },
  { author: 'Adam', age: 33, status: 'draft', id: 5 }
]
store.add('post', posts)
const results = store.query('post').limit(2).run()
console.log(results)

log(level, args)

Log the provided values. By default sends values to console[level]. Debug-level logs are only logged if Component#debug is true.

Will attempt to use appropriate console methods if they are available.

Method parameters:
Name Type Argument Description
level String

Log level.

args * <optional>
<repeatable>

Values to log.

Details
Since Source
3.0.0 Component.js, line 134
Inherited From:

map(mapFn, thisArg)

Apply a mapping function to the result data.

Method parameters:
Name Type Argument Description
mapFn Function

Mapping function.

thisArg * <optional>

Context to which to bind mapFn.

Return value:
Type Description
Query

A reference to itself for chaining.

Details
Since Source
3.0.0 Query.js, line 761
Example
// Return the age of all users
const store = new JSData.DataStore()
store.defineMapper('user')
const users = [
  { name: 'Peter', age: 25, id: 1 },
  { name: 'Jim', age: 19, id: 2 },
  { name: 'Mike', age: 17, id: 3 },
  { name: 'Alan', age: 29, id: 4 },
  { name: 'Katie', age: 33, id: 5 }
]
store.add('post', posts)
const ages = store.query('user').map((user) => {
  return user.age
}).run()
console.log(ages)

mapCall(funcName)

Return the result of calling the specified function on each item in this collection's main index.

Method parameters:
Name Type Description
funcName String

Name of function to call

Return value:
Type Description
Query

A reference to itself for chaining.

Details
Since Source
3.0.0 Query.js, line 792
Example
const stringAges = UserCollection.query().mapCall('toString').run()

off(event, listener)

Remove an event listener from this Component. If no listener is provided, then all listeners for the specified event will be removed. If no event is specified then all listeners for all events will be removed.

Method parameters:
Name Type Argument Description
event String <optional>

Name of event to unsubsribe to.

listener Function <optional>

Listener to remove.

Details
Since Source
3.0.0 Component.js, line 180
Inherited From:
Examples
// Remove a particular listener for a particular event
collection.off('add', handler)
// Remove all listeners for a particular event
record.off('change')
// Remove all listeners to all events
store.off()

on(event, listener, ctx)

Register a new event listener on this Component.

Method parameters:
Name Type Argument Description
event String

Name of event to subsribe to.

listener Function

Listener function to handle the event.

ctx * <optional>

Optional content in which to invoke the listener.

Details
Since Source
3.0.0 Component.js, line 147
Inherited From:
Examples
// Listen for all "afterCreate" events in a DataStore
store.on('afterCreate', (mapperName, props, opts, result) => {
  console.log(mapperName) // "post"
  console.log(props.id) // undefined
  console.log(result.id) // 1234
})
store.create('post', { title: 'Modeling your data' }).then((post) => {
  console.log(post.id) // 1234
})
// Listen for the "add" event on a collection
collection.on('add', (records) => {
  console.log(records) // [...]
})
// Listen for "change" events on a record
post.on('change', (record, changes) => {
  console.log(changes) // { changed: { title: 'Modeling your data' } }
})
post.title = 'Modeling your data'

run()

Complete the execution of the query and return the resulting data.

Return value:
Type Description
Array

The result of executing this query.

Details
Since Source
3.0.0 Query.js, line 812

skip(num)

Skip a number of results.

Method parameters:
Name Type Description
num Number

The number of entities to skip.

Return value:
Type Description
Query

A reference to itself for chaining.

Details
Since Source
3.0.0 Query.js, line 825
Example

const store = new JSData.DataStore()
store.defineMapper('post')
const posts = [
  { author: 'John', age: 30, status: 'published', id: 1 },
  { author: 'Sally', age: 31, status: 'draft', id: 2 },
  { author: 'Mike', age: 32, status: 'draft', id: 3 },
  { author: 'Adam', age: 33, status: 'deleted', id: 4 },
  { author: 'Adam', age: 33, status: 'draft', id: 5 }
]
store.add('post', posts)
const results = store.query('post').skip(2).run()
console.log(results)