Open mikegreiling opened 12 years ago
Since this does break some BC and requires changes to framework
in addition to lithium
, this should probably live in a branch and wait for the next milestone release (1.0 or 0.11).
This is an interesting proposal and I'm not opposed to it. I just need to think on it for a while.
I'm not sure if this is appropriate, but if its ok, I'd like to add my vote for this, and see it implemented in the current master.
Thanks @nateabele, I'm interested to hear your considered opinion, and I'd love to get feedback from anyone else with 2¢ to add to the conversation as well.
There are more issues than this with the Session functionality:
Might as well look at them together?
@Ciaro The reason they seem to eat each other is because I had a design idea originally where you could read or write to multiple ones in a single call. That ended up just not working well, so yeah, that's definitely something we can address as well.
The issue with session encryption and flash messages is that li3_flash_message
always uses its own session storage. This is obviously a problem, which I'm trying to address here: https://github.com/uor/li3_flash_message (fork and contribute if you feel so inclined).
@nateabele Thanks for the update!
Atm, I'm quite swamped with a new project. I probably cannot invest time looking into your fork (in detail). I'm more than happy to test it out on one or two projects once it's finished, though...
It's been a few weeks. Any thoughts on these or other changes to the session/auth adapters?
@pixelcog I just had a kid, so to me it's still only been a few days. ;-)
@nateabele I'd say that's a valid excuse :)
Description of the issue.
Lithium does a great job of avoiding the use of superglobals in favor of the Request object, and relegating all output functionality to the Response object's render() method. All other objects defer to these two in all input/output functions. This enhances testability by reducing the side effects of globally scoped variables and output functions, essentially leaving the global I/O immutable outside of these privelaged objects. I think the term for this behavior is referential transparency, and you guys talk a great deal about it in your FAQs.
Lithium, however falls short in one area. The adapters for
\lithium\storage\Session
and\lithium\security\Auth
appear to have a unique exclusion to the rule that the rest of the library abides by. They both take liberties withheader()
,setcookie()
, andsession_start()
(which send output to the client), and read data directly from$_COOKIE
(and$_GET
/$_POST
if you includesession_start()
whensession.use_only_cookies
is false).Prescription
I think the separation of concerns regarding client I/O is important, and should be consistant. I would propose the following:
$_COOKIE
superglobal to\lithium\action\Request
(it is part of the request after all). It could be accessed alongside$request->data
and$request->query
as$request->cookie
or something similar.\lithium\action\Response
, to be rendered only inResponse::render()
. Just as you can currently set arbitrary headers with$response->headers()
, setting cookies will store them in some temporary location along with TTL and scope data to await rendering.Update
\lithium\storage\Session
to include two adapter methods for Request injection and Response manipulation. I'd call these something likeSession::prime($request)
andSession::apply($response)
, and they would be filtered intoDispatcher::run()
like so:Note the
prime
method should not actually do anything other than collect the $request object and store it for later use. This is because due to the ordering of Dispatcher filters, theEnvironment::set()
may not yet have been called.\lithium\security\Auth
similarly, withprime()
andapply()
adapter methods. Theprime()
method could be ignored if you intend to pass the request intoAuth::check()
every time. Theapply()
method would have no use in any of the currentAuth
adapters, but it would have applications if someone wanted to create an adapter which saves an authentication token as a cookie upon login or logout (implementing "keep me logged in for xxx days" functionality). These methods could also be wrapped aroundDispatcher::run()
header()
, andsetcookie()
, and neuteringsession_start()
withini_set("session.use_cookies", false)
and setting the id manually withsession_id($key)
.headers_list()
.Concerns
Cons:
framework
as well aslithium
.Session::read()
is called prior toSession::prime()
). Plus, if needed, taking out and plugging in the old session class in place of the new one is an easy task due to Li3's flexible nature.Pros:
Implementation
I can help write tests, update the classes, and do whatever is necessary to make this happen, but I want some tentative approval from the powers that be before I put forth all of that effort. And of course, I would welcome any help.
I had brought this up in the #li3-core chatroom about a year and a half ago and @gwoo seemed to be on board. Unfortunately I did not have the free time back then to implement it.