DBIx-Custom
view release on metacpan or search on metacpan
lib/DBIx/Custom.pm view on Meta::CPAN
# Created time and updated time
if (defined $opt{ctime} || defined $opt{mtime}) {
for my $param (@$params) {
$param = {%$param};
}
my $now = $self->now;
$now = $now->() if ref $now eq 'CODE';
if (defined $opt{ctime}) {
$_->{$opt{ctime}} = $now for @$params;
}
if (defined $opt{mtime}) {
$_->{$opt{mtime}} = $now for @$params;
}
}
# Merge id to parameter
if (defined $opt{id} && !$multi) {
_deprecate('0.39', "DBIx::Custom::insert method's id option is DEPRECATED!");
for my $param (@$params) {
$param = {%$param};
}
confess "insert id option must be specified with primary_key option"
unless $opt{primary_key};
$opt{primary_key} = [$opt{primary_key}] unless ref $opt{primary_key} eq 'ARRAY';
$opt{id} = [$opt{id}] unless ref $opt{id} eq 'ARRAY';
for (my $i = 0; $i < @{$opt{primary_key}}; $i++) {
my $key = $opt{primary_key}->[$i];
next if exists $params->[0]->{$key};
$params->[0]->{$key} = $opt{id}->[$i];
}
}
if ($opt{bulk_insert}) {
$sql .= $self->_multi_values_clause($params, {wrap => $opt{wrap}}) . " ";
my $new_param = {};
$new_param->{$_} = [] for keys %{$params->[0]};
for my $param (@$params) {
push @{$new_param->{$_}}, $param->{$_} for keys %$param;
}
$params = [$new_param];
}
else {
$sql .= $self->values_clause($params->[0], {wrap => $opt{wrap}}) . " ";
}
# Execute query
if (@$params > 1) {
for my $param (@$params) {
$self->execute($sql, $param, %opt);
}
}
else {
$self->execute($sql, $params->[0], %opt);
}
}
sub update {
my $self = shift;
# Options
my $param = @_ % 2 ? shift : undef;
my %opt = @_;
$param ||= {};
# Don't allow update all rows
confess qq{update method where option must be specified } . _subname
if !$opt{where} && !defined $opt{id} && !$opt{allow_update_all};
# Created time and updated time
if (defined $opt{mtime}) {
$param = {%$param};
my $now = $self->now;
$now = $now->() if ref $now eq 'CODE';
$param->{$opt{mtime}} = $self->now->();
}
# Assign clause
my $assign_clause = $self->assign_clause($param, {wrap => $opt{wrap}});
# Where
my $where;
if (defined $opt{id}) {
$where = $self->_id_to_param($opt{id}, $opt{primary_key}, $opt{table}) ;
}
else {
$where = $opt{where};
}
my $w = $self->_where_clause_and_param($where);
# Merge update parameter with where parameter
$param = $self->merge_param($param, $w->{param});
# Update statement
my $sql = "update ";
$sql .= "$opt{prefix} " if defined $opt{prefix};
$sql .= $self->_tq($opt{table}) . " set $assign_clause $w->{clause} ";
# Execute query
$self->execute($sql, $param, %opt);
}
sub update_all { shift->update(@_, allow_update_all => 1) };
sub values_clause {
my ($self, $param, $opts) = @_;
my $wrap = $opts->{wrap} || {};
# Create insert parameter tag
my ($q, $p) = $self->_qp;
my $safety_character = $self->safety_character;
my @columns;
my @place_holders;
for my $column (sort keys %$param) {
confess qq{"$column" is not safety column name in values clause} . _subname
unless $column =~ /^[$safety_character\.]+$/;
push @columns, "$q$column$p";
push @place_holders, ref $param->{$column} eq 'SCALAR' ? ${$param->{$column}} :
$wrap->{$column} ? $wrap->{$column}->(":$column") :
":$column";
}
my $values_clause = '(' . join(', ', @columns) . ') values (' . join(', ', @place_holders) . ')';
return $values_clause;
}
sub assign_clause {
my ($self, $param, $opts) = @_;
my $wrap = $opts->{wrap} || {};
my ($q, $p) = $self->_qp;
my $safety_character = $self->safety_character;
my @set_values;
for my $column (sort keys %$param) {
confess qq{"$column" is not safety column name in assign clause} . _subname
unless $column =~ /^[$safety_character\.]+$/;
push @set_values, ref $param->{$column} eq 'SCALAR' ? "$q$column$p = " . ${$param->{$column}}
: $wrap->{$column} ? "$q$column$p = " . $wrap->{$column}->(":$column")
: "$q$column$p = :$column";
}
my $assign_clause = join(', ', @set_values);
return $assign_clause;
}
sub where { DBIx::Custom::Where->new(dbi => shift, @_) }
sub type_rule {
my $self = shift;
$self->{_type_rule_is_called} = 1;
if (@_) {
my $type_rule = ref $_[0] eq 'HASH' ? $_[0] : {@_};
lib/DBIx/Custom.pm view on Meta::CPAN
elsif (ref $where eq 'ARRAY') {
$obj = $self->where(clause => $where->[0], param => $where->[1], join => $where->[2]);
}
# Check where argument
confess qq{"where" must be hash reference or DBIx::Custom::Where object}
. qq{or array reference, which contains where clause and parameter}
. _subname
unless ref $obj eq 'DBIx::Custom::Where';
$w->{clause} = $obj->to_string;
$w->{param} = $obj->param;
$w->{join} = $obj->{join};
}
elsif ($where) {
$w->{clause} = "where $where";
}
return $w;
}
# DEPRECATED
our $AUTOLOAD;
sub AUTOLOAD {
my $self = shift;
_deprecate('0.39', "DBIx::Custom AUTOLOAD feature is DEPRECATED!");
# Method name
my ($package, $mname) = $AUTOLOAD =~ /^([\w\:]+)\:\:(\w+)$/;
# Call method
$self->{_methods} ||= {};
if (my $method = $self->{_methods}->{$mname}) {
return $self->$method(@_)
}
elsif ($self->{dbh} && (my $dbh_method = $self->dbh->can($mname))) {
$self->dbh->$dbh_method(@_);
}
else {
confess qq{Can't locate object method "$mname" via "$package" }
. _subname;
}
}
sub DESTROY {}
# DEPRECATED
sub helper {
my $self = shift;
_deprecate('0.39', "DBIx::Custom::helper method is DEPRECATED!");
# Register method
my $methods = ref $_[0] eq 'HASH' ? $_[0] : {@_};
$self->{_methods} = {%{$self->{_methods} || {}}, %$methods};
return $self;
}
# DEPRECATED
sub update_or_insert {
_deprecate('0.39', "DBIx::Custom::update_or_insert method is DEPRECATED!");
my ($self, $param, %opt) = @_;
confess "update_or_insert method need primary_key and id option "
unless defined $opt{id} && defined $opt{primary_key};
my $statement_opt = $opt{option} || {};
my $rows = $self->select(%opt, %{$statement_opt->{select} || {}})->all;
if (@$rows == 0) {
return $self->insert($param, %opt, %{$statement_opt->{insert} || {}});
}
elsif (@$rows == 1) {
return 0 unless keys %$param;
return $self->update($param, %opt, %{$statement_opt->{update} || {}});
}
else { confess "selected row must be one " . _subname }
}
# DEPRECATED
sub count {
_deprecate('0.39', "DBIx::Custom::count method is DEPRECATED!");
shift->select(column => 'count(*)', @_)->fetch_one->[0]
}
1;
=head1 NAME
DBIx::Custom - DBI extension to execute insert, update, delete, and select easily
=head1 SYNOPSIS
use DBIx::Custom;
# Connect
my $dbi = DBIx::Custom->connect(
"dbi:mysql:database=dbname",
'ken',
'!LFKD%$&',
{mysql_enable_utf8 => 1}
);
# Create model
$dbi->create_model('book');
# Insert
$dbi->model('book')->insert({title => 'Perl', author => 'Ken'});
# Update
$dbi->model('book')->update({title => 'Perl', author => 'Ken'}, where => {id => 5});
# Delete
$dbi->model('book')->delete(where => {author => 'Ken'});
# Select
my $result = $dbi->model('book')->select(['title', 'author'], where => {author => 'Ken'});
# Select, more complex
# select book.title as book.title,
( run in 0.686 second using v1.01-cache-2.11-cpan-600a1bdf6e4 )