【发布时间】:2010-01-23 02:11:50
【问题描述】:
使用CGI::Session::Auth::DBI 和CGI::Session::Auth 页面中的示例,我尝试实现_login 函数,但没有成功。我使用的是 Windows 7 和 Apache 2。
#!/usr/bin/perl -w
use strict;
use CGI::Carp qw(fatalsToBrowser);
use CGI;
use CGI::Session;
use CGI::Session::Auth::DBI;
my $cgi = new CGI;
# using '.' directory for testing
my $session = new CGI::Session(undef, $cgi, {Directory=>'.'});
my $auth = new CGI::Session::Auth::DBI({
CGI => $cgi,
Session => $session,
DSN => 'dbi:mysql:dbname=foobar:host=localhost',
DBUser => 'foo',
DBPasswd => 'bar',
UserTable => 'cgi_auth_user' # auth_user already in use
});
print "Content-type: text/html\n\n";
if ($auth->_login("admin", "admin")) {
print "<p>login ok</p>";
} else {
print "<p>login fail</p>";
}
if ($auth->loggedIn) {
print "<p>logged in; go to <a href='index.pl'>index</a></p>";
} else {
print "<p>not logged in</p>";
}
由此得到的渲染输出是:
login ok
not logged in
如果我将传递给_login 的值更改为“foo”、“bar”(无效的用户名/密码),那么我会得到这个渲染结果:
login fail
not logged in
我正在使用“。”只是为了测试,因为我知道这是我可以写的目录。每次我运行代码时,都会创建一个cgisess_ 文件(例如cgisess_9fb493cc9155ee9dd2b18fddc38139d8),但无论我是否使用正确的用户名,都会创建这个文件。没有返回任何错误,但 $auth->loggedIn 始终为 false。
文档说_login 是虚拟的,听起来 DBI 模块会覆盖它,但我不确定。
我做错了什么?
更新 1:
在调用$auth->loggedIn 之前,我也尝试过使用$auth->authenticate(),但这没有效果。成功登录后,我还尝试在另一个上使用$auth->authenticate() 和$auth->loggedIn,但我得到了相同的结果。不管我做什么,$auth->loggedI 总是假的。
更新 2:
我也尝试将目录更改为“/”,它所做的只是在 / 而不是当前目录中创建 cgisess 文件。
更新 3:
我认为这可能是数据库记录的问题;我正在使用示例页面中的默认示例,但修改了管理员密码。这是一个 phpMyAdmin 导出:
CREATE TABLE IF NOT EXISTS `cgi_auth_user` (
`userid` char(32) collate utf8_unicode_ci NOT NULL,
`username` varchar(30) collate utf8_unicode_ci NOT NULL,
`passwd` varchar(30) collate utf8_unicode_ci NOT NULL default '',
PRIMARY KEY (`userid`),
UNIQUE KEY `username` (`username`)
) ENGINE=MyISAM DEFAULT CHARSET=utf8 COLLATE=utf8_unicode_ci;
INSERT INTO `cgi_auth_user` (`userid`, `username`, `passwd`) VALUES
('325684ec1b028eaf562dd484c5607a65', 'admin', 'admin'),
('ef19a80d627b5c48728d388c11900f3f', 'guest', 'guest');
再一次,如果_login 使用有效的用户名和密码返回true,那么我会假设用户ID 是有效的......不是吗?
更新 4:
我也在我们的 Linux 生产服务器上对此进行了测试,我遇到了完全相同的问题。
【问题讨论】:
-
避免使用间接对象表示法(即
new CGI)。使用方法调用语法(即CGI->new)。见perldoc.perl.org/perlobj.html#Indirect-Object-Syntax和perlbuzz.com/mechanix/2008/02/… -
我只是查看了代码,并且 ::DBI 模块确实覆盖了_login。至于为什么您的代码不起作用:数据库设置了吗?你看过错误日志吗?可以打开调试吗?
-
是的,数据库已设置并正在运行;为了证明这一点,我更改为错误的数据库用户名并收到数据库错误。我应该使用
perl开关打开调试信息吗?我查看了--help,但我不了解调试部分;也许这应该是一个新问题? -
$auth->Log=1(来自阅读源代码)
-
您可以尝试使用 Perl 调试器运行它——我个人觉得它有点令人困惑。我想如果您可以从命令行运行 CGI 脚本,这是一个可行的选择。 Auth 模块确实有内置的调试语句 - 查看源代码。正如 ergosys 指出的那样,有一个 Log 标志(到
new)。我认为您可能还需要提供一个初始化的 Log4Perl 对象...抱歉,不是这些模块的专家(从未使用过它们)只是想提供帮助;-)
标签: perl authentication cgi