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

ServerRequest and UploadedFIle Implementation #54

Merged
merged 13 commits into from Mar 21, 2016

Conversation

ivank
Copy link
Contributor

@ivank ivank commented Dec 23, 2015

This is an implementation of ServerRequest and UploadedFIle and closes #13.

I realize there is already a PR for that (#32) but it seams sort-of abandoned. I was waiting on that functionality as I need it in one of my projects, so seeing this PR stagnate I decided to reimplement it myself.
It has almost full test coverage, the $_FILES array conversion handles more cases, the moveTo method is according to spec and I try to use the already available functionality as much as possible

Merry Christmas 🎄 :)

@ivank
Copy link
Contributor Author

ivank commented Jan 6, 2016

@mtdowling post holiday ping, hope you guys are doing well :)

@mtdowling
Copy link
Member

Thanks for putting this together!

I haven't reviewed this yet, but one thing I want to ensure is that if this is work based on #32, then I'd prefer it if you include the original author's commits in the history so we can ensure credit is given in the log. If that is not the case, then no worries.


return $uri
->withScheme(isset($_SERVER['HTTPS']) && $_SERVER['HTTPS'] == 'on' ? 'https' : 'http')
->withHost($_SERVER['SERVER_NAME'])
Copy link

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Sometimes this is empty, throwing an PHP Notice undefined index

@ivank
Copy link
Contributor Author

ivank commented Jan 8, 2016

@mtdowling I haven't based this on @SaphirAngel pull request, rather copy-pasted small amounts of code here and there, then heavily modified, I thought basing it on his work and then radically changing everything will make little sense to future reviewers of the code, (since this is not how this code came to be) but if you prefer I could certainly do it like that.

Another approach would be to rewrite the commits and mention him explicitly if you think that will be more appropriate.

10x @jmatosp will certainly fix those

@jmatosp
Copy link

jmatosp commented Jan 8, 2016

I haven't seen the code, but keep an eye on basic benchmarks... so far so good

diactoros psr7 from globals: 22,249 reqs/s
symfony request from globals: 46,943 reqs/s
Guzzle psr7 from globals: 219,159 reqs/s

This is just instance creation

https://gist.github.com/jmatosp/bbb33c8121e6cc106615

@ivank
Copy link
Contributor Author

ivank commented Jan 12, 2016

Well they do quite a lot of additional processing to make the data appear in a unified interface, while I just stick to the PSR-7 standard and don't add any more stuff than necessary. I think this is a good approach as anything more can be built on top of this afterwards.

@ivank
Copy link
Contributor Author

ivank commented Jan 22, 2016

@mtdowling @jmatosp any idea when you guys could take a look at this and tell me if you need something else improved or you think its a good enough MVP? I know you are probably very busy people and hate to nag but it would be really great to not need to rely on composer repository hacks for a project I'm working on (https://github.com/spiderling-php more specifically - https://github.com/spiderling-php/kohana-driver/blob/master/src/Loader.php and some other repos in this project too).

*/
private function isStringNotEmpty($param)
{
return is_string($param) && false == empty($param);
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

strict comparison ===

Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

...or !empty($params)?

@webda2l
Copy link
Contributor

webda2l commented Jan 22, 2016

Hope a merge too.
I'll just move static functions of ServerRequest class after __construct, more usual way.

$uri = $uri->withScheme($_SERVER['HTTPS'] == 'on' ? 'https' : 'http');
}

if (isset($_SERVER['SERVER_NAME'])) {
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

When $_SERVER['HTTP_HOST'] is defined, I think it contains better information. I think Diactoros and Symfony both prioritize using that value.

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Yeah the long SO question has all of those issues explained. I read a bit deeper and indeed due to some bugs in PHP, HTTP_HOST is what we need. And as you said it is true that others already prioritize it, and it must be working for them.

Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

IMO relying on the Host header is way more insecure than server variables. Anyone can modify the host header. But if the server variables are broken then it's more likely a broken webserver setup. So the host header, if used at all, should have lower priority than the SERVER_NAME.

Also the implementation using the host header is broken as the host header can also include the port. So it needs to be excluded before calling ->withHost.

@jeremeamia
Copy link
Member

Any advantages or disadvantages to using filter_input vs. directly accessing the super globals?

@ivank
Copy link
Contributor Author

ivank commented Jan 22, 2016

To tell you the truth never heard of "filter_input" till now :) It does look neat, but it might be harder to write tests for. I can certainly rewrite it using filter_input instead of direct superglobal access, but I don't really see what's the difference, apart from longer code ...

@jeremeamia
Copy link
Member

It actually makes it impossible to test as far as I can tell, and there doesn't seem to be any strong benefits. So, we'll table that.

