=head3 Paged results
When you expect a large number of results, you can ask L<DBIx::Class> for a
-paged resultset, which will fetch only a small number of records at a time:
+paged resultset, which will fetch only a defined number of records at a time:
my $rs = $schema->resultset('Artist')->search(
undef,
return $rs->page(1); # DBIx::Class::ResultSet containing first 10 records
-In either of the above cases, you can return a L<Data::Page> object for the
+In either of the above cases, you can get a L<Data::Page> object for the
resultset (suitable for use in e.g. a template) using the C<pager> method:
return $rs->pager();
join => [qw/ artist /],
order_by => [qw/ artist.name /]
}
- };
+ );
# Equivalent SQL:
# SELECT cd.* FROM cd
=head2 Schema import/export
-This functionality requires you to have L<SQL::Translator> (also known as
-"SQL Fairy") installed.
+To create a DBIx::Class schema from an existing database, use
+L<DBIx::Class::Schema::Loader>'s C<make_schema_at>:
-To create a DBIx::Class schema from an existing database:
+ perl -MDBIx::Class::Schema::Loader=make_schema_at,dump_to_dir:./lib -e 'make_schema_at("My::Schema", { debug => 1 }, [ "dbi:Pg:dbname=foo","postgres" ])'
- sqlt --from DBI
- --to DBIx::Class::File
- --prefix "MySchema" > MySchema.pm
+The following functionality requires you to have L<SQL::Translator>
+(also known as "SQL Fairy") installed.
-To create a MySQL database from an existing L<DBIx::Class> schema, convert the
-schema to MySQL's dialect of SQL:
+To create a set of database-specific .sql files for the above schema:
- sqlt --from SQL::Translator::Parser::DBIx::Class
- --to MySQL
- --DBIx::Class "MySchema.pm" > Schema1.sql
-
-And import using the mysql client:
+ my $schema = My::Schema->connect($dsn);
+ $schema->create_ddl_dir(['MySQL', 'SQLite', 'PostgreSQL'],
+ '0.1',
+ '/dbscriptdir/'
+ );
+
+By default this will create schema files in the current directory, for
+MySQL, SQLite and PostgreSQL, using the $VERSION from your Schema.pm.
+
+To create a new database using the schema:
+
+ my $schema = My::Schema->connect($dsn);
+ $schema->deploy({ add_drop_tables => 1});
+
+To import created .sql files using the mysql client:
+
+ mysql -h "host" -D "database" -u "user" -p < My_Schema_1.0_MySQL.sql
+
+To create C<ALTER TABLE> conversion scripts to update a database to a
+newer version of your schema at a later point, first set a new
+$VERSION in your Schema file, then:
+
+ my $schema = My::Schema->connect($dsn);
+ $schema->create_ddl_dir(['MySQL', 'SQLite', 'PostgreSQL'],
+ '0.2',
+ '/dbscriptdir/',
+ '0.1'
+ );
+
+This will produce new database-specific .sql files for the new version
+of the schema, plus scripts to convert from version 0.1 to 0.2. This
+requires that the files for 0.1 as created above are available in the
+given directory to diff against.
- mysql -h "host" -D "database" -u "user" -p < Schema1.sql
=head2 Easy migration from class-based to schema-based setup
=head3 Save the schema
-Use C<sqlt> to transform your schema into an SQL script suitable for your
-customer's database. E.g. for MySQL:
-
- sqlt --from SQL::Translator::Parser::DBIx::Class
- --to MySQL
- --DBIx::Class "MySchema.pm" > Schema1.mysql.sql
-
-If you need to target databases from multiple vendors, just generate an SQL
-script suitable for each. To support PostgreSQL too:
-
- sqlt --from SQL::Translator::DBIx::Class
- --to PostgreSQL
- --DBIx::Class "MySchema.pm" > Schema1.pgsql.sql
+Call L<DBIx::Class::Schema/create_ddl_dir> as above under L<Schema
+import/export>.
=head3 Deploy to customers
=head3 Modify the schema to change functionality
-As your application evolves, it may be necessary to modify your schema to
-change functionality. Once the changes are made to your schema in DBIx::Class,
-export the modified schema as before, taking care not to overwrite the original:
-
- sqlt --from SQL::Translator::DBIx::Class
- --to MySQL
- --DBIx::Class "Anything.pm" > Schema2.mysql.sql
-
-Next, use sqlt-diff to create an SQL script that will update the customer's
-database schema:
-
- sqlt-diff --to MySQL Schema1=MySQL Schema2=MySQL > SchemaUpdate.mysql.sql
+As your application evolves, it may be necessary to modify your schema
+to change functionality. Once the changes are made to your schema in
+DBIx::Class, export the modified schema and the conversion scripts as
+in L<Schema import/export>.
=head3 Deploy update to customers
-The schema update can be deployed to customers using the same method as before.
+Add the L<DBIx::Class::Schema::Versioned> schema component to your
+Schema class. This will add a new table to your database called
+C<SchemaVersions> which will keep track of which version is installed
+and warn if the user trys to run a newer schema version than the
+database thinks it has.
+
+Alternatively, you can send the conversion sql scripts to your
+customers as above.
=head2 Setting limit dialect for SQL::Abstract::Limit
my $sql = shift();
my $params = @_;
- print "Executing $sql: ".join(', ', @params)."\n";
+ $self->print("Executing $sql: ".join(', ', @params)."\n");
$start = time();
}
my $sql = shift();
my @params = @_;
- printf("Execution took %0.4f seconds.\n", time() - $start);
+ my $elapsed = sprintf("%0.4f", time() - $start);
+ $self->print("Execution took $elapsed seconds.\n");
$start = undef;
}
You can then install that class as the debugging object:
- __PACKAGE__->storage()->debugobj(new My::Profiler());
- __PACKAGE__->storage()->debug(1);
+ __PACKAGE__->storage->debugobj(new My::Profiler());
+ __PACKAGE__->storage->debug(1);
A more complicated example might involve storing each execution of SQL in an
array:
You could then create average, high and low execution times for an SQL
statement and dig down to see if certain parameters cause aberrant behavior.
+You might want to check out L<DBIx::Class::QueryLog> as well.
=head2 Getting the value of the primary key for the last database insert