Alzabo
view release on metacpan or search on metacpan
lib/Alzabo/Intro.pod view on Meta::CPAN
my $location = $self;
while ( my $location = $location->parent )
{
die "Insert into location would create loop"
if $location->parent_location_id == $data{location_id};
}
}
}
=head2 Using SQL functions
Each subclass of Alzabo::SQLMaker is capable of exporting functions
that allow you to use all the SQL functions that your RDBMS provides.
These functions are normal Perl functions. They take as arguments
normal scalars (strings and numbers), C<Alzabo::Column> objects, or
the return value of another SQL function. They may be used to select
data via the C<select()> and C<function()> methods in both the
L<C<Alzabo::Runtime::Table>|Alzabo::Runtime::Table/"function and
select"> and
L<C<Alzabo::Runtime::Schema>|Alzabo::Runtime::Schema/"function and
select"> classes. They may also be used as part of updates, inserts,
and where clauses in any place that is valid SQL.
Examples:
use Alzabo::SQLMaker::MySQL qw(MAX NOW PI);
my $max =
$table->function( select => MAX( $table->column('budget') ),
where => [ $table->column('country'), '=', 'USA' ] );
$table->insert( values => { create_date => NOW() } );
$row->update( pi => PI() );
my $cursor =
$table->rows_where( where =>
[ $table->column('expire_date'), '<=', NOW() ] );
my $cursor =
$table->rows_where( where =>
[ LENGTH( $table->column('password') ), '<=', 5 ] );
The documentation for the Alzabo::SQLMaker subclass for your RDBMS
will contain a detailed list of all exportable functions.
=head2 Row Objects Not in the Database
Sometimes you'll want to create an object with the row object API, but
which does not represent a row in the database. See the
L<C<Alzabo::Runtime::Row> documentation|Alzabo::Runtime::Row/POTENTIAL
ROWS> for details on how these objects can be created.
=head2 Changing the schema
In MySQL, there are a number of various types of integers. The type
C<TINYINT> can hold values from -128 to 127. But what if have more
than 127 movies? And if that's the case we might have more than 127
people too.
For safety's sake, it might be best to make all of the primary key
integer columns C<INT> columns instead. And while we're at it we want
to make them C<UNSIGNED> as well, as we don't need to insert negative
numbers into these columns.
You could break out the RDBMS manual (because you probably forgot the
exact C<ALTER TABLE> syntax you'll need). Or you could use Alzabo.
Note that this time we use a
L<C<Alzabo::Create::Schema>|Alzabo::Create::Schema> object, not
L<C<Alzabo::Runtime::Schema>|Alzabo::Runtime::Schema>.
my $schema = Alzabo::Create::Schema->load_from_file( name => 'movies' );
foreach my $t ( $schema->tables )
{
foreach my $c ( $t->columns )
{
if ( $c->is_primary_key and lc $c->type eq 'tinyint' )
{
$c->set_type('int');
$c->add_attribute('unsigned');
}
}
}
$schema->create( user => 'user', password => 'password' );
$schema->save_to_file;
Because Alzabo keeps track of the schema's state the last time it was
created in the RDBMS, the C<create()> method here will generate the
appropriate SQL to alter the RDBMS schema so that it matches the
schema as defined in Alzabo.
=head1 TRANSACTIONS
Alzabo uses transactions internally in order to guarantee consistency.
Obviously, if you are using a database such as MySQL (without InnoDB)
that does not support transactions, this is not possible.
If you would like to use transactions explicitly in your code, please
make sure to use the L<C<Alzabo::Schema>|Alzabo::Schema> class's
L<C<begin_work()>|Alzabo::Schema/begin_work>,
L<C<commit()>|Alzabo::Schema/commit>, and
L<C<rollback()>|Alzabo::Schema/rollback> methods.
=head1 EXCEPTIONS
Alzabo uses exceptions as its error reporting mechanism. This means
that all calls to its methods should be wrapped in C<eval{}>. This is
less onerous than it sounds. In general, there's no reason not to
wrap all of your calls in one large eval block. Then at the end of
the block simply check the value of C<$@>.
Also see the L<C<Alzabo::Exceptions>|Alzabo::Exceptions>
documentation, which lists all of the different exception used by
Alzabo.
This is similar to using C<DBI> with the C<RaiseError> attribute set
to a true value.
Its important to note that some methods (such as the driver's
( run in 1.204 second using v1.01-cache-2.11-cpan-39bf76dae61 )