[Zodb-checkins] CVS: ZODB3/ZEO - zpasswd.py:1.1.2.1
Exceptions.py:1.6.12.1 ServerStub.py:1.12.12.1
StorageServer.py:1.92.10.1 runzeo.py:1.12.10.1
Johan Dahlin
jdahlin at telia.com
Tue Apr 29 17:03:25 EDT 2003
Update of /cvs-repository/ZODB3/ZEO
In directory cvs.zope.org:/tmp/cvs-serv23889
Modified Files:
Tag: ZODB3-auth-branch
Exceptions.py ServerStub.py StorageServer.py runzeo.py
Added Files:
Tag: ZODB3-auth-branch
zpasswd.py
Log Message:
Initial checkin of AuthZEO (without SRP)
=== Added File ZODB3/ZEO/zpasswd.py ===
##############################################################################
#
# Copyright (c) 2003 Zope Corporation and Contributors.
# All Rights Reserved.
#
# This software is subject to the provisions of the Zope Public License,
# Version 2.0 (ZPL). A copy of the ZPL should accompany this distribution.
# THIS SOFTWARE IS PROVIDED "AS IS" AND ANY AND ALL EXPRESS OR IMPLIED
# WARRANTIES ARE DISCLAIMED, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
# WARRANTIES OF TITLE, MERCHANTABILITY, AGAINST INFRINGEMENT, AND FITNESS
# FOR A PARTICULAR PURPOSE
#
##############################################################################
"""Usage:
zpasswd [-cd] passwordfile username
zpasswd -b[cd] passwordfile username password
zpasswd -n[d] username
zpasswd -nb[d] username password
-c Create a new file.
-d Delete user
-n Don't update file; display results on stdout.
-b Use the password from the command line rather than prompting for it."""
import sys
import getopt
import getpass
from ZEO.auth.database import Database
#from ZEO.auth.srp import SRPDatabase
try:
opts, args = getopt.getopt(sys.argv[1:], 'cdnbs')
except getopt.GetoptError:
# print help information and exit:
print __doc__
sys.exit(2)
stdout = 0
create = 0
delete = 0
prompt = 1
#srp = 0
for opt, arg in opts:
if opt in ("-h", "--help"):
print __doc__
sys.exit()
if opt == "-n":
stdout = 1
if opt == "-c":
create = 1
if opt == "-d":
delete = 1
if opt == "b":
prompt = 0
# if opt == "-s":
# srp = 1
if create and delete:
print "Can't create and delete at the same time"
sys.exit(3)
if len(args) < 2:
print __doc__
sys.exit()
output = args[0]
username = args[1]
if not delete:
if len(args) > 3:
print __doc__
sys.exit()
if prompt:
password = getpass.getpass('Enter passphrase: ')
else:
password = args[2]
#if srp:
# db = SRPDatabase(output)
#else:
db = Database(output)
if create:
try:
db.add_user(username, password)
except LookupError:
print 'The username already exists'
sys.exit(4)
if stdout:
db.save(fd=sys.stdout)
else:
db.save()
if delete:
try:
db.del_user(username)
except LockupError:
print 'The username doesn\'t exist'
sys.exit(5)
if stdout:
db.save(fd=sys.stdout)
else:
db.save()
=== ZODB3/ZEO/Exceptions.py 1.6 => 1.6.12.1 ===
--- ZODB3/ZEO/Exceptions.py:1.6 Wed Jan 15 13:19:15 2003
+++ ZODB3/ZEO/Exceptions.py Tue Apr 29 16:02:54 2003
@@ -24,3 +24,5 @@
class ClientDisconnected(ClientStorageError):
"""The database storage is disconnected from the storage."""
+class AuthError(StorageError):
+ """The client provided invalid authentication credentials."""
=== ZODB3/ZEO/ServerStub.py 1.12 => 1.12.12.1 ===
--- ZODB3/ZEO/ServerStub.py:1.12 Tue Jan 14 14:08:33 2003
+++ ZODB3/ZEO/ServerStub.py Tue Apr 29 16:02:54 2003
@@ -1,6 +1,6 @@
##############################################################################
#
-# Copyright (c) 2001, 2002 Zope Corporation and Contributors.
+# Copyright (c) 2001, 2002, 2003 Zope Corporation and Contributors.
# All Rights Reserved.
#
# This software is subject to the provisions of the Zope Public License,
@@ -45,6 +45,9 @@
def get_info(self):
return self.rpc.call('get_info')
+ def getAuthProtocol(self):
+ return self.rpc.call('getAuthProtocol')
+
def lastTransaction(self):
# Not in protocol version 2.0.0; see __init__()
return self.rpc.call('lastTransaction')
=== ZODB3/ZEO/StorageServer.py 1.92 => 1.92.10.1 ===
--- ZODB3/ZEO/StorageServer.py:1.92 Mon Jan 20 16:26:31 2003
+++ ZODB3/ZEO/StorageServer.py Tue Apr 29 16:02:54 2003
@@ -1,6 +1,6 @@
##############################################################################
#
-# Copyright (c) 2001, 2002 Zope Corporation and Contributors.
+# Copyright (c) 2001, 2002, 2003 Zope Corporation and Contributors.
# All Rights Reserved.
#
# This software is subject to the provisions of the Zope Public License,
@@ -31,6 +31,7 @@
from ZEO import ClientStub
from ZEO.CommitLog import CommitLog
+from ZEO.auth.database import Database
from ZEO.monitor import StorageStats, StatsServer
from ZEO.zrpc.server import Dispatcher
from ZEO.zrpc.connection import ManagedServerConnection, Delay, MTDelay
@@ -161,6 +162,8 @@
"""Select the storage that this client will use
This method must be the first one called by the client.
+ For authenticated storages this method will be called by the client
+ immediately after authentication is finished.
"""
if self.storage is not None:
self.log("duplicate register() call")
@@ -410,6 +413,15 @@
else:
return self._wait(lambda: self._vote())
+ def getAuthProtocol(self):
+ """Return string specifying name of authentication module to use.
+
+ The module name should be auth_%s where %s is auth_protocol."""
+ protocol = self.server.auth_protocol
+ if not protocol or protocol == 'none':
+ return None
+ return protocol
+
def abortVersion(self, src, id):
self._check_tid(id, exc=StorageTransactionError)
if self.locked:
@@ -577,7 +589,9 @@
def __init__(self, addr, storages, read_only=0,
invalidation_queue_size=100,
transaction_timeout=None,
- monitor_address=None):
+ monitor_address=None,
+ auth_protocol=None,
+ auth_filename=None):
"""StorageServer constructor.
This is typically invoked from the start.py script.
@@ -618,7 +632,22 @@
monitor_address -- The address at which the monitor server
should listen. If specified, a monitor server is started.
The monitor server provides server statistics in a simple
- text format.
+ text format.
+
+ auth_protocol -- The name of the authentication protocol to use.
+ Examples are "plaintext", "sha" and "srp".
+
+ auth_filename -- The name of the password database filename.
+ It should be in a format compatible with the authentication
+ protocol used; for instance, "sha" and "srp" require different
+ formats.
+
+ Note that to implement an authentication protocol, a server
+ and client authentication mechanism must be implemented in a
+ auth_* module, which should be stored inside the "auth"
+ subdirectory. This module may also define a DatabaseClass
+ variable that should indicate what database should be used
+ by the authenticator.
"""
self.addr = addr
@@ -633,6 +662,10 @@
for s in storages.values():
s._waiting = []
self.read_only = read_only
+ self.auth_protocol = auth_protocol
+ self.auth_filename = auth_filename
+ if auth_protocol:
+ self._setup_auth(auth_protocol)
# A list of at most invalidation_queue_size invalidations
self.invq = []
self.invq_bound = invalidation_queue_size
@@ -654,7 +687,43 @@
self.monitor = StatsServer(monitor_address, self.stats)
else:
self.monitor = None
+
+ def _setup_auth(self, protocol):
+ # Load the auth protocol
+ fullname = 'ZEO.auth.auth_' + protocol
+ try:
+ module = __import__(fullname, globals(), locals(), protocol)
+ except ImportError:
+ log("%s: no such an auth protocol: %s" %
+ (self.__class__.__name__, protocol))
+ self.auth_protocol = None
+ return
+
+ from ZEO.auth.storage import AuthZEOStorage
+
+ # And set up ZEOStorageClass
+ klass = getattr(module, 'StorageClass', None)
+ if not klass or not issubclass(klass, AuthZEOStorage):
+ log(("%s: %s is not a valid auth protocol, must have a " + \
+ "StorageClass class") % (self.__class__.__name__, protocol))
+ self.auth_protocol = None
+ return
+ self.ZEOStorageClass = klass
+ log("%s: using auth protocol: %s" % \
+ (self.__class__.__name__, protocol))
+
+ dbklass = getattr(module, 'DatabaseClass', None)
+ if not dbklass:
+ dbklass = Database
+
+ # We create a Database instance here for use with the authenticator
+ # modules. Having one instance allows it to be shared between multiple
+ # storages, avoiding the need to bloat each with a new authenticator
+ # Database that would contain the same info, and also avoiding any
+ # possibly synchronization issues between them.
+ self.database = dbklass(self.auth_filename)
+
def new_connection(self, sock, addr):
"""Internal: factory to create a new connection.
@@ -663,6 +732,8 @@
connection.
"""
z = self.ZEOStorageClass(self, self.read_only)
+ if self.auth_protocol:
+ z.set_database(self.database)
c = self.ManagedServerConnectionClass(sock, addr, z, self)
log("new connection %s: %s" % (addr, `c`))
return c
=== ZODB3/ZEO/runzeo.py 1.12 => 1.12.10.1 ===
--- ZODB3/ZEO/runzeo.py:1.12 Fri Jan 24 17:37:20 2003
+++ ZODB3/ZEO/runzeo.py Tue Apr 29 16:02:54 2003
@@ -1,7 +1,7 @@
#!python
##############################################################################
#
-# Copyright (c) 2001, 2002 Zope Corporation and Contributors.
+# Copyright (c) 2001, 2002, 2003 Zope Corporation and Contributors.
# All Rights Reserved.
#
# This software is subject to the provisions of the Zope Public License,
@@ -89,7 +89,9 @@
"t:", "timeout=", float)
self.add("monitor_address", "zeo.monitor_address", "m:", "monitor=",
self.handle_monitor_address)
-
+ self.add('auth_protocol', 'zeo.auth_protocol', None,
+ 'auth-protocol=', default=None)
+ self.add('auth_filename', 'zeo.auth_filename', None, 'auth-filename=')
class ZEOOptions(ZDOptions, ZEOOptionsMixin):
@@ -189,7 +191,9 @@
read_only=self.options.read_only,
invalidation_queue_size=self.options.invalidation_queue_size,
transaction_timeout=self.options.transaction_timeout,
- monitor_address=self.options.monitor_address)
+ monitor_address=self.options.monitor_address,
+ auth_protocol=self.options.auth_protocol,
+ auth_filename=self.options.auth_filename)
def loop_forever(self):
import ThreadedAsync.LoopCallback
More information about the Zodb-checkins
mailing list