1 package DBIx::Class::Schema::Loader;
5 use base qw/DBIx::Class::Schema Class::Accessor::Grouped/;
8 use Carp::Clan qw/^DBIx::Class/;
9 use Scalar::Util 'weaken';
10 use Sub::Util 'set_subname';
11 use DBIx::Class::Schema::Loader::Utils 'array_eq';
13 use Hash::Merge 'merge';
17 # Always remember to do all digits for the version even if they're 0
18 # i.e. first release of 0.XX *must* be 0.XX000. This avoids fBSD ports
19 # brain damage and presumably various other packaging systems too
20 our $VERSION = '0.07047';
22 __PACKAGE__->mk_group_accessors('inherited', qw/
31 __PACKAGE__->_loader_args({});
37 DBIx::Class::Schema::Loader - Create a DBIx::Class::Schema based on a database
41 ### use this module to generate a set of class files
44 use DBIx::Class::Schema::Loader qw/ make_schema_at /;
48 dump_directory => './lib',
50 [ 'dbi:Pg:dbname="foo"', 'myuser', 'mypassword',
51 { loader_class => 'MyLoader' } # optionally
55 # from the command line or a shell script with dbicdump (distributed
56 # with this module). Do `perldoc dbicdump` for usage.
57 dbicdump -o dump_directory=./lib \
58 -o components='["InflateColumn::DateTime"]' \
65 ### or generate and load classes at runtime
66 # note: this technique is not recommended
67 # for use in production code
70 use base qw/DBIx::Class::Schema::Loader/;
72 __PACKAGE__->loader_options(
73 constraint => '^foo.*',
77 #### in application code elsewhere:
81 my $schema1 = My::Schema->connect( $dsn, $user, $password, $attrs);
83 my $schema1 = "My::Schema"; $schema1->connection(as above);
87 DBIx::Class::Schema::Loader automates the definition of a
88 L<DBIx::Class::Schema> by scanning database table definitions and setting up
89 the columns, primary keys, unique constraints and relationships.
91 See L<dbicdump> for the C<dbicdump> utility.
93 DBIx::Class::Schema::Loader currently supports only the DBI storage type. It
94 has explicit support for L<DBD::Pg>, L<DBD::mysql>, L<DBD::DB2>,
95 L<DBD::Firebird>, L<DBD::InterBase>, L<DBD::Informix>, L<DBD::SQLAnywhere>,
96 L<DBD::SQLite>, L<DBD::Sybase> (for Sybase ASE and MSSSQL), L<DBD::ODBC> (for
97 MSSQL, MSAccess, Firebird and SQL Anywhere) L<DBD::ADO> (for MSSQL and
98 MSAccess) and L<DBD::Oracle>. Other DBI drivers may function to a greater or
99 lesser degree with this loader, depending on how much of the DBI spec they
100 implement, and how standard their implementation is.
102 Patches to make other DBDs work correctly welcome.
104 See L<DBIx::Class::Schema::Loader::DBI::Writing> for notes on writing
105 your own vendor-specific subclass for an unsupported DBD driver.
107 This module requires L<DBIx::Class> 0.08127 or later, and obsoletes the older
108 L<DBIx::Class::Loader>.
110 See L<DBIx::Class::Schema::Loader::Base> for available options.
116 The loader object, as class data on your Schema. For methods available see
117 L<DBIx::Class::Schema::Loader::Base> and L<DBIx::Class::Schema::Loader::DBI>.
130 =item Argument: $loader_class
134 Set the loader class to be instantiated when L</connection> is called.
135 If the classname starts with "::", "DBIx::Class::Schema::Loader" is
136 prepended. Defaults to L<DBIx::Class::Schema/storage_type> (which must
137 start with "::" when using L<DBIx::Class::Schema::Loader>).
139 This is mostly useful for subclassing existing loaders or in conjunction
140 with L</dump_to_dir>.
142 =head2 loader_options
146 =item Argument: \%loader_options
150 Example in Synopsis above demonstrates a few common arguments. For
151 detailed information on all of the arguments, most of which are
152 only useful in fairly complex scenarios, see the
153 L<DBIx::Class::Schema::Loader::Base> documentation.
155 If you intend to use C<loader_options>, you must call
156 C<loader_options> before any connection is made, or embed the
157 C<loader_options> in the connection information itself as shown
158 below. Setting C<loader_options> after the connection has
159 already been made is useless.
166 my %args = (ref $_[0] eq 'HASH') ? %{$_[0]} : @_;
167 $self->_loader_args(\%args);
174 my $class = ref $self || $self;
176 my $args = $self->_loader_args;
178 # temporarily copy $self's storage to class
179 my $class_storage = $class->storage;
181 $class->storage($self->storage);
182 $class->storage->set_schema($class);
185 $args->{schema} = $class;
186 $args->{schema_class} = $class;
187 $args->{dump_directory} ||= $self->dump_to_dir;
188 $args->{naming} = $self->naming if $self->naming;
189 $args->{use_namespaces} = $self->use_namespaces if defined $self->use_namespaces;
191 # XXX this only works for relative storage_type, like ::DBI ...
192 my $loader_class = $self->loader_class;
194 $loader_class = "DBIx::Class::Schema::Loader${loader_class}" if $loader_class =~ /^::/;
195 $args->{loader_class} = $loader_class;
198 my $impl = $loader_class || "DBIx::Class::Schema::Loader" . $self->storage_type;
200 $self->ensure_class_loaded($impl)
203 croak qq/Could not load loader_class "$impl": "$_"/;
206 $class->loader($impl->new(%$args));
207 $class->loader->load;
208 $class->_loader_invoked(1);
212 $self->loader($class->loader);
213 $self->_loader_invoked(1);
215 $self->_merge_state_from($class);
218 # restore $class's storage
219 $class->storage($class_storage);
224 # FIXME This needs to be moved into DBIC at some point, otherwise we are
225 # maintaining things to do with DBIC guts, which we have no business of
226 # maintaining. But at the moment it would be just dead code in DBIC, so we'll
228 sub _merge_state_from {
229 my ($self, $from) = @_;
231 my $orig_class_mappings = $self->class_mappings;
232 my $orig_source_registrations = $self->source_registrations;
234 $self->_copy_state_from($from);
236 $self->class_mappings(merge($orig_class_mappings, $self->class_mappings))
237 if $orig_class_mappings;
239 $self->source_registrations(merge($orig_source_registrations, $self->source_registrations))
240 if $orig_source_registrations;
243 sub _copy_state_from {
247 # older DBIC's do not have this method
248 if (try { DBIx::Class->VERSION('0.08197'); 1 }) {
249 return $self->next::method(@_);
252 # this is a copy from DBIC git master pre 0.08197
253 $self->class_mappings({ %{$from->class_mappings} });
254 $self->source_registrations({ %{$from->source_registrations} });
256 foreach my $moniker ($from->sources) {
257 my $source = $from->source($moniker);
258 my $new = $source->new($source);
259 # we use extra here as we want to leave the class_mappings as they are
260 # but overwrite the source_registrations entry with the new source
261 $self->register_extra_source($moniker => $new);
264 if ($from->storage) {
265 $self->storage($from->storage);
266 $self->storage->set_schema($self);
275 =item Arguments: @args
277 =item Return Value: $new_schema
281 See L<DBIx::Class::Schema/connection> for basic usage.
283 If the final argument is a hashref, and it contains the keys C<loader_options>
284 or C<loader_class>, those keys will be deleted, and their values value will be
285 used for the loader options or class, respectively, just as if set via the
286 L</loader_options> or L</loader_class> methods above.
288 The actual auto-loading operation (the heart of this module) will be invoked
289 as soon as the connection information is defined.
295 my $class = ref $self || $self;
297 if($_[-1] && ref $_[-1] eq 'HASH') {
298 for my $option (qw/loader_class loader_options/) {
299 if(my $value = delete $_[-1]->{$option}) {
300 $self->$option($value);
303 pop @_ if !keys %{$_[-1]};
306 # Make sure we inherit from schema_base_class and load schema_components
308 require DBIx::Class::Schema::Loader::Base;
309 my $temp_loader = DBIx::Class::Schema::Loader::Base->new(
310 %{ $self->_loader_args },
319 if ($temp_loader->schema_base_class || $temp_loader->schema_components) {
320 @components = @{ $temp_loader->schema_components }
321 if $temp_loader->schema_components;
323 push @components, ('+'.$temp_loader->schema_base_class)
324 if $temp_loader->schema_base_class;
331 my @component_classes = map {
332 /^\+/ ? substr($_, 1, length($_) - 1) : "DBIx::Class::$_"
335 $modify_isa++ if not array_eq([ @$class_isa[0..(@components-1)] ], \@component_classes)
339 $class->load_components(@components);
341 # This hack is necessary because we changed @ISA of $self through
342 # ->load_components and we are now in a different place in the mro.
343 no warnings 'redefine';
345 local *connection = set_subname __PACKAGE__.'::connection' => sub {
347 $self->next::method(@_);
350 my @linear_isa = @{ mro::get_linear_isa($class) };
354 foreach my $i (1..$#linear_isa) {
356 $next_method = *{$linear_isa[$i].'::connection'}{CODE};
357 last if $next_method;
360 $self = $self->$next_method(@_);
363 $self = $self->next::method(@_);
366 if(!$class->_loader_invoked) {
367 $self->_invoke_loader
375 See L<DBIx::Class::Schema/clone>.
382 my $clone = $self->next::method(@_);
384 if($clone->_loader_args) {
385 $clone->_loader_args->{schema} = $clone;
386 weaken($clone->_loader_args->{schema});
396 =item Argument: $directory
400 Calling this as a class method on either L<DBIx::Class::Schema::Loader>
401 or any derived schema class will cause all schemas to dump
402 manual versions of themselves to the named directory when they are
403 loaded. In order to be effective, this must be set before defining a
404 connection on this schema class or any derived object (as the loading
405 happens as soon as both a connection and loader_options are set, and
406 only once per class).
408 See L<DBIx::Class::Schema::Loader::Base/dump_directory> for more
409 details on the dumping mechanism.
411 This can also be set at module import time via the import option
412 C<dump_to_dir:/foo/bar> to L<DBIx::Class::Schema::Loader>, where
413 C</foo/bar> is the target directory.
417 # My::Schema isa DBIx::Class::Schema::Loader, and has connection info
418 # hardcoded in the class itself:
419 perl -MDBIx::Class::Schema::Loader=dump_to_dir:/foo/bar -MMy::Schema -e1
421 # Same, but no hard-coded connection, so we must provide one:
422 perl -MDBIx::Class::Schema::Loader=dump_to_dir:/foo/bar -MMy::Schema -e 'My::Schema->connection("dbi:Pg:dbname=foo", ...)'
424 # Or as a class method, as long as you get it done *before* defining a
425 # connection on this schema class or any derived object:
427 My::Schema->dump_to_dir('/foo/bar');
428 My::Schema->connection(........);
430 # Or as a class method on the DBIx::Class::Schema::Loader itself, which affects all
434 DBIx::Class::Schema::Loader->dump_to_dir('/foo/bar');
435 My::Schema->connection(.......);
436 My::OtherSchema->connection(.......);
438 # Another alternative to the above:
439 use DBIx::Class::Schema::Loader qw| dump_to_dir:/foo/bar |;
442 My::Schema->connection(.......);
443 My::OtherSchema->connection(.......);
452 my $cpkg = (caller)[0];
454 foreach my $opt (@_) {
455 if($opt =~ m{^dump_to_dir:(.*)$}) {
456 $self->dump_to_dir($1)
458 elsif($opt eq 'make_schema_at') {
460 *{"${cpkg}::make_schema_at"} = \&make_schema_at;
462 elsif($opt eq 'naming') {
464 *{"${cpkg}::naming"} = $self->curry::naming;
466 elsif($opt eq 'use_namespaces') {
468 *{"${cpkg}::use_namespaces"} = $self->curry::use_namespaces,
473 =head2 make_schema_at
477 =item Arguments: $schema_class_name, \%loader_options, \@connect_info
479 =item Return Value: $schema_class_name
483 This function creates a DBIx::Class schema from an existing RDBMS
484 schema. With the C<dump_directory> option, generates a set of
485 DBIx::Class classes from an existing database schema read from the
486 given dsn. Without a C<dump_directory>, creates schema classes in
487 memory at runtime without generating on-disk class files.
489 For a complete list of supported loader_options, see
490 L<DBIx::Class::Schema::Loader::Base>
492 The last hashref in the C<\@connect_info> can specify the L</loader_class>.
494 This function can be imported in the usual way, as illustrated in
497 # Simple example, creates as a new class 'New::Schema::Name' in
498 # memory in the running perl interpreter.
499 use DBIx::Class::Schema::Loader qw/ make_schema_at /;
503 [ 'dbi:Pg:dbname="foo"','postgres','',
504 { loader_class => 'MyLoader' } # optionally
508 # Inside a script, specifying a dump directory in which to write
510 use DBIx::Class::Schema::Loader qw/ make_schema_at /;
513 { debug => 1, dump_directory => './lib' },
514 [ 'dbi:Pg:dbname="foo"','postgres','',
515 { loader_class => 'MyLoader' } # optionally
519 The last hashref in the C<\@connect_info> is checked for loader arguments such
520 as C<loader_options> and C<loader_class>, see L</connection> for more details.
525 my ($target, $opts, $connect_info) = @_;
529 @{$target . '::ISA'} = qw/DBIx::Class::Schema::Loader/;
532 $target->_loader_invoked(0);
534 $target->loader_options($opts);
536 my $temp_schema = $target->connect(@$connect_info);
538 $target->storage($temp_schema->storage);
539 $target->storage->set_schema($target);
548 =item Return Value: @new_monikers
552 Re-scans the database for newly added tables since the initial
553 load, and adds them to the schema at runtime, including relationships,
554 etc. Does not process drops or changes.
556 Returns a list of the new monikers added.
560 sub rescan { my $self = shift; $self->loader->rescan($self) }
566 =item Arguments: \%opts | $ver
570 Controls the naming options for backward compatibility, see
571 L<DBIx::Class::Schema::Loader::Base/naming> for details.
573 To upgrade a dynamic schema, use:
575 __PACKAGE__->naming('current');
577 Can be imported into your dump script and called as a function as well:
581 =head2 use_namespaces
589 Controls the use_namespaces options for backward compatibility, see
590 L<DBIx::Class::Schema::Loader::Base/use_namespaces> for details.
592 To upgrade a dynamic schema, use:
594 __PACKAGE__->use_namespaces(1);
596 Can be imported into your dump script and called as a function as well:
602 =head2 Multiple Database Schemas
604 See L<DBIx::Class::Schema::Loader::Base/db_schema>.
606 =head1 ACKNOWLEDGEMENTS
608 Matt S Trout, all of the #dbix-class folks, and everyone who's ever sent
609 in a bug report or suggestion.
611 Based on L<DBIx::Class::Loader> by Sebastian Riedel
613 Based upon the work of IKEBE Tomohiro
617 Caelum: Rafael Kitover <rkitover@cpan.org>
619 Dag-Erling Smørgrav <des@des.no>
621 Matias E. Fernandez <mfernandez@pisco.ch>
623 SineSwiper: Brendan Byrd <byrd.b@insightcom.com>
625 TSUNODA Kazuya <drk@drk7.jp>
627 acmoore: Andrew Moore <amoore@cpan.org>
629 alnewkirk: Al Newkirk <awncorp@cpan.org>
631 andrewalker: André Walker <andre@andrewalker.net>
633 angelixd: Paul C. Mantz <pcmantz@cpan.org>
635 arc: Aaron Crane <arc@cpan.org>
637 arcanez: Justin Hunter <justin.d.hunter@gmail.com>
639 ash: Ash Berlin <ash@cpan.org>
641 blblack: Brandon Black <blblack@gmail.com>
643 bphillips: Brian Phillips <bphillips@cpan.org>
645 btilly: Ben Tilly <btilly@gmail.com>
647 domm: Thomas Klausner <domm@plix.at>
649 gugu: Andrey Kostenko <a.kostenko@rambler-co.ru>
651 hobbs: Andrew Rodland <arodland@cpan.org>
653 ilmari: Dagfinn Ilmari MannsE<aring>ker <ilmari@ilmari.org>
655 jhannah: Jay Hannah <jay@jays.net>
657 jnap: John Napiorkowski <jjn1056@yahoo.com>
659 kane: Jos Boumans <kane@cpan.org>
661 mattp: Matt Phillips <mattp@cpan.org>
663 mephinet: Philipp Gortan <philipp.gortan@apa.at>
665 moritz: Moritz Lenz <moritz@faui2k3.org>
667 mst: Matt S. Trout <mst@shadowcatsystems.co.uk>
669 mstratman: Mark A. Stratman <stratman@gmail.com>
671 oalders: Olaf Alders <olaf@wundersolutions.com>
673 rbo: Robert Bohne <rbo@cpan.org>
675 rbuels: Robert Buels <rbuels@gmail.com>
677 ribasushi: Peter Rabbitson <ribasushi@cpan.org>
679 schwern: Michael G. Schwern <mschwern@cpan.org>
681 spb: Stephen Bennett <spb@exherbo.org>
683 timbunce: Tim Bunce <timb@cpan.org>
685 waawaamilk: Nigel McNie <nigel@mcnie.name>
687 ... and lots of other folks. If we forgot you, please write the current
690 =head1 COPYRIGHT & LICENSE
692 Copyright (c) 2006 - 2015 by the aforementioned
693 L<DBIx::Class::Schema::Loader/AUTHORS>.
695 This library is free software; you can redistribute it and/or modify it under
696 the same terms as Perl itself.
700 L<DBIx::Class>, L<DBIx::Class::Manual::Intro>, L<DBIx::Class::Tutorial>,
701 L<DBIx::Class::Schema::Loader::Base>
706 # vim:et sts=4 sw=4 tw=0: