Fixed dumbass typo in t/lib
[dbsrgits/DBIx-Class.git] / lib / DBIx / Class / InflateColumn.pm
CommitLineData
0e5c2582 1package DBIx::Class::InflateColumn;
2
3use strict;
4use warnings;
aa562407 5
6use Carp qw/croak/;
7
75a23b3e 8use base qw/DBIx::Class::Row/;
0e5c2582 9
bcae85db 10=head1 NAME
11
12DBIx::Class::InflateColumn - Automatically create objects from column data
13
14=head1 SYNOPSIS
15
16 # In your table classes
17 __PACKAGE__->inflate_column('column_name', {
18 inflate => sub { ... },
19 deflate => sub { ... },
20 });
21
22=head1 DESCRIPTION
23
24This component translates column data into objects, i.e. "inflating"
25the column data. It also "deflates" objects into an appropriate format
26for the database.
27
28It can be used, for example, to automatically convert to and from
29L<DateTime> objects for your date and time fields.
30
31=head1 METHODS
32
33=head2 inflate_column
34
35Instruct L<DBIx::Class> to inflate the given column.
36
37In addition to the column name, you must provide C<inflate> and
38C<deflate> methods. The C<inflate> method is called when you access
39the field, while the C<deflate> method is called when the field needs
40to used by the database.
41
42For example, if you have a table C<events> with a timestamp field
43named C<insert_time>, you could inflate the column in the
44corresponding table class using something like:
45
46 __PACKAGE__->inflate_column('insert_time', {
47 inflate => sub { DateTime::Format::Pg->parse_datetime(shift); },
48 deflate => sub { DateTime::Format::Pg->format_datetime(shift); },
49 });
50
51(Replace L<DateTime::Format::Pg> with the appropriate module for your
52database, or consider L<DateTime::Format::DBI>.)
53
54In this example, calls to an event's C<insert_time> accessor return a
55L<DateTime> object. This L<DateTime> object is later "deflated" when
56used in the database layer.
57
58=cut
59
0e5c2582 60sub inflate_column {
61 my ($self, $col, $attrs) = @_;
aa562407 62 croak "No such column $col to inflate" unless $self->has_column($col);
63 croak "inflate_column needs attr hashref" unless ref $attrs eq 'HASH';
103647d5 64 $self->column_info($col)->{_inflate_info} = $attrs;
0e5c2582 65 $self->mk_group_accessors('inflated_column' => $col);
66 return 1;
67}
68
4a07648a 69sub _inflated_column {
0e5c2582 70 my ($self, $col, $value) = @_;
9f300b1b 71 return $value unless defined $value; # NULL is NULL is NULL
aa562407 72 my $info = $self->column_info($col) || croak "No column info for $col";
103647d5 73 return $value unless exists $info->{_inflate_info};
74 my $inflate = $info->{_inflate_info}{inflate};
aa562407 75 croak "No inflator for $col" unless defined $inflate;
0e5c2582 76 return $inflate->($value, $self);
77}
78
4a07648a 79sub _deflated_column {
0e5c2582 80 my ($self, $col, $value) = @_;
81 return $value unless ref $value; # If it's not an object, don't touch it
aa562407 82 my $info = $self->column_info($col) || croak "No column info for $col";
103647d5 83 return $value unless exists $info->{_inflate_info};
84 my $deflate = $info->{_inflate_info}{deflate};
aa562407 85 croak "No deflator for $col" unless defined $deflate;
0e5c2582 86 return $deflate->($value, $self);
87}
88
89sub get_inflated_column {
90 my ($self, $col) = @_;
91 $self->throw("$col is not an inflated column") unless
103647d5 92 exists $self->column_info($col)->{_inflate_info};
4a07648a 93
0e5c2582 94 return $self->{_inflated_column}{$col}
95 if exists $self->{_inflated_column}{$col};
0e5c2582 96 return $self->{_inflated_column}{$col} =
4a07648a 97 $self->_inflated_column($col, $self->get_column($col));
0e5c2582 98}
99
100sub set_inflated_column {
101 my ($self, $col, @rest) = @_;
47bd0267 102 my $ret = $self->_inflated_column_op('set', $col, @rest);
0e5c2582 103 return $ret;
104}
105
106sub store_inflated_column {
47bd0267 107 my ($self, $col, @rest) = @_;
108 my $ret = $self->_inflated_column_op('store', $col, @rest);
109 return $ret;
110}
111
112sub _inflated_column_op {
113 my ($self, $op, $col, $obj) = @_;
114 my $meth = "${op}_column";
0e5c2582 115 unless (ref $obj) {
116 delete $self->{_inflated_column}{$col};
47bd0267 117 return $self->$meth($col, $obj);
0e5c2582 118 }
4a07648a 119
120 my $deflated = $self->_deflated_column($col, $obj);
9f300b1b 121 # Do this now so we don't store if it's invalid
4a07648a 122
0e5c2582 123 $self->{_inflated_column}{$col} = $obj;
47bd0267 124 $self->$meth($col, $deflated);
0e5c2582 125 return $obj;
126}
127
128sub new {
129 my ($class, $attrs, @rest) = @_;
130 $attrs ||= {};
0e5c2582 131 foreach my $key (keys %$attrs) {
103647d5 132 if (ref $attrs->{$key}
133 && exists $class->column_info($key)->{_inflate_info}) {
484c9dda 134 $attrs->{$key} = $class->_deflated_column($key, $attrs->{$key});
0e5c2582 135 }
136 }
147dd158 137 return $class->next::method($attrs, @rest);
0e5c2582 138}
139
bcae85db 140=head1 SEE ALSO
141
142=over 4
143
144=item L<DBIx::Class::Core> - This component is loaded as part of the
145 "core" L<DBIx::Class> components; generally there is no need to
146 load it directly
147
148=back
149
150=head1 AUTHOR
151
152Matt S. Trout <mst@shadowcatsystems.co.uk>
153
154=head1 CONTRIBUTORS
155
156Daniel Westermann-Clark <danieltwc@cpan.org> (documentation)
157
158=head1 LICENSE
159
160You may distribute this code under the same terms as Perl itself.
161
162=cut
163
0e5c2582 1641;