X-Git-Url: http://git.shadowcat.co.uk/gitweb/gitweb.cgi?a=blobdiff_plain;f=lib%2FDBIx%2FClass%2FSchema%2FLoader%2FBase.pm;h=7f72358ce649e431930b945b21d57caf27d619b7;hb=refs%2Fheads%2F0.08;hp=e8a5ac7cc89388b0ea7de0c524fdfdffa36ae072;hpb=c9cf9b4def5db80a79facea0eaba6dc32ac1e2c3;p=dbsrgits%2FDBIx-Class-Schema-Loader.git diff --git a/lib/DBIx/Class/Schema/Loader/Base.pm b/lib/DBIx/Class/Schema/Loader/Base.pm index e8a5ac7..7f72358 100644 --- a/lib/DBIx/Class/Schema/Loader/Base.pm +++ b/lib/DBIx/Class/Schema/Loader/Base.pm @@ -3,7 +3,6 @@ package DBIx::Class::Schema::Loader::Base; use strict; use warnings; use base qw/Class::Accessor::Grouped Class::C3::Componentised/; -use namespace::autoclean; use Class::C3; use Carp::Clan qw/^DBIx::Class/; use DBIx::Class::Schema::Loader::RelBuilder; @@ -17,13 +16,15 @@ use Lingua::EN::Inflect::Phrase qw//; use File::Temp qw//; use Class::Unload; use Class::Inspector (); -use Data::Dumper::Concise; use Scalar::Util 'looks_like_number'; use File::Slurp 'slurp'; -use DBIx::Class::Schema::Loader::Utils 'split_name'; -require DBIx::Class; +use DBIx::Class::Schema::Loader::Utils qw/split_name dumper_squashed/; +use DBIx::Class::Schema::Loader::Optional::Dependencies (); +use Try::Tiny; +use DBIx::Class (); +use namespace::clean; -our $VERSION = '0.07001'; +our $VERSION = '0.08000'; __PACKAGE__->mk_group_ro_accessors('simple', qw/ schema @@ -131,7 +132,7 @@ overwriting a dump made with an earlier version. The option also takes a hashref: - naming => { relationships => 'v7', monikers => 'v7' } + naming => { relationships => 'v8', monikers => 'v8' } The keys are: @@ -193,6 +194,11 @@ transition instead of just being lowercased, so C becomes C. If you don't have any CamelCase table or column names, you can upgrade without breaking any of your code. +=item v8 + +This mode tries harder to not have collisions between column accessors and +belongs_to relationship accessors. + =back Dynamic schemas will always default to the 0.04XXX relationship names and won't @@ -201,10 +207,10 @@ and singularization put this in your C file: __PACKAGE__->naming('current'); -Or if you prefer to use 0.07XXX features but insure that nothing breaks in the +Or if you prefer to use 0.08XXX features but insure that nothing breaks in the next major version upgrade: - __PACKAGE__->naming('v7'); + __PACKAGE__->naming('v8'); =head2 generate_pod @@ -258,10 +264,10 @@ relationship types override those set in 'all'. For example: relationship_attrs => { - belongs_to => { is_deferrable => 1 }, + belongs_to => { is_deferrable => 0 }, }, -use this to make your foreign key constraints DEFERRABLE. +use this to turn off DEFERRABLE on your foreign key constraints. =head2 debug @@ -473,6 +479,14 @@ setting this option. Set to true to prepend the L to table names for C<< __PACKAGE__->table >> calls, and to some other things like Oracle sequences. +=head2 use_moose + +Creates Schema and Result classes that use L, L and +L. The default content after the md5 sum also makes the +classes immutable. + +It is safe to upgrade your existing Schema to this option. + =head1 METHODS None of these methods are intended for direct invocation by regular @@ -481,7 +495,7 @@ L. =cut -my $CURRENT_V = 'v7'; +my $CURRENT_V = 'v8'; my @CLASS_ARGS = qw( schema_base_class result_base_class additional_base_classes @@ -536,15 +550,10 @@ sub new { $self->_validate_class_args; if ($self->use_moose) { - eval <<'EOF'; -package __DBICSL__DUMMY; -use Moose; -use MooseX::NonMoose; -use namespace::autoclean; -EOF - if ($@) { - die sprintf "You must install the following CPAN modules to enable the use_moose option: %s.\n", - "Moose, MooseX::NonMoose and namespace::autoclean"; + if (not DBIx::Class::Schema::Loader::Optional::Dependencies->req_ok_for('use_moose')) { + die sprintf "You must install the following CPAN modules to enable the use_moose option: %s.\nYou are missing: %s.\n", + "Moose, MooseX::NonMoose and namespace::autoclean", + DBIx::Class::Schema::Loader::Optional::Dependencies->req_missing_for('use_moose'); } } @@ -1002,6 +1011,15 @@ sub _relbuilder { $self->relationship_attrs, ); } + elsif ($self->naming->{relationships} eq 'v6') { + require DBIx::Class::Schema::Loader::RelBuilder::Compat::v0_07; + return $self->{relbuilder} ||= DBIx::Class::Schema::Loader::RelBuilder::Compat::v0_07->new ( + $self->schema, + $self->inflect_plural, + $self->inflect_singular, + $self->relationship_attrs, + ); + } return $self->{relbuilder} ||= DBIx::Class::Schema::Loader::RelBuilder->new ( $self->schema, @@ -1100,7 +1118,7 @@ sub _reload_classes { local *Class::C3::reinitialize = sub {}; use warnings; - if ($class->can('meta')) { + if ($class->can('meta') && try { $class->meta->isa('Moose::Meta::Class') }) { $class->meta->make_mutable; } Class::Unload->unload($class) if $unload; @@ -1111,7 +1129,7 @@ sub _reload_classes { && ($resultset_class ne 'DBIx::Class::ResultSet') ) { my $has_file = Class::Inspector->loaded_filename($resultset_class); - if ($resultset_class->can('meta')) { + if ($resultset_class->can('meta') && try { $resultset_class->meta->isa('Moose::Meta::Class') }) { $resultset_class->meta->make_mutable; } Class::Unload->unload($resultset_class) if $unload; @@ -1226,7 +1244,15 @@ sub _dump_to_dir { . qq|# DO NOT MODIFY THE FIRST PART OF THIS FILE\n\n| . qq|use strict;\nuse warnings;\n\n|; if ($self->use_moose) { - $src_text.= qq|use Moose;\nuse MooseX::NonMoose;\nuse namespace::autoclean;\nextends '$result_base_class';\n\n|; + $src_text.= qq|use Moose;\nuse MooseX::NonMoose;\nuse namespace::autoclean;|; + + # these options 'use base' which is compile time + if (@{ $self->left_base_classes } || @{ $self->additional_base_classes }) { + $src_text .= qq|\nBEGIN { extends '$result_base_class' }\n\n|; + } + else { + $src_text .= qq|\nextends '$result_base_class';\n\n|; + } } else { $src_text .= qq|use base '$result_base_class';\n\n|; @@ -1424,11 +1450,13 @@ sub _use { sub _inject { my $self = shift; my $target = shift; - my $schema_class = $self->schema_class; my $blist = join(q{ }, @_); - warn "$target: use base qw/ $blist /;" if $self->debug && @_; - $self->_raw_stmt($target, "use base qw/ $blist /;") if @_; + + return unless $blist; + + warn "$target: use base qw/$blist/;" if $self->debug; + $self->_raw_stmt($target, "use base qw/$blist/;"); } sub _result_namespace { @@ -1522,7 +1550,7 @@ sub _resolve_col_accessor_collisions { my @methods; - for my $class ($base, @components) { + for my $class ($base, @components, $self->use_moose ? 'Moose::Object' : ()) { eval "require ${class};"; die $@ if $@; @@ -1532,6 +1560,9 @@ sub _resolve_col_accessor_collisions { my %methods; @methods{@methods} = (); + # futureproof meta + $methods{meta} = undef; + while (my ($col, $info) = each %$col_info) { my $accessor = $info->{accessor} || $col; @@ -1777,12 +1808,10 @@ sub _make_pod { my ($table) = @_; my $pcm = $self->pod_comment_mode; my ($comment, $comment_overflows, $comment_in_name, $comment_in_desc); - if ( $self->can('_table_comment') ) { - $comment = $self->_table_comment($table); - $comment_overflows = ($comment and length $comment > $self->pod_comment_spillover_length); - $comment_in_name = ($pcm eq 'name' or ($pcm eq 'auto' and !$comment_overflows)); - $comment_in_desc = ($pcm eq 'description' or ($pcm eq 'auto' and $comment_overflows)); - } + $comment = $self->__table_comment($table); + $comment_overflows = ($comment and length $comment > $self->pod_comment_spillover_length); + $comment_in_name = ($pcm eq 'name' or ($pcm eq 'auto' and !$comment_overflows)); + $comment_in_desc = ($pcm eq 'description' or ($pcm eq 'auto' and $comment_overflows)); $self->_pod( $class, "=head1 NAME" ); my $table_descr = $class; $table_descr .= " - " . $comment if $comment and $comment_in_name; @@ -1806,12 +1835,7 @@ sub _make_pod { $s = !defined $s ? 'undef' : length($s) == 0 ? '(empty string)' : ref($s) eq 'SCALAR' ? $$s : - ref($s) ? do { - my $dd = Dumper; - $dd->Indent(0); - $dd->Values([$s]); - $dd->Dump; - } : + ref($s) ? dumper_squashed $s : looks_like_number($s) ? $s : qq{'$s'} ; @@ -1820,9 +1844,7 @@ sub _make_pod { } sort keys %$attrs, ); - if( $self->can('_column_comment') - and my $comment = $self->_column_comment( $self->{_class2table}{$class}, $col_counter) - ) { + if (my $comment = $self->__column_comment($self->{_class2table}{$class}, $col_counter)) { $self->_pod( $class, $comment ); } } @@ -1838,6 +1860,36 @@ sub _make_pod { } } +sub _filter_comment { + my ($self, $txt) = @_; + + $txt = '' if not defined $txt; + + $txt =~ s/(?:\015?\012|\015\012?)/\n/g; + + return $txt; +} + +sub __table_comment { + my $self = shift; + + if (my $code = $self->can('_table_comment')) { + return $self->_filter_comment($self->$code(@_)); + } + + return ''; +} + +sub __column_comment { + my $self = shift; + + if (my $code = $self->can('_column_comment')) { + return $self->_filter_comment($self->$code(@_)); + } + + return ''; +} + # Stores a POD documentation sub _pod { my ($self, $class, $stmt) = @_;