Skip to content

Commit

Permalink
Added transport to support egeloen/http-adapter
Browse files Browse the repository at this point in the history
Supporting [egeloen/http-adapter](https://github.com/egeloen/ivory-http-adapter) will
allow to make http calls using  multiple libraries (including Guzzle3) :

* Buzz
* Cake
* cURL
* FileGetContents
* Fopen
* Guzzle
* GuzzleHttp
* Httpful
* React
* Socket
* Zend1
* Zend2

Here is an example of how to use it :

```php
  $guzzle3 = new \Guzzle\Http\Client();

  $httpAdapter = new \Ivory\HttpAdapter\GuzzleHttpAdapter();
  $httpAdapterTransport = new \Elastica\Transport\HttpAdapter(null, $httpAdapter);

  $elastica = new \Elastica\Client(array(
      'connections' => array(
          array(
          '   host' => 'localhost',
              'port' => 9200,
              'transport' => $httpAdapterTransport,
          )
      )
  ));

  var_dump($elastica->getIndex('livre')->getType('livre')->getDocument('9782212136777')->getData());
```
  • Loading branch information
agallou committed Nov 23, 2014
1 parent 5fe627f commit 0683bf1
Show file tree
Hide file tree
Showing 2 changed files with 162 additions and 0 deletions.
1 change: 1 addition & 0 deletions composer.json
Original file line number Diff line number Diff line change
Expand Up @@ -23,6 +23,7 @@
"suggest": {
"munkie/elasticsearch-thrift-php": "Allow using thrift transport",
"guzzlehttp/guzzle": "Allow using guzzle 4.x as the http transport (requires php 5.4)",
"egeloen/http-adapter": "Allow using httpadapter transport",
"psr/log": "for logging",
"monolog/monolog": "Logging request"
},
Expand Down
161 changes: 161 additions & 0 deletions lib/Elastica/Transport/HttpAdapter.php
Original file line number Diff line number Diff line change
@@ -0,0 +1,161 @@
<?php

namespace Elastica\Transport;

use Elastica\Connection;
use Elastica\Exception\PartialShardFailureException;
use Elastica\Exception\ResponseException;
use Elastica\JSON;
use Elastica\Request as ElasticaRequest;
use Elastica\Response as ElasticaResponse;
use Elastica\Transport\AbstractTransport;
use Ivory\HttpAdapter\HttpAdapterInterface;
use Ivory\HttpAdapter\Message\Stream\StringStream;
use Ivory\HttpAdapter\Message\Request as HttpAdapterRequest;
use Ivory\HttpAdapter\Message\Response as HttpAdapterResponse;

class HttpAdapter extends AbstractTransport
{
/**
* @var HttpAdapterInterface
*/
private $httpAdapter;

/**
* @var string
*/
private $_scheme = 'http';

/**
* Construct transport
*
*/
public function __construct(Connection $connection = null, HttpAdapterInterface $httpAdapter)
{
parent::__construct($connection);
$this->httpAdapter = $httpAdapter;
}

/**
* Makes calls to the elasticsearch server
*
* All calls that are made to the server are done through this function
*
* @param \Elastica\Request $elasticaRequest
* @param array $params Host, Port, ...
* @throws \Elastica\Exception\ConnectionException
* @throws \Elastica\Exception\ResponseException
* @throws \Elastica\Exception\Connection\HttpException
* @return \Elastica\Response Response object
*/
public function exec(ElasticaRequest $elasticaRequest, array $params)
{
$connection = $this->getConnection();

if ($timeout = $connection->getTimeout()) {
$this->httpAdapter->getConfiguration()->setTimeout($timeout);
}

$httpAdapterRequest = $this->createHttpAdapterRequest($elasticaRequest, $connection);

$start = microtime(true);
$httpAdapterResponse = $this->httpAdapter->sendRequest($httpAdapterRequest);
$end = microtime(true);

$elasticaResponse = $this->createElasticaResponse($httpAdapterResponse, $connection);

if (defined('DEBUG') && DEBUG) {
$elasticaResponse->setQueryTime($end - $start);
}

$elasticaResponse->setTransferInfo(
array(
'request_header' => $httpAdapterRequest->getMethod(),
'http_code' => $httpAdapterResponse->getStatusCode(),
)
);

if ($elasticaResponse->hasError()) {
throw new ResponseException($elasticaRequest, $elasticaResponse);
}

if ($elasticaResponse->hasFailedShards()) {
throw new PartialShardFailureException($elasticaRequest, $elasticaResponse);
}

return $elasticaResponse;
}

/**
* @param HttpAdapterResponse $httpAdapterResponse
*
* @return ElasticaResponse
*/
protected function createElasticaResponse(HttpAdapterResponse $httpAdapterResponse)
{
return new ElasticaResponse((string)$httpAdapterResponse->getBody(), $httpAdapterResponse->getStatusCode());
}

/**
* @param ElasticaRequest $elasticaRequest
* @param Connection $connection
*
* @return HttpAdapterRequest
*/
protected function createHttpAdapterRequest(ElasticaRequest $elasticaRequest, Connection $connection)
{
$data = $elasticaRequest->getData();
$body = null;
$method = $elasticaRequest->getMethod();
$headers = $connection->hasConfig('headers') ?: array();
if (!empty($data) || '0' === $data) {

if ($method == ElasticaRequest::GET) {
$method = ElasticaRequest::POST;
}

if ($this->hasParam('postWithRequestBody') && $this->getParam('postWithRequestBody') == true) {
$elasticaRequest->setMethod(ElasticaRequest::POST);
$method = ElasticaRequest::POST;
}

if (is_array($data)) {
$body = JSON::stringify($data, 'JSON_ELASTICSEARCH');
} else {
$body = $data;
}
}

$url = $this->getUri($elasticaRequest, $connection);
$streamBody = new StringStream($body);

return new HttpAdapterRequest($url, $method, HttpAdapterRequest::PROTOCOL_VERSION_1_1, $headers, $streamBody);
}

/**
* @param ElasticaRequest $request
* @param \Elastica\Connection $connection
*
* @return string
*/
protected function getUri(ElasticaRequest $request, Connection $connection)
{
$url = $connection->hasConfig('url') ? $connection->getConfig('url') : '';

if (!empty($url)) {
$baseUri = $url;
} else {
$baseUri = $this->_scheme . '://' . $connection->getHost() . ':' . $connection->getPort() . '/' . $connection->getPath();
}

$baseUri .= $request->getPath();

$query = $request->getQuery();

if (!empty($query)) {
$baseUri .= '?' . http_build_query($query);
}

return $baseUri;
}
}

0 comments on commit 0683bf1

Please sign in to comment.