【问题标题】:Why does my Perl script fail to connect to the database?为什么我的 Perl 脚本无法连接到数据库?
【发布时间】:2012-05-13 07:21:39
【问题描述】:

我有一个从 MySQL 数据库检索数据的 Perl 脚本。这是代码:

sub startSession{
    my $self = shift;

    my $dsn = "dbi:".$self{platform}.":".$self{database}.":".$self{host}.":".$self{port};
    print "$dsn\n" ;
    $self{dbHandle} = DBI->connect($dsn,$user,$password);   
}

我提供了来自外部文件的所有信息。我收到错误消息

DBI connect('dbname:**.**.**.**:3306','',...) failed: Access denied for user 'root'@'dbserver' (using password: NO) at line 89

Can't call method "prepare" on an undefined value at at line 97

我很确定root可以从任何主机连接,而且密码也是正确的。

【问题讨论】:

  • 一个问题是$self{...}my $self = shift无关。您需要使用$self->{...}

标签: mysql perl dbi perl-module


【解决方案1】:

首先,您的直接问题是,正如@Sinan Ünür 所说,您需要将$self{platform} 更改为$self->{platform} 等。

您的第二个直接问题是您似乎从无处获得$user$password(它们没有传递给函数,因此除非它们是全局变量,否则它们是未定义的),这可以解释@987654325 @部分错误。也许那些应该是$self->{user}$self->{password}

您应该考虑将其放在模块的顶部,至少在开发期间,以自动捕获如下错误:

use warnings qw(all);
use strict;

但我还要评论,从设计的角度来看,您确实应该将 DSN 视为不透明的字符串。每个数据库都有自己的 DSN 格式。因此,如果您想要针对不同的数据库,您将需要不同的 DSN 格式。或者,可能有一天 MySQL 会使用不同的格式(它已经有两种格式)。无论哪种方式,在配置文件中将其更改为一个位置要比跟踪将各个部分连接在一起的每个位置要容易得多。

【讨论】:

  • 就像我在问题陈述中所说,userpassword 取自外部文件。
  • @user1304082:这就是你的想法。很明显,$user$password 甚至没有在你使用它们的范围内声明,如果你想帮助解决你的问题,你需要提供更多的上下文。
  • @user1304082 我已经澄清了我的答案。您还没有将 $user 和 $password 传递给函数(或者,如果有,则缺少 my $user = shift;my $password = shift; 行),因此除非它们是全局变量,否则它们是未定义的。 use strict 会抓住这个。
【解决方案2】:

我看到的警告的关键部分是“using password: NO”。检查密码是否设置正确。

【讨论】:

  • 我该怎么做?还有一件事,我什至没有名为'dbserver'的主机
  • 如果您为此打开 use strict;use warnings;,我敢打赌,它会比 SO 用户提供更多有关如何解决此问题的信息。
  • 它给了我这个警告Global symbol "$user" requires explicit package name at dbAdmin.pm line 27.Global symbol "$password" requires explicit package name at dbAdmin.pm line 27
  • 脚本中的某处,您需要有my $username = 'my_db_user';my $password = 'my_db_password';
  • 我这样做了,机器是全新安装的,你认为我在使用这个脚本之前需要在上面安装任何mysql驱动程序吗?
【解决方案3】:

大概,$self 是一个 hashref,而不是一个普通的 hash,你没有 warnings on。所以,打开它们,然后使用$self->{platform} 等。

【讨论】:

  • 这些是我收到的警告Global symbol "$user" requires explicit package name at dbAdmin.pm line 27. Global symbol "$password" requires explicit package name at dbAdmin.pm line 27
  • 非常正确,但 OP 的直接问题是对 DBI->connect 的调用失败。
  • 那么显然您的变量 $user 和 $password 没有从您提到的外部文件中设置。你是怎么做到的?
猜你喜欢
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2018-03-01
  • 2017-10-10
  • 1970-01-01
  • 2014-07-07
  • 1970-01-01
相关资源
最近更新 更多