diff --git a/ZopeProducts/README b/ZopeProducts/README deleted file mode 100644 index 74226803..00000000 --- a/ZopeProducts/README +++ /dev/null @@ -1,5 +0,0 @@ - - Produits Zope2 anciens et adaptes pour ScoDoc - -E. Viennet 2013 - diff --git a/ZopeProducts/ZPsycopgDA/DA.py b/ZopeProducts/ZPsycopgDA/DA.py deleted file mode 100644 index 723a6880..00000000 --- a/ZopeProducts/ZPsycopgDA/DA.py +++ /dev/null @@ -1,372 +0,0 @@ -# ZPsycopgDA/DA.py - ZPsycopgDA Zope product: Database Connection -# -# Copyright (C) 2004-2010 Federico Di Gregorio -# -# psycopg2 is free software: you can redistribute it and/or modify it -# under the terms of the GNU Lesser General Public License as published -# by the Free Software Foundation, either version 3 of the License, or -# (at your option) any later version. -# -# psycopg2 is distributed in the hope that it will be useful, but WITHOUT -# ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or -# FITNESS FOR A PARTICULAR PURPOSE. See the GNU Lesser General Public -# License for more details. - -# Import modules needed by _psycopg to allow tools like py2exe to do -# their work without bothering about the module dependencies. - - -import sys -import time -import db -import re - -import Acquisition -import Shared.DC.ZRDB.Connection - -from db import DB -from Globals import HTMLFile -from ExtensionClass import Base -from App.Dialogs import MessageDialog -from DateTime import DateTime - -# ImageFile is deprecated in Zope >= 2.9 -try: - from App.ImageFile import ImageFile -except ImportError: - # Zope < 2.9. If PIL's installed with a .pth file, we're probably - # hosed. - from ImageFile import ImageFile - -# import psycopg and functions/singletons needed for date/time conversions - -import psycopg2 -from psycopg2 import NUMBER, STRING, ROWID, DATETIME -from psycopg2.extensions import INTEGER, LONGINTEGER, FLOAT, BOOLEAN, DATE -from psycopg2.extensions import TIME, INTERVAL -from psycopg2.extensions import new_type, register_type - - -# add a new connection to a folder - -manage_addZPsycopgConnectionForm = HTMLFile('dtml/add',globals()) - -def manage_addZPsycopgConnection(self, id, title, connection_string, - zdatetime=None, tilevel=2, - encoding='', check=None, REQUEST=None): - """Add a DB connection to a folder.""" - self._setObject(id, Connection(id, title, connection_string, - zdatetime, check, tilevel, encoding)) - if REQUEST is not None: return self.manage_main(self, REQUEST) - - -# the connection object - -class Connection(Shared.DC.ZRDB.Connection.Connection): - """ZPsycopg Connection.""" - _isAnSQLConnection = 1 - - id = 'Psycopg2_database_connection' - database_type = 'Psycopg2' - meta_type = title = 'Z Psycopg 2 Database Connection' - icon = 'misc_/conn' - - def __init__(self, id, title, connection_string, - zdatetime, check=None, tilevel=2, encoding='UTF-8'): - self.zdatetime = zdatetime - self.id = str(id) - self.edit(title, connection_string, zdatetime, - check=check, tilevel=tilevel, encoding=encoding) - - def factory(self): - return DB - - ## connection parameters editing ## - - def edit(self, title, connection_string, - zdatetime, check=None, tilevel=2, encoding='UTF-8'): - self.title = title - self.connection_string = connection_string - self.zdatetime = zdatetime - self.tilevel = tilevel - self.encoding = encoding - - if check: self.connect(self.connection_string) - - manage_properties = HTMLFile('dtml/edit', globals()) - - def manage_edit(self, title, connection_string, - zdatetime=None, check=None, tilevel=2, encoding='UTF-8', - REQUEST=None): - """Edit the DB connection.""" - self.edit(title, connection_string, zdatetime, - check=check, tilevel=tilevel, encoding=encoding) - if REQUEST is not None: - msg = "Connection edited." - return self.manage_main(self,REQUEST,manage_tabs_message=msg) - - def connect(self, s): - try: - self._v_database_connection.close() - except: - pass - - # check psycopg version and raise exception if does not match - check_psycopg_version(psycopg2.__version__) - - self._v_connected = '' - dbf = self.factory() - - # TODO: let the psycopg exception propagate, or not? - self._v_database_connection = dbf( - self.connection_string, self.tilevel, self.get_type_casts(), self.encoding) - self._v_database_connection.open() - self._v_connected = DateTime() - - return self - - def get_type_casts(self): - # note that in both cases order *is* important - if self.zdatetime: - return ZDATETIME, ZDATE, ZTIME - else: - return DATETIME, DATE, TIME - - ## browsing and table/column management ## - - manage_options = Shared.DC.ZRDB.Connection.Connection.manage_options - # + ( - # {'label': 'Browse', 'action':'manage_browse'},) - - #manage_tables = HTMLFile('dtml/tables', globals()) - #manage_browse = HTMLFile('dtml/browse', globals()) - - info = None - - def table_info(self): - return self._v_database_connection.table_info() - - - def __getitem__(self, name): - if name == 'tableNamed': - if not hasattr(self, '_v_tables'): self.tpValues() - return self._v_tables.__of__(self) - raise KeyError, name - - def tpValues(self): - res = [] - conn = self._v_database_connection - for d in conn.tables(rdb=0): - try: - name = d['TABLE_NAME'] - b = TableBrowser() - b.__name__ = name - b._d = d - b._c = c - try: - b.icon = table_icons[d['TABLE_TYPE']] - except: - pass - r.append(b) - except: - pass - return res - -def check_psycopg_version(version): - """ - Check that the psycopg version used is compatible with the zope adpter. - """ - try: - m = re.match(r'\d+\.\d+(\.\d+)?', version.split(' ')[0]) - tver = tuple(map(int, m.group().split('.'))) - except: - raise ImportError("failed to parse psycopg version %s" % version) - - if tver < (2, 4): - raise ImportError("psycopg version %s is too old" % version) - - if tver in ((2,4,2), (2,4,3)): - raise ImportError("psycopg version %s is known to be buggy" % version) - - -## database connection registration data ## - -classes = (Connection,) - -meta_types = ({'name':'Z Psycopg 2 Database Connection', - 'action':'manage_addZPsycopgConnectionForm'},) - -folder_methods = { - 'manage_addZPsycopgConnection': manage_addZPsycopgConnection, - 'manage_addZPsycopgConnectionForm': manage_addZPsycopgConnectionForm} - -__ac_permissions__ = ( - ('Add Z Psycopg Database Connections', - ('manage_addZPsycopgConnectionForm', 'manage_addZPsycopgConnection')),) - -# add icons - -misc_={'conn': ImageFile('icons/DBAdapterFolder_icon.gif', globals())} - -for icon in ('table', 'view', 'stable', 'what', 'field', 'text', 'bin', - 'int', 'float', 'date', 'time', 'datetime'): - misc_[icon] = ImageFile('icons/%s.gif' % icon, globals()) - - -## zope-specific psycopg typecasters ## - -# convert an ISO timestamp string from postgres to a Zope DateTime object -def _cast_DateTime(iso, curs): - if iso: - if iso in ['-infinity', 'infinity']: - return iso - else: - return DateTime(iso) - -# convert an ISO date string from postgres to a Zope DateTime object -def _cast_Date(iso, curs): - if iso: - if iso in ['-infinity', 'infinity']: - return iso - else: - return DateTime(iso) - -# Convert a time string from postgres to a Zope DateTime object. -# NOTE: we set the day as today before feeding to DateTime so -# that it has the same DST settings. -def _cast_Time(iso, curs): - if iso: - if iso in ['-infinity', 'infinity']: - return iso - else: - return DateTime(time.strftime('%Y-%m-%d %H:%M:%S', - time.localtime(time.time())[:3]+ - time.strptime(iso[:8], "%H:%M:%S")[3:])) - -# NOTE: we don't cast intervals anymore because they are passed -# untouched to Zope. -def _cast_Interval(iso, curs): - return iso - -ZDATETIME = new_type((1184, 1114), "ZDATETIME", _cast_DateTime) -ZINTERVAL = new_type((1186,), "ZINTERVAL", _cast_Interval) -ZDATE = new_type((1082,), "ZDATE", _cast_Date) -ZTIME = new_type((1083,), "ZTIME", _cast_Time) - - -## table browsing helpers ## - -class TableBrowserCollection(Acquisition.Implicit): - pass - -class Browser(Base): - def __getattr__(self, name): - try: - return self._d[name] - except KeyError: - raise AttributeError, name - -class values: - def len(self): - return 1 - - def __getitem__(self, i): - try: - return self._d[i] - except AttributeError: - pass - self._d = self._f() - return self._d[i] - -class TableBrowser(Browser, Acquisition.Implicit): - icon = 'what' - Description = check = '' - info = HTMLFile('table_info', globals()) - menu = HTMLFile('table_menu', globals()) - - def tpValues(self): - v = values() - v._f = self.tpValues_ - return v - - def tpValues_(self): - r=[] - tname=self.__name__ - for d in self._c.columns(tname): - b=ColumnBrowser() - b._d=d - try: b.icon=field_icons[d['Type']] - except: pass - b.TABLE_NAME=tname - r.append(b) - return r - - def tpId(self): return self._d['TABLE_NAME'] - def tpURL(self): return "Table/%s" % self._d['TABLE_NAME'] - def Name(self): return self._d['TABLE_NAME'] - def Type(self): return self._d['TABLE_TYPE'] - - manage_designInput=HTMLFile('designInput',globals()) - def manage_buildInput(self, id, source, default, REQUEST=None): - "Create a database method for an input form" - args=[] - values=[] - names=[] - columns=self._columns - for i in range(len(source)): - s=source[i] - if s=='Null': continue - c=columns[i] - d=default[i] - t=c['Type'] - n=c['Name'] - names.append(n) - if s=='Argument': - values.append("'" % - (n, vartype(t))) - a='%s%s' % (n, boboType(t)) - if d: a="%s=%s" % (a,d) - args.append(a) - elif s=='Property': - values.append("'" % - (n, vartype(t))) - else: - if isStringType(t): - if find(d,"\'") >= 0: d=join(split(d,"\'"),"''") - values.append("'%s'" % d) - elif d: - values.append(str(d)) - else: - raise ValueError, ( - 'no default was given for %s' % n) - -class ColumnBrowser(Browser): - icon='field' - - def check(self): - return ('\t' % - (self.TABLE_NAME, self._d['Name'])) - def tpId(self): return self._d['Name'] - def tpURL(self): return "Column/%s" % self._d['Name'] - def Description(self): - d=self._d - if d['Scale']: - return " %(Type)s(%(Precision)s,%(Scale)s) %(Nullable)s" % d - else: - return " %(Type)s(%(Precision)s) %(Nullable)s" % d - -table_icons={ - 'TABLE': 'table', - 'VIEW':'view', - 'SYSTEM_TABLE': 'stable', - } - -field_icons={ - NUMBER.name: 'i', - STRING.name: 'text', - DATETIME.name: 'date', - INTEGER.name: 'int', - FLOAT.name: 'float', - BOOLEAN.name: 'bin', - ROWID.name: 'int' - } diff --git a/ZopeProducts/ZPsycopgDA/__init__.py b/ZopeProducts/ZPsycopgDA/__init__.py deleted file mode 100644 index b501cbfd..00000000 --- a/ZopeProducts/ZPsycopgDA/__init__.py +++ /dev/null @@ -1,29 +0,0 @@ -# ZPsycopgDA/__init__.py - ZPsycopgDA Zope product -# -# Copyright (C) 2004-2010 Federico Di Gregorio -# -# psycopg2 is free software: you can redistribute it and/or modify it -# under the terms of the GNU Lesser General Public License as published -# by the Free Software Foundation, either version 3 of the License, or -# (at your option) any later version. -# -# psycopg2 is distributed in the hope that it will be useful, but WITHOUT -# ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or -# FITNESS FOR A PARTICULAR PURPOSE. See the GNU Lesser General Public -# License for more details. - -# Import modules needed by _psycopg to allow tools like py2exe to do -# their work without bothering about the module dependencies. - -__doc__ = "ZPsycopg Database Adapter Registration." -__version__ = '2.4.6' - -import DA - -def initialize(context): - context.registerClass( - DA.Connection, - permission = 'Add Z Psycopg 2 Database Connections', - constructors = (DA.manage_addZPsycopgConnectionForm, - DA.manage_addZPsycopgConnection), - icon = 'icons/DBAdapterFolder_icon.gif') diff --git a/ZopeProducts/ZPsycopgDA/db.py b/ZopeProducts/ZPsycopgDA/db.py deleted file mode 100644 index a272c02d..00000000 --- a/ZopeProducts/ZPsycopgDA/db.py +++ /dev/null @@ -1,209 +0,0 @@ -# ZPsycopgDA/db.py - query execution -# -# Copyright (C) 2004-2010 Federico Di Gregorio -# -# psycopg2 is free software: you can redistribute it and/or modify it -# under the terms of the GNU Lesser General Public License as published -# by the Free Software Foundation, either version 3 of the License, or -# (at your option) any later version. -# -# psycopg2 is distributed in the hope that it will be useful, but WITHOUT -# ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or -# FITNESS FOR A PARTICULAR PURPOSE. See the GNU Lesser General Public -# License for more details. - -# Import modules needed by _psycopg to allow tools like py2exe to do -# their work without bothering about the module dependencies. - -from Shared.DC.ZRDB.TM import TM -from Shared.DC.ZRDB import dbi_db - -from ZODB.POSException import ConflictError - -import site -import pool - -import psycopg2 -from psycopg2.extensions import INTEGER, LONGINTEGER, FLOAT, BOOLEAN, DATE, TIME -from psycopg2.extensions import TransactionRollbackError, register_type -from psycopg2 import NUMBER, STRING, ROWID, DATETIME - - -# the DB object, managing all the real query work - -class DB(TM, dbi_db.DB): - - _p_oid = _p_changed = _registered = None - - def __init__(self, dsn, tilevel, typecasts, enc='utf-8'): - self.dsn = dsn - self.tilevel = tilevel - self.typecasts = typecasts - if enc is None or enc == "": - self.encoding = "utf-8" - else: - self.encoding = enc - self.failures = 0 - self.calls = 0 - self.make_mappings() - - def getconn(self, init=True): - # if init is False we are trying to get hold on an already existing - # connection, so we avoid to (re)initialize it risking errors. - conn = pool.getconn(self.dsn) - if init: - # use set_session where available as in these versions - # set_isolation_level generates an extra query. - if psycopg2.__version__ >= '2.4.2': - conn.set_session(isolation_level=int(self.tilevel)) - else: - conn.set_isolation_level(int(self.tilevel)) - conn.set_client_encoding(self.encoding) - for tc in self.typecasts: - register_type(tc, conn) - return conn - - def putconn(self, close=False): - try: - conn = pool.getconn(self.dsn, False) - except AttributeError: - pass - pool.putconn(self.dsn, conn, close) - - def getcursor(self): - conn = self.getconn(False) - return conn.cursor() - - def _finish(self, *ignored): - try: - conn = self.getconn(False) - conn.commit() - self.putconn() - except AttributeError: - pass - - def _abort(self, *ignored): - try: - conn = self.getconn(False) - conn.rollback() - self.putconn() - except AttributeError: - pass - - def open(self): - # this will create a new pool for our DSN if not already existing, - # then get and immediately release a connection - self.getconn() - self.putconn() - - def close(self): - # FIXME: if this connection is closed we flush all the pool associated - # with the current DSN; does this makes sense? - pool.flushpool(self.dsn) - - def sortKey(self): - return 1 - - def make_mappings(self): - """Generate the mappings used later by self.convert_description().""" - self.type_mappings = {} - for t, s in [(INTEGER,'i'), (LONGINTEGER, 'i'), (NUMBER, 'n'), - (BOOLEAN,'n'), (ROWID, 'i'), - (DATETIME, 'd'), (DATE, 'd'), (TIME, 'd')]: - for v in t.values: - self.type_mappings[v] = (t, s) - - def convert_description(self, desc, use_psycopg_types=False): - """Convert DBAPI-2.0 description field to Zope format.""" - items = [] - for name, typ, width, ds, p, scale, null_ok in desc: - m = self.type_mappings.get(typ, (STRING, 's')) - items.append({ - 'name': name, - 'type': use_psycopg_types and m[0] or m[1], - 'width': width, - 'precision': p, - 'scale': scale, - 'null': null_ok, - }) - return items - - ## tables and rows ## - - def tables(self, rdb=0, _care=('TABLE', 'VIEW')): - self._register() - c = self.getcursor() - c.execute( - "SELECT t.tablename AS NAME, 'TABLE' AS TYPE " - " FROM pg_tables t WHERE tableowner <> 'postgres' " - "UNION SELECT v.viewname AS NAME, 'VIEW' AS TYPE " - " FROM pg_views v WHERE viewowner <> 'postgres' " - "UNION SELECT t.tablename AS NAME, 'SYSTEM_TABLE\' AS TYPE " - " FROM pg_tables t WHERE tableowner = 'postgres' " - "UNION SELECT v.viewname AS NAME, 'SYSTEM_TABLE' AS TYPE " - "FROM pg_views v WHERE viewowner = 'postgres'") - res = [] - for name, typ in c.fetchall(): - if typ in _care: - res.append({'TABLE_NAME': name, 'TABLE_TYPE': typ}) - self.putconn() - return res - - def columns(self, table_name): - self._register() - c = self.getcursor() - try: - r = c.execute('SELECT * FROM "%s" WHERE 1=0' % table_name) - except: - return () - self.putconn() - return self.convert_description(c.description, True) - - ## query execution ## - - def query(self, query_string, max_rows=None, query_data=None): - self._register() - self.calls = self.calls+1 - - desc = () - res = [] - nselects = 0 - - c = self.getcursor() - - try: - for qs in [x for x in query_string.split('\0') if x]: - try: - if query_data: - c.execute(qs, query_data) - else: - c.execute(qs) - except TransactionRollbackError: - # Ha, here we have to look like we are the ZODB raising conflict errrors, raising ZPublisher.Publish.Retry just doesn't work - #logging.debug("Serialization Error, retrying transaction", exc_info=True) - raise ConflictError("TransactionRollbackError from psycopg2") - except psycopg2.OperationalError: - #logging.exception("Operational error on connection, closing it.") - try: - # Only close our connection - self.putconn(True) - except: - #logging.debug("Something went wrong when we tried to close the pool", exc_info=True) - pass - if c.description is not None: - nselects += 1 - if c.description != desc and nselects > 1: - raise psycopg2.ProgrammingError( - 'multiple selects in single query not allowed') - if max_rows: - res = c.fetchmany(max_rows) - else: - res = c.fetchall() - desc = c.description - self.failures = 0 - - except StandardError, err: - self._abort() - raise err - - return self.convert_description(desc), res diff --git a/ZopeProducts/ZPsycopgDA/dtml/add.dtml b/ZopeProducts/ZPsycopgDA/dtml/add.dtml deleted file mode 100644 index 330a001b..00000000 --- a/ZopeProducts/ZPsycopgDA/dtml/add.dtml +++ /dev/null @@ -1,108 +0,0 @@ - - - - -

-A Zope Psycopg 2 Database Connection is used to connect and execute -queries on a PostgreSQL database. -

- -

-In the form below Connection String (also called the Data Source Name -or DSN for short) is a string... (TODO: finish docs) -

- -
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
-
- Id -
-
- -
-
- Title -
-
- -
-
- Connection string -
-
- -
-
- Connect immediately -
-
- -
-
- Use Zope's internal DateTime -
-
- -
-
- Transaction isolation level -
-
- -
-
- Encoding -
-
- -
-
- -
-
-
- - diff --git a/ZopeProducts/ZPsycopgDA/dtml/browse.dtml b/ZopeProducts/ZPsycopgDA/dtml/browse.dtml deleted file mode 100644 index deffd0ab..00000000 --- a/ZopeProducts/ZPsycopgDA/dtml/browse.dtml +++ /dev/null @@ -1,11 +0,0 @@ - - <dtml-var title_or_id >tables - - - - <dtml-var Type> - - - - diff --git a/ZopeProducts/ZPsycopgDA/dtml/edit.dtml b/ZopeProducts/ZPsycopgDA/dtml/edit.dtml deleted file mode 100644 index cffb43bf..00000000 --- a/ZopeProducts/ZPsycopgDA/dtml/edit.dtml +++ /dev/null @@ -1,84 +0,0 @@ - - - -
- - - - - - - - - - - - - - - - - - - - - - - - -
-
- Title -
-
- -
-
- Connection string -
-
- -
-
- Use Zope's internal DateTime -
-
- checked="YES" /> -
-
- Transaction isolation level -
-
- -
-
- Encoding -
-
- -
-
- -
-
-
- - diff --git a/ZopeProducts/ZPsycopgDA/dtml/table_info.dtml b/ZopeProducts/ZPsycopgDA/dtml/table_info.dtml deleted file mode 100644 index 639c23fd..00000000 --- a/ZopeProducts/ZPsycopgDA/dtml/table_info.dtml +++ /dev/null @@ -1,7 +0,0 @@ - - - - owned by -
- - diff --git a/ZopeProducts/ZPsycopgDA/icons/DBAdapterFolder_icon.gif b/ZopeProducts/ZPsycopgDA/icons/DBAdapterFolder_icon.gif deleted file mode 100755 index ced0ef26..00000000 Binary files a/ZopeProducts/ZPsycopgDA/icons/DBAdapterFolder_icon.gif and /dev/null differ diff --git a/ZopeProducts/ZPsycopgDA/icons/bin.gif b/ZopeProducts/ZPsycopgDA/icons/bin.gif deleted file mode 100644 index e4691265..00000000 Binary files a/ZopeProducts/ZPsycopgDA/icons/bin.gif and /dev/null differ diff --git a/ZopeProducts/ZPsycopgDA/icons/date.gif b/ZopeProducts/ZPsycopgDA/icons/date.gif deleted file mode 100644 index 0d88a573..00000000 Binary files a/ZopeProducts/ZPsycopgDA/icons/date.gif and /dev/null differ diff --git a/ZopeProducts/ZPsycopgDA/icons/datetime.gif b/ZopeProducts/ZPsycopgDA/icons/datetime.gif deleted file mode 100644 index faa540b1..00000000 Binary files a/ZopeProducts/ZPsycopgDA/icons/datetime.gif and /dev/null differ diff --git a/ZopeProducts/ZPsycopgDA/icons/field.gif b/ZopeProducts/ZPsycopgDA/icons/field.gif deleted file mode 100644 index 9bf8692b..00000000 Binary files a/ZopeProducts/ZPsycopgDA/icons/field.gif and /dev/null differ diff --git a/ZopeProducts/ZPsycopgDA/icons/float.gif b/ZopeProducts/ZPsycopgDA/icons/float.gif deleted file mode 100644 index dd427299..00000000 Binary files a/ZopeProducts/ZPsycopgDA/icons/float.gif and /dev/null differ diff --git a/ZopeProducts/ZPsycopgDA/icons/int.gif b/ZopeProducts/ZPsycopgDA/icons/int.gif deleted file mode 100644 index ef2c5e36..00000000 Binary files a/ZopeProducts/ZPsycopgDA/icons/int.gif and /dev/null differ diff --git a/ZopeProducts/ZPsycopgDA/icons/stable.gif b/ZopeProducts/ZPsycopgDA/icons/stable.gif deleted file mode 100644 index acdd37df..00000000 Binary files a/ZopeProducts/ZPsycopgDA/icons/stable.gif and /dev/null differ diff --git a/ZopeProducts/ZPsycopgDA/icons/table.gif b/ZopeProducts/ZPsycopgDA/icons/table.gif deleted file mode 100644 index cce83bea..00000000 Binary files a/ZopeProducts/ZPsycopgDA/icons/table.gif and /dev/null differ diff --git a/ZopeProducts/ZPsycopgDA/icons/text.gif b/ZopeProducts/ZPsycopgDA/icons/text.gif deleted file mode 100644 index a2e5aab6..00000000 Binary files a/ZopeProducts/ZPsycopgDA/icons/text.gif and /dev/null differ diff --git a/ZopeProducts/ZPsycopgDA/icons/time.gif b/ZopeProducts/ZPsycopgDA/icons/time.gif deleted file mode 100644 index 6d089150..00000000 Binary files a/ZopeProducts/ZPsycopgDA/icons/time.gif and /dev/null differ diff --git a/ZopeProducts/ZPsycopgDA/icons/view.gif b/ZopeProducts/ZPsycopgDA/icons/view.gif deleted file mode 100644 index 71b30de1..00000000 Binary files a/ZopeProducts/ZPsycopgDA/icons/view.gif and /dev/null differ diff --git a/ZopeProducts/ZPsycopgDA/icons/what.gif b/ZopeProducts/ZPsycopgDA/icons/what.gif deleted file mode 100644 index 8b5516e3..00000000 Binary files a/ZopeProducts/ZPsycopgDA/icons/what.gif and /dev/null differ diff --git a/ZopeProducts/ZPsycopgDA/pool.py b/ZopeProducts/ZPsycopgDA/pool.py deleted file mode 100644 index b47f46cc..00000000 --- a/ZopeProducts/ZPsycopgDA/pool.py +++ /dev/null @@ -1,193 +0,0 @@ -# ZPsycopgDA/pool.py - ZPsycopgDA Zope product: connection pooling -# -# Copyright (C) 2004-2010 Federico Di Gregorio -# -# psycopg2 is free software: you can redistribute it and/or modify it -# under the terms of the GNU Lesser General Public License as published -# by the Free Software Foundation, either version 3 of the License, or -# (at your option) any later version. -# -# psycopg2 is distributed in the hope that it will be useful, but WITHOUT -# ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or -# FITNESS FOR A PARTICULAR PURPOSE. See the GNU Lesser General Public -# License for more details. - -# Import modules needed by _psycopg to allow tools like py2exe to do -# their work without bothering about the module dependencies. - -# All the connections are held in a pool of pools, directly accessible by the -# ZPsycopgDA code in db.py. - -import threading -import psycopg2 -from psycopg2.pool import PoolError - - -class AbstractConnectionPool(object): - """Generic key-based pooling code.""" - - def __init__(self, minconn, maxconn, *args, **kwargs): - """Initialize the connection pool. - - New 'minconn' connections are created immediately calling 'connfunc' - with given parameters. The connection pool will support a maximum of - about 'maxconn' connections. - """ - self.minconn = minconn - self.maxconn = maxconn - self.closed = False - - self._args = args - self._kwargs = kwargs - - self._pool = [] - self._used = {} - self._rused = {} # id(conn) -> key map - self._keys = 0 - - for i in range(self.minconn): - self._connect() - - def _connect(self, key=None): - """Create a new connection and assign it to 'key' if not None.""" - conn = psycopg2.connect(*self._args, **self._kwargs) - if key is not None: - self._used[key] = conn - self._rused[id(conn)] = key - else: - self._pool.append(conn) - return conn - - def _getkey(self): - """Return a new unique key.""" - self._keys += 1 - return self._keys - - def _getconn(self, key=None): - """Get a free connection and assign it to 'key' if not None.""" - if self.closed: raise PoolError("connection pool is closed") - if key is None: key = self._getkey() - - if key in self._used: - return self._used[key] - - if self._pool: - self._used[key] = conn = self._pool.pop() - self._rused[id(conn)] = key - return conn - else: - if len(self._used) == self.maxconn: - raise PoolError("connection pool exausted") - return self._connect(key) - - def _putconn(self, conn, key=None, close=False): - """Put away a connection.""" - if self.closed: raise PoolError("connection pool is closed") - if key is None: key = self._rused[id(conn)] - - if not key: - raise PoolError("trying to put unkeyed connection") - - if len(self._pool) < self.minconn and not close: - self._pool.append(conn) - else: - conn.close() - - # here we check for the presence of key because it can happen that a - # thread tries to put back a connection after a call to close - if not self.closed or key in self._used: - del self._used[key] - del self._rused[id(conn)] - - def _closeall(self): - """Close all connections. - - Note that this can lead to some code fail badly when trying to use - an already closed connection. If you call .closeall() make sure - your code can deal with it. - """ - if self.closed: raise PoolError("connection pool is closed") - for conn in self._pool + list(self._used.values()): - try: - conn.close() - except: - pass - self.closed = True - - -class PersistentConnectionPool(AbstractConnectionPool): - """A pool that assigns persistent connections to different threads. - - Note that this connection pool generates by itself the required keys - using the current thread id. This means that until a thread puts away - a connection it will always get the same connection object by successive - `!getconn()` calls. This also means that a thread can't use more than one - single connection from the pool. - """ - - def __init__(self, minconn, maxconn, *args, **kwargs): - """Initialize the threading lock.""" - import threading - AbstractConnectionPool.__init__( - self, minconn, maxconn, *args, **kwargs) - self._lock = threading.Lock() - - # we we'll need the thread module, to determine thread ids, so we - # import it here and copy it in an instance variable - import thread - self.__thread = thread - - def getconn(self): - """Generate thread id and return a connection.""" - key = self.__thread.get_ident() - self._lock.acquire() - try: - return self._getconn(key) - finally: - self._lock.release() - - def putconn(self, conn=None, close=False): - """Put away an unused connection.""" - key = self.__thread.get_ident() - self._lock.acquire() - try: - if not conn: conn = self._used[key] - self._putconn(conn, key, close) - finally: - self._lock.release() - - def closeall(self): - """Close all connections (even the one currently in use.)""" - self._lock.acquire() - try: - self._closeall() - finally: - self._lock.release() - - -_connections_pool = {} -_connections_lock = threading.Lock() - -def getpool(dsn, create=True): - _connections_lock.acquire() - try: - if not _connections_pool.has_key(dsn) and create: - _connections_pool[dsn] = \ - PersistentConnectionPool(4, 200, dsn) - finally: - _connections_lock.release() - return _connections_pool[dsn] - -def flushpool(dsn): - _connections_lock.acquire() - try: - _connections_pool[dsn].closeall() - del _connections_pool[dsn] - finally: - _connections_lock.release() - -def getconn(dsn, create=True): - return getpool(dsn, create=create).getconn() - -def putconn(dsn, conn, close=False): - getpool(dsn).putconn(conn, close=close) diff --git a/ZopeProducts/exUserFolder/AuthSources/__init__.py b/ZopeProducts/exUserFolder/AuthSources/__init__.py deleted file mode 100644 index dedaed0a..00000000 --- a/ZopeProducts/exUserFolder/AuthSources/__init__.py +++ /dev/null @@ -1,47 +0,0 @@ -# -# Extensible User Folder -# -# (C) Copyright 2000-2004 The Internet (Aust) Pty Ltd -# ACN: 082 081 472 ABN: 83 082 081 472 -# All Rights Reserved -# -# THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND -# ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE -# IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE -# ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE -# FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL -# DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS -# OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) -# HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT -# LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY -# OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF -# SUCH DAMAGE. -# -# Author: Andrew Milton -# $Id: __init__.py,v 1.1 2004/11/10 14:15:34 akm Exp $ - -#import etcAuthSource -#import httpsAuthSource -#import mysqlAuthSource -import pgAuthSource -#import pgAuthSourceAlt -#import radiusAuthSource -#import smbAuthSource -#import usAuthSource -#import zodbAuthSource -#import zodbBTreeAuthSource - -# -# These have special requirements for external libraries -# that my not be present. -# - -# try: -# import nisAuthSource -# except: -# pass - -# try: -# import LDAPAuthSource -# except: -# pass diff --git a/ZopeProducts/exUserFolder/AuthSources/pgAuthSource/.cvsignore b/ZopeProducts/exUserFolder/AuthSources/pgAuthSource/.cvsignore deleted file mode 100644 index 57c4bccb..00000000 --- a/ZopeProducts/exUserFolder/AuthSources/pgAuthSource/.cvsignore +++ /dev/null @@ -1,4 +0,0 @@ -*.pyc -*.pyo -*~ -.*.swp diff --git a/ZopeProducts/exUserFolder/AuthSources/pgAuthSource/__init__.py b/ZopeProducts/exUserFolder/AuthSources/pgAuthSource/__init__.py deleted file mode 100644 index a23a103c..00000000 --- a/ZopeProducts/exUserFolder/AuthSources/pgAuthSource/__init__.py +++ /dev/null @@ -1,2 +0,0 @@ -# $Id: __init__.py,v 1.1 2004/11/10 14:15:36 akm Exp $ -import pgAuthSource diff --git a/ZopeProducts/exUserFolder/AuthSources/pgAuthSource/manage_addpgAuthSourceForm.dtml b/ZopeProducts/exUserFolder/AuthSources/pgAuthSource/manage_addpgAuthSourceForm.dtml deleted file mode 100644 index ff0790c3..00000000 --- a/ZopeProducts/exUserFolder/AuthSources/pgAuthSource/manage_addpgAuthSourceForm.dtml +++ /dev/null @@ -1,40 +0,0 @@ - -
- -"> - - - - - - - - - - - - - - - - - - - - - - - - - - -
Database Connection: - -
Table Name:
Username Column:
Password Column:
Roles Column:

Add">
-
- diff --git a/ZopeProducts/exUserFolder/AuthSources/pgAuthSource/manage_editpgAuthSourceForm.dtml b/ZopeProducts/exUserFolder/AuthSources/pgAuthSource/manage_editpgAuthSourceForm.dtml deleted file mode 100644 index 7cd811cf..00000000 --- a/ZopeProducts/exUserFolder/AuthSources/pgAuthSource/manage_editpgAuthSourceForm.dtml +++ /dev/null @@ -1,37 +0,0 @@ - - -
- - - - - - - - - - - - - - - - - - - - - - - - -
Database Connection: - -
Table Name:">
Username Column:">
Password Column:">
Roles Column:">

