Some more minor corrections to get it to run as well as compile... (removes some XXX comments and adds some error checking)

This commit is contained in:
ian%hixie.ch 2001-06-03 15:27:16 +00:00
Родитель f71bddbcc2
Коммит 17da5d7b8a
6 изменённых файлов: 59 добавлений и 255 удалений

Просмотреть файл

@ -48,8 +48,12 @@ sub getUserByUsername {
my($app, $username) = @_;
# decent databases can do this in one go. Those that can't can do
# it in a generic two-step process:
return $self->getUserByID($app, $self->getUserIDByUsername($app, $username));
# XXX no error checking! if getUserID... return undef, return ()!
my $userID = $self->getUserIDByUsername($app, $username);
if (defined($userID)) {
return $self->getUserByID($app, $userID);
} else {
return ();
}
# return the same as getUserByID()
}
@ -65,8 +69,12 @@ sub getUserByContactDetails {
my($app, $contactName, $address) = @_;
# decent databases can do this in one go. Those that can't can do
# it in a generic two-step process:
return $self->getUserByID($app, $self->getUserIDByContactDetails($app, $contactName, $address));
# XXX no error checking! if getUserID... return undef, return ()!
my $userID = $self->getUserIDByContactDetails($app, $contactName, $address);
if (defined($userID)) {
return $self->getUserByID($app, $userID);
} else {
return ();
}
# return the same as getUserByID()
}

Просмотреть файл

