ORLite
view release on metacpan or search on metacpan
lib/ORLite.pm view on Meta::CPAN
package => 'My::ORM',
file => 'data/sqlite.db',
user_version => 12,
readonly => 1,
create => sub {
my $dbh = shift;
$dbh->do('CREATE TABLE foo ( bar TEXT NOT NULL )');
},
tables => [ 'table1', 'table2' ],
cleanup => 'VACUUM',
prune => 1,
};
=head1 DESCRIPTION
L<SQLite> is a light single file SQL database that provides an
excellent platform for embedded storage of structured data.
However, while it is superficially similar to a regular server-side SQL
database, SQLite has some significant attributes that make using it like
a traditional database difficult.
For example, SQLite is extremely fast to connect to compared to server
databases (1000 connections per second is not unknown) and is
particularly bad at concurrency, as it can only lock transactions at
a database-wide level.
This role as a superfast internal data store can clash with the roles and
designs of traditional object-relational modules like L<Class::DBI> or
L<DBIx::Class>.
What this situation would seem to need is an object-relation system that is
designed specifically for SQLite and is aligned with its idiosyncracies.
ORLite is an object-relation system specifically tailored for SQLite that
follows many of the same principles as the ::Tiny series of modules and
has a design and feature set that aligns directly to the capabilities of
SQLite.
Further documentation will be available at a later time, but the synopsis
gives a pretty good idea of how it works.
=head2 How ORLite Works
ORLite discovers the schema of a SQLite database, and then generates the
code for a complete set of classes that let you work with the objects stored
in that database.
In the simplest form, your target root package "uses" ORLite, which will do
the schema discovery and code generation at compile-time.
When called, ORLite generates two types of packages.
Firstly, it builds database connectivity, transaction support, and other
purely database level functionality into your root namespace.
Secondly, it will create one sub-package underneath the namespace of the root
module for each table or view it finds in the database.
Once the basic table support has been generated, it will also try to load an
"overlay" module of the same name. Thus, by created a Foo::TableName module on
disk containing "extra" code, you can extend the original and add additional
functionality to it.
=head1 OPTIONS
ORLite takes a set of options for the class construction at compile time
as a HASH parameter to the "use" line.
As a convenience, you can pass just the name of an existing SQLite file
to load, and ORLite will apply defaults to all other options.
# The following are equivalent
use ORLite $filename;
use ORLite {
file => $filename,
};
The behaviour of each of the options is as follows:
=head2 package
The optional C<package> parameter is used to provide the Perl root namespace
to generate the code for. This class does not need to exist as a module on
disk, nor does it need to have anything loaded or in the namespace.
By default, the package used is the package that is calling ORLite's import
method (typically via the C<use ORLite { ... }> line).
=head2 file
The compulsory C<file> parameter (the only compulsory parameter) provides
the path to the SQLite file to use for the ORM class tree.
If the file already exists, it must be a valid SQLite file match that
supported by the version of L<DBD::SQLite> that is installed on your
system.
L<ORLite> will throw an exception if the file does not exist, B<unless>
you also provide the C<create> option to signal that L<ORLite> should
create a new SQLite file on demand.
If the C<create> option is provided, the path provided must be creatable.
When creating the database, L<ORLite> will also create any missing
directories as needed.
=head2 user_version
When working with ORLite, the biggest risk to the stability of your code
is often the reliability of the SQLite schema structure over time.
When the database schema changes the code generated by ORLite will also
change. This can easily result in an unexpected change in the API of your
class tree, breaking the code that sits on top of those generated APIs.
To resolve this, L<ORLite> supports a feature called schema version-locking.
Via the C<user_version> SQLite pragma, you can set a revision for your
database schema, increasing the number each time to make a non-trivial
( run in 2.282 seconds using v1.01-cache-2.11-cpan-39bf76dae61 )