Edit ">
-
- diff --git a/ZopeProducts/exUserFolder/AuthSources/pgAuthSource/pgAuthSource.py b/ZopeProducts/exUserFolder/AuthSources/pgAuthSource/pgAuthSource.py deleted file mode 100644 index bffe3b71..00000000 --- a/ZopeProducts/exUserFolder/AuthSources/pgAuthSource/pgAuthSource.py +++ /dev/null @@ -1,333 +0,0 @@ -# -# Extensible User Folder -# -# Postgres Authentication Source for exUserFolder -# -# (C) Copyright 2000,2001 The Internet (Aust) Pty Ltd -# ACN: 082 081 472 ABN: 83 082 081 472 -# All Rights Reserved -# -# THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND -# ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE -# IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE -# ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE -# FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL -# DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS -# OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) -# HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT -# LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY -# OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF -# SUCH DAMAGE. -# -# Author: Andrew Milton -# $Id: pgAuthSource.py,v 1.1 2004/11/10 14:15:36 akm Exp $ - -# -# This class only authenticates users, it stores no properties. -# - -import string,Acquisition - -from Globals import HTMLFile, MessageDialog, INSTANCE_HOME - -from OFS.Folder import Folder - -from Products.ZSQLMethods.SQL import SQL - -from Products.exUserFolder.exUserFolder import exUserFolder -from Products.exUserFolder.Plugins import PluginRegister - -try: - from crypt import crypt -except: - from Products.exUserFolder.fcrypt.fcrypt import crypt - -# debug XXX -# def xLOG(msg): -# f = open('/tmp/debug.log','a') -# f.write(msg+'\n') -# f.close() - -def manage_addpgAuthSource(self, REQUEST): - """ Add a Postgres Auth Source """ - - connection=REQUEST['pgauth_connection'] - table=REQUEST['pgauth_table'] - usernameColumn=REQUEST['pgauth_usernameColumn'] - passwordColumn=REQUEST['pgauth_passwordColumn'] - rolesColumn=REQUEST['pgauth_rolesColumn'] - o = pgAuthSource(connection, table, usernameColumn, passwordColumn, - rolesColumn) - self._setObject('pgAuthSource', o, None, None, 0) - o=getattr(self,'pgAuthSource') - if hasattr(o, 'postInitialisation'): - o.postInitialisation(REQUEST) - - self.currentAuthSource=o - return '' - -manage_addpgAuthSourceForm=HTMLFile('manage_addpgAuthSourceForm', globals()) -manage_editpgAuthSourceForm=HTMLFile('manage_editpgAuthSourceForm', globals()) - -class pgAuthSource(Folder): - """ Authenticate Users against a Postgres Database """ - - meta_type='Authentication Source' - title='Postgresql Authentication' - - icon ='misc_/exUserFolder/exUserFolderPlugin.gif' - - manage_tabs=Acquisition.Acquired - - manage_editForm=manage_editpgAuthSourceForm - - # - # You can define this to go off and do the authentication instead of - # using the basic one inside the User Object - # - remoteAuthMethod=None - - def __init__(self, connection, table, usernameColumn, passwordColumn, - rolesColumn): - self.id='pgAuthSource' - self.connection=connection - self.table=table - self.usernameColumn=usernameColumn - self.passwordColumn=passwordColumn - self.rolesColumn=rolesColumn - self.addSQLQueries() - - def manage_editAuthSource(self, REQUEST): - """ Edit a Postgres Auth Source """ - - self.connection=REQUEST['pgauth_connection'] - self.table=REQUEST['pgauth_table'] - self.usernameColumn=REQUEST['pgauth_usernameColumn'] - self.passwordColumn=REQUEST['pgauth_passwordColumn'] - self.rolesColumn=REQUEST['pgauth_rolesColumn'] - self.delSQLQueries() - self.addSQLQueries() # Re-add queries with new parameters - - def createUser(self, username, password, roles): - """ Add A Username """ - - if type(roles) != type([]): - if roles: - roles=list(roles) - else: - roles=[] - - rolestring='' - for role in roles: - rolestring=rolestring+role+',' - - rolestring=rolestring[:-1] - secret=self.cryptPassword(username, password) - self.sqlInsertUser(username=username, - password=secret, - roles=rolestring) - self._v_lastUser={} - - def updateUser(self, username, password, roles): - if type(roles) != type([]): - if roles: - roles=list(roles) - else: - roles=[] - - rolestring='' - for role in roles: - print role - rolestring=rolestring+role+',' - - rolestring=rolestring[:-1] - - # Don't change passwords if it's null - if password: - secret=self.cryptPassword(username, password) - self.sqlUpdateUserPassword(username=username, - password=secret) - - self.sqlUpdateUser(username=username, - roles=rolestring) - self._v_lastUser={} - - def delSQLQueries(self): - sqllist=self.objectIds('Z SQL Method') - self.manage_delObjects(ids=sqllist) - - def addSQLQueries(self): - sqlListUsers=SQL( - 'sqlListUsers', - 'List All Users', - self.connection, - 'table=%s'%(self.table), - _sqlListUsers) - - self._setObject('sqlListUsers', sqlListUsers) - - sqlListOneUser=SQL( - 'sqlListOneUser', - 'List ONE User', - self.connection, - 'table=%s usernameColumn=%s username:string'%( - self.table, self.usernameColumn), - _sqlListOneUser) - - self._setObject('sqlListOneUser', sqlListOneUser) - - sqlDeleteOneUser=SQL( - 'sqlDeleteOneUser', - 'Delete One User', - self.connection, - 'table=%s usernameColumn=%s username:string'%( - self.table,self.usernameColumn), - _sqlDeleteOneUser) - - self._setObject('sqlDeleteOneUser', sqlDeleteOneUser) - - sqlInsertUser=SQL( - 'sqlInsertUser', - 'Insert One User', - self.connection, - 'table=%s usernameColumn=%s passwordColumn=%s rolesColumn=%s username:string password:string roles:string'%( - self.table, self.usernameColumn, self.passwordColumn, self.rolesColumn), - _sqlInsertUser) - - self._setObject('sqlInsertUser', sqlInsertUser) - - sqlUpdateUser=SQL( - 'sqlUpdateUser', - 'Update User', - self.connection, - 'table=%s rolesColumn=%s username:string roles:string'%(self.table, self.rolesColumn), - _sqlUpdateUser) - - self._setObject('sqlUpdateUser', sqlUpdateUser) - - sqlUpdateUserPassword=SQL( - 'sqlUpdateUserPassword', - 'Update just the password', - self.connection, - 'table=%s usernameColumn=%s passwordColumn=%s username:string password:string'%(self.table, self.usernameColumn, self.passwordColumn), - _sqlUpdateUserPassword) - - self._setObject('sqlUpdateUserPassword', sqlUpdateUserPassword) - - def cryptPassword_old(self, username, password): - salt =username[:2] - secret = crypt(password, salt) - return secret - - def deleteUsers(self, userids): - for uid in userids: - self.sqlDeleteOneUser(username=uid) - self._v_lastUser={} - - def listUserNames(self): - """Returns a real list of user names """ - users = [] - result=self.sqlListUsers() - for n in result: - username=sqlattr(n,self.usernameColumn) - users.append(username) - return users - - def listUsers(self): - """Returns a list of user names or [] if no users exist""" - users = [] - result=self.sqlListUsers() - for n in result: - roles=[] - username=sqlattr(n,self.usernameColumn) - if sqlattr(n, self.rolesColumn): - roles=string.split(sqlattr(n,self.rolesColumn),',') - password=sqlattr(n, self.passwordColumn) - N={'username':username, 'password':password, 'roles':roles} - users.append(N) - return users - - def listOneUser(self,username): - #xLOG('pg.listOneUser(%s)' % username) - if getattr(self, '_v_lastUser', {}): - if self._v_lastUser['username']==username: - return self._v_lastUser['users'] - #xLOG('pg.listOneUser continuing') - users = [] - result=self.sqlListOneUser(username=username) - #xLOG('pg.listOneUser result=%s' % result) - for n in result: - roles=[] - username=sqlattr(n,self.usernameColumn) - password=sqlattr(n,self.passwordColumn) - if sqlattr(n, self.rolesColumn): - roles=string.split(sqlattr(n,self.rolesColumn),',') #Andreas - N={'username':username, 'password':password, 'roles':roles} - users.append(N) - self._v_lastUser={} - self._v_lastUser['username']=username - self._v_lastUser['users']=users - return users - - def postInitialisation(self, REQUEST): - self._v_lastUser={} - -pgAuthReg=PluginRegister('pgAuthSource', 'Postgresql Authentication Source', - pgAuthSource, manage_addpgAuthSourceForm, - manage_addpgAuthSource, - manage_editpgAuthSourceForm) -exUserFolder.authSources['pgAuthSource']=pgAuthReg - -from string import upper, lower -import Missing -mt=type(Missing.Value) - -def typeconv(val): - if type(val)==mt: - return '' - return val - -def sqlattr(ob, attr): - name=attr - if hasattr(ob, attr): - return typeconv(getattr(ob, attr)) - attr=upper(attr) - if hasattr(ob, attr): - return typeconv(getattr(ob, attr)) - attr=lower(attr) - if hasattr(ob, attr): - return typeconv(getattr(ob, attr)) - raise NameError, name - - - -_sqlListUsers=""" -SELECT * FROM -""" - -_sqlListOneUser=""" -SELECT * FROM -where = -""" - -_sqlDeleteOneUser=""" -DELETE FROM -where = -""" - -_sqlInsertUser=""" -INSERT INTO (, , ) -VALUES (, - , - ) -""" - -_sqlUpdateUserPassword=""" -UPDATE set = -WHERE = -""" - -_sqlUpdateUser=""" -UPDATE set = -WHERE = -""" diff --git a/ZopeProducts/exUserFolder/CHANGES.txt b/ZopeProducts/exUserFolder/CHANGES.txt deleted file mode 100644 index 6271ba5e..00000000 --- a/ZopeProducts/exUserFolder/CHANGES.txt +++ /dev/null @@ -1,865 +0,0 @@ -Changes for 0.50.1 - -Add a README.Upgrading file to explain the impact of the 0.50.0 source -restructure, since people don't seem to be reading this file. --akm - -Fix the default docLogin to use &dtml-URL as the default destination. -I porked the fcrypt import. It obviously doesn't get imported here since -I have a crypt module installed. -- akm - -Fixed; https://sourceforge.net/tracker/?func=detail&aid=1084903&group_id=36318&atid=416446 -thanks to vigine -- akm - -Changes for 0.50.0 - -Restructured Source Tree. This will make this version incompatible with -previous versions, as the classes have moved. This breaks upgrading existing -installs unless you keep the old classes around. If you only use external -Auth/Prop/Group sources, you will probably be unaffected. - -o Auth Sources moved to single directory -o Prop Sources moved to single directory -o Group Sources moved to single directory -o Docs moved to doc directory ---akm - -Added Pluggable Crypto methods. Any authSource that contains a -cryptPassword method, will have it's method called, otherwise the -method selected by the user is called. --akm - -Removed the cryptPassword method from existing Auth Sources. --akm - -docLoginRedirect is no longer used. --akm - -Changes for 0.20.2 -BLAH! I missed some LDAP changes! --akm - -Changes for 0.20.1 - -Fix import problem for pgPropSource --akm -Add performance boost to pgAuthSource and pgPropSource --akm -Make zodbAuthSource.listUsernames return a list. --akm -Update some LDAP Auth source bugs. --akm -Change references to "Authorisation" to "Authentication" since XUF -auth sources authenticate, they don't authorise. --akm -Changed the

