[dancer-users] session() auto-flush
Warren Young
warren at etr-usa.com
Fri Feb 14 18:41:44 GMT 2014
On 2/14/2014 03:45, David Golden wrote:
> On Thu, Feb 13, 2014 at 11:37 PM, Warren Young <warren at etr-usa.com> wrote:
>> I finally tracked it down to the fact that session(X, Y) automatically calls
>> flush() on the object for you, whereas session() with no parameters returns
>> a hashref that doesn't auto-flush itself.
>
> Really, session() with no parameters returns a session *object*, it
> happens to be implemented as a hash ref. There's no magic to it. To
> make objects do things, you have to call methods on them.
...But there *could* be magic to it. :)
I tracked the problem down further. It is that when you call
Dancer::Session::YAML::retrieve() indirectly via Dancer::session(), it
is loading the session object back up from disk, obliterating the
contents of the previous object.
You can see the problem easily:
1. Create a new Dancer 1 project
2. Edit the lone route handler:
session a => 1;
session()->{b} = 2;
session c => 3;
The 'b' line simulates my passing of session()'s return to another module.
3. Add session: "YAML" to config.yml
4. Run the app, hit the page, examine the session file:
--- !!perl/hash:Dancer::Session::YAML
a: 1
c: 3
id: 375432505278121443472247271047126129
My notion was that session() was returning the same global object, in
the same way that request() does. The 'b' field would remain in memory
only until the 'c' field is written, which implicitly calls flush() due
to the difference in the way session() handles parameters.
It would be even nicer if, at the end of a route handler's processing,
Dancer would detect that there is a dirty session object and flush it
for you.
"Exit without saving" is never a desired use case with session objects,
as it can be for, say, word processing documents.
This doesn't happen with Dancer::Session::Simple for fairly obvious
reasons. However, I suspect it would happen with any other persistent
session mechanism.
The "magic" I hinted at above would be to keep the session object loaded
and in RAM from the first session() call until the end of the route
handler, never reloading from disk, but auto-flushing at the end.
This would have the nice side benefit of speeding up session I/O.
Really, there's not a lot of point of persisting the session object more
than once per route call, is there? There's even less point to
repeatedly re-loading it from disk. It's not like there's another
process also writing to the same session.
...Or is there? With a forking front end, do all calls from a
particular client go to a particular Dancer app instance, or is that
parallelized, too?
> I assume you're talking Dancer 1, here, right?
Yes, and I realize it's feature-frozen. This behavior strikes me as
bug-like, so I don't see that the freeze is a reason not to improve the
behavior.
More information about the dancer-users
mailing list