release 0.07030
[dbsrgits/DBIx-Class-Schema-Loader.git] / lib / DBIx / Class / Schema / Loader.pm
1 package DBIx::Class::Schema::Loader;
2
3 use strict;
4 use warnings;
5 use base qw/DBIx::Class::Schema Class::Accessor::Grouped/;
6 use MRO::Compat;
7 use mro 'c3';
8 use Carp::Clan qw/^DBIx::Class/;
9 use Scalar::Util 'weaken';
10 use Sub::Name 'subname';
11 use DBIx::Class::Schema::Loader::Utils 'array_eq';
12 use Try::Tiny;
13 use Hash::Merge 'merge';
14 use namespace::clean;
15
16 # Always remember to do all digits for the version even if they're 0
17 # i.e. first release of 0.XX *must* be 0.XX000. This avoids fBSD ports
18 # brain damage and presumably various other packaging systems too
19 our $VERSION = '0.07030';
20
21 __PACKAGE__->mk_group_accessors('inherited', qw/
22                                 _loader_args
23                                 dump_to_dir
24                                 _loader_invoked
25                                 _loader
26                                 loader_class
27                                 naming
28                                 use_namespaces
29 /);
30 __PACKAGE__->_loader_args({});
31
32 =head1 NAME
33
34 DBIx::Class::Schema::Loader - Create a DBIx::Class::Schema based on a database
35
36 =head1 SYNOPSIS
37
38   ### use this module to generate a set of class files
39
40   # in a script
41   use DBIx::Class::Schema::Loader qw/ make_schema_at /;
42   make_schema_at(
43       'My::Schema',
44       { debug => 1,
45         dump_directory => './lib',
46       },
47       [ 'dbi:Pg:dbname="foo"', 'myuser', 'mypassword',
48          { loader_class => 'MyLoader' } # optionally
49       ],
50   );
51
52   # from the command line or a shell script with dbicdump (distributed
53   # with this module).  Do `perldoc dbicdump` for usage.
54   dbicdump -o dump_directory=./lib \
55            -o components='["InflateColumn::DateTime"]' \
56            -o debug=1 \
57            My::Schema \
58            'dbi:Pg:dbname=foo' \
59            myuser \
60            mypassword
61
62   ### or generate and load classes at runtime
63   # note: this technique is not recommended
64   # for use in production code
65
66   package My::Schema;
67   use base qw/DBIx::Class::Schema::Loader/;
68
69   __PACKAGE__->loader_options(
70       constraint              => '^foo.*',
71       # debug                 => 1,
72   );
73
74   #### in application code elsewhere:
75
76   use My::Schema;
77
78   my $schema1 = My::Schema->connect( $dsn, $user, $password, $attrs);
79   # -or-
80   my $schema1 = "My::Schema"; $schema1->connection(as above);
81
82 =head1 DESCRIPTION 
83
84 DBIx::Class::Schema::Loader automates the definition of a
85 L<DBIx::Class::Schema> by scanning database table definitions and setting up
86 the columns, primary keys, unique constraints and relationships.
87
88 See L<dbicdump> for the C<dbicdump> utility.
89
90 DBIx::Class::Schema::Loader currently supports only the DBI storage type. It
91 has explicit support for L<DBD::Pg>, L<DBD::mysql>, L<DBD::DB2>,
92 L<DBD::Firebird>, L<DBD::InterBase>, L<DBD::Informix>, L<DBD::SQLAnywhere>,
93 L<DBD::SQLite>, L<DBD::Sybase> (for Sybase ASE and MSSSQL), L<DBD::ODBC> (for
94 MSSQL, MSAccess, Firebird and SQL Anywhere) L<DBD::ADO> (for MSSQL and
95 MSAccess) and L<DBD::Oracle>.  Other DBI drivers may function to a greater or
96 lesser degree with this loader, depending on how much of the DBI spec they
97 implement, and how standard their implementation is.
98
99 Patches to make other DBDs work correctly welcome.
100
101 See L<DBIx::Class::Schema::Loader::DBI::Writing> for notes on writing
102 your own vendor-specific subclass for an unsupported DBD driver.
103
104 This module requires L<DBIx::Class> 0.08127 or later, and obsoletes the older
105 L<DBIx::Class::Loader>.
106
107 See L<DBIx::Class::Schema::Loader::Base> for available options.
108
109 =head1 METHODS
110
111 =head2 loader
112
113 The loader object, as class data on your Schema. For methods available see
114 L<DBIx::Class::Schema::Loader::Base> and L<DBIx::Class::Schema::Loader::DBI>.
115
116 =cut
117
118 sub loader {
119     my $self = shift;
120     $self->_loader(@_);
121 }
122
123 =head2 loader_class
124
125 =over 4
126
127 =item Argument: $loader_class
128
129 =back
130
131 Set the loader class to be instantiated when L</connection> is called.
132 If the classname starts with "::", "DBIx::Class::Schema::Loader" is
133 prepended. Defaults to L<DBIx::Class::Schema/storage_type> (which must
134 start with "::" when using L<DBIx::Class::Schema::Loader>).
135
136 This is mostly useful for subclassing existing loaders or in conjunction
137 with L</dump_to_dir>.
138
139 =head2 loader_options
140
141 =over 4
142
143 =item Argument: \%loader_options
144
145 =back
146
147 Example in Synopsis above demonstrates a few common arguments.  For
148 detailed information on all of the arguments, most of which are
149 only useful in fairly complex scenarios, see the
150 L<DBIx::Class::Schema::Loader::Base> documentation.
151
152 If you intend to use C<loader_options>, you must call
153 C<loader_options> before any connection is made, or embed the
154 C<loader_options> in the connection information itself as shown
155 below.  Setting C<loader_options> after the connection has
156 already been made is useless.
157
158 =cut
159
160 sub loader_options {
161     my $self = shift;
162
163     my %args = (ref $_[0] eq 'HASH') ? %{$_[0]} : @_;
164     $self->_loader_args(\%args);
165
166     $self;
167 }
168
169 sub _invoke_loader {
170     my $self = shift;
171     my $class = ref $self || $self;
172
173     my $args = $self->_loader_args;
174
175     # temporarily copy $self's storage to class
176     my $class_storage = $class->storage;
177     if (ref $self) {
178         $class->storage($self->storage);
179         $class->storage->set_schema($class);
180     }
181
182     $args->{schema} = $class;
183     $args->{schema_class} = $class;
184     $args->{dump_directory} ||= $self->dump_to_dir;
185     $args->{naming} = $self->naming if $self->naming;
186     $args->{use_namespaces} = $self->use_namespaces if defined $self->use_namespaces;
187
188     # XXX this only works for relative storage_type, like ::DBI ...
189     my $loader_class = $self->loader_class;
190     if ($loader_class) {
191         $loader_class = "DBIx::Class::Schema::Loader${loader_class}" if $loader_class =~ /^::/;
192         $args->{loader_class} = $loader_class;
193     };
194
195     my $impl = $loader_class || "DBIx::Class::Schema::Loader" . $self->storage_type;
196     try {
197         $self->ensure_class_loaded($impl)
198     }
199     catch {
200         croak qq/Could not load loader_class "$impl": "$_"/;
201     };
202
203     $class->loader($impl->new(%$args));
204     $class->loader->load;
205     $class->_loader_invoked(1);
206
207     # copy to $self
208     if (ref $self) {
209         $self->loader($class->loader);
210         $self->_loader_invoked(1);
211
212         $self->_merge_state_from($class);
213     }
214
215     # restore $class's storage
216     $class->storage($class_storage);
217
218     return $self;
219 }
220
221 # FIXME This needs to be moved into DBIC at some point, otherwise we are
222 # maintaining things to do with DBIC guts, which we have no business of
223 # maintaining. But at the moment it would be just dead code in DBIC, so we'll
224 # maintain it here.
225 sub _merge_state_from {
226     my ($self, $from) = @_;
227
228     my $orig_class_mappings       = $self->class_mappings;
229     my $orig_source_registrations = $self->source_registrations;
230
231     $self->_copy_state_from($from);
232
233     $self->class_mappings(merge($orig_class_mappings, $self->class_mappings))
234         if $orig_class_mappings;
235
236     $self->source_registrations(merge($orig_source_registrations, $self->source_registrations))
237         if $orig_source_registrations;
238 }
239
240 sub _copy_state_from {
241     my $self = shift;
242     my ($from) = @_;
243
244     # older DBIC's do not have this method
245     if (try { DBIx::Class->VERSION('0.08197'); 1 }) {
246         return $self->next::method(@_);
247     }
248     else {
249         # this is a copy from DBIC git master pre 0.08197
250         $self->class_mappings({ %{$from->class_mappings} });
251         $self->source_registrations({ %{$from->source_registrations} });
252
253         foreach my $moniker ($from->sources) {
254             my $source = $from->source($moniker);
255             my $new = $source->new($source);
256             # we use extra here as we want to leave the class_mappings as they are
257             # but overwrite the source_registrations entry with the new source
258             $self->register_extra_source($moniker => $new);
259         }
260
261         if ($from->storage) {
262             $self->storage($from->storage);
263             $self->storage->set_schema($self);
264         }
265     }
266 }
267
268 =head2 connection
269
270 =over 4
271
272 =item Arguments: @args
273
274 =item Return Value: $new_schema
275
276 =back
277
278 See L<DBIx::Class::Schema/connection> for basic usage.
279
280 If the final argument is a hashref, and it contains the keys C<loader_options>
281 or C<loader_class>, those keys will be deleted, and their values value will be
282 used for the loader options or class, respectively, just as if set via the
283 L</loader_options> or L</loader_class> methods above.
284
285 The actual auto-loading operation (the heart of this module) will be invoked
286 as soon as the connection information is defined.
287
288 =cut
289
290 sub connection {
291     my $self  = shift;
292     my $class = ref $self || $self;
293
294     if($_[-1] && ref $_[-1] eq 'HASH') {
295         for my $option (qw/loader_class loader_options/) {
296             if(my $value = delete $_[-1]->{$option}) {
297                 $self->$option($value);
298             }
299         }
300         pop @_ if !keys %{$_[-1]};
301     }
302
303     # Make sure we inherit from schema_base_class and load schema_components
304     # before connecting.
305     require DBIx::Class::Schema::Loader::Base;
306     my $temp_loader = DBIx::Class::Schema::Loader::Base->new(
307         %{ $self->_loader_args },
308         schema => $self,
309         naming => 'current',
310         use_namespaces => 1,
311     );
312
313     my $modify_isa = 0;
314     my @components;
315
316     if ($temp_loader->schema_base_class || $temp_loader->schema_components) {
317         @components = @{ $temp_loader->schema_components }
318             if $temp_loader->schema_components;
319
320         push @components, ('+'.$temp_loader->schema_base_class)
321             if $temp_loader->schema_base_class;
322
323         my $class_isa = do {
324             no strict 'refs';
325             \@{"${class}::ISA"};
326         };
327
328         my @component_classes = map {
329             /^\+/ ? substr($_, 1, length($_) - 1) : "DBIx::Class::$_"
330         } @components;
331
332         $modify_isa++ if not array_eq([ @$class_isa[0..(@components-1)] ], \@component_classes)
333     }
334
335     if ($modify_isa) {
336         $class->load_components(@components);
337
338         # This hack is necessary because we changed @ISA of $self through
339         # ->load_components and we are now in a different place in the mro.
340         no warnings 'redefine';
341
342         local *connection = subname __PACKAGE__.'::connection' => sub {
343             my $self = shift;
344             $self->next::method(@_);
345         };
346
347         my @linear_isa = @{ mro::get_linear_isa($class) };
348
349         my $next_method;
350
351         foreach my $i (1..$#linear_isa) {
352             no strict 'refs';
353             $next_method = *{$linear_isa[$i].'::connection'}{CODE};
354             last if $next_method;
355         }
356
357         $self = $self->$next_method(@_);
358     }
359     else {
360         $self = $self->next::method(@_);
361     }
362
363     if(!$class->_loader_invoked) {
364         $self->_invoke_loader
365     }
366
367     return $self;
368 }
369
370 =head2 clone
371
372 See L<DBIx::Class::Schema/clone>.
373
374 =cut
375
376 sub clone {
377     my $self = shift;
378
379     my $clone = $self->next::method(@_);
380
381     if($clone->_loader_args) {
382         $clone->_loader_args->{schema} = $clone;
383         weaken($clone->_loader_args->{schema});
384     }
385
386     $clone;
387 }
388
389 =head2 dump_to_dir
390
391 =over 4
392
393 =item Argument: $directory
394
395 =back
396
397 Calling this as a class method on either L<DBIx::Class::Schema::Loader>
398 or any derived schema class will cause all schemas to dump
399 manual versions of themselves to the named directory when they are
400 loaded.  In order to be effective, this must be set before defining a
401 connection on this schema class or any derived object (as the loading
402 happens as soon as both a connection and loader_options are set, and
403 only once per class).
404
405 See L<DBIx::Class::Schema::Loader::Base/dump_directory> for more
406 details on the dumping mechanism.
407
408 This can also be set at module import time via the import option
409 C<dump_to_dir:/foo/bar> to L<DBIx::Class::Schema::Loader>, where
410 C</foo/bar> is the target directory.
411
412 Examples:
413
414     # My::Schema isa DBIx::Class::Schema::Loader, and has connection info
415     #   hardcoded in the class itself:
416     perl -MDBIx::Class::Schema::Loader=dump_to_dir:/foo/bar -MMy::Schema -e1
417
418     # Same, but no hard-coded connection, so we must provide one:
419     perl -MDBIx::Class::Schema::Loader=dump_to_dir:/foo/bar -MMy::Schema -e 'My::Schema->connection("dbi:Pg:dbname=foo", ...)'
420
421     # Or as a class method, as long as you get it done *before* defining a
422     #  connection on this schema class or any derived object:
423     use My::Schema;
424     My::Schema->dump_to_dir('/foo/bar');
425     My::Schema->connection(........);
426
427     # Or as a class method on the DBIx::Class::Schema::Loader itself, which affects all
428     #   derived schemas
429     use My::Schema;
430     use My::OtherSchema;
431     DBIx::Class::Schema::Loader->dump_to_dir('/foo/bar');
432     My::Schema->connection(.......);
433     My::OtherSchema->connection(.......);
434
435     # Another alternative to the above:
436     use DBIx::Class::Schema::Loader qw| dump_to_dir:/foo/bar |;
437     use My::Schema;
438     use My::OtherSchema;
439     My::Schema->connection(.......);
440     My::OtherSchema->connection(.......);
441
442 =cut
443
444 sub import {
445     my $self = shift;
446
447     return if !@_;
448
449     my $cpkg = (caller)[0];
450
451     foreach my $opt (@_) {
452         if($opt =~ m{^dump_to_dir:(.*)$}) {
453             $self->dump_to_dir($1)
454         }
455         elsif($opt eq 'make_schema_at') {
456             no strict 'refs';
457             *{"${cpkg}::make_schema_at"} = \&make_schema_at;
458         }
459         elsif($opt eq 'naming') {
460             no strict 'refs';
461             *{"${cpkg}::naming"} = sub { $self->naming(@_) };
462         }
463         elsif($opt eq 'use_namespaces') {
464             no strict 'refs';
465             *{"${cpkg}::use_namespaces"} = sub { $self->use_namespaces(@_) };
466         }
467     }
468 }
469
470 =head2 make_schema_at
471
472 =over 4
473
474 =item Arguments: $schema_class_name, \%loader_options, \@connect_info
475
476 =item Return Value: $schema_class_name
477
478 =back
479
480 This function creates a DBIx::Class schema from an existing RDBMS
481 schema.  With the C<dump_directory> option, generates a set of
482 DBIx::Class classes from an existing database schema read from the
483 given dsn.  Without a C<dump_directory>, creates schema classes in
484 memory at runtime without generating on-disk class files.
485
486 For a complete list of supported loader_options, see
487 L<DBIx::Class::Schema::Loader::Base>
488
489 The last hashref in the C<\@connect_info> can specify the L</loader_class>.
490
491 This function can be imported in the usual way, as illustrated in
492 these Examples:
493
494     # Simple example, creates as a new class 'New::Schema::Name' in
495     #  memory in the running perl interpreter.
496     use DBIx::Class::Schema::Loader qw/ make_schema_at /;
497     make_schema_at(
498         'New::Schema::Name',
499         { debug => 1 },
500         [ 'dbi:Pg:dbname="foo"','postgres','',
501           { loader_class => 'MyLoader' } # optionally
502         ],
503     );
504
505     # Inside a script, specifying a dump directory in which to write
506     # class files
507     use DBIx::Class::Schema::Loader qw/ make_schema_at /;
508     make_schema_at(
509         'New::Schema::Name',
510         { debug => 1, dump_directory => './lib' },
511         [ 'dbi:Pg:dbname="foo"','postgres','',
512           { loader_class => 'MyLoader' } # optionally
513         ],
514     );
515
516 The last hashref in the C<\@connect_info> is checked for loader arguments such
517 as C<loader_options> and C<loader_class>, see L</connection> for more details.
518
519 =cut
520
521 sub make_schema_at {
522     my ($target, $opts, $connect_info) = @_;
523
524     {
525         no strict 'refs';
526         @{$target . '::ISA'} = qw/DBIx::Class::Schema::Loader/;
527     }
528
529     $target->_loader_invoked(0);
530
531     $target->loader_options($opts);
532
533     my $temp_schema = $target->connect(@$connect_info);
534
535     $target->storage($temp_schema->storage);
536     $target->storage->set_schema($target);
537
538     return $target;
539 }
540
541 =head2 rescan
542
543 =over 4
544
545 =item Return Value: @new_monikers
546
547 =back
548
549 Re-scans the database for newly added tables since the initial
550 load, and adds them to the schema at runtime, including relationships,
551 etc.  Does not process drops or changes.
552
553 Returns a list of the new monikers added.
554
555 =cut
556
557 sub rescan { my $self = shift; $self->loader->rescan($self) }
558
559 =head2 naming
560
561 =over 4
562
563 =item Arguments: \%opts | $ver
564
565 =back
566
567 Controls the naming options for backward compatibility, see
568 L<DBIx::Class::Schema::Loader::Base/naming> for details.
569
570 To upgrade a dynamic schema, use:
571
572     __PACKAGE__->naming('current');
573
574 Can be imported into your dump script and called as a function as well:
575
576     naming('v4');
577
578 =head2 use_namespaces
579
580 =over 4
581
582 =item Arguments: 1|0
583
584 =back
585
586 Controls the use_namespaces options for backward compatibility, see
587 L<DBIx::Class::Schema::Loader::Base/use_namespaces> for details.
588
589 To upgrade a dynamic schema, use:
590
591     __PACKAGE__->use_namespaces(1);
592
593 Can be imported into your dump script and called as a function as well:
594
595     use_namespaces(1);
596
597 =head1 KNOWN ISSUES
598
599 =head2 Multiple Database Schemas
600
601 See L<DBIx::Class::Schema::Loader::Base/db_schema>.
602
603 =head1 ACKNOWLEDGEMENTS
604
605 Matt S Trout, all of the #dbix-class folks, and everyone who's ever sent
606 in a bug report or suggestion.
607
608 Based on L<DBIx::Class::Loader> by Sebastian Riedel
609
610 Based upon the work of IKEBE Tomohiro
611
612 =head1 AUTHOR
613
614 blblack: Brandon Black <blblack@gmail.com>
615
616 =head1 CONTRIBUTORS
617
618 ilmari: Dagfinn Ilmari MannsE<aring>ker <ilmari@ilmari.org>
619
620 arcanez: Justin Hunter <justin.d.hunter@gmail.com>
621
622 ash: Ash Berlin <ash@cpan.org>
623
624 btilly: Ben Tilly <btilly@gmail.com>
625
626 Caelum: Rafael Kitover <rkitover@cpan.org>
627
628 TSUNODA Kazuya <drk@drk7.jp>
629
630 rbo: Robert Bohne <rbo@cpan.org>
631
632 ribasushi: Peter Rabbitson <ribasushi@cpan.org>
633
634 gugu: Andrey Kostenko <a.kostenko@rambler-co.ru>
635
636 jhannah: Jay Hannah <jay@jays.net>
637
638 jnap: John Napiorkowski <jjn1056@yahoo.com>
639
640 rbuels: Robert Buels <rbuels@gmail.com>
641
642 timbunce: Tim Bunce <timb@cpan.org>
643
644 mst: Matt S. Trout <mst@shadowcatsystems.co.uk>
645
646 mstratman: Mark A. Stratman <stratman@gmail.com>
647
648 kane: Jos Boumans <kane@cpan.org>
649
650 waawaamilk: Nigel McNie <nigel@mcnie.name>
651
652 acmoore: Andrew Moore <amoore@cpan.org>
653
654 bphillips: Brian Phillips <bphillips@cpan.org>
655
656 schwern: Michael G. Schwern <mschwern@cpan.org>
657
658 SineSwiper: Brendan Byrd <byrd.b@insightcom.com>
659
660 hobbs: Andrew Rodland <arodland@cpan.org>
661
662 domm: Thomas Klausner <domm@plix.at>
663
664 spb: Stephen Bennett <spb@exherbo.org>
665
666 Matias E. Fernandez <mfernandez@pisco.ch>
667
668 alnewkirk: Al Newkirk <awncorp@cpan.org>
669
670 angelixd: Paul C. Mantz <pcmantz@cpan.org>
671
672 andrewalker: AndrĂ© Walker <andre@andrewalker.net>
673
674 ... and lots of other folks. If we forgot you, please write the current
675 maintainer or RT.
676
677 =head1 COPYRIGHT & LICENSE
678
679 Copyright (c) 2006 - 2009 by the aforementioned
680 L<DBIx::Class::Schema::Loader/AUTHOR> and
681 L<DBIx::Class::Schema::Loader/CONTRIBUTORS>.
682
683 This library is free software; you can redistribute it and/or modify it under
684 the same terms as Perl itself.
685
686 =head1 SEE ALSO
687
688 L<DBIx::Class>, L<DBIx::Class::Manual::Intro>, L<DBIx::Class::Tutorial>,
689 L<DBIx::Class::Schema::Loader::Base>
690
691 =cut
692
693 1;
694 # vim:et sts=4 sw=4 tw=0: