summary refs log tree commit diff
path: root/spec/spore_impl.pod
blob: 3e8aa6974ad80ebc618f2a73ec81724927610125 (plain) (blame)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
214
215
216
217
218
219
220
221
222
223
224
225
226
227
228
229
230
231
232
233
234
235
236
237
238
239
240
241
242
243
244
245
246
247
248
249
250
=encoding utf-8

=head1 NAME

Spore (Specifications to a POrtable Rest Environment) Client Implementation

=head1 ABSTRACT

Spore is a specification for describing ReST API that can be parsed and used
automatically by client implementations to communicate with the descibed API.

This document describes what features are required in a Spore client
implementation.

=head1 TERMINOLOGY

=over 4

=item API

An I<API> is a ReST application that can exchange data with client
applications over http/https. It presents one or more method endpoints which
accept http requests with varying headers, parameters and body content to
perform specific operations.

=item Client implementation

A I<Client implementation> is a library targeting a specific system or
language. It can use I<Descriptions files> to create programmatic interfaces
usable in applications.

=item Description file

A I<Description file> is a file in JSON format describing an I<API> (see
specification). It can directly be used by a  I<Client implementation> to
create a programmatic interface in the target system.

=item Middleware

A I<Middleware> is Spore component that is added to the workflow of
the I<Client implementation> to modify the I<Requests> and
I<responses> sent and received. It can also shortcircuit the rest of
the workflow if needed. It can be thought of a plugin to extend Spore.

=item Request

A I<Request> is a data structure that contains standardized data and
metadata inspired by the CGI specification. It is used by the I<Client
implementation> to create the http request that will be sent to the
I<API>.

=item Response

A I<Response> is a data structure that contains standardized data and
metadata inspired by the CGI specification. It is created from the
http response sent by the I<API> and is used after being processed by
the I<Middlewares> to create the structure returned to the user.

=back

=head1 SPECIFICATION

=head2 Client Implementation

A I<Client implementation> B<MUST> provide a function or method
(eg. new_from_spec) to generate the specific API methods in the target
system by reading the JSON string from a I<Description file> (and
optionaly directly from the file itself).

A I<Client implementation> B<MUST> also provide a method to enable or
disable spore middlewares at runtime. The order in which the
middlewares are enambled  is the order in which the request will go
through each middleware, and the inverse order in which the response
will go through each optional middleware postprocessing callback.

  If middlewares I<A>, I<B> and I<C> were enabled in this order, then
  the processing order will be:
    I<A>, I<B>, I<C> ... make request ... I<C>, I<B>, I<A>

=head2 Middleware

Each middleware B<MUST> accept arbitrary initialization parameters. It
B<MUST> also provide a function to which the request environment or an
object containing it will be passed. The function can have 3 types of
return values :

=over 4

=item Nothing

Control is passed to the next middleware in the chain.

=item A callback

Control is passed to the next middleware in the chain. The callback is
stored and will be passed the response later on after the request is
made.

=item A response

The response is directly passed to the first stored callback in the
chain. No further middlewares are used and no request is sent. Useful
if a middleware needs to shortcicuit the remaining of the chain, for
testing or caching purpose for exemple.

=back

=head3 The Request environment

The request environment B<MUST> be a data structure that includes
CGI-like headers, as detailed below. Each middleware is free to modify
the environment. The environment B<MUST> include these keys (adopted
from L<PEP 333|http://www.python.org/dev/peps/pep-0333/>,
L<Rack|http://rack.rubyforge.org/doc/files/SPEC.html>,
L<PSGI|http://search.cpan.org/perldoc?PSGI> and
L<JSGI|http://jackjs.org/jsgi-spec.html>) except when they would
normally be empty. The environment is used by the I<Client
implementation> to build the final http request that will be sent to
the I<API>.

=over 4

=item *

C<REQUEST_METHOD>: The HTTP request method, such as "GET" or
"POST". This B<MUST NOT> be an empty string, and so is always
required.

=item *

C<SCRIPT_NAME>: The initial portion of the base URL's path, minus the
schema and domain name. This tells the client what is the API virtual
"location". This may be an empty string if the method corresponds to
the server's root URI.

If this key is not empty, it B<MUST> start with a forward slash (C</>).

=item *

C<PATH_INFO>: The remainder of the request URL's path, designating the
virtual "location" of the request's target within the API. This may be
an empty string if the request URL targets the application root and
does not have a trailing slash. It still contains the placeholders
which will be interpolated later with the params.

If this key is not empty, it B<MUST> start with a forward slash (C</>).

=item *

C<REQUEST_URI>: The undecoded, raw request URL line. It is the raw URI
path and query part that appears in the HTTP C<GET /... HTTP/1.x> line
and doesn't contain URI scheme and host names. It still contains the
placeholders which will be interpolated later with the params.

=item *

C<SERVER_NAME>, C<SERVER_PORT>: When combined with C<SCRIPT_NAME> and
C<PATH_INFO>, these keys can be used to complete the URL. Note,
however, that C<HTTP_HOST>, if present, should be used in preference
to C<SERVER_NAME> for reconstructing the request URL. C<SERVER_NAME>
and C<SERVER_PORT> B<MUST NOT> be empty strings, and are always
required.

=item *

C<SERVER_PROTOCOL>: The version of the protocol the client used to
send the request. Typically this will be something like "HTTP/1.0" or
"HTTP/1.1" and may be used by the middlewares to determine how to
treat any HTTP request headers.

=item *

C<QUERY_STRING>: The portion of the request URL that follows the ?, if
any. May be empty, but is always required. It will always be empty
before the request is actually made and sent.

=item *

C<spore.payload>: The actual content body of the call. Modified in
place by the middlewares.

=item *

C<spore.params>: A list of key/value pairs. These will be interpolated
in the url with the placeholders when the request is made. The rest of
them will be used in the C<QUERY_STRING> part of the uri. B>MAY> be
empty but B<MUST> always be present.

=item *

C<spore.scheme>: !!! Check if url_scheme !! The scheme of the url.


=item *

C<spore.scheme>: !!! Check if url_scheme !! The scheme of the url.

=back

=head1 CHANGELOGS

0.1: 2010.10.xx

=over 4

=item *

Initial version.

=back

=head1 ACKNOWLEDGEMENTS

Some parts of this specification are adopted from the following specifications.

=over 4

=item *

PSGI Specification L<PSGI|http://search.cpan.org/perldoc?PSGI>

=item *

PEP333 Python Web Server Gateway Interface L<http://www.python.org/dev/peps/pep-0333>

=item *

Rack L<http://rack.rubyforge.org/doc/SPEC.html>

=item *

JSGI Specification L<http://jackjs.org/jsgi-spec.html>

=back

I'd like to thank authors of these great documents.

=head1 AUTHOR

XXX

=head1 CONTRIBUTORS

=head1 COPYRIGHT AND LICENSE

Copyright XXX, 2010.

This document is licensed under the Creative Commons license by-sa.

=cut