This commit is contained in:
Manish Verma
2016-12-13 18:18:25 +05:30
parent fc98add11c
commit 2d8e640e9b
2314 changed files with 97798 additions and 75664 deletions

View File

@@ -1,54 +0,0 @@
# HTTP Client - Static Usage
## Overview
The `Zend\Http` component also provides `Zend\Http\ClientStatic`, a static HTTP client which exposes
a simplified API for quickly performing GET and POST operations:
## Quick Start
```php
use Zend\Http\ClientStatic;
// Simple GET request
$response = ClientStatic::get('http://example.org');
// More complex GET request, specifying query string 'foo=bar' and adding a
// custom header to request JSON data be returned (Accept: application/json)
$response = ClientStatic::get(
'http://example.org',
array('foo' => 'bar'),
array('Accept' => 'application/json')
);
// We can also do a POST request using the same format. Here we POST
// login credentials (username/password) to a login page:
$response = ClientStatic::post('https://example.org/login.php', array(
'username' => 'foo',
'password' => 'bar',
));
```
## Available Methods
**get**
`get(string $url, array $query = array(), array $headers = array(), mixed $body = null,
$clientOptions = null)`
Perform an HTTP `GET` request using the provided URL, query string variables, headers and request
body. The fifth parameter can be used to pass configuration options to the HTTP Client instance.
Returns Zend\\Http\\Response
<!-- -->
**post**
`post(string $url, array $params, array $headers = array(), mixed $body = null, $clientOptions =
null)`
Perform an HTTP `POST` request using the provided URL, parameters, headers and request body. The
fifth parameter can be used to pass configuration options to the HTTP Client instance.
Returns Zend\\Http\\Response

View File