tags to tags in the manage_adds. - -Changes for 0.20.0 - -Fix: -https://sourceforge.net/tracker/index.php?func=detail&aid=547327&group_id=36318&atid=416446 -https://sourceforge.net/tracker/index.php?func=detail&aid=616485&group_id=36318&atid=416448 -https://sourceforge.net/tracker/index.php?func=detail&aid=594081&group_id=36318&atid=416448 -https://sourceforge.net/tracker/index.php?func=detail&aid=594526&group_id=36318&atid=416448 - -Added LDAPAuthSource, based on the auth_ldap module for Apache -(http://www.rudedog.org/auth_ldap/) and the NDS Auth Source of -Phil Harris (AKA ftmpsh). This is only lightly tested, I don't have -the LDAP resources here to test all the features. Binding using uid/ -cn and using various filters works (if the userPassword item is -present). This needs more testing by people with better LDAP setups -that I do. --akm - -Padded docLoginRedirect to prevent IE from displaying "Friendly" error -messages when -D flag not present when running Zope --akm. - -Update UZG to contain entry for LDAPAuthSource. Reformat text -slightly. --akm - -Propogate "unable to auth" here requests up. This means the Manager -doesn't get locked out in cookie mode after adding an XUF instance. -It also means that people using a non-existant username at this level -get thrown up a level higher. This might not be what people want to -happen. --akm - -Added method makeRedirectPath which is called from docLoginRedirect. -This makes the destination include any querystring that was present -when needing to redirect. -- akm. - -Removed some Class globals from exUseFolder.py. These are now set -in __set_state__ if not present in the class so that upgrading users -don't get a crash (hopefully). -- akm. - -pgPropSource was losing track of properties under heavy load. -Only noticable if you were setting and deleting a lot of temporary -properties. There is a global property timeout for pgPropSource. --akm - -Jason Gibson provided a nisAuthSource, -I've added it here --akm. - -Refactored validate method to behave a lot more like BasicUserFolder. -Among other things, this fixes the issue where a local role could not -be granted to a user and granted permissions on the same object. --mb - -Add NuxUserGroups support (previously on NuxUserGroups_support_branch) -and group sources. --bmh, mb - -Now passes authFailedCode to Membership Login Page, The Default Login -Page as defined in the README.Membership will correctly display reason -for login being required --cab - -Fixed Edit management pages for user-supplied auth and property -sources --bmh - -Removed overriding of __len__ to return the number of users. This was -causing performance problems during authentication. See -http://sourceforge.net/mailarchive/message.php?msg_id=2230743 for -details. WARNING: this means using len(acl_users) to get the number -of users will no longer work! If you were using this trick, please -use len(acl_users.listUsers()) instead. --bmh - -Make title property editable --bmh - -Make Group Sources changeable dynamically after the acl_users folder has -been created --bmh - -Inital import of https Auth source. Also, added a listUsers method -to the zodbBTreeProps source to support listUsers. -- jsb - -Changes for 0.10.10 - -Added mysql Auth and mysql Prop source and mysql.sql schema. Just a -copy of the appropriate pg source with sql that works with myqsl -cab - -Fixed negative user cache lookup in std_validade so that it actually -works for users being authenticated thru basic auth, especially if -they're authenticating in outer user folders -- rochael - -Made smbAuthSource catch NetBIOSTimeout errors during authentication -- rochael - -Fixed dtml/mainUser.dtml to be virtualhost-sensitive when displaying user -icons -- rochael - -Updated UZG per user request. Fixed numbering, added information about -addition parameters like Negative Caching. - -Changes for 0.10.9 - -Made dummyZBabelTag compatible to replace the NoBabel in OrderedFolder -while keeping its functionality in XUF -- cab - -Changed _doAddUser, _doChangeUser to work with the public interface for -userfolders introduced in Zope2.5. Optional keyword arguments can now -be passed to _doAddUser and _doChangeUser. - -PropertySource: Please note that createUser and updateUser, when called -from _doAddUser and _doChangeUser, will no longer be passed a REQUEST, -but a mapping with items from REQUEST updated with those from the -optional keyword arguments. -- pj - -Fixed the problem with upgrading from 0.10.7 and below that didn't -account for existing XUF's not having a MessageDialog in their -contents. Now unless specificy replace it will use the MessageDialog -provided. Added how to do that to FAQ and README.Membership --cab - -Made docLoginRedirect provide an absolute URL --bmh - -MessageDialog in common no longer uses mangage_page_header and -mangage_page_footer v--cab - -Changes for 0.10.8 - -Added the ability for members to change properties, and a default page -in the README.Membership to show how to do it --cab - -MessageDialog is now an object in the ZODB that can be changed to fit -the site --cab - -Now with 100% guaranteed race-condition-free UserCache goodness! Those -subclassing XUFUser, you will have to change your code. See User.py -for details. --mb - -zodbBTreePropSource was returning None instead of the requested -default value, when called with (e.g.) someuser.getProperty('shoesize',13). -(Other property sources didn't have that bug.) ---davidc@debian.org - -The tutorial loginform was wrong for Membership in README.Membership - -Seems delProperty has never worked.. fixed --akm -Seems delProperty for pgPropSource has never worked.. fixed --akm - -Fixed Basic Auth not auth problem. --akm -Fixed Basic Auth not cache problem. --akm -Fixed Cached Users bypassing some auth checks. --akm - -Added usPropSource, which allows users to supply property methods TTW. ---bmh - -Changes for 0.10.7 - -PropertyEditor had a typo in dtml and was casting int to None. --zxc - -BasicAuth is now broken the other way, it'll allow any user to validate -with any password. --akm - -Negative cache checking move was bogus. --akm - -redirectToLogin didn't have a security declaration so 2.5.0 refused to -work in cookie mode *sigh* --akm - -Fixed the 'None' object has no attribute 'load' setstate errors that -could crop up on propSources, and preemptively took care of the -authSources as well. Also fixed some of the weirder bugs relating to -user object acquisition context. --mb - -Bug fixes from sf applied. --akm - -Changes for 0.10.6 - -dummyZBabelTag used the python 2 re, which broke installations using -python 1.5 which still used the now deprecated regex, changed it to -catch the exception and use regex instead for python 1.5, else still -use re --cab - -The redirectToLogin without Membership had a little logic problem where it -would basically garantee the existence of a query string, with at least a -lonely question mark even when there was no query string in the original -URL --rochael - -smbAuthSource needed to cast NULL role properties to an empty list --akm - -smbAuthSource had some dodgey zLOGing in it. --akm - -smbAuthSource had some methods that should return [] instead of None. --akm - -s/postgres/RADIUS/ in the radiusAuthSource DTML --akm - -cookie_validate no longer pulls you from the cache if you're -logging in (which means your cookie wouldn't get set). --akm - -Cookies are no longer expired if you're successfully authenticated but -merely unauthorized. --mb - -Basic auth resynched with standard user folder, trying to fix -some basic auth issues. --akm. - -Negative cache checking now performed outside of the two specific -validate methods. --akm. - -A fairly innocuous print debug statement turned into a zLOG at error -level, removed --akm. - -Clean up smbAuthSource log messages, and quieten. Only truly -exceptional cases are now logged above BLATHER. --mb - -Changes for 0.10.5 - -Membership redirecting to login was still broken. It should be better -now (twice) --akm - -logout() wasn't clearing the advanced cookie. --akm - -Negative Cache Value wasn't being passed through to the XUF constructor. --akm -Log Users Out DTML code was broken, should work now. --akm - -The User object now contains the authSource as well as the propSource, -making access to roles for custom User-objects possible. --dlk - -Following akm's advice, fixed manage_beforeDelete to use two separate -try:except blocks to ensure that if cache-removal fails, deleting -the container.__allow_groups__ property is attempted. This should -fix the problem where deleted xuf instances remain as "ghost" products -causing interference with newer versions of xuf, and also fixes the -problem where deleting a xuf acl_users in a folder makes that folder -inaccessible. --dlk - -Fixed cache_delete that was missing the "self" parameter in the method -defintion. --dlk - -Fixed xcache_delete that was missing the "self" parameter in the method -definition --akm d8) - -These previous two fix the problems with manage_beforeDelete, but, it -will stay the same for now --akm. - -Fixed cache_deleteCookieCache that was missing the "self" parameter in -the method defintion. --dlk ;) - -Changes for 0.10.4 - -The instructions for File Based Auth were incorrect in the UZG --akm - -redirectToLogin was totally wrong for membership... --akm -docLogin was fixed for VHM use. --akm - -Advanced Cookie Mode has changed so that it no longer sends the username -and password. Instead a hash is used as a key into a module level cache. -This should be 100% more secure than standard cookie mode, and removes -the stupid back doors I enabled in the previous version. This work was -based on conversations I had with Stuart Bishop (I basically lifted -the hashing scheme from GUF). This makes use of the Module level cache -code. --akm - -There was a code cleanup and a slight reorganisation of some files. --akm - -The main User Object has migrated to XUFUser and simarly with the -AnonUser. There is now an empty [Anon]User class that has XUFUser as -it's base. This allows people to create custom User Objects without -jumping through hoops (and simplifies maintaining patches) --akm - -Cache Code has changed again. Now there is a module level cache, so -that auth data is shared between threads for a single XUF (thanks to -Stuart Bishop for an enlightening discussion on this and other issues, -and thanks to Chris McDonough for talking me through setting up module -level globals [and sending me some code to work from]) --akm - -A Negative User Cache now exists. This is only generally useful for -use with remote auth sources where repeatedly trying to auth non-existant -users is very expensive (where they are authed at a higher level). -You can enable this on creation or from the parameters screen (positive -time in seconds enables). --akm - -Domain checking code finally removed. --akm - -zodbBTreePropSource changed to be friendlier about users that exist -in remote locations (i.e. aren't create as such through the ZMI). -- akm - -Changed some 'print's in the code to use zLOG.LOG -instead. Files affected so far (more to follow): -- rochael - - * exUserFolder.py - * basicMemberSource/basicMemberSource.py - * zodbBTreePropSource/zodbBTreePropSource.py - * zodbPropSource/zodbPropSource.py - -Changed a couple things in smbAuthSource.py: -- rbanffy - - * Method _authenticate_retry now logs several kinds of information - for debugging and diagnostics. - - * Modified socket.error handling in _authenticate_retry: changed - "raise" to "return 0". - - * Since this generated more problems (failed authentications) than - it solved (our impression it was not right not to return 0 in an - auth fail even due to a communications malfunction), we also - changed socket.error handling to retry no mather what errno tells - us (it said different things for the same problem under Windows - and Linux). - - * In order to prevent infinite retries, changed retry handling a - bit. It now retries 3 times. Real-use data will tell us if we - should increase or not retries. To better convey the meaning of - the parameter, changed "retry_depth" to "retries". I strongly - advise the use of credential caching with smbAuthSource, tough, as - it reduces socket errors and load on the domain controllers. - -Changes for 0.10.3.1 - -Readded support for I18N without ZBabel installation, somehow missed -during the transition to SF CVS. - -Some text changes as well as an update to the dictionary while we're -at it. No functional changes for this release though. - -Changes for 0.10.3 - -Missed a few LoginRequireds. - -Fixed a bug with __allow_groups__ not being set after paste -(probably also not after import). - -The sources are now sorted by name in the drop down box.. - -a BTree version of zodbAuthSource -a BTree version of zodbPropSource - -These aren't really all that different to the originals that were -provided by Alex, but, they use BTrees instead of PersistentMappings, -and try to avoid various persistence problems associated with dicts. -Both versions will continue to be supported. - -Patches from SF applied. - -Advanced Cookie Mode added. -This mode adds a rotor cipher around the cookie. A secret is provided -in order to encode the cookie. The username and password are placed -within a small class which is pickled and then encrypted and then -base64 encoded for transport. There is also a timestamp inside the cookie, -so the ultra-paranoid of you can rotate the cookie based on the timestamp -inside. - -Abstracted out the setting and decoding of cookies. - -Changes for 0.10.2 - -all raise 'LoginRequired' <- raise 'Unauthorized' - -Raising unauthorizes breaks a million things. CMF people can just -put up with configuring their portal properly. - -Radius resynced with version from sourceforge. -manage_tabs redone to be ZBabel'd and to look like standard tabs. - -German Language added to the ZBabel dictionary. - - -Changes for 0.10.1 - -all raise 'LoginRequired' -> raise 'Unauthorized' - -Bug in etcAuthSource listUsers fixed, -and cryptPassword also fixed to get the actual salt. - -Zope 2.4.3 has dicked with security settings again.. I've had a round -of permission whacking. - -Buggy handling of empty role lists was fixed. - -Change to smbAuthSource to use string.lower on usernames for -python 1.5.2 compatibility? - - -Changes for 0.10.0 - -Added explicit roles for manage_editUser and friends, to allow -the "Manage users" permission to be useful to non-Manager Users. -Thanks to Heimo Laukkanen for reporting this -one. - -zodbAuthSource made more persistent -zodbPropSource was blowing when deleting temporary properties. - -XUF is now ZBabel'd which means you can view XUF in different languages -for logging in and installation, if your browser locale is set up. -You will need the latest ZBabel installed. The translation file is in the -I18N directory. - -Import this (using Import/Export in ZODB) at the same level as your -ZBabelTower, and then import it from ZBabel. If you have ZBabel installed, -but, your application can't find a ZBabelTower, because of a bug in the -current dtml-fish tag, you might experience some problems. This ZBabel -bug should be fixed sometime soon. - -You do not need ZBabel installed to run XUF, XUF installs a dummy -interface for ZBabel so that XUF can continue to run (sorry folks it -defaults to Australian English). - -getUserNames() was returning the wrong stuff (notably affected TheJester's -WorkOrders Product) - -There is a now an 'Advanced Postgres' Auth Source that uses a seperate -Roles table and a 'more relational' layout. The schema is with the -auth source in pgAuthSourceAlt. Contributed by -Adam Manock - -If you had a membership source and had specified a login page, XUF was -still using the stock docLogin instead of the membership specified page -(for redirectToLogin, exceptions still raise the docLogin). - -I changed the icon to something a *little* less hideous - -Leonardo Rochael Almeida made the following changes -to smbAuthSource - -* Added a 'winsserver' constructor parameter and a '_winsserver' - instance variable to the 'smbAuthSource' class. This variable should - be the empty string, meaning that the authenticaton host will be - looked up by broadcast, or an IP address string pointing to a WINS - server. - -* Modified the dtml templates to ask for the above mentioned WINS - server (and also to replace 'Add' with 'Change' in - 'manage_editsmbAuthSourceForm'). - -* Refactored the smbAuthSource class to isolate all smb interaction - inside well defined methods. - - -Changes for 0.9.0 - -Messages are now sent back to the docLogin form. There's a file called -LoginRequiredMessages.py where the messages are kept for now (it might -end up a run-time configurable thing later). - -There's a new docLogin.dtml file on disk that shows how to use the new -messages. Because docLogin is in the ZODB this won't be automatically -upgraded. - -Idle Session Timeouts are in (this is the reason for the minor bump). -If you flick the switch, then users are forced back to the login form -(with a message saying their session timed out), when they're removed -from the cache. - -I made some adjustments to the tabs on the management interface because -they were too big, and I cleaned it up a bit for times when they run -together. - -The internal API was inconsistent, so that's been updated. -AuthSources no longer need to provide getUsers(), it was never -being called anyway since exUserFolder built it's own. -listUsers now returns the same data as listOneUser, this is used in -other places as if it were a list of listOneUser calls. - -Fixed pgAuthSource to deal with NULL rather than empty roles -columns (legacy columns). - -Changed Home Directory creation to use copy & paste functions to -copy the skeleton data. - -Changes for 0.8.5 - -I forgot to update the schema file for userproperties to reflect -the temporary properties flag. - -Checks for existing cache weren't being performed before removing users -from it, when their data was updated. - -Reversed the order for checking in cookie_validate, to allow logging -in as a new user, when session tracking was on. Also now you can -login as a different user, without logging out first, which might -be useful to some people. - -etcAuthSource now looks for the correct salt from the file for -encrypting the user supplied password - -Changes for 0.8.4 - -Activating Session Tracking and then adding a new user when there -were none in the XUF was broken. - -Changes for 0.8.3 - -The idle users are flushed from the cache when you ask for the list -of cache users (since it's iterating over the whole list anyway). So -you can manually clear your cache by looking at the Cache Stats page. - -If you display the list of logged in users on your site, then your cache -will be flushed for you automagically. - -Allowed a destination to be sent to redirectToLogin to allow you to -manually override the destination after logging in. - -Added in a __setstate__ for pgPropSource to deal with new ZSQL Methods -being added. - -Changes for 0.8.2 -A number of bugs related to temp properties fixed in pgPropSource - -FTP Access to folders protected with cookie_mode has been fixed, it -now reverts to std_auth (which handles the FTP connection fine), since -FTP auths are handled by getting a "Basic" auth tag coming through, which -should never happen in cookie mode. - -This has the knock-on effect of authenticating users that auth from a -higher acl_users that doesn't use cookies, 'more' correctly now. Which is -if you have a user defined above, and in XUF and the XUF user has less -permissions, it'll 401 you if you don't have permissions locally -(which is the correct behaviour). This bit me in the arse when I changed it, -and I'm still leaving it this way. d8) - -Users are now flushed from the cache when you edit them (in case you changed -roles), so that new roles should take effect immediately. - -The credential cache now uses the (Zope) builtin BTree Module for caching -rather than the AVL Tree implementation. There was a nasty issue with users -appearing multiple times in the AVL Tree which sucked. - -There is a report of the Radius Auth Source being broken (most likely -by me), if your radius source stops working, you can try copying the -py-radius.py file from sourceforge over the top of radius.py. If someone -gives me a traceback, I can fix it. I don't seem to be having problems, -but, I don't have a full time RADIUS source either. - - -Changes for 0.8.1 - -A bug in _doAddUser was fixed -A bug in the User Object unconditionally calling the prop source was fixed. - - -Changes for 0.8.0 - -Experimental "Session Tracking" added (why is it called that? we don't really -track anything, just associate arbitrary data with anonymous users). -This relies on the credential cache being active. Your session will -automatically expire when the anonymous user is so idle that they are -expired from the cache. This is not currently acceptable (to me), but, -it might be to other people, I await feedback on how sessions should expire -gracefully. - -Updated the README.txt file to point at the UZG and to explain the -version numbering system. - -All this time you couldn't delete properties from a user... who knew? -It's fixed now. - -Temporary properties now available, you can setTempProperty() on a -user object, and also flushTempProperties() on a user object. -Temporary properties are accessed like normal properties, and can be -deleted in the same way. flushTempProperties is there to do a quick -flush of all the crap you might have inserted (useful for sessions). -If your user is flushed from the cache, then all temp properties will -also be removed at that point. - -Propsource providers should look at the new temp properties stuff and -update accordingly. - -Alex provided a whole heap of patches to make basicMembership more usable, -well make it actually work. - -Matt Behrens supplied patches to prevent null logins and to allow case -insensitive logins for smbAuthSource - -Added a basic FAQ. - - -Changes for 0.7.10 - -Active Users type functionality was added. The new function is called -getUserCacheUsers(). It returns a list of dicts; - -{'username': theusername, 'lastAccessed': float_value} - -lastAccessed represents the last time the user touched something. -The Cache Stats page shows an example usage showing idle time (very cool -I think :-) - -The logout method was not correctly removing users from the cache, -although the cookie was removed, so logins were still enforced. I'm not -sure of any side-effects related to it, but, - -Some permissions were a little too liberal, including allowing arbitrary -users to set and get Properties on the acl_users folder. - -Copy/Paste support for pasting exUserFolders into the root was added. -I'm not sure I like the way this is done. I haven't found any side effects -so far, but, just be wary. Adding an exUserFolder to the root becomes -semi-trivial now. Create one in a sub-folder. Login as the emergency user. -CUT the exUserFolder. Delete the standard acl_users folder. Paste exUserFolder. -You should be away. At least it worked fine for me... YMMV - -_doChangeUser and _doDelUsers added so users can be altered and deleted -like for Standard UserFolder. - -_createInitialUser added so there should always be your initUser (hopefully) -when you create your exUserFolder. - -Emergency User checking brought into line with Standard Folder - -__creatable_by_emergency_user_ added and returns 1 to explicitly allow this. - -Unenlightened Zopistas Guide updated to have a 'Recipe' like section. -Currently contains a section about adding exUserFolders from python. - - -Changes for 0.7.9 - -RADIUS authSource had a problem with non-integers being extracted from -REQUEST (I wish someone at DC would fix this already). I worked around -this problem - -Default port for RADIUS is now 1812 in line with the IANA sanctioned list. - -Unenlightened Zopistas Guide to exUserFolder version 0.0 included, -covers installation and authentication sources, and the most common -configuration mistake (or misunderstanding). - -I almost released with the daggy management screens all Purple or SkyBlue, -so consider yoursevles lucky. This would have been the "Blue" release. - -Changes for 0.7.8 - -zodbPropSource had a bug that must have been there since 0.0.0 where -_p_changed wasn't being called on create, update, or delete user. -Thanks to Bouke Scheurwater for spotting that one. - -Alex provided a number of patched to fix a whole bunch of goofy stuff -with Basic Member Source that was stupidly wrong. - -Matt Behrens provided a patch to allow emergency user to own exUserFolders -and some of the sources. I've grudgingly updated all the sources to allow -this. It's just a hey nonny nonny to people using it as a root authenticator -now. - -Matt Behrens also provided a patch to fix 'broken pipe' problems with -smbAuthSource. - -pySMB is now at 0.2 for smbAuthSource WARNING: This will try to use DES -encrypted passwords. Apparently it should be ok if your server doesn't want -them. However if it breaks, unpack the pySMB distribution in the -smbAuthSource directory, there are registry examples there to turn -it off. It unfortunately needs the mxCrypto tools for encrypted passwords -to work. When I've got a bit more time, I'll see if I can make it use -crypt or fcrypt if available instead. - -Explicit checks for the emergency user were placed into the cookie_validate -routines. I suspect this may have been the cause of some grief with people -doing weird things like trying to make it the root auth folder. - -Changes for 0.7.7 - -Some Auth sources had problems coping with no roles being selected when -a user was created from the management interface, the stock ones were fixed. - -I screwed up some of the DTML, and forgot to change the loading of two of -the methods from the dtml directory. - -NO MORE TRACEBACKS ON LOGIN FORMS, there is a little redirector dtml file -dtml/docLoginRedirect that redirects to acl_users/docLogin with destination -set to take them back to where they were going. If you have a custom loginPage -change the redirector dtml to point to your new page. - -standard_html swapped for manage_page on Management Pages. Hopefully -this doesn't break someone with an old copy of Zope. - -Credential Caching is now available by default for all Authentication Sources, -upgrading installs will get this defaulted to 0 for no caching. You can alter -the cache level from the Parameters Tab. Authors of external sources should -remove any internal auth caching they're doing, and allow the user to decide -how long to cache the credentials for. - - -Changes for 0.7.6 - -smbAuthSource included. Doesn't require any external libraries, or compiling. -Uses pySMB from Micheal Teo - -Changes for 0.7.5 -The Management Interface now batches the user list by 10. This isn't -configurable at the moment (just change the dtml). - -The code was re-organised slightly, with all the DTML moving into its -own directory for core. - -radiusAuthSource added, but, is so far untested. It is a direct port of -ZRadius for GUF, but, I haven't had a chance to setup a RADIUS server to -test it out. - -You can add properties to a user from the management interface. - -List Properties on users can be added and edited, if I can work out a decent -way to edit Dicts/Mappings, I'll add that feature in. - -This paves the way for defining a set of properties in the Membership -source, so it can create a Signup and Edit page for you automatically. -You will also be able to specify which properties the user can edit, or -roles required to edit a property, this will be in a later release though. - -pgPropSource was updated to take into account non-scalar types, and now -pickles all data going into the database, this means ints will stay as ints, -et al. -There is code in there to cope with older properties coming out as strings. -The Schema remains the same. - -Changes for 0.7.2 -Changes to make it work with older version of python -Some minor bug fixes for membership. - -Changes for 0.7.1 -DTML Change for cmfPropSource - -Changes for 0.7.0 -exUserFolder was a little too liberal in removing its cruft, this is now -fixed. - -cmfPropSource was provided by Alan Runyan which is a layer around the CMF -property stuff. It's conditionally imported, so if you don't have CMF -installed you don't need to worry that'll it'll break. - -Property Sources are optional, and there is a NULL Property Source for this -purpose. - -Membership hooks, and a rough start at membership (basicMemberSource), -which has some usable functionality (you MUST read README.Membership before -using this). - -Membership Sources are optional and there is a NULL Membership Source for -this purpose. - - -Changes for 0.6.2 -exUserFolder was leaving cruft around when it was being deleted from -Folders. The cruft should now be obliterated if you delete an exUserFolder. - -Changes for 0.6.1 -Ownership tab enabled, for those sick monkeys that want to use it as a root -Folder (there are some). - -fcrypt got the __init__.py that was missing from the 0.6.0 release -zodbAuthSource updated to pull in fcrypt if crypt was missing. - -Changes for 0.6.0 - -Updated for 2.4.1 / Python 2.1 -Bug in pgPropSource not deleting users from the property cache fixed. -Bug with Local Roles not getting what it expected fixed. -Alex Verstraeten provided zodbAuthSource, there's a README.zodbAuthSource, -and the same README inside the zodbAuthSource directory. -fcrypt is now included and used if crypt cannot be imported. More information -on fcrypt can be found at http://home.clear.net.nz/pages/c.evans/sw/. This -should help particularly Windows users a lot. -Rudimentary API doc included. - -Changes for 0.5.0 - -A serious bug in zodbPropSource was fixed. - -There is now the option of providing a 'Remote Auth' function for -validating. This allows things like IMAP/LDAP auth sources to do their -authentication, since they don't return passwords you can use in general. - -There's already a 3rd Party solution that provides IMAP/POP3 authentication, -using the new API. - -Changes for 0.4.6 - -Minor dtml hacks - -Changes for 0.4.5 - -Hooks for 'editing' Authentication and Property Sources were added, along -with the relevant methods in each of the sources. - -The management interfaces got a little overhaul, just to make them -a little different (yes I know everything I do looks the same). The two -I didn't want to mess with still have the acquired management interfaces. - -A fix for the ZODB Property Source which was missing a few methods. - -Changes for 0.4.0 - -Based on an idea from Martin von Loewis, I added in support for defining -roles for etcAuthSource. This basically uses the current Prop source to -store a 'roles' property. The default role is still there as well for -those of you who might be using it. - -Changes for 0.3.0 - -Adrien Hernot noticed that properties for new users using zodbPropSource -were causing havoc, and that the version.txt file was completely wrong. -Andreas also noticed the version.txt was wrong. - -I've been bugged enough by the pair of them to change the single += -into 1.5.2 compliant syntax. - -I don't make any claims about it working under 1.5.2 though. - -Changes for 0.2.0 - -Even more embarassment... - -Andreas Heckel provided fixes for some stupid things I left out including; - -o Fixing the way I was handling multiple roles coming out of the database -o The wrong icon in the user display -o Alerting me to the fact that pgPropSource didn't actually have a - deleteUsers hook -o Providing a schema for automatically deleting properties in postgres - if you delete a user from the auth source (you have to be using both - pg sources for this to work, and they'd have to be in the same database) - I've put Andreas schema into the distribution, if you want to use - exUserFolder as a straight pgUserFolder, you'll also need to edit - exUserFolder.py and comment out the line indicated in deleteUsers() - -Changes for 0.1.0 - -Pretty embarassing really. - -M. Adam Kendall (DaJoker) found some stupid things in the 0.0.0 release -including the fact you couldn't edit user properties, or update them, -or actually change a user in anyway. - -I also discovered I was resetting the password to empty if you left it -empty.. diff --git a/ZopeProducts/exUserFolder/CryptoSources/__init__.py b/ZopeProducts/exUserFolder/CryptoSources/__init__.py deleted file mode 100644 index 49ebc6d4..00000000 --- a/ZopeProducts/exUserFolder/CryptoSources/__init__.py +++ /dev/null @@ -1,4 +0,0 @@ -import pass_crypt -import pass_md5 -import pass_sha -import pass_plain diff --git a/ZopeProducts/exUserFolder/CryptoSources/fcrypt/.cvsignore b/ZopeProducts/exUserFolder/CryptoSources/fcrypt/.cvsignore deleted file mode 100644 index 57c4bccb..00000000 --- a/ZopeProducts/exUserFolder/CryptoSources/fcrypt/.cvsignore +++ /dev/null @@ -1,4 +0,0 @@ -*.pyc -*.pyo -*~ -.*.swp diff --git a/ZopeProducts/exUserFolder/CryptoSources/fcrypt/ChangeLog b/ZopeProducts/exUserFolder/CryptoSources/fcrypt/ChangeLog deleted file mode 100644 index 70299bed..00000000 --- a/ZopeProducts/exUserFolder/CryptoSources/fcrypt/ChangeLog +++ /dev/null @@ -1,35 +0,0 @@ -2001-05-05 Carey Evans - - * fcrypt.py: Add module doc string for pydoc, and other globals - for pydoc as well. Add __all__ for Python 2.1, and add - underscores to the front of private variables and functions. - (_set_key): Remove overly clever copying of globals into default - parameters, explicitly copying _shift2 and _skb before the loop. - (_body): Copy _SPtrans explicitly, as above. Remove CR_ENCRYPT - inline function, and reroll unrolled loop using the contents of - this function. Result: more readable code, and a 400% speedup! - (crypt): Add doc string for pydoc and doctest. - (_test): New function for doctest. - - * setup.py: Add fields for PKG-INFO metadata. - - * README: Add URL of distutils installation manual. - - * LICENSE: Add note about license on fcrypt.py being the union of - my license on the Python code and Eric Young's on the original C. - -2001-03-24 Carey Evans - - * setup.py: Move license to separate file. Change email address - to SpamCop forwardder. Update version to 1.1. - - * fcrypt.py: Update license text and email address. - (crypt): Fix bug where passwords longer than eight characters were - not truncated. - - * README: Update crypt module URL. Remove license text, and add - pointer to LICENSE file. Update email address. - - * MANIFEST.in: Add LICENSE, ChangeLog and MANIFEST.in. - - * LICENSE: New file. diff --git a/ZopeProducts/exUserFolder/CryptoSources/fcrypt/LICENSE b/ZopeProducts/exUserFolder/CryptoSources/fcrypt/LICENSE deleted file mode 100644 index c26e615d..00000000 --- a/ZopeProducts/exUserFolder/CryptoSources/fcrypt/LICENSE +++ /dev/null @@ -1,77 +0,0 @@ - fcrypt.py copyrights and license - -------------------------------- - - -The Python code by Carey Evans has the following license, which is the -original Python license with the serial numbers filed off, and the -restrictions on advertising removed. - - Copyright (C) 2001, 2001 Carey Evans - - Permission to use, copy, modify, and distribute this software and its - documentation for any purpose and without fee is hereby granted, - provided that the above copyright notice appear in all copies and that - both that copyright notice and this permission notice appear in - supporting documentation. - - CAREY EVANS DISCLAIMS ALL WARRANTIES WITH REGARD TO THIS SOFTWARE, - INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS, IN NO - EVENT SHALL CAREY EVANS BE LIABLE FOR ANY SPECIAL, INDIRECT OR - CONSEQUENTIAL DAMAGES OR ANY DAMAGES WHATSOEVER RESULTING FROM LOSS OF - USE, DATA OR PROFITS, WHETHER IN AN ACTION OF CONTRACT, NEGLIGENCE OR - OTHER TORTIOUS ACTION, ARISING OUT OF OR IN CONNECTION WITH THE USE OR - PERFORMANCE OF THIS SOFTWARE. - - -The original C code on which this module was based has the following -more restrictive license, so the source for fcrypt.py should be -considered to be covered by the union of my license and Eric Young's. - - This library is free for commercial and non-commercial use as long as - the following conditions are aheared to. The following conditions - apply to all code found in this distribution, be it the RC4, RSA, - lhash, DES, etc., code; not just the SSL code. The SSL documentation - included with this distribution is covered by the same copyright terms - except that the holder is Tim Hudson (tjh@mincom.oz.au). - - Copyright remains Eric Young's, and as such any Copyright notices in - the code are not to be removed. - If this package is used in a product, Eric Young should be given attribution - as the author of the parts of the library used. - This can be in the form of a textual message at program startup or - in documentation (online or textual) provided with the package. - - Redistribution and use in source and binary forms, with or without - modification, are permitted provided that the following conditions - are met: - 1. Redistributions of source code must retain the copyright - notice, this list of conditions and the following disclaimer. - 2. Redistributions in binary form must reproduce the above copyright - notice, this list of conditions and the following disclaimer in the - documentation and/or other materials provided with the distribution. - 3. All advertising materials mentioning features or use of this software - must display the following acknowledgement: - "This product includes cryptographic software written by - Eric Young (eay@mincom.oz.au)" - The word 'cryptographic' can be left out if the rouines from the library - being used are not cryptographic related :-). - 4. If you include any Windows specific code (or a derivative thereof) from - the apps directory (application code) you must include an acknowledgement: - "This product includes software written by Tim Hudson (tjh@mincom.oz.au)" - - THIS SOFTWARE IS PROVIDED BY ERIC YOUNG ``AS IS'' AND - ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE - IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE - ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE - FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL - DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS - OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) - HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT - LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY - OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF - SUCH DAMAGE. - - The licence and distribution terms for any publically available version or - derivative of this code cannot be changed. i.e. this code cannot simply be - copied and put under another distribution licence - [including the GNU Public Licence.] diff --git a/ZopeProducts/exUserFolder/CryptoSources/fcrypt/MANIFEST.in b/ZopeProducts/exUserFolder/CryptoSources/fcrypt/MANIFEST.in deleted file mode 100644 index a42d250c..00000000 --- a/ZopeProducts/exUserFolder/CryptoSources/fcrypt/MANIFEST.in +++ /dev/null @@ -1 +0,0 @@ -include LICENSE ChangeLog MANIFEST.in diff --git a/ZopeProducts/exUserFolder/CryptoSources/fcrypt/PKG-INFO b/ZopeProducts/exUserFolder/CryptoSources/fcrypt/PKG-INFO deleted file mode 100644 index c35737e0..00000000 --- a/ZopeProducts/exUserFolder/CryptoSources/fcrypt/PKG-INFO +++ /dev/null @@ -1,13 +0,0 @@ -Metadata-Version: 1.0 -Name: fcrypt -Version: 1.2 -Summary: The Unix password crypt function. -Home-page: http://home.clear.net.nz/pages/c.evans/sw/ -Author: Carey Evans -Author-email: careye@spamcop.net -License: BSD -Description: A pure Python implementation of the Unix DES password crypt function, - based on Eric Young's fcrypt.c. It works with any version of Python - from version 1.5 or higher, and because it's pure Python it doesn't - need a C compiler to install it. -Platform: UNKNOWN diff --git a/ZopeProducts/exUserFolder/CryptoSources/fcrypt/README b/ZopeProducts/exUserFolder/CryptoSources/fcrypt/README deleted file mode 100644 index 168500ff..00000000 --- a/ZopeProducts/exUserFolder/CryptoSources/fcrypt/README +++ /dev/null @@ -1,33 +0,0 @@ - fcrypt.py - --------- - -This is a pure Python implementation of the Unix DES password crypt -function. It was ported from C code by Eric Young (eay@mincom.oz.au). -See the file LICENSE for copyright and license details. - -This module is packaged with Distutils. If you have this installed, -or it came with your version of Python, you can install it by typing: - - python setup.py install - -If not, you can just copy `fcrypt.py' into a directory on your Python -library path, or into the same directory as the program that wants to -use it. - -For more information, see the documentation for Python's built-in -crypt module at: - - http://www.python.org/doc/current/lib/module-crypt.html - -Eric Young's fcrypt.c is available from: - - ftp://ftp.psy.uq.oz.au/pub/Crypto/DES/ - -For more Distutils information, see: - - http://www.python.org/doc/current/inst/inst.html - http://www.python.org/sigs/distutils-sig/ - --- -Carey Evans -5 May 2001 diff --git a/ZopeProducts/exUserFolder/CryptoSources/fcrypt/__init__.py b/ZopeProducts/exUserFolder/CryptoSources/fcrypt/__init__.py deleted file mode 100644 index 97f6031c..00000000 --- a/ZopeProducts/exUserFolder/CryptoSources/fcrypt/__init__.py +++ /dev/null @@ -1 +0,0 @@ -import fcrypt diff --git a/ZopeProducts/exUserFolder/CryptoSources/fcrypt/fcrypt.py b/ZopeProducts/exUserFolder/CryptoSources/fcrypt/fcrypt.py deleted file mode 100644 index 760347cb..00000000 --- a/ZopeProducts/exUserFolder/CryptoSources/fcrypt/fcrypt.py +++ /dev/null @@ -1,602 +0,0 @@ -# fcrypt.py - -"""Unix crypt(3) password hash algorithm. - -This is a port to Python of the standard Unix password crypt function. -It's a single self-contained source file that works with any version -of Python from version 1.5 or higher. The code is based on Eric -Young's optimised crypt in C. - -Python fcrypt is intended for users whose Python installation has not -had the crypt module enabled, or whose C library doesn't include the -crypt function. See the documentation for the Python crypt module for -more information: - - http://www.python.org/doc/current/lib/module-crypt.html - -The crypt() function is a one-way hash function, intended to hide a -password such that the only way to find out the original password is -to guess values until you get a match. If you need to encrypt and -decrypt data, this is not the module for you. - -There are at least two packages providing Python cryptography support: -M2Crypto at , and amkCrypto at -. - -Functions: - - crypt() -- return hashed password -""" - -__author__ = 'Carey Evans ' -__version__ = '1.2' -__date__ = '6 May 2001' -__credits__ = '''michal j wallace for inspiring me to write this. -Eric Young for the C code this module was copied from.''' - -__all__ = ['crypt'] - - -# Copyright (C) 2000, 2001 Carey Evans -# -# Permission to use, copy, modify, and distribute this software and -# its documentation for any purpose and without fee is hereby granted, -# provided that the above copyright notice appear in all copies and -# that both that copyright notice and this permission notice appear in -# supporting documentation. -# -# CAREY EVANS DISCLAIMS ALL WARRANTIES WITH REGARD TO THIS SOFTWARE, -# INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS, IN NO -# EVENT SHALL CAREY EVANS BE LIABLE FOR ANY SPECIAL, INDIRECT OR -# CONSEQUENTIAL DAMAGES OR ANY DAMAGES WHATSOEVER RESULTING FROM LOSS OF -# USE, DATA OR PROFITS, WHETHER IN AN ACTION OF CONTRACT, NEGLIGENCE OR -# OTHER TORTIOUS ACTION, ARISING OUT OF OR IN CONNECTION WITH THE USE OR -# PERFORMANCE OF THIS SOFTWARE. - -# Based on C code by Eric Young (eay@mincom.oz.au), which has the -# following copyright. Especially note condition 3, which imposes -# extra restrictions on top of the standard Python license used above. -# -# The fcrypt.c source is available from: -# ftp://ftp.psy.uq.oz.au/pub/Crypto/DES/ - -# ----- BEGIN fcrypt.c LICENSE ----- -# -# This library is free for commercial and non-commercial use as long as -# the following conditions are aheared to. The following conditions -# apply to all code found in this distribution, be it the RC4, RSA, -# lhash, DES, etc., code; not just the SSL code. The SSL documentation -# included with this distribution is covered by the same copyright terms -# except that the holder is Tim Hudson (tjh@mincom.oz.au). -# -# Copyright remains Eric Young's, and as such any Copyright notices in -# the code are not to be removed. -# If this package is used in a product, Eric Young should be given attribution -# as the author of the parts of the library used. -# This can be in the form of a textual message at program startup or -# in documentation (online or textual) provided with the package. -# -# Redistribution and use in source and binary forms, with or without -# modification, are permitted provided that the following conditions -# are met: -# 1. Redistributions of source code must retain the copyright -# notice, this list of conditions and the following disclaimer. -# 2. Redistributions in binary form must reproduce the above copyright -# notice, this list of conditions and the following disclaimer in the -# documentation and/or other materials provided with the distribution. -# 3. All advertising materials mentioning features or use of this software -# must display the following acknowledgement: -# "This product includes cryptographic software written by -# Eric Young (eay@mincom.oz.au)" -# The word 'cryptographic' can be left out if the rouines from the library -# being used are not cryptographic related :-). -# 4. If you include any Windows specific code (or a derivative thereof) from -# the apps directory (application code) you must include an acknowledgement: -# "This product includes software written by Tim Hudson (tjh@mincom.oz.au)" -# -# THIS SOFTWARE IS PROVIDED BY ERIC YOUNG ``AS IS'' AND -# ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE -# IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE -# ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE -# FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL -# DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS -# OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) -# HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT -# LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY -# OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF -# SUCH DAMAGE. -# -# The licence and distribution terms for any publically available version or -# derivative of this code cannot be changed. i.e. this code cannot simply be -# copied and put under another distribution licence -# [including the GNU Public Licence.] -# -# ----- END fcrypt.c LICENSE ----- - - -import string, struct - - -_ITERATIONS = 16 - -_SPtrans = ( - # nibble 0 - [ 0x00820200, 0x00020000, 0x80800000, 0x80820200, - 0x00800000, 0x80020200, 0x80020000, 0x80800000, - 0x80020200, 0x00820200, 0x00820000, 0x80000200, - 0x80800200, 0x00800000, 0x00000000, 0x80020000, - 0x00020000, 0x80000000, 0x00800200, 0x00020200, - 0x80820200, 0x00820000, 0x80000200, 0x00800200, - 0x80000000, 0x00000200, 0x00020200, 0x80820000, - 0x00000200, 0x80800200, 0x80820000, 0x00000000, - 0x00000000, 0x80820200, 0x00800200, 0x80020000, - 0x00820200, 0x00020000, 0x80000200, 0x00800200, - 0x80820000, 0x00000200, 0x00020200, 0x80800000, - 0x80020200, 0x80000000, 0x80800000, 0x00820000, - 0x80820200, 0x00020200, 0x00820000, 0x80800200, - 0x00800000, 0x80000200, 0x80020000, 0x00000000, - 0x00020000, 0x00800000, 0x80800200, 0x00820200, - 0x80000000, 0x80820000, 0x00000200, 0x80020200 ], - - # nibble 1 - [ 0x10042004, 0x00000000, 0x00042000, 0x10040000, - 0x10000004, 0x00002004, 0x10002000, 0x00042000, - 0x00002000, 0x10040004, 0x00000004, 0x10002000, - 0x00040004, 0x10042000, 0x10040000, 0x00000004, - 0x00040000, 0x10002004, 0x10040004, 0x00002000, - 0x00042004, 0x10000000, 0x00000000, 0x00040004, - 0x10002004, 0x00042004, 0x10042000, 0x10000004, - 0x10000000, 0x00040000, 0x00002004, 0x10042004, - 0x00040004, 0x10042000, 0x10002000, 0x00042004, - 0x10042004, 0x00040004, 0x10000004, 0x00000000, - 0x10000000, 0x00002004, 0x00040000, 0x10040004, - 0x00002000, 0x10000000, 0x00042004, 0x10002004, - 0x10042000, 0x00002000, 0x00000000, 0x10000004, - 0x00000004, 0x10042004, 0x00042000, 0x10040000, - 0x10040004, 0x00040000, 0x00002004, 0x10002000, - 0x10002004, 0x00000004, 0x10040000, 0x00042000 ], - - # nibble 2 - [ 0x41000000, 0x01010040, 0x00000040, 0x41000040, - 0x40010000, 0x01000000, 0x41000040, 0x00010040, - 0x01000040, 0x00010000, 0x01010000, 0x40000000, - 0x41010040, 0x40000040, 0x40000000, 0x41010000, - 0x00000000, 0x40010000, 0x01010040, 0x00000040, - 0x40000040, 0x41010040, 0x00010000, 0x41000000, - 0x41010000, 0x01000040, 0x40010040, 0x01010000, - 0x00010040, 0x00000000, 0x01000000, 0x40010040, - 0x01010040, 0x00000040, 0x40000000, 0x00010000, - 0x40000040, 0x40010000, 0x01010000, 0x41000040, - 0x00000000, 0x01010040, 0x00010040, 0x41010000, - 0x40010000, 0x01000000, 0x41010040, 0x40000000, - 0x40010040, 0x41000000, 0x01000000, 0x41010040, - 0x00010000, 0x01000040, 0x41000040, 0x00010040, - 0x01000040, 0x00000000, 0x41010000, 0x40000040, - 0x41000000, 0x40010040, 0x00000040, 0x01010000 ], - - # nibble 3 - [ 0x00100402, 0x04000400, 0x00000002, 0x04100402, - 0x00000000, 0x04100000, 0x04000402, 0x00100002, - 0x04100400, 0x04000002, 0x04000000, 0x00000402, - 0x04000002, 0x00100402, 0x00100000, 0x04000000, - 0x04100002, 0x00100400, 0x00000400, 0x00000002, - 0x00100400, 0x04000402, 0x04100000, 0x00000400, - 0x00000402, 0x00000000, 0x00100002, 0x04100400, - 0x04000400, 0x04100002, 0x04100402, 0x00100000, - 0x04100002, 0x00000402, 0x00100000, 0x04000002, - 0x00100400, 0x04000400, 0x00000002, 0x04100000, - 0x04000402, 0x00000000, 0x00000400, 0x00100002, - 0x00000000, 0x04100002, 0x04100400, 0x00000400, - 0x04000000, 0x04100402, 0x00100402, 0x00100000, - 0x04100402, 0x00000002, 0x04000400, 0x00100402, - 0x00100002, 0x00100400, 0x04100000, 0x04000402, - 0x00000402, 0x04000000, 0x04000002, 0x04100400 ], - - # nibble 4 - [ 0x02000000, 0x00004000, 0x00000100, 0x02004108, - 0x02004008, 0x02000100, 0x00004108, 0x02004000, - 0x00004000, 0x00000008, 0x02000008, 0x00004100, - 0x02000108, 0x02004008, 0x02004100, 0x00000000, - 0x00004100, 0x02000000, 0x00004008, 0x00000108, - 0x02000100, 0x00004108, 0x00000000, 0x02000008, - 0x00000008, 0x02000108, 0x02004108, 0x00004008, - 0x02004000, 0x00000100, 0x00000108, 0x02004100, - 0x02004100, 0x02000108, 0x00004008, 0x02004000, - 0x00004000, 0x00000008, 0x02000008, 0x02000100, - 0x02000000, 0x00004100, 0x02004108, 0x00000000, - 0x00004108, 0x02000000, 0x00000100, 0x00004008, - 0x02000108, 0x00000100, 0x00000000, 0x02004108, - 0x02004008, 0x02004100, 0x00000108, 0x00004000, - 0x00004100, 0x02004008, 0x02000100, 0x00000108, - 0x00000008, 0x00004108, 0x02004000, 0x02000008 ], - - # nibble 5 - [ 0x20000010, 0x00080010, 0x00000000, 0x20080800, - 0x00080010, 0x00000800, 0x20000810, 0x00080000, - 0x00000810, 0x20080810, 0x00080800, 0x20000000, - 0x20000800, 0x20000010, 0x20080000, 0x00080810, - 0x00080000, 0x20000810, 0x20080010, 0x00000000, - 0x00000800, 0x00000010, 0x20080800, 0x20080010, - 0x20080810, 0x20080000, 0x20000000, 0x00000810, - 0x00000010, 0x00080800, 0x00080810, 0x20000800, - 0x00000810, 0x20000000, 0x20000800, 0x00080810, - 0x20080800, 0x00080010, 0x00000000, 0x20000800, - 0x20000000, 0x00000800, 0x20080010, 0x00080000, - 0x00080010, 0x20080810, 0x00080800, 0x00000010, - 0x20080810, 0x00080800, 0x00080000, 0x20000810, - 0x20000010, 0x20080000, 0x00080810, 0x00000000, - 0x00000800, 0x20000010, 0x20000810, 0x20080800, - 0x20080000, 0x00000810, 0x00000010, 0x20080010 ], - - # nibble 6 - [ 0x00001000, 0x00000080, 0x00400080, 0x00400001, - 0x00401081, 0x00001001, 0x00001080, 0x00000000, - 0x00400000, 0x00400081, 0x00000081, 0x00401000, - 0x00000001, 0x00401080, 0x00401000, 0x00000081, - 0x00400081, 0x00001000, 0x00001001, 0x00401081, - 0x00000000, 0x00400080, 0x00400001, 0x00001080, - 0x00401001, 0x00001081, 0x00401080, 0x00000001, - 0x00001081, 0x00401001, 0x00000080, 0x00400000, - 0x00001081, 0x00401000, 0x00401001, 0x00000081, - 0x00001000, 0x00000080, 0x00400000, 0x00401001, - 0x00400081, 0x00001081, 0x00001080, 0x00000000, - 0x00000080, 0x00400001, 0x00000001, 0x00400080, - 0x00000000, 0x00400081, 0x00400080, 0x00001080, - 0x00000081, 0x00001000, 0x00401081, 0x00400000, - 0x00401080, 0x00000001, 0x00001001, 0x00401081, - 0x00400001, 0x00401080, 0x00401000, 0x00001001 ], - - # nibble 7 - [ 0x08200020, 0x08208000, 0x00008020, 0x00000000, - 0x08008000, 0x00200020, 0x08200000, 0x08208020, - 0x00000020, 0x08000000, 0x00208000, 0x00008020, - 0x00208020, 0x08008020, 0x08000020, 0x08200000, - 0x00008000, 0x00208020, 0x00200020, 0x08008000, - 0x08208020, 0x08000020, 0x00000000, 0x00208000, - 0x08000000, 0x00200000, 0x08008020, 0x08200020, - 0x00200000, 0x00008000, 0x08208000, 0x00000020, - 0x00200000, 0x00008000, 0x08000020, 0x08208020, - 0x00008020, 0x08000000, 0x00000000, 0x00208000, - 0x08200020, 0x08008020, 0x08008000, 0x00200020, - 0x08208000, 0x00000020, 0x00200020, 0x08008000, - 0x08208020, 0x00200000, 0x08200000, 0x08000020, - 0x00208000, 0x00008020, 0x08008020, 0x08200000, - 0x00000020, 0x08208000, 0x00208020, 0x00000000, - 0x08000000, 0x08200020, 0x00008000, 0x00208020 ] ) - -_skb = ( - # for C bits (numbered as per FIPS 46) 1 2 3 4 5 6 - [ 0x00000000, 0x00000010, 0x20000000, 0x20000010, - 0x00010000, 0x00010010, 0x20010000, 0x20010010, - 0x00000800, 0x00000810, 0x20000800, 0x20000810, - 0x00010800, 0x00010810, 0x20010800, 0x20010810, - 0x00000020, 0x00000030, 0x20000020, 0x20000030, - 0x00010020, 0x00010030, 0x20010020, 0x20010030, - 0x00000820, 0x00000830, 0x20000820, 0x20000830, - 0x00010820, 0x00010830, 0x20010820, 0x20010830, - 0x00080000, 0x00080010, 0x20080000, 0x20080010, - 0x00090000, 0x00090010, 0x20090000, 0x20090010, - 0x00080800, 0x00080810, 0x20080800, 0x20080810, - 0x00090800, 0x00090810, 0x20090800, 0x20090810, - 0x00080020, 0x00080030, 0x20080020, 0x20080030, - 0x00090020, 0x00090030, 0x20090020, 0x20090030, - 0x00080820, 0x00080830, 0x20080820, 0x20080830, - 0x00090820, 0x00090830, 0x20090820, 0x20090830 ], - - # for C bits (numbered as per FIPS 46) 7 8 10 11 12 13 - [ 0x00000000, 0x02000000, 0x00002000, 0x02002000, - 0x00200000, 0x02200000, 0x00202000, 0x02202000, - 0x00000004, 0x02000004, 0x00002004, 0x02002004, - 0x00200004, 0x02200004, 0x00202004, 0x02202004, - 0x00000400, 0x02000400, 0x00002400, 0x02002400, - 0x00200400, 0x02200400, 0x00202400, 0x02202400, - 0x00000404, 0x02000404, 0x00002404, 0x02002404, - 0x00200404, 0x02200404, 0x00202404, 0x02202404, - 0x10000000, 0x12000000, 0x10002000, 0x12002000, - 0x10200000, 0x12200000, 0x10202000, 0x12202000, - 0x10000004, 0x12000004, 0x10002004, 0x12002004, - 0x10200004, 0x12200004, 0x10202004, 0x12202004, - 0x10000400, 0x12000400, 0x10002400, 0x12002400, - 0x10200400, 0x12200400, 0x10202400, 0x12202400, - 0x10000404, 0x12000404, 0x10002404, 0x12002404, - 0x10200404, 0x12200404, 0x10202404, 0x12202404 ], - - # for C bits (numbered as per FIPS 46) 14 15 16 17 19 20 - [ 0x00000000, 0x00000001, 0x00040000, 0x00040001, - 0x01000000, 0x01000001, 0x01040000, 0x01040001, - 0x00000002, 0x00000003, 0x00040002, 0x00040003, - 0x01000002, 0x01000003, 0x01040002, 0x01040003, - 0x00000200, 0x00000201, 0x00040200, 0x00040201, - 0x01000200, 0x01000201, 0x01040200, 0x01040201, - 0x00000202, 0x00000203, 0x00040202, 0x00040203, - 0x01000202, 0x01000203, 0x01040202, 0x01040203, - 0x08000000, 0x08000001, 0x08040000, 0x08040001, - 0x09000000, 0x09000001, 0x09040000, 0x09040001, - 0x08000002, 0x08000003, 0x08040002, 0x08040003, - 0x09000002, 0x09000003, 0x09040002, 0x09040003, - 0x08000200, 0x08000201, 0x08040200, 0x08040201, - 0x09000200, 0x09000201, 0x09040200, 0x09040201, - 0x08000202, 0x08000203, 0x08040202, 0x08040203, - 0x09000202, 0x09000203, 0x09040202, 0x09040203 ], - - # for C bits (numbered as per FIPS 46) 21 23 24 26 27 28 - [ 0x00000000, 0x00100000, 0x00000100, 0x00100100, - 0x00000008, 0x00100008, 0x00000108, 0x00100108, - 0x00001000, 0x00101000, 0x00001100, 0x00101100, - 0x00001008, 0x00101008, 0x00001108, 0x00101108, - 0x04000000, 0x04100000, 0x04000100, 0x04100100, - 0x04000008, 0x04100008, 0x04000108, 0x04100108, - 0x04001000, 0x04101000, 0x04001100, 0x04101100, - 0x04001008, 0x04101008, 0x04001108, 0x04101108, - 0x00020000, 0x00120000, 0x00020100, 0x00120100, - 0x00020008, 0x00120008, 0x00020108, 0x00120108, - 0x00021000, 0x00121000, 0x00021100, 0x00121100, - 0x00021008, 0x00121008, 0x00021108, 0x00121108, - 0x04020000, 0x04120000, 0x04020100, 0x04120100, - 0x04020008, 0x04120008, 0x04020108, 0x04120108, - 0x04021000, 0x04121000, 0x04021100, 0x04121100, - 0x04021008, 0x04121008, 0x04021108, 0x04121108 ], - - # for D bits (numbered as per FIPS 46) 1 2 3 4 5 6 - [ 0x00000000, 0x10000000, 0x00010000, 0x10010000, - 0x00000004, 0x10000004, 0x00010004, 0x10010004, - 0x20000000, 0x30000000, 0x20010000, 0x30010000, - 0x20000004, 0x30000004, 0x20010004, 0x30010004, - 0x00100000, 0x10100000, 0x00110000, 0x10110000, - 0x00100004, 0x10100004, 0x00110004, 0x10110004, - 0x20100000, 0x30100000, 0x20110000, 0x30110000, - 0x20100004, 0x30100004, 0x20110004, 0x30110004, - 0x00001000, 0x10001000, 0x00011000, 0x10011000, - 0x00001004, 0x10001004, 0x00011004, 0x10011004, - 0x20001000, 0x30001000, 0x20011000, 0x30011000, - 0x20001004, 0x30001004, 0x20011004, 0x30011004, - 0x00101000, 0x10101000, 0x00111000, 0x10111000, - 0x00101004, 0x10101004, 0x00111004, 0x10111004, - 0x20101000, 0x30101000, 0x20111000, 0x30111000, - 0x20101004, 0x30101004, 0x20111004, 0x30111004 ], - - # for D bits (numbered as per FIPS 46) 8 9 11 12 13 14 - [ 0x00000000, 0x08000000, 0x00000008, 0x08000008, - 0x00000400, 0x08000400, 0x00000408, 0x08000408, - 0x00020000, 0x08020000, 0x00020008, 0x08020008, - 0x00020400, 0x08020400, 0x00020408, 0x08020408, - 0x00000001, 0x08000001, 0x00000009, 0x08000009, - 0x00000401, 0x08000401, 0x00000409, 0x08000409, - 0x00020001, 0x08020001, 0x00020009, 0x08020009, - 0x00020401, 0x08020401, 0x00020409, 0x08020409, - 0x02000000, 0x0A000000, 0x02000008, 0x0A000008, - 0x02000400, 0x0A000400, 0x02000408, 0x0A000408, - 0x02020000, 0x0A020000, 0x02020008, 0x0A020008, - 0x02020400, 0x0A020400, 0x02020408, 0x0A020408, - 0x02000001, 0x0A000001, 0x02000009, 0x0A000009, - 0x02000401, 0x0A000401, 0x02000409, 0x0A000409, - 0x02020001, 0x0A020001, 0x02020009, 0x0A020009, - 0x02020401, 0x0A020401, 0x02020409, 0x0A020409 ], - - # for D bits (numbered as per FIPS 46) 16 17 18 19 20 21 - [ 0x00000000, 0x00000100, 0x00080000, 0x00080100, - 0x01000000, 0x01000100, 0x01080000, 0x01080100, - 0x00000010, 0x00000110, 0x00080010, 0x00080110, - 0x01000010, 0x01000110, 0x01080010, 0x01080110, - 0x00200000, 0x00200100, 0x00280000, 0x00280100, - 0x01200000, 0x01200100, 0x01280000, 0x01280100, - 0x00200010, 0x00200110, 0x00280010, 0x00280110, - 0x01200010, 0x01200110, 0x01280010, 0x01280110, - 0x00000200, 0x00000300, 0x00080200, 0x00080300, - 0x01000200, 0x01000300, 0x01080200, 0x01080300, - 0x00000210, 0x00000310, 0x00080210, 0x00080310, - 0x01000210, 0x01000310, 0x01080210, 0x01080310, - 0x00200200, 0x00200300, 0x00280200, 0x00280300, - 0x01200200, 0x01200300, 0x01280200, 0x01280300, - 0x00200210, 0x00200310, 0x00280210, 0x00280310, - 0x01200210, 0x01200310, 0x01280210, 0x01280310 ], - - # for D bits (numbered as per FIPS 46) 22 23 24 25 27 28 - [ 0x00000000, 0x04000000, 0x00040000, 0x04040000, - 0x00000002, 0x04000002, 0x00040002, 0x04040002, - 0x00002000, 0x04002000, 0x00042000, 0x04042000, - 0x00002002, 0x04002002, 0x00042002, 0x04042002, - 0x00000020, 0x04000020, 0x00040020, 0x04040020, - 0x00000022, 0x04000022, 0x00040022, 0x04040022, - 0x00002020, 0x04002020, 0x00042020, 0x04042020, - 0x00002022, 0x04002022, 0x00042022, 0x04042022, - 0x00000800, 0x04000800, 0x00040800, 0x04040800, - 0x00000802, 0x04000802, 0x00040802, 0x04040802, - 0x00002800, 0x04002800, 0x00042800, 0x04042800, - 0x00002802, 0x04002802, 0x00042802, 0x04042802, - 0x00000820, 0x04000820, 0x00040820, 0x04040820, - 0x00000822, 0x04000822, 0x00040822, 0x04040822, - 0x00002820, 0x04002820, 0x00042820, 0x04042820, - 0x00002822, 0x04002822, 0x00042822, 0x04042822 ] ) - -_shifts2 = (0,0,1,1,1,1,1,1,0,1,1,1,1,1,1,0) - -_con_salt = [ - 0xD2,0xD3,0xD4,0xD5,0xD6,0xD7,0xD8,0xD9, - 0xDA,0xDB,0xDC,0xDD,0xDE,0xDF,0xE0,0xE1, - 0xE2,0xE3,0xE4,0xE5,0xE6,0xE7,0xE8,0xE9, - 0xEA,0xEB,0xEC,0xED,0xEE,0xEF,0xF0,0xF1, - 0xF2,0xF3,0xF4,0xF5,0xF6,0xF7,0xF8,0xF9, - 0xFA,0xFB,0xFC,0xFD,0xFE,0xFF,0x00,0x01, - 0x02,0x03,0x04,0x05,0x06,0x07,0x08,0x09, - 0x0A,0x0B,0x05,0x06,0x07,0x08,0x09,0x0A, - 0x0B,0x0C,0x0D,0x0E,0x0F,0x10,0x11,0x12, - 0x13,0x14,0x15,0x16,0x17,0x18,0x19,0x1A, - 0x1B,0x1C,0x1D,0x1E,0x1F,0x20,0x21,0x22, - 0x23,0x24,0x25,0x20,0x21,0x22,0x23,0x24, - 0x25,0x26,0x27,0x28,0x29,0x2A,0x2B,0x2C, - 0x2D,0x2E,0x2F,0x30,0x31,0x32,0x33,0x34, - 0x35,0x36,0x37,0x38,0x39,0x3A,0x3B,0x3C, - 0x3D,0x3E,0x3F,0x40,0x41,0x42,0x43,0x44 ] - -_cov_2char = './0123456789ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz' - - -def _HPERM_OP(a): - """Clever bit manipulation.""" - t = ((a << 18) ^ a) & 0xcccc0000 - return a ^ t ^ ((t >> 18) & 0x3fff) - -def _PERM_OP(a,b,n,m): - """Cleverer bit manipulation.""" - t = ((a >> n) ^ b) & m - b = b ^ t - a = a ^ (t << n) - return a,b - - -def _set_key(password): - """Generate DES key schedule from ASCII password.""" - - c,d = struct.unpack('> 16) | ((c >> 4) & 0x0f000000)) - c = c & 0x0fffffff - - # Copy globals into local variables for loop. - shifts2 = _shifts2 - skbc0, skbc1, skbc2, skbc3, skbd0, skbd1, skbd2, skbd3 = _skb - - k = [0] * (_ITERATIONS * 2) - - for i in range(_ITERATIONS): - # Only operates on top 28 bits. - if shifts2[i]: - c = (c >> 2) | (c << 26) - d = (d >> 2) | (d << 26) - else: - c = (c >> 1) | (c << 27) - d = (d >> 1) | (d << 27) - c = c & 0x0fffffff - d = d & 0x0fffffff - - s = ( skbc0[ c & 0x3f ] | - skbc1[((c>> 6) & 0x03) | ((c>> 7) & 0x3c)] | - skbc2[((c>>13) & 0x0f) | ((c>>14) & 0x30)] | - skbc3[((c>>20) & 0x01) | - ((c>>21) & 0x06) | ((c>>22) & 0x38)] ) - - t = ( skbd0[ d & 0x3f ] | - skbd1[((d>> 7) & 0x03) | ((d>> 8) & 0x3c)] | - skbd2[((d>>15) & 0x3f) ] | - skbd3[((d>>21) & 0x0f) | ((d>>22) & 0x30)] ) - - k[2*i] = ((t << 16) | (s & 0x0000ffff)) & 0xffffffff - s = (s >> 16) | (t & 0xffff0000) - - # Top bit of s may be 1. - s = (s << 4) | ((s >> 28) & 0x0f) - k[2*i + 1] = s & 0xffffffff - - return k - - -def _body(ks, E0, E1): - """Use the key schedule ks and salt E0, E1 to create the password hash.""" - - # Copy global variable into locals for loop. - SP0, SP1, SP2, SP3, SP4, SP5, SP6, SP7 = _SPtrans - - inner = range(0, _ITERATIONS*2, 2) - l = r = 0 - for j in range(25): - l,r = r,l - for i in inner: - t = r ^ ((r >> 16) & 0xffff) - u = t & E0 - t = t & E1 - u = u ^ (u << 16) ^ r ^ ks[i] - t = t ^ (t << 16) ^ r ^ ks[i+1] - t = ((t >> 4) & 0x0fffffff) | (t << 28) - - l,r = r,(SP1[(t ) & 0x3f] ^ SP3[(t>> 8) & 0x3f] ^ - SP5[(t>>16) & 0x3f] ^ SP7[(t>>24) & 0x3f] ^ - SP0[(u ) & 0x3f] ^ SP2[(u>> 8) & 0x3f] ^ - SP4[(u>>16) & 0x3f] ^ SP6[(u>>24) & 0x3f] ^ l) - - l = ((l >> 1) & 0x7fffffff) | ((l & 0x1) << 31) - r = ((r >> 1) & 0x7fffffff) | ((r & 0x1) << 31) - - r,l = _PERM_OP(r, l, 1, 0x55555555) - l,r = _PERM_OP(l, r, 8, 0x00ff00ff) - r,l = _PERM_OP(r, l, 2, 0x33333333) - l,r = _PERM_OP(l, r, 16, 0x0000ffff) - r,l = _PERM_OP(r, l, 4, 0x0f0f0f0f) - - return l,r - - -def crypt(password, salt): - """Generate an encrypted hash from the passed password. If the password -is longer than eight characters, only the first eight will be used. - -The first two characters of the salt are used to modify the encryption -algorithm used to generate in the hash in one of 4096 different ways. -The characters for the salt must be alphanumeric, '.' or '/'. - -The returned hash begins with the two characters of the salt, and -should be passed as the salt to verify the password. - -Example: - - >>> from fcrypt import crypt - >>> password = 'AlOtBsOl' - >>> salt = 'cE' - >>> hash = crypt(password, salt) - >>> hash - 'cEpWz5IUCShqM' - >>> crypt(password, hash) == hash - 1 - >>> crypt('IaLaIoK', hash) == hash - 0 - -In practice, you would read the password using something like the -getpass module, and generate the salt randomly: - - >>> import random, string - >>> saltchars = string.letters + string.digits + './' - >>> salt = random.choice(saltchars) + random.choice(saltchars) -""" - - if len(salt) < 2: - salt = salt + 'AA' - - Eswap0 = _con_salt[ord(salt[0])] - Eswap1 = _con_salt[ord(salt[1])] << 4 - - ks = _set_key((password + '\0\0\0\0\0\0\0\0')[:8]) - out1,out2 = _body(ks, Eswap0, Eswap1) - - # Convert numbers to big-endian... - be1, be2 = struct.unpack('>ii', struct.pack('> 8) & 0xffffff, - ((be1 << 16) & 0xff0000) | ((be2 >> 16) & 0xffff), - (be2 << 8) & 0xffff00] - - # Convert to ASCII encoding, 4 characters for each 24 bits. - res = [salt[0], salt[1]] - for b in b24: - for i in range(18, -6, -6): - res.append(_cov_2char[(b >> i) & 0x3f]) - - return string.join(res[:13], '') - -def _test(): - """Run doctest on fcrypt module.""" - import doctest, fcrypt - return doctest.testmod(fcrypt) - -if __name__ == '__main__': - _test() diff --git a/ZopeProducts/exUserFolder/CryptoSources/fcrypt/setup.py b/ZopeProducts/exUserFolder/CryptoSources/fcrypt/setup.py deleted file mode 100644 index 33ccb6d3..00000000 --- a/ZopeProducts/exUserFolder/CryptoSources/fcrypt/setup.py +++ /dev/null @@ -1,22 +0,0 @@ -#!/usr/bin/env python - -# distutils setup script for fcrypt. -# -# Copyright (C) 2000, 2001 Carey Evans - -from distutils.core import setup - -setup( name = 'fcrypt', - version = '1.2', - description = 'The Unix password crypt function.', - author = 'Carey Evans', - author_email = 'careye@spamcop.net', - url = 'http://home.clear.net.nz/pages/c.evans/sw/', - licence = 'BSD', - long_description = """\ -A pure Python implementation of the Unix DES password crypt function, -based on Eric Young's fcrypt.c. It works with any version of Python -from version 1.5 or higher, and because it's pure Python it doesn't -need a C compiler to install it.""", - - py_modules = ['fcrypt'] ) diff --git a/ZopeProducts/exUserFolder/CryptoSources/pass_crypt.py b/ZopeProducts/exUserFolder/CryptoSources/pass_crypt.py deleted file mode 100644 index ef1d2954..00000000 --- a/ZopeProducts/exUserFolder/CryptoSources/pass_crypt.py +++ /dev/null @@ -1,44 +0,0 @@ -# -# Extensible User Folder -# -# (C) Copyright 2000-2004 The Internet (Aust) Pty Ltd -# ACN: 082 081 472 ABN: 83 082 081 472 -# All Rights Reserved -# -# THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND -# ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE -# IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE -# ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE -# FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL -# DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS -# OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) -# HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT -# LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY -# OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF -# SUCH DAMAGE. -# -# Author: Andrew Milton -# $Id: pass_crypt.py,v 1.3 2004/11/18 09:24:46 akm Exp $ - -from Products.exUserFolder.exUserFolder import exUserFolder -from Products.exUserFolder.Plugins import CryptoPluginRegister - -try: - from crypt import crypt -except: - from fcrypt.fcrypt import crypt - - -def cryptPassword(authSource, username, password): - u = authSource.listOneUser(username) - if not u: - salt = username[:2] - else: - salt=u[0]['password'][:2] - - secret = crypt(password, salt) - return secret - - -CryptPlugin=CryptoPluginRegister('Crypt', 'crypt', 'Crypt', cryptPassword) -exUserFolder.cryptoSources['Crypt']=CryptPlugin diff --git a/ZopeProducts/exUserFolder/CryptoSources/pass_md5.py b/ZopeProducts/exUserFolder/CryptoSources/pass_md5.py deleted file mode 100644 index c67af140..00000000 --- a/ZopeProducts/exUserFolder/CryptoSources/pass_md5.py +++ /dev/null @@ -1,47 +0,0 @@ -# -# Extensible User Folder -# -# (C) Copyright 2000-2004 The Internet (Aust) Pty Ltd -# ACN: 082 081 472 ABN: 83 082 081 472 -# All Rights Reserved -# -# THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND -# ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE -# IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE -# ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE -# FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL -# DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS -# OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) -# HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT -# LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY -# OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF -# SUCH DAMAGE. -# -# Author: Andrew Milton -# $Id: pass_md5.py,v 1.1 2004/11/10 14:15:52 akm Exp $ - -import md5, base64, string - -from Products.exUserFolder.exUserFolder import exUserFolder -from Products.exUserFolder.Plugins import CryptoPluginRegister - -# Simple digest -def cryptPassword(authSource, username, password): - digest = md5.new() - digest.update(password) - digest = digest.digest() - secret = string.strip(base64.encodestring(digest)) - return secret - -# Digest includes username -# So two passwords for different users hash differently -def cryptPassword2(authSource, username, password): - newPass = username+':'+password - return cryptPassword(authSource, username, newPass) - - -MD5Plugin1=CryptoPluginRegister('MD51', 'MD5', 'MD5 Password Only', cryptPassword) -exUserFolder.cryptoSources['MD51']=MD5Plugin1 - -MD5Plugin2=CryptoPluginRegister('MD52', 'MD5', 'MD5 Username + Password', cryptPassword2) -exUserFolder.cryptoSources['MD52']=MD5Plugin2 diff --git a/ZopeProducts/exUserFolder/CryptoSources/pass_plain.py b/ZopeProducts/exUserFolder/CryptoSources/pass_plain.py deleted file mode 100644 index 2d29c78d..00000000 --- a/ZopeProducts/exUserFolder/CryptoSources/pass_plain.py +++ /dev/null @@ -1,31 +0,0 @@ -# -# Extensible User Folder -# -# (C) Copyright 2000-2004 The Internet (Aust) Pty Ltd -# ACN: 082 081 472 ABN: 83 082 081 472 -# All Rights Reserved -# -# THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND -# ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE -# IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE -# ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE -# FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL -# DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS -# OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) -# HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT -# LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY -# OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF -# SUCH DAMAGE. -# -# Author: Andrew Milton -# $Id: pass_plain.py,v 1.1 2004/11/10 14:15:52 akm Exp $ - -from Products.exUserFolder.exUserFolder import exUserFolder -from Products.exUserFolder.Plugins import CryptoPluginRegister - -# Simple digest -def cryptPassword(authSource, username, password): - return password - -PlainPlugin=CryptoPluginRegister('Plaintext', 'Plaintext', 'No Encryption', cryptPassword) -exUserFolder.cryptoSources['Plaintext']=PlainPlugin diff --git a/ZopeProducts/exUserFolder/CryptoSources/pass_sha.py b/ZopeProducts/exUserFolder/CryptoSources/pass_sha.py deleted file mode 100644 index a4bc8fd3..00000000 --- a/ZopeProducts/exUserFolder/CryptoSources/pass_sha.py +++ /dev/null @@ -1,41 +0,0 @@ -# -# Extensible User Folder -# -# (C) Copyright 2000-2004 The Internet (Aust) Pty Ltd -# ACN: 082 081 472 ABN: 83 082 081 472 -# All Rights Reserved -# -# THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND -# ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE -# IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE -# ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE -# FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL -# DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS -# OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) -# HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT -# LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY -# OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF -# SUCH DAMAGE. -# -# Author: Andrew Milton -# $Id: pass_sha.py,v 1.1 2004/11/10 14:15:52 akm Exp $ - -import sha -from base64 import encodestring - -from Products.exUserFolder.exUserFolder import exUserFolder -from Products.exUserFolder.Plugins import CryptoPluginRegister - - -def cryptPassword(authSource, username, password): - return encodestring(sha.new(password).digest()) - -def cryptPassword2(authSource, username, password): - newPass = username+':'+password - return cryptPassword(authSource, username, newPass) - -SHAPlugin1=CryptoPluginRegister('SHA1', 'SHA', 'SHA Password Only', cryptPassword) -exUserFolder.cryptoSources['SHA1']=SHAPlugin1 - -SHAPlugin2=CryptoPluginRegister('SHA2', 'SHA', 'SHA Username + Password', cryptPassword2) -exUserFolder.cryptoSources['SHA2']=SHAPlugin2 diff --git a/ZopeProducts/exUserFolder/Extensions/.cvsignore b/ZopeProducts/exUserFolder/Extensions/.cvsignore deleted file mode 100644 index 57c4bccb..00000000 --- a/ZopeProducts/exUserFolder/Extensions/.cvsignore +++ /dev/null @@ -1,4 +0,0 @@ -*.pyc -*.pyo -*~ -.*.swp diff --git a/ZopeProducts/exUserFolder/Extensions/getOldGroups.py b/ZopeProducts/exUserFolder/Extensions/getOldGroups.py deleted file mode 100644 index 9fa8088e..00000000 --- a/ZopeProducts/exUserFolder/Extensions/getOldGroups.py +++ /dev/null @@ -1,20 +0,0 @@ -# This script interrogates the old-skool NuxUserGroups_support_branch -# group structure and outputs a tab-delimited file you can send to -# loadOldGroups. Just in case anyone is using it. :-) -# -# Matt Behrens - -def getOldGroups(self): - "Reconstruct a group list from the old-style _groups property" - from string import join - props = self.currentPropSource.userProperties - groups = {} - for username in props.keys(): - for groupname in props[username].getProperty('_groups', ()): - if not groups.has_key(groupname): - groups[groupname] = [] - groups[groupname].append(username) - out = '' - for groupname in groups.keys(): - out = out + '%s %s\n' % (groupname, join(groups[groupname], ' ')) - return out diff --git a/ZopeProducts/exUserFolder/Extensions/loadOldGroups.py b/ZopeProducts/exUserFolder/Extensions/loadOldGroups.py deleted file mode 100644 index b7f2f702..00000000 --- a/ZopeProducts/exUserFolder/Extensions/loadOldGroups.py +++ /dev/null @@ -1,26 +0,0 @@ -# This takes 'old_groups.txt' from var (create it using getOldGroups) -# and sets up all the groups therein using NuxUserGroups calls. This -# will load a group source if you need to do such a thing. -# -# Matt Behrens - -def loadOldGroups(self): - from os.path import join as pathJoin - from string import split, strip - - groups_file = open(pathJoin(CLIENT_HOME, 'old_groups.txt'), 'r') - out = '' - for group_line in groups_file.readlines(): - group_line_elements = split(strip(group_line), ' ') - group_name = group_line_elements[0] - group_members = group_line_elements[1:] - - if self.getGroupById(group_name, default=None) is None: - out = out + 'adding group %s\n' % group_name - self.userFolderAddGroup(group_name) - - out = out + 'setting group %s membership to %s\n' % (group_name, group_members) - self.setUsersOfGroup(group_members, group_name) - - return out - diff --git a/ZopeProducts/exUserFolder/Extensions/usAuthSourceMethods.py b/ZopeProducts/exUserFolder/Extensions/usAuthSourceMethods.py deleted file mode 100644 index bb43162d..00000000 --- a/ZopeProducts/exUserFolder/Extensions/usAuthSourceMethods.py +++ /dev/null @@ -1,140 +0,0 @@ -# (C) Copyright 2000,2001 The Internet (Aust) Pty Ltd -# ACN: 082 081 472 ABN: 83 082 081 472 -# All Rights Reserved -# -# THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND -# ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE -# IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE -# ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE -# FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL -# DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS -# OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) -# HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT -# LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY -# OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF -# SUCH DAMAGE. -# -# Author: Andrew Milton -# $Id: usAuthSourceMethods.py,v 1.3 2001/12/01 08:40:04 akm Exp $ -# -######################################################################## -# -# This is an example of an Extension Module to provide User Supplied -# Authentication Methods. -# -# It mimics the behaviour of the pgAuthSource Module, and the sql queries -# Used here would be added as ZSQLMethods in the usAuthSource Folder. -# (you can basically cut and paste them from the bottom of this .py file -# into the ZSQL Method Template Area -# -# It's not complete, but, you do get the idea... -# -# Each function becomes usFunctionName -# -# e.g. listOneUser -> usListOneUser -# -import string -from crypt import crypt - -def listOneUser(self,username): - users = [] - result=self.sqlListOneUser(username=username) - for n in result: - username=sqlattr(n,'username') - password=sqlattr(n,'password') - roles=string.split(sqlattr(n,'roles')) - N={'username':username, 'password':password, 'roles':roles} - users.append(N) - return users - -def listUsers(self): - """Returns a list of user names or [] if no users exist""" - users = [] - result=self.sqlListUsers() - for n in result: - username=sqlattr(n,'username') - N={'username':username} - users.append(N) - return users - -def getUsers(self): - """Return a list of user objects or [] if no users exist""" - data=[] - try: items=self.listusers() - except: return data - for people in items: - roles=string.split(people['roles'],',') - user=User(people['username'], roles, '') - data.append(user) - return data - -def cryptPassword(self, username, password): - salt =username[:2] - secret = crypt(password, salt) - return secret - -def deleteUsers(self, userids): - for uid in userids: - self.sqlDeleteOneUser(userid=uid) - - -# Helper Functions... -from string import upper, lower -import Missing -mt=type(Missing.Value) - -def typeconv(val): - if type(val)==mt: - return '' - return val - -def sqlattr(ob, attr): - name=attr - if hasattr(ob, attr): - return typeconv(getattr(ob, attr)) - attr=upper(attr) - if hasattr(ob, attr): - return typeconv(getattr(ob, attr)) - attr=lower(attr) - if hasattr(ob, attr): - return typeconv(getattr(ob, attr)) - raise NameError, name - - -######################################################################## -# SQL METHODS USED ABOVE -# PASTE INTO ZSQL METHODS -# take note of what parameters are used in each query -######################################################################## - -_sqlListUsers=""" -SELECT * FROM passwd -""" - -_sqlListOneUser=""" -SELECT * FROM passwd -where username= -""" - -_sqlDeleteOneUser=""" -DELETE FROM passwd -where uid= -""" - -_sqlInsertUser=""" -INSERT INTO passwd (username, password, roles) -VALUES (, - , - ) -""" - -_sqlUpdateUserPassword=""" -UPDATE passwd set password= -WHERE username= -""" - -_sqlUpdateUser=""" -UPDATE passwd set roles= -WHERE username= -""" - diff --git a/ZopeProducts/exUserFolder/GroupSource/.cvsignore b/ZopeProducts/exUserFolder/GroupSource/.cvsignore deleted file mode 100644 index 57c4bccb..00000000 --- a/ZopeProducts/exUserFolder/GroupSource/.cvsignore +++ /dev/null @@ -1,4 +0,0 @@ -*.pyc -*.pyo -*~ -.*.swp diff --git a/ZopeProducts/exUserFolder/GroupSource/GroupSource.py b/ZopeProducts/exUserFolder/GroupSource/GroupSource.py deleted file mode 100644 index 478ab0b3..00000000 --- a/ZopeProducts/exUserFolder/GroupSource/GroupSource.py +++ /dev/null @@ -1,32 +0,0 @@ -# -# Extensible User Folder -# -# Null Group Source for exUserFolder -# -# Author: Brent Hendricks -# $Id: GroupSource.py,v 1.1 2002/12/02 23:20:49 bmh Exp $ -from Globals import DTMLFile - - -manage_addGroupSourceForm=DTMLFile('manage_addGroupSourceForm', globals(), __name__='manage_addGroupSourceForm') - - -def manage_addGroupSource(dispatcher, REQUEST): - """ Add a Group Source """ - - # Get the XUF object we're being added to - xuf = dispatcher.Destination() - - groupId = REQUEST.get('groupId', None) - if groupId: - # Invoke the add method for this plugin - xuf.groupSources[groupId].manage_addMethod(xuf, REQUEST) - else: - raise "BadRequest", "Required parameter 'groupId' omitted" - - dispatcher.manage_main(dispatcher, REQUEST) - - -class GroupSource: - pass - diff --git a/ZopeProducts/exUserFolder/GroupSource/__init__.py b/ZopeProducts/exUserFolder/GroupSource/__init__.py deleted file mode 100644 index dc5d3a81..00000000 --- a/ZopeProducts/exUserFolder/GroupSource/__init__.py +++ /dev/null @@ -1,2 +0,0 @@ -# $Id: __init__.py,v 1.1 2002/12/02 23:20:49 bmh Exp $ -import GroupSource diff --git a/ZopeProducts/exUserFolder/GroupSource/manage_addGroupSourceForm.dtml b/ZopeProducts/exUserFolder/GroupSource/manage_addGroupSourceForm.dtml deleted file mode 100644 index 3e6605a0..00000000 --- a/ZopeProducts/exUserFolder/GroupSource/manage_addGroupSourceForm.dtml +++ /dev/null @@ -1,33 +0,0 @@ - - - - - - - - - - -
- - - - - - - - - -
- Group Source - - -

Add ">
-
- -
- \ No newline at end of file diff --git a/ZopeProducts/exUserFolder/GroupSources/__init__.py b/ZopeProducts/exUserFolder/GroupSources/__init__.py deleted file mode 100644 index 4f36cdc5..00000000 --- a/ZopeProducts/exUserFolder/GroupSources/__init__.py +++ /dev/null @@ -1,31 +0,0 @@ -# -# Extensible User Folder -# -# (C) Copyright 2000-2004 The Internet (Aust) Pty Ltd -# ACN: 082 081 472 ABN: 83 082 081 472 -# All Rights Reserved -# -# THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND -# ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE -# IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE -# ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE -# FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL -# DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS -# OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) -# HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT -# LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY -# OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF -# SUCH DAMAGE. -# -# Author: Andrew Milton -# $Id: __init__.py,v 1.1 2004/11/10 14:15:53 akm Exp $ - -import nullGroupSource - -# If this fails due to NUG being absent, just skip it -try: - import zodbGroupSource -except ImportError: - pass - - diff --git a/ZopeProducts/exUserFolder/GroupSources/nullGroupSource/.cvsignore b/ZopeProducts/exUserFolder/GroupSources/nullGroupSource/.cvsignore deleted file mode 100644 index 57c4bccb..00000000 --- a/ZopeProducts/exUserFolder/GroupSources/nullGroupSource/.cvsignore +++ /dev/null @@ -1,4 +0,0 @@ -*.pyc -*.pyo -*~ -.*.swp diff --git a/ZopeProducts/exUserFolder/GroupSources/nullGroupSource/__init__.py b/ZopeProducts/exUserFolder/GroupSources/nullGroupSource/__init__.py deleted file mode 100644 index b8943369..00000000 --- a/ZopeProducts/exUserFolder/GroupSources/nullGroupSource/__init__.py +++ /dev/null @@ -1,2 +0,0 @@ -# $Id: __init__.py,v 1.1 2004/11/10 14:15:53 akm Exp $ -import nullGroupSource diff --git a/ZopeProducts/exUserFolder/GroupSources/nullGroupSource/manage_addNullPluginSourceForm.dtml b/ZopeProducts/exUserFolder/GroupSources/nullGroupSource/manage_addNullPluginSourceForm.dtml deleted file mode 100644 index f57a2c3a..00000000 --- a/ZopeProducts/exUserFolder/GroupSources/nullGroupSource/manage_addNullPluginSourceForm.dtml +++ /dev/null @@ -1,21 +0,0 @@ - -
- - - - - - - - - "> - - - - - -This Group Source has no configuration Items
-
-Add"> -
- diff --git a/ZopeProducts/exUserFolder/GroupSources/nullGroupSource/nullGroupSource.py b/ZopeProducts/exUserFolder/GroupSources/nullGroupSource/nullGroupSource.py deleted file mode 100644 index cee50ff9..00000000 --- a/ZopeProducts/exUserFolder/GroupSources/nullGroupSource/nullGroupSource.py +++ /dev/null @@ -1,34 +0,0 @@ -# -# Extensible User Folder -# -# Null Group Source for exUserFolder -# -# Author: Brent Hendricks -# $Id: nullGroupSource.py,v 1.1 2004/11/10 14:15:53 akm Exp $ -from Globals import HTMLFile, INSTANCE_HOME - -from OFS.Folder import Folder - -from Products.exUserFolder.exUserFolder import exUserFolder -from Products.exUserFolder.Plugins import PluginRegister -from Products.exUserFolder.nullPlugin import nullPlugin - -def manage_addNullGroupSource(self, REQUEST): - """ Add a Group Source """ - self.currentGroupSource=None - return '' - - -manage_addNullGroupSourceForm=HTMLFile('manage_addNullPluginSourceForm',globals()) -manage_editNullGroupSourceForm=None - - -nullGroupReg=PluginRegister('nullGroupSource', - 'Null Group Source', - nullPlugin, - manage_addNullGroupSourceForm, - manage_addNullGroupSource, - manage_editNullGroupSourceForm) - -exUserFolder.groupSources['nullGroupSource']=nullGroupReg - diff --git a/ZopeProducts/exUserFolder/GroupSources/zodbGroupSource/.cvsignore b/ZopeProducts/exUserFolder/GroupSources/zodbGroupSource/.cvsignore deleted file mode 100644 index 57c4bccb..00000000 --- a/ZopeProducts/exUserFolder/GroupSources/zodbGroupSource/.cvsignore +++ /dev/null @@ -1,4 +0,0 @@ -*.pyc -*.pyo -*~ -.*.swp diff --git a/ZopeProducts/exUserFolder/GroupSources/zodbGroupSource/__init__.py b/ZopeProducts/exUserFolder/GroupSources/zodbGroupSource/__init__.py deleted file mode 100644 index c2e979ba..00000000 --- a/ZopeProducts/exUserFolder/GroupSources/zodbGroupSource/__init__.py +++ /dev/null @@ -1,2 +0,0 @@ -# $Id: __init__.py,v 1.1 2004/11/10 14:15:54 akm Exp $ -import zodbGroupSource diff --git a/ZopeProducts/exUserFolder/GroupSources/zodbGroupSource/manage_addzodbGroupSourceForm.dtml b/ZopeProducts/exUserFolder/GroupSources/zodbGroupSource/manage_addzodbGroupSourceForm.dtml deleted file mode 100644 index 2d618cf5..00000000 --- a/ZopeProducts/exUserFolder/GroupSources/zodbGroupSource/manage_addzodbGroupSourceForm.dtml +++ /dev/null @@ -1,21 +0,0 @@ - - -
- - - - - - - - - "> - - - - - -This group source requires no user configuration items at this time.
-NEXT "> -
- diff --git a/ZopeProducts/exUserFolder/GroupSources/zodbGroupSource/manage_editzodbGroupSourceForm.dtml b/ZopeProducts/exUserFolder/GroupSources/zodbGroupSource/manage_editzodbGroupSourceForm.dtml deleted file mode 100644 index 3c04422e..00000000 --- a/ZopeProducts/exUserFolder/GroupSources/zodbGroupSource/manage_editzodbGroupSourceForm.dtml +++ /dev/null @@ -1,7 +0,0 @@ - - -
-This group source requires no user configuration items at this time.
-OK "> -
- diff --git a/ZopeProducts/exUserFolder/GroupSources/zodbGroupSource/zodbGroupSource.py b/ZopeProducts/exUserFolder/GroupSources/zodbGroupSource/zodbGroupSource.py deleted file mode 100644 index 78b441b6..00000000 --- a/ZopeProducts/exUserFolder/GroupSources/zodbGroupSource/zodbGroupSource.py +++ /dev/null @@ -1,177 +0,0 @@ -# -# Extensible User Folder -# -# ZODB Group Source for exUserFolder -# -# Author: Brent Hendricks -# $Id: zodbGroupSource.py,v 1.1 2004/11/10 14:15:54 akm Exp $ -from Globals import HTMLFile, MessageDialog, INSTANCE_HOME,Acquisition, PersistentMapping - -from OFS.Folder import Folder - -from Products.ZSQLMethods.SQL import SQL - -from Products.exUserFolder.exUserFolder import exUserFolder -from Products.exUserFolder.Plugins import PluginRegister -from Products.NuxUserGroups.UserFolderWithGroups import Group, _marker - -import time -import zLOG -import sys - -manage_addGroupSourceForm=HTMLFile('manage_addzodbGroupSourceForm', globals()) - -def manage_addzodbGroupSource(self, REQUEST): - """ Add a ZODB Group Source """ - - o = zodbGroupSource() - self._setObject('zodbGroupSource', o, None, None, 0) - o = getattr(self, 'zodbGroupSource') - - # Allow Prop Source to setup default users... - if hasattr(o, 'postInitialisation'): - o.postInitialisation(REQUEST) - self.currentGroupSource=o - -manage_addzodbGroupSourceForm=HTMLFile('manage_addzodbGroupSourceForm', globals()) -manage_editzodbGroupSourceForm=HTMLFile('manage_editzodbGroupSourceForm', globals()) - -# -# Very very simple thing, used as an example of how to write a property source -# Not recommended for large scale production sites... -# - -class zodbGroupSource(Folder): - """ Store Group Data inside ZODB, the simplistic way """ - - meta_type='Group Source' - title='Simplistic ZODB Groups' - icon ='misc_/exUserFolder/exUserFolderPlugin.gif' - manage_editForm=manage_editzodbGroupSourceForm - manage_tabs=Acquisition.Acquired - - def __init__(self): - self.id='zodbGroupSource' - self.groups=PersistentMapping() - - - def addGroup(self, groupname, title='', users=(), **kw): - """Creates a group""" - if self.groups.has_key(groupname): - raise ValueError, 'Group "%s" already exists' % groupname - a = 'before: groupname %s groups %s' % (groupname, self.groups) - group = apply(Group, (groupname,), kw) - group.setTitle(title) - group._setUsers(users) - self.groups[groupname] = group - - - def getGroup(self, groupname, default=_marker): - """Returns the given group""" - try: - group = self.groups[groupname] - except KeyError: - if default is _marker: raise - return default - return group - - - def delGroup(self, groupname): - """Deletes the given group""" - usernames = self.groups[groupname].getUsers() - #self.delUsersFromGroup(usernames, groupname) - del self.groups[groupname] - - - def listGroups(self): - """Returns a list of group names""" - return tuple(self.groups.keys()) - - - def getGroupsOfUser(self, username): - "Get a user's groups" - groupnames = [] - allnames = self.listGroups() - groupnames = filter(lambda g, u=username, self=self: u in self.groups[g].getUsers(), allnames) - return tuple(groupnames) - - - def setGroupsOfUser(self, groupnames, username): - "Set a user's groups" - oldGroups = self.getGroupsOfUser(username) - self.delGroupsFromUser(oldGroups, username) - self.addGroupsToUser(groupnames, username) - - - def addGroupsToUser(self, groupnames, username): - "Add groups to a user" - for name in groupnames: - group = self.groups[name] - if not username in group.getUsers(): - group._addUsers([username]) - - - def delGroupsFromUser(self, groupnames, username): - "Delete groups from a user" - for name in groupnames: - group = self.groups[name] - if username in group.getUsers(): - group._delUsers([username]) - - - def getUsersOfGroup(self, groupname): - "Get the users in a group" - return self.groups[groupname].getUsers() - - - def setUsersOfGroup(self, usernames, groupname): - "Set the users in a group" - # uniquify - dict = {} - for u in usernames: dict[u] = None - usernames = dict.keys() - - self.groups[groupname]._setUsers(usernames) - - - def addUsersToGroup(self, usernames, groupname): - "Add users to a group" - # uniquify - dict = {} - for u in usernames: dict[u] = None - usernames = dict.keys() - - self.groups[groupname]._addUsers(usernames) - - - def delUsersFromGroup(self, usernames, groupname): - "Delete users from a group" - # uniquify - dict = {} - for u in usernames: dict[u] = None - usernames = dict.keys() - - self.groups[groupname]._delUsers(usernames) - - - def deleteUsers(self, usernames): - "Delete a list of users" - for user in usernames: - groups = self.getGroupsOfUser(user) - self.delGroupsFromUser(groups, user) - - - def postInitialisation(self, REQUEST): - pass - - - def manage_beforeDelete(self, item, container): - # Notify the exUserFolder that it doesn't have a group source anymore - container.currentGroupSource=None - - -zodbGroupReg=PluginRegister('zodbGroupSource','Simplistic ZODB Group Source', - zodbGroupSource, manage_addzodbGroupSourceForm, - manage_addzodbGroupSource, - manage_editzodbGroupSourceForm) -exUserFolder.groupSources['zodbGroupSource']=zodbGroupReg diff --git a/ZopeProducts/exUserFolder/I18N/ZBabelDictionary_txt.zexp b/ZopeProducts/exUserFolder/I18N/ZBabelDictionary_txt.zexp deleted file mode 100644 index be6e17c2..00000000 Binary files a/ZopeProducts/exUserFolder/I18N/ZBabelDictionary_txt.zexp and /dev/null differ diff --git a/ZopeProducts/exUserFolder/LICENSE b/ZopeProducts/exUserFolder/LICENSE deleted file mode 100644 index 3a969486..00000000 --- a/ZopeProducts/exUserFolder/LICENSE +++ /dev/null @@ -1,91 +0,0 @@ -XUF as a whole is covered by the BSD License, however it uses software -covered by other compatible licenses (see below) - ------------------------------------------------------------------------- - -All of the documentation and software included in the exUserFolder -Releases is copyrighted by The Internet (Aust) Pty Ltd and contributors -ACN: 082 081 472 ABN: 83 082 081 472 - -Copyright 2001, 2002 The Internet (Aust) Pty Ltd - -Redistribution and use in source and binary forms, with or without -modification, are permitted provided that the following conditions -are met: -1. Redistributions of source code must retain the above copyright - notice, this list of conditions and the following disclaimer. -2. Redistributions in binary form must reproduce the above copyright - notice, this list of conditions and the following disclaimer in the - documentation and/or other materials provided with the distribution. - -THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND -ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE -IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE -ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE -FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL -DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS -OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) -HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT -LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY -OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF -SUCH DAMAGE. - ------------------------------------------------------------------------- - -This product includes software developed by Digital Creations for use in -the Z Object Publishing Environment (http://www.zope.org/) - -Portions of smbAuthSource Copyright (C) 2001 Michael Teo - -Portions of radiusAuthSource Copyright (C) 1999 Stuart Bishop - -fcrypt is Copyright (C) 2001, 2001 Carey Evans - -This product includes cryptographic software written by Eric Young -(eay@mincom.oz.au) - ------------------------------------------------------------------------- - -Brief discussion of what the license means to you, not meant to be -all encompassing, but, to give you the general idea. This editorial does -not need to be distributed d8) - -If you want to incorporate this product (or parts of it) into a commercial -product that's fine. - -If you want to modify this product that's fine. - -If you want to modify and distribute this product that's fine (even in -commercial products). - -If you want to incorporate this into a larger work that's fine (even -if that work has a different license). - -None of the previous items place any obligation of notification, compensation, -or return of code to us. In fact we don't care if you do these things. Go -forth and prosper. Basically as long as you recognise that this doesn't -belong to you, you can do what you want with it even charge money for it. - -Note: If you do distribute this as source, then the XUF components are -removable and distributable independently of your license as a whole -(although that's a lot of trouble to go to when they could just download it -from the same place you did). - -What you can't do, is claim it's yours, and this one thing encompasses a lot -of things, here's a few. - -If it's not yours you can't; - -Change the license even if you change the code since the copyright -of the modified files remains with the original copyright holders. - -Use bits of it inside products that require the license to change, because -only the copyright holders have the right to modify the license (not a -concern for commercial projects, only some other Free/Open Source licenses). - -Assign the copyright or other IP to any other party of the whole or any -part (even if you change the code), because it's not yours to give away or -sell to a 3rd party. - -If the fact you can almost do whatever you want with this code isn't -liberal enough for you, contact us and we'll see what we can arrange. diff --git a/ZopeProducts/exUserFolder/LoginRequiredMessages.py b/ZopeProducts/exUserFolder/LoginRequiredMessages.py deleted file mode 100644 index 1bee9173..00000000 --- a/ZopeProducts/exUserFolder/LoginRequiredMessages.py +++ /dev/null @@ -1,27 +0,0 @@ -# -# Extensible User Folder -# -# (C) Copyright 2000,2001 The Internet (Aust) Pty Ltd -# ACN: 082 081 472 ABN: 83 082 081 472 -# All Rights Reserved -# -# THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND -# ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE -# IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE -# ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE -# FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL -# DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS -# OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) -# HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT -# LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY -# OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF -# SUCH DAMAGE. -# -# Author: Andrew Milton -# $Id: LoginRequiredMessages.py,v 1.2 2001/12/01 08:40:03 akm Exp $ - -LoginRequiredMessages={ - 'session_expired':'Your Session has Expired', - 'unauthorized':'Please Login', - 'login_failed':'Login Failed', - } diff --git a/ZopeProducts/exUserFolder/MembershipSources/__init__.py b/ZopeProducts/exUserFolder/MembershipSources/__init__.py deleted file mode 100644 index 9dc1d5ff..00000000 --- a/ZopeProducts/exUserFolder/MembershipSources/__init__.py +++ /dev/null @@ -1,25 +0,0 @@ -# -# Extensible User Folder -# -# (C) Copyright 2000-2005 The Internet (Aust) Pty Ltd -# ACN: 082 081 472 ABN: 83 082 081 472 -# All Rights Reserved -# -# THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND -# ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE -# IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE -# ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE -# FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL -# DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS -# OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) -# HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT -# LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY -# OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF -# SUCH DAMAGE. -# -# Author: Andrew Milton -# $Id: - -import basicMemberSource -import nullMemberSource - diff --git a/ZopeProducts/exUserFolder/MembershipSources/basicMemberSource/.cvsignore b/ZopeProducts/exUserFolder/MembershipSources/basicMemberSource/.cvsignore deleted file mode 100644 index 57c4bccb..00000000 --- a/ZopeProducts/exUserFolder/MembershipSources/basicMemberSource/.cvsignore +++ /dev/null @@ -1,4 +0,0 @@ -*.pyc -*.pyo -*~ -.*.swp diff --git a/ZopeProducts/exUserFolder/MembershipSources/basicMemberSource/PasswordForm.dtml b/ZopeProducts/exUserFolder/MembershipSources/basicMemberSource/PasswordForm.dtml deleted file mode 100644 index 98bf3777..00000000 --- a/ZopeProducts/exUserFolder/MembershipSources/basicMemberSource/PasswordForm.dtml +++ /dev/null @@ -1,22 +0,0 @@ - -
- - - - - - - - - - - - - - - - -
Old Password
Password
Confirm Password
Password Hint
-Change Password "> -
- diff --git a/ZopeProducts/exUserFolder/MembershipSources/basicMemberSource/SignupForm.dtml b/ZopeProducts/exUserFolder/MembershipSources/basicMemberSource/SignupForm.dtml deleted file mode 100644 index 98ae04ef..00000000 --- a/ZopeProducts/exUserFolder/MembershipSources/basicMemberSource/SignupForm.dtml +++ /dev/null @@ -1,31 +0,0 @@ - -
- - - - - - - - - - - - - - - - - - - - - - - - - -
Username
Password
Confirm Password
Password Hint
Real Name
Email
-Signup "> -
- diff --git a/ZopeProducts/exUserFolder/MembershipSources/basicMemberSource/__init__.py b/ZopeProducts/exUserFolder/MembershipSources/basicMemberSource/__init__.py deleted file mode 100644 index a774af80..00000000 --- a/ZopeProducts/exUserFolder/MembershipSources/basicMemberSource/__init__.py +++ /dev/null @@ -1,2 +0,0 @@ -# $Id: __init__.py,v 1.1 2004/11/10 14:15:55 akm Exp $ -import basicMemberSource diff --git a/ZopeProducts/exUserFolder/MembershipSources/basicMemberSource/basicMemberSource.py b/ZopeProducts/exUserFolder/MembershipSources/basicMemberSource/basicMemberSource.py deleted file mode 100644 index 7be098a5..00000000 --- a/ZopeProducts/exUserFolder/MembershipSources/basicMemberSource/basicMemberSource.py +++ /dev/null @@ -1,629 +0,0 @@ -# -# Extensible User Folder -# -# Basic Membership Source for exUserFolder -# -# (C) Copyright 2000,2001 The Internet (Aust) Pty Ltd -# ACN: 082 081 472 ABN: 83 082 081 472 -# All Rights Reserved -# -# THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND -# ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE -# IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE -# ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE -# FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL -# DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS -# OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) -# HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT -# LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY -# OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF -# SUCH DAMAGE. -# -# Author: Andrew Milton -# $Id: basicMemberSource.py,v 1.1 2004/11/10 14:15:55 akm Exp $ - -# -# Basically membership is a layer between the signup/login form, and -# the authentication layer, it uses the prop source of the users to -# store additional information about a user i.e. doesn't impact on the -# authentication source. -# -# Some membership features imply some extra properties for the user will -# be available; specifically at this time an email property. -# -# You also need a MailHost setup and ready to go for emailing stuff to users -# - -import string,Acquisition -from random import choice - - -from Globals import HTMLFile, INSTANCE_HOME - -from OFS.Folder import Folder -from OFS.DTMLMethod import DTMLMethod - -from Products.exUserFolder.exUserFolder import exUserFolder -from Products.exUserFolder.Plugins import PluginRegister - -from base64 import encodestring -from urllib import quote - -import zLOG - -""" -Password Policy enforcement (min/max length, caps etc) -Create Password, or User Chooses. -Timing out of passwords... -Empty Password force change on login... -Create Home Directory -Copy files from Skelton Directory -EMail password hint to user (forgot my password) -Reset password and email user (needs plugin?) -Redirect on login to fixed or varying per username location. -Automatically add users, or manually approve of users. -""" - -# Stupid little things for making a password -# Don't hassle me, it's supposed to be basic. - -nouns=['ace', 'ant', 'arc', 'arm', 'axe', - 'bar', 'bat', 'bee', 'bib', 'bin', - 'can', 'cap', 'car', 'cat', 'cob', - 'day', 'den', 'dog', 'dot', 'dux', - 'ear', 'eel', 'egg', 'elf', 'elk', - 'fad', 'fan', 'fat', 'fig', 'fez', - 'gag', 'gas', 'gin', 'git', 'gum', - 'hag', 'hat', 'hay', 'hex', 'hub'] - -pastConjs = [ 'did', 'has', 'was' ] -suffixes = [ 'ing', 'es', 'ed', 'ious', 'ily'] - -def manage_addBasicMemberSource(self, REQUEST): - """ Add a Membership Source """ - - pvfeatures=[] - minLength=0 - passwordPolicy='' - createHomedir=0 - homeRoot='' - copyFilesFrom='' - postLogin='' - postSignup='' - forgottenPasswords='' - defaultRoles=[] - usersCanChangePasswords=0 - baseURL='' - loginPage='' - signupPage='' - passwordPage='' - mailHost='' - fixedDest='' - - if REQUEST.has_key('basicmember_pvfeatures'): - pvfeatures=REQUEST['basicmember_pvfeatures'] - - if REQUEST.has_key('basicmember_roles'): - defaultRoles=REQUEST['basicmember_roles'] - - if not defaultRoles: - defaultRoles=['Member'] - - if 'minlength' in pvfeatures: - minLength=REQUEST['basicmember_minpasslen'] - - if REQUEST.has_key('basicmember_passwordpolicy'): - passwordPolicy=REQUEST['basicmember_passwordpolicy'] - - if REQUEST.has_key('basicmember_createhomedir'): - homeRoot=REQUEST['basicmember_homeroot'] - createHomedir=1 - - if REQUEST.has_key('basicmember_copyfiles'): - copyFilesFrom=REQUEST['basicmember_copyfiles'] - - if REQUEST.has_key('basicmember_changepasswords'): - usersCanChangePasswords=1 - - if REQUEST.has_key('basicmember_fixeddest'): - fixedDest='' - - forgottenPasswords=REQUEST['basicmember_forgottenpasswords'] - postLogin=REQUEST['basicmember_postlogin'] - - baseURL=REQUEST['basicmember_baseurl'] - loginPage=REQUEST['basicmember_loginpage'] - signupPage=REQUEST['basicmember_signuppage'] - passwordPage=REQUEST['basicmember_passwordpage'] - siteEmail=REQUEST['basicmember_siteemail'] - siteName=REQUEST['basicmember_sitename'] - - mailHost=REQUEST['basicmember_mailhost'] - - # postSignup=REQUEST['basicmember_postsignup'] - - # - # Yep this is obscene - # - o = BasicMemberSource(pvfeatures, minLength, passwordPolicy, - createHomedir, copyFilesFrom, postLogin, - homeRoot, forgottenPasswords, defaultRoles, - usersCanChangePasswords, baseURL, loginPage, - signupPage, passwordPage, mailHost, - siteName, siteEmail, fixedDest) - - self._setObject('basicMemberSource', o, None, None, 0) - o = getattr(self, 'basicMemberSource') - - if hasattr(o, 'postInitialisation'): - o.postInitialisation(REQUEST) - - self.currentMembershipSource=o - return '' - - -manage_addBasicMemberSourceForm=HTMLFile('manage_addBasicMemberSourceForm', - globals()) -manage_editBasicMemberSourceForm=HTMLFile('manage_editBasicMemberSourceForm', - globals()) - -# -# Crap, I don't know why I called this basic, I'd hate to see a -# complicated one. -# -class BasicMemberSource(Folder): - """ Provide High Level User Management """ - meta_type="Membership Source" - title="Basic Membership Source" - icon ='misc_/exUserFolder/exUserFolderPlugin.gif' - manage_tabs=Acquisition.Acquired - manage_editForm=manage_editBasicMemberSourceForm - - # Ugh... - def __init__(self, pvFeatures=[], minLength=0, passwordPolicy='', - createHomeDir=0, copyFilesFrom='', postLogin='', homeRoot='', - forgottenPasswords='', defaultRoles=[], usersCanChangePasswords=0, - baseURL='', loginPage='', signupPage='', passwordPage='', - mailHost='', siteName='', siteEmail='', fixedDest=''): - - self.id='basicMemberSource' - self.pvFeatures=pvFeatures - self.minLength=int(minLength) - self.passwordPolicy=passwordPolicy - self.createHomeDir=createHomeDir - self.copyFilesFrom=copyFilesFrom - self.postLogin=postLogin - self.homeRoot=homeRoot - self.forgottenPasswords=forgottenPasswords - self.defaultRoles=defaultRoles - self.usersCanChangePasswords=usersCanChangePasswords - self.baseURL=baseURL - self.loginPage=loginPage - self.signupPage=signupPage - self.passwordPage=passwordPage - self.siteName=siteName - self.siteEmail=siteEmail - self.fixedDest=fixedDest - - _SignupForm=HTMLFile('SignupForm', globals()) - SignupForm=DTMLMethod() - SignupForm.manage_edit(data=_SignupForm, title='Signup Form') - self._setObject('SignupForm', SignupForm) - - _PasswordForm=HTMLFile('PasswordForm', globals()) - PasswordForm=DTMLMethod() - PasswordForm.manage_edit(data=_PasswordForm, - title='Change Password') - self._setObject('PasswordForm', PasswordForm) - - self.mailHost=mailHost - - _newPasswordEmail=HTMLFile('newPasswordEmail', globals()) - newPasswordEmail=DTMLMethod() - newPasswordEmail.manage_edit(data=_newPasswordEmail, - title='Send New Password') - self._setObject('newPasswordEmail', newPasswordEmail) - - _forgotPasswordEmail=HTMLFile('forgotPasswordEmail', globals()) - forgotPasswordEmail=DTMLMethod() - forgotPasswordEmail.manage_edit(data=_forgotPasswordEmail, - title='Send Forgotten Password') - self._setObject('forgotPasswordEmail', forgotPasswordEmail) - - _passwordHintEmail=HTMLFile('passwordHintEmail', globals()) - passwordHintEmail=DTMLMethod() - passwordHintEmail.manage_edit(data=_passwordHintEmail, - title='Send Forgotten Password Hint') - self._setObject('passwordHintEmail', passwordHintEmail) - - def postInitialisation(self, REQUEST): - if self.createHomeDir and self.homeRoot: - self.findHomeRootObject() - else: - self.homeRootObj=None - - if self.copyFilesFrom: - self.findSkelRootObject() - else: - self.homeSkelObj=None - - # The nice sendmail tag doesn't allow expressions for - # the mailhost - self.mailHostObject=getattr(self, self.mailHost) - - def manage_editMembershipSource(self, REQUEST): - """ Edit a basic Membership Source """ - if REQUEST.has_key('pvfeatures'): - self.pvFeatures=REQUEST['pvfeatures'] - else: - self.pvFeatures=[] - - if REQUEST.has_key('minpasslength'): - self.minLength=REQUEST['minpasslength'] - - if REQUEST.has_key('createhomedir'): - createHomeDir=1 - else: - createHomeDir=0 - - if createHomeDir: - self.copyFilesFrom=REQUEST['copyfiles'] - if self.copyFilesFrom: - self.findSkelRootObject() - else: - self.homeRoot=REQUEST['homeroot'] - self.findHomeRootObject() - - if REQUEST.has_key('memberroles'): - self.defaultRoles=REQUEST['memberroles'] - if REQUEST.has_key('changepasswords'): - self.usersCanChangePasswords=1 - else: - self.usersCanChangePasswords=0 - - self.postLogin=REQUEST['postlogin'] - if REQUEST.has_key('fixeddest'): - self.fixedDest=REQUEST['fixeddest'] - - self.baseURL=REQUEST['baseurl'] - self.loginPage=REQUEST['loginpage'] - self.signupPage=REQUEST['signuppage'] - self.passwordPage=REQUEST['passwordpage'] - self.siteName=REQUEST['sitename'] - self.siteEmail=REQUEST['siteemail'] - return self.MessageDialog(self, - title ='Updated!', - message="Membership was Updated", - action ='manage_editMembershipSourceForm', - REQUEST=REQUEST) - - - - def forgotPassword(self, REQUEST): - username=REQUEST['username'] - curUser=self.getUser(username) - if not curUser: - return self.MessageDialog(self, - title ='No such user', - message="No users matching that username were found.", - action ='%s/%s'%(self.baseURL, self.loginPage), - REQUEST=REQUEST) - - - userEmail=curUser.getProperty('email') - userName=curUser.getProperty('realname') - if self.forgottenPasswords == "hint": - passwordHint=curUser.getProperty('passwordhint') - self.passwordHintEmail(self, - REQUEST=REQUEST, - username=username, - hint=passwordHint, - realname=userName, - email=userEmail) - else: - # make a new password, and mail it to the user - password = self.generatePassword() - curCrypt=self.currentAuthSource.cryptPassword(username,password) - - # Update the user - bogusREQUEST={} - #bogusREQUEST['username']=username - bogusREQUEST['password']=password - bogusREQUEST['password_confirm']=password - bogusREQUEST['roles']=curUser.roles - self.manage_editUser(username, bogusREQUEST) - - self.forgotPasswordEmail(self, - REQUEST=REQUEST, - username=username, - password=password, - realname=userName, - email=userEmail) - return self.MessageDialog(self, - title ='Sent!', - message="Password details have been emailed to you", - action ='%s/%s'%(self.baseURL, self.loginPage), - REQUEST=REQUEST) - - - def changeProperties(self, REQUEST): - - curUser=self.listOneUser(REQUEST['AUTHENTICATED_USER'].getUserName()) - curUser=curUser[0] - if not curUser: - return self.MessageDialog(self, - title ='Erm!', - message="You don't seem to be logged in", - action ='%s/%s'%(self.baseURL, self.passwordPage), - REQUEST=REQUEST) - - - - self.currentPropSource.updateUser(curUser['username'],REQUEST) - - return self.MessageDialog(self, - title ='Properties updated', - message="Your properties have been updated", - action =self.baseURL, - REQUEST=REQUEST, - ) - - - def changePassword(self, REQUEST): - if not self.usersCanChangePasswords: - return '' - - curUser=self.listOneUser(REQUEST['AUTHENTICATED_USER'].getUserName()) - curUser=curUser[0] - if not curUser: - return self.MessageDialog( - title ='Erm!', - message="You don't seem to be logged in", - action ='%s/%s'%(self.baseURL, self.passwordPage), - REQUEST=REQUEST) - - curCrypt=self.currentAuthSource.cryptPassword(curUser['username'],REQUEST['current_password']) - if curCrypt != curUser['password']: - return self.MessageDialog(self, - title ='Password Mismatch', - message="Password is incorrect", - action ='%s/%s'%(self.baseURL, self.passwordPage), - REQUEST=REQUEST) - - if REQUEST['password'] != REQUEST['password_confirm']: - return self.MessageDialog(self, - title ='Password Mismatch', - message="Passwords do not match", - action ='%s/%s'%(self.baseURL, self.passwordPage), - REQUEST=REQUEST) - - # OK the old password matches the one the user provided - # Both new passwords match... - # Time to validate against our normal set of rules... - # - if not self.validatePassword(REQUEST['password'], curUser['username']): - return self.MessageDialog(self, - title ='Password problem', - message="Your password is invalid, please choose another", - action ='%s/%s'%(self.baseURL, self.passwordPage), - REQUEST=REQUEST) - - if self.passwordPolicy=='hint': - if not hasattr(REQUEST,'user_passwordhint'): - return self.MessageDialog(self, - title ='Password requires hint', - message='You must choose a password hint', - action ='%s/%s'%(self.baseURL, self.passwordPage), - REQUEST=REQUEST) - - bogusREQUEST={} - - bogusREQUEST['password']=REQUEST['password'] - bogusREQUEST['password_confirm']=REQUEST['password'] - bogusREQUEST['roles']=curUser['roles'] - self.manage_editUser(curUser['username'],bogusREQUEST) - # update the cookie so he doesnt have to re-login: - if self.cookie_mode: - token='%s:%s' %(curUser['username'], REQUEST['password']) - token=encodestring(token) - token=quote(token) - REQUEST.response.setCookie('__ac', token, path='/') - REQUEST['__ac']=token - - return self.MessageDialog(self, - title ='Password updated', - message="Your password has been updated", - action =self.baseURL, - REQUEST=REQUEST) - - - def goHome(self, REQUEST, RESPONSE): - redirectstring="%s/%s/%s/manage_main"%(self.baseURL, self.homeRoot, REQUEST.AUTHENTICATED_USER.getUserName()) - RESPONSE.redirect(redirectstring) - return '' - - # Tell exUserFolder where we want to go... - def getLoginDestination(self, REQUEST): - script='' - pathinfo='' - querystring='' - redirectstring='' - if self.postLogin=="destination": - script=REQUEST['SCRIPT_NAME'] - pathinfo=REQUEST['PATH_INFO'] - elif self.postLogin=="varied": - script=self.baseURL - pathinfo="/acl_users/goHome" - - elif self.postLogin=="fixed": - pathinfo="%s"%(self.fixedDest) - - if REQUEST.has_key('QUERY_STRING'): - querystring='?'+REQUEST['QUERY_STRING'] - - redirectstring=script+pathinfo - if querystring: - redirectstring=redirectstring+querystring - - return redirectstring - - def validatePassword(self, password, username): - if 'minlength' in self.pvFeatures: - if len(password) < self.minLength: - return 0 - - if 'mixedcase' in self.pvFeatures: - lower = 0 - upper = 0 - for c in password: - if c in string.lowercase: - lower = 1 - if c in string.uppercase: - upper = 1 - if not upper and lower: - return 0 - - if 'specialchar' in self.pvFeatures: - special = 0 - for c in password: - if c in string.punctuation: - special = 1 - break - elif c in string.digits: - special = 1 - break - if not special: - return 0 - - # - # XXX Move this somewhere else - # - - if 'notstupid' in self.pvFeatures: - email='' - # We try some permutations here... - curUser=self.getUser(username) - if curUser: - email = curUser.getProperty('email') - elif hasattr(self, 'REQUEST'): - if self.REQUEST.has_key('user_email'): # new signup - email=self.REQUEST['user_email'] - elif self.REQUEST.has_key('email'): - email=self.REQUEST['email'] - - if ((string.find(password, username)>=0) or - ( email and - (string.find(password, - string.split(email,'@')[0]) >=0))): - return 0 - return 1 - - # These next two look the same (and they are for now), but, the reason I - # Don't use one single method, is I think that SkelObj might migrate to - # using full paths, not relative paths. - - def findSkelRootObject(self): - # Parent should be acl_users - parent = getattr(self, 'aq_parent') - - # This should be the root... - root = getattr(parent, 'aq_parent') - searchPaths = string.split(self.copyFilesFrom, '/') - for o in searchPaths: - if not getattr(root, o): - break - root = getattr(root, o) - - self.homeSkelObj=root - - def findHomeRootObject(self): - # Parent should be acl_users - parent = getattr(self, 'aq_parent') - - # This should be the root... - root = getattr(parent, 'aq_parent') - - searchPaths = string.split(self.homeRoot, '/') - for o in searchPaths: - if o not in root.objectIds(): - root.manage_addFolder(id=o, title=o, createPublic=0, createUserF=0) - root = getattr(root, o) - - self.homeRootObj=root - - def makeHomeDir(self, username): - if not self.homeRootObj: - return - - self.homeRootObj.manage_addFolder(id=username, title=username, createPublic=0, createUserF=0) - home = getattr(self.homeRootObj, username) - - - # Allow user to be in charge of their own destiny - # XXXX WARNING THIS IS A NORMAL FOLDER *SO USERS CAN ADD ANYTHING* - # YOU NEED TO CHANGE THE TYPE OF OBJECT ADDED FOR A USER UNLESS - # THIS IS WHAT YOU WANT TO HAPPEN - home.manage_addLocalRoles(userid=username, roles=['Manager']) - - if self.copyFilesFrom and self.homeSkelObj and self.homeSkelObj.objectIds(): - cp=self.homeSkelObj.manage_copyObjects( - self.homeSkelObj.objectIds()) - home.manage_pasteObjects(cp) - - # Fix it so the user owns their stuff - curUser=self.getUser(username).__of__(self.aq_parent) - home.changeOwnership(curUser, recursive=1) - - def generatePassword(self): - password = (choice(nouns) + choice(pastConjs) + - choice(nouns) + choice(suffixes)) - return password - - def createUser(self, REQUEST): - if self.passwordPolicy == 'user': - if not self.validatePassword(REQUEST['password'], REQUEST['username']): - return self.MessageDialog(self, - title ='Password problem', - message='Your password is invalid, please choose another', - action ='%s/%s'%(self.baseURL, self.signupPage), - REQUEST=REQUEST) - - if self.passwordPolicy=='hint': - if not hasattr(REQUEST,'user_passwordhint'): - return self.MessageDialog(self, - title ='Password requires hint', - message='You must choose a password hint', - action ='%s/%s'%(self.baseURL, self.signupPage), - REQUEST=REQUEST) - - elif self.passwordPolicy == 'system': - REQUEST['password']=self.generatePassword() - REQUEST['password_confirm']=REQUEST['password'] - - # Email the password. - self.newPasswordEmail(self, REQUEST) - - zLOG.LOG("exUserFolder.basicMemberSource", zLOG.BLATHER, - "Creating user", - "Passed all tests -- creating [%s]" % REQUEST['username']) - REQUEST['roles']=self.defaultRoles - self.manage_addUser(REQUEST) # Create the User... - if self.createHomeDir: - self.makeHomeDir(REQUEST['username']) - - return self.MessageDialog(self, - title ='You have signed up', - message='You have been signed up succesfully', - action ='%s'%(self.baseURL), - REQUEST=REQUEST) - - - -basicMemberReg=PluginRegister('basicMemberSource', - 'Basic Membership Source', - BasicMemberSource, - manage_addBasicMemberSourceForm, - manage_addBasicMemberSource, - manage_editBasicMemberSourceForm) -exUserFolder.membershipSources['basicMemberSource']=basicMemberReg - diff --git a/ZopeProducts/exUserFolder/MembershipSources/basicMemberSource/forgotPasswordEmail.dtml b/ZopeProducts/exUserFolder/MembershipSources/basicMemberSource/forgotPasswordEmail.dtml deleted file mode 100644 index 1dc67b2b..00000000 --- a/ZopeProducts/exUserFolder/MembershipSources/basicMemberSource/forgotPasswordEmail.dtml +++ /dev/null @@ -1,15 +0,0 @@ - -To: <> -From: <> -Subject: You forgot your password for - -Dear , - -Your username is and your password is now -. - -You should have tested this first, and now that you've tested it, you'll -see you need to customise this method. - - - diff --git a/ZopeProducts/exUserFolder/MembershipSources/basicMemberSource/manage_addBasicMemberSourceForm.dtml b/ZopeProducts/exUserFolder/MembershipSources/basicMemberSource/manage_addBasicMemberSourceForm.dtml deleted file mode 100644 index 434e1f09..00000000 --- a/ZopeProducts/exUserFolder/MembershipSources/basicMemberSource/manage_addBasicMemberSourceForm.dtml +++ /dev/null @@ -1,143 +0,0 @@ - -Membership requires a valid property source, you cannot use this with NULL Property Source -
- - - - - - - - - "> - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Site Name (used in emails) -
Site Email (used for emails) -
Mail Host - -
Site Base"> -
Relative Path (from base) of Login Page -
Relative Path (from base) of Signup Page -
Relative Path (from base) of Change Password Page -
Password Validation Features - -
Minimum Length (0 if not required) - -
Password Policy - -
Forgotten Passwords - -
Allow users to change passwords - Yes -
Create 'Home Directory' - Yes -
Relative Path to 'Home Directory' Root - -
Copy initial 'Home Directory' files from...(empty=No Copy) - "> -
After login.... - -
Fixed Destination - -
Default Roles - -
-Add"> -
- diff --git a/ZopeProducts/exUserFolder/MembershipSources/basicMemberSource/manage_editBasicMemberSourceForm.dtml b/ZopeProducts/exUserFolder/MembershipSources/basicMemberSource/manage_editBasicMemberSourceForm.dtml deleted file mode 100644 index c7092b32..00000000 --- a/ZopeProducts/exUserFolder/MembershipSources/basicMemberSource/manage_editBasicMemberSourceForm.dtml +++ /dev/null @@ -1,116 +0,0 @@ - - -
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Site Name (used in emails) -
Site Email (used for emails) -
Mail Host - -
Site Base -
Relative Path (from base) of Login Page -
Relative Path (from base) of Signup Page -
Relative Path (from base) of Change Password Page -
Password Validation Features - -
Minimum Length (if required) - -
Allow users to change passwords - checked>Yes -
Create 'Home Directory' - checked>Yes -
Path to 'Home Directory' Root - -
Copy initial 'Home Directory' files from...(empty=No Copy) - -
After login.... - -
Fixed Destination - -
Default Roles - -
-Update "> -
-
- - diff --git a/ZopeProducts/exUserFolder/MembershipSources/basicMemberSource/newPasswordEmail.dtml b/ZopeProducts/exUserFolder/MembershipSources/basicMemberSource/newPasswordEmail.dtml deleted file mode 100644 index 4de7dc6b..00000000 --- a/ZopeProducts/exUserFolder/MembershipSources/basicMemberSource/newPasswordEmail.dtml +++ /dev/null @@ -1,16 +0,0 @@ - -To: <> -From: <> -Subject: Welcome to - -Dear , - -Welcome to . - -Your username is and your password is . - -You should have tested this first, and now that you've tested it, you'll -see you need to customise this method. - - - diff --git a/ZopeProducts/exUserFolder/MembershipSources/basicMemberSource/passwordHintEmail.dtml b/ZopeProducts/exUserFolder/MembershipSources/basicMemberSource/passwordHintEmail.dtml deleted file mode 100644 index 75c7cca9..00000000 --- a/ZopeProducts/exUserFolder/MembershipSources/basicMemberSource/passwordHintEmail.dtml +++ /dev/null @@ -1,15 +0,0 @@ - -To: <> -From: <> -Subject: Hint for - -Dear , - -Your username is and your password hint was; -. - -You should have tested this first, and now that you've tested it, you'll -see you need to customise this method. - - - diff --git a/ZopeProducts/exUserFolder/MembershipSources/nullMemberSource/.cvsignore b/ZopeProducts/exUserFolder/MembershipSources/nullMemberSource/.cvsignore deleted file mode 100644 index 57c4bccb..00000000 --- a/ZopeProducts/exUserFolder/MembershipSources/nullMemberSource/.cvsignore +++ /dev/null @@ -1,4 +0,0 @@ -*.pyc -*.pyo -*~ -.*.swp diff --git a/ZopeProducts/exUserFolder/MembershipSources/nullMemberSource/__init__.py b/ZopeProducts/exUserFolder/MembershipSources/nullMemberSource/__init__.py deleted file mode 100644 index 9eb51622..00000000 --- a/ZopeProducts/exUserFolder/MembershipSources/nullMemberSource/__init__.py +++ /dev/null @@ -1,2 +0,0 @@ -# $Id: __init__.py,v 1.1 2004/11/10 14:15:55 akm Exp $ -import nullMemberSource diff --git a/ZopeProducts/exUserFolder/MembershipSources/nullMemberSource/manage_addNullPluginSourceForm.dtml b/ZopeProducts/exUserFolder/MembershipSources/nullMemberSource/manage_addNullPluginSourceForm.dtml deleted file mode 100644 index 4ae809bf..00000000 --- a/ZopeProducts/exUserFolder/MembershipSources/nullMemberSource/manage_addNullPluginSourceForm.dtml +++ /dev/null @@ -1,21 +0,0 @@ - -
- - - - - - - - - "> - - - - - -This Membership Source has no configuration Items
-
-Add"> -
- diff --git a/ZopeProducts/exUserFolder/MembershipSources/nullMemberSource/nullMemberSource.py b/ZopeProducts/exUserFolder/MembershipSources/nullMemberSource/nullMemberSource.py deleted file mode 100644 index 49f26a50..00000000 --- a/ZopeProducts/exUserFolder/MembershipSources/nullMemberSource/nullMemberSource.py +++ /dev/null @@ -1,49 +0,0 @@ -# -# Extensible User Folder -# -# Null Membership Source for exUserFolder -# -# (C) Copyright 2000,2001 The Internet (Aust) Pty Ltd -# ACN: 082 081 472 ABN: 83 082 081 472 -# All Rights Reserved -# -# THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND -# ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE -# IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE -# ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE -# FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL -# DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS -# OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) -# HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT -# LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY -# OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF -# SUCH DAMAGE. -# -# Author: Andrew Milton -# $Id: nullMemberSource.py,v 1.1 2004/11/10 14:15:55 akm Exp $ -from Globals import HTMLFile, INSTANCE_HOME - -from OFS.Folder import Folder - -from Products.exUserFolder.exUserFolder import exUserFolder -from Products.exUserFolder.Plugins import PluginRegister -from Products.exUserFolder.nullPlugin import nullPlugin - -def manage_addNullMemberSource(self, REQUEST): - """ Add a Membership Source """ - self.currentMembershipSource=None - return '' - - -manage_addNullMemberSourceForm=HTMLFile('manage_addNullPluginSourceForm',globals()) -manage_editNullMemberSourceForm=None - - -nullMemberReg=PluginRegister('nullMemberSource', - 'Null Membership Source', - nullPlugin, - manage_addNullMemberSourceForm, - manage_addNullMemberSource, - manage_editNullMemberSourceForm) -exUserFolder.membershipSources['nullMemberSource']=nullMemberReg - diff --git a/ZopeProducts/exUserFolder/Plugins.py b/ZopeProducts/exUserFolder/Plugins.py deleted file mode 100644 index 58cdc2ef..00000000 --- a/ZopeProducts/exUserFolder/Plugins.py +++ /dev/null @@ -1,46 +0,0 @@ -# -# -# (C) Copyright 2001 The Internet (Aust) Pty Ltd -# ACN: 082 081 472 ABN: 83 082 081 472 -# All Rights Reserved -# -# THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND -# ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE -# IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE -# ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE -# FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL -# DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS -# OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) -# HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT -# LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY -# OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF -# SUCH DAMAGE. -# -# Author: Andrew Milton -# $Id: Plugins.py,v 1.5 2004/11/10 14:15:33 akm Exp $ - -import App, Globals, OFS -import string -import time - -from Globals import ImageFile, HTMLFile, HTML, MessageDialog, package_home -from OFS.Folder import Folder - -class PluginRegister: - def __init__(self, name, description, pluginClass, - pluginStartForm, pluginStartMethod, - pluginEditForm=None, pluginEditMethod=None): - self.name=name #No Spaces please... - self.description=description - self.plugin=pluginClass - self.manage_addForm=pluginStartForm - self.manage_addMethod=pluginStartMethod - self.manage_editForm=pluginEditForm - self.manage_editMethod=pluginEditMethod - -class CryptoPluginRegister: - def __init__(self, name, crypto, description, pluginMethod): - self.name = name #No Spaces please... - self.cryptoMethod = crypto - self.description = description - self.plugin = pluginMethod diff --git a/ZopeProducts/exUserFolder/PropSources/__init__.py b/ZopeProducts/exUserFolder/PropSources/__init__.py deleted file mode 100644 index e11388e4..00000000 --- a/ZopeProducts/exUserFolder/PropSources/__init__.py +++ /dev/null @@ -1,28 +0,0 @@ -# -# Extensible User Folder -# -# (C) Copyright 2000-2004 The Internet (Aust) Pty Ltd -# ACN: 082 081 472 ABN: 83 082 081 472 -# All Rights Reserved -# -# THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND -# ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE -# IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE -# ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE -# FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL -# DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS -# OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) -# HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT -# LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY -# OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF -# SUCH DAMAGE. -# -# Author: Andrew Milton -# $Id: __init__.py,v 1.1 2004/11/10 14:15:55 akm Exp $ - - -import nullPropSource -# aucune autre prop source pour ScoDoc - - - diff --git a/ZopeProducts/exUserFolder/PropSources/nullPropSource/.cvsignore b/ZopeProducts/exUserFolder/PropSources/nullPropSource/.cvsignore deleted file mode 100644 index 57c4bccb..00000000 --- a/ZopeProducts/exUserFolder/PropSources/nullPropSource/.cvsignore +++ /dev/null @@ -1,4 +0,0 @@ -*.pyc -*.pyo -*~ -.*.swp diff --git a/ZopeProducts/exUserFolder/PropSources/nullPropSource/__init__.py b/ZopeProducts/exUserFolder/PropSources/nullPropSource/__init__.py deleted file mode 100644 index 14ecc014..00000000 --- a/ZopeProducts/exUserFolder/PropSources/nullPropSource/__init__.py +++ /dev/null @@ -1,2 +0,0 @@ -# $Id: __init__.py,v 1.1 2004/11/10 14:15:56 akm Exp $ -import nullPropSource diff --git a/ZopeProducts/exUserFolder/PropSources/nullPropSource/manage_addNullPluginSourceForm.dtml b/ZopeProducts/exUserFolder/PropSources/nullPropSource/manage_addNullPluginSourceForm.dtml deleted file mode 100644 index a1979b0e..00000000 --- a/ZopeProducts/exUserFolder/PropSources/nullPropSource/manage_addNullPluginSourceForm.dtml +++ /dev/null @@ -1,21 +0,0 @@ - -
- - - - - - - - - "> - - - - - -This Property Source has no configuration Items
-
-Add"> -
- diff --git a/ZopeProducts/exUserFolder/PropSources/nullPropSource/nullPropSource.py b/ZopeProducts/exUserFolder/PropSources/nullPropSource/nullPropSource.py deleted file mode 100644 index ab269b03..00000000 --- a/ZopeProducts/exUserFolder/PropSources/nullPropSource/nullPropSource.py +++ /dev/null @@ -1,50 +0,0 @@ -# -# Extensible User Folder -# -# Null Membership Source for exUserFolder -# -# (C) Copyright 2000,2001 The Internet (Aust) Pty Ltd -# ACN: 082 081 472 ABN: 83 082 081 472 -# All Rights Reserved -# -# THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND -# ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE -# IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE -# ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE -# FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL -# DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS -# OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) -# HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT -# LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY -# OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF -# SUCH DAMAGE. -# -# Author: Andrew Milton -# $Id: nullPropSource.py,v 1.1 2004/11/10 14:15:56 akm Exp $ -from Globals import HTMLFile, INSTANCE_HOME - -from OFS.Folder import Folder - -from Products.exUserFolder.exUserFolder import exUserFolder -from Products.exUserFolder.Plugins import PluginRegister -from Products.exUserFolder.nullPlugin import nullPlugin - -def manage_addNullPropSource(self, REQUEST): - """ Add a Property Source """ - self.currentPropSource=None - return '' - - -manage_addNullPropSourceForm=HTMLFile('manage_addNullPluginSourceForm',globals()) -manage_editNullPropSourceForm=None - - -nullPropReg=PluginRegister('nullPropSource', - 'Null Property Source', - nullPlugin, - manage_addNullPropSourceForm, - manage_addNullPropSource, - manage_editNullPropSourceForm) - -exUserFolder.propSources['nullPropSource']=nullPropReg - diff --git a/ZopeProducts/exUserFolder/PropertyEditor/.cvsignore b/ZopeProducts/exUserFolder/PropertyEditor/.cvsignore deleted file mode 100644 index 57c4bccb..00000000 --- a/ZopeProducts/exUserFolder/PropertyEditor/.cvsignore +++ /dev/null @@ -1,4 +0,0 @@ -*.pyc -*.pyo -*~ -.*.swp diff --git a/ZopeProducts/exUserFolder/PropertyEditor/PropertyEditor.py b/ZopeProducts/exUserFolder/PropertyEditor/PropertyEditor.py deleted file mode 100644 index 711d4a0f..00000000 --- a/ZopeProducts/exUserFolder/PropertyEditor/PropertyEditor.py +++ /dev/null @@ -1,122 +0,0 @@ -# -# Extensible User Folder -# -# (C) Copyright 2000,2001 The Internet (Aust) Pty Ltd -# ACN: 082 081 472 ABN: 83 082 081 472 -# All Rights Reserved -# -# THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND -# ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE -# IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE -# ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE -# FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL -# DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS -# OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) -# HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT -# LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY -# OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF -# SUCH DAMAGE. -# -# Author: Andrew Milton -# $Id: PropertyEditor.py,v 1.3 2002/01/29 17:42:02 alex_zxc Exp $ - -from Globals import DTMLFile, MessageDialog, INSTANCE_HOME -from string import join,strip,split,lower,upper,find -from urllib import quote, unquote - - -def editStringProperty( name, value): - """ """ - return('\n'%(name, value)) - -def viewStringProperty( name, value): - """ """ - return('
%s
\n'%(value, value)) - - -def editIntegerProperty( name, value): - """ """ - return('\n'%(name, value or 0)) - -def viewIntegerProperty( name, value): - """ """ - return('
%d
\n'%(value or 0 , value or 0)) - - -def editLongProperty( name, value): - """ """ - return('\n'%(name, value or 0)) - -def viewLongProperty( name, value): - """ """ - return('
%d
\n'%(value or 0, value or 0)) - - -def editFloatProperty( name, value): - """ """ - return('\n'%(name, value)) - -def viewFloatProperty( name, value): - """ """ - return('
%f
\n'%(value, value)) - - -def editListProperty( name, value): - a='' - if value: - a = a + 'Select Items to keep
\n' - a = a + '\n
' - a = a + 'Add an item\n
' - a = a + ''%(name) - return(a) - -def viewListProperty( name, value): - a='' - if value: - for i in value: - a = a + ( - '\n'%(i)) - a = a + '%s\n
'%(i) - return(a) - - -def editDictProperty( name, value): - """ """ - a='' - if value and value.keys(): - for i in value.keys(): - a = a + '%s : \n
'%(i, name, i, value[i]) - return a - - -def viewDictProperty( name, value): - """ """ - a='' - if value and value.keys(): - for i in value.keys(): - a = a + '%s : \n
'%(i, name, i, value[i]) - a = a + '%s\n
'%(value[i]) - return a - -EditMethods={'String':editStringProperty, - 'Integer':editIntegerProperty, - 'Long':editLongProperty, - 'Float':editFloatProperty, - 'List':editListProperty, - 'Dict':editDictProperty} - - -ViewMethods={'String':viewStringProperty, - 'Integer':viewIntegerProperty, - 'Long':viewLongProperty, - 'Float':viewFloatProperty, - 'List':viewListProperty, - 'Dict':viewDictProperty} - - - - diff --git a/ZopeProducts/exUserFolder/PropertyEditor/__init__.py b/ZopeProducts/exUserFolder/PropertyEditor/__init__.py deleted file mode 100644 index 4189a84d..00000000 --- a/ZopeProducts/exUserFolder/PropertyEditor/__init__.py +++ /dev/null @@ -1,22 +0,0 @@ -# -# Extensible User Folder -# -# (C) Copyright 2000,2001 The Internet (Aust) Pty Ltd -# ACN: 082 081 472 ABN: 83 082 081 472 -# All Rights Reserved -# -# THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND -# ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE -# IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE -# ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE -# FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL -# DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS -# OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) -# HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT -# LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY -# OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF -# SUCH DAMAGE. -# -# Author: Andrew Milton -# $Id: __init__.py,v 1.2 2001/12/01 08:40:04 akm Exp $ -import PropertyEditor diff --git a/ZopeProducts/exUserFolder/README.Upgrading b/ZopeProducts/exUserFolder/README.Upgrading deleted file mode 100644 index 384001a4..00000000 --- a/ZopeProducts/exUserFolder/README.Upgrading +++ /dev/null @@ -1,14 +0,0 @@ -If you are upgrading an existing site from < 0.50 - -I have restructured the source tree. This will make this version -incompatible with previous versions, as the classes have moved. This -breaks upgrading existing installs unless you keep the old classes -around. If you only use external Auth/Prop/Group sources, you will -probably be unaffected. - -This means for those of you using SQL or LDAP or any non-ZODB sources, -you can remove and then re-add your XUF acl_users to get going again. - -If you are using a ZODB source, then you need to keep the old classes -and the old paths around (e.g. symlink zodbAuthSource to -AuthSources/zodbAuthSource). diff --git a/ZopeProducts/exUserFolder/User.py b/ZopeProducts/exUserFolder/User.py deleted file mode 100644 index 7b55e0f9..00000000 --- a/ZopeProducts/exUserFolder/User.py +++ /dev/null @@ -1,243 +0,0 @@ -# -# Extensible User Folder -# -# (C) Copyright 2000,2001 The Internet (Aust) Pty Ltd -# ACN: 082 081 472 ABN: 83 082 081 472 -# All Rights Reserved -# -# THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND -# ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE -# IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE -# ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE -# FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL -# DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS -# OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) -# HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT -# LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY -# OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF -# SUCH DAMAGE. -# -# Author: Andrew Milton -# $Id: User.py,v 1.10 2004/12/14 05:30:29 akm Exp $ - -############################################################################## -# -# Zope Public License (ZPL) Version 0.9.4 -# --------------------------------------- -# -# Copyright (c) Digital Creations. All rights reserved. -# -# Redistribution and use in source and binary forms, with or -# without modification, are permitted provided that the following -# conditions are met: -# -# 1. Redistributions in source code must retain the above -# copyright notice, this list of conditions, and the following -# disclaimer. -# -# 6. Redistributions of any form whatsoever must retain the -# following acknowledgment: -# -# "This product includes software developed by Digital -# Creations for use in the Z Object Publishing Environment -# (http://www.zope.org/)." -# -# Disclaimer -# -# THIS SOFTWARE IS PROVIDED BY DIGITAL CREATIONS ``AS IS'' AND -# ANY EXPRESSED OR IMPLIED WARRANTIES, INCLUDING, BUT NOT -# LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND -# FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT -# SHALL DIGITAL CREATIONS OR ITS CONTRIBUTORS BE LIABLE FOR ANY -# DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR -# CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, -# PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, -# DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND -# ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT -# LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING -# IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF -# THE POSSIBILITY OF SUCH DAMAGE. -# -############################################################################## -from AccessControl.User import BasicUser -from string import join,strip,split,lower,upper,find - -class XUFUser(BasicUser): - - icon='misc_/exUserFolder/exUser.gif' - - # cacheable is a dict that must contain at least name, password, - # roles, and domains -- unless you're working with your own User class, - # in which case you need to override __init__ and define it yourself. - def __init__(self, cacheable, propSource, cryptPassword, authSource, - groupSource=None): - self.name =cacheable['name'] - self.__ =cacheable['password'] - if cacheable['roles']: - self.roles = filter(None, cacheable['roles']) - else: - self.roles = [] - # domains may be passed as a string or a list - if type(cacheable['domains']) == type(''): - self.domains=filter(None, map(strip, - split(cacheable['domains'], ','))) - else: - self.domains=cacheable['domains'] - self._authSource=authSource - self._propSource=propSource - self._groupSource=groupSource - self.cryptPassword=cryptPassword - - def getUserName(self): - return self.name - - def _getPassword(self): - return self.__ - - def getRoles(self): - return tuple(self.roles) + ('Authenticated',) - - def getDomains(self): - return self.domains - - # Ultra generic way of getting, checking and setting properties - def getProperty(self, property, default=None): - if self._propSource: - return self._propSource.getUserProperty(property, self.name, default) - - def hasProperty(self, property): - if self._propSource: - return self._propSource.hasProperty(property) - - def setProperty(self, property, value): - if property[0]=='_': - return - if self._propSource: - return self._propSource.setUserProperty(property, self.name, value) - - def setTempProperty(self, property, value): - if property[0]=='_': - return - if self._propSource: - return self._propSource.setTempProperty(property, value) - - def flushTempProperties(self): - if self._propSource: - return self._propSource.flushTempProperties() - - def delProperty(self, property): - if property[0]=='_': - return - if self._propSource: - return self._propSource.delUserProperty(property, self.name) - - def listProperties(self): - if self._propSource: - return self._propSource.listUserProperties(self.name) - - # Try to allow User['property'] -- won't work for password d;) - def __getitem__(self, key): - # Don't return 'private' keys - if key[0] != '_': - if hasattr(self, key): - return getattr(self, key) - if self._propSource and self._propSource.hasProperty(key): - - return self._propSource.getUserProperty(key, self.name) - raise KeyError, key - - def __setitem__(self, key, value): - if key[0]=='_': - return - if self._propSource: - self._propSource.setUserProperty(key, self.name, value) - - # List one user is supplied by the Auth Source... - - def authenticate(self, listOneUser, password, request, remoteAuth=None): - result=listOneUser(username=self.name) - for people in result: - if remoteAuth: - return remoteAuth(self.name, password) - else: - secret=self.cryptPassword(self.name, password) - return secret==people['password'] - return None - - # You can set logout times or whatever here if you want to, the - # property source is still active. - def notifyCacheRemoval(self): - if self._propSource: - self._propSource.flushTempProperties() - - # You must override this and __init__ if you are subclassing - # the user object, or your user object may not be reconstructed - # properly! All values in this dict must be non-Persistent objects - # or types, and may not hold any references to Persistent objects, - # or the cache will break. - def _getCacheableDict(self): - return {'name': self.name, - 'password': self.__, - 'roles': self.roles, - 'domains': self.domains} - - def getGroups(self): - if self._groupSource: - return self._groupSource.getGroupsOfUser(self.name) - else: - return () - - - def _setGroups(self, groupnames): - if self._groupSource: - return self._groupSource.setGroupsOfUser(groupnames, self.name) - - - def _addGroups(self, groupnames): - if self._groupSource: - return self._groupSource.addGroupsToUser(groupnames, self.name) - - def _delGroups(self, groupnames): - if self._groupSource: - return self._groupSource.delGroupsFromUser(groupnames, self.name) - - def getId(self): - if self._propSource and self._propSource.getUserProperty('userid', self.name): - return self._propSource.getUserProperty('userid', self.name) - return self.name - - -# -# An Anonymous User for session tracking... -# Can set and get properties just like a normal user. -# -# These objects live in the cache, so, we have a __del__ method to -# clean ourselves up. -# - -class XUFAnonUser(XUFUser): - def __init__(self, name, roles, propSource): - self.name =name - self.__ ='' - self.roles =filter(None, roles) - self._propSource=propSource - - def getRoles(self): - return tuple(self.roles) + ('Anonymous',) - - def authenticate(self, listOneUser, password, request, remoteAuth=None): - return 1 - - def notifyCacheRemoval(self): - if self._propSource: - self._propSource.deleteUsers([self.name,]) - -# We now set up a dummy classes so that people can extend the User objects -# or override stuff with much less pain --akm - -class User(XUFUser): - pass - -class AnonUser(XUFAnonUser): - pass - diff --git a/ZopeProducts/exUserFolder/UserCache/.cvsignore b/ZopeProducts/exUserFolder/UserCache/.cvsignore deleted file mode 100644 index 57c4bccb..00000000 --- a/ZopeProducts/exUserFolder/UserCache/.cvsignore +++ /dev/null @@ -1,4 +0,0 @@ -*.pyc -*.pyo -*~ -.*.swp diff --git a/ZopeProducts/exUserFolder/UserCache/UserCache.py b/ZopeProducts/exUserFolder/UserCache/UserCache.py deleted file mode 100644 index b3b6a942..00000000 --- a/ZopeProducts/exUserFolder/UserCache/UserCache.py +++ /dev/null @@ -1,409 +0,0 @@ -# -# Extensible User Folder -# -# (C) Copyright 2000,2001 The Internet (Aust) Pty Ltd -# ACN: 082 081 472 ABN: 83 082 081 472 -# All Rights Reserved -# -# THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND -# ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE -# IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE -# ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE -# FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL -# DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS -# OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) -# HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT -# LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY -# OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF -# SUCH DAMAGE. -# -# Author: Andrew Milton -# $Id: UserCache.py,v 1.16 2003/07/10 21:11:26 akm Exp $ - -# Module Level Caches for Various User Operations - -from time import time -from BTrees.OOBTree import OOBTree -import threading -from Acquisition import aq_inner -from Products.exUserFolder.User import User - -class UserCacheItem: - lastAccessed=0 - def __init__(self, username, password, cacheable): - self.username=username - self.password=password - self.cacheable=cacheable - self.lastAccessed=time() - - def touch(self): - self.lastAccessed=time() - - def __repr__(self): - return self.username - -class NegativeUserCacheItem(UserCacheItem): - def __init__(self, username): - self.username=username - self.lastAccessed=time() - -class AdvancedCookieCacheItem(UserCacheItem): - lastAccessed=0 - def __init__(self, username, password): - self.username=username - self.password=password - self.lastAccessed=time() - -class SessionExpiredException(Exception): - 'User Session Expired' - - -class UserCache: - def __init__(self, sessionLength): - self.sessionLength=sessionLength - self.cache=OOBTree() - self.hits=0 - self.fail=0 - self.nouser=0 - self.attempts=0 - self.timeouts=0 - self.cacheStarted=time() - self.lock=threading.Lock() - - def addToCache(self, username, password, User): - self.lock.acquire() - try: - if not self.sessionLength: - return - - try: - u = self.cache.items(username) - if u: - for x in self.cache[username]: - self.cache.remove(x) - except: - pass - - u = UserCacheItem(username, password, User._getCacheableDict()) - self.cache[username]=u - finally: - self.lock.release() - - def getUser(self, caller, username, password, checkpassword=1): - self.lock.acquire() - try: - if not self.sessionLength: - return None - - self.attempts=self.attempts+1 - - u = None - try: - u = self.cache[username] - except KeyError: - self.nouser=self.nouser+1 - return None - - now = time() - if u: - if checkpassword and (u.password != password): - self.fail=self.fail+1 - del self.cache[u.username] - elif self.sessionLength and ( - (now - u.lastAccessed) > self.sessionLength): - del self.cache[u.username] - self.timeouts=self.timeouts+1 - user_object=User(u.cacheable, - caller.currentPropSource, - caller.cryptPassword, - caller.currentAuthSource, - caller.currentGroupSource) - user_object.notifyCacheRemoval() - del u - raise SessionExpiredException - else: - u.touch() - self.hits=self.hits+1 - return User(u.cacheable, - caller.currentPropSource, - caller.cryptPassword, - caller.currentAuthSource, - caller.currentGroupSource) - - self.nouser=self.nouser+1 - return None - finally: - self.lock.release() - - def removeUser(self, username): - self.lock.acquire() - try: - if not self.sessionLength: - return - try: - if self.cache[username]: - del self.cache[username] - except: - pass - finally: - self.lock.release() - - def getCacheStats(self): - self.lock.acquire() - try: - return ( - {'attempts':self.attempts, - 'hits':self.hits, - 'fail':self.fail, - 'misses':self.nouser, - 'cachesize':len(self.cache), - 'time':self.cacheStarted, - 'timeouts':self.timeouts, - 'length':self.sessionLength}) - finally: - self.lock.release() - - def getCurrentUsers(self, caller): - self.lock.acquire() - try: - x=[] - now = time() - for z in self.cache.keys(): - u = self.cache[z] - if self.sessionLength and ( - (now - u.lastAccessed) > self.sessionLength): - del self.cache[u.username] - self.timeouts=self.timeouts+1 - user_object=User(u.cacheable, - caller.currentPropSource, - caller.cryptPassword, - caller.currentAuthSource, - caller.currentGroupSource) - user_object.notifyCacheRemoval() - del u - else: - x.append({'username':u.username, - 'lastAccessed':u.lastAccessed}) - return x - finally: - self.lock.release() - -class NegativeUserCache: - def __init__(self, sessionLength): - self.sessionLength=sessionLength - self.cache=OOBTree() - self.hits=0 - self.cacheStarted=time() - self.lock=threading.Lock() - - def addToCache(self, username): - self.lock.acquire() - try: - if not self.sessionLength: - return - - try: - u = self.cache.items(username) - if u: - for x in self.cache[username]: - self.cache.remove(x) - except: - pass - - u = NegativeUserCacheItem(username) - self.cache[username]=u - finally: - self.lock.release() - - def getUser(self, username): - self.lock.acquire() - try: - if not self.sessionLength: - return 0 - - u = None - try: - u = self.cache[username] - except KeyError: - return 0 - - now = time() - if u: - if self.sessionLength and ( - (now - u.lastAccessed) > self.sessionLength): - del self.cache[u.username] - else: - # We don't touch negative user caches - # u.touch() - self.hits=self.hits+1 - return 1 - return 0 - finally: - self.lock.release() - - def removeUser(self, username): - self.lock.acquire() - try: - if not self.sessionLength: - return - try: - del self.cache[username] - except: - pass - finally: - self.lock.release() - -class CookieCache: - def __init__(self, sessionLength): - self.sessionLength=sessionLength - self.cache=OOBTree() - self.hits=0 - self.cacheStarted=time() - self.lock=threading.Lock() - - def addToCache(self, username, password, key): - self.lock.acquire() - try: - if not self.sessionLength: - return - - try: - u = self.cache.items(key) - if u: - for x in self.cache[key]: - self.cache.remove(x) - except: - pass - u = AdvancedCookieCacheItem(username, password) - self.cache[key]=u - finally: - self.lock.release() - - def getUser(self, key): - self.lock.acquire() - try: - if not self.sessionLength: - return None - - u = None - try: - u = self.cache[key] - except KeyError: - return None - - now = time() - if u: - if self.sessionLength and ( - (now - u.lastAccessed) > self.sessionLength): - del self.cache[key] - else: - # We don't touch negative user caches - # u.touch() - self.hits=self.hits+1 - return u.username, u.password - return None - finally: - self.lock.release() - - def removeUser(self, key): - self.lock.acquire() - try: - if not self.sessionLength: - return - try: - del self.cache[key] - except: - pass - finally: - self.lock.release() - -class GlobalUserCache: - caches={} - def __init__(self): - self.lock = threading.Lock() - - def createCache(self, who, sessionLength): - self.lock.acquire() - try: - self.caches[who]=UserCache(sessionLength) - return self.caches[who] - finally: - self.lock.release() - - def getCache(self, who): - self.lock.acquire() - try: - if self.caches.has_key(who): - return self.caches[who] - else: - return None - finally: - self.lock.release() - - def deleteCache(self, who): - self.lock.acquire() - try: - del self.caches[who] - finally: - self.lock.release() - -class GlobalNegativeUserCache: - caches={} - def __init__(self): - self.lock = threading.Lock() - - def createCache(self, who, sessionLength): - self.lock.acquire() - try: - self.caches[who]=NegativeUserCache(sessionLength) - return self.caches[who] - finally: - self.lock.release() - - def getCache(self, who): - self.lock.acquire() - try: - if self.caches.has_key(who): - return self.caches[who] - else: - return None - finally: - self.lock.release() - - def deleteCache(self, who): - self.lock.acquire() - try: - del self.caches[who] - finally: - self.lock.release() - -class GlobalAdvancedCookieCache: - caches={} - def __init__(self): - self.lock = threading.Lock() - - def createCache(self, who, sessionLength): - self.lock.acquire() - try: - self.caches[who]=CookieCache(sessionLength) - return self.caches[who] - finally: - self.lock.release() - - def getCache(self, who): - self.lock.acquire() - try: - if self.caches.has_key(who): - return self.caches[who] - else: - return None - finally: - self.lock.release() - - def deleteCache(self, who): - self.lock.acquire() - try: - del self.caches[who] - finally: - self.lock.release() - diff --git a/ZopeProducts/exUserFolder/UserCache/__init__.py b/ZopeProducts/exUserFolder/UserCache/__init__.py deleted file mode 100644 index 5a484ebd..00000000 --- a/ZopeProducts/exUserFolder/UserCache/__init__.py +++ /dev/null @@ -1,22 +0,0 @@ -# -# Extensible User Folder -# -# (C) Copyright 2000,2001 The Internet (Aust) Pty Ltd -# ACN: 082 081 472 ABN: 83 082 081 472 -# All Rights Reserved -# -# THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND -# ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE -# IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE -# ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE -# FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL -# DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS -# OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) -# HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT -# LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY -# OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF -# SUCH DAMAGE. -# -# Author: Andrew Milton -# $Id: __init__.py,v 1.2 2001/12/01 08:40:04 akm Exp $ -import UserCache diff --git a/ZopeProducts/exUserFolder/__init__.py b/ZopeProducts/exUserFolder/__init__.py deleted file mode 100644 index 49f0cbcc..00000000 --- a/ZopeProducts/exUserFolder/__init__.py +++ /dev/null @@ -1,85 +0,0 @@ -# -# Extensible User Folder -# -# (C) Copyright 2000-2005 The Internet (Aust) Pty Ltd -# ACN: 082 081 472 ABN: 83 082 081 472 -# All Rights Reserved -# -# THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND -# ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE -# IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE -# ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE -# FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL -# DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS -# OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) -# HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT -# LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY -# OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF -# SUCH DAMAGE. -# -# Author: Andrew Milton -# $Id: __init__.py,v 1.18 2004/11/10 14:15:33 akm Exp $ - -import exUserFolder - -import CryptoSources -import AuthSources -import PropSources -import MembershipSources -import GroupSources - -from GroupSource import GroupSource - -from App.ImageFile import ImageFile -import OFS - -# -# Install a dummy ZBabel setup if we don't have ZBabel installed. -# -import dummyZBabelTag - -# Methods we need access to from any ObjectManager context -legacy_methods = ( - ('manage_addexUserFolderForm', exUserFolder.manage_addexUserFolderForm), - ('manage_addexUserFolder', exUserFolder.manage_addexUserFolder), - ('getAuthSources', exUserFolder.getAuthSources), - #('getPropSources', exUserFolder.getPropSources), - ('getCryptoSources', exUserFolder.getCryptoSources), - ('getMembershipSources', exUserFolder.getMembershipSources), - ('getGroupSources', exUserFolder.getGroupSources), - ('doAuthSourceForm', exUserFolder.doAuthSourceForm), - #('doPropSourceForm', exUserFolder.doPropSourceForm), - ('doMembershipSourceForm', exUserFolder.doMembershipSourceForm), - # ('doGroupSourceForm', exUserFolder.doGroupSourceForm), - ('getVariableType', exUserFolder.getVariableType), - ('DialogHeader', exUserFolder.exUserFolder.DialogHeader), - ('DialogFooter', exUserFolder.exUserFolder.DialogFooter), - #('MailHostIDs', exUserFolder.MailHostIDs), - ) - -# Image files to place in the misc_ object so they are accesible from misc_/exUserFolder -misc_={'exUserFolder.gif': ImageFile('exUserFolder.gif', globals()), - 'exUserFolderPlugin.gif': ImageFile('exUserFolderPlugin.gif', globals()), - 'exUser.gif': ImageFile('exUser.gif', globals()), - } - - -def initialize(context): - """ - Register base classes - """ - context.registerClass(exUserFolder.exUserFolder, - meta_type="ex User Folder", - permission="Add exUser Folder", - constructors=(exUserFolder.manage_addexUserFolderForm, - exUserFolder.manage_addexUserFolder,), - legacy=legacy_methods, - icon="exUserFolder.gif") - - context.registerClass(GroupSource.GroupSource, - meta_type="ex User Folder Group Source", - permission="Add exUser Folder", - constructors=(GroupSource.manage_addGroupSourceForm, - GroupSource.manage_addGroupSource,), - icon="exUserFolderPlugin.gif") - diff --git a/ZopeProducts/exUserFolder/common/DialogFooter.dtml b/ZopeProducts/exUserFolder/common/DialogFooter.dtml deleted file mode 100644 index 00add5fe..00000000 --- a/ZopeProducts/exUserFolder/common/DialogFooter.dtml +++ /dev/null @@ -1,4 +0,0 @@ - - - - \ No newline at end of file diff --git a/ZopeProducts/exUserFolder/common/DialogHeader.dtml b/ZopeProducts/exUserFolder/common/DialogHeader.dtml deleted file mode 100644 index fad53794..00000000 --- a/ZopeProducts/exUserFolder/common/DialogHeader.dtml +++ /dev/null @@ -1,7 +0,0 @@ -
- - - - - -
diff --git a/ZopeProducts/exUserFolder/common/MessageDialog.dtml b/ZopeProducts/exUserFolder/common/MessageDialog.dtml deleted file mode 100644 index 0d0bc555..00000000 --- a/ZopeProducts/exUserFolder/common/MessageDialog.dtml +++ /dev/null @@ -1,41 +0,0 @@ - -
TARGET=""> - - - - - - - - - "> - - - - - - - - - - - - -
-
-
!
-
-

