<?php
namespace GuzzleHttp\Command\Guzzle;
use GuzzleHttp\Command\CommandInterface;
use GuzzleHttp\Command\Guzzle\RequestLocation\BodyLocation;
use GuzzleHttp\Command\Guzzle\RequestLocation\FormParamLocation;
use GuzzleHttp\Command\Guzzle\RequestLocation\HeaderLocation;
use GuzzleHttp\Command\Guzzle\RequestLocation\JsonLocation;
use GuzzleHttp\Command\Guzzle\RequestLocation\MultiPartLocation;
use GuzzleHttp\Command\Guzzle\RequestLocation\QueryLocation;
use GuzzleHttp\Command\Guzzle\RequestLocation\RequestLocationInterface;
use GuzzleHttp\Command\Guzzle\RequestLocation\XmlLocation;
use GuzzleHttp\Psr7\Request;
use GuzzleHttp\Psr7\Uri;
use Psr\Http\Message\RequestInterface;
class Serializer
{
private $locations;
private $description;
public function __construct(
DescriptionInterface $description,
array $requestLocations = []
) {
static $defaultRequestLocations;
if (!$defaultRequestLocations) {
$defaultRequestLocations = [
'body' => new BodyLocation(),
'query' => new QueryLocation(),
'header' => new HeaderLocation(),
'json' => new JsonLocation(),
'xml' => new XmlLocation(),
'formParam' => new FormParamLocation(),
'multipart' => new MultiPartLocation(),
];
}
$this->locations = $requestLocations + $defaultRequestLocations;
$this->description = $description;
}
public function __invoke(CommandInterface $command)
{
$request = $this->createRequest($command);
return $this->prepareRequest($command, $request);
}
protected function prepareRequest(
CommandInterface $command,
RequestInterface $request
) {
$visitedLocations = [];
$operation = $this->description->getOperation($command->getName());
foreach ($operation->getParams() as $name => $param) {
$location = $param->getLocation();
if ($location == 'uri' || !$command->hasParam($name)) {
continue;
}
if (!isset($this->locations[$location])) {
throw new \RuntimeException("No location registered for $name");
}
$visitedLocations[$location] = true;
$request = $this->locations[$location]->visit($command, $request, $param);
}
if ($additional = $operation->getAdditionalParameters()) {
$visitedLocations[$additional->getLocation()] = true;
}
foreach (array_keys($visitedLocations) as $location) {
$request = $this->locations[$location]->after($command, $request, $operation);
}
return $request;
}
protected function createRequest(CommandInterface $command)
{
$operation = $this->description->getOperation($command->getName());
if (null === $operation->getUri()) {
return new Request(
$operation->getHttpMethod(),
$this->description->getBaseUri()
);
}
return $this->createCommandWithUri($operation, $command);
}
private function createCommandWithUri(
Operation $operation,
CommandInterface $command
) {
$variables = [];
foreach ($operation->getParams() as $name => $arg) {
if ($arg->getLocation() == 'uri') {
if (isset($command[$name])) {
$variables[$name] = $arg->filter($command[$name]);
if (!is_array($variables[$name])) {
$variables[$name] = (string) $variables[$name];
}
}
}
}
$uri = \GuzzleHttp\uri_template($operation->getUri(), $variables);
return new Request(
$operation->getHttpMethod(),
Uri::resolve($this->description->getBaseUri(), $uri)
);
}
}