Skip to content
Closed
Show file tree
Hide file tree
Changes from all commits
Commits
Show all changes
128 commits
Select commit Hold shift + click to select a range
abe28ae
Multipart parser (not updated to new interface yet)
WyriHaximus Oct 5, 2016
55dcb6e
Implement cancelable parser
WyriHaximus Oct 5, 2016
5ef8f76
Remove all listeners after emitting error in RequestHeaderParser (#68)
WyriHaximus Nov 9, 2016
0385533
Added 0.4.2 to changelog
WyriHaximus Nov 9, 2016
56f09cd
Removed testing against HHVM nightly (#66)
WyriHaximus Nov 30, 2016
409defb
Typo in $reques, should be $request
WyriHaximus Dec 16, 2016
a993fd1
Fixes #81 issue: data listener is removed if HeaderParser emits error…
Feb 5, 2017
a05c1c2
check max header size
nopolabs Feb 5, 2017
12a8282
add phpunit 4.8 to require-dev, force travisci to use local phpunit
nopolabs Feb 6, 2017
49b5794
replace getMock for forward compatibility
nopolabs Feb 6, 2017
d1c3356
ServerInterface is unnecessary
legionth Feb 7, 2017
9e03e07
Fix assertion in ServerTests
legionth Feb 7, 2017
9b10bd4
Remove unneeded type hints
legionth Feb 7, 2017
30ff0bf
Remove stubs from server tests
legionth Feb 9, 2017
7c51dd3
Remove unneeded stubs
legionth Feb 9, 2017
161b4d9
First class support for PHP7 and HHVM
clue Feb 9, 2017
9d32b26
Mock React\Socket\Server in tests
legionth Feb 9, 2017
474a540
2016-04-01: Let's support PHP 5.3, again..
clue Apr 1, 2016
91f327f
Added v0.4.3 to the changelog
WyriHaximus Feb 10, 2017
b8bf67c
Prepare v0.4.3 release
clue Feb 10, 2017
1d40eb7
Add request header accessors (à la PSR-7)
clue Oct 13, 2016
fb82059
Be explicit about differences with PSR-7
clue Feb 9, 2017
6c3b918
Fix headers to be handled case insensitive
clue Feb 9, 2017
92918e8
Documentation for writeContinue() and writeHead()
clue Feb 10, 2017
680b6a8
Forward pause/resume from request to connection
clue Feb 10, 2017
fa954ac
The Expect field-value is case-insensitive.
clue Feb 10, 2017
227aafc
Ignore 100-continue expectation for HTTP/1.0 requests
clue Feb 10, 2017
3915a67
Do not emit empty data events
clue Feb 9, 2017
6348a91
Ignore empty writes to not mess up chunked transfer encoding
clue Feb 9, 2017
5875cc5
Upgrade ringcentral/psr7 to 1.2
andig Feb 11, 2017
09927d4
Fix minimum phpunit version and allow v5
andig Feb 11, 2017
0c82c80
PhpUnit 5 compatibility
andig Feb 12, 2017
39e6d86
Test lowest version constraints
andig Feb 11, 2017
1229a7d
Prepare v0.4.4 release
clue Feb 13, 2017
6c112ef
Update Socket component to v0.5
clue Feb 5, 2017
ab21b35
Change Request methods to be in line with PSR-7
clue Feb 14, 2017
a55482a
Mark internal APIs as internal or private
clue Feb 15, 2017
c82b959
Secure HTTPS server example
clue Feb 5, 2017
eff46ec
Prepare v0.5.0 release
clue Feb 16, 2017
4781e6b
Update README.md
clue Feb 16, 2017
2eeebb6
Register all event listeners before notifying other listeners
clue Feb 16, 2017
7d550d4
Send HTTP status code 400 for invalid requests
clue Feb 16, 2017
50955ca
Closing request will now stop reading from connection
clue Feb 17, 2017
a96c349
Documentation for invalid request messages
clue Feb 18, 2017
0fdbc7c
Response uses same HTTP protocol version as corresponding request
clue Feb 17, 2017
6028c81
Apply chunked transfer encoding only for HTTP/1.1 responses by default
clue Feb 17, 2017
90a90e9
Ensure writeContinue() only works for HTTP/1.1 messages
clue Feb 17, 2017
b6e1964
Only support HTTP/1.1 and HTTP/1.0 requests
clue Feb 17, 2017
f027f18
Explicitly send Connection: close header for HTTP/1.1 messages
clue Feb 19, 2017
7b9bcbf
Add TestCase methods
legionth Feb 11, 2017
6d06957
Add Chunked Decoder class
legionth Feb 13, 2017
4378fe8
Add ChunkedDecoder to Server
legionth Feb 10, 2017
5a01f55
Validate Host header for HTTP/1.1 requests
clue Feb 17, 2017
b430246
The Server should always have a `request` listener
clue Feb 16, 2017
fdc7531
Request closes after forwarding close event
clue Feb 20, 2017
5ab993a
Send HTTP status code 431 if request header is too large
clue Feb 16, 2017
e7ccaca
Response closes after forwarding close event
clue Feb 20, 2017
68aeafe
RequestHeaderParser returns PSR-7 request
clue Feb 21, 2017
57dfe21
Inject PSR-7 request instance into Request class
clue Feb 21, 2017
60f8024
Add LenghtLimitedStream
legionth Feb 15, 2017
99b6faf
Handle Content-Length requests
legionth Feb 15, 2017
a3ce836
Ignore Content-Length if Transfer-Encoding isset instead of replacing
legionth Feb 19, 2017
ecf8ddf
Handle unexpected end in LengthLimitedStream
legionth Feb 21, 2017
eba363b
Request stream will now be handled internally
clue Feb 21, 2017
73e4a1b
Leading zeros are correct chunked encoding
legionth Feb 28, 2017
42747fe
Test error events from other streams on request object
legionth Mar 1, 2017
5867db4
Protect streams against close of other streams on error
legionth Feb 21, 2017
86c7130
Update README
legionth Mar 1, 2017
0222a6b
Handle events of simple requests
legionth Feb 22, 2017
9dbcfb8
Use PSR-7 approach to handle bodiless data
legionth Mar 2, 2017
29636f6
Remove TE and CL header before emitting the request event
legionth Mar 3, 2017
b6524db
Update README
legionth Mar 3, 2017
eafa635
Handle TE and CL in Response object
legionth Mar 3, 2017
3d2302b
Add system date 'Date' header if none isset
legionth Mar 3, 2017
cb52776
Only allow chunked-encoding for requests
legionth Mar 4, 2017
284e335
Add example to handle body data
legionth Mar 6, 2017
6043b24
Forward compatibility with Stream v0.5 and upcoming v0.6
clue Mar 8, 2017
ac74afa
Prepare v0.6.0 release
clue Mar 9, 2017
1680c7d
Update CHANGELOG.md
clue Mar 9, 2017
d8e98fa
Send '100 Continue' response automatically via Server
legionth Mar 9, 2017
0a90127
Use callback function instead of request event
legionth Feb 26, 2017
88ffd60
Replace Request class with PSR-7 Request
legionth Mar 7, 2017
30ab51f
Add tests to test case sensitivity
legionth Mar 20, 2017
d149199
Update documentation for RequestInterface
clue Mar 23, 2017
cf5c8ca
Simplify examples to ease getting started
clue Mar 24, 2017
1122c4a
Return Promise with PSR-7 Response resolving
legionth Mar 10, 2017
324356b
Handle Exception in callback function
legionth Mar 27, 2017
ed96b93
Adapt examples to always returning a promise
legionth Mar 27, 2017
e52ea38
Update README
legionth Mar 24, 2017
e21e946
Forward compatibility with upcoming Socket v0.6 and v0.7
clue Mar 30, 2017
9c38e42
Always use same HTTP protocol version for automatic error responses
clue Mar 30, 2017
ca19b02
Responses to HEAD requests and certain status codes never contain a body
clue Mar 30, 2017
5b9d143
Support asterisk-form request target for OPTIONS method
clue Mar 11, 2017
0f907ab
Certain status codes never contain a body length
clue Mar 30, 2017
625c51f
Support CONNECT method
clue Mar 29, 2017
ec43538
Update SocketClient to v0.7 to simplify CONNECT example
clue Apr 3, 2017
8f595b2
Replace deprecated SocketClient with new Socket component
clue Apr 4, 2017
fca4a6e
Fix tests to support new Socket v0.6 and up
clue Apr 6, 2017
1bb100e
Add benchmarking example
clue Apr 4, 2017
83e75bc
Use https-scheme for request URIs if secure TLS is used
clue Apr 3, 2017
e668e04
Replace Request with ServerRequest
legionth Apr 19, 2017
9dc6ab1
Update documentation
legionth Apr 19, 2017
c4463f5
Validate proxy requests in absolute-form
clue Mar 3, 2017
c77accb
Use socket address for URI if Host header is missing
clue Apr 18, 2017
440ab68
Simplify request validation by moving logic to RequestHeaderParser
clue Apr 21, 2017
d973e40
Sanitize Host header value across all requests
clue Apr 21, 2017
eac22d2
Move complete URI handling to RequestHeaderParser
clue Apr 21, 2017
75b7dee
Add server-side parameters to implementation
legionth Apr 21, 2017
be143dd
Update docs and add example
legionth Apr 23, 2017
e570bb6
Add query parameters to ServerRequest
legionth Apr 26, 2017
fa17cf7
Update README
legionth Apr 26, 2017
ee49ccb
Add function to parse cookies
legionth Apr 21, 2017
a180831
Parse cookie for request object
legionth Apr 21, 2017
190ebd4
Add description and example
legionth Apr 23, 2017
6a03ff4
Forward compatibility with Socket v1.0 and v0.8
clue May 6, 2017
8969bbf
Forward compatibility with Stream v1.0 and v0.7
clue May 12, 2017
3dcc5ec
Simplify buffering tests by using new react/promise-stream release
clue May 15, 2017
9a9971f
Ignore HHVM test failures for now until Travis tests work again
clue May 15, 2017
aaa70b0
Automatically cancel pending promises once client connection closes
clue May 21, 2017
93a963e
Send empty response body for closed response body stream
clue May 22, 2017
1573e89
Automatically close response stream if connection closes
clue May 23, 2017
4908d32
Validate request-target of CONNECT in RequestHeaderParser
clue May 22, 2017
961f8f0
Use duplex stream response body for CONNECT requests
clue May 22, 2017
b9ed029
Support Upgrade header such as `Upgrade: WebSocket` or custom protocols
clue May 12, 2017
9a8a536
Fix reporting listening addresses in examples
clue May 26, 2017
748e456
Add listen() method to support multiple listening sockets
clue May 27, 2017
f4bc564
Prepare v0.7.0 release
clue May 29, 2017
9ab8d84
Converted MultipartParser to use PSR-7 request with a HttpBodyStream
WyriHaximus May 31, 2017
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
18 changes: 12 additions & 6 deletions .travis.yml
Original file line number Diff line number Diff line change
@@ -1,21 +1,27 @@
language: php

php:
- 5.3
- 5.4
- 5.5
- 5.6
- 7
- hhvm
- hhvm-nightly

matrix:
include:
- php: 5.3
env:
- DEPENDENCIES=lowest
- php: 7.0
env:
- DEPENDENCIES=lowest
allow_failures:
- php: 7
- php: hhvm
- php: hhvm-nightly

before_script:
- composer install --dev --prefer-source
install:
- composer install --no-interaction
- if [ "$DEPENDENCIES" = "lowest" ]; then composer update --prefer-lowest -n; fi

script:
- phpunit --coverage-text
- ./vendor/bin/phpunit --coverage-text
295 changes: 294 additions & 1 deletion CHANGELOG.md
Original file line number Diff line number Diff line change
@@ -1,6 +1,299 @@
# Changelog

## 0.4.1 (2014-05-21)
## 0.7.0 (2017-05-29)

* Feature / BC break: Use PSR-7 (http-message) standard and
`Request-In-Response-Out`-style request handler callback.
Pass standard PSR-7 `ServerRequestInterface` and expect any standard
PSR-7 `ResponseInterface` in return for the request handler callback.
(#146 and #152 and #170 by @legionth)

```php
// old
$app = function (Request $request, Response $response) {
$response->writeHead(200, array('Content-Type' => 'text/plain'));
$response->end("Hello world!\n");
};

// new
$app = function (ServerRequestInterface $request) {
return new Response(
200,
array('Content-Type' => 'text/plain'),
"Hello world!\n"
);
};
```

A `Content-Length` header will automatically be included if the size can be
determined from the response body.
(#164 by @maciejmrozinski)

The request handler callback will automatically make sure that responses to
HEAD requests and certain status codes, such as `204` (No Content), never
contain a response body.
(#156 by @clue)

The intermediary `100 Continue` response will automatically be sent if
demanded by a HTTP/1.1 client.
(#144 by @legionth)

The request handler callback can now return a standard `Promise` if
processing the request needs some time, such as when querying a database.
Similarly, the request handler may return a streaming response if the
response body comes from a `ReadableStreamInterface` or its size is
unknown in advance.

```php
// old
$app = function (Request $request, Response $response) use ($db) {
$db->query()->then(function ($result) use ($response) {
$response->writeHead(200, array('Content-Type' => 'text/plain'));
$response->end($result);
});
};

// new
$app = function (ServerRequestInterface $request) use ($db) {
return $db->query()->then(function ($result) {
return new Response(
200,
array('Content-Type' => 'text/plain'),
$result
);
});
};
```

Pending promies and response streams will automatically be canceled once the
client connection closes.
(#187 and #188 by @clue)

The `ServerRequestInterface` contains the full effective request URI,
server-side parameters, query parameters and parsed cookies values as
defined in PSR-7.
(#167 by @clue and #174, #175 and #180 by @legionth)

```php
$app = function (ServerRequestInterface $request) {
return new Response(
200,
array('Content-Type' => 'text/plain'),
$request->getUri()->getScheme()
);
};
```

Advanced: Support duplex stream response for `Upgrade` requests such as
`Upgrade: WebSocket` or custom protocols and `CONNECT` requests
(#189 and #190 by @clue)

> Note that the request body will currently not be buffered and parsed by
default, which depending on your particilar use-case, may limit
interoperability with the PSR-7 (http-message) ecosystem.
The provided streaming request body interfaces allow you to perform
buffering and parsing as needed in the request handler callback.
See also the README and examples for more details.

* Feature / BC break: Replace `request` listener with callback function and
use `listen()` method to support multiple listening sockets
(#97 by @legionth and #193 by @clue)

```php
// old
$server = new Server($socket);
$server->on('request', $app);

// new
$server = new Server($app);
$server->listen($socket);
```

* Feature: Support the more advanced HTTP requests, such as
`OPTIONS * HTTP/1.1` (`OPTIONS` method in asterisk-form),
`GET http://example.com/path HTTP/1.1` (plain proxy requests in absolute-form),
`CONNECT example.com:443 HTTP/1.1` (`CONNECT` proxy requests in authority-form)
and sanitize `Host` header value across all requests.
(#157, #158, #161, #165, #169 and #173 by @clue)

* Feature: Forward compatibility with Socket v1.0, v0.8, v0.7 and v0.6 and
forward compatibility with Stream v1.0 and v0.7
(#154, #163, #183, #184 and #191 by @clue)

* Feature: Simplify examples to ease getting started and
add benchmarking example
(#151 and #162 by @clue)

* Improve test suite by adding tests for case insensitive chunked transfer
encoding and ignoring HHVM test failures until Travis tests work again.
(#150 by @legionth and #185 by @clue)

## 0.6.0 (2017-03-09)

* Feature / BC break: The `Request` and `Response` objects now follow strict
stream semantics and their respective methods and events.
(#116, #129, #133, #135, #136, #137, #138, #140, #141 by @legionth
and #122, #123, #130, #131, #132, #142 by @clue)

This implies that the `Server` now supports proper detection of the request
message body stream, such as supporting decoding chunked transfer encoding,
delimiting requests with an explicit `Content-Length` header
and those with an empty request message body.

These streaming semantics are compatible with previous Stream v0.5, future
compatible with v0.5 and upcoming v0.6 versions and can be used like this:

```php
$http->on('request', function (Request $request, Response $response) {
$contentLength = 0;
$request->on('data', function ($data) use (&$contentLength) {
$contentLength += strlen($data);
});

$request->on('end', function () use ($response, &$contentLength){
$response->writeHead(200, array('Content-Type' => 'text/plain'));
$response->end("The length of the submitted request body is: " . $contentLength);
});

// an error occured
// e.g. on invalid chunked encoded data or an unexpected 'end' event
$request->on('error', function (\Exception $exception) use ($response, &$contentLength) {
$response->writeHead(400, array('Content-Type' => 'text/plain'));
$response->end("An error occured while reading at length: " . $contentLength);
});
});
```

Similarly, the `Request` and `Response` now strictly follow the
`close()` method and `close` event semantics.
Closing the `Request` does not interrupt the underlying TCP/IP in
order to allow still sending back a valid response message.
Closing the `Response` does terminate the underlying TCP/IP
connection in order to clean up resources.

You should make sure to always attach a `request` event listener
like above. The `Server` will not respond to an incoming HTTP
request otherwise and keep the TCP/IP connection pending until the
other side chooses to close the connection.

* Feature: Support `HTTP/1.1` and `HTTP/1.0` for `Request` and `Response`.
(#124, #125, #126, #127, #128 by @clue and #139 by @legionth)

The outgoing `Response` will automatically use the same HTTP version as the
incoming `Request` message and will only apply `HTTP/1.1` semantics if
applicable. This includes that the `Response` will automatically attach a
`Date` and `Connection: close` header if applicable.

This implies that the `Server` now automatically responds with HTTP error
messages for invalid requests (status 400) and those exceeding internal
request header limits (status 431).

## 0.5.0 (2017-02-16)

* Feature / BC break: Change `Request` methods to be in line with PSR-7
(#117 by @clue)
* Rename `getQuery()` to `getQueryParams()`
* Rename `getHttpVersion()` to `getProtocolVersion()`
* Change `getHeaders()` to always return an array of string values
for each header

* Feature / BC break: Update Socket component to v0.5 and
add secure HTTPS server support
(#90 and #119 by @clue)

```php
// old plaintext HTTP server
$socket = new React\Socket\Server($loop);
$socket->listen(8080, '127.0.0.1');
$http = new React\Http\Server($socket);

// new plaintext HTTP server
$socket = new React\Socket\Server('127.0.0.1:8080', $loop);
$http = new React\Http\Server($socket);

// new secure HTTPS server
$socket = new React\Socket\Server('127.0.0.1:8080', $loop);
$socket = new React\Socket\SecureServer($socket, $loop, array(
'local_cert' => __DIR__ . '/localhost.pem'
));
$http = new React\Http\Server($socket);
```

* BC break: Mark internal APIs as internal or private and
remove unneeded `ServerInterface`
(#118 by @clue, #95 by @legionth)

## 0.4.4 (2017-02-13)

* Feature: Add request header accessors (à la PSR-7)
(#103 by @clue)

```php
// get value of host header
$host = $request->getHeaderLine('Host');

// get list of all cookie headers
$cookies = $request->getHeader('Cookie');
```

* Feature: Forward `pause()` and `resume()` from `Request` to underlying connection
(#110 by @clue)

```php
// support back-pressure when piping request into slower destination
$request->pipe($dest);

// manually pause/resume request
$request->pause();
$request->resume();
```

* Fix: Fix `100-continue` to be handled case-insensitive and ignore it for HTTP/1.0.
Similarly, outgoing response headers are now handled case-insensitive, e.g
we no longer apply chunked transfer encoding with mixed-case `Content-Length`.
(#107 by @clue)

```php
// now handled case-insensitive
$request->expectsContinue();

// now works just like properly-cased header
$response->writeHead($status, array('content-length' => 0));
```

* Fix: Do not emit empty `data` events and ignore empty writes in order to
not mess up chunked transfer encoding
(#108 and #112 by @clue)

* Lock and test minimum required dependency versions and support PHPUnit v5
(#113, #115 and #114 by @andig)

## 0.4.3 (2017-02-10)

* Fix: Do not take start of body into account when checking maximum header size
(#88 by @nopolabs)

* Fix: Remove `data` listener if `HeaderParser` emits an error
(#83 by @nick4fake)

* First class support for PHP 5.3 through PHP 7 and HHVM
(#101 and #102 by @clue, #66 by @WyriHaximus)

* Improve test suite by adding PHPUnit to require-dev,
improving forward compatibility with newer PHPUnit versions
and replacing unneeded test stubs
(#92 and #93 by @nopolabs, #100 by @legionth)

## 0.4.2 (2016-11-09)

* Remove all listeners after emitting error in RequestHeaderParser #68 @WyriHaximus
* Catch Guzzle parse request errors #65 @WyriHaximus
* Remove branch-alias definition as per reactphp/react#343 #58 @WyriHaximus
* Add functional example to ease getting started #64 by @clue
* Naming, immutable array manipulation #37 @cboden

## 0.4.1 (2015-05-21)

* Replaced guzzle/parser with guzzlehttp/psr7 by @cboden
* FIX Continue Header by @iannsp
* Missing type hint by @marenzo
Expand Down
Loading