@@ -1,451 +0,0 @@
# HTTP Client - Connection Adapters
## Overview
`Zend\Http\Client` is based on a connection adapter design. The connection adapter is the object in
charge of performing the actual connection to the server, as well as writing requests and reading
responses. This connection adapter can be replaced, and you can create and extend the default
connection adapters to suite your special needs, without the need to extend or replace the entire
*HTTP* client class, and with the same interface.
Currently, the `Zend\Http\Client` class provides four built-in connection adapters:
- `Zend\Http\Client\Adapter\Socket` (default)
- `Zend\Http\Client\Adapter\Proxy`
- `Zend\Http\Client\Adapter\Curl`
- `Zend\Http\Client\Adapter\Test`
The `Zend\Http\Client` object's adapter connection adapter is set using the 'adapter' configuration
option. When instantiating the client object, you can set the 'adapter' configuration option to a
string containing the adapter's name (eg. 'Zend\\Http\\Client\\Adapter\\Socket') or to a variable
holding an adapter object (eg. `new Zend\Http\Client\Adapter\Socket`). You can also set the adapter
later, using the `Zend\Http\Client->setAdapter()` method.
## The Socket Adapter
The default connection adapter is the `Zend\Http\Client\Adapter\Socket` adapter - this adapter will
be used unless you explicitly set the connection adapter. The Socket adapter is based on *PHP*'s
built-in fsockopen() function, and does not require any special extensions or compilation flags.
The Socket adapter allows several extra configuration options that can be set using
`Zend\Http\Client->setOptions()` or passed to the client constructor.
> ## Note
#### Persistent TCP Connections
Using persistent *TCP* connections can potentially speed up *HTTP* requests - but in most use cases,
will have little positive effect and might overload the *HTTP* server you are connecting to.
It is recommended to use persistent *TCP* connections only if you connect to the same server very
frequently, and are sure that the server is capable of handling a large number of concurrent
connections. In any case you are encouraged to benchmark the effect of persistent connections on
both the client speed and server load before using this option.
Additionally, when using persistent connections it is recommended to enable Keep-Alive *HTTP*
requests as described in \[the configuration section\](zend.http.client.options)- otherwise
persistent connections might have little or no effect.
#### note
#### HTTPS SSL Stream Parameters
`ssltransport`, `sslcert` and `sslpassphrase` are only relevant when connecting using *HTTPS*.
While the default *SSL* settings should work for most applications, you might need to change them if
the server you are connecting to requires special client setup. If so, you should read the sections
about *SSL* transport layers and options
[here](http://www.php.net/manual/en/transports.php#transports.inet).
**Changing the HTTPS transport layer**
```php
// Set the configuration parameters
$config = array(
'adapter' => 'Zend\Http\Client\Adapter\Socket',
'ssltransport' => 'tls'
);
// Instantiate a client object
$client = new Zend\Http\Client('https://www.example.com', $config);
// The following request will be sent over a TLS secure connection.
$response = $client->send();
```
The result of the example above will be similar to opening a *TCP* connection using the following
*PHP* command:
`fsockopen('tls://www.example.com', 443)`
### Customizing and accessing the Socket adapter stream context
`Zend\Http\Client\Adapter\Socket` provides direct access to the underlying [stream
context](http://php.net/manual/en/stream.contexts.php) used to connect to the remote server. This
allows the user to pass specific options and parameters to the *TCP* stream, and to the *SSL*
wrapper in case of *HTTPS* connections.
You can access the stream context using the following methods of `Zend\Http\Client\Adapter\Socket`:
> - **setStreamContext($context)** Sets the stream context to be used by the adapter. Can accept
either a stream context resource created using the
[stream\_context\_create()](http://php.net/manual/en/function.stream-context-create.php) *PHP*
function, or an array of stream context options, in the same format provided to this function.
Providing an array will create a new stream context using these options, and set it.
- **getStreamContext()** Get the stream context of the adapter. If no stream context was set, will
create a default stream context and return it. You can then set or get the value of different
context options using regular *PHP* stream context functions.
**Setting stream context options for the Socket adapter**
```php
// Array of options
$options = array(
'socket' => array(
// Bind local socket side to a specific interface
'bindto' => '10.1.2.3:50505'
),
'ssl' => array(
// Verify server side certificate,
// do not accept invalid or self-signed SSL certificates
'verify_peer' => true,
'allow_self_signed' => false,
// Capture the peer's certificate
'capture_peer_cert' => true
)
);
// Create an adapter object and attach it to the HTTP client
$adapter = new Zend\Http\Client\Adapter\Socket();
$client = new Zend\Http\Client();
$client->setAdapter($adapter);
// Method 1: pass the options array to setStreamContext()
$adapter->setStreamContext($options);
// Method 2: create a stream context and pass it to setStreamContext()
$context = stream_context_create($options);
$adapter->setStreamContext($context);
// Method 3: get the default stream context and set the options on it
$context = $adapter->getStreamContext();
stream_context_set_option($context, $options);
// Now, perform the request
$response = $client->send();
// If everything went well, you can now access the context again
$opts = stream_context_get_options($adapter->getStreamContext());
echo $opts['ssl']['peer_certificate'];
```
> ## Note
Note that you must set any stream context options before using the adapter to perform actual
requests. If no context is set before performing *HTTP* requests with the Socket adapter, a default
stream context will be created. This context resource could be accessed after performing any
requests using the `getStreamContext()` method.
## The Proxy Adapter
The `Zend\Http\Client\Adapter\Proxy` adapter is similar to the default Socket adapter - only the
connection is made through an *HTTP* proxy server instead of a direct connection to the target
server. This allows usage of `Zend\Http\Client` behind proxy servers - which is sometimes needed for
security or performance reasons.
Using the Proxy adapter requires several additional configuration parameters to be set, in addition
to the default 'adapter' option:
`proxy_host` should always be set - if it is not set, the client will fall back to a direct
connection using `Zend\Http\Client\Adapter\Socket`. `proxy_port` defaults to '8080' - if your proxy
listens on a different port you must set this one as well.
`proxy_user` and `proxy_pass` are only required if your proxy server requires you to authenticate.
Providing these will add a 'Proxy-Authentication' header to the request. If your proxy does not
require authentication, you can leave these two options out.
`proxy_auth` sets the proxy authentication type, if your proxy server requires authentication.
Possibly values are similar to the ones accepted by the `Zend\Http\Client::setAuth()` method.
Currently, only basic authentication (`Zend\Http\Client::AUTH_BASIC`) is supported.
**Using Zend\\Http\\Client behind a proxy server**
```php
// Set the configuration parameters
$config = array(
'adapter' => 'Zend\Http\Client\Adapter\Proxy',
'proxy_host' => 'proxy.int.zend.com',
'proxy_port' => 8000,
'proxy_user' => 'shahar.e',
'proxy_pass' => 'bananashaped'
);
// Instantiate a client object
$client = new Zend\Http\Client('http://www.example.com', $config);
// Continue working...
```
As mentioned, if `proxy_host` is not set or is set to a blank string, the connection will fall back
to a regular direct connection. This allows you to easily write your application in a way that
allows a proxy to be used optionally, according to a configuration parameter.
> ## Note
Since the proxy adapter inherits from `Zend\Http\Client\Adapter\Socket`, you can use the stream
context access method (see \[this section\](zend.http.client.adapters.socket.streamcontext)) to set
stream context options on Proxy connections as demonstrated above.
## The cURL Adapter
cURL is a standard *HTTP* client library that is distributed with many operating systems and can be
used in *PHP* via the cURL extension. It offers functionality for many special cases which can occur
for a *HTTP* client and make it a perfect choice for a *HTTP* adapter. It supports secure
connections, proxy, all sorts of authentication mechanisms and shines in applications that move
large files around between servers.
**Setting cURL options**
```php
$config = array(
'adapter' => 'Zend\Http\Client\Adapter\Curl',
'curloptions' => array(CURLOPT_FOLLOWLOCATION => true),
);
$client = new Zend\Http\Client($uri, $config);
```
By default the cURL adapter is configured to behave exactly like the Socket Adapter and it also
accepts the same configuration parameters as the Socket and Proxy adapters. You can also change the
cURL options by either specifying the 'curloptions' key in the constructor of the adapter or by
calling `setCurlOption($name, $value)`. The `$name` key corresponds to the CURL\_\* constants of the
cURL extension. You can get access to the Curl handle by calling `$adapter->getHandle();`
**Transfering Files by Handle**
You can use cURL to transfer very large files over *HTTP* by filehandle.
```php
$putFileSize = filesize("filepath");
$putFileHandle = fopen("filepath", "r");
$adapter = new Zend\Http\Client\Adapter\Curl();
$client = new Zend\Http\Client();
$client->setAdapter($adapter);
$client->setMethod('PUT');
$adapter->setOptions(array(
'curloptions' => array(
CURLOPT_INFILE => $putFileHandle,
CURLOPT_INFILESIZE => $putFileSize
)
));
$client->send();
```
## The Test Adapter
Sometimes, it is very hard to test code that relies on *HTTP* connections. For example, testing an
application that pulls an *RSS* feed from a remote server will require a network connection, which
is not always available.
For this reason, the `Zend\Http\Client\Adapter\Test` adapter is provided. You can write your
application to use `Zend\Http\Client`, and just for testing purposes, for example in your unit
testing suite, you can replace the default adapter with a Test adapter (a mock object), allowing you
to run tests without actually performing server connections.
The `Zend\Http\Client\Adapter\Test` adapter provides an additional method, `setResponse()`. This
method takes one parameter, which represents an *HTTP* response as either text or a
`Zend\Http\Response` object. Once set, your Test adapter will always return this response, without
even performing an actual *HTTP* request.
**Testing Against a Single HTTP Response Stub**
```php
// Instantiate a new adapter and client
$adapter = new Zend\Http\Client\Adapter\Test();
$client = new Zend\Http\Client('http://www.example.com', array(
'adapter' => $adapter
));
// Set the expected response
$adapter->setResponse(
"HTTP/1.1 200 OK" . "\r\n" .
"Content-type: text/xml" . "\r\n" .
"\r\n" .
'<?xml version="1.0" encoding="UTF-8"?>' .
'<rss version="2.0" ' .
' xmlns:content="http://purl.org/rss/1.0/modules/content/"' .
' xmlns:wfw="http://wellformedweb.org/CommentAPI/"' .
' xmlns:dc="http://purl.org/dc/elements/1.1/">' .
' <channel>' .
' <title>Premature Optimization</title>' .
// and so on...
'</rss>');
$response = $client->send();
// .. continue parsing $response..
```
The above example shows how you can preset your *HTTP* client to return the response you need. Then,
you can continue testing your own code, without being dependent on a network connection, the
server's response, etc. In this case, the test would continue to check how the application parses
the *XML* in the response body.
Sometimes, a single method call to an object can result in that object performing multiple *HTTP*
transactions. In this case, it's not possible to use setResponse() alone because there's no
opportunity to set the next response(s) your program might need before returning to the caller.
**Testing Against Multiple HTTP Response Stubs**
```php
// Instantiate a new adapter and client
$adapter = new Zend\Http\Client\Adapter\Test();
$client = new Zend\Http\Client('http://www.example.com', array(
'adapter' => $adapter
));
// Set the first expected response
$adapter->setResponse(
"HTTP/1.1 302 Found" . "\r\n" .
"Location: /" . "\r\n" .
"Content-Type: text/html" . "\r\n" .
"\r\n" .
'<html>' .
' <head><title>Moved</title></head>' .
' <body><p>This page has moved.</p></body>' .
'</html>');
// Set the next successive response
$adapter->addResponse(
"HTTP/1.1 200 OK" . "\r\n" .
"Content-Type: text/html" . "\r\n" .
"\r\n" .
'<html>' .
' <head><title>My Pet Store Home Page</title></head>' .
' <body><p>...</p></body>' .
'</html>');
// inject the http client object ($client) into your object
// being tested and then test your object's behavior below
```
The `setResponse()` method clears any responses in the `Zend\Http\Client\Adapter\Test`'s buffer and
sets the first response that will be returned. The `addResponse()` method will add successive
responses.
The responses will be replayed in the order that they were added. If more requests are made than the
number of responses stored, the responses will cycle again in order.
In the example above, the adapter is configured to test your object's behavior when it encounters a
302 redirect. Depending on your application, following a redirect may or may not be desired
behavior. In our example, we expect that the redirect will be followed and we configure the test
adapter to help us test this. The initial 302 response is set up with the `setResponse()` method and
the 200 response to be returned next is added with the `addResponse()` method. After configuring the
test adapter, inject the *HTTP* client containing the adapter into your object under test and test
its behavior.
If you need the adapter to fail on demand you can use `setNextRequestWillFail($flag)`. The method
will cause the next call to `connect()` to throw an
`Zend\Http\Client\Adapter\Exception\RuntimeException` exception. This can be useful when our
application caches content from an external site (in case the site goes down) and you want to test
this feature.
**Forcing the adapter to fail**
```php
// Instantiate a new adapter and client
$adapter = new Zend\Http\Client\Adapter\Test();
$client = new Zend\Http\Client('http://www.example.com', array(
'adapter' => $adapter
));
// Force the next request to fail with an exception
$adapter->setNextRequestWillFail(true);
try {
// This call will result in a Zend\Http\Client\Adapter\Exception\RuntimeException
$client->send();
} catch (Zend\Http\Client\Adapter\Exception\RuntimeException $e) {
// ...
}
// Further requests will work as expected until
// you call setNextRequestWillFail(true) again
```
## Creating your own connection adapters
`Zend\Http\Client` has been designed so that you can create and use your own connection adapters.
You could, for example, create a connection adapter that uses persistent sockets, or a connection
adapter with caching abilities, and use them as needed in your application.
In order to do so, you must create your own adapter class that implements the
`Zend\Http\Client\Adapter\AdapterInterface` interface. The following example shows the skeleton of a
user-implemented adapter class. All the public functions defined in this example must be defined in
your adapter as well:
**Creating your own connection adapter**
```php
class MyApp\Http\Client\Adapter\BananaProtocol
implements Zend\Http\Client\Adapter\AdapterInterface
{
/**
* Set Adapter Options
*
* @param array $config
*/
public function setOptions($config = array())
{
// This rarely changes - you should usually copy the
// implementation in Zend\Http\Client\Adapter\Socket.
}
/**
* Connect to the remote server
*
* @param string $host
* @param int $port
* @param boolean $secure
*/
public function connect($host, $port = 80, $secure = false)
{
// Set up the connection to the remote server
}
/**
* Send request to the remote server
*
* @param string $method
* @param Zend\Uri\Http $url
* @param string $http_ver
* @param array $headers
* @param string $body
* @return string Request as text
*/
public function write($method,
$url,
$http_ver = '1.1',
$headers = array(),
$body = '')
{
// Send request to the remote server.
// This function is expected to return the full request
// (headers and body) as a string
}
/**
* Read response from server
*
* @return string
*/
public function read()
{
// Read response from remote server and return it as a string
}
/**
* Close the connection to the server
*
*/
public function close()
{
// Close the connection to the remote server - called last.
}
}
// Then, you could use this adapter:
$client = new Zend\Http\Client(array(
'adapter' => 'MyApp\Http\Client\Adapter\BananaProtocol'
));
```

View File

@@ -1,341 +0,0 @@
# HTTP Client - Advanced Usage
## HTTP Redirections
`Zend\Http\Client` automatically handles *HTTP* redirections, and by default will follow up to 5
redirections. This can be changed by setting the `maxredirects` configuration parameter.
According to the *HTTP*/1.1 RFC, *HTTP* 301 and 302 responses should be treated by the client by
resending the same request to the specified location - using the same request method. However, most
clients to not implement this and always use a `GET` request when redirecting. By default,
`Zend\Http\Client` does the same - when redirecting on a 301 or 302 response, all `GET` and POST
parameters are reset, and a `GET` request is sent to the new location. This behavior can be changed
by setting the `strictredirects` configuration parameter to boolean `TRUE`:
**Forcing RFC 2616 Strict Redirections on 301 and 302 Responses**
```php
// Strict Redirections
$client->setOptions(array('strictredirects' => true));
// Non-strict Redirections
$client->setOptions(array('strictredirects' => false));
```
You can always get the number of redirections done after sending a request using the
`getRedirectionsCount()` method.
## Adding Cookies and Using Cookie Persistence
`Zend\Http\Client` provides an easy interface for adding cookies to your request, so that no direct
header modification is required. Cookies can be added using either the addCookie() or `setCookies`
method. The `addCookie` method has a number of operating modes:
**Setting Cookies Using addCookie()**
```php
// Easy and simple: by providing a cookie name and cookie value
$client->addCookie('flavor', 'chocolate chips');
// By providing a Zend\Http\Header\SetCookie object
$cookie = Zend\Http\Header\SetCookie::fromString('Set-Cookie: flavor=chocolate%20chips');
$client->addCookie($cookie);
// Multiple cookies can be set at once by providing an
// array of Zend\Http\Header\SetCookie objects
$cookies = array(
Zend\Http\Header\SetCookie::fromString('Set-Cookie: flavorOne=chocolate%20chips'),
Zend\Http\Header\SetCookie::fromString('Set-Cookie: flavorTwo=vanilla'),
);
$client->addCookie($cookies);
```
The `setCookies()` method works in a similar manner, except that it requires an array of cookie
values as its only argument and also clears the cookie container before adding the new cookies:
**Setting Cookies Using setCookies()**
```php
// setCookies accepts an array of cookie values as $name => $value
$client->setCookies(array(
'flavor' => 'chocolate chips',
'amount' => 10,
));
```
For more information about `Zend\Http\Header\SetCookie` objects, see \[this
section\](zend.http.headers).
`Zend\Http\Client` also provides a means for simplifying cookie stickiness - that is having the
client internally store all sent and received cookies, and resend them on subsequent requests:
`Zend\Http\Cookies`. This is useful, for example when you need to log in to a remote site first and
receive and authentication or session ID cookie before sending further requests.
**Enabling Cookie Stickiness**
```php
$headers = $client->getRequest()->getHeaders();
$cookies = new Zend\Http\Cookies($headers);
// First request: log in and start a session
$client->setUri('http://example.com/login.php');
$client->setParameterPost(array('user' => 'h4x0r', 'password' => 'l33t'));
$client->setMethod('POST');
$response = $client->getResponse();
$cookies->addCookiesFromResponse($response, $client->getUri());
// Now we can send our next request
$client->setUri('http://example.com/read_member_news.php');
$client->setCookies($cookies->getMatchingCookies($client->getUri()));
$client->setMethod('GET');
```
For more information about the `Zend\Http\Cookies` class, see this section
&lt;zend.http.client.cookies&gt;.
## Setting Custom Request Headers
Setting custom headers is performed by first fetching the header container from the client's
`Zend\Http\Request` object. This method is quite diverse and can be used in several ways, as the
following example shows:
**Setting A Single Custom Request Header**
```php
// Fetch the container
$headers = $client->getRequest()->getHeaders();
// Setting a single header. Will not overwrite any
// previously-added headers of the same name.
$headers->addHeaderLine('Host', 'www.example.com');
// Another way of doing the exact same thing
$headers->addHeaderLine('Host: www.example.com');
// Another way of doing the exact same thing using
// the provided Zend\Http\Header class
$headers->addHeader(Zend\Http\Header\Host::fromString('Host: www.example.com'));
// You can also add multiple headers at once by passing an
// array to addHeaders using any of the formats below:
$headers->addHeaders(array(
// Zend\Http\Header\* object
Zend\Http\Header\Host::fromString('Host: www.example.com'),
// Header name as array key, header value as array key value
'Cookie' => 'PHPSESSID=1234567890abcdef1234567890abcdef',
// Raw header string
'Cookie: language=he',
));
```
`Zend\Http\Client` also provides a convenience method for setting request headers, `setHeaders`.
This method will create a new header container, add the specified headers and then store the new
header container in it's `Zend\Http\Request` object. As a consequence, any pre-existing headers will
be erased.
**Setting Multiple Custom Request Headers**
```php
// Setting multiple headers. Will remove all existing
// headers and add new ones to the Request header container
$client->setHeaders(array(
Zend\Http\Header\Host::fromString('Host: www.example.com'),
'Accept-Encoding' => 'gzip,deflate',
'X-Powered-By: Zend Framework',
));
```
## File Uploads
You can upload files through *HTTP* using the setFileUpload method. This method takes a file name as
the first parameter, a form name as the second parameter, and data as a third optional parameter. If
the third data parameter is `NULL`, the first file name parameter is considered to be a real file on
disk, and `Zend\Http\Client` will try to read this file and upload it. If the data parameter is not
`NULL`, the first file name parameter will be sent as the file name, but no actual file needs to
exist on the disk. The second form name parameter is always required, and is equivalent to the
"name" attribute of an `<input>` tag, if the file was to be uploaded through an *HTML* form. A
fourth optional parameter provides the file's content-type. If not specified, and `Zend\Http\Client`
reads the file from the disk, the `mime_content_type` function will be used to guess the file's
content type, if it is available. In any case, the default MIME type will be
application/octet-stream.
**Using setFileUpload to Upload Files**
```php
// Uploading arbitrary data as a file
$text = 'this is some plain text';
$client->setFileUpload('some_text.txt', 'upload', $text, 'text/plain');
// Uploading an existing file
$client->setFileUpload('/tmp/Backup.tar.gz', 'bufile');
// Send the files
$client->setMethod('POST');
$client->send();
```
In the first example, the `$text` variable is uploaded and will be available as `$_FILES['upload']`
on the server side. In the second example, the existing file `/tmp/Backup.tar.gz` is uploaded to the
server and will be available as `$_FILES['bufile']`. The content type will be guessed automatically
if possible - and if not, the content type will be set to 'application/octet-stream'.
> ## Note
#### Uploading files
When uploading files, the *HTTP* request content-type is automatically set to multipart/form-data.
Keep in mind that you must send a POST or PUT request in order to upload files. Most servers will
ignore the request body on other request methods.
## Sending Raw POST Data
You can use a `Zend\Http\Client` to send raw POST data using the `setRawBody()` method. This method
takes one parameter: the data to send in the request body. When sending raw POST data, it is
advisable to also set the encoding type using `setEncType()`.
**Sending Raw POST Data**
```php
$xml = '<book>' .
' <title>Islands in the Stream</title>' .
' <author>Ernest Hemingway</author>' .
' <year>1970</year>' .
'</book>';
$client->setMethod('POST');
$client->setRawBody($xml);
$client->setEncType('text/xml');
$client->send();
```
The data should be available on the server side through *PHP*'s `$HTTP_RAW_POST_DATA` variable or
through the `php://input` stream.
> ## Note
#### Using raw POST data
Setting raw POST data for a request will override any POST parameters or file uploads. You should
not try to use both on the same request. Keep in mind that most servers will ignore the request body
unless you send a POST request.
## HTTP Authentication
Currently, `Zend\Http\Client` only supports basic *HTTP* authentication. This feature is utilized
using the `setAuth()` method, or by specifying a username and a password in the URI. The `setAuth()`
method takes 3 parameters: The user name, the password and an optional authentication type
parameter. As mentioned, currently only basic authentication is supported (digest authentication
support is planned).
**Setting HTTP Authentication User and Password**
```php
// Using basic authentication
$client->setAuth('shahar', 'myPassword!', Zend\Http\Client::AUTH_BASIC);
// Since basic auth is default, you can just do this:
$client->setAuth('shahar', 'myPassword!');
// You can also specify username and password in the URI
$client->setUri('http://christer:secret@example.com');
```
## Sending Multiple Requests With the Same Client
`Zend\Http\Client` was also designed specifically to handle several consecutive requests with the
same object. This is useful in cases where a script requires data to be fetched from several places,
or when accessing a specific *HTTP* resource requires logging in and obtaining a session cookie, for
example.
When performing several requests to the same host, it is highly recommended to enable the
'keepalive' configuration flag. This way, if the server supports keep-alive connections, the
connection to the server will only be closed once all requests are done and the Client object is
destroyed. This prevents the overhead of opening and closing *TCP* connections to the server.
When you perform several requests with the same client, but want to make sure all the
request-specific parameters are cleared, you should use the `resetParameters()` method. This ensures
that GET and POST parameters, request body and headers are reset and are not reused in the next
request.
> ## Note
#### Resetting parameters
Note that cookies are not reset by default when the `resetParameters()` method is used. To clean all
cookies as well, use `resetParameters(true)`, or call `clearCookies()` after calling
`resetParameters()`.
Another feature designed specifically for consecutive requests is the `Zend\Http\Cookies` object.
This "Cookie Jar" allow you to save cookies set by the server in a request, and send them back on
consecutive requests transparently. This allows, for example, going through an authentication
request before sending the actual data-fetching request.
If your application requires one authentication request per user, and consecutive requests might be
performed in more than one script in your application, it might be a good idea to store the Cookies
object in the user's session. This way, you will only need to authenticate the user once every
session.
**Performing consecutive requests with one client**
```php
// First, instantiate the client
$client = new Zend\Http\Client('http://www.example.com/fetchdata.php', array(
'keepalive' => true
));
// Do we have the cookies stored in our session?
if (isset($_SESSION['cookiejar']) &&
$_SESSION['cookiejar'] instanceof Zend\Http\Cookies) {
$cookieJar = $_SESSION['cookiejar'];
} else {
// If we don't, authenticate and store cookies
$client->setUri('http://www.example.com/login.php');
$client->setParameterPost(array(
'user' => 'shahar',
'pass' => 'somesecret'
));
$response = $client->setMethod('POST')->send();
$cookieJar = Zend\Http\Cookies::fromResponse($response);
// Now, clear parameters and set the URI to the original one
// (note that the cookies that were set by the server are now
// stored in the jar)
$client->resetParameters();
$client->setUri('http://www.example.com/fetchdata.php');
}
// Add the cookies to the new request
$client->setCookies($cookieJar->getMatchingCookies($client->getUri()));
$response = $client->setMethod('GET')->send();
// Store cookies in session, for next page
$_SESSION['cookiejar'] = $cookieJar;
```
## Data Streaming
By default, `Zend\Http\Client` accepts and returns data as *PHP* strings. However, in many cases
there are big files to be received, thus keeping them in memory might be unnecessary or too
expensive. For these cases, `Zend\Http\Client` supports writing data to files (streams).
In order to receive data from the server as stream, use `setStream()`. Optional argument specifies
the filename where the data will be stored. If the argument is just `TRUE` (default), temporary file
will be used and will be deleted once response object is destroyed. Setting argument to `FALSE`
disables the streaming functionality.
When using streaming, `send()` method will return object of class `Zend\Http\Response\Stream`, which
has two useful methods: `getStreamName()` will return the name of the file where the response is
stored, and `getStream()` will return stream from which the response could be read.
You can either write the response to pre-defined file, or use temporary file for storing it and send
it out or write it to another file using regular stream functions.
> ## Receiving file from HTTP server with streaming
```php
$client-setStream(); // will use temp file
$response = $client-send();
// copy file
copy($response-getStreamName(), "my/downloads/file");
// use stream
$fp = fopen("my/downloads/file2", "w");
stream_copy_to_stream($response-getStream(), $fp);
// Also can write to known file
$client-setStream("my/downloads/myfile")-send();
```

View File

@@ -1,230 +0,0 @@
# HTTP Client
## Overview
`Zend\Http\Client` provides an easy interface for performing Hyper-Text Transfer Protocol (HTTP)
requests. `Zend\Http\Client` supports the most simple features expected from an *HTTP* client, as
well as some more complex features such as *HTTP* authentication and file uploads. Successful
requests (and most unsuccessful ones too) return a `Zend\Http\Response` object, which provides
access to the response's headers and body (see this
section &lt;zend.http.response&gt;).
## Quick Start
The class constructor optionally accepts a URL as its first parameter (can be either a string or a
`Zend\Uri\Http` object), and an array or `Zend\Config\Config` object containing configuration
options. The `send()` method is used to submit the request to the remote server, and a
`Zend\Http\Response` object is returned:
```php
use Zend\Http\Client;
$client = new Client('http://example.org', array(
'maxredirects' => 0,
'timeout' => 30
));
$response = $client->send();
```
Both constructor parameters can be left out, and set later using the setUri() and setConfig()
methods:
```php
use Zend\Http\Client;
$client = new Client();
$client->setUri('http://example.org');
$client->setOptions(array(
'maxredirects' => 0,
'timeout' => 30
));
$response = $client->send();
```
`Zend\Http\Client` can also dispatch requests using a separately configured `request` object (see
the Zend\\\\Http\\\\Request manual page&lt;zend.http.request&gt; for full details of the methods
available):
```php
use Zend\Http\Client;
use Zend\Http\Request;
$request = new Request();
$request->setUri('http://example.org');
$client = new Client();
$response = $client->send($request);
```
> ## Note
`Zend\Http\Client` uses `Zend\Uri\Http` to validate URLs. See the Zend\\\\Uri manual
page&lt;zend.uri&gt; for more information on the validation process.
## Configuration
The constructor and setOptions() method accepts an associative array of configuration parameters, or
a `Zend\Config\Config` object. Setting these parameters is optional, as they all have default
values.
The options are also passed to the adapter class upon instantiation, so the same array or
`Zend\Config\Config` object) can be used for adapter configuration. See the Zend Http Client adapter
section&lt;zend.http.client.adapters&gt; for more information on the adapter-specific options
available.
## Examples
### Performing a Simple GET Request
Performing simple *HTTP* requests is very easily done:
```php
use Zend\Http\Client;
$client = new Client('http://example.org');
$response = $client->send();
```
### Using Request Methods Other Than GET
The request method can be set using `setMethod()`. If no method is specified, the method set by the
last `setMethod()` call is used. If `setMethod()` was never called, the default request method is
`GET`.
```php
use Zend\Http\Client;
$client = new Client('http://example.org');
// Performing a POST request
$client->setMethod('POST');
$response = $client->send();
```
For convenience, `Zend\Http\Request` defines all the request methods as class constants,
`Zend\Http\Request::METHOD_GET`, `Zend\Http\Request::METHOD_POST` and so on:
```php
use Zend\Http\Client;
use Zend\Http\Request;
$client = new Client('http://example.org');
// Performing a POST request
$client->setMethod(Request::METHOD_POST);
$response = $client->send();
```
### Setting GET parameters
Adding `GET` parameters to an *HTTP* request is quite simple, and can be done either by specifying
them as part of the URL, or by using the `setParameterGet()` method. This method takes the `GET`
parameters as an associative array of name =&gt; value `GET` variables.
```php
use Zend\Http\Client;
$client = new Client();
// This is equivalent to setting a URL in the Client's constructor:
$client->setUri('http://example.com/index.php?knight=lancelot');
// Adding several parameters with one call
$client->setParameterGet(array(
'first_name' => 'Bender',
'middle_name' => 'Bending',
'last_name' => 'Rodríguez',
'made_in' => 'Mexico',
));
```
### Setting POST Parameters
While `GET` parameters can be sent with every request method, `POST` parameters are only sent in the
body of `POST` requests. Adding `POST` parameters to a request is very similar to adding `GET`
parameters, and can be done with the `setParameterPost()` method, which is identical to the
`setParameterGet()` method in structure.
```php
use Zend\Http\Client;
$client = new Client();
// Setting several POST parameters, one of them with several values
$client->setParameterPost(array(
'language' => 'es',
'country' => 'ar',
'selection' => array(45, 32, 80)
));
```
Note that when sending `POST` requests, you can set both `GET` and `POST` parameters. On the other
hand, setting POST parameters on a non-`POST` request will not trigger an error, rendering it
useless. Unless the request is a `POST` request, `POST` parameters are simply ignored.
### Connecting to SSL URLs
If you are trying to connect to an SSL (https) URL and are using the default
(`Zend\Http\Client\Adapter\Socket`) adapter, you may need to set the `sslcapath` configuration
option in order to allow PHP to validate the SSL certificate:
```php
use Zend\Http\Client;
$client = new Client('https://example.org', array(
'sslcapath' => '/etc/ssl/certs'
));
$response = $client->send();
```
The exact path to use will vary depending on your Operating System. Without this you'll get the
exception "Unable to enable crypto on TCP connection" when trying to connect.
Alternatively, you could switch to the curl adapter, which negotiates SSL connections more
transparently:
```php
use Zend\Http\Client;
$client = new Client('https://example.org', array(
'adapter' => 'Zend\Http\Client\Adapter\Curl'
));
$response = $client->send();
```
### A Complete Example
```php
use Zend\Http\Client;
$client = new Client();
$client->setUri('http://www.example.com');
$client->setMethod('POST');
$client->setParameterPost(array(
'foo' => 'bar'
));
$response = $client->send();
if ($response->isSuccess()) {
// the POST was successful
}
```
or the same thing, using a request object:
```php
use Zend\Http\Client;
use Zend\Http\Request;
$request = new Request();
$request->setUri('http://www.example.com');
$request->setMethod('POST');
$request->getPost()->set('foo', 'bar');
$client = new Client();
$response = $client->send($request);
if ($response->isSuccess()) {
// the POST was successful
}
```

File diff suppressed because it is too large Load Diff

View File

@@ -1,451 +0,0 @@
# The Request Class
## Overview
The `Zend\Http\Request` object is responsible for providing a fluent API that allows a developer to
interact with all the various parts of an HTTP request.
A typical HTTP request looks like this:
##
## | METHOD | URI | VERSION |
## | HEADERS |
## | BODY |
In simplified terms, the request consists of a method, *URI* and HTTP version number which together
make up the "Request Line." Next come the HTTP headers, of which there can be 0 or more. After that
is the request body, which is typically used when a client wishes to send data to the server in the
form of an encoded file, or include a set of POST parameters, for example. More information on the
structure and specification of a HTTP request can be found in [RFC-2616 on the W3.org
site](http://www.w3.org/Protocols/rfc2616/rfc2616-sec5.html).
## Quick Start
Request objects can either be created from the provided `fromString()` factory, or, if you wish to
have a completely empty object to start with, by simply instantiating the `Zend\Http\Request` class.
```php
use Zend\Http\Request;
$request = Request::fromString(<<<EOS
POST /foo HTTP/1.1
\r\n
HeaderField1: header-field-value1
HeaderField2: header-field-value2
\r\n\r\n
foo=bar&
EOS
);
// OR, the completely equivalent
$request = new Request();
$request->setMethod(Request::METHOD_POST);
$request->setUri('/foo');
$request->getHeaders()->addHeaders(array(
'HeaderField1' => 'header-field-value1',
'HeaderField2' => 'header-field-value2',
));
$request->getPost()->set('foo', 'bar');
```
## Configuration Options
No configuration options are available.
## Available Methods
**Request::fromString**
`Request::fromString(string $string)`
A factory that produces a Request object from a well-formed HTTP Request string.
Returns `Zend\Http\Request`
<!-- -->
**setMethod**
`setMethod(string $method)`
Set the method for this request.
Returns `Zend\Http\Request`
<!-- -->
**getMethod**
`getMethod()`
Return the method for this request.
Returns string
<!-- -->
**setUri**
`setUri(string|Zend\Uri\Http $uri)`
Set the URI/URL for this request; this can be a string or an instance of `Zend\Uri\Http`.
Returns `Zend\Http\Request`
<!-- -->
**getUri**
`getUri()`
Return the URI for this request object.
Returns `Zend\Uri\Http`
<!-- -->
**getUriString**
`getUriString()`
Return the URI for this request object as a string.
Returns string
<!-- -->
**setVersion**
`setVersion(string $version)`
Set the HTTP version for this object, one of 1.0 or 1.1 (`Request::VERSION_10`,
`Request::VERSION_11`).
Returns `Zend\Http\Request`
<!-- -->
**getVersion**
`getVersion()`
Return the HTTP version for this request.
Returns string
<!-- -->
**setQuery**
`setQuery(Zend\Stdlib\ParametersInterface $query)`
Provide an alternate Parameter Container implementation for query parameters in this object. (This
is NOT the primary API for value setting; for that, see `getQuery()`).
Returns `Zend\Http\Request`
<!-- -->
**getQuery**
`getQuery(string|null $name, mixed|null $default)`
Return the parameter container responsible for query parameters or a single query parameter.
Returns `string`, `Zend\Stdlib\ParametersInterface`, or `null` depending on value of `$name`
argument.
<!-- -->
**setPost**
`setPost(Zend\Stdlib\ParametersInterface $post)`
Provide an alternate Parameter Container implementation for POST parameters in this object. (This is
NOT the primary API for value setting; for that, see `getPost()`).
Returns `Zend\Http\Request`
<!-- -->
**getPost**
`getPost(string|null $name, mixed|null $default)`
Return the parameter container responsible for POST parameters or a single POST parameter.
Returns `string`, `Zend\Stdlib\ParametersInterface`, or `null` depending on value of `$name`
argument.
<!-- -->
**getCookie**
`getCookie()`
Return the Cookie header, this is the same as calling
*$request-&gt;getHeaders()-&gt;get('Cookie');*.
Returns `Zend\Http\Header\Cookie`
<!-- -->
**setFiles**
`setFiles(Zend\Stdlib\ParametersInterface $files)`
Provide an alternate Parameter Container implementation for file parameters in this object, (This is
NOT the primary API for value setting; for that, see `getFiles()`).
Returns `Zend\Http\Request`
<!-- -->
**getFiles**
`getFiles(string|null $name, mixed|null $default)`
Return the parameter container responsible for file parameters or a single file parameter.
Returns `string`, `Zend\Stdlib\ParametersInterface`, or `null` depending on value of `$name`
argument.
<!-- -->
**setHeaders**
`setHeaders(Zend\Http\Headers $headers)`
Provide an alternate Parameter Container implementation for headers in this object, (this is NOT the
primary API for value setting, for that see `getHeaders()`).
Returns `Zend\Http\Request`
<!-- -->
**getHeaders**
`getHeaders(string|null $name, mixed|null $default)`
Return the container responsible for storing HTTP headers. This container exposes the primary API
for manipulating headers set in the HTTP request. See the section on
Zend\\\\Http\\\\Headers&lt;zend.http.headers&gt; for more information.
Returns `Zend\Http\Headers` if `$name` is `null`. Returns `Zend\Http\Header\HeaderInterface` or
`ArrayIterator` if `$name` matches one or more stored headers, respectively.
<!-- -->
**setMetadata**
`setMetadata(string|int|array|Traversable $spec, mixed $value)`
Set message metadata.
Non-destructive setting of message metadata; always adds to the metadata, never overwrites the
entire metadata container.
Returns `Zend\Http\Request`
<!-- -->
**getMetadata**
`getMetadata(null|string|int $key, null|mixed $default)`
Retrieve all metadata or a single metadatum as specified by key.
Returns mixed
<!-- -->
**setContent**
`setContent(mixed $value)`
Set request body (content).
Returns `Zend\Http\Request`
<!-- -->
**getContent**
`getContent()`
Get request body (content).
Returns mixed
<!-- -->
**isOptions**
`isOptions()`
Is this an OPTIONS method request?
Returns bool
<!-- -->
**isGet**
`isGet()`
Is this a GET method request?
Returns bool
<!-- -->
**isHead**
`isHead()`
Is this a HEAD method request?
Returns bool
<!-- -->
**isPost**
`isPost()`
Is this a POST method request?
Returns bool
<!-- -->
**isPut**
`isPut()`
Is this a PUT method request?
Returns bool
<!-- -->
**isDelete**
`isDelete()`
Is this a DELETE method request?
Returns bool
<!-- -->
**isTrace**
`isTrace()`
Is this a TRACE method request?
Returns bool
<!-- -->
**isConnect**
`isConnect()`
Is this a CONNECT method request?
Returns bool
<!-- -->
**isPatch**
`isPatch()`
Is this a PATCH method request?
Returns bool
<!-- -->
**isXmlHttpRequest**
`isXmlHttpRequest()`
Is this a Javascript XMLHttpRequest?
Returns bool
<!-- -->
**isFlashRequest**
`isFlashRequest()`
Is this a Flash request?
Returns bool
<!-- -->
**renderRequestLine**
`renderRequestLine()`
Return the formatted request line (first line) for this HTTP request.
Returns string
<!-- -->
**toString**
`toString()`
Returns string
<!-- -->
**\_\_toString**
`__toString()`
Allow PHP casting of this object.
Returns string
## Examples
**Generating a Request object from a string**
```php
use Zend\Http\Request;
$string = "GET /foo HTTP/1.1\r\n\r\nSome Content";
$request = Request::fromString($string);
$request->getMethod(); // returns Request::METHOD_GET
$request->getUri(); // returns Zend\Uri\Http object
$request->getUriString(); // returns '/foo'
$request->getVersion(); // returns Request::VERSION_11 or '1.1'
$request->getContent(); // returns 'Some Content'
```
**Retrieving and setting headers**
```php
use Zend\Http\Request;
use Zend\Http\Header\Cookie;
$request = new Request();
$request->getHeaders()->get('Content-Type'); // return content type
$request->getHeaders()->addHeader(new Cookie(array('foo' => 'bar')));
foreach ($request->getHeaders() as $header) {
echo $header->getFieldName() . ' with value ' . $header->getFieldValue();
}
```
**Retrieving and setting GET and POST values**
```php
use Zend\Http\Request;
$request = new Request();
// getPost() and getQuery() both return, by default, a Parameters object, which extends ArrayObject
$request->getPost()->foo = 'Foo value';
$request->getQuery()->bar = 'Bar value';
$request->getPost('foo'); // returns 'Foo value'
$request->getQuery()->offsetGet('bar'); // returns 'Bar value'
```
**Generating a formatted HTTP Request from a Request object**
```php
use Zend\Http\Request;
$request = new Request();
$request->setMethod(Request::METHOD_POST);
$request->setUri('/foo');
$request->getHeaders()->addHeaders(array(
'HeaderField1' => 'header-field-value1',
'HeaderField2' => 'header-field-value2',
));
$request->getPost()->set('foo', 'bar');
$request->setContent($request->getPost()->toString());
echo $request->toString();
/** Will produce:
POST /foo HTTP/1.1
HeaderField1: header-field-value1
HeaderField2: header-field-value2
foo=bar
*/
```

View File

@@ -1,352 +0,0 @@
# The Response Class
## Overview
The `Zend\Http\Response` class is responsible for providing a fluent API that allows a developer to
interact with all the various parts of an HTTP response.
A typical HTTP Response looks like this:
##
## | VERSION | CODE | REASON |
## | HEADERS |
## | BODY |
The first line of the response consists of the HTTP version, status code, and the reason string for
the provided status code; this is called the Response Line. Next is a set of headers; there can be 0
or an unlimited number of headers. The remainder of the response is the response body, which is
typically a string of HTML that will render on the client's browser, but which can also be a place
for request/response payload data typical of an AJAX request. More information on the structure and
specification of an HTTP response can be found in [RFC-2616 on the W3.org
site](http://www.w3.org/Protocols/rfc2616/rfc2616-sec6.html).
## Quick Start
Response objects can either be created from the provided `fromString()` factory, or, if you wish to
have a completely empty object to start with, by simply instantiating the `Zend\Http\Response`
class.
```php
use Zend\Http\Response;
$response = Response::fromString(<<<EOS
HTTP/1.0 200 OK
HeaderField1: header-field-value
HeaderField2: header-field-value2
<html>
<body>
Hello World
</body>
</html>
EOS);
// OR
$response = new Response();
$response->setStatusCode(Response::STATUS_CODE_200);
$response->getHeaders()->addHeaders(array(
'HeaderField1' => 'header-field-value',
'HeaderField2' => 'header-field-value2',
));
$response->setContent(<<<EOS
<html>
<body>
Hello World
</body>
</html>
EOS
);
```
## Configuration Options
No configuration options are available.
## Available Methods
**Response::fromString**
`Response::fromString(string $string)`
Populate object from string
Returns `Zend\Http\Response`
<!-- -->
**renderStatusLine**
`renderStatusLine()`
Render the status line header
Returns string
<!-- -->
**setHeaders**
`setHeaders(Zend\Http\Headers $headers)`
Provide an alternate Parameter Container implementation for headers in this object. (This is NOT the
primary API for value setting; for that, see `getHeaders()`.)
Returns `Zend\Http\Request`
<!-- -->
**getHeaders**
`getHeaders()`
Return the container responsible for storing HTTP headers. This container exposes the primary API
for manipulating headers set in the HTTP response. See the section on
Zend\\\\Http\\\\Headers&lt;zend.http.headers&gt; for more information.
Returns `Zend\Http\Headers`
<!-- -->
**setVersion**
`setVersion(string $version)`
Set the HTTP version for this object, one of 1.0 or 1.1 (`Request::VERSION_10`,
`Request::VERSION_11`).
Returns `Zend\Http\Request`.
<!-- -->
**getVersion**
`getVersion()`
Return the HTTP version for this request
Returns string
<!-- -->
**setStatusCode**
`setStatusCode(numeric $code)`
Set HTTP status code
Returns `Zend\Http\Response`
<!-- -->
**getStatusCode**
`getStatusCode()`
Retrieve HTTP status code
Returns int
<!-- -->
**setReasonPhrase**
`setReasonPhrase(string $reasonPhrase)`
Set custom HTTP status message
Returns `Zend\Http\Response`
<!-- -->
**getReasonPhrase**
`getReasonPhrase()`
Get HTTP status message
Returns string
<!-- -->
**isClientError**
`isClientError()`
Does the status code indicate a client error?
Returns bool
<!-- -->
**isForbidden**
`isForbidden()`
Is the request forbidden due to ACLs?
Returns bool
<!-- -->
**isInformational**
`isInformational()`
Is the current status "informational"?
Returns bool
<!-- -->
**isNotFound**
`isNotFound()`
Does the status code indicate the resource is not found?
Returns bool
<!-- -->
**isOk**
`isOk()`
Do we have a normal, OK response?
Returns bool
<!-- -->
**isServerError**
`isServerError()`
Does the status code reflect a server error?
Returns bool
<!-- -->
**isRedirect**
`isRedirect()`
Do we have a redirect?
Returns bool
<!-- -->
**isSuccess**
`isSuccess()`
Was the response successful?
Returns bool
<!-- -->
**decodeChunkedBody**
`decodeChunkedBody(string $body)`
Decode a "chunked" transfer-encoded body and return the decoded text
Returns string
<!-- -->
**decodeGzip**
`decodeGzip(string $body)`
Decode a gzip encoded message (when Content-encoding = gzip)
Currently requires PHP with zlib support
Returns string
<!-- -->
**decodeDeflate**
`decodeDeflate(string $body)`
Decode a zlib deflated message (when Content-encoding = deflate)
Currently requires PHP with zlib support
Returns string
<!-- -->
**setMetadata**
`setMetadata(string|int|array|Traversable $spec, mixed $value)`
Set message metadata
Non-destructive setting of message metadata; always adds to the metadata, never overwrites the
entire metadata container.
Returns `Zend\Stdlib\Message`
<!-- -->
**getMetadata**
`getMetadata(null|string|int $key, null|mixed $default)`
Retrieve all metadata or a single metadatum as specified by key
Returns mixed
<!-- -->
**setContent**
`setContent(mixed $value)`
Set message content
Returns `Zend\Stdlib\Message`
<!-- -->
**getContent**
`getContent()`
Get raw message content
Returns mixed
<!-- -->
**getBody**
`getBody()`
Get decoded message content
Returns mixed
<!-- -->
**toString**
`toString()`
Returns string
## Examples
**Generating a Response object from a string**
```php
use Zend\Http\Response;
$request = Response::fromString(<<<EOS
HTTP/1.0 200 OK
HeaderField1: header-field-value
HeaderField2: header-field-value2
<html>
<body>
Hello World
</body>
</html>
EOS);
```
**Generating a formatted HTTP Response from a Response object**
```php
use Zend\Http\Response;
$response = new Response();
$response->setStatusCode(Response::STATUS_CODE_200);
$response->getHeaders()->addHeaders(array(
'HeaderField1' => 'header-field-value',
'HeaderField2' => 'header-field-value2',
));
$response->setContent(<<<EOS
<html>
<body>
Hello World
</body>
</html>
EOS);
```

View File

@@ -1,13 +0,0 @@
{
"title": "Zend\\Http",
"target": "html/",
"content": [
"book/zend.http.request.md",
"book/zend.http.response.md",
"book/zend.http.headers.md",
"book/zend.http.client.md",
"book/zend.http.client.adapters.md",
"book/zend.http.client.advanced.md",
"book/zend.http.client-static.md"
]
}

View File

@@ -2,29 +2,6 @@
All notable changes to this project will be documented in this file, in reverse chronological order by release.
## 3.1.0 - 2016-09-13
### Added
- [#63](https://github.com/zendframework/zend-stdlib/pull/63) adds a new
`Zend\Stdlib\ConsoleHelper` class, providing minimal support for writing
output to `STDOUT` and `STDERR`, with optional colorization, when the console
supports that feature.
### Deprecated
- [#38](https://github.com/zendframework/zend-stdlib/pull/38) deprecates
`Zend\Stdlib\JsonSerializable`, as all supported version of PHP now support
it.
### Removed
- Nothing.
### Fixed
- Nothing.
## 3.0.1 - 2016-04-12
### Added

View File

@@ -7,6 +7,7 @@
class for different scopes like:
- array utilities functions;
- json serializable interfaces;
- general messaging systems;
- string wrappers;
- etc.
@@ -14,4 +15,4 @@ class for different scopes like:
---
- File issues at https://github.com/zendframework/zend-stdlib/issues
- Documentation is at https://docs.zendframework.com/zend-stdlib/
- Documentation is at http://framework.zend.com/manual/current/en/index.html#zend-stdlib

View File

@@ -13,17 +13,17 @@
}
},
"require": {
"php": "^5.6 || ^7.0"
"php": "^5.5 || ^7.0"
},
"require-dev": {
"athletic/athletic": "~0.1",
"fabpot/php-cs-fixer": "1.7.*",
"phpunit/PHPUnit": "~4.0",
"squizlabs/php_codesniffer": "^2.6.2"
"athletic/athletic": "~0.1"
},
"extra": {
"branch-alias": {
"dev-master": "3.1-dev",
"dev-develop": "3.2-dev"
"dev-master": "3.0-dev",
"dev-develop": "3.1-dev"
}
},
"autoload-dev": {
@@ -31,12 +31,5 @@
"ZendTest\\Stdlib\\": "test/",
"ZendBench\\Stdlib\\": "benchmark/"
}
},
"scripts": {
"cs-check": "phpcs --colors",
"cs-fix": "phpcbf --colors",
"test": "phpunit --colors=always",
"test-coverage": "phpunit --colors=always --coverage-clover clover.xml",
"upload-coverage": "coveralls -v"
}
}

View File

@@ -1,126 +0,0 @@
# Console Helper
Writing one-off scripts or vendor binaries for a package is often problematic:
- You need to parse arguments manually.
- You need to send output to the console in a meaningful fashion:
- Using `STDOUT` for meaningful, expected output
- Using `STDERR` for error messages
- Ensuring any line breaks are converted to `PHP_EOL`
- Optionally, using console colors to provide context, which means:
- Detecting whether or not the console supports colors in the first place
- Providing appropriate escape sequences to produce color
`Zend\Stdlib\ConsoleHelper` helps to address the second major bullet point and
all beneath it in a minimal fashion.
## Usage
Typical usage is to instantiate a `ConsoleHelper`, and call one of its methods:
```php
use Zend\Stdlib\ConsoleHelper;
$helper = new ConsoleHelper();
$helper->writeLine('This is output');
```
You can optionally pass a PHP stream resource to the constructor, which will be
used to determine whether or not color support is available:
```php
$helper = new ConsoleHelper($stream);
```
By default, it assumes `STDOUT`, and tests against that.
## Available methods
`ConsoleHelper` provides the following methods.
### colorize
- `colorize(string $string) : string`
`colorize()` accepts a formatted string, and will then apply ANSI color
sequences to them, if color support is detected.
The following sequences are currently supported:
- `<info>...</info>` will apply a green color sequence around the provided text.
- `<error>...</error>` will apply a red color sequence around the provided text.
You may mix multiple sequences within the same stream.
### write
- `write(string $string, bool $colorize = true, resource $stream = STDOUT) : void`
Emits the provided `$string` to the provided `$stream` (which defaults to
`STDOUT` if not provided). Any EOL sequences are convered to `PHP_EOL`. If
`$colorize` is `true`, the string is first passed to `colorize()` as well.
### writeline
- `writeLine(string $string, bool $colorize = true, resource $stream = STDOUT) : void`
Same as `write()`, except it also appends a `PHP_EOL` sequence to the `$string`.
### writeErrorMessage
- `writeErrorMessage(string $message)`
Wraps `$message` in an `<error></error>` sequence, and passes it to
`writeLine()`, using `STDERR` as the `$stream`.
## Example
Below is an example class that accepts an argument list, and determines how and
what to emit.
```php
namespace Foo;
use Zend\Stdlib\ConsoleHelper;
class HelloWorld
{
private $helper;
public function __construct(ConsoleHelper $helper = null)
{
$this->helper = $helper ?: new ConsoleHelper();
}
public function __invoke(array $args)
{
if (! count($args)) {
$this->helper->writeErrorMessage('Missing arguments!');
return;
}
if (count($args) > 1) {
$this->helper->writeErrorMessage('Too many arguments!');
return;
}
$target = array_shift($args);
$this->helper->writeLine(sprintf(
'<info>Hello</info> %s',
$target
));
}
}
```
## When to upgrade
`ConsoleHelper` is deliberately simple, and assumes that your primary need for
console tooling is for output considerations.
If you need to parse complex argument strings, we recommend using
[zend-console](https://docs.zendframework.com/zend-console/)/[zf-console](https://github.com/zfcampus/zf-console)
or [symfony/console](http://symfony.com/doc/current/components/console.html),
as these packages provide those capabilities, as well as far more colorization
and console feature detection facilities.

View File

@@ -2,8 +2,6 @@ docs_dir: doc/book
site_dir: doc/html
pages:
- index.md
- Reference:
- "Console Helper": console-helper.md
- Migration: migration.md
site_name: zend-stdlib
site_description: Zend\Stdlib

View File

@@ -1,27 +0,0 @@
<?xml version="1.0"?>
<ruleset name="Zend Framework coding standard">
<description>Zend Framework coding standard</description>
<!-- display progress -->
<arg value="p"/>
<arg name="colors"/>
<!-- inherit rules from: -->
<rule ref="PSR2"/>
<rule ref="Generic.Arrays.DisallowLongArraySyntax"/>
<rule ref="Generic.Formatting.SpaceAfterNot"/>
<rule ref="Squiz.WhiteSpace.OperatorSpacing">
<properties>
<property name="ignoreNewlines" value="true"/>
</properties>
</rule>
<rule ref="Squiz.WhiteSpace.SuperfluousWhitespace">
<properties>
<property name="ignoreBlankLines" value="false"/>
</properties>
</rule>
<!-- Paths to check -->
<file>src</file>
<file>test</file>
</ruleset>

View File

@@ -13,7 +13,6 @@ use Traversable;
abstract class AbstractOptions implements ParameterObjectInterface
{
// @codingStandardsIgnoreStart
/**
* We use the __ prefix to avoid collisions with properties in
* user-implementations.
@@ -21,7 +20,6 @@ abstract class AbstractOptions implements ParameterObjectInterface
* @var bool
*/
protected $__strictMode__ = true;
// @codingStandardsIgnoreEnd
/**
* Constructor
@@ -48,7 +46,7 @@ abstract class AbstractOptions implements ParameterObjectInterface
$options = $options->toArray();
}
if (! is_array($options) && ! $options instanceof Traversable) {
if (!is_array($options) && !$options instanceof Traversable) {
throw new Exception\InvalidArgumentException(
sprintf(
'Parameter provided to %s must be an %s, %s or %s',

View File

@@ -180,16 +180,14 @@ class ArrayObject implements IteratorAggregate, ArrayAccess, Serializable, Count
*/
public function exchangeArray($data)
{
if (! is_array($data) && ! is_object($data)) {
throw new Exception\InvalidArgumentException(
'Passed variable is not an array or object, using empty array instead'
);
if (!is_array($data) && !is_object($data)) {
throw new Exception\InvalidArgumentException('Passed variable is not an array or object, using empty array instead');
}
if (is_object($data) && ($data instanceof self || $data instanceof \ArrayObject)) {
$data = $data->getArrayCopy();
}
if (! is_array($data)) {
if (!is_array($data)) {
$data = (array) $data;
}
@@ -292,7 +290,7 @@ class ArrayObject implements IteratorAggregate, ArrayAccess, Serializable, Count
public function &offsetGet($key)
{
$ret = null;
if (! $this->offsetExists($key)) {
if (!$this->offsetExists($key)) {
return $ret;
}
$ret =& $this->storage[$key];

View File

@@ -39,11 +39,11 @@ abstract class ArrayUtils
*/
public static function hasStringKeys($value, $allowEmpty = false)
{
if (! is_array($value)) {
if (!is_array($value)) {
return false;
}
if (! $value) {
if (!$value) {
return $allowEmpty;
}
@@ -59,11 +59,11 @@ abstract class ArrayUtils
*/
public static function hasIntegerKeys($value, $allowEmpty = false)
{
if (! is_array($value)) {
if (!is_array($value)) {
return false;
}
if (! $value) {
if (!$value) {
return $allowEmpty;
}
@@ -86,11 +86,11 @@ abstract class ArrayUtils
*/
public static function hasNumericKeys($value, $allowEmpty = false)
{
if (! is_array($value)) {
if (!is_array($value)) {
return false;
}
if (! $value) {
if (!$value) {
return $allowEmpty;
}
@@ -119,11 +119,11 @@ abstract class ArrayUtils
*/
public static function isList($value, $allowEmpty = false)
{
if (! is_array($value)) {
if (!is_array($value)) {
return false;
}
if (! $value) {
if (!$value) {
return $allowEmpty;
}
@@ -161,11 +161,11 @@ abstract class ArrayUtils
*/
public static function isHashTable($value, $allowEmpty = false)
{
if (! is_array($value)) {
if (!is_array($value)) {
return false;
}
if (! $value) {
if (!$value) {
return $allowEmpty;
}
@@ -187,7 +187,7 @@ abstract class ArrayUtils
*/
public static function inArray($needle, array $haystack, $strict = false)
{
if (! $strict) {
if (!$strict) {
if (is_int($needle) || is_float($needle)) {
$needle = (string) $needle;
}
@@ -215,11 +215,11 @@ abstract class ArrayUtils
*/
public static function iteratorToArray($iterator, $recursive = true)
{
if (! is_array($iterator) && ! $iterator instanceof Traversable) {
if (!is_array($iterator) && !$iterator instanceof Traversable) {
throw new Exception\InvalidArgumentException(__METHOD__ . ' expects an array or Traversable object');
}
if (! $recursive) {
if (!$recursive) {
if (is_array($iterator)) {
return $iterator;
}
@@ -274,7 +274,7 @@ abstract class ArrayUtils
} elseif (isset($a[$key]) || array_key_exists($key, $a)) {
if ($value instanceof MergeRemoveKey) {
unset($a[$key]);
} elseif (! $preserveNumericKeys && is_int($key)) {
} elseif (!$preserveNumericKeys && is_int($key)) {
$a[] = $value;
} elseif (is_array($value) && is_array($a[$key])) {
$a[$key] = static::merge($a[$key], $value, $preserveNumericKeys);
@@ -282,7 +282,7 @@ abstract class ArrayUtils
$a[$key] = $value;
}
} else {
if (! $value instanceof MergeRemoveKey) {
if (!$value instanceof MergeRemoveKey) {
$a[$key] = $value;
}
}

View File

@@ -1,158 +0,0 @@
<?php
/**
* @link http://github.com/zendframework/zend-stdlib for the canonical source repository
* @copyright Copyright (c) 2016 Zend Technologies USA Inc. (http://www.zend.com)
* @license http://framework.zend.com/license/new-bsd New BSD License
*/
namespace Zend\Stdlib;
/**
* Utilities for console tooling.
*
* Provides the following facilities:
*
* - Colorize strings using markup (e.g., `<info>message</info>`,
* `<error>message</error>`)
* - Write output to a specified stream, optionally with colorization.
* - Write a line of output to a specified stream, optionally with
* colorization, using the system EOL sequence..
* - Write an error message to STDERR.
*
* Colorization will only occur when expected sequences are discovered, and
* then, only if the console terminal allows it.
*
* Essentially, provides the bare minimum to allow you to provide messages to
* the current console.
*/
class ConsoleHelper
{
const COLOR_GREEN = "\033[32m";
const COLOR_RED = "\033[31m";
const COLOR_RESET = "\033[0m";
const HIGHLIGHT_INFO = 'info';
const HIGHLIGHT_ERROR = 'error';
private $highlightMap = [
self::HIGHLIGHT_INFO => self::COLOR_GREEN,
self::HIGHLIGHT_ERROR => self::COLOR_RED,
];
/**
* @var string Exists only for testing.
*/
private $eol = PHP_EOL;
/**
* @var resource Exists only for testing.
*/
private $stderr = STDERR;
/**
* @var bool
*/
private $supportsColor;
/**
* @param resource $resource
*/
public function __construct($resource = STDOUT)
{
$this->supportsColor = $this->detectColorCapabilities($resource);
}
/**
* Colorize a string for use with the terminal.
*
* Takes strings formatted as `<key>string</key>` and formats them per the
* $highlightMap; if color support is disabled, simply removes the formatting
* tags.
*
* @param string $string
* @return string
*/
public function colorize($string)
{
$reset = $this->supportsColor ? self::COLOR_RESET : '';
foreach ($this->highlightMap as $key => $color) {
$pattern = sprintf('#<%s>(.*?)</%s>#s', $key, $key);
$color = $this->supportsColor ? $color : '';
$string = preg_replace($pattern, $color . '$1' . $reset, $string);
}
return $string;
}
/**
* @param string $string
* @param bool $colorize Whether or not to colorize the string
* @param resource $resource Defaults to STDOUT
* @return void
*/
public function write($string, $colorize = true, $resource = STDOUT)
{
if ($colorize) {
$string = $this->colorize($string);
}
$string = $this->formatNewlines($string);
fwrite($resource, $string);
}
/**
* @param string $string
* @param bool $colorize Whether or not to colorize the line
* @param resource $resource Defaults to STDOUT
* @return void
*/
public function writeLine($string, $colorize = true, $resource = STDOUT)
{
$this->write($string . $this->eol, $colorize, $resource);
}
/**
* Emit an error message.
*
* Wraps the message in `<error></error>`, and passes it to `writeLine()`,
* using STDERR as the resource; emits an additional empty line when done,
* also to STDERR.
*
* @param string $message
* @return void
*/
public function writeErrorMessage($message)
{
$this->writeLine(sprintf('<error>%s</error>', $message), true, $this->stderr);
$this->writeLine('', false, $this->stderr);
}
/**
* @param resource $resource
* @return bool
*/
private function detectColorCapabilities($resource = STDOUT)
{
if ('\\' === DIRECTORY_SEPARATOR) {
// Windows
return false !== getenv('ANSICON')
|| 'ON' === getenv('ConEmuANSI')
|| 'xterm' === getenv('TERM');
}
return function_exists('posix_isatty') && posix_isatty($resource);
}
/**
* Ensure newlines are appropriate for the current terminal.
*
* @param string
* @return string
*/
private function formatNewlines($string)
{
$string = str_replace($this->eol, "\0PHP_EOL\0", $string);
$string = preg_replace("/(\r\n|\n|\r)/", $this->eol, $string);
return str_replace("\0PHP_EOL\0", $this->eol, $string);
}
}

View File

@@ -51,7 +51,7 @@ abstract class ErrorHandler
*/
public static function start($errorLevel = \E_WARNING)
{
if (! static::$stack) {
if (!static::$stack) {
set_error_handler([get_called_class(), 'addError'], $errorLevel);
}
@@ -72,7 +72,7 @@ abstract class ErrorHandler
if (static::$stack) {
$errorException = array_pop(static::$stack);
if (! static::$stack) {
if (!static::$stack) {
restore_error_handler();
}

View File

@@ -38,7 +38,7 @@ abstract class Glob
*/
public static function glob($pattern, $flags = 0, $forceFallback = false)
{
if (! defined('GLOB_BRACE') || $forceFallback) {
if (!defined('GLOB_BRACE') || $forceFallback) {
return static::fallbackGlob($pattern, $flags);
}
@@ -96,7 +96,7 @@ abstract class Glob
*/
protected static function fallbackGlob($pattern, $flags)
{
if (! $flags & self::GLOB_BRACE) {
if (!$flags & self::GLOB_BRACE) {
return static::systemGlob($pattern, $flags);
}
@@ -182,7 +182,7 @@ abstract class Glob
$current = $begin;
while ($current < $length) {
if (! $flags & self::GLOB_NOESCAPE && $pattern[$current] === '\\') {
if (!$flags & self::GLOB_NOESCAPE && $pattern[$current] === '\\') {
if (++$current === $length) {
break;
}

View File

@@ -29,7 +29,7 @@ trait ArrayOrTraversableGuardTrait
$dataName = 'Argument',
$exceptionClass = 'Zend\Stdlib\Exception\InvalidArgumentException'
) {
if (! is_array($data) && ! ($data instanceof Traversable)) {
if (!is_array($data) && !($data instanceof Traversable)) {
$message = sprintf(
"%s must be an array or Traversable, [%s] given",
$dataName,

View File

@@ -9,9 +9,6 @@
namespace Zend\Stdlib;
/**
* @deprecated Since 3.1.0; use the native JsonSerializable interface
*/
interface JsonSerializable extends \JsonSerializable
{
}

View File

@@ -40,7 +40,7 @@ class Message implements MessageInterface
$this->metadata[$spec] = $value;
return $this;
}
if (! is_array($spec) && ! $spec instanceof Traversable) {
if (!is_array($spec) && !$spec instanceof Traversable) {
throw new Exception\InvalidArgumentException(sprintf(
'Expected a string, array, or Traversable argument in first position; received "%s"',
(is_object($spec) ? get_class($spec) : gettype($spec))
@@ -66,7 +66,7 @@ class Message implements MessageInterface
return $this->metadata;
}
if (! is_scalar($key)) {
if (!is_scalar($key)) {
throw new Exception\InvalidArgumentException('Non-scalar argument provided for key');
}

View File

@@ -70,7 +70,7 @@ class Parameters extends PhpArrayObject implements ParametersInterface
*/
public function toString()
{
return http_build_query($this->toArray());
return http_build_query($this);
}
/**

View File

@@ -62,7 +62,7 @@ class PriorityList implements Iterator, Countable
*/
public function insert($name, $value, $priority = 0)
{
if (! isset($this->items[$name])) {
if (!isset($this->items[$name])) {
$this->count++;
}
@@ -85,7 +85,7 @@ class PriorityList implements Iterator, Countable
*/
public function setPriority($name, $priority)
{
if (! isset($this->items[$name])) {
if (!isset($this->items[$name])) {
throw new \Exception("item $name not found");
}
@@ -131,7 +131,7 @@ class PriorityList implements Iterator, Countable
*/
public function get($name)
{
if (! isset($this->items[$name])) {
if (!isset($this->items[$name])) {
return;
}
@@ -145,7 +145,7 @@ class PriorityList implements Iterator, Countable
*/
protected function sort()
{
if (! $this->sorted) {
if (!$this->sorted) {
uasort($this->items, [$this, 'compare']);
$this->sorted = true;
}
@@ -161,7 +161,7 @@ class PriorityList implements Iterator, Countable
protected function compare(array $item1, array $item2)
{
return ($item1['priority'] === $item2['priority'])
? ($item1['serial'] > $item2['serial'] ? -1 : 1) * $this->isLIFO
? ($item1['serial'] > $item2['serial'] ? -1 : 1) * $this->isLIFO
: ($item1['priority'] > $item2['priority'] ? -1 : 1);
}

View File

@@ -99,7 +99,7 @@ class PriorityQueue implements Countable, IteratorAggregate, Serializable
unset($this->items[$key]);
$this->queue = null;
if (! $this->isEmpty()) {
if (!$this->isEmpty()) {
$queue = $this->getQueue();
foreach ($this->items as $item) {
$queue->insert($item['data'], $item['priority']);
@@ -277,7 +277,7 @@ class PriorityQueue implements Countable, IteratorAggregate, Serializable
{
if (null === $this->queue) {
$this->queue = new $this->queueClass();
if (! $this->queue instanceof \SplPriorityQueue) {
if (!$this->queue instanceof \SplPriorityQueue) {
throw new Exception\DomainException(sprintf(
'PriorityQueue expects an internal queue of type SplPriorityQueue; received "%s"',
get_class($this->queue)

View File

@@ -36,7 +36,7 @@ class SplPriorityQueue extends \SplPriorityQueue implements Serializable
*/
public function insert($datum, $priority)
{
if (! is_array($priority)) {
if (!is_array($priority)) {
$priority = [$priority, $this->serial--];
}
parent::insert($datum, $priority);

View File

@@ -84,7 +84,7 @@ abstract class StringUtils
public static function registerWrapper($wrapper)
{
$wrapper = (string) $wrapper;
if (! in_array($wrapper, static::$wrapperRegistry, true)) {
if (!in_array($wrapper, static::$wrapperRegistry, true)) {
static::$wrapperRegistry[] = $wrapper;
}
}

View File

@@ -38,11 +38,11 @@ abstract class AbstractStringWrapper implements StringWrapperInterface
{
$supportedEncodings = static::getSupportedEncodings();
if (! in_array(strtoupper($encoding), $supportedEncodings)) {
if (!in_array(strtoupper($encoding), $supportedEncodings)) {
return false;
}
if ($convertEncoding !== null && ! in_array(strtoupper($convertEncoding), $supportedEncodings)) {
if ($convertEncoding !== null && !in_array(strtoupper($convertEncoding), $supportedEncodings)) {
return false;
}
@@ -61,7 +61,7 @@ abstract class AbstractStringWrapper implements StringWrapperInterface
$supportedEncodings = static::getSupportedEncodings();
$encodingUpper = strtoupper($encoding);
if (! in_array($encodingUpper, $supportedEncodings)) {
if (!in_array($encodingUpper, $supportedEncodings)) {
throw new Exception\InvalidArgumentException(
'Wrapper doesn\'t support character encoding "' . $encoding . '"'
);
@@ -69,7 +69,7 @@ abstract class AbstractStringWrapper implements StringWrapperInterface
if ($convertEncoding !== null) {
$convertEncodingUpper = strtoupper($convertEncoding);
if (! in_array($convertEncodingUpper, $supportedEncodings)) {
if (!in_array($convertEncodingUpper, $supportedEncodings)) {
throw new Exception\InvalidArgumentException(
'Wrapper doesn\'t support character encoding "' . $convertEncoding . '"'
);

View File

@@ -214,7 +214,7 @@ class Iconv extends AbstractStringWrapper
*/
public function __construct()
{
if (! extension_loaded('iconv')) {
if (!extension_loaded('iconv')) {
throw new Exception\ExtensionNotLoadedException(
'PHP extension "iconv" is required for this wrapper'
);

View File

@@ -37,7 +37,7 @@ class Intl extends AbstractStringWrapper
*/
public function __construct()
{
if (! extension_loaded('intl')) {
if (!extension_loaded('intl')) {
throw new Exception\ExtensionNotLoadedException(
'PHP extension "intl" is required for this wrapper'
);

View File

@@ -48,7 +48,7 @@ class MbString extends AbstractStringWrapper
*/
public function __construct()
{
if (! extension_loaded('mbstring')) {
if (!extension_loaded('mbstring')) {
throw new Exception\ExtensionNotLoadedException(
'PHP extension "mbstring" is required for this wrapper'
);

View File

@@ -35,7 +35,7 @@ class Native extends AbstractStringWrapper
$encodingUpper = strtoupper($encoding);
$supportedEncodings = static::getSupportedEncodings();
if (! in_array($encodingUpper, $supportedEncodings)) {
if (!in_array($encodingUpper, $supportedEncodings)) {
return false;
}
@@ -69,7 +69,7 @@ class Native extends AbstractStringWrapper
$supportedEncodings = static::getSupportedEncodings();
$encodingUpper = strtoupper($encoding);
if (! in_array($encodingUpper, $supportedEncodings)) {
if (!in_array($encodingUpper, $supportedEncodings)) {
throw new Exception\InvalidArgumentException(
'Wrapper doesn\'t support character encoding "' . $encoding . '"'
);