Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Psr17Factory does not construct ServerRequest with body? #128

Closed
burzum opened this issue Sep 11, 2019 · 3 comments
Closed

Psr17Factory does not construct ServerRequest with body? #128

burzum opened this issue Sep 11, 2019 · 3 comments

Comments

@burzum
Copy link

burzum commented Sep 11, 2019

Why is https://github.com/Nyholm/psr7/blob/master/src/Factory/Psr17Factory.php#L69 the factory not initialized with the body?

I figured out that there is a separate package (Nyholm\Psr7Server). OK, But why!?

Now I have to add another dependency and I basically have to copy and paste the code from the docs into my own ServerRequestFactory? Why?

I had the hope to just use this package and start off with a working server request by using the factory included in this package.

<?php
declare(strict_types=1);

namespace App\Infrastructure\Http;

use Nyholm\Psr7\Factory\Psr17Factory;
use Nyholm\Psr7\ServerRequest;
use Nyholm\Psr7Server\ServerRequestCreator;
use Psr\Http\Message\ResponseInterface;
use Psr\Http\Message\ServerRequestFactoryInterface;
use Psr\Http\Message\ServerRequestInterface;
use Psr\Http\Message\UriInterface;

class ServerRequestFactory implements ServerRequestFactoryInterface
{
    public function createServerRequest(string $method, $uri, array $serverParams = []): ServerRequestInterface
    {
        $psr17Factory = new Psr17Factory();

        $creator = new ServerRequestCreator(
            $psr17Factory, // ServerRequestFactory
            $psr17Factory, // UriFactory
            $psr17Factory, // UploadedFileFactory
            $psr17Factory  // StreamFactory
        );

        return $creator->fromGlobals();
    }
}
@Zegnat
Copy link
Collaborator

Zegnat commented Oct 5, 2019

Now I have to add another dependency and I basically have to copy and paste the code from the docs into my own ServerRequestFactory? Why?

This repo implements the PSR standards with as little extras as possible. PSR-17 only defines a method for creating a ServerRequest with its HTTP method, an URI, and a collection of parameters. There is no standard way of creating it with more than those things already set, so if one would be added here it could lead to incompatibilities between PSR-17 implementations.

In fact, the unit tests for PSR-17 HTTP Factories specifically include tests to make sure an implementation never reads the global server values. PSR-17 implementations are not allowed to do so.

This combines means the “correct” way to fill a ServerRequest object based on the current request that came to your webserver is to write your own code to do so. That is why psr7-server was written.

I hope I was able to shine some light on the situation for you! I am going to close this issue as it isn’t actually an issue with this library.

@Zegnat Zegnat closed this as completed Oct 5, 2019
@burzum
Copy link
Author

burzum commented Apr 3, 2020

@Zegnat so what would be a proper, standard conform way of getting the body filled with the expected data of a POST request that would respect the PSR standards?

@Zegnat
Copy link
Collaborator

Zegnat commented Apr 4, 2020

@burzum something like this:

// Pick your favourite PSR-17 factory, using Nyholm here:
$psr17Factory = new \Nyholm\Psr7\Factory\Psr17Factory();
// Create the ServerRequest with whatever parameters you have:
$serverRequest = $psr17Factory->createServerRequest($method, $uri, $serverParams)
// And add the value of $_POST:
    ->withParsedBody($_POST);

Although to be really fully standard conform, you have to do a whole bunch of checks before doing the withParsedBody() call. Even psr7-server may not be completely correct, see my PR over there with the extra checks that are needed. But in most cases it gets the job done right.

In part because of all these little small details did the PHP-FIG (makers of the PSR) not standardise a way to create a ServerRequest from an actual request. How to create this object depends completely on what server you have, what sort of context your application is running in, and more. So only you know how to fill a ServerRequest in the correct way.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

No branches or pull requests

2 participants