1

How can I change a Slim Request's URI path? I tried the following, however, withPath() clones the uri thus the request object isn't changed. If it is not possible, is there a straightforward process to create a new Slim Request based on the original Request but the new URI path?

Background regarding why I wish to do so. I have a method which accepts a Slim Request, performs a cURL request to another server using Guzzle, writes to the Slim Response, and returns the Slim Response. The API which Guzzle queries almost the same path but with a version number.

$app->get('/{basetype:guids|tester}/{guid}/logs/{id:[0-9]+}', function (Request $request, Response $response, $args) {
    switch($request->getQueryParam('ContentType')) {
        case 'text':
            //
            return $this->view->render($response, 'log.html', $rs);
        case 'file':
            $uri=$request->getUri();
            $path=$uri->getPath();
            $uri->withPath(_VER_.$path);
            return $this->serverBridge->proxy($request, $response, 'application/octet-stream');
    }
});

class ServerBridge
{
    protected $httpClient;

    public function __construct(\GuzzleHttp\Client $httpClient)
    {
        $this->httpClient=$httpClient;
    }

    public function proxy(\Slim\Http\Request $slimRequest, \Slim\Http\Response $slimResponse):\Slim\Http\Response {
        //$slimRequest is used to obtain data to send to Guzzle 
        $curlResponse = $this->httpClient->request($method, $path, $options);
        //use $curlResponse to get data and write to $slimResponse
        return $slimResponse;
    }
}
user1032531
  • 24,767
  • 68
  • 217
  • 387

1 Answers1

2

If you change the Uri path, you have to change the request as well. This is by design. Don't worry, cloning is cheap in PHP.

<?php

$request = $request->withUri($request->getUri()->withPath('your/changed/path'));

Note: Be careful to use that new $request in some other calls in the middleware stack. They were made immutable for a reason. Changing the uri of a request early in the execution can have undesirable side effects.

  • Thanks Matias, Ah, I see you just make a new Request object using the withUri method. Haven't tested, but works for me. Yes, I saw that they are immutable. Just curious, why is it by design? Note that I need to, but if I wanted a different path and port, would I just clone the object twice? – user1032531 Dec 26 '18 at 23:54
  • That is actually a good question. I think that the PHP-FIG and PHP devs in general are adopting some of the good functional practices and concepts. Immutability is one of them. I'm skeptic that bears some benefits in this case, but I guess it was made like that because the Request and Response would be end up being passed along a pretty big middleware stack. In any case, the [meta document](https://www.php-fig.org/psr/psr-7/meta/) of the psr provides a better explanation that the one I can probably give you. – Matías Navarro Carter Dec 27 '18 at 11:36
  • And yes, you just can change pretty much anything in the Request object with no problem. If you pass that to a middleware stack though, they will handle the changed request. If you want to store metadata in the Request, the `withAttribute` method is your friend. – Matías Navarro Carter Dec 27 '18 at 12:11