@aurimasniekis
Copy link

Any progress on this? Would like to use this instead own implementation on my http server

@ivank
Copy link
Contributor Author

ivank commented Jan 26, 2016

Well I hope I've addressed all the comments from the team, waiting for the next wave :)

*/
private $uploadedFiles;

/**
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Outdated phpdoc

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

@webda2l sorry didn't get this one, how should this be documented?

Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

__construct params don't matches phpdoc.

@param string $method
@param string|Uri $uri
....

@ivank
Copy link
Contributor Author

ivank commented Feb 13, 2016

@webda2l, @GCDS updated the phpdocs, you guys should really look into scrutinizer as it handles all of these psr standards checking, phpdoc updating and code coverage automatically. I have it on for most of my OSS projects and I've kind of don't really pay that much attention to it anymore, sorry.

Example: https://scrutinizer-ci.com/g/clippings/composer-init/ more specifically: https://scrutinizer-ci.com/g/clippings/composer-init/inspections/73324ada-d30e-4d37-aba7-0fef471ba659/patches

@webda2l
Copy link
Contributor

webda2l commented Feb 14, 2016

@ivank Yes true. This is not my project here, just a developer who use your fork and hope a merge. But for my own projects and projects clients, I use scrutinizer too, it ease this kind of review, yes.

/**
* @var array
*/
private $serverParams = [];

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Does not require initial value as constructor passes default value []

@ivank
Copy link
Contributor Author

ivank commented Feb 27, 2016

@mtdowling, @jeremeamia I've rebased this with latest master. It would be fantastic if you guys could take a look and tell me what else needs to be done to get this thing merged?

@webda2l
Copy link
Contributor

webda2l commented Mar 14, 2016

@guzzle Will nice to merge this PR while there is no conflicts.
Other PSR-7 like SLIM one, progress http://www.slimframework.com/2016/03/10/slim-3.3.0.html

@webda2l
Copy link
Contributor

webda2l commented Mar 16, 2016

Ẁill be better to adding this patch before merge I think

diff --git a/src/functions.php b/src/functions.php
index 921a5a8..65ee687 100644
--- a/src/functions.php
+++ b/src/functions.php
@@ -234,6 +234,19 @@
         $uri = $uri->withQuery($changes['query']);
     }

+    if ($request instanceof ServerRequest) {
+        return new ServerRequest(
+            isset($changes['method']) ? $changes['method'] : $request->getMethod(),
+            $uri,
+            $headers,
+            isset($changes['body']) ? $changes['body'] : $request->getBody(),
+            isset($changes['version'])
+                ? $changes['version']
+                : $request->getProtocolVersion(),
+            $request->getServerParams()
+        );
+    }
+
     return new Request(
         isset($changes['method']) ? $changes['method'] : $request->getMethod(),
         $uri,

@mtdowling
Copy link
Member

@ivank Thanks for all the work you put into this. Can you comment on if you would be able to help me and the rest of the Guzzle team to help support and maintain this functionality?

@ivank
Copy link
Contributor Author

ivank commented Mar 21, 2016

@mtdowling sure I can help, though as of last month I don't really work with PHP all that much so might be a bit slow in participating.

@mtdowling
Copy link
Member

Thanks @ivank! I like that most of the implementation details are private, which will make this easier to maintain IMO. 🎈

mtdowling added a commit that referenced this pull request Mar 21, 2016
ServerRequest and UploadedFIle Implementation
@mtdowling mtdowling merged commit ee6a9b7 into guzzle:master Mar 21, 2016
@mtdowling mtdowling mentioned this pull request Mar 21, 2016
@ivank ivank deleted the server-request branch March 27, 2016 08:38
* @throws InvalidArgumentException for unrecognized values
* @return array
*/
public static function normalizeFiles(array $files)
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I don't think this should be public.

@barryvdh
Copy link
Contributor

barryvdh commented Jun 4, 2016

@ivank Could you update the readme with docs/examples for the new methods?

@Tobion
Copy link
Member

Tobion commented Jun 5, 2016

How to determine the request uri is also standarized: http://tools.ietf.org/html/rfc7230#section-5.5
They use the Host header as well. So I assume the webserver must really be configured to not just blindly accept any host header.

@iotch
Copy link

iotch commented Jul 29, 2016

Hello.
I think apache_request_headers()/getallheaders() polyfill should be provided for this:
https://github.com/guzzle/psr7/blob/master/src/ServerRequest.php#L169
as those functions are only available when running PHP as an Apache module.

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

Successfully merging this pull request may close these issues.

Implement missing PSR-7 implementations
10 participants