@ -45,25 +45,33 @@ sub getUserIDByUsername {
# example, for the field 'contact.icq', the type data field might
# contain the string 'ICQ:' and the user field might be '55378571'
# making the username 'ICQ:55378571'.
return $self->database($app)->execute('SELECT userData.userID
FROM userData, userDataTypes
WHERE userData.fieldID = userDataTypes.fieldID
AND userDataTypes.category = \'contact\'
AND CONCAT(userDataTypes.data, userData.data) = ?', $username)->row->[0];
# XXX no error checking!
my $row = $self->database($app)->execute('SELECT userData.userID
FROM userData, userDataTypes
WHERE userData.fieldID = userDataTypes.fieldID
AND userDataTypes.category = \'contact\'
AND CONCAT(userDataTypes.data, userData.data) = ?', $username)->row;
if (defined($row)) {
return $row->[0];
} else {
return undef;
}
# return userID or undef
}
sub getUserIDByContactDetails {
my $self = shift;
my($app, $contactName, $address) = @_;
return $self->database($app)->execute('SELECT userData.userID
FROM userData, userDataTypes
WHERE userData.fieldID = userDataTypes.fieldID
AND userDataTypes.category = \'contact\'
AND userDataTypes.name = ?
AND userData.data = ?', $contactName, $address)->row->[0];
# XXX no error checking!
my $row = $self->database($app)->execute('SELECT userData.userID
FROM userData, userDataTypes
WHERE userData.fieldID = userDataTypes.fieldID
AND userDataTypes.category = \'contact\'
AND userDataTypes.name = ?
AND userData.data = ?', $contactName, $address)->row;
if (defined($row)) {
return $row->[0];
} else {
return undef;
}
# return userID or undef
}
@ -218,8 +226,13 @@ sub getGroups {
sub getGroupName {
my $self = shift;
my($app, $groupID) = @_;
return $self->database($app)->execute('SELECT name FROM groups WHERE groupID = ?', $groupID)->row->[0];
# return name
my $row = $self->database($app)->execute('SELECT name FROM groups WHERE groupID = ?', $groupID)->row;
if (defined($row)) {
return $row->[0];
} else {
return undef;
}
# return name or undef
}
sub setGroup {
@ -271,7 +284,13 @@ sub addRight {
sub getRightID {
my $self = shift;
my($app, $name) = @_;
return $self->database($app)->execute('SELECT rightID FROM rights WHERE name = ?', $name)->row->[0];
my $row = $self->database($app)->execute('SELECT rightID FROM rights WHERE name = ?', $name)->row;
if (defined($row)) {
return $row->[0];
} else {
return undef;
}
# return rightID or undef
}
sub setupInstall {
@ -286,11 +305,11 @@ sub setupInstall {
CREATE TABLE user (
userID integer unsigned auto_increment NOT NULL PRIMARY KEY,
password varchar(255) NOT NULL,
mode integer unsigned DEFAULT 0,
mode integer unsigned NOT NULL DEFAULT 0,
adminMessage varchar(255),
newFieldID integer unsigned,
newFieldValue varchar(255),
newFieldKey varchar(255),
newFieldKey varchar(255)
)
');
# +-------------------+
@ -338,7 +357,7 @@ sub setupInstall {
name varchar(64) NOT NULL,
type varchar(64) NOT NULL,
data text,
mode integer unsigned DEFAULT 0,
mode integer unsigned NOT NULL DEFAULT 0,
UNIQUE KEY (category, name)
)
');

Просмотреть файл

@ -101,6 +101,11 @@ sub createResultsFrame {
my($statement, $execute, @values) = @_;
$self->assert($self->handle, 1, 'No database handle: '.(defined($self->errstr) ? $self->errstr : 'unknown error'));
my $handle = $self->handle->prepare($statement);
# untaint the values... (XXX?)
foreach my $value (@values) {
$value =~ /^(.*)$/os;
$value = $1;
}
if ($handle and ((not defined($execute)) or $handle->execute(@values))) {
return PLIF::Database::ResultsFrame::DBI->create($handle, $self, $execute);
} else {

Просмотреть файл

@ -74,7 +74,8 @@ sub getArguments {
# Returns the values given for that argument if it already exists,
# otherwise undef. In a scalar context, returns the first value (or
# undef if the argument was never given). In an array context, returns
# all the values given.
# all the values given. (i.e., the same as getArgument but without the
# implicit call to createArgument)
sub peekArgument {
my $self = shift;
my($argument) = @_;
@ -151,7 +152,7 @@ sub propertyGet {
if ($self->SUPER::propertyExists(@_)) {
return $self->SUPER::propertyGet(@_);
} else {
return $self->getArgument(@_); # XXX assumes that return propagates wantarray context...
return $self->peekArgument(@_); # XXX assumes that return propagates wantarray context...
# if not:
# my @result = $self->getArgument(@_);
# if (wantarray) {

Просмотреть файл

@ -1,229 +0,0 @@
# -*- Mode: perl; tab-width: 4; indent-tabs-mode: nil; -*-
#
# This file is MPL/GPL dual-licensed under the following terms:
#
# The contents of this file are subject to the Mozilla Public License
# Version 1.1 (the "License"); you may not use this file except in
# compliance with the License. You may obtain a copy of the License at
# http://www.mozilla.org/MPL/
#
# Software distributed under the License is distributed on an "AS IS"
# basis, WITHOUT WARRANTY OF ANY KIND, either express or implied. See
# the License for the specific language governing rights and
# limitations under the License.
#
# The Original Code is PLIF 1.0.
# The Initial Developer of the Original Code is Ian Hickson.
#
# Alternatively, the contents of this file may be used under the terms
# of the GNU General Public License Version 2 or later (the "GPL"), in
# which case the provisions of the GPL are applicable instead of those
# above. If you wish to allow use of your version of this file only
# under the terms of the GPL and not to allow others to use your
# version of this file under the MPL, indicate your decision by
# deleting the provisions above and replace them with the notice and
# other provisions required by the GPL. If you do not delete the
# provisions above, a recipient may use your version of this file
# under either the MPL or the GPL.
package PLIF::Service::Login;
use strict;
use vars qw(@ISA);
use PLIF::Service;
@ISA = qw(PLIF::Service);
1;
sub provides {
my $class = shift;
my($service) = @_;
return ($service eq 'input.verify' or
$service eq 'input.verify.user.generic' or
$service eq 'user.login' or
$service eq 'dispatcher.commands' or
$service eq 'dispatcher.output.generic' or
$service eq 'dataSource.strings.default' or
$class->SUPER::provides($service));
}
# input.verify
sub verifyInput {
my $self = shift;
my($app) = @_;
# let's see if there are any protocol-specific user authenticators
my @result = $app->getSelectingServiceList('input.verify.user.'.$app->input->defaultOutputProtocol)->authenticateUser($app);
if (not @result) {
# ok, let's try the generic authenticators...
@result = $app->getSelectingServiceList('input.verify.user.generic')->authenticateUser($app);
}
# now let's see what that gave us
if (@result) {
# horrah, somebody knew what to do!
if (defined($result[0])) {
$app->addObject($result[0]); # they will have returned a user object
} else {
# hmm, so apparently user is not authentic
return $self; # supports user.login (reportInputVerificationError)
}
}
return; # nope, nothing to see here... (no error, anyway)
}
# input.verify.user.generic
sub authenticateUser {
my $self = shift;
my($app) = @_;
if (defined($app->input->username)) {
return $app->getService('user.factory')->getUserByCredentials($app, $app->input->username, $app->input->password);
} else {
return; # return nothing (not undef)
}
}
# input.verify
sub reportInputVerificationError {
my $self = shift;
my($app) = @_;
$app->output->loginFailed(1); # 1 means 'invalid username/password'
}
# dispatcher.commands
sub cmdSendPassword {
my $self = shift;
my($app) = @_;
my $protocol = $app->input->getAttribute('protocol');
my $address = $app->input->getAttribute('address');
if (defined($protocol) and defined($address)) {
my $user = $app->getService('user.factory')->getUserByContactDetails($app, $protocol, $address);
my $password;
if (defined($user)) {
$password = $self->changePassword($app, $user);
} else {
($user, $password) = $self->createUser($app, $protocol, $address);
}
$self->sendPassword($app, $user, $protocol, $password);
} else {
$app->output->loginFailed(0); # 0 means 'no username/password'
}
}
# user.login
sub hasRight {
my $self = shift;
my($app, $right) = @_;
my $user = $app->getObject('user');
if (defined($user)) {
if ($user->hasRight($right)) {
return $user;
} else {
$app->output->loginInsufficient($right);
}
} else {
$self->requireLogin($app);
}
return undef;
}
# user.login
# this assumes user is not logged in
sub requireLogin {
my $self = shift;
my($app) = @_;
my $address = $app->input->address;
if (defined($address) and not defined($app->getService('user.factory')->getUserByContactDetails($app, $app->input->protocol, $address))) {
my($user, $password) = $self->createUser($app, $app->input->protocol, $address);
$self->sendPassword($app, $user, $app->input->protocol, $password);
} else {
$app->output->loginFailed(0);
}
}
# dispatcher.output.generic
sub outputLoginInsufficient {
my $self = shift;
my($app, $output, $right) = @_;
$output->output(undef, 'loginAccessDenied', {
'right' => $right,
});
}
# dispatcher.output.generic
sub outputLoginFailed {
my $self = shift;
my($app, $output, $tried) = @_;
$output->output(undef, 'loginFailed', {
'tried' => $tried,
});
}
# dispatcher.output.generic
sub outputLoginDetailsSent {
my $self = shift;
my($app, $output, $address, $protocol) = @_;
$output->output(undef, 'loginDetailsSent', {
'address' => $address,
'protocol' => $protocol,
});
}
# dispatcher.output.generic
sub outputLoginDetails {
my $self = shift;
my($app, $output, $username, $password) = @_;
$output->output(undef, 'loginDetails', {
'username' => $username,
'password' => $password,
});
}
# dataSource.strings.default
sub getDefaultString {
my $self = shift;
my($app, $protocol, $string) = @_;
if ($protocol eq 'stdout') {
if ($string eq 'loginAccessDenied') {
return '<text>Access Denied<br/></text>';
} elsif ($string eq 'loginFailed') {
return '<text><if lvalue="(data.tried)" condition="=" rvalue="1">Wrong username or password.</if><else>You must give your username or password.</else><br/><!-- XXX offer to create an account or send the password --><br/></text>';
} elsif ($string eq 'loginDetailsSent') {
return '<text>Login details were sent. (Protocol: <text variable="(data.protocol)"/>; Address: <text variable="(data.address)"/>)<br/></text>';
}
} elsif ($protocol eq 'http') {
if ($string eq 'loginAccessDenied') {
return '<text>HTTP/1.1 401 Access Denied<br/>Content-Type: text/plain<br/><br/>Access Denied</text>';
} elsif ($string eq 'loginFailed') {
return '<text>HTTP/1.1 401 Login Required<br/>WWW-Authenticate: Basic realm="<text variable="(data.app.name)"/>"<br/>Content-Type: text/plain<br/><br/><if lvalue="(data.tried)" condition="=" rvalue="1">Wrong username or password.</if><else>You must give your username or password.</else><br/><!-- XXX offer to create an account or send the password --></text>';
} elsif ($string eq 'loginDetailsSent') {
return '<text>HTTP/1.1 200 OK<br/>Content-Type: text/plain<br/><br/>Login details were sent.<br/>Protocol: <text variable="(data.protocol)"/><br/>Address: <text variable="(data.address)"/>)</text>';
}
}
return; # nope, sorry
}
# internal routines
sub changePassword {
my $self = shift;
my($app, $user) = @_;
my($password, $crypt) = $app->getService('service.passwords')->newPassword();
$user->password($crypt);
return $password;
}
sub createUser {
my $self = shift;
my($app, $protocol, $address) = @_;
my($password, $crypt) = $app->getService('service.passwords')->newPassword();
my $user = $app->getService('user.factory')->getNewUser($app, $crypt);
$user->getField('contact', $protocol)->data($address);
return ($user, $password);
}
sub sendPassword {
my $self = shift;
my($app, $user, $protocol, $password) = @_;
my $field = $user->hasField('contact', $protocol);
$self->assert(defined($field), 1, 'Tried to send a password using a protocol that the user has no mention of!'); # XXX grammar... :-)
$app->output($protocol, $user)->loginDetails($app, $field->username, $password);
$app->output->loginDetailsSent($app, $field->address, $protocol);
}

Просмотреть файл

@ -53,7 +53,7 @@ sub getUserByCredentials {
my $self = shift;
my($app, $username, $password) = @_;
my $object = $self->getUserByUsername($app, $username);
if ($object->checkPassword($password)) {
if (defined($object) and ($object->checkPassword($password))) {
return $object;
} else {
return undef;