Another overhaul of transaction/savepoint handling
[dbsrgits/DBIx-Class.git] / lib / DBIx / Class.pm
CommitLineData
ea2e61bf 1package DBIx::Class;
2
5d283305 3use strict;
4use warnings;
5
87bf71d5 6BEGIN {
e0b2dc74 7 package DBIx::Class::_ENV_;
8
87bf71d5 9 if ($] < 5.009_005) {
10 require MRO::Compat;
e0b2dc74 11 *OLD_MRO = sub () { 1 };
87bf71d5 12 }
13 else {
14 require mro;
e0b2dc74 15 *OLD_MRO = sub () { 0 };
87bf71d5 16 }
4bea1fe7 17
18 # ::Runmode would only be loaded by DBICTest, which in turn implies t/
e0b2dc74 19 *DBICTEST = eval { DBICTest::RunMode->is_author }
4bea1fe7 20 ? sub () { 1 }
21 : sub () { 0 }
22 ;
e0b2dc74 23
24 # During 5.13 dev cycle HELEMs started to leak on copy
25 *PEEPEENESS = (defined $ENV{DBICTEST_ALL_LEAKS}
26 # request for all tests would force "non-leaky" illusion and vice-versa
27 ? ! $ENV{DBICTEST_ALL_LEAKS}
28
29 # otherwise confess that this perl is busted ONLY on smokers
30 : do {
31 if (eval { DBICTest::RunMode->is_smoker }) {
32
33 # leaky 5.13.6 (fixed in blead/cefd5c7c)
34 if ($] == '5.013006') { 1 }
35
36 # not sure why this one leaks, but disable anyway - ANDK seems to make it weep
37 elsif ($] == '5.013005') { 1 }
38
39 else { 0 }
40 }
41 else { 0 }
42 }
43 ) ? sub () { 1 } : sub () { 0 };
87bf71d5 44}
45
d38cd95c 46use mro 'c3';
329d7385 47
2527233b 48use DBIx::Class::Optional::Dependencies;
49
5d283305 50use vars qw($VERSION);
db29433c 51use base qw/DBIx::Class::Componentised DBIx::Class::AccessorGroup/;
11736b4c 52use DBIx::Class::StartupCheck;
3e110410 53
70c28808 54__PACKAGE__->mk_group_accessors(inherited => '_skip_namespace_frames');
55__PACKAGE__->_skip_namespace_frames('^DBIx::Class|^SQL::Abstract|^Try::Tiny');
56
ade0fe3b 57sub mk_classdata {
77d518d1 58 shift->mk_classaccessor(@_);
59}
60
61sub mk_classaccessor {
62 my $self = shift;
ade0fe3b 63 $self->mk_group_accessors('inherited', $_[0]);
77d518d1 64 $self->set_inherited(@_) if @_ > 1;
3e110410 65}
3c0068c1 66
7411204b 67sub component_base_class { 'DBIx::Class' }
227d4dee 68
95da6f35 69# Always remember to do all digits for the version even if they're 0
70# i.e. first release of 0.XX *must* be 0.XX000. This avoids fBSD ports
71# brain damage and presumably various other packaging systems too
86b9a583 72$VERSION = '0.08190';
748ab0dc 73
033955f9 74$VERSION = eval $VERSION if $VERSION =~ /_/; # numify for warning-free dev releases
b8777a0d 75
f0750722 76sub MODIFY_CODE_ATTRIBUTES {
b5d2c57f 77 my ($class,$code,@attrs) = @_;
78 $class->mk_classdata('__attr_cache' => {})
79 unless $class->can('__attr_cache');
80 $class->__attr_cache->{$code} = [@attrs];
81 return ();
f0750722 82}
83
da95b45f 84sub _attr_cache {
b5d2c57f 85 my $self = shift;
86 my $cache = $self->can('__attr_cache') ? $self->__attr_cache : {};
9780718f 87
88 return {
89 %$cache,
90 %{ $self->maybe::next::method || {} },
20674fcd 91 };
da95b45f 92}
93
ea2e61bf 941;
34d52be2 95
75d07914 96=head1 NAME
34d52be2 97
7e4b2f59 98DBIx::Class - Extensible and flexible object <-> relational mapper.
34d52be2 99
3b1c2bbd 100=head1 GETTING HELP/SUPPORT
101
102The community can be found via:
103
a06e1181 104=over
3b1c2bbd 105
054235c6 106=item * Web Site: L<http://www.dbix-class.org/>
107
c6fdaf2a 108=item * IRC: irc.perl.org#dbix-class
109
110=for html
e3194e31 111<a href="http://chat.mibbit.com/#dbix-class@irc.perl.org">(click for instant chatroom login)</a>
3b1c2bbd 112
a06e1181 113=item * Mailing list: L<http://lists.scsys.co.uk/mailman/listinfo/dbix-class>
3b1c2bbd 114
a06e1181 115=item * RT Bug Tracker: L<https://rt.cpan.org/Dist/Display.html?Queue=DBIx-Class>
116
aeb669b8 117=item * gitweb: L<http://git.shadowcat.co.uk/gitweb/gitweb.cgi?p=dbsrgits/DBIx-Class.git>
a06e1181 118
aeb669b8 119=item * git: L<git://git.shadowcat.co.uk/dbsrgits/DBIx-Class.git>
a06e1181 120
43517a60 121=item * twitter L<http://www.twitter.com/dbix_class>
122
a06e1181 123=back
3b1c2bbd 124
34d52be2 125=head1 SYNOPSIS
126
03460bef 127Create a schema class called MyApp/Schema.pm:
34d52be2 128
03460bef 129 package MyApp::Schema;
a0638a7b 130 use base qw/DBIx::Class::Schema/;
34d52be2 131
f0bb26f3 132 __PACKAGE__->load_namespaces();
daec44b8 133
a0638a7b 134 1;
daec44b8 135
30e1753a 136Create a result class to represent artists, who have many CDs, in
03460bef 137MyApp/Schema/Result/Artist.pm:
daec44b8 138
30e1753a 139See L<DBIx::Class::ResultSource> for docs on defining result classes.
140
03460bef 141 package MyApp::Schema::Result::Artist;
d88ecca6 142 use base qw/DBIx::Class::Core/;
daec44b8 143
a0638a7b 144 __PACKAGE__->table('artist');
145 __PACKAGE__->add_columns(qw/ artistid name /);
146 __PACKAGE__->set_primary_key('artistid');
03460bef 147 __PACKAGE__->has_many(cds => 'MyApp::Schema::Result::CD');
daec44b8 148
a0638a7b 149 1;
daec44b8 150
30e1753a 151A result class to represent a CD, which belongs to an artist, in
03460bef 152MyApp/Schema/Result/CD.pm:
39fe0e65 153
03460bef 154 package MyApp::Schema::Result::CD;
d88ecca6 155 use base qw/DBIx::Class::Core/;
39fe0e65 156
d88ecca6 157 __PACKAGE__->load_components(qw/InflateColumn::DateTime/);
a0638a7b 158 __PACKAGE__->table('cd');
bd077b47 159 __PACKAGE__->add_columns(qw/ cdid artistid title year /);
a0638a7b 160 __PACKAGE__->set_primary_key('cdid');
03460bef 161 __PACKAGE__->belongs_to(artist => 'MyApp::Schema::Result::Artist', 'artistid');
39fe0e65 162
a0638a7b 163 1;
39fe0e65 164
a0638a7b 165Then you can use these classes in your application's code:
39fe0e65 166
a0638a7b 167 # Connect to your database.
03460bef 168 use MyApp::Schema;
169 my $schema = MyApp::Schema->connect($dbi_dsn, $user, $pass, \%dbi_params);
a0638a7b 170
171 # Query for all artists and put them in an array,
172 # or retrieve them as a result set object.
30e1753a 173 # $schema->resultset returns a DBIx::Class::ResultSet
2053ab2a 174 my @all_artists = $schema->resultset('Artist')->all;
175 my $all_artists_rs = $schema->resultset('Artist');
126042ee 176
30e1753a 177 # Output all artists names
4e8ffded 178 # $artist here is a DBIx::Class::Row, which has accessors
16ccb4fe 179 # for all its columns. Rows are also subclasses of your Result class.
85067746 180 foreach $artist (@all_artists) {
30e1753a 181 print $artist->name, "\n";
182 }
183
a0638a7b 184 # Create a result set to search for artists.
86beca1d 185 # This does not query the DB.
2053ab2a 186 my $johns_rs = $schema->resultset('Artist')->search(
6576ef54 187 # Build your WHERE using an SQL::Abstract structure:
2053ab2a 188 { name => { like => 'John%' } }
a0638a7b 189 );
39fe0e65 190
2053ab2a 191 # Execute a joined query to get the cds.
a0638a7b 192 my @all_john_cds = $johns_rs->search_related('cds')->all;
448c8424 193
f0bb26f3 194 # Fetch the next available row.
a0638a7b 195 my $first_john = $johns_rs->next;
448c8424 196
2053ab2a 197 # Specify ORDER BY on the query.
a0638a7b 198 my $first_john_cds_by_title_rs = $first_john->cds(
199 undef,
200 { order_by => 'title' }
201 );
448c8424 202
bd077b47 203 # Create a result set that will fetch the artist data
2053ab2a 204 # at the same time as it fetches CDs, using only one query.
884559b1 205 my $millennium_cds_rs = $schema->resultset('CD')->search(
a0638a7b 206 { year => 2000 },
207 { prefetch => 'artist' }
208 );
448c8424 209
880a1a0c 210 my $cd = $millennium_cds_rs->next; # SELECT ... FROM cds JOIN artists ...
bd077b47 211 my $cd_artist_name = $cd->artist->name; # Already has the data so no 2nd query
076652e8 212
264f1571 213 # new() makes a DBIx::Class::Row object but doesnt insert it into the DB.
214 # create() is the same as new() then insert().
884559b1 215 my $new_cd = $schema->resultset('CD')->new({ title => 'Spoon' });
f183eccd 216 $new_cd->artist($cd->artist);
f183eccd 217 $new_cd->insert; # Auto-increment primary key filled in after INSERT
f183eccd 218 $new_cd->title('Fork');
219
884559b1 220 $schema->txn_do(sub { $new_cd->update }); # Runs the update in a transaction
f183eccd 221
bd077b47 222 # change the year of all the millennium CDs at once
223 $millennium_cds_rs->update({ year => 2002 });
f183eccd 224
225=head1 DESCRIPTION
226
227This is an SQL to OO mapper with an object API inspired by L<Class::DBI>
bd077b47 228(with a compatibility layer as a springboard for porting) and a resultset API
f183eccd 229that allows abstract encapsulation of database operations. It aims to make
230representing queries in your code as perl-ish as possible while still
a0638a7b 231providing access to as many of the capabilities of the database as possible,
f183eccd 232including retrieving related records from multiple tables in a single query,
bd077b47 233JOIN, LEFT JOIN, COUNT, DISTINCT, GROUP BY, ORDER BY and HAVING support.
f183eccd 234
235DBIx::Class can handle multi-column primary and foreign keys, complex
236queries and database-level paging, and does its best to only query the
75d07914 237database in order to return something you've directly asked for. If a
238resultset is used as an iterator it only fetches rows off the statement
239handle as requested in order to minimise memory usage. It has auto-increment
2053ab2a 240support for SQLite, MySQL, PostgreSQL, Oracle, SQL Server and DB2 and is
241known to be used in production on at least the first four, and is fork-
ec6415a9 242and thread-safe out of the box (although
243L<your DBD may not be|DBI/Threads_and_Thread_Safety>).
f183eccd 244
dfccde48 245This project is still under rapid development, so large new features may be
246marked EXPERIMENTAL - such APIs are still usable but may have edge bugs.
247Failing test cases are *always* welcome and point releases are put out rapidly
248as bugs are found and fixed.
249
250We do our best to maintain full backwards compatibility for published
251APIs, since DBIx::Class is used in production in many organisations,
252and even backwards incompatible changes to non-published APIs will be fixed
253if they're reported and doing so doesn't cost the codebase anything.
254
264f1571 255The test suite is quite substantial, and several developer releases
256are generally made to CPAN before the branch for the next release is
257merged back to trunk for a major release.
f183eccd 258
f183eccd 259=head1 WHERE TO GO NEXT
260
2ca930b4 261L<DBIx::Class::Manual::DocMap> lists each task you might want help on, and
262the modules where you will find documentation.
076652e8 263
3942ab4d 264=head1 AUTHOR
34d52be2 265
266bdcc3 266mst: Matt S. Trout <mst@shadowcatsystems.co.uk>
34d52be2 267
dfccde48 268(I mostly consider myself "project founder" these days but the AUTHOR heading
269is traditional :)
270
3942ab4d 271=head1 CONTRIBUTORS
272
907ed671 273abraxxa: Alexander Hartmaier <abraxxa@cpan.org>
84e3c114 274
fd4b0742 275acca: Alexander Kuznetsov <acca@cpan.org>
276
6d84db2c 277aherzog: Adam Herzog <adam@herzogdesigns.com>
278
daeb1865 279Alexander Keusch <cpan@keusch.at>
280
630ba6e5 281alnewkirk: Al Newkirk <we@ana.im>
282
6ebf5cbb 283amiri: Amiri Barksdale <amiri@metalabel.com>
284
b703fec7 285amoore: Andrew Moore <amoore@cpan.org>
286
266bdcc3 287andyg: Andy Grundman <andy@hybridized.org>
3942ab4d 288
266bdcc3 289ank: Andres Kievsky
3942ab4d 290
59ac6523 291arc: Aaron Crane <arc@cpan.org>
292
624764ae 293arcanez: Justin Hunter <justin.d.hunter@gmail.com>
294
ce4c07df 295ash: Ash Berlin <ash@cpan.org>
296
3d5bd2af 297bert: Norbert Csongradi <bert@cpan.org>
298
967a4c40 299blblack: Brandon L. Black <blblack@gmail.com>
3942ab4d 300
62eb8fe8 301bluefeet: Aran Deltac <bluefeet@cpan.org>
302
d6170b26 303bphillips: Brian Phillips <bphillips@cpan.org>
304
f856fe01 305boghead: Bryan Beeley <cpan@beeley.org>
306
bcb8f3ed 307bricas: Brian Cassidy <bricas@cpan.org>
308
3d7e3e05 309brunov: Bruno Vecchi <vecchi.b@gmail.com>
310
281719d2 311caelum: Rafael Kitover <rkitover@cpan.org>
312
f5f2af8f 313caldrin: Maik Hentsche <maik.hentsche@amd.com>
314
d3b0e369 315castaway: Jess Robinson
3942ab4d 316
266bdcc3 317claco: Christopher H. Laco
ccb9c9b1 318
266bdcc3 319clkao: CL Kao
3942ab4d 320
e21dfd6a 321da5id: David Jack Olrik <djo@cpan.org>
18360aed 322
13de943d 323debolaz: Anders Nor Berle <berle@cpan.org>
324
d1f542db 325dew: Dan Thomas <dan@godders.org>
326
266bdcc3 327dkubb: Dan Kubb <dan.kubb-cpan@onautopilot.com>
ccb9c9b1 328
9382ad07 329dnm: Justin Wheeler <jwheeler@datademons.com>
330
0818c9a7 331dpetrov: Dimitar Petrov <mitakaa@gmail.com>
332
266bdcc3 333dwc: Daniel Westermann-Clark <danieltwc@cpan.org>
4685e006 334
5cffe785 335dyfrgi: Michael Leuchtenburg <michael@slashhome.org>
8fe164b9 336
0ffada27 337freetime: Bill Moseley <moseley@hank.org>
338
ade0fe3b 339frew: Arthur Axel "fREW" Schmidt <frioux@gmail.com>
340
b4987ed0 341goraxe: Gordon Irving <goraxe@cpan.org>
342
d3b0e369 343gphat: Cory G Watson <gphat@cpan.org>
ad3d2d7c 344
61f031bf 345Grant Street Group L<http://www.grantstreet.com/>
346
e758ffe6 347groditi: Guillermo Roditi <groditi@cpan.org>
348
6dad89f5 349Haarg: Graham Knop <haarg@haarg.org>
350
157ce0cf 351hobbs: Andrew Rodland <arodland@cpan.org>
352
5d779578 353ilmari: Dagfinn Ilmari MannsE<aring>ker <ilmari@ilmari.org>
354
0ac0af6c 355initself: Mike Baas <mike@initselftech.com>
356
f165eda8 357jawnsy: Jonathan Yu <jawnsy@cpan.org>
358
bee21976 359jasonmay: Jason May <jason.a.may@gmail.com>
360
d3b0e369 361jesper: Jesper Krogh
5fb0c64c 362
4a743a00 363jgoulah: John Goulah <jgoulah@cpan.org>
364
102a2984 365jguenther: Justin Guenther <jguenther@cpan.org>
d7c4c15c 366
a14a46e2 367jhannah: Jay Hannah <jay@jays.net>
368
8b93a938 369jnapiorkowski: John Napiorkowski <jjn1056@yahoo.com>
370
11736b4c 371jon: Jon Schutz <jjschutz@cpan.org>
372
1aec4bac 373jshirley: J. Shirley <jshirley@gmail.com>
374
41519379 375kaare: Kaare Rasmussen
376
d3b0e369 377konobi: Scott McWhirter
535fc2ee 378
4e0a89e4 379littlesavage: Alexey Illarionov <littlesavage@orionet.ru>
380
4367679a 381lukes: Luke Saunders <luke.saunders@gmail.com>
382
709ea492 383marcus: Marcus Ramberg <mramberg@cpan.org>
384
114780ee 385mattlaw: Matt Lawrence
386
45bffdf0 387mattp: Matt Phillips <mattp@cpan.org>
388
58755bba 389michaelr: Michael Reddick <michael.reddick@gmail.com>
390
91d0c99f 391milki: Jonathan Chu <milki@rescomp.berkeley.edu>
392
77e7e47d 393ned: Neil de Carteret
394
266bdcc3 395nigel: Nigel Metheringham <nigelm@cpan.org>
6565b410 396
d3b0e369 397ningu: David Kamholz <dkamholz@cpan.org>
398
66cf3a84 399Nniuq: Ron "Quinn" Straight" <quinnfazigu@gmail.org>
400
20b4c148 401norbi: Norbert Buchmuller <norbi@nix.hu>
402
48580715 403nuba: Nuba Princigalli <nuba@cpan.org>
404
d3b0e369 405Numa: Dan Sully <daniel@cpan.org>
406
dc571b76 407ovid: Curtis "Ovid" Poe <ovid@cpan.org>
408
bf356c54 409oyse: Øystein Torget <oystein.torget@dnv.com>
410
266bdcc3 411paulm: Paul Makepeace
4763f4b7 412
d3b0e369 413penguin: K J Cheetham
414
8cfef6f5 415perigrin: Chris Prather <chris@prather.org>
416
14899528 417peter: Peter Collingbourne <peter@pcc.me.uk>
caac1708 418
266bdcc3 419phaylon: Robert Sedlacek <phaylon@dunkelheit.at>
a53b95f1 420
56fadd8f 421plu: Johannes Plunien <plu@cpan.org>
422
0c1a4a15 423Possum: Daniel LeWarne <possum@cpan.org>
424
d3b0e369 425quicksilver: Jules Bean
022e0893 426
4ed01b34 427rafl: Florian Ragwitz <rafl@debian.org>
428
0c1a4a15 429rainboxx: Matthias Dietrich <perl@rb.ly>
430
868a7b26 431rbo: Robert Bohne <rbo@cpan.org>
432
7ff0dace 433rbuels: Robert Buels <rmb32@cornell.edu>
434
0da8b7da 435rdj: Ryan D Johnson <ryan@innerfence.com>
436
66b1e361 437ribasushi: Peter Rabbitson <ribasushi@cpan.org>
d76e282a 438
b487918c 439rjbs: Ricardo Signes <rjbs@cpan.org>
440
6ffb5be5 441robkinyon: Rob Kinyon <rkinyon@cpan.org>
442
726c8f65 443Robert Olson <bob@rdolson.org>
444
e4c9f3f0 445Roman: Roman Filippov <romanf@cpan.org>
446
dc81dba3 447Sadrak: Felix Antonius Wilhelm Ostmann <sadrak@cpan.org>
448
d3b0e369 449sc_: Just Another Perl Hacker
ba606e58 450
266bdcc3 451scotty: Scotty Allen <scotty@scottyallen.com>
181a28f4 452
1c133e22 453semifor: Marc Mims <marc@questright.com>
454
20b4c148 455solomon: Jared Johnson <jaredj@nmgi.com>
456
88f937fb 457spb: Stephen Bennett <stephen@freenode.net>
458
59187a3b 459Squeeks <squeek@cpan.org>
460
637ca936 461sszabo: Stephan Szabo <sszabo@bigpanda.com>
462
a9e8284f 463talexb: Alex Beamish <talexb@gmail.com>
464
7bf0d0d6 465tamias: Ronald J Kimball <rjk@tamias.net>
f92a9d79 466
386c2272 467teejay : Aaron Trevena <teejay@cpan.org>
468
84e3c114 469Todd Lipcon
e063fe2c 470
6eb6264e 471Tom Hukins
472
2e4b6d78 473tonvoon: Ton Voon <tonvoon@cpan.org>
474
d15e3fc5 475triode: Pete Gamache <gamache@cpan.org>
476
d3b0e369 477typester: Daisuke Murase <typester@cpan.org>
c0e7b4e5 478
4740bdb7 479victori: Victor Igumnov <victori@cpan.org>
480
d3b0e369 481wdh: Will Hawes
4c248161 482
00c03ced 483willert: Sebastian Willert <willert@cpan.org>
484
66d2a14e 485wreis: Wallace Reis <wreis@cpan.org>
486
d52d4d6e 487yrlnry: Mark Jason Dominus <mjd@plover.com>
488
d3b0e369 489zamolxes: Bogdan Lucaciu <bogdan@wiz.ro>
78060df8 490
b38e10bd 491=head1 COPYRIGHT
492
48580715 493Copyright (c) 2005 - 2010 the DBIx::Class L</AUTHOR> and L</CONTRIBUTORS>
b38e10bd 494as listed above.
495
96154ef7 496=head1 LICENSE
497
498This library is free software and may be distributed under the same terms
499as perl itself.
500
34d52be2 501=cut