-
Notifications
You must be signed in to change notification settings - Fork 13
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Add queryable interfaces #30
Merged
Merged
Changes from all commits
Commits
Show all changes
21 commits
Select commit
Hold shift + click to select a range
b962f59
Add initial draft interfaces for the query spec
rubensworks e30f83b
Move all mutability methods to Bindings
rubensworks e2d62fc
Tweak queryable interfaces based on implementation tests
rubensworks bc7163e
Add changelog for addition of queryable interfaces
rubensworks 5577666
Enter prerelease mode and version packages
rubensworks 4e5bafb
Make GitHub CI also publish prereleases from feature/query branch
rubensworks 71ee4ea
Allow supported metadata types to be overridden
rubensworks 1a2e38e
Add TODO to merge Stream types
rubensworks 60ff070
Release 1.1.0-next.1
rubensworks f64f002
Temporarily remove filterable typings
rubensworks d32e71c
Also allow Bindings interaction via strings
rubensworks 2b8f571
Fix typo in SparqlQueryable tsdoc
rubensworks 762a892
Add tests for queryable interface
rubensworks 3b7ba40
modularizes Queryable and SparqlQueryable interfaces
jacoscaz 61f5a6a
mentions the difference between queries provided as strings and queri…
jacoscaz d7ba23c
adds support for multiple algebra types, drops conceptual dependency …
jacoscaz a666eab
updates test to use modularized interfaces
jacoscaz 186c2b7
adds tests for Algebra interfaces
jacoscaz d47c8b1
drops redundant semicolons
jacoscaz 567ae66
Merge pull request #32 from jacoscaz/feature/query-separate-interfaces
rubensworks 09ad631
Exit prerelease mode
rubensworks File filter
Filter by extension
Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
There are no files selected for viewing
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,5 @@ | ||
--- | ||
"@rdfjs/types": patch | ||
--- | ||
|
||
Make queryable metadata types configurable |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,13 @@ | ||
{ | ||
"mode": "exit", | ||
"tag": "next", | ||
"initialVersions": { | ||
"@rdfjs/types": "1.0.1" | ||
}, | ||
"changesets": [ | ||
"friendly-lies-suffer", | ||
"long-files-look", | ||
"seven-shrimps-build", | ||
"tough-guests-flash" | ||
] | ||
} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,5 @@ | ||
--- | ||
"@rdfjs/types": minor | ||
--- | ||
|
||
Add queryable interfaces |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
|
@@ -4,6 +4,7 @@ on: | |
push: | ||
branches: | ||
- master | ||
- feature/query | ||
|
||
jobs: | ||
release: | ||
|
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
|
@@ -3,3 +3,4 @@ | |
export * from './data-model'; | ||
export * from './stream'; | ||
export * from './dataset'; | ||
export * from './query'; |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,7 @@ | ||
/* Query Interfaces */ | ||
/* https://rdf.js.org/query-spec/ */ | ||
|
||
export * from './query/common'; | ||
export * from './query/queryable'; | ||
|
||
|
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,287 @@ | ||
/* Query Interfaces - Common */ | ||
/* https://rdf.js.org/query-spec/ */ | ||
|
||
import { EventEmitter } from "events"; | ||
import * as RDF from '../data-model'; | ||
|
||
/** | ||
* Helper union type for quad term names. | ||
*/ | ||
export type QuadTermName = 'subject' | 'predicate' | 'object' | 'graph'; | ||
|
||
// TODO: merge this with Stream upon the next major change | ||
/** | ||
* Custom typings for the RDF/JS ResultStream interface as the current | ||
* typings restrict the generic param Q to extensions of "BaseQuad", | ||
* meaning it cannot be used for Bindings. | ||
*/ | ||
export interface ResultStream<Q> extends EventEmitter { | ||
read(): Q | null; | ||
jacoscaz marked this conversation as resolved.
Show resolved
Hide resolved
|
||
} | ||
|
||
/** | ||
* QueryOperationCost represents the cost of a given query operation. | ||
*/ | ||
export interface QueryOperationCost { | ||
/** | ||
* An estimation of how many iterations over items are executed. | ||
* This is used to determine the CPU cost. | ||
*/ | ||
iterations: number; | ||
/** | ||
* An estimation of how many items are stored in memory. | ||
* This is used to determine the memory cost. | ||
*/ | ||
persistedItems: number; | ||
/** | ||
* An estimation of how many items block the stream. | ||
* This is used to determine the time the stream is not progressing anymore. | ||
*/ | ||
blockingItems: number; | ||
/** | ||
* An estimation of the time to request items from sources. | ||
* This is used to determine the I/O cost. | ||
*/ | ||
requestTime: number; | ||
/** | ||
* Custom properties | ||
*/ | ||
[key: string]: any; | ||
} | ||
|
||
/** | ||
* QueryOperationOrder represents an ordering of the results of a given query operation. | ||
* | ||
* These objects can represent orderings of both quad and bindings streams, | ||
* respectively identified by quad term names and variables. | ||
*/ | ||
export interface QueryOperationOrder<T extends QuadTermName | RDF.Variable> { | ||
cost: QueryOperationCost; | ||
terms: { term: T, direction: 'asc' | 'desc' }[]; | ||
} | ||
|
||
/** | ||
* QueryResultCardinality represents the number of results, which can either be an estimate or exact value. | ||
*/ | ||
export interface QueryResultCardinality { | ||
/** | ||
* indicates the type of counting that was done, and MUST either be "estimate" or "exact". | ||
*/ | ||
type: 'estimate' | 'exact'; | ||
|
||
/** | ||
* Indicates an estimated of the number of results in the stream if type = "estimate", | ||
* or the exact number of results in the stream if type = "exact". | ||
*/ | ||
value: number; | ||
} | ||
|
||
/** | ||
* BaseMetadataQuery is helper interface that provides a metadata callback. | ||
*/ | ||
interface BaseMetadataQuery<OrderItemsType extends QuadTermName | RDF.Variable, AdditionalMetadataType extends unknown, SupportedMetadataType> { | ||
/** | ||
* Asynchronously return metadata of the current result. | ||
*/ | ||
metadata<M extends MetadataOpts<SupportedMetadataType>>(opts?: M): Promise<ConditionalMetadataType<AdditionalMetadataType, M, OrderItemsType>>; | ||
} | ||
|
||
export type AllMetadataSupport = CardinalityMetadataSupport & OrderMetadataSupport & AvailableOrdersMetadataSupport; | ||
export type CardinalityMetadataSupport = { cardinality: true }; | ||
export type OrderMetadataSupport = { order: true }; | ||
export type AvailableOrdersMetadataSupport = { availableOrders: true }; | ||
|
||
export type MetadataOpts<SupportedMetadataType> = | ||
(SupportedMetadataType extends CardinalityMetadataSupport ? CardinalityMetadataOpts : unknown) | | ||
(SupportedMetadataType extends OrderMetadataSupport ? OrderMetadataOpts : unknown) | | ||
(SupportedMetadataType extends AvailableOrdersMetadataSupport ? AvailableOrdersMetadataOpts : unknown); | ||
export interface CardinalityMetadataOpts { cardinality: 'estimate' | 'exact'; } | ||
export interface OrderMetadataOpts { order: true; } | ||
export interface AvailableOrdersMetadataOpts { availableOrders: true; } | ||
|
||
export type ConditionalMetadataType<AdditionalMetadataType, M, OrderItemsType extends QuadTermName | RDF.Variable> = AdditionalMetadataType | ||
& (M extends CardinalityMetadataOpts ? { cardinality: QueryResultCardinality } : Record<string, unknown>) | ||
& (M extends OrderMetadataOpts ? { order: QueryOperationOrder<OrderItemsType>['terms'] } : Record<string, unknown>) | ||
& (M extends AvailableOrdersMetadataOpts ? { availableOrders: QueryOperationOrder<OrderItemsType>[] } : Record<string, unknown>); | ||
|
||
jacoscaz marked this conversation as resolved.
Show resolved
Hide resolved
|
||
/** | ||
* Options that can be passed when executing a query. | ||
*/ | ||
export interface QueryExecuteOptions<OrderItemsType extends QuadTermName | RDF.Variable> { | ||
/** | ||
* The required order for the result stream. | ||
*/ | ||
order?: QueryOperationOrder<OrderItemsType>; | ||
|
||
/** | ||
* Custom properties | ||
*/ | ||
[key: string]: any; | ||
} | ||
|
||
/** | ||
* Generic interface that defines query objects following the Future pattern. | ||
*/ | ||
export interface BaseQuery { | ||
/** | ||
* Identifier for the type of result of tis query. | ||
*/ | ||
resultType: string; | ||
|
||
/** | ||
* Returns either a stream containing all the items that match the given query, | ||
* a boolean or void depending on the semantics of the given query. | ||
*/ | ||
execute(opts?: any): Promise<ResultStream<any> | boolean | void>; | ||
} | ||
|
||
/** | ||
* Query object that returns bindings. | ||
*/ | ||
export interface QueryBindings<SupportedMetadataType> extends BaseQuery, BaseMetadataQuery<RDF.Variable, { variables: RDF.Variable[] }, SupportedMetadataType> { | ||
resultType: 'bindings'; | ||
execute(opts?: QueryExecuteOptions<RDF.Variable>): Promise<ResultStream<Bindings>>; | ||
} | ||
|
||
/** | ||
* Query object that returns quads. | ||
*/ | ||
export interface QueryQuads<SupportedMetadataType> extends BaseQuery, BaseMetadataQuery<QuadTermName, unknown, SupportedMetadataType> { | ||
resultType: 'quads'; | ||
execute(opts?: QueryExecuteOptions<QuadTermName>): Promise<ResultStream<RDF.Quad>>; | ||
} | ||
|
||
/** | ||
* Query object that returns a boolean. | ||
*/ | ||
export interface QueryBoolean extends BaseQuery { | ||
resultType: 'boolean'; | ||
execute(): Promise<boolean>; | ||
} | ||
|
||
/** | ||
* Query object that returns void. | ||
*/ | ||
export interface QueryVoid extends BaseQuery { | ||
resultType: 'void'; | ||
execute(): Promise<void>; | ||
} | ||
|
||
/** | ||
* Union type for the different query types. | ||
*/ | ||
export type Query<SupportedMetadataType> = QueryBindings<SupportedMetadataType> | QueryBoolean | QueryQuads<SupportedMetadataType> | QueryVoid; | ||
|
||
/** | ||
* Bindings represents the mapping of variables to RDF values using an immutable Map-like representation. | ||
* This means that methods such as `set` and `delete` do not modify this instance, | ||
* but they return a new Bindings instance that contains the modification. | ||
* | ||
* Bindings instances are created using a BindingsFactory. | ||
* | ||
* The internal order of variable-value entries is undefined. | ||
*/ | ||
export interface Bindings extends Iterable<[RDF.Variable, RDF.Term]> { | ||
rubensworks marked this conversation as resolved.
Show resolved
Hide resolved
|
||
type: 'bindings'; | ||
/** | ||
* Check if a binding exist for the given variable. | ||
* @param key A variable term or string. If it is a string, no `?` prefix must be given. | ||
*/ | ||
has: (key: RDF.Variable | string) => boolean; | ||
/** | ||
* Obtain the binding value for the given variable. | ||
* @param key A variable term or string. If it is a string, no `?` prefix must be given. | ||
*/ | ||
get: (key: RDF.Variable | string) => RDF.Term | undefined; | ||
/** | ||
* Create a new Bindings object by adding the given variable and value mapping. | ||
* | ||
* If the variable already exists in the binding, then the existing mapping is overwritten. | ||
* | ||
* @param key The variable key term or string. If it is a string, no `?` prefix must be given. | ||
* @param value The value. | ||
*/ | ||
set: (key: RDF.Variable | string, value: RDF.Term) => Bindings; | ||
/** | ||
* Create a new Bindings object by removing the given variable. | ||
* | ||
* If the variable does not exist in the binding, a copy of the Bindings object is returned. | ||
* | ||
* @param key The variable key term or string. If it is a string, no `?` prefix must be given. | ||
*/ | ||
delete: (key: RDF.Variable | string) => Bindings; | ||
/** | ||
* Obtain all variables for which mappings exist. | ||
*/ | ||
keys: () => Iterable<RDF.Variable>; | ||
/** | ||
* Obtain all values that are mapped to. | ||
*/ | ||
values: () => Iterable<RDF.Term>; | ||
/** | ||
* Iterate over all variable-value pairs. | ||
* @param fn A callback that is called for each variable-value pair | ||
* with value as first argument, and variable as second argument. | ||
*/ | ||
forEach: (fn: (value: RDF.Term, key: RDF.Variable) => any) => void; | ||
/** | ||
* The number of variable-value pairs. | ||
*/ | ||
size: number; | ||
/** | ||
* Iterator over all variable-value pairs. | ||
*/ | ||
[Symbol.iterator]: () => Iterator<[RDF.Variable, RDF.Term]>; | ||
/** | ||
* Check if all entries contained in this Bindings object are equal to all entries in the other Bindings object. | ||
* @param other A Bindings object. | ||
*/ | ||
equals(other: Bindings | null | undefined): boolean; | ||
/** | ||
* Create a new Bindings object by filtering entries using a callback. | ||
* @param fn A callback that is applied on each entry. | ||
* Returning true indicates that this entry must be contained in the resulting Bindings object. | ||
*/ | ||
filter: (fn: (value: RDF.Term, key: RDF.Variable) => boolean) => Bindings; | ||
/** | ||
* Create a new Bindings object by mapping entries using a callback. | ||
* @param fn A callback that is applied on each entry, in which the original value is replaced by the returned value. | ||
*/ | ||
map: (fn: (value: RDF.Term, key: RDF.Variable) => RDF.Term) => Bindings; | ||
/** | ||
* Merge this bindings with another. | ||
* | ||
* If a merge conflict occurs (this and other have an equal variable with unequal value), | ||
* then undefined is returned. | ||
* | ||
* @param other A Bindings object. | ||
*/ | ||
merge: (other: Bindings) => Bindings | undefined; | ||
/** | ||
* Merge this bindings with another, where merge conflicts can be resolved using a callback function. | ||
* @param merger A function that is invoked when a merge conflict occurs, | ||
* for which the returned value is considered the merged value. | ||
* @param other A Bindings object. | ||
*/ | ||
mergeWith: ( | ||
merger: (self: RDF.Term, other: RDF.Term, key: RDF.Variable) => RDF.Term, | ||
other: Bindings, | ||
) => Bindings; | ||
} | ||
|
||
/** | ||
* BindingsFactory can create new instances of Bindings. | ||
*/ | ||
export interface BindingsFactory { | ||
/** | ||
* Create a new Bindings object from the given variable-value entries. | ||
* @param entries An array of entries, where each entry is a tuple containing a variable and a term. | ||
*/ | ||
bindings: (entries?: [RDF.Variable, RDF.Term][]) => Bindings; | ||
|
||
/** | ||
* Create a copy of the given bindings object using this factory. | ||
* @param bindings A Bindings object. | ||
*/ | ||
fromBindings: (bindings: Bindings) => Bindings; | ||
} |
Oops, something went wrong.
Add this suggestion to a batch that can be applied as a single commit.
This suggestion is invalid because no changes were made to the code.
Suggestions cannot be applied while the pull request is closed.
Suggestions cannot be applied while viewing a subset of changes.
Only one suggestion per line can be applied in a batch.
Add this suggestion to a batch that can be applied as a single commit.
Applying suggestions on deleted lines is not supported.
You must change the existing code in this line in order to create a valid suggestion.
Outdated suggestions cannot be applied.
This suggestion has been applied or marked resolved.
Suggestions cannot be applied from pending reviews.
Suggestions cannot be applied on multi-line comments.
Suggestions cannot be applied while the pull request is queued to merge.
Suggestion cannot be applied right now. Please check back later.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Aha! This will be the real last comment. Should the
pre
take be removed or are you intending another prerelease?There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Yes, will remove.