Huge rewrite of the code: $session->get, ->set etc. do not read from
[catagits/Web-Session.git] / lib / Plack / Session / Store / File.pm
1 package Plack::Session::Store::File;
2 use strict;
3 use warnings;
4
5 our $VERSION   = '0.03';
6 our $AUTHORITY = 'cpan:STEVAN';
7
8 use Storable ();
9
10 use parent 'Plack::Session::Store';
11
12 use Plack::Util::Accessor qw[
13     dir
14     serializer
15     deserializer
16 ];
17
18 sub new {
19     my ($class, %params) = @_;
20
21     $params{'dir'} ||= $ENV{TMPDIR} || '/tmp';
22
23     die "Storage directory (" . $params{'dir'} . ") is not writeable"
24         unless -w $params{'dir'};
25
26     $params{'serializer'}   ||= sub { Storable::lock_nstore( @_ ) };
27     $params{'deserializer'} ||= sub { Storable::lock_retrieve( @_ ) };
28
29     bless { %params } => $class;
30 }
31
32 sub fetch {
33     my ($self, $session_id) = @_;
34     return $self->_deserialize( $session_id );
35 }
36
37 sub store {
38     my ($self, $session_id, $session) = @_;
39     $self->_serialize( $session_id, $session->dump );
40 }
41
42 sub cleanup {
43     my ($self, $session_id) = @_;
44     unlink $self->_get_session_file_path( $session_id );
45 }
46
47 sub _get_session_file_path {
48     my ($self, $session_id) = @_;
49     $self->dir . '/' . $session_id;
50 }
51
52 sub _serialize {
53     my ($self, $session_id, $value) = @_;
54     my $file_path = $self->_get_session_file_path( $session_id );
55     $self->serializer->( $value, $file_path );
56 }
57
58 sub _deserialize {
59     my ($self, $session_id) = @_;
60     my $file_path = $self->_get_session_file_path( $session_id );
61     $self->_serialize( $session_id, {} ) unless -f $file_path;
62     $self->deserializer->( $file_path );
63 }
64
65 1;
66
67 __END__
68
69 =pod
70
71 =head1 NAME
72
73 Plack::Session::Store::File - Basic file-based session store
74
75 =head1 SYNOPSIS
76
77   use Plack::Builder;
78   use Plack::Middleware::Session;
79   use Plack::Session::Store::File;
80
81   my $app = sub {
82       return [ 200, [ 'Content-Type' => 'text/plain' ], [ 'Hello Foo' ] ];
83   };
84
85   builder {
86       enable 'Session',
87           store => Plack::Session::Store::File->new(
88               dir => '/path/to/sessions'
89           );
90       $app;
91   };
92
93   # with custom serializer/deserializer
94
95   builder {
96       enable 'Session',
97           store => Plack::Session::Store::File->new(
98               dir          => '/path/to/sessions',
99               # YAML takes it's args the opposite order
100               serializer   => sub { YAML::DumpFile( reverse @_ ) },
101               deserializer => sub { YAML::LoadFile( @_ ) },
102           );
103       $app;
104   };
105
106 =head1 DESCRIPTION
107
108 This implements a basic file based storage for session data. By
109 default it will use L<Storable> to serialize and deserialize the
110 data, but this can be configured easily. 
111
112 This is a subclass of L<Plack::Session::Store> and implements
113 it's full interface.
114
115 =head1 METHODS
116
117 =over 4
118
119 =item B<new ( %params )>
120
121 The C<%params> can include I<dir>, I<serializer> and I<deserializer>
122 options. It will check to be sure that the I<dir> is writeable for
123 you.
124
125 =item B<dir>
126
127 This is the directory to store the session data files in, if nothing
128 is provided then "/tmp" is used.
129
130 =item B<serializer>
131
132 This is a CORE reference that implements the serialization logic.
133 The CODE ref gets two arguments, the C<$value>, which is a HASH
134 reference to be serialized, and the C<$file_path> to save it to.
135 It is not expected to return anything.
136
137 =item B<deserializer>
138
139 This is a CORE reference that implements the deserialization logic.
140 The CODE ref gets one argument, the C<$file_path> to load the data
141 from. It is expected to return a HASH reference.
142
143 =back
144
145 =head1 BUGS
146
147 All complex software has bugs lurking in it, and this module is no
148 exception. If you find a bug please either email me, or add the bug
149 to cpan-RT.
150
151 =head1 AUTHOR
152
153 Stevan Little E<lt>stevan.little@iinteractive.comE<gt>
154
155 =head1 COPYRIGHT AND LICENSE
156
157 Copyright 2009, 2010 Infinity Interactive, Inc.
158
159 L<http://www.iinteractive.com>
160
161 This library is free software; you can redistribute it and/or modify
162 it under the same terms as Perl itself.
163
164 =cut
165