Initial commit, module as it went live as 0.10
[catagits/Catalyst-Plugin-Session-State-Stash.git] / lib / Catalyst / Plugin / Session / State / Stash.pm
1 package Catalyst::Plugin::Session::State::Stash;
2 use base qw/Catalyst::Plugin::Session::State Class::Accessor::Fast/;
3
4 use strict;
5 use warnings;
6 use MRO::Compat;
7
8 our $VERSION = "0.10";
9
10 BEGIN { __PACKAGE__->mk_accessors(qw/_deleted_session_id _prepared/) }
11
12 sub _session_stash_key {
13     my ($c) = @_;
14
15     $c->config->{session}->{stash_key};
16 }
17
18 sub _get_session {
19     my ($c) = @_;
20     
21     $c->stash->{$c->_session_stash_key};
22 }
23
24 sub _set_session {
25     my ( $c,$key,$value) = @_;
26     
27     $c->stash->{$c->_session_stash_key}->{$key} = $value;
28 }
29
30 sub setup_session {
31     my $c = shift;
32
33     $c->config->{session}->{stash_key}
34         ||= '_session';
35 }
36
37 sub prepare_action {
38     my $c = shift;
39     my $id = $c->get_session_id;
40     $c->_prepared(1);
41     if ( $id ) {
42         $c->sessionid( $id );
43     }
44     $c->maybe::next::method( @_ );
45 }
46
47 sub get_session_id {
48     my $c = shift;
49     if(!$c->_deleted_session_id and my $session = $c->_get_session) {
50         my $sid = $session->{id};
51         return $sid if $sid;
52     }
53     $c->maybe::next::method(@_);
54 }
55
56 sub set_session_id {
57     my ( $c, $sid ) = @_;
58     $c->_set_session(id => $sid);
59     $c->maybe::next::method($sid);
60 }
61
62 sub get_session_expires {
63     my $c = shift;
64     my $session = $c->_get_session;
65     defined $session->{expires} ? $session->{expires} : undef;
66 }
67
68 sub set_session_expires {
69     my ( $c, $expires ) = @_;
70     
71     $c->_set_session(expires => time() + $expires);
72     $c->maybe::next::method($expires)
73 }
74
75 sub delete_session_id {
76     my ($c, $sid ) = @_;
77     $c->_deleted_session_id(1);
78     undef $c->{stash}->{$c->_session_stash_key};
79     $c->maybe::next::method($sid);
80 }
81
82
83 1;
84 __END__
85
86 =pod
87
88 =head1 NAME
89
90 Catalyst::Plugin::Session::State::Stash - Maintain session IDs using the stash
91
92 =head1 SYNOPSIS
93
94  use Catalyst qw/Session Session::State::Stash Session::Store::Foo/;
95
96 =head1 DESCRIPTION
97
98 An alternative state storage plugin that allows you some more flexibility in
99 dealing with session storage. This plugin loads and saves the session ID from
100 and to the stash.
101
102 =head1 METHODS
103
104 =over 4
105
106 =item delete_session_id
107
108 Deletes the session. Unfortunately I've been unable to squash a bug that will
109 stop you from opening a new session in the same execution, however.
110 Patches welcome!
111
112 =item get_session_id
113
114 Gets the current session id.
115
116 =item set_session_id
117
118 Sets the session id to the C<shift>.
119
120 =item get_session_expires
121
122 Gets when the current session expires.
123
124 =item set_session_expires
125
126 Sets how many seconds from now the session should expire.
127
128 =back
129
130 =head1 EXTENDED METHODS
131
132 =over 4
133
134 =item prepare_action
135
136 Loads the id off the stash.
137
138 =item setup_session
139
140 Defaults the C<stash_key> parameter to C<_session>.
141
142 =back
143
144 =head1 CONFIGURATION
145
146 =over 4
147
148 =item stash_key
149
150 The name of the hash key to use. Defaults to C<_session>.
151
152 =item expires
153     
154 How long the session should last in seconds.
155
156 =back
157
158 For example, you could stick this in MyApp.pm:
159
160   __PACKAGE__->config( session => {
161      stash_key  => 'session_id',
162   });
163
164 =head1 BUGS
165
166 You can't delete a session then create a new one. If this is important to you,
167 patches welcome. It is not important to me and fixing this for completeness
168 is pretty low on my list of priorities.
169
170 =head1 CAVEATS
171
172 Manual work may be involved to make better use of this.
173
174 If you are writing a stateful web service with
175 L<Catalyst::Plugin::Server::XMLRPC>, you will probably only have to deal with 
176 loading, as when saving, the ID will already be on the stash.
177
178 =head1 SEE ALSO
179
180 L<Catalyst>, L<Catalyst::Plugin::Session>, L<Catalyst::Plugin::Session::State>,
181 L<Catalyst::Plugin::Session::State::Cookie> (what you probably want).
182
183 =head1 AUTHORS
184
185 James Laver E<lt>perl -e 'printf qw/%s@%s.com cpan jameslaver/'E<gt>
186
187 =head1 CONTRIBUTORS
188
189 This module is derived from L<Catalyst::Plugin::Session::State::Cookie> code.
190
191 Thanks to anyone who wrote code for that.
192
193 =head1 COPYRIGHT
194
195 This program is free software, you can redistribute it and/or modify it
196 under the same terms as Perl itself.
197
198 =cut
199
200 1;