-
- -
-
- -
- Ok "> -
-
- - - - diff --git a/ZopeProducts/exUserFolder/common/manage_tabs.dtml b/ZopeProducts/exUserFolder/common/manage_tabs.dtml deleted file mode 100644 index c6c66c2e..00000000 --- a/ZopeProducts/exUserFolder/common/manage_tabs.dtml +++ /dev/null @@ -1,176 +0,0 @@ - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
   - ">
 href="&dtml-action;"href="&dtml-URL1;" target="&dtml-target;"> -   href="&dtml-action;"href="&dtml-URL1;" target="&dtml-target;"> -  
-
- - -
- - - - - - - - - - - - - - - -
-
- - &dtml-meta_type; - - - - - &dtml-meta_type; - - &dtml-meta_type; - - - Object - - at - - - - This item has been modified in this version - - This item has been modified in another version - () - - - - This item has been locked by WebDAV - -
-
-
- -
-
-
- -
-
- - -
-You are currently working in version -
-
-
- - -
- -() -
-
- -
diff --git a/ZopeProducts/exUserFolder/common/text_manage_tabs.dtml b/ZopeProducts/exUserFolder/common/text_manage_tabs.dtml deleted file mode 100644 index 62922a0e..00000000 --- a/ZopeProducts/exUserFolder/common/text_manage_tabs.dtml +++ /dev/null @@ -1,19 +0,0 @@ - - - -
- - - - -
- - href="" - href="" - target=""> - []  - -
-
-
-
diff --git a/ZopeProducts/exUserFolder/doc/FAQ.txt b/ZopeProducts/exUserFolder/doc/FAQ.txt deleted file mode 100644 index d2a0be5d..00000000 --- a/ZopeProducts/exUserFolder/doc/FAQ.txt +++ /dev/null @@ -1,119 +0,0 @@ -Frequently Asked Questions - -1. Why shouldn't I use Core Session Tracking + Login Manager? -XUF serves a different set of users to the combination above. XUF -aims to be a simple out of the box solution. Login Manager allows -for very complex authorisation schemes that can query multiple user -sources. We don't do that. - -2. Why use XUF at all? -In its simplest configuration, XUF provides the same functionality -as the standard User Folder, but, is more secure. Passwords are -stored encrypted, which is not the case for the standard User Folder. -So even if you don't want to set properties on users, or any -membership facilities, there is a benefit to running XUF. - -3. Do I have to have all this other stuff? -No. The only thing you need to enable is authentication. There is -a null property source, and a null membership source. Everything -other than authentication is optional. - -4. Can I use it as a root folder? -Some people have reported success in doing so. We don't recommend -it for various reasons. The main one is that the internal Zope API -can change without warning, which could break XUF and lock you out -of your Zope. This can happen with any User Folder product. We -recommend you look at VHM and other Site Access methods to allow -you to store your main site in a sub-folder. - -5. When will XUF support authentication against XYZ system? -That depends. First the active developers need to have an interest -in it, and more importantly they need to be able to test it. Writing -your authentication method is very simple, so if you understand -what you want to authenticate against, and know some python you -could write one in an hour. You can also use the usAuthSource to -write one using PythonScripts, ExternalMethods, DTML, or any other -callable method that Zope supports. - -6. I wrote this cool authentication source can I get it into the main - distribution? -Yes and No. If your authentication is Open Source, and has a -compatible license with XUF, and doesn't require any external -libraries, odds are it'll go into the main distribution. If it -depends on external libraries, it's possible it can conditionally -go into the main distribution. The nice thing about XUF is that -Authentication, Property, and Membership sources are all packagable -as independent products, so you can distribute it as a standalone -product, and it'll work (without having to have the code drop into -the XUF directory either). - -7. Is XUF going to be part of the Core Zope? -No idea. At the moment (0.10.5) XUF is probably not at a level that -Zope Corporation would consider mature enough for core inclusion -anyway. - -Actually the answer now, is probably not. At a minimum smbAuthSource, -and radiusAuthSource would have to be stripped and distributed -seperately. Over and above that, I would have to assign Zope Corp -co-ownership rights on the IP, which amongst other things gives -them or anyone that buys them unlimited access to future derived -works. I refuse to do this on principle, the liberal licensing of -the product should be more than adequate for any (especially open -source) endeavour. - -8. What's with the Management Screens? -It's a joke on the Zope World. - -9. But they're really ugly I want to change them. -That's fine, you do that, that's the point. - -10. Can I send you patches to put them back to standard Management - Screens? -You can put patches into the tracker at Source Forge if you want to. - -11. HELP!!!! I tried to install XUF as my root folder, without - reading the FAQ, or really knowing what I'm doing, and now I'm - hosed!!! -That's a shame. - -12. Will XUF work with ZEO? -Unknown. However, it's almost certain that in its current form -credential caching will not work across ZEO -- you will get a -seperate User Cache for each Zope Client (which isn't really all -that bad). However, it means that if you want to use Session Tracking, -you need to lock users to one particular server. Most commercial -Load Balancers do this for you anyhow. A persistent cache will form -part of an upcoming release which will allow all of this to work -transparently across ZEO farms. - -13. Shouldn't it be EUF? -No, it should be XUF :-P - -14. How can I log in a user via a form submission? -Yes, the key is sending the __ac_name and __ac_password (yes that's -two underscores in front) as form variables to any object covered -by the XUF. - -This form will take your users to the /index_html and log them in. -You can place this anywhere in your site including /index_html. - -
-Name:
-Password: - -
- -15. That Dialog box sure is ugly! How can I customize it so it looks - right in my site? -Under the contents tab add an object called MessageDialog , it can -be a dtml document, method, or even a page template. Make it look -how you want, it will acquire all objects from the folder the XUF -is in so you can use the standard_html_header, call scripts, etc. - -16. Why can't I change the default crypto method? -Because someone will change it, and all the existing passwords will cease -to work. Then I'll get lots of hate-mail, or get slagged off on other mailing -lists :-) - -17. Where is the Zen Master's Guide to exUserFolder? -Everywhere and nowhere. diff --git a/ZopeProducts/exUserFolder/doc/README.API b/ZopeProducts/exUserFolder/doc/README.API deleted file mode 100644 index ab6e8ebd..00000000 --- a/ZopeProducts/exUserFolder/doc/README.API +++ /dev/null @@ -1,171 +0,0 @@ -User Sources ------------- - -This is the list of functions your auth source should provide. - -createUser(self, username, password, roles) -Create a User to authenticate against username, password and roles, -should all be obvious. - - -updateUser(self, username, password, roles) -Update a user's roles and password. -An empty password means do not change passwords, so at least at this time -it's not possible to have passwordless accounts. - - -cryptPassword(self, username, password) -Encrypt a password -If no 'crypt' method is supplied return the Password -- -i.e. plaintext password. - - -deleteUsers(self, userids) -Delete a set of users, userids is a list of usernames to delete. - - -listUserNames(self) -returns a list of usernames. - -listOneUser(self,username) -Return one user matching the username -Should be a dictionary; - {'username':username, 'password':cryptedPassword, 'roles':list_of_roles} -Once again, you can provide more information than this if you're customising -the forms. - -listUsers(self) -Return the list of users in the same format as listOneUser - - -remoteAuthMethod(self, username, password) -You can define this to go off and do the authentication instead of -using the basic one inside the User Object. Useful for IMAP/LDAP auth -type methods where the authentication is handled elsewhere and we just want -to know success or failure. If you don't want to do this you should have; - -remoteAuthMethod=None - -in your AuthSource (to explicitly tell the exUserFolder that you don't). - ------------------------------------------------------------------------- -This is a skeleton class; - -manage_addfooAuthSourceForm=HTMLFile('manage_addfooAuthSourceForm', globals()) -manage_editfooAuthSourceForm=HTMLFile('manage_editfooAuthSourceForm', globals()) - -class fooAuthSource(Folder): - - meta_type='Authentication Source' - title='User Supplied Authentication' - icon ='misc_/exUserFolder/exUserFolderPlugin.gif' - manage_editForm=manage_editfooAuthSourceForm - - def __init__(self): - self.id='fooAuthSource' - - # Create a User to authenticate against - # username, password and roles - def createUser(self, username, password, roles): - """ Add A Username """ - pass - - # Update a user's roles and password - # An empty password means do not change passwords... - def updateUser(self, username, password, roles): - pass - - # Encrypt a password - # If no 'crypt' method is supplied return the - # Password -- i.e. plaintext password - def cryptPassword(self, username, password): - pass - - # Delete a set of users - def deleteUsers(self, userids): - pass - - # Return a list of usernames - def listUserNames(self): - pass - - # Return a list of user dictionaries with - # {'username':username} can be extended to pass back other - # information, but, we don't do that just now - def listUsers(self): - pass - - # Return one user matching the username - # Should be a dictionary; - # {'username':username, 'password':cryptedPassword, 'roles':list_of_roles} - def listOneUser(self,username): - pass - - # - # Return a list of users, dictionary format as for listOneUser - # - def getUsers(self): - pass - - # - # You can define this to go off and do the authentication instead of - # using the basic one inside the User Object - # - remoteAuthMethod=None - -## def remoteAuthMethod(self, username, password): -## pass - - def postInitialisation(self, REQUEST): - pass - -fooAuthReg=PluginRegister('fooAuthSource', 'User Supplied Authentication Source', - fooAuthSource, manage_addfooAuthSourceForm, - manage_addfooAuthSource, - manage_editfooAuthSourceForm) -exUserFolder.authSources['fooAuthSource']=fooAuthReg - ------------------------------------------------------------------------- - -Property Sources ----------------- - -Property Sources have only a few things they need to provide; - -hasProperty(self, key) -Returns true if the current user has that property - -setProperty(self, key, value) -Sets a property for the current user - - -setUserProperty(self, key, username, value) -Sets a property for the given user. - - -getProperty(self, key, default=None) -Returns the requested property or the default for the current user. - - -getUserProperty(self, key, username, default=None) -Returns the requested property or the default for the named user. - - -listProperties(self) -Returns a list of properties (just the properties not their values). - - -listUserProperties(self, username) -Returns a list of properties for the named user. - -createUser(self, username, REQUEST) -Creates a new user, and adds in the properties in the REQUEST. -New properties are preceded with "user_KEYNAME", so strip user_ to -set the property. - -deleteUsers(self, userids) -Delete the list of users (and their properties) contained within userids. - -updateUser(self, username, REQUEST) -Change the list of properties for a user, the variables are formatted as for -createUser. diff --git a/ZopeProducts/exUserFolder/doc/README.LDAPAuthSource b/ZopeProducts/exUserFolder/doc/README.LDAPAuthSource deleted file mode 100644 index fa3bc004..00000000 --- a/ZopeProducts/exUserFolder/doc/README.LDAPAuthSource +++ /dev/null @@ -1,20 +0,0 @@ -This is a reimplementation of the auth_ldap auth source for apache, written by -Dave Carrigan and others. - -You can find the original auth_ldap Apache code at -http://www.rudedog.org/auth_ldap/ - -This auth source is covered by the Apache license; - -Copyright (C) 1998, 1999 Enbridge Pipelines Inc. -Copyright (C) 1999-2001 Dave Carrigan -Copyright (C) 2003 The Internet (Aust) Pty Ltd. -All rights reserved. - -This module is free software; you can redistribute it and/or modify -it under the same terms as Apache itself. This module is -distributed in the hope that it will be useful, but WITHOUT ANY -WARRANTY; without even the implied warranty of MERCHANTABILITY or -FITNESS FOR A PARTICULAR PURPOSE. The copyright holder of this -module can not be held liable for any general, special, incidental -or consequential damages arising out of the use of the module. diff --git a/ZopeProducts/exUserFolder/doc/README.Membership b/ZopeProducts/exUserFolder/doc/README.Membership deleted file mode 100644 index 17937f39..00000000 --- a/ZopeProducts/exUserFolder/doc/README.Membership +++ /dev/null @@ -1,144 +0,0 @@ -There are now membership hooks defined, and a basic membership -source defined for exUserFolder. This is a first stab at this, so -please be careful :-) - -Membership adds a level of complexity to everything, and basically is a -controlled way of breaching your security. - -You will need to prepare a few things before trying to add an exUserFolder -with Membership support; - -a) You will need a MailHost object available -b) You will need to define some methods for Membership to use - i) a Login Page - ii) a Change Password Page - iii) a Signup Page - iv) a Forgot My Password Page (optional) - v) a change Properties Page (optional) - These should live at the same level as your acl_user (i.e. not inside). - These should be fairly simple, I've included some examples below. - These should just wrap the ones below acl_users. There will be methods - you can edit to get all your fields and layout done. -c) If you want the results pages from Signup, Change Password, etc to fit - your site, you'll need to add a MessageDialog document in the contents - of the XUF. See FAQ 15 for more - - -When you see the creation form, obviously some of the options are -mutually exclusive. - -e.g. You can't choose system defined passwords, and have the system - email a hint, if they forgot their password. So try to pick sane - combinations of options. - - - - - -If you choose to have Home Directories, basicMemberSource will create -the path you provide, so you don't need to do that in advance. - -If you want to have skeleton files copied to their homedir you'll need -to have that directory (it can be empty) setup and ready to go, before -the first user signs up. - -WARNING WARNING WARNING WARNING WARNING WARNING WARNING WARNING WARNING -WARNING WARNING WARNING WARNING WARNING WARNING WARNING WARNING WARNING -WARNING WARNING WARNING WARNING WARNING WARNING WARNING WARNING WARNING -If you get basicMembershipSource to create Home Directories for your -users, it will create a 'Folder' and it will give the user management -permissions on that Folder. This means that they will be able to add -any object you can, just at a level below this. You should create/have -a proper HomeFolder object that is restricted in what is available -for adding, and change makeHomeDir() in basicMemberSource.py to create -one of those. - -I will look at creating a restricted HomeDirectory Object in a later -release, and allow you to add and remove meta_types from it. -WARNING WARNING WARNING WARNING WARNING WARNING WARNING WARNING WARNING -WARNING WARNING WARNING WARNING WARNING WARNING WARNING WARNING WARNING -WARNING WARNING WARNING WARNING WARNING WARNING WARNING WARNING WARNING - -======================================================================== - - - ------------------------------------------------------------------------- -LoginForm ------------------------------------------------------------------------- - - - ------------------------------------------------------------------------- - - - ------------------------------------------------------------------------- -ChangePasswordForm ------------------------------------------------------------------------- - - - - - - - ------------------------------------------------------------------------- - - - ------------------------------------------------------------------------- -SignupForm ------------------------------------------------------------------------- - - - - - - - - - ------------------------------------------------------------------------- -ForgotMyPassword ------------------------------------------------------------------------- - -
-Username: -
- - - - ------------------------------------------------------------------------- -ChangePropertiesForm ------------------------------------------------------------------------- - - -

Changing Properties for

- - -
- - -
-

Properties

- - - - - - - - - -
Property NameValue
">
- - -
- -
- ------------------------------------------------------------------------- diff --git a/ZopeProducts/exUserFolder/doc/README.httpsAuthSource b/ZopeProducts/exUserFolder/doc/README.httpsAuthSource deleted file mode 100644 index 21697df3..00000000 --- a/ZopeProducts/exUserFolder/doc/README.httpsAuthSource +++ /dev/null @@ -1,28 +0,0 @@ -This plugin implements authentication from an https service. - -Upon installation, the mangament forms allow you to configure: -* the url to the service, -* the parameter that will contain the username -* the parameter that will contain the password -* The expected authorization response regex (returned from the authorization service). -* The default role that authorized users will be assinged upon their first login - -The https auth source posts a request over https to the named service with the username and -passowrd passed according to the parameters defined in the configuration. It will attempt -to match the authorization pattern specified, and if the pattern is found, the user will be -authenticated. - -Once a user has logged in, they will appear in xuf user list, and their roles can be updated. - -This auth source has been developed using the zodbBTreeProps plugin, and stores the user's -roles in this property tool. - -A typical use case for this authorization service might be to authenticate against -a legacy user directory for which no xuf auth plugin currently exists. Hopefully, the -development of a the auth service on the other end will be trivial, or better yet, -already exist. - -IMPORTANT NOTE: In order to use this plugin you must compile your python to include -ssl support. The python that ships with zope 2.X does not have this enabled by default. - -Thanks to akm, bcsaller, runyaga for all their help. diff --git a/ZopeProducts/exUserFolder/doc/README.pgAuthSource-Alternate b/ZopeProducts/exUserFolder/doc/README.pgAuthSource-Alternate deleted file mode 100644 index 8652263c..00000000 --- a/ZopeProducts/exUserFolder/doc/README.pgAuthSource-Alternate +++ /dev/null @@ -1,20 +0,0 @@ -This alternate pgAuthSource was developed to allow Zope and jakarta-tomcat to -share common PostGreSQL auth tables. It's really just a mod of the original -pgAuthSource, with changes to the original kept to a minimum. This should help -when it comes to cross porting improvements / maintenence changes between the -two versions. - -The only thing that's new is the table schema. This auth source uses: -A user table - Username, password - -A role table: - rolename - -and a associative userrole table for relating the two: - username, rolename - -ps. Use the Source, Luke! -If you dig a little you will find a couple of different ways of crypting -passwords commented out (plain and MD5). - diff --git a/ZopeProducts/exUserFolder/doc/README.radiusAuthSource b/ZopeProducts/exUserFolder/doc/README.radiusAuthSource deleted file mode 100644 index 60b940a5..00000000 --- a/ZopeProducts/exUserFolder/doc/README.radiusAuthSource +++ /dev/null @@ -1,12 +0,0 @@ -I have converted ZRadius to work with exUserFolder as an AuthSource -it should function at least as well as it functioned with GUF d8) --- akm - -Radius - - This product implements simple Radius authentication. If you need - to authenticate Zope users from a Radius server, this product will - plug into the GenericUserFolder product. - - © Copywrite 1999 Stuart Bishop <zen@cs.rmit.edu.au> - diff --git a/ZopeProducts/exUserFolder/doc/README.smbAuthSource b/ZopeProducts/exUserFolder/doc/README.smbAuthSource deleted file mode 100644 index ba4e52ab..00000000 --- a/ZopeProducts/exUserFolder/doc/README.smbAuthSource +++ /dev/null @@ -1,41 +0,0 @@ - -SMB Authentication Source for exUserFolder - -(C) Copyright 2000,2001 The Internet (Aust) Pty Ltd -ACN: 082 081 472 ABN: 83 082 081 472 -All Rights Reserved - -THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND -ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE -IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE -ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE -FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL -DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS -OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) -HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT -LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY -OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF -SUCH DAMAGE. - -This smbAuthSource uses pySMB by Michael Teo whose copyright is as follows. - -Copyright (C) 2001 Michael Teo - -This software is provided 'as-is', without any express or implied warranty. -In no event will the author be held liable for any damages arising from the -use of this software. - -Permission is granted to anyone to use this software for any purpose, -including commercial applications, and to alter it and redistribute it -freely, subject to the following restrictions: - -1. The origin of this software must not be misrepresented; you must not - claim that you wrote the original software. If you use this software - in a product, an acknowledgment in the product documentation would be - appreciated but is not required. - -2. Altered source versions must be plainly marked as such, and must not be - misrepresented as being the original software. - -3. This notice cannot be removed or altered from any source distribution. - diff --git a/ZopeProducts/exUserFolder/doc/README.txt b/ZopeProducts/exUserFolder/doc/README.txt deleted file mode 100644 index 3152aa79..00000000 --- a/ZopeProducts/exUserFolder/doc/README.txt +++ /dev/null @@ -1,127 +0,0 @@ -A lot of this stuff is now covered in the Unenlightened Zopistas Guide to -exUserFolder, so this document is slightly redundant (but not completely). -It's also shockingly out of date... - -A note on the version numbering... there's none of that odd/even -numbering nonsense you find in Lin*x land. The numbers are based on - -Major.Minor.Micro - -A bump in Major means a milestone or set of milestones has been reached. -A bump in Minor means some piece of functionality has been added, or -a major bug was fixed. -A bump in Micro usually means bug fixes. - -These numbers go from 0-99, and are not necessarily continuous or -monotonically increasing (but they are increasing). - -What you consider major and what I consider major are probably two -different things. - -Release candidates before a Major bump start at 99.. so; - -0.99.0 is the first Release Candidate prior to 1.0.0 -0.99.1 is the next Release Candidate -1.0.0 is the 'final' release. - -It's possible that there will be no changes between final release candidate -and release. - -Sometimes due to the nature of the changes a release will be marked -development. This usually means some core functionality was changed. - -Extensible User Folder - -Extensible User Folder is a user folder that requires the authentication -of users to be removed from the storage of properties for users. - -Writing new authentication or property sources is (almost) a trivial operation -and require no authentication knowledge to write, most simply return lists -of attributes, or dictionaries. You don't need to incorporate them into -the base exUserFolder code, they can be written as normal Zope Products, -(i.e. you can distribute new sources independently of exUserFolder). - -There are three authentication sources provided OOTB; - -o pgAuthSource -- Postgresql Authentication Source -Actually this is pretty generic, and could be used for most SQL databases, -the schema isn't all that advanced either. - -This source allows you to specify the table, and the name of each of the -columns (username, password, roles), so you can use an existing database. - - -All ZSQL Methods are available inside the pgAuthSource folder for editing. -You need to have a DB Connection already in place for use. - -o usAuthSource -- User Supplied Authentication -This is similar to Generic User Folder, or Generic User Sources for -Login Manager. You provide a set of methods; - -createUser -- if you want to create users. -cryptPassword -- if you want to encrypt passwords. -listUsers -- return a list of userIds. -listOneUser -- return a dictionary containing the username, password, and - a list of roles -getUsers -- return a list of users ala listOneUser but lots of them. - -that's it. listOneUser is mandatory. - -There is an example of ExternalMethods you could use to create an 'sql' -user source in the Extensions directory. - -o etcAuthSource -- File Based Authentication -This is etcUserFolder reworked to be a plugin for this. Since I used -etcUserFolder as a base for this product, I might as well add the functionality -in. - -Each of the plugins has a 'manage_addForm' that is called when the User Folder -is added, so that parameters can be garnered from the user (pg*Source e.g. -get the dbconnection) - -etcAuthSource doesn't allow roles to be set, although it does ask for -a default role to be assigned to a user (which it dutifully does). - - -There are two property sources provided: - -o pgPropertySource -- Postgresql Property Source -A very naive sql implementation for properties, works fine, I wouldn't want -to load it up too high though. - -o zodbProperySource -- ZODB Property Source -This is a very simple property keeper, and is more available as an example -of what functionality needs to be provided. - -There is a postUserCreate method which you can replace with anything really, -if you want to do something once a user is created (send an email to someone, -page someone...) - -You can mix-n-match authentication methods and property methods. - -You can have cookie or standard (Basic) authentication. - -docLogin and docLogout methods are present in the ZODB for editing, because -you will hate the way the default login and logout pages look d8) - -The various plugins need some more configurable options atm, but, it -shouldn't be that much of a drama to add them in soon. - -Arbitrary properties can be set on a user (at least if the PropertySource -is written correctly they can). - - - - - - -Will all work (assuming the user is logged in). - -When creating a new user any fields with user_ will be set as properties. -So 'user_email' field will create an 'email' property. You just have to -provide the input form, and exUserFolder will do the rest. - -This has only been lightly tested, but, it seems to work just fine. - - - diff --git a/ZopeProducts/exUserFolder/doc/README.zodbAuthSource b/ZopeProducts/exUserFolder/doc/README.zodbAuthSource deleted file mode 100644 index 492e7f3f..00000000 --- a/ZopeProducts/exUserFolder/doc/README.zodbAuthSource +++ /dev/null @@ -1,13 +0,0 @@ -ZODB Authentication Source for exUserFolder - -This is an auth source that works pretty much like the standard user folder provided by zope. -It stores the usernames, roles and passwords on a ZODB persistent dictionary. - -It doesn't require any configuration at all, just select it as your auth source and you're -ready to add user accounts. - - -Author: Alex Verstraeten (aka: zxc) -Email: alex@quad.com.ar - - diff --git a/ZopeProducts/exUserFolder/doc/UnenlightenedZopistasGuide.txt b/ZopeProducts/exUserFolder/doc/UnenlightenedZopistasGuide.txt deleted file mode 100644 index 547bdc20..00000000 --- a/ZopeProducts/exUserFolder/doc/UnenlightenedZopistasGuide.txt +++ /dev/null @@ -1,671 +0,0 @@ -The Unenlightened Zopistas Guide to exUserFolder. -(C) 2001-2003 Andrew Milton - -0. INTRODUCTION. - -exUserFolder is an extensible authentication product for the Zope -Application Server. It allows a user to choose from a number of -methods of authenticating their users, and allows the setting and -fetching of arbitrary properties on a User object. - -Authentication methods, and Property methods do not have to use the -same backing store, so it is possible to use legacy user sources, and -still have configuration information stored about a user. - -exUserFolder supports HTTP Basic Authentication, and the so called -Cookie Authentication schemes popular with most webservers. - -0.1 Audience. - -Everybody, and Nobody. If we build our product correctly, we shouldn't -need user documentation, that's why Nobody. For some reason, normal -sane people seem to lose all of their common sense when sitting in -front of a computer. To the point where plain messages e.g. "Please -Insert a Floppy", evoke a response of "What does that mean?" So that's -why this document is for Everybody. - -This is not a guide for writing your own authentication, property, or -membership sources. You need the Zen Masters Guide to exUserFolder -document for that. - - -1. GETTING STARTED - -exUserFolder requires Python 2.1 or above (may work with older -pythons, but, this is not supported). And has been tested on Zope -2.3.0 and above (including 2.4.3). - -exUserFolder comes as a source tarball, and it does not rely on any -outside dependencies to be work. Some items may require additional -products to be installed in your Zope tree, but, simply will not -appear if these are not available. Some items may also require -external products to add functionality to them, but, at no time should -the Product not install because of these dependencies. - - -1.1 Installing exUserFolder. - -Unpack exUserFolder in your Products directory. This can be achieved by -executing the following on most UNIX systems. - -gzip -d -c exUserFolder-Ma_Mi_u.tgz | tar xvf - - -where exUserFolder-Ma_Mi_u.tgz is the version of exUserFolder you have -downloaded. - -On systems that have the GNU tar this can be shortened to; - -tar zxvf exUserFolder-Ma_Mi_u.tgz - -You should restart Zope after unpacking. Installing the product will not -affect your Zope installation in anyway. - -If you go to Folder inside your Zope Management Interface, you should see -exUserFolder as a dropdown item near the bottom somewhere. - -Congratulations, it's installed. - - -2. AUTHENTICATION SOURCES AND YOU. - -The only mandatory component of an exUserFolder installation, is -choosing an Authentication Source. There are six Authentication -Sources to choose from in the default install. There are other add-on -Sources available from other parties. - -Each Authentication Source is different, and assumes at least some -knowledge of that type of authentication scheme. - -Most if not all sources store the password encrypted in some -manner. This means that discovering other people's passwords is going -to be more difficult, than with the standard user folder that comes -with Zope. - -By default crypt or fcrypt are used, which is are DES encryption -methods. While this is not the strongest, fastest, choose another -superlative, of encryption techniques, it is certainly adequate for -protecting webpages. - -In a later release exUserFolder will allow you to choose what method -is used for password hashing. - -Some Authentication Sources can list the users that are available, -some cannot (or will not). Some allow you to add users, and others do -not. What features are availble depend on the individual -Authentication Source. - - -2.1 ZODB Authentication Source - -The ZODB Authentication Source operates just like a normal User -Folder. It stores its authentication items in the ZODB as the name -suggests. This is the simplest folder to setup, requiring no -parameters. - -Choosing ZODB Authentication Source is recommended for testing your install. - - -2.2 File Based Authentication. - -File Based Authentication allows you to have a fixed set of users in a -file with their encrypted passwords. The prerequisites for this are -somewhat convoluted. - -In the root of your Zope Installation, on the actual file system (not -in the ZODB), create a directory called exUsers. Make sure that Zope -has access to that directory. - -This is the directory where you will create your files. - -This is a read only Authentication Source. You will not be able to -create users, or modify their passwords. You can change their roles if you -choose a Property Source. - -There are two parameters asked for; - -2.2.1 Password File - -This is the name of the file that contains your users and passwords. -It should be of the format; - -username:cryptedPassword -user2:otherCryptedPasswd - -I can contain other fields after the password also delimited by : but these -will not be ussed. - -This file should exist inside the exUsers directory. - -2.2.2 Default Role - -This is the role that all users should be given when the log in. Because this -is a Read Only authentication source, you may not be able to add Roles at a -later date. - - -2.3 Postgresql Authentication Source - -Postgresql Authentication source is an RDBMS backed user store. You -can add, change, and list users. It requires a Postgresql Database -Connection to be created before creating the User Folder. - -You should be familiar with databases, and with your schema before -using this Authentication Source. If you don't already have a table -structure in place, a default schema is provided called 'pgScheme.sql' -in the exUserFolder distribution. - -The required schema is very simple. You need to store usernames, -passwords, and roles. If your existing schema doesn't support a roles -column you will have to add one. - -The configuration scheme looks daunting, but, it is setup to use the -defaults for 'pgScheme.sql' so if you're using this you can safely -continue. - -We will run through the items. - -2.3.1 Database Connection - -If you have any database connections, they will be listed in the drop -down box. Choose the one that represents your connection to your users -table. - -2.3.2 Table Name - -This is the name of the table containing your users. If you have a -different table to the default, you should change it here. - -2.3.3 Username Column - -This is the name of the column inside your table that contains the -usernames or logins of your users. This should contain exactly what -the user needs to type in as their username. - - -2.3.4 Password Column - -This is the name of the column inside your table that contains the -encrypted passwords of your users. - - -2.3.5 Roles Column - -This is where the roles are stored. These are used to provide access -to items in Zope. - - -2.4 User Supplied Authentication Source - -This allows you to create your methods in DTML, PythonScripts, -External Methods, or any other callable Zope item for listing, -authenticating, adding and changing your users. - -It is beyond the scope of this guide to describe how to do this, but, -the API is quite well defined inside the source, and also in the -README.API document. - -This Authentication Source has no configuration parameters. - - -2.5 RADIUS Authentication Source - -This allows you to authenticate your users against a RADIUS server. If -you don't know what this means, then this User Source is not for you -:-) - -You will require a RADIUS server to be operating, and for the server -that Zope is running on to have access to it. You will also need to -know the secret key to access the RADIUS server. - -2.5.1 Host - -This is the host your RADIUS server is running on. - -2.5.2 Port - -This is the port your RADIUS server is running on. Older installs may -require this to be 1645. The new 'blessed' port by IANA is 1812, and -this is now the default port. - -2.5.3 Secret - -Every remote host has a secret key it has to share with the server in -order to gain access to the authentication server. You need to know -this. - -2.5.4 Retries - -Because this is a networked authentication service, errors can -occur. This sets the number of times it will try to authenticate -before giving up. - -2.5.5 Timeout - -This is how long the RADIUS authenticator will wait for a -response. Because RADIUS operates over UDP, which is a connectionless -protocol, answers may never come back, or never reach their -destination in the first place. - -The default is 5 seconds which is actually quite a long time. - - -2.6 SMB Authentication Source - -This source allows you to authenticate your users in a Microsoft -Environment, using the SMB protocols. This is not the same as -authenticating via Directory Services. - -If your SMB server requires passwords to be encrypted in transit, you'll -need to install mxCrypto. - -2.6.1 Host - -This is the host that your Authentication service is on, this is -normally an NT or Win2K server, but, it can also be a UNIX box running -Samba. This should be the NetBIOS name of the server. - -2.6.2 Domain - -This is the NT/Windows DOMAIN that the user is to authenticate -against. - -2.6.3 WINS Server IP Address (optional) - -If provided, this should be the IP address of the WINS server to be -queried to locate your auth host (see 2.5.1 above). - -If you leave this field empty, the location of the authentication host -will be queried by broadcast, which works just fine if the Zope -machine is on the same subnet as your auth host but not if the auth -host is across a subnet link or if it's in the same machine as Zope -(don't ask. Apparently, some braindmamaged creature at M$ decided that -a machine shouldn't answer to its own broadcasts no matter what) - -Fill in this field if you are getting "NetBIOSTimeout" errors but you -are sure that your auth host was specified correctly, or if Windows -machines in your subnet also use a WINS server. - - -2.7 LDAP Authentication - -This source allows you to authenticate your users against an LDAP -server. This code is based on the auth_ldap module for Apache. The -documentation for these parameters is unashamedly lifted directly from -the documentation of the Apache directives for auth_ldap. - -See: http://www.rudedog.org/auth_ldap/ - -You must choose a property source when using LDAP Authentication, all -of the properties associated with the LDAP user entry are stored as -properties when they authenticate. Items with multiple entries are -stored as a list of items. - -You will need the pyLDAP module installed to use this authsource. -If you don't have it installed, you will not see an LDAP Auth Source available -for use. - -2.7.1 URL - -An RFC 2255 URL which specifies the LDAP search parameters to use. The syntax -of the URL is -ldap://host:port/basedn?attribute?scope?filter - -ldap For regular ldap, use the string ldap. For secure LDAP, use ldaps - instead. Secure LDAP is only available if auth_ldap was compiled with - SSL support. -host:port The name/port of the ldap server (defaults to localhost:389 for ldap, - and localhost:636 for ldaps). - - Once a connection has been made to a server, that connection remains - active for the life of the Zope process, or until the LDAP server - goes down. - - If the LDAP server goes down and breaks an existing connection, - the Auth Source will attempt to re-connect - -basedn The DN of the branch of the directory where all searches should start - from. At the very least, this must be the top of your directory tree, - but could also specify a subtree in the directory. - -attribute The attribute to search for. Although RFC 2255 allows a - comma-separated list of attributes, only the first attribute will be - used, no matter how many are provided. If no attributes are provided, - the default is to use uid. It's a good idea to choose an attribute - that will be unique across all entries in the subtree you will be - using. - -scope The scope of the search. Can be either one or sub. Note that a scope - of base is also supported by RFC 2255, but is not supported by this - module. If the scope is not provided, or if base scope is specified, - the default is to use a scope of sub. - -filter A valid LDAP search filter. If not provided, defaults to (objectClass - =*), which will search for all objects in the tree. - -When doing searches, the attribute, filter and username passed by the HTTP -client are combined to create a search filter that looks like (&(filter) -(attribute=username)). - -For example, consider an URL of ldap://ldap.xuf.com/o=XUF?cn?sub?(posixid -=*). When a client attempts to connect using a username of The Jester, the -resulting search filter will be (&(posixid=*)(cn=The Jester)). - - -2.7.2 Bind DN - -An optional Distinguished Name user to bind to the server when searching -for entries. If not provided an Anonymous bind will be used. - -2.7.3 Bind Password. -A bind password to use in conjunction with the bind DN. Note that the bind -password is probably sensitive data, and should be properly protected. You -should only use the Bind DN and Bind Password if you absolutely -need them to search the directory. - -2.7.4 Cert DB Path - -Specifies in which directory LDAP Auth Source should look for the certificate -authorities database. There should be a file named cert7.db in that directory. - -2.7.5 Compare DN On Server - -When set, LDAP Auth Source will use the LDAP server to compare the -DNs. This is the only foolproof way to compare DNs. LDAP Auth Source -will search the directory for the DN specified with the require dn -directive, then, retrieve the DN and compare it with the DN retrieved -from the user entry. If this directive is not set, LDAP Auth Source -simply does a string comparison. It is possible to get false negatives -with this approach, but it is much faster. Note the LDAP Auth Source cache -can speed up DN comparison in most situations. - -2.7.6 Dereference Aliases - -This directive specifies when LDAP Auth Source will de-reference -aliases during LDAP operations. The default is always. - -2.7.7 Group Attribute is DN - -When set, this directive says to use the distinguished name of the -client username when checking for group membership. Otherwise, the -username will be used. For example, assume that the client sent the -username tjester, which corresponds to the LDAP DN cn=The Jester, -o=XUF. If this directive is set, LDAP Auth Source will check if the -group has cn=The Jester, o=XUF as a member. If this directive is not -set, then LDAP Auth Source will check if the group has tjester as a -member. - -2.7.8 Compare Cache Size - -This specifies the size of the cache used to cache LDAP compare -operations. The default is 1024 entries. Setting it to 0 disables -operation caching. - -2.7.9 Compare Cache TTL - -Specifies the time (in seconds) that entries in the operation cache -remain valid. The default is 600 seconds. - -2.7.10 Start TLS - -If this is set to Yes, LDAP Auth Source will start a secure TLS -session after connecting to the LDAP server. This requires your LDAP -server to support TLS. - -2.7.11 Require User (one per line) - -The require user directive specifies what usernames can access the -resource. Once LDAP Auth Source has retrieved a unique DN from the -directory, it does an LDAP compare operation using the username -specified in the require user to see if that username is part of the -just-fetched LDAP entry. Multiple users can be granted access by -putting multiple usernames in the box, separated with newlines. For -example, with a AuthLDAPURL of ldap://ldap/o=XUF?cn (i.e., cn is used -for searches), the following require entries could be used to restrict -access: The Jester Fred User Joe Manager - -Because of the way that LDAP Auth Source handles this directive, The -Jester could sign on as The Jester, Zen Jester or any other cn that he -has in his LDAP entry. Only the single require user line is needed to -support all values of the attribute in the user's entry. - -If the uid attribute was used instead of the cn attribute in the URL -above, the above three lines could be; - -tj -fred_u -jmanager - -2.7.12 Require Group (one per line) - -This directive specifies an LDAP group whose members are allowed -access. It takes the distinguished name of the LDAP group. For -example, assume that the following entry existed in the LDAP -directory: - -dn: cn=Administrators, o=XUF -objectClass: groupOfUniqueNames -uniqueMember: cn=The Jester, o=XUF -uniqueMember: cn=Fred User, o=XUF - -The following directive would grant access to both Fred and Jester: - -require group cn=Administrators, o=XUF - -Behavior of this directive is modified by the Group Attribute and -Group Attribute Is DN options. - -2.7.13 Require DN - -The require dn option allows the administrator to grant access based -on distinguished names. It specifies a DN that must match for access -to be granted. If the distinguished name that was retrieved from the -directory server matches the distinguished name in the require dn, -then authorization is granted. - -The following directive would grant access to a specific DN: -require dn cn=The Jester, o=XUF - -Behavior of this directive is modified by the Compare DN On Server option. - -2.7.14 Default Manager - -This allows you to specify the username of the Manager for this area. -The manager will still need to meet auth requirements above, but, if -they do they will get the 'Manager' role added to their list of roles. - -2.7.15 Default Role - -This is a role to be assigned to users when they auth correctly. This -is to differentiate them from merely being 'authenticated'. - -2.7.16 Examples - - * Grant access to anyone who exists in the LDAP directory, using their UID - for searches. - URL ldap://ldap1.zope.com:389/ou=People, o=XUF?uid?sub?(objectClass=*) - - * The next example is similar to the previous one, but is uses the common - name instead of the UID. Note that this could be problematical if multiple - people in the directory share the same cn, because a search on cn must - return exactly one entry. That's why this approach is not recommended: it's - a better idea to choose an attribute that is guaranteed unique in your - directory, such as uid. - URL ldap://ldap.zope.com/ou=People, o=XUF?cn - - * Grant access to anybody in the Administrators group. The users must - authenticate using their UID. - URL ldap://ldap.zope.com/o=XUF?uid - require group: - cn=Administrators, o=XUF - - * The next example assumes that everyone at XUF who carries an - alphanumeric pager will have an LDAP attribute of qpagePagerID. The example - will grant access only to people (authenticated via their UID) who have - alphanumeric pagers: - URL: ldap://ldap.zope.com/o=XUF?uid??(qpagePagerID=*) - - * The next example demonstrates the power of using filters to accomplish - complicated administrative requirements. Without filters, it would have - been necessary to create a new LDAP group and ensure that the group's - members remain synchronized with the pager users. This becomes trivial with - filters. The goal is to grant access to anyone who has a filter, plus grant - access to Joe Manager, who doesn't have a pager, but does need to access - the same resource: - URL ldap://ldap.zope.com/o=XUF?uid??(|(qpagePagerID=*)(uid=jmanager)) - - This last may look confusing at first, so it helps to evaluate what the - search filter will look like based on who connects, as shown below. - If Fred User connects as fuser, the filter would look like - - (&(|(qpagePagerID=*)(uid=jmanager))(uid=fuser)) - - The above search will only succeed if fuser has a pager. When Joe Manager - connects as jmanager, the filter looks like - - (&(|(qpagePagerID=*)(uid=jmanager))(uid=jmanager)) - - The above search will succeed whether jmanager has a pager or not. - - -2.8 General Items. - -You can choose to use standard auth, or cookie auth, and you can -decide how long you want to cache the users credentials before -retrying. - -2.8.1 Authentication Type - -2.8.1.1 Standard Authentication - -This method causes the browser to pop up a dialog box to ask for the -username and password. - -2.8.1.2 Cookie Authentication - -This method allows you to use a normal HTML form to get the username -and password from the user. It also will present the default form to -the user if they try to access an unauthorised area. - - -2.8.1.3 Secure Cookie based Authentication - -This method, like Cookie Authentication allows you to use a HTML form -to get the user details. However, the cookie it uses does not contain -any login information. It is internally checked against a cache of -hashes and the information is derived from that. This cache disappears -if you restart Zope, so this is not a good option for people who want -to persistently cache logins across sessions. - - -2.8.2 Credential Cache Timeout in Seconds - -exUserFolder by default caches credential information, so that the -authorisation source isn't hit *for every object and page* that has to -be fetched. For remote authentication services this can slow things -down quite considerably. Even setting this to a modest setting will -quicken response times. - -Setting this too long could cause problems if you want to lock out a -troublesome user. The credential cache is flushed if someone provides -a password that doesn't match the one in the cache. - - -2.8.3 Negative Credential Cache Timeout in Seconds - -exUserFolder allows you to cache login failures for users that do not -exist. This means you don't have to go out to your auth source when -you know for certain this user is never going to be able to -authenticate. - -Due to the way some auth sources are designed, this doesn't work for -auth sources like SMB Auth Source that lie initially about the user -existing (because you can't verify the existence of a user without -authenticating them), and then check the credentials later. - -It's possible to create a hybrid auth source that lets this work -correctly for auth sources that can't list the users. - - -2.8.4 Log out users who expire from cache? - -If you've got caching turned on, then this will force any user who has -their session expire to login again. Some people like to do this. - - -2.8.5 Activate Session Tracking for anoymous users? - -For any anonymous user, a new temporary user is created. This allows -you to set/get properties for anonymous users too. Currently -experimental. - - -3.0 PROPERTY SOURCES - -4.0 MEMBERSHIP SOURCES - -5.0 TIPS FOR THE UNWARY - -Generally these things apply to Cookie Authentication models, since -there is additional access required to present the login form. - -5.1 Too much protection. - -A lot of people try to protect a folder by placing an exUserFolder -inside. They then change the permissions on this folder to only allow -Authenticated or some Local Role to have permission. - -5.1.1 The problem - -When you try to access the folder, instead of getting the form, you -get a popup box, even though you chose Cookie Authentication. Even -when you enter a username and password it doesn't work. - - -5.1.2 What happened - -You tried to access an area you don't have access to. Zope found the -closest user folder to the object you were trying to access. The user -folder decided you were not authorised and tried to display the login -form. You don't have access to view the login form, so Zope finds the -nearest user folder to the login form, which is the user folder above -the protected directory. It pops up the authentication dialog. If you -put in a valid username and password for this top level, then lower -level then displays the login form. - -5.1.3 Solution 1 (preferred). - -Place the user folder one level *above* the folder you want to protect, -that is in the unprotected area. Everything should work fine. - -5.1.4. Solution 2 (not so preferred). - -Set the 'View' permission on the docLogin form inside the acl_users -folder. You can get there by Choosing 'Contents' on docLogin and -scrolling down to the bottom. - -6.0 MISCELLANY - -6.1 Adding an exUserFolder from a product. - -You can add an exUserFolder from a Python product fairly easily, if -not a tad messily. - - -from Products.exUserFolder.exUserFolder import manage_addexUserFolder, eUserFolder - -manage_addexUserFolder(authId='zodbAuthSource', propId='zodbPropSource', - memberId='basicMemberSource', - cookie_mode=1, session_length=600, REQUEST) - -Obviously change authId, propId, and memberId to what you want. -However, you'll need to ram in the appropriate form fields for the various -source constructors into your REQUEST. - -6.2 Session Tracking. - -Session tracking (currently) relies on having the credential cache -active, and a property source active. Your trackable user will only -last as long as they are not expired from the cache. You should set -the cache expiry length to be somewhat longer than normal if you plan -to use Session Tracking, and you should also be prepared to check that -the current session is valid. diff --git a/ZopeProducts/exUserFolder/doc/mysql.sql b/ZopeProducts/exUserFolder/doc/mysql.sql deleted file mode 100644 index b2bf5f82..00000000 --- a/ZopeProducts/exUserFolder/doc/mysql.sql +++ /dev/null @@ -1,18 +0,0 @@ -DROP TABLE IF EXISTS passwd; -CREATE TABLE passwd ( - username varchar(64) NOT NULL PRIMARY KEY, - password varchar(64) NOT NULL, - roles varchar(255) -); - -DROP TABLE IF EXISTS UserProperties; -CREATE TABLE UserProperties ( - username varchar(64) NOT NULL, - prop_key varchar(128) NOT NULL, - value text NOT NULL, - istemporary int -); - -CREATE UNIQUE INDEX username_prop_idx on UserProperties(username,prop_key ); -CREATE INDEX username_idx on UserProperties(username); - diff --git a/ZopeProducts/exUserFolder/doc/pgAndreasScheme.sql b/ZopeProducts/exUserFolder/doc/pgAndreasScheme.sql deleted file mode 100644 index 57fd21a4..00000000 --- a/ZopeProducts/exUserFolder/doc/pgAndreasScheme.sql +++ /dev/null @@ -1,14 +0,0 @@ -CREATE TABLE "passwd" ( - "username" character varying(64) UNIQUE NOT NULL, - "password" character varying(64) NOT NULL, - "roles" character varying(255), - Constraint "passwd_pkey" Primary Key ("username") -); - -CREATE TABLE "userproperties" ( - "username" character varying(64) NOT NULL REFERENCES passwd (username) ON DELETE CASCADE ON UPDATE CASCADE, - "key" character varying(128) NOT NULL, - "value" text NOT NULL -); - -CREATE INDEX "username_idx" on "userproperties" using btree ( "username" "varchar_ops" ); diff --git a/ZopeProducts/exUserFolder/doc/pgScheme.sql b/ZopeProducts/exUserFolder/doc/pgScheme.sql deleted file mode 100644 index 45e5e1a0..00000000 --- a/ZopeProducts/exUserFolder/doc/pgScheme.sql +++ /dev/null @@ -1,46 +0,0 @@ -CREATE SEQUENCE "passwd_userid_seq" start 1 increment 1 maxvalue 2147483647 minvalue 1 cache 1 ; - --- --- TOC Entry ID 6 (OID 24949) --- --- Name: passwd Type: TABLE Owner: akm --- - -CREATE TABLE "passwd" ( - "userid" integer DEFAULT nextval('"passwd_userid_seq"'::text) NOT NULL, - "username" character varying(64) NOT NULL, - "password" character varying(64) NOT NULL, - "roles" character varying(255), - Constraint "passwd_pkey" Primary Key ("userid") -); - --- --- TOC Entry ID 4 (OID 24965) --- --- Name: userproperties_propertyid_seq Type: SEQUENCE Owner: akm --- - -CREATE SEQUENCE "userproperties_propertyid_seq" start 1 increment 1 maxvalue 2147483647 minvalue 1 cache 1 ; - --- --- TOC Entry ID 7 (OID 24984) --- --- Name: userproperties Type: TABLE Owner: akm --- - -CREATE TABLE "userproperties" ( - "propertyid" integer DEFAULT nextval('"userproperties_propertyid_seq"'::text) NOT NULL, - "username" character varying(64) NOT NULL, - "key" character varying(128) NOT NULL, - "value" text NOT NULL, - "istemporary" integer, - Constraint "userproperties_pkey" Primary Key ("propertyid") -); - --- --- TOC Entry ID 8 (OID 24984) --- --- Name: "username_idx" Type: INDEX Owner: akm --- - -CREATE INDEX "username_idx" on "userproperties" using btree ( "username" "varchar_ops" ); diff --git a/ZopeProducts/exUserFolder/dtml/docLogin.dtml b/ZopeProducts/exUserFolder/dtml/docLogin.dtml deleted file mode 100644 index 87e30194..00000000 --- a/ZopeProducts/exUserFolder/dtml/docLogin.dtml +++ /dev/null @@ -1,49 +0,0 @@ - -
- - - - - - -

- -

- - - - - Added by Emmanuel for ScoDoc - - - - - - - - - - - - - - - -
- Name - - -
- Password - - -
-
-
-Ok "> -
- -
- -
- diff --git a/ZopeProducts/exUserFolder/dtml/docLoginRedirect.dtml b/ZopeProducts/exUserFolder/dtml/docLoginRedirect.dtml deleted file mode 100644 index 30ed97b4..00000000 --- a/ZopeProducts/exUserFolder/dtml/docLoginRedirect.dtml +++ /dev/null @@ -1,26 +0,0 @@ - - -Logging In - -"> -&authFailedCode=&dtml-authFailedCode;
"> - - - - - diff --git a/ZopeProducts/exUserFolder/dtml/docLogout.dtml b/ZopeProducts/exUserFolder/dtml/docLogout.dtml deleted file mode 100644 index 5210fc74..00000000 --- a/ZopeProducts/exUserFolder/dtml/docLogout.dtml +++ /dev/null @@ -1,16 +0,0 @@ - -

-

-

Vous êtes déconnecté de ScoDoc. -

- -

">revenir à l'accueil

- -
-

(Attention: si vous êtes administrateur, vous ne pouvez vous déconnecter complètement qu'en relançant votre navigateur) -

-
- - - - diff --git a/ZopeProducts/exUserFolder/dtml/mainUser.dtml b/ZopeProducts/exUserFolder/dtml/mainUser.dtml deleted file mode 100644 index e1188165..00000000 --- a/ZopeProducts/exUserFolder/dtml/mainUser.dtml +++ /dev/null @@ -1,55 +0,0 @@ - - - -
- -

-The following users have been defined. Click on the name of a -user to edit that user. -

- - - - - - - - - - - - - - - - -
- - - -
  - -
- - -
-
- -

-There are no users defined. -

- -

-

- -
-

-
-
- - - diff --git a/ZopeProducts/exUserFolder/dummyZBabelTag.py b/ZopeProducts/exUserFolder/dummyZBabelTag.py deleted file mode 100644 index fc45c244..00000000 --- a/ZopeProducts/exUserFolder/dummyZBabelTag.py +++ /dev/null @@ -1,164 +0,0 @@ -try: - from Products.ZBabel import ZBabelTag -except: - - from DocumentTemplate.DT_String import String - from DocumentTemplate.DT_Util import render_blocks, Eval, ParseError - import string, zLOG - - - # fake Babel/Fish Tags - - class ZBabelTag: - '''ZBabel Tag class - The cool translation tag''' - - # define the name of the tag; also tell the system it is a doublet - name = 'babel' - blockContinuations = () - - - def __init__(self, blocks): - '''__init__(self, blocks) --> Initialize tag object; return None''' - (tname, args, section,) = blocks[0] - - self.section = section - - - def render(self, md): - '''render(self, md) --> Do the Translation; return string''' - return render_blocks(self.section.blocks, md) - __call__=render - # register the DTML-BABEL tag - String.commands['babel'] = ZBabelTag - - class FishTag: - '''Fish Tag class - Short-Cut version of the cool translation tag (babel) - - This tag is used to quickly translate menu-like text snippets, similar to - the KDE translation.''' - - # define the tag name - name = 'fish' - - # define additional variables - literal = 1 - - src = 'label' - attrs = {'dst': None, 'label': '', 'data': None, 'towerId': None} - - def __init__(self, args): - '''__init__(self, blocks) --> Initialize tag object; return None''' - self.section = None - args = parseTagParameters(args, tag=self.name) - self.args = self.validateArguments(args) - - for attr in self.attrs.keys(): - setattr(self, attr, self.attrs[attr]) - - def validateArguments(self, args): - '''validateArguments(self, args) --> try to evaluate the passed expression or try to get an object from the passed id; if all this fails, leave the string, it is probably cool!; return tuple of (name, value)''' - # I stole this from dtml-let... - # SR: Like he said: Always copy existing code to make you life easier (evben though - # I changed some variables around - for count in range(len(args)): - (name, expr,) = args[count] - if ((expr[:1] == '"') and ((expr[-1:] == '"') and (len(expr) > 1))): - expr = expr[1:-1] - try: - - args[count] = (name, Eval(expr).eval) - - except SyntaxError, v: - (m, (huh, l, c, src,),) = v - raise ParseError, (('Expression (Python) Syntax error:' + - '
\012%s\012
\012' % v[0]), 'babel') - - elif ((expr[:1] == "'") and ((expr[-1:] == "'") and (len(expr) > 1))): - expr = expr[1:-1] - args[count] = (name, expr) - - return args - - def render(self, md): - '''render(self, md) --> Do the Translation; return string''' - data = None - for name, expr in self.args: - if type(expr) is type(''): - try: - data = md[expr] - except: - data = expr - else: - data = expr(md) - - #zLOG.LOG("exUserFolder", zLOG.INFO, "rendering name=%s expr=%s data=%s"%(name,expr,data)) - - print data - return str(data) - - __call__=render - - - # register the DTML-FISH tag - String.commands['fish'] = FishTag - - - -try: - import re - parmre=re.compile('''([\000- ]*([^\000- ="']+)=([^\000- ="']+))''');#")) - dqparmre=re.compile('([\000- ]*([^\000- ="]+)="([^"]*)")') - sqparmre=re.compile('''([\000- ]*([^\000- =']+)='([^']*)')''') -except: - import regex - parmre=regex.compile('''([\000- ]*([^\000- ="']+)=([^\000- ="']+))''');#")) - dqparmre=regex.compile('([\000- ]*([^\000- ="]+)="([^"]*)")') - sqparmre=regex.compile('''([\000- ]*([^\000- =']+)='([^']*)')''') - - - -def parseTagParameters(paramText, result = None, tag = 'babel', - parmre=parmre, - dqparmre=dqparmre, - sqparmre=sqparmre, - **parms): - result = (result or []) - - parsedParam = parmre.match(paramText) - dqParsedParam = dqparmre.match(paramText) - sqParsedParam = sqparmre.match(paramText) - - # Parse parameters of the form: name=value - if parsedParam is not None: - name = parsedParam.group(2) - value = parsedParam.group(3) - length = len(parsedParam.group(1)) - - # Parse parameters of the form: name="value" - elif dqParsedParam is not None: - name = dqParsedParam.group(2) - value = ('"%s"' % dqParsedParam.group(3)) - length = len(dqParsedParam.group(1)) - - # Parse parameters of the form: name='value' - elif sqParsedParam is not None: - name = sqParsedParam.group(2) - value = ('''"'%s'"''' % sqParsedParam.group(3)) - length = len(sqParsedParam.group(1)) - - else: - # There are no more parameters to parse - if ((not paramText) or (not string.strip(paramText))): - return result - raise ParseError, (('invalid parameter: "%s"' % paramText), tag) - - # add the parameter/value pait to the results - result.append((name, value)) - - # remove the found parameter from the paramText - paramText = string.strip(paramText[length:]) - - if paramText: - return apply(parseTagParameters, (paramText, result, tag), parms) - else: - return result diff --git a/ZopeProducts/exUserFolder/exUser.gif b/ZopeProducts/exUserFolder/exUser.gif deleted file mode 100644 index c7f852b0..00000000 Binary files a/ZopeProducts/exUserFolder/exUser.gif and /dev/null differ diff --git a/ZopeProducts/exUserFolder/exUserFolder.gif b/ZopeProducts/exUserFolder/exUserFolder.gif deleted file mode 100644 index fea892ae..00000000 Binary files a/ZopeProducts/exUserFolder/exUserFolder.gif and /dev/null differ diff --git a/ZopeProducts/exUserFolder/exUserFolder.py b/ZopeProducts/exUserFolder/exUserFolder.py deleted file mode 100644 index a5b07c8e..00000000 --- a/ZopeProducts/exUserFolder/exUserFolder.py +++ /dev/null @@ -1,1380 +0,0 @@ -# Zope User Folder for ScoDoc -# Adapte de l'Extensible User Folder -# simplifie pour les besoins de ScoDoc. -# Emmanuel Viennet 2013 - -# -# Extensible User Folder -# -# (C) Copyright 2000,2001 The Internet (Aust) Pty Ltd -# ACN: 082 081 472 ABN: 83 082 081 472 -# All Rights Reserved -# -# THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND -# ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE -# IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE -# ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE -# FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL -# DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS -# OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) -# HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT -# LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY -# OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF -# SUCH DAMAGE. -# -# Author: Andrew Milton -# $Id: exUserFolder.py,v 1.93 2004/11/10 14:15:33 akm Exp $ - -############################################################################## -# -# Zope Public License (ZPL) Version 0.9.4 -# --------------------------------------- -# -# Copyright (c) Digital Creations. All rights reserved. -# -# Redistribution and use in source and binary forms, with or -# without modification, are permitted provided that the following -# conditions are met: -# -# 1. Redistributions in source code must retain the above -# copyright notice, this list of conditions, and the following -# disclaimer. -# -# 6. Redistributions of any form whatsoever must retain the -# following acknowledgment: -# -# "This product includes software developed by Digital -# Creations for use in the Z Object Publishing Environment -# (http://www.zope.org/)." -# -# Disclaimer -# -# THIS SOFTWARE IS PROVIDED BY DIGITAL CREATIONS ``AS IS'' AND -# ANY EXPRESSED OR IMPLIED WARRANTIES, INCLUDING, BUT NOT -# LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND -# FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT -# SHALL DIGITAL CREATIONS OR ITS CONTRIBUTORS BE LIABLE FOR ANY -# DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR -# CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, -# PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, -# DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND -# ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT -# LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING -# IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF -# THE POSSIBILITY OF SUCH DAMAGE. -# -############################################################################## - -# Portions Copyright (c) 2002 Nuxeo SARL , -# Copyright (c) 2002 Florent Guillaume . -# -# Redistribution and use in source and binary forms, with or without -# modification, are permitted provided that the following conditions are -# met: -# -# 1. Redistributions of source code must retain the above copyright -# notice, this list of conditions and the following disclaimer. -# -# 2. Redistributions in binary form must reproduce the above copyright -# notice, this list of conditions and the following disclaimer in -# the documentation and/or other materials provided with the -# distribution. -# -# THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS -# IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED -# TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A -# PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT -# OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, -# SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT -# LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, -# DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY -# THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT -# (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE -# OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. - -import Globals, App.Undo, socket, os, string, sha, random, sys, zLOG - -from Globals import DTMLFile, PersistentMapping -from string import join,strip,split,lower,upper,find - -from OFS.Folder import Folder -from OFS.CopySupport import CopyContainer - -from base64 import decodestring, encodestring -from urllib import quote, unquote - -from Acquisition import aq_base -from AccessControl import ClassSecurityInfo -from AccessControl.Role import RoleManager -from AccessControl.User import BasicUser, BasicUserFolder, readUserAccessFile -from AccessControl.PermissionRole import PermissionRole -from AccessControl.ZopeSecurityPolicy import _noroles -from OFS.DTMLMethod import DTMLMethod -from time import time -from OFS.ObjectManager import REPLACEABLE -from Persistence import Persistent - -from PropertyEditor import * - -from User import User, AnonUser -from UserCache.UserCache import GlobalUserCache, GlobalNegativeUserCache, GlobalAdvancedCookieCache, SessionExpiredException - -from LoginRequiredMessages import LoginRequiredMessages - -from AccessControl import Unauthorized - -class LoginRequired(Exception): - """Login required""" - pass - - -# If there is no NUG Product just define a dummy class -try: - from Products.NuxUserGroups.UserFolderWithGroups import BasicGroupFolderMixin, _marker -except ImportError: - class BasicGroupFolderMixin: - pass - _marker = None - -# Little function to create temp usernames -def createTempName(): - t=time() - t1=time() - t2=time() - t3 = 0.0 - t3 = (t + t1 + t2) / 3 - un = "Anonymous %.0f"%(t3) - return(un) - - -manage_addexUserFolderForm=DTMLFile('dtml/manage_addexUserFolder', globals(), __name__='manage_addexUserFolderForm') - - - -def manage_addexUserFolder(self, authId, propId, memberId, - cookie_mode=0, session_length=0, - not_session_length=0, - sessionTracking=None, idleTimeout=None, - REQUEST={}, groupId=None, cryptoId=None): - """ """ - if hasattr(self.aq_base, 'acl_users'): - return Globals.MessageDialog(self,REQUEST, - title ='Item Exists', - message='This object already contains a User Folder', - action ='%s/manage_main' % REQUEST['URL1']) - ob=exUserFolder(authId, propId, memberId, groupId, cryptoId, cookie_mode, - session_length, sessionTracking, idleTimeout, - not_session_length) - - self._setObject('acl_users', ob, None, None, 0) - self.__allow_groups__=self.acl_users - ob=getattr(self, 'acl_users') - ob.postInitialisation(REQUEST) - - if REQUEST: - return self.manage_main(self, REQUEST) - return '' - -# -# Module level caches -# -XUFUserCache=GlobalUserCache() -XUFNotUserCache=GlobalNegativeUserCache() -XUFCookieCache=GlobalAdvancedCookieCache() - -class exUserFolder(Folder,BasicUserFolder,BasicGroupFolderMixin, - CopyContainer): - """ """ - - # HACK! We use this meta_type internally so we can be pasted into - # the root. We registered with 'exUserFolder' meta_type however, so - # our constructors work. - meta_type='User Folder' - id ='acl_users' - title ='Extensible User Folder' - icon ='misc_/exUserFolder/exUserFolder.gif' - - isPrincipiaFolderish=1 - isAUserFolder=1 - __allow_access_to_unprotected_subobjects__=1 - authSources={} - propSources={} - cryptoSources={} - membershipSources={} - groupSources={} # UNUSED by ScoDoc - - manage_options=( - {'label':'Users', 'action':'manage_main'}, - {'label':'Groups', 'action':'manage_userGroups'}, - {'label':'Parameters', 'action':'manage_editexUserFolderForm'}, - {'label':'Authentication Source','action':'manage_editAuthSourceForm'}, - {'label':'Properties Source','action':'manage_editPropSourceForm'}, - {'label':'Membership Source', 'action':'manage_editMembershipSourceForm'}, - {'label':'Cache Data', 'action':'manage_showCacheData'}, - {'label':'Security', 'action':'manage_access'}, - {'label':'Contents', 'action':'manage_contents'}, - {'label':'Ownership', 'action':'manage_owner'}, - {'label':'Undo', 'action':'manage_UndoForm'}, - ) - - __ac_permissions__=( - ('View management screens', ('manage','manage_menu','manage_main', - 'manage_copyright', 'manage_tabs', - 'manage_properties', 'manage_UndoForm', - 'manage_edit', 'manage_contents', - 'manage_cutObjects','manage_copyObjects', - 'manage_pasteObjects', - 'manage_renameForm', - 'manage_renameObject', - 'manage_renameObjects', ), - ('Manager',)), - - ('Undo changes', ('manage_undo_transactions',), - ('Manager',)), - - ('Change permissions', ('manage_access',), - ('Manager',)), - - ('Manage users', ('manage_users', 'manage_editUserForm', - 'manage_editUser', 'manage_addUserForm', - 'manage_addUser', 'manage_userActions', - 'userFolderAddGroup', - 'userFolderDelGroups', - 'getGroupNames', - 'getGroupById', - 'manage_userGroups', - 'manage_addGroup', - 'manage_showGroup',), - ('Manager',)), - - ('Change exUser Folders', ('manage_edit',), - ('Manager',)), - - ('View', ('manage_changePassword', - 'manage_forgotPassword','docLoginRedirect', - 'logout', 'DialogHeader', - 'DialogFooter', 'manage_signupUser', - 'MessageDialog', 'redirectToLogin','manage_changeProps'), - ('Anonymous', 'Authenticated', 'Manager')), - - ('Manage properties', ('manage_addProperty', - 'manage_editProperties', - 'manage_delProperties', - 'manage_changeProperties', - 'manage_propertiesForm', - 'manage_propertyTypeForm', - 'manage_changePropertyTypes', - ), - ('Manager',)), - ('Access contents information', ('hasProperty', 'propertyIds', - 'propertyValues','propertyItems', - 'getProperty', 'getPropertyType', - 'propertyMap', 'docLoginRedirect', - 'DialogHeader', 'DialogFooter', - 'MessageDialog', 'redirectToLogin',), - ('Anonymous', 'Authenticated', 'Manager')), - ) - manage_access=DTMLFile('dtml/access',globals()) - manage_tabs=DTMLFile('common/manage_tabs',globals()) - manage_properties=DTMLFile('dtml/properties', globals()) - manage_main=DTMLFile('dtml/mainUser', globals()) - manage_contents=Folder.manage_main - manage_showCacheData=DTMLFile('dtml/manage_showCacheData', globals()) - - # This is going away soon... - docLoginRedirect=DTMLFile('dtml/docLoginRedirect', globals()) - - # Stupid crap - try: - manage_contents._setName('manage_contents') - except AttributeError: - pass - - - MessageDialog=DTMLFile('common/MessageDialog', globals()) - MessageDialog.__replaceable__ = REPLACEABLE - - manage_addUserForm=DTMLFile('dtml/manage_addUserForm',globals()) - manage_editUserForm=DTMLFile('dtml/manage_editUserForm',globals()) - - DialogHeader__roles__=() - DialogHeader=DTMLFile('common/DialogHeader',globals()) - DialogFooter__roles__=() - DialogFooter=DTMLFile('common/DialogFooter',globals()) - - manage_editAuthSourceForm=DTMLFile('dtml/manage_editAuthSourceForm',globals()) - manage_editPropSourceForm=DTMLFile('dtml/manage_editPropSourceForm',globals()) - manage_editMembershipSourceForm=DTMLFile('dtml/manage_editMembershipSourceForm', globals()) - - manage_addPropertyForm=DTMLFile('dtml/manage_addPropertyForm', globals()) - manage_createPropertyForm=DTMLFile('dtml/manage_createPropertyForm', globals()) - manage_editUserPropertyForm=DTMLFile('dtml/manage_editUserPropertyForm', globals()) - - manage_editexUserFolderForm=DTMLFile('dtml/manage_editexUserFolderForm', globals()) - - manage_userGroups=DTMLFile('dtml/mainGroup',globals()) - - - # Use pages from NUG if it's there, otherwise no group support - try: - manage_addGroup = BasicGroupFolderMixin.manage_addGroup - manage_showGroup = BasicGroupFolderMixin.manage_showGroup - except: - manage_addGroup = None - manage_showGroup = None - - # No more class globals - - # sessionLength=0 # Upgrading users should get no caching. - # notSessionLength=0 # bad cache limit - # cookie_mode=0 - # sessionTracking=None # Or session tracking. - # idleTimeout=0 - - def __init__(self, authId, propId, memberId, groupId, cryptoId, - cookie_mode=0, session_length=0, sessionTracking=None, - idleTimeout=0, not_session_length=0): - self.cookie_mode=cookie_mode - self.sessionLength=session_length - self.notSessionLength=not_session_length - self.sessionTracking=sessionTracking - self.idleTimeout=idleTimeout - - _docLogin=DTMLFile('dtml/docLogin',globals()) - _docLogout=DTMLFile('dtml/docLogout',globals()) - - docLogin=DTMLMethod(__name__='docLogin') - docLogin.manage_edit(data=_docLogin, title='Login Page') - self._setObject('docLogin', docLogin, None, None, 0) - - docLogout=DTMLMethod(__name__='docLogout') - docLogout.manage_edit(data=_docLogout, title='Logout Page') - self._setObject('docLogout', docLogout, None, None, 0) - - postUserCreate=DTMLMethod(__name__='postUserCreate') - postUserCreate.manage_edit(data=_postUserCreate, title='Post User Creation methods') - self._setObject('postUserCreate', postUserCreate, None, None, 0) - - self.manage_addAuthSource=self.authSources[authId].manage_addMethod - self.manage_addPropSource=self.propSources[propId].manage_addMethod - self.manage_addMembershipSource=self.membershipSources[memberId].manage_addMethod - - self.manage_addGroupSource=None # UNUSED by ScoDoc - self.currentGroupsSource=None - - if cryptoId: - self.cryptoId = cryptoId - else: - self.cryptoId = 'Crypt' - - def __setstate__(self, state): - Persistent.__setstate__(self, state) - if not hasattr(self, 'currentGroupSource'): - self.currentGroupSource = None - if not hasattr(self, 'sessionLength'): - self.sessionLength = 0 - if not hasattr(self, 'notSessionLength'): - self.notSessionLength = 0 - if not hasattr(self, 'cookie_mode'): - self.cookie_mode = 0 - if not hasattr(self, 'sessionTraining'): - self.sessionTracking = None - if not hasattr(self, 'idleTimeout'): - self.idleTimeout=0 - - def manage_beforeDelete(self, item, container): - zLOG.LOG("exUserFolder", zLOG.BLATHER, "Attempting to delete an exUserFolder instance") - if item is self: - try: - self.cache_deleteCache() - self.xcache_deleteCache() - zLOG.LOG("exUserFolder", zLOG.BLATHER, "-- Caches deleted") - except: - #pass - zLOG.LOG("exUserFolder", zLOG.BLATHER, "-- Cache deletion failed") - - try: - del container.__allow_groups__ - zLOG.LOG("exUserFolder", zLOG.BLATHER, "-- container.__allow_groups_ deleted") - except: - #pass - zLOG.LOG("exUserFolder", zLOG.BLATHER, "-- container.__allow_groups_ deletion failed") - - - def manage_afterAdd(self, item, container): - zLOG.LOG("exUserFolder", zLOG.BLATHER, "Adding an exUserFolder") - - if item is self: - if hasattr(self, 'aq_base'): self=self.aq_base - container.__allow_groups__=self - - def manage_editPropSource(self, REQUEST): - """ Edit Prop Source """ - if self.currentPropSource: - self.currentPropSource.manage_editPropSource(REQUEST) - return self.manage_main(self, REQUEST) - - def manage_editAuthSource(self, REQUEST): - """ Edit Auth Source """ - self.currentAuthSource.manage_editAuthSource(REQUEST) - return self.manage_main(self, REQUEST) - - def manage_editMembershipSource(self, REQUEST): - """ Edit Membership Source """ - if self.currentMembershipSource: - return self.currentMembershipSource.manage_editMembershipSource(REQUEST) - - def postInitialisation(self, REQUEST): - self.manage_addAuthSource(self=self,REQUEST=REQUEST) - self.manage_addPropSource(self=self,REQUEST=REQUEST) - self.manage_addMembershipSource(self=self,REQUEST=REQUEST) - self.currentGroupSource = None - - def addAuthSource(self, REQUEST={}): - return self.manage_addAuthSourceForm(self, REQUEST) - - def addPropSource(self, REQUEST={}): - return self.manage_addPropSourceForm(self, REQUEST) - - def addMembershipSource(self, REQUEST={}): - return self.manage_editMembershipSourceForm(self, REQUEST) - - def listUserProperties(self, username): - if self.currentPropSource: - return self.currentPropSource.listUserProperties(username=username) - - def getUserProperty(self, username, key): - if self.currentPropSource: - return self.currentPropSource.getUserProperty(key=key, username=username) - - def reqattr(self, request, attr, default=None): - try: return request[attr] - except: return default - - def getAuthFailedMessage(self, code): - """ Return a code """ - if LoginRequiredMessages.has_key(code): - return LoginRequiredMessages[code] - return 'Login Required' - - # Called when we are deleted - def cache_deleteCache(self): - pp = string.join(self.getPhysicalPath(), '/') - XUFUserCache.deleteCache(pp) - - def cache_addToCache(self, username, password, user): - if not self.sessionLength: - return - # fix by emmanuel - if username == self._emergency_user.getUserName(): - return - # /fix - pp = string.join(self.getPhysicalPath(), '/') - x = XUFUserCache.getCache(pp) - if not x: - x = XUFUserCache.createCache(pp, self.sessionLength) - x.addToCache(username, password, user) - - def cache_getUser(self, username, password, checkpassword=1): - if not self.sessionLength: - return None - pp = string.join(self.getPhysicalPath(), '/') - x = XUFUserCache.getCache(pp) - if not x: - return None - u = x.getUser(self, username, password, checkpassword) - if u is not None: - u = u.__of__(self) - return u - - def cache_removeUser(self, username): - if not self.sessionLength: - return - pp = string.join(self.getPhysicalPath(), '/') - x = XUFUserCache.getCache(pp) - if x: - x.removeUser(username) - - def cache_getCacheStats(self): - pp = string.join(self.getPhysicalPath(), '/') - x = XUFUserCache.getCache(pp) - if not x: - x = XUFUserCache.createCache(pp, self.sessionLength) - if x: - return x.getCacheStats() - - def cache_getCurrentUsers(self): - pp = string.join(self.getPhysicalPath(), '/') - x = XUFUserCache.getCache(pp) - if x: - return x.getCurrentUsers(self) - - # negative cache functions - def xcache_deleteCache(self): - pp = string.join(self.getPhysicalPath(), '/') - XUFNotUserCache.deleteCache(pp) - - def xcache_addToCache(self, username): - if not self.notSessionLength: - return - pp = string.join(self.getPhysicalPath(), '/') - x = XUFNotUserCache.getCache(pp) - if not x: - x = XUFNotUserCache.createCache(pp, self.notSessionLength) - x.addToCache(username) - - def xcache_getUser(self, username): - if not self.notSessionLength: - return None - pp = string.join(self.getPhysicalPath(), '/') - x = XUFNotUserCache.getCache(pp) - if not x: - return None - return x.getUser(username) - - def xcache_removeUser(self, username): - #zLOG.LOG('exUserFolder', zLOG.PANIC, 'xcache_removeUser(%s)' % username) - if not self.notSessionLength: - return - pp = string.join(self.getPhysicalPath(), '/') - x = XUFNotUserCache.getCache(pp) - if x: - #zLOG.LOG('exUserFolder', zLOG.PANIC, 'xcache_removeUser removing') - x.removeUser(username) - - # Cookie Cache Functions - def cache_deleteCookieCache(self): - pp = string.join(self.getPhysicalPath(), '/') - XUFCookieCache.deleteCache(pp) - - def cache_addToCookieCache(self, username, password, key): - pp = string.join(self.getPhysicalPath(), '/') - c = XUFCookieCache.getCache(pp) - if not c: - c = XUFCookieCache.createCache(pp, 86400) - c.addToCache(username, password, key) - - def cache_getCookieCacheUser(self, key): - pp = string.join(self.getPhysicalPath(), '/') - c = XUFCookieCache.getCache(pp) - if not c: - return None - return c.getUser(key) - - def cache_removeCookieCacheUser(self, key): - pp = string.join(self.getPhysicalPath(), '/') - c = XUFCookieCache.getCache(pp) - if c: - c.removeUser(key) - - def manage_editUser(self, username, REQUEST={}): # UNUSED by ScoDoc - """ Edit a User """ - # username=self.reqattr(REQUEST,'username') - password=self.reqattr(REQUEST,'password') - password_confirm=self.reqattr(REQUEST,'password_confirm') - roles=self.reqattr(REQUEST,'roles', []) - groups=self.reqattr(REQUEST, 'groupnames', []) - - if not username: - return self.MessageDialog(self,REQUEST=REQUEST, - title ='Illegal value', - message='A username must be specified', - action ='manage_main') - - if (password or password_confirm) and (password != password_confirm): - return self.MessageDialog(self,REQUEST=REQUEST, - title ='Illegal value', - message='Password and confirmation do not match', - action ='manage_main') - - self._doChangeUser(username, password, roles, domains='', groups=groups, REQUEST=REQUEST) - - return self.MessageDialog(self,REQUEST=REQUEST, - title = 'User Updated', - message= 'User %s was updated.'%(username), - action = 'manage_main') - - - # Methode special pour ScoDoc: evite le code inutile dans notre contexte - # et accede a la BD via le curseur psycopg2 fourni - # (facilitera la separation de Zope) - def scodoc_editUser(self, cursor, username, password=None, roles=[]): - """Edit a ScoDoc user""" - roles = list(roles) - rolestring= ','.join(roles) - # Don't change passwords if it's null - if password: - secret=self.cryptPassword(username, password) - # Update just the password: - # self.sqlUpdateUserPassword(username=username, password=secret) - cursor.execute("UPDATE sco_users SET passwd=%(secret)s WHERE user_name=%(username)s", - { 'secret':secret, 'username': username } ) - - #self.sqlUpdateUser(username=username, roles=rolestring) - cursor.execute("UPDATE sco_users SET roles=%(rolestring)s WHERE user_name=%(username)s", - { 'rolestring':rolestring, 'username': username } ) - - if hasattr(self.currentAuthSource, '_v_lastUser'): - # Specific for pgAuthSource: - self.currentAuthSource._v_lastUser={} # clear pg user cache - - # We may have updated roles or passwords... flush the user... - self.cache_removeUser(username) - self.xcache_removeUser(username) - - # - # Membership helper - # - def goHome(self, REQUEST, RESPONSE): - """ Go to home directory """ - if self.currentMembershipSource: - self.currentMembershipSource.goHome(REQUEST, RESPONSE) - - - # - # Membership method of changing user properties - # - - def manage_changeProps(self, REQUEST): - """ Change Properties """ - if self.currentMembershipSource: - return self.currentMembershipSource.changeProperties(REQUEST) - else: - - return self.MessageDialog(self,REQUEST, - title = 'This is a test', - message= 'This was a test', - action = '..') - - - # - # Membership method of adding a new user. - # If everything goes well the membership plugin calls manage_addUser() - # - - def manage_signupUser(self, REQUEST): - """ Signup a new user """ - """ This is seperate so you can add users using the normal """ - """ interface w/o going through membership policy """ - - username=self.reqattr(REQUEST,'username') - roles=self.reqattr(REQUEST,'roles') - - if not username: - return self.MessageDialog(self,REQUEST=REQUEST, - title ='Illegal value', - message='A username must be specified', - action ='manage_main') - - if (self.getUser(username) or - (self._emergency_user and - username == self._emergency_user.getUserName())): - return self.MessageDialog(self,REQUEST=REQUEST, - title ='Illegal value', - message='A user with the specified name already exists', - action ='manage_main') - - if self.currentMembershipSource: - return self.currentMembershipSource.createUser(REQUEST) - - # - # Membership method of changing passwords - # - def manage_changePassword(self, REQUEST): - """ Change a password """ - if self.currentMembershipSource: - return self.currentMembershipSource.changePassword(REQUEST) - - # - # User says they can't remember their password - # - def manage_forgotPassword(self, REQUEST): - """ So something about forgetting your password """ - if self.currentMembershipSource: - return self.currentMembershipSource.forgotPassword(REQUEST) - - def __creatable_by_emergency_user__(self): return 1 - - def manage_addUser(self, REQUEST): - """ Add a New User """ - username=self.reqattr(REQUEST,'username') - password=self.reqattr(REQUEST,'password') - password_confirm=self.reqattr(REQUEST,'password_confirm') - roles=self.reqattr(REQUEST,'roles') - groups=self.reqattr(REQUEST, 'groupnames', []) - - if not username: - return self.MessageDialog(self,REQUEST=REQUEST, - title ='Illegal value', - message='A username must be specified', - action ='manage_main') - - if not password or not password_confirm: - return self.MessageDialog(self,REQUEST=REQUEST, - title ='Illegal value', - message='Password and confirmation must be specified', - action ='manage_main') - - if (self.getUser(username) or - (self._emergency_user and - username == self._emergency_user.getUserName())): - return self.MessageDialog(self,REQUEST=REQUEST, - title ='Illegal value', - message='A user with the specified name already exists', - action ='manage_main') - - if (password or password_confirm) and (password != password_confirm): - return self.MessageDialog(self,REQUEST=REQUEST, - title ='Illegal value', - message='Password and confirmation do not match', - action ='manage_main') - - self._doAddUser(username, password, roles, domains='', groups=groups, REQUEST=REQUEST) - # - # Explicitly check our contents, do not just acquire postUserCreate - # - if 'postUserCreate' in self.objectIds(): - self.postUserCreate(self, REQUEST) - - return self.MessageDialog(self,REQUEST=REQUEST, - title = 'User Created', - message= 'User %s was created.'%(username), - action = 'manage_main') - - def _doAddUser(self, name, password, roles, domains='', groups=(), **kw): - """ For programatically adding simple users """ - self.currentAuthSource.createUser(name, password, roles) - if self.currentPropSource: - # copy items not in kw from REQUEST - REQUEST = kw.get('REQUEST', self.REQUEST) - map(kw.setdefault, REQUEST.keys(), REQUEST.values()) - self.currentPropSource.createUser(name, kw) - - def _doChangeUser(self, name, password, roles, domains='', groups=(), **kw): - self.currentAuthSource.updateUser(name, password, roles) - if self.currentPropSource: - # copy items not in kw from REQUEST - REQUEST = kw.get('REQUEST', self.REQUEST) - map(kw.setdefault, REQUEST.keys(), REQUEST.values()) - self.currentPropSource.updateUser(name, kw) - # We may have updated roles or passwords... flush the user... - self.cache_removeUser(name) - self.xcache_removeUser(name) - - def _doDelUsers(self, names): - self.deleteUsers(names) - - def _createInitialUser(self): - if len(self.getUserNames()) <= 1: - info = readUserAccessFile('inituser') - if info: - name, password, domains, remote_user_mode = info - self._doAddUser(name, password, ('Manager',), domains) - - - def getUsers(self): - """Return a list of user objects or [] if no users exist""" - data=[] - try: - items=self.listUsers() - for people in items: - user=User({'name': people['username'], - 'password': people['password'], - 'roles': people['roles'], - 'domains': ''}, - self.currentPropSource, - self.cryptPassword, - self.currentAuthSource, - self.currentGroupSource) - data.append(user) - except: - import traceback - traceback.print_exc() - pass - - return data - - getUsers__roles__=('Anonymous','Authenticated') - - def getUser(self, name): - """Return the named user object or None if no such user exists""" - user = self.cache_getUser(name, '', 0) - #zLOG.LOG('exUserFolder.getUser', zLOG.PANIC, 'cache_getUser(%s)=%s' % (name,user)) - if user: - return user - try: - items=self.listOneUser(name) - #zLOG.LOG('exUserFolder.getUser', zLOG.PANIC, 'listOneUser=%s' % items) - except: - zLOG.LOG("exUserFolder", zLOG.ERROR, - "error trying to list user %s" % name, - '', - sys.exc_info()) - return None - - if not items: - return None - - for people in items: - user = User({'name': people['username'], - 'password':people['password'], - 'roles': people['roles'], - 'domains': ''}, - self.currentPropSource, - self.cryptPassword, - self.currentAuthSource, - self.currentGroupSource) - return user - return None - - def manage_userActions(self, submit=None, userids=None, REQUEST={}): - """ Do things to users """ - if submit==' Add ': - if hasattr(self.currentAuthSource,'manage_addUserForm'): - return self.currentAuthSource.manage_addUserForm(self, REQUEST) - else: - return self.manage_addUserForm(self, REQUEST) - if submit==' Delete ': - self.deleteUsers(userids) - return self.MessageDialog(self,REQUEST=REQUEST, - title ='Users Deleted', - message='Selected Users have been deleted', - action =REQUEST['URL1']+'/manage_main', - target ='manage_main') - - if REQUEST: - return self.manage_main(self,REQUEST) - return '' - - def identify(self, auth): - # Identify the username and password. This is where new modes should - # be called from, and if pluggable modes ever take shape, here ya go! - - if self.cookie_mode and not auth: - # The identify signature does not include the request, sadly. - # I think that's dumb. - request = self.REQUEST - response = request.RESPONSE - - if request.has_key('__ac_name') and request.has_key('__ac_password'): - return request['__ac_name'], request['__ac_password'] - elif request.has_key('__ac') and self.cookie_mode == 1: - return self.decodeBasicCookie(request, response) - elif request.has_key('__aca') and self.cookie_mode == 2: - return self.decodeAdvancedCookie(request, response) - - if auth and lower(auth[:6]) == 'basic ': - return tuple(split(decodestring(split(auth)[-1]), ':', 1)) - - return None, None - - def decodeUserCookie(self, request, response): - return self.identify('') - - def validate(self, request, auth='', roles=_noroles): - """ - Perform identification, authentication, and authorization. - """ - # Called at each web request - #zLOG.LOG('exUserFolder', zLOG.PANIC, 'validate') - v = request['PUBLISHED'] - a, c, n, v = self._getobcontext(v, request) - - name, password = self.identify(auth) # decode cookie, and raises LoginRequired if no ident info - # password is the cleartext passwd - # zLOG.LOG('exUserFolder', zLOG.DEBUG, 'identify returned %s, %s' % (name, password)) - - response = request.RESPONSE - if name is not None: - try: - xcached_user = self.xcache_getUser(name) - #zLOG.LOG('exUserFolder.validate', zLOG.PANIC, 'xcached_user=%s' % xcached_user) - if xcached_user: - #zLOG.LOG('exUserFolder.validate', zLOG.PANIC, 'returning None') - return None - except: - zLOG.LOG('exUserFolder', zLOG.ERROR, - "error while looking up '%s' on the xcache" % name, - '', - sys.exc_info()) - - user = self.authenticate(name, password, request) - #zLOG.LOG('exUserFolder.validate', zLOG.PANIC, 'user=%s' % user) - if user is None: - # If it's none, because there's no user by that name, - # don't raise a login, allow it to go higher... - # This kinda breaks for people putting in the wrong username - # when the Folder above uses a different auth method. - # But it doesn't lock Manager users out inside Zope. - # Perhaps this should be a tunable. - - # modified by Emmanuel - try: - lou = self.listOneUser(name) - except: - lou = None - if lou: - self.challenge(request, response, 'login_failed', auth) - return None - self.remember(name, password, request) - self.cache_addToCache(name, password, user) - emergency = self._emergency_user - if emergency and user is emergency: - if self._isTop(): - return emergency.__of__(self) - else: - return None - if self.authorize(user, a, c, n, v, roles): - return user.__of__(self) - if self._isTop() and self.authorize(self._nobody, a, c, n, v, roles): - return self._nobody.__of__(self) - self.challenge(request, response, 'unauthorized') - return None - else: - if self.sessionTracking and self.currentPropSource: - user = self.createAnonymousUser(request, response) - if self.authorize(user, a, c, n, v, roles): - return user.__of__(self) - if self.authorize(self._nobody, a, c, n, v, roles): - if self._isTop(): - return self._nobody.__of__(self) - else: - return None - else: - self.challenge(request, response, None, auth) - return None - - def authenticate(self, name, password, request): - #zLOG.LOG('exUserFolder.authenticate', zLOG.PANIC, '%s %s' % (name, password)) - emergency = self._emergency_user - if emergency and name == emergency.getUserName(): - return emergency - try: - user = self.cache_getUser(name, password) - #zLOG.LOG('exUserFolder.authenticate', zLOG.PANIC, 'cache_getUser=%s' % user) - if user: - return user - except SessionExpiredException: - if self.idleTimeout: - self.logout(request) - self.challenge(request, request.RESPONSE, 'session_expired') - return None - user = self.getUser(name) - #zLOG.LOG('exUserFolder.authenticate', zLOG.PANIC, 'getUser=%s' % user) - if user is not None: - if user.authenticate(self.currentAuthSource.listOneUser, - password, - request, - self.currentAuthSource.remoteAuthMethod): - return user - return None - - def challenge(self, request, response, reason_code='unauthorized', - auth=''): - # Give whatever mode we're in a chance to challenge the validation - # failure. We do this to preserve LoginRequired behavior. The - # other thing we could do is let the None propagate on up and patch - # the request's unauthorized method to - - if self.cookie_mode and not auth: - zLOG.LOG('exUserFolder', zLOG.DEBUG, 'raising LoginRequired for %s' % reason_code) - if reason_code == 'login_failed': - response.expireCookie('__ac', path='/') - response.expireCookie('__aca', path='/') - if reason_code: - request.set('authFailedCode', reason_code) - raise LoginRequired(self.docLogin(self, request)) - else: - zLOG.LOG('exUserFolder', zLOG.DEBUG, 'not raising LoginRequired for %s' % reason_code) - - def remember(self, name, password, request): - response = request.RESPONSE - if self.cookie_mode == 1: - self.setBasicCookie(name, password, request, response) - elif self.cookie_mode == 2: - self.setAdvancedCookie(name, password, request, response) - - if self.cookie_mode: - try: - del request.form['__ac_name'] - del request.form['__ac_password'] - except KeyError: - pass - - def makeRedirectPath(self): - REQUEST=self.REQUEST - if not REQUEST.has_key('destination'): - script=REQUEST['SCRIPT_NAME'] - pathinfo=REQUEST['PATH_INFO'] - redirectstring=script+pathinfo - if REQUEST.has_key('QUERY_STRING'): - querystring='?'+quote(REQUEST['QUERY_STRING']) - redirectstring=redirectstring+querystring - - REQUEST['destination']=redirectstring - - def redirectToLogin(self, REQUEST): - """ Allow methods to call from Web """ - script='' - pathinfo='' - querystring='' - redirectstring='' - authFailedCode='' - - if not REQUEST.has_key('destination'): - if self.currentMembershipSource: - redirectstring = self.currentMembershipSource.getLoginDestination(REQUEST) - else: - script=REQUEST['SCRIPT_NAME'] - pathinfo=REQUEST['PATH_INFO'] - redirectstring=script+pathinfo - if REQUEST.has_key('QUERY_STRING'): - querystring='?'+REQUEST['QUERY_STRING'] - redirectstring=redirectstring+querystring - - REQUEST['destination']=redirectstring - - - if REQUEST.has_key('authFailedCode'): - authFailedCode='&authFailedCode='+REQUEST['authFailedCode'] - - - - if self.currentMembershipSource and self.currentMembershipSource.loginPage: - try: - REQUEST.RESPONSE.redirect('%s/%s?destination=%s%s'%(self.currentMembershipSource.baseURL, self.currentMembershipSource.loginPage,REQUEST['destination'],authFailedCode)) - return - except: - pass - return self.docLogin(self,REQUEST) - - def decodeBasicCookie(self, request, response): - c=request['__ac'] - c=unquote(c) - try: - c=decodestring(c) - except: - response.expireCookie('__ac', path='/') - raise LoginRequired(self.docLogin(self, request)) - - name,password=tuple(split(c, ':', 1)) - return name, password - - def decodeAdvancedCookie(self, request, response): - c = '' - try: - c = request['__aca'] - c = unquote(c) - except: - response.expireCookie('__aca', path='/') - response.expireCookie('__ac', path='/') # Precaution - response.flush() - raise LoginRequired(self.docLogin(self, request)) - - u = self.cache_getCookieCacheUser(c) - if u: - return u - - response.expireCookie('__aca', path='/') - response.expireCookie('__ac', path='/') # Precaution - response.flush() - raise LoginRequired(self.docLogin(self, request)) - - def setBasicCookie(self, name, password, request, response): - token='%s:%s' % (name, password) - token=encodestring(token) - token=quote(token) - response.setCookie('__ac', token, path='/') - request['__ac']=token - - def setAdvancedCookie(self, name, password, request, response): - xufid = self._p_oid - hash = encodestring(sha.new('%s%s%f%f%s'%( - name, password, time(), random.random(), str(request))).digest()) - token=quote(hash) - response.setCookie('__aca', token, path='/') - response.flush() - request['__aca']=token - self.cache_addToCookieCache(name, password, hash) - - def setAnonCookie(self, name, request, resp): - token='%s:%s' % (name, '') - token=encodestring(token) - token=quote(token) - resp.setCookie('__ac', token, path='/') - request['__ac']=token - - def createAnonymousUser(self, request, resp): - aName=createTempName() - bogusREQUEST={} - bogusREQUEST['user_realname']='Guest User' - self.currentPropSource.createUser(aName, bogusREQUEST) - ob = AnonUser(aName, [], self.currentPropSource) - ob = ob.__of__(self) - self.cache_addToCache(aName, '', ob) - self.setAnonCookie(aName, request, resp) - return ob - - def manage_edit(self, cookie_mode, session_length, sessionTracking=None, - idleTimeout=0, not_session_length=0, - title=None, - REQUEST=None): - """Change properties""" - - self.cookie_mode=cookie_mode - self.sessionLength=session_length - self.notSessionLength=not_session_length - self.sessionTracking=sessionTracking - self.idleTimeout=idleTimeout - if title: - self.title = title - - if REQUEST: - return self.MessageDialog(self,REQUEST=REQUEST, - title ='exUserFolder Changed', - message='exUserFolder properties have been updated', - action =REQUEST['URL1']+'/manage_main', - target ='manage_main') - - def logout(self, REQUEST): - """Logout""" - try: - self.cache_removeUser(REQUEST['AUTHENTICATED_USER'].getUserName()) - except: - pass - - REQUEST['RESPONSE'].expireCookie('__ac', path='/') - REQUEST.cookies['__ac']='' - try: - acc = REQUEST['__aca'] - self.cache_removeCookieCacheUser(acc) - REQUEST.cookies['__aca']='' - except: - pass - REQUEST['RESPONSE'].expireCookie('__aca', path='/') - - - - return self.docLogout(self, REQUEST) - - # - # Methods to be supplied by Auth Source - # - def deleteUsers(self, userids): - self.currentAuthSource.deleteUsers(userids) - - # Comment out to use Andreas' pgSchema - if self.currentPropSource: - self.currentPropSource.deleteUsers(userids) - - if self.currentGroupSource: - self.currentGroupSource.deleteUsers(userids) - - - def listUsers(self): - return self.currentAuthSource.listUsers() - - def user_names(self): - return self.currentAuthSource.listUserNames() - - def getUserNames(self): - return self.currentAuthSource.listUserNames() - - def listOneUser(self,username): - return self.currentAuthSource.listOneUser(username) - - def cryptPassword(self, username, password): - if hasattr(aq_base(self.currentAuthSource), 'cryptPassword'): - return self.currentAuthSource.cryptPassword(username, password) - - if hasattr(self, 'cryptoId'): - return self.cryptoSources[self.cryptoId].plugin(self, username, password) - return self.cryptoSources['Crypt'].plugin(self, username, password) - - def PropertyEditor(self): - """ """ - if self.REQUEST.has_key(self.REQUEST['propName']): - return PropertyEditor.EditMethods[self.REQUEST['propType']](self.REQUEST['propName'], self.REQUEST[self.REQUEST['propName']]) - return PropertyEditor.EditMethods[self.REQUEST['propType']](self.REQUEST['propName'], None) - - def PropertyView(self): - """ """ - if self.REQUEST.has_key(self.REQUEST['propName']): - return PropertyEditor.ViewMethods[self.REQUEST['propType']](self.REQUEST['propName'], self.REQUEST[self.REQUEST['propName']]) - return PropertyEditor.ViewMethods[self.REQUEST['propType']](self.REQUEST['propName'], None) - - def manage_addUserProperty(self, username, propName, propValue, REQUEST): - """ add a new property """ - self.currentPropSource.setUserProperty(propName, username, propValue) - if hasattr(self.currentAuthSource,'manage_editUserForm'): - return self.currentAuthSource.manage_editUserForm(self, REQUEST) - else: - return self.manage_editUserForm(self,REQUEST) - - def getUserCacheStats(self): - """ Stats """ - if self.sessionLength: - if self.cache_getCacheStats()['attempts']: - return self.cache_getCacheStats() - return None - - def getUserCacheUsers(self): - """ Current Users """ - if self.sessionLength: - return self.cache_getCurrentUsers() - return None - - def userFolderAddGroup(self, groupname, title='', **kw): - """Creates a group""" - if self.currentGroupSource: - apply(self.currentGroupSource.addGroup, (groupname, title), kw) - - def userFolderDelGroups(self, groupnames): - """Deletes groups""" - if self.currentGroupSource: - for groupname in groupnames: - self.currentGroupSource.delGroup(groupname) - - def getGroupNames(self): - """Returns a list of group names""" - if self.currentGroupSource: - return self.currentGroupSource.listGroups() - else: - return [] - - - def getGroupById(self, groupname, default=_marker): - """Returns the given group""" - if self.currentGroupSource: - group = self.currentGroupSource.getGroup(groupname, default) - if group: - return group.__of__(self) - else: - return None - - def setUsersOfGroup(self, usernames, groupname): - """Sets the users of the group""" - if self.currentGroupSource: - return self.currentGroupSource.setUsersOfGroup(usernames, groupname) - - def addUsersToGroup(self, usernames, groupname): - """Adds users to a group""" - if self.currentGroupSource: - return self.currentGroupSource.addUsersToGroup(usernames, groupname) - - def delUsersFromGroup(self, usernames, groupname): - """Deletes users from a group""" - if self.currentGroupSource: - return self.currentGroupSource.delUsersFromGroup(usernames, groupname) - - def setGroupsOfUser(self, groupnames, username): - """Sets the groups of a user""" - if self.currentGroupSource: - return self.currentGroupSource.setGroupsOfUser(groupnames, username) - - def addGroupsOfUser(self, groupnames, username): - """Add groups to a user""" - if self.currentGroupSource: - return self.currentGroupSource.addGroupsToUser(groupnames, username) - - def delGroupsOfUser(self, groupnames, username): - """Deletes groups from a user""" - if self.currentGroupSource: - return self.currentGroupSource.delGroupsFromUser(groupnames, username) - - # We lie. - def hasUsers(self): - return 1 - - -def doAuthSourceForm(self,authId): - """ la de da """ - return exUserFolder.authSources[authId].manage_addForm - -def doPropSourceForm(self,propId): - """ la de da """ - return exUserFolder.propSources[propId].manage_addForm - -def doMembershipSourceForm(self, memberId): - """ doot de doo """ - return exUserFolder.membershipSources[memberId].manage_addForm - -#def doGroupSourceForm(self,groupId): -# """ la de da """ -# return exUserFolder.groupSources[groupId].manage_addForm - -def getAuthSources(self): - """ Hrm I need a docstring """ - l=[] - for o in exUserFolder.authSources.keys(): - l.append( - exUserFolder.authSources[o] - ) - return l - -def getPropSources(self): - """ Hrm I need a docstring """ - l=[] - for o in exUserFolder.propSources.keys(): - l.append( - exUserFolder.propSources[o] - ) - return l - -def getMembershipSources(self): - """ Hrm I need a docstring """ - l=[] - for o in exUserFolder.membershipSources.keys(): - l.append( - exUserFolder.membershipSources[o] - ) - return l - -def getGroupSources(self): - """ Hrm I need a docstring """ - return [] # UNUSED by ScoDoc: empty - -def getCryptoSources(self): - """ Doc String """ - l = [] - for o in exUserFolder.cryptoSources.keys(): - l.append( - exUserFolder.cryptoSources[o] - ) - return l - -def MailHostIDs(self): - """Find SQL database connections in the current folder and above - - This function return a list of ids. - """ - return [] # UNUSED BY SCODOC - -from types import ListType, IntType, LongType, FloatType, NoneType, DictType, StringType - -def getVariableType(self, o): - - if type(o) == ListType: - return 'List' - if type(o) == IntType: - return 'Int' - if type(o) == LongType: - return 'Long' - if type(o) == FloatType: - return 'Float' - if type(o) == NoneType: - return 'None' - if type(o) == DictType: - return 'Dict' - if type(o) == StringType: - return 'String' - return 'Unknown or Restricted' - -_postUserCreate=''' - -Replace this method with whatever you want to do -when a user is created, you can use a Python Script, -or External Method, or keep it as a DTML Method if you -want to - -''' diff --git a/ZopeProducts/exUserFolder/exUserFolderPlugin.gif b/ZopeProducts/exUserFolder/exUserFolderPlugin.gif deleted file mode 100644 index dd8e2c9f..00000000 Binary files a/ZopeProducts/exUserFolder/exUserFolderPlugin.gif and /dev/null differ diff --git a/ZopeProducts/exUserFolder/nullPlugin/__init__.py b/ZopeProducts/exUserFolder/nullPlugin/__init__.py deleted file mode 100644 index b0d9e576..00000000 --- a/ZopeProducts/exUserFolder/nullPlugin/__init__.py +++ /dev/null @@ -1,2 +0,0 @@ -# $Id: __init__.py,v 1.4 2004/11/10 14:15:57 akm Exp $ -import nullPlugin diff --git a/ZopeProducts/exUserFolder/nullPlugin/nullPlugin.py b/ZopeProducts/exUserFolder/nullPlugin/nullPlugin.py deleted file mode 100644 index dd9cd526..00000000 --- a/ZopeProducts/exUserFolder/nullPlugin/nullPlugin.py +++ /dev/null @@ -1,39 +0,0 @@ -# -# Extensible User Folder -# -# Null Plugin for exUserFolder -# -# (C) Copyright 2000,2001 The Internet (Aust) Pty Ltd -# ACN: 082 081 472 ABN: 83 082 081 472 -# All Rights Reserved -# -# THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND -# ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE -# IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE -# ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE -# FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL -# DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS -# OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) -# HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT -# LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY -# OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF -# SUCH DAMAGE. -# -# Author: Andrew Milton -# $Id: nullPlugin.py,v 1.5 2004/11/10 14:15:57 akm Exp $ -import string,Acquisition - -from Globals import HTMLFile, INSTANCE_HOME - -from OFS.Folder import Folder - -from Products.exUserFolder.exUserFolder import exUserFolder -from Products.exUserFolder.Plugins import PluginRegister - -class NullPlugin(Folder): - - def __init__(self): - pass - - def postInitialisation(self, REQUEST): - pass diff --git a/ZopeProducts/exUserFolder/version.txt b/ZopeProducts/exUserFolder/version.txt deleted file mode 100644 index af0accc3..00000000 --- a/ZopeProducts/exUserFolder/version.txt +++ /dev/null @@ -1 +0,0 @@ -exUserFolder-0-50-1