File Coverage

blib/lib/DateTime/Format/SQLite.pm
Criterion Covered Total %
statement 34 34 100.0
branch n/a
condition 4 4 100.0
subroutine 9 9 100.0
pod 4 4 100.0
total 51 51 100.0


line stmt bran cond sub pod time code
1             # $Id: SQLite.pm 4363 2009-12-10 16:47:25Z cfaerber $
2             #
3             package DateTime::Format::SQLite;
4              
5 4     4   690634 use strict;
  4         12  
  4         183  
6 4     4   20 use vars qw ($VERSION);
  4         7  
  4         176  
7 4     4   32 use warnings;
  4         9  
  4         2673  
8              
9             our $VERSION = '0.11';
10             $VERSION = eval { $VERSION };
11              
12             # "days since noon in Greenwich on November 24, 4714 B.C."
13             my %jd0 = ( 'year' => -4713, 'month' => 11, 'day' => 24, 'hour' => 12, time_zone => 'UTC' );
14              
15             use DateTime::Format::Builder
16             ( parsers =>
17             { parse_datetime =>
18             [
19             # format 1
20             #
21             { params => [ qw( year month day ) ],
22             regex => qr/^(-?\d+)-(\d+)-(\d+)$/,
23             extra => { time_zone => 'UTC' },
24             },
25              
26             # formats 2 and 5
27             #
28             { params => [ qw( year month day hour minute ) ],
29             regex => qr/^(-?\d+)-(\d{1,2})-(\d{1,2})[Tt ](\d{1,2}):(\d{1,2})$/,
30             extra => { time_zone => 'UTC' },
31             },
32              
33             # formats 3, 4, 6 and 7
34             #
35             { params => [ qw( year month day hour minute second nanosecond ) ],
36             regex => qr/^(-?\d+)-(\d{1,2})-(\d{1,2})[Tt ](\d{1,2}):(\d{1,2}):(\d{1,2})(\.\d*)?$/,
37             extra => { time_zone => 'UTC' },
38             postprocess => \&_fix_nanoseconds,
39             },
40              
41             # format 8
42             #
43             { params => [ qw( hour minute ) ],
44             regex => qr/^(\d{1,2}):(\d{1,2})$/,
45             extra => { time_zone => 'UTC', 'year' => 2000, },
46             },
47              
48             # format 9, 10
49             #
50             { params => [ qw( hour minute second nanosecond ) ],
51             regex => qr/^(\d{1,2}):(\d{1,2}):(\d{1,2})(\.\d*)?$/,
52             extra => { time_zone => 'UTC', 'year' => 2000, },
53             postprocess => \&_fix_nanoseconds,
54             },
55              
56             # format 11
57             #
58             { params => [ qw ( dummy ) ],
59             regex => qr/^([Nn][Oo][Ww])$/,
60 1         908 constructor => sub { return DateTime->now },
61             },
62              
63             # format 12
64             #
65             { params => [ qw( jd secs ) ],
66             regex => qr/^(\d+(\.\d*)?)$/,
67 4   100     4197 constructor => sub { shift; my %p=(@_); return DateTime->new(%jd0)->add(
  4         12  
  4         26  
68             'days' => int($p{'jd'}), 'seconds' => ($p{'secs'} || 0) * (3600 * 24) ); },
69             },
70 4         437 ]
71             },
72 4     4   10547 );
  4         559651  
73              
74             *parse_date = \&parse_datetime;
75             *parse_time = \&parse_datetime;
76             *parse_julianday = \&parse_datetime;
77              
78             sub format_date
79             {
80 3     3 1 4373 my ( $self, $dt ) = @_;
81              
82 3         13 $dt = $dt->clone;
83 3         44 $dt->set_time_zone('UTC');
84              
85 3         516 return $dt->ymd('-');
86             }
87              
88             sub format_time
89             {
90 2     2 1 2683 my ( $self, $dt ) = @_;
91              
92 2         8 $dt = $dt->clone;
93 2         27 $dt->set_time_zone('UTC');
94              
95 2         278 return $dt->hms(':');
96             }
97              
98             sub format_datetime
99             {
100 3     3 1 12238 my ( $self, $dt ) = @_;
101              
102 3         15 $dt = $dt->clone;
103 3         47 $dt->set_time_zone('UTC');
104              
105 3         491 return join ' ', $dt->ymd('-'), $dt->hms(':');
106             }
107              
108              
109             sub format_julianday
110             {
111 2     2 1 2392 my ( $self, $dt ) = @_;
112              
113 2         8 return $dt->jd;
114             }
115              
116             sub _fix_nanoseconds
117             {
118 21     21   26019 my %args = @_;
119 21   100     96 $args{'parsed'}->{'nanosecond'} ||= 0;
120 21         48 $args{'parsed'}->{'nanosecond'} *= 1000 * 1000 * 1000;
121 21         73 1;
122             }
123              
124             1;
125              
126             __END__
127              
128             =encoding utf8
129              
130             =head1 NAME
131              
132             DateTime::Format::SQLite - Parse and format SQLite dates and times
133              
134             =head1 SYNOPSIS
135              
136             use DateTime::Format::SQLite;
137              
138             my $dt = DateTime::Format::SQLite->parse_datetime( '2003-01-16 23:12:01' );
139              
140             # 2003-01-16 23:12:01
141             DateTime::Format::SQLite->format_datetime($dt);
142              
143             =head1 DESCRIPTION
144              
145             This module understands the formats used by SQLite for its
146             C<date>, C<datetime> and C<time> functions. It can be used to
147             parse these formats in order to create L<DateTime> objects, and it
148             can take a DateTime object and produce a timestring accepted by
149             SQLite.
150              
151             B<NOTE:> SQLite does not have real date/time types but stores
152             everything as strings. This module deals with the date/time
153             strings as understood/returned by SQLite's C<date>, C<time>,
154             C<datetime>, C<julianday> and C<strftime> SQL functions.
155             You will usually want to store your dates in one of these formats.
156              
157             =head1 METHODS
158              
159             This class offers the methods listed below. All of the parsing
160             methods set the returned DateTime object's time zone to the B<UTC>
161             zone because SQLite does always uses UTC for date calculations.
162             This means your dates may seem to be one day off if you convert
163             them to local time.
164              
165             =over 4
166              
167             =item * parse_datetime($string)
168              
169             Given a C<$string> representing a date, this method will return a new
170             C<DateTime> object.
171              
172             The C<$string> may be in any of the formats understood by SQLite's
173             C<date>, C<time>, C<datetime>, C<julianday> and C<strftime> SQL
174             functions or it may be in the format returned by these functions
175             (except C<strftime>, of course).
176              
177             The time zone for this object will always be in UTC because SQLite
178             assumes UTC for all date calculations.
179              
180             If C<$string> contains no date, the parser assumes 2000-01-01
181             (just like SQLite).
182              
183             If given an improperly formatted string, this method may die.
184              
185             =item * parse_date($string)
186              
187             =item * parse_time($string)
188              
189             =item * parse_julianday($string)
190              
191             These are aliases for C<parse_datetime>, for symmetry with
192             C<format_I<*>> functions.
193              
194             =item * format_date($datetime)
195              
196             Given a C<DateTime> object, this methods returnes a string in the
197             format YYYY-MM-DD, i.e. in the same format SQLite's C<date>
198             function uses.
199              
200             =item * format_time($datetime)
201              
202             Given a C<DateTime> object, this methods returnes a string in the
203             format HH:MM:SS, i.e. in the same format SQLite's C<time>
204             function uses.
205              
206             =item * format_datetime($datetime)
207              
208             Given a C<DateTime> object, this methods returnes a string in the
209             format YYYY-MM-DD HH:MM:SS, i.e. in the same format SQLite's C<datetime>
210             function uses.
211              
212             =item * format_julianday($datetime)
213              
214             Given a C<DateTime> object, this methods returnes a string in the
215             format DDDDDDDDDD, i.e. in the same format SQLite's C<julianday>
216             function uses.
217              
218             =back
219              
220             =head1 AUTHOR
221              
222             Claus Färber <CFAERBER@cpan.org>
223              
224             based on C<DateTime::Format::MySQL> by David Rolsky.
225              
226             =head1
227              
228             Copyright © 2008 Claus Färber.
229              
230             Copyright © 2003 David Rolsky.
231              
232             This program is free software; you can redistribute it and/or
233             modify it under the same terms as Perl itself.
234              
235             The full text of the license can be found in the LICENSE file
236             included with this module.
237              
238             =head1 SEE ALSO
239              
240             http://datetime.perl.org/
241              
242             http://www.sqlite.org/lang_datefunc.html
243              
244             =cut