Skip to content

Commit 115d1e6

Browse files
author
Alexandre Daubois
committed
Add psr/query draft
1 parent a1a0674 commit 115d1e6

File tree

1 file changed

+173
-0
lines changed

1 file changed

+173
-0
lines changed

proposed/query.md

+173
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,173 @@
1+
Common Interface for data querying
2+
==================================
3+
4+
This document describes common interfaces to query data. These data can be from different sources, from in-memory data to databases, as well as filesystem files.
5+
6+
The key words "MUST", "MUST NOT", "REQUIRED", "SHALL", "SHALL NOT", "SHOULD",
7+
"SHOULD NOT", "RECOMMENDED", "MAY", and "OPTIONAL" in this document are to be
8+
interpreted as described in [RFC 2119][].
9+
10+
The final implementations MAY decorate the objects with more
11+
functionality than the one proposed but they MUST implement the indicated
12+
interfaces/functionality first.
13+
14+
[RFC 2119]: http://tools.ietf.org/html/rfc2119
15+
16+
## 1. Specification
17+
18+
### 1.1 Goal
19+
20+
There are numerous ways of querying data from so many sources. Each system has its very own way of doing it. For instance, Doctrine ORM and Symfony Finder are both querying data with query builders (or alike), but there is no standardized interface to implement such data querying.
21+
22+
The goal of this PSR it to define common interfaces to query data, no matter where they come from (arrays, iterators, etc.) or their format.
23+
24+
### 1.2 Definitions
25+
26+
* **Query** - The object that will be used to query data. It receives a source as an `iterable`, which allows processing of arrays as well as other type of collections like generators.
27+
28+
* **Modifier** - A modifier is an action applied to the source, which will be executed before each operation. There can be multiple modifiers on a Query, for instance a `where` clause, an `order by`, a `limit` or even an `offset`. Operations are applied _after_ modifiers.
29+
30+
* **Operation** - An operation is a one-time action applied to a processed source, after all modifiers has been applied. An operation can return any type of data: generators, scalars, etc.
31+
32+
* **Context** - What holds additional information to be passed to the query, modifiers and operations in the case they need it.
33+
34+
## 2. Interfaces
35+
36+
### 2.1 QueryInterface
37+
38+
Has the ability to query an iterable source.
39+
40+
```php
41+
namespace Psr\Query;
42+
43+
use Psr\Query\QueryContextInterface;
44+
use Psr\Query\QueryModifierInterface;
45+
use Psr\Query\QueryOperationInterface;
46+
47+
/**
48+
* Defines an object which will execute modifiers and operations to query data.
49+
* A QueryInterface could receive any iterable depending on the implementation. This could go from the
50+
* basic array of data to generators.
51+
*/
52+
interface QueryInterface
53+
{
54+
/**namespace Psr\Query;
55+
* Creates a new object to query data.
56+
*
57+
* @param iterable $source
58+
* The source to apply manipulations on.
59+
*
60+
* @param QueryContextInterface|null $context
61+
* The optional context that forward needed information to the Query for its execution.
62+
*
63+
* @return QueryInterface
64+
*/
65+
public static function from(iterable $source, QueryContextInterface $context = null): QueryInterface;
66+
67+
/**
68+
* Get the context of the current Query, possibly modified by the latter.
69+
*
70+
* @return QueryContextInterface
71+
*/
72+
public function getContext(): QueryContextInterface;
73+
74+
/**
75+
* Gets the source of the Query.
76+
*
77+
* @return iterable
78+
*/
79+
public function getSource(): iterable;
80+
81+
/**
82+
* Applies a modifier to the Query.
83+
*
84+
* @param QueryModifierInterface $modifier
85+
* The actual modifier to apply.
86+
*
87+
* @return QueryInterface
88+
*/
89+
public function applyModifier(QueryModifierInterface $modifier): QueryInterface;
90+
91+
/**
92+
* Applies an operation to the Query.
93+
*
94+
* @param QueryOperationInterface $operation
95+
* The actual operation to apply.
96+
*
97+
* @return mixed
98+
*/
99+
public function applyOperation(QueryOperationInterface $operation): mixed;
100+
}
101+
```
102+
103+
### 2.2 QueryContextInterface
104+
105+
Has the ability to hold and transmit information to the Query, which would be needed for modifiers and operations to be applied.
106+
107+
```php
108+
namespace Psr\Query;
109+
110+
/**
111+
* Defines the context of a Query. This could be used to pass additional data to the query, such as
112+
* already used alias in the current Query context.
113+
*/
114+
interface QueryContextInterface
115+
{
116+
}
117+
```
118+
119+
### 2.3 QueryModifierInterface
120+
121+
Applies some modification on Query's source, before applying a final operation on the processed source.
122+
123+
```php
124+
namespace Psr\Query;
125+
126+
use Psr\Query\QueryInterface;
127+
128+
/**
129+
* Defines a Query modifier. A modifier is applied before any operation. This could be a `where` clause, as well
130+
* as an ordering, a shuffling, limiting the max number of results, etc.
131+
*/
132+
interface QueryModifierInterface
133+
{
134+
/**
135+
* Applies the modifier to the given source, and returns the result of this modifier.
136+
*
137+
* @param QueryInterface $query
138+
* The source to apply the modifier on.
139+
*
140+
* Optional context if needed by the modifier.
141+
*
142+
* @return iterable
143+
* The modified source.
144+
*/
145+
public function apply(QueryInterface $query): iterable;
146+
}
147+
```
148+
149+
### 2.4 QueryOperationInterface
150+
151+
Applies a final operation to source after modifiers has been applied, and returns the result. The result can be of any type, according to what the operation actually does.
152+
153+
```php
154+
namespace Psr\Query;
155+
156+
use Psr\Query\QueryInterface;
157+
158+
/**
159+
* Defines a final operation done to the source, after modifiers has been applied. An operation can be
160+
* a simple concatenation, selecting data, get an average/min/max value, etc.
161+
*/
162+
interface QueryOperationInterface
163+
{
164+
/**
165+
* @param QueryInterface $query
166+
* The source to apply the operation on.
167+
*
168+
* @return mixed
169+
* The result of the operation. This can be any type of data, depending on what the operation actually does.
170+
*/
171+
public function apply(QueryInterface $query): mixed;
172+
}
173+
```

0 commit comments

Comments
 (0)