我在PostgreSQL系统上返回布尔值的查询:
my $sth = $dbh->prepare("select 'f'::boolean");
$sth->execute;
my @vals = $sth->fetchrow_array;
Run Code Online (Sandbox Code Playgroud)
根据DBD :: Pg文档,
PostgreSQL的当前实现返回“ t”为真,“ f”为假。从Perl的角度来看,这是一个非常不幸的选择。因此,DBD :: Pg以Perlish方式转换BOOL数据类型的结果:'f'变为数字0,'t'变为数字1。这样,应用程序不必检查特定于数据库的返回值数据类型为BOOL,因为Perl将0视为false,将1视为true。您可以根据需要将pg_bool_tf属性设置为true值,以将值更改回't'和'f'。
因此,只要pg_bool_tf返回0,它就应该返回0。但是,在JSON :: XS(和纯JSON)的过程中,会将返回的0解释为字符串:
use JSON::XS qw(encode_json);
my $options =
{
layout => 0,
show_widget_help => $vals[0] // 1,
};
die encode_json($options);
Run Code Online (Sandbox Code Playgroud)
...死于:
{“ layout”:0,“ show_widget_help”:“ 0”}
...那很好,除了我的JavaScript在那里期望布尔值,并且非空字符串“ 0”被评估为true。为什么后一个引用0,而前一个引用不呢?
根据JSON :: XS docs,这是一个主要功能:
往返完整性
当仅使用JSON支持的数据类型序列化perl数据结构时,反序列化的数据结构在Perl级别上是相同的。(例如,字符串“ 2.0”不会因为看起来像数字而突然变成“ 2”)。对此有一些例外,请阅读下面的“映射”部分以了解这些内容。
...表示:
简单的Perl标量(不是引用的任何标量)是最难编码的对象:JSON :: XS将未定义的标量编码为JSON空值,在编码为JSON字符串之前在字符串上下文中最后使用过的标量,以及其他任何数值。
但是我从不在字符串上下文中使用@vals [0]。也许DBD :: Pg在返回它之前将其布尔值0用作字符串?
我正在INSERT为一个尚不存在的数据库创建一组SQL 语句,我将它们保存到文件中.
如何在不访问特定数据库的情况下使用Perl强大的DBI模块来创建这些INSERT语句.特别是,看起来使用该$dbh->quote()函数需要我实例化$dbh与数据库的连接.
在处理持久的MySQL连接时,一个问题是它们在一定的超时(通常是28800秒)后被丢弃.DBIx :: Connector似乎完成了自动重新连接到已断开连接的工作,但它为每个SQL语句添加了更多Perl代码,这可能会让人讨厌.例如,而不是:
$dbh->do('DROP DATABASE stackoverflow');
Run Code Online (Sandbox Code Playgroud)
人们不得不说:
$conn->run(
fixup => sub {
my $dbh = shift;
$dbh->do('DROP DATABASE stackoverflow');
}
);
Run Code Online (Sandbox Code Playgroud)
假设一个人不需要交易.为什么要使用DBIx :: Connector而不是传递$ dbh - > {mysql_auto_reconnect} = 1,哪个也运行良好?
我在所有服务器上安装了Perl 5.8,并希望使用DBI和DBD :: Oracle模块来访问我们的数据库.我主要担心的是更新版本的perl DBI和DBD模块将停止使用5.8.然后我必须将每台服务器升级到最新的perl版本.
我的问题是perl本身成为更高版本,并且为他们开发的模块是否仍然可以向后兼容?"如果我创建文档说运行"cpan -i DBI",如果最新版本的DBI不能与5.8一起运行,那么"CPAN不会包含Perl的所有古老版本和补丁级别".
我正在尝试执行以下脚本:
#!/usr/bin/perl -w
use strict;
use DBI;
my $db = "Pg";
my $db_database = "whatever";
my $user = "whatever";
my $password = "whatever";
my $dbh = DBI->connect("dbi:$db:dbname=$db_database", $user, $password);
my $query = $dbh->prepare (q{SELECT
arrival_date - INTERVAL '? MINUTE'
FROM emails LIMIT 1})
or die ("unable to prepare");
$query->execute(60) or die("unable to execute");
print $query->fetchrow_array, "\n";
Run Code Online (Sandbox Code Playgroud)
(arrival_date具有以下格式:带时区的时间戳NOT NULL默认值CURRENT_TIMESTAMP)
问题是没有检测到问号占位符,因为它的内部单引号:
DBD::Pg::st execute failed: called with 1 bind variables when 0 are needed
Run Code Online (Sandbox Code Playgroud)
如果我使用qq {},$ 1占位符,并尝试使用$ dbh-> quote进行一些变化,则无效.我怎样才能做到这一点?
我有一个大型事务,包括从数据库A获取大量数据,对这些数据进行一些操作,然后将操纵数据插入数据库B.我只有在数据库A中选择的权限,但我可以创建表和在数据库B中插入/更新等
操作和插入部分用perl编写,并且已经用于从其他数据源将数据加载到数据库B中,因此所需要的只是从数据库A获取必要的数据并使用它来初始化perl类.
我怎样才能这样做,以便在操作或插入过程中发生任何错误(数据库断开,由于无效值导致的类初始化问题,硬盘故障等)时,我可以轻松跟踪并从错误发生的位置进行检索. .)?一次性完成事务似乎不是一个好的选择,因为来自数据库A的数据量意味着数据操作和插入数据库B需要至少一天或2天.
来自数据库A的数据可以使用唯一键分组到大约1000个组中,每个键包含1000个行.我认为我能做的一种方法是编写一个每组提交的脚本,这意味着我必须跟踪哪个组已经插入到数据库B中.我能想到的唯一方法是跟踪哪些组的进度是否处理过或者是在日志文件中还是在数据库B中的表中.我认为可以工作的第二种方法是转储加载类以进行操作和插入到flatfile所需的所有必要字段,读取文件以进行初始化这些类并插入到数据库B中.这也意味着我必须进行一些日志记录,但如果发生任何错误,应将其缩小到flatfile中的确切行.该脚本将如下所示:
use strict;
use warnings;
use DBI;
#connect to database A
my $dbh = DBI->connect('dbi:oracle:my_db', $user, $password, { RaiseError => 1, AutoCommit => 0 });
#statement to get data based on group unique key
my $sth = $dbh->prepare($my_sql);
my @groups; #I have a list of this already
open my $fh, '>>', 'my_logfile' or die "can't open logfile $!";
eval {
foreach my $g (@groups){
#subroutine to check if group has already been processed, either from log …Run Code Online (Sandbox Code Playgroud) 我收录了宝石,
dbd-mysql (0.4.4)
dbi (0.4.5)
mysql (2.8.1)
Run Code Online (Sandbox Code Playgroud)
在我运行以下代码时在rails控制台上,
require 'rubygems'
require "dbi"
require 'dbd-mysql'
dbh = DBI.connect("DBI:Mysql:TestDB:localhost","username", "pwd")
1.9.2-p180 :001 > require 'rubygems'
=> false
1.9.2-p180 :002 > require "dbi"
=> false
1.9.2p180 :003 > require 'dbd-mysql'
LoadError: no such file to load -- dbd-mysql
from /.rvm/gems/ruby-1.9.2-p180@rails3/gems/dbi-0.4.5/lib/dbi.rb:318:in `rescue in load_driver'
from /.rvm/gems/ruby-1.9.2-p180@rails3/gems/dbi-0.4.5/lib/dbi.rb:242:in `load_driver'
from /.rvm/gems/ruby-1.9.2-p180@rails3/gems/dbi-0.4.5/lib/dbi.rb:160:in `_get_full_driver'
from /.rvm/gems/ruby-1.9.2-p180@rails3/gems/dbi-0.4.5/lib/dbi.rb:145:in `connect'
from (irb):3
from /.rvm/gems/ruby-1.9.2-p180@rails3/gems/railties-3.1.1/lib/rails/commands/console.rb:45:in `start'
from /.rvm/gems/ruby-1.9.2-p180@rails3/gems/railties-3.1.1/lib/rails/commands/console.rb:8:in `start'
from /.rvm/gems/ruby-1.9.2-p180@rails3/gems/railties-3.1.1/lib/rails/commands.rb:40:in `<top (required)>'
from script/rails:6:in `require'
from script/rails:6:in `<main>'
1.9.2-p180 :004 > …Run Code Online (Sandbox Code Playgroud) 构造具有各种WHERE条件的sql的最佳方法是什么?我的解决方案看起来很难看
my ($where, @values);
if ($phone_number)
{
$where = 'AND pnone_number=?';
@values = ($from, $till, $phone_number);
}
else
{
$where = '';
@values = ($from, $till);
}
my $sql = 'SELECT * FROM calls WHERE time between ? AND ? '.$where.' ORDER BY time';
my $res = $dbh->selectall_arrayref($sql, undef, @values) or warn 'error';
Run Code Online (Sandbox Code Playgroud) 尝试使用Perl和DBI在PostgreSQL中设置一个值,从而设置DBD :: Pg.
我收到一个奇怪的错误.
2013-05-23 19:02:36.641139500 updating status to 0
2013-05-23 19:02:36.641410500 DBD::Pg::st execute failed: ERROR: syntax error at or near "$1"
2013-05-23 19:02:36.641418500 LINE 1: UPDATE instances SET $1 = $2
2013-05-23 19:02:36.641423500 ^ at /usr/lib/perl5/vendor_perl/Mitel/MslRest/mbg.pm line 161.
2013-05-23 19:02:36.642425500 [Thu May 23 19:02:36 2013] [error] DBD::Pg::st execute failed: ERROR: syntax error at or near "$1"
2013-05-23 19:02:36.642438500 LINE 1: UPDATE instances SET $1 = $2
2013-05-23 19:02:36.642443500 ^ at /usr/lib/perl5/vendor_perl/Mitel/MslRest/mbg.pm line 161.
2013-05-23 19:02:36.642447500
Run Code Online (Sandbox Code Playgroud)
相关代码是
my $sql = …Run Code Online (Sandbox Code Playgroud) 尝试运行DBI升级到El Capitan后使用的perl脚本时遇到以下错误(典型!):
install_driver(mysql) failed: Can't load '/Library/Perl/5.18/darwin-thread-multi-2level/auto/DBD/mysql/mysql.bundle' for module DBD::mysql: dlopen(/Library/Perl/5.18/darwin-thread-multi-2level/auto/DBD/mysql/mysql.bundle, 1): Library not loaded: libmysqlclient.18.dylib
Referenced from: /Library/Perl/5.18/darwin-thread-multi-2level/auto/DBD/mysql/mysql.bundle
Reason: unsafe use of relative rpath libmysqlclient.18.dylib in /Library/Perl/5.18/darwin-thread-multi-2level/auto/DBD/mysql/mysql.bundle with restricted binary at /System/Library/Perl/5.18/darwin-thread-multi-2level/DynaLoader.pm line 194.
Run Code Online (Sandbox Code Playgroud)
看到贴在Python中的类似问题的解决方案后,在这里我已经发布了以下的Perl相同的解决方案.