------------------------------------------------------------
revno: 1297
committer: Mark Sapiro <msap...@value.net>
branch nick: 2.1
timestamp: Mon 2011-04-25 16:52:35 -0700
message:
  A new list poster password has been implemented.  This password may only
  be used in Approved: or X-Approved: headers for pre-approving posts.
  Using this password for that purpose precludes compromise of a more
  valuable password sent in plain text email.  Bug #770581.
modified:
  Mailman/Cgi/admin.py
  Mailman/Defaults.py.in
  Mailman/Handlers/Approve.py
  Mailman/SecurityManager.py
  Mailman/Version.py
  Mailman/versions.py
  NEWS


--
lp:mailman/2.1
https://code.launchpad.net/~mailman-coders/mailman/2.1

Your team Mailman Checkins is subscribed to branch lp:mailman/2.1.
To unsubscribe from this branch go to 
https://code.launchpad.net/~mailman-coders/mailman/2.1/+edit-subscription
=== modified file 'Mailman/Cgi/admin.py'
--- Mailman/Cgi/admin.py	2011-04-24 00:49:15 +0000
+++ Mailman/Cgi/admin.py	2011-04-25 23:52:35 +0000
@@ -1258,6 +1258,22 @@
                    PasswordBox('confirmmodpw', size=20)])
     # Add these tables to the overall password table
     table.AddRow([atable, mtable])
+    table.AddRow([_("""\
+In addition to the above passwords you may specify a password for
+pre-approving posts to the list. Either of the above two passwords can
+be used in an Approved: header or first body line pseudo-header to
+pre-approve a post that would otherwise be held for moderation. In
+addition, the password below, if set, can be used for that purpose and
+no other.""")])
+    table.AddCellInfo(table.GetCurrentRowIndex(), 0, colspan=2)
+    # Set up the post password table
+    ptable = Table(border=0, cellspacing=3, cellpadding=4,
+                   bgcolor=mm_cfg.WEB_ADMINPW_COLOR)
+    ptable.AddRow([Label(_('Enter new poster password:')),
+                   PasswordBox('newpostpw', size=20)])
+    ptable.AddRow([Label(_('Confirm poster password:')),
+                   PasswordBox('confirmpostpw', size=20)])
+    table.AddRow([ptable])
     return table
 
 
@@ -1288,6 +1304,17 @@
             # password doesn't get you into these pages.
         else:
             doc.addError(_('Moderator passwords did not match'))
+    # Handle changes to the list poster password.  Do this before checking
+    # the new admin password, since the latter will force a reauthentication.
+    new = cgidata.getvalue('newpostpw', '').strip()
+    confirm = cgidata.getvalue('confirmpostpw', '').strip()
+    if new or confirm:
+        if new == confirm:
+            mlist.post_password = sha_new(new).hexdigest()
+            # No re-authentication necessary because the poster's
+            # password doesn't get you into these pages.
+        else:
+            doc.addError(_('Poster passwords did not match'))
     # Handle changes to the list administrator password
     new = cgidata.getvalue('newpw', '').strip()
     confirm = cgidata.getvalue('confirmpw', '').strip()

=== modified file 'Mailman/Defaults.py.in'
--- Mailman/Defaults.py.in	2011-04-25 22:40:16 +0000
+++ Mailman/Defaults.py.in	2011-04-25 23:52:35 +0000
@@ -1375,6 +1375,11 @@
 #   option settings
 # - List creator, someone who can create and delete lists, but cannot
 #   (necessarily) configure the list.
+# - List poster, someone who can pre-approve her/his own posts to the list by
+#   including an Approved: or X-Approved: header or first body line pseudo-
+#   header containing the poster password. The list admin and moderator
+#   passwords can also be used for this purpose, but the poster password can
+#   only be used for this and nothing else.
 # - List moderator, someone who can tend to pending requests such as
 #   subscription requests, or held messages
 # - List administrator, someone who has total control over a list, can
@@ -1389,7 +1394,8 @@
 AuthCreator = 2       # List Creator / Destroyer
 AuthListAdmin = 3     # List Administrator (total control over list)
 AuthListModerator = 4 # List Moderator (can only handle held requests)
-AuthSiteAdmin = 5     # Site Administrator (total control over everything)
+AuthListPoster = 5    # List poster (Approved: <pw> header in posts only)
+AuthSiteAdmin = 6     # Site Administrator (total control over everything)
 
 # Useful directories
 LIST_DATA_DIR   = os.path.join(VAR_PREFIX, 'lists')

=== modified file 'Mailman/Handlers/Approve.py'
--- Mailman/Handlers/Approve.py	2010-05-10 21:11:45 +0000
+++ Mailman/Handlers/Approve.py	2011-04-25 23:52:35 +0000
@@ -1,4 +1,4 @@
-# Copyright (C) 1998-2010 by the Free Software Foundation, Inc.
+# Copyright (C) 1998-2011 by the Free Software Foundation, Inc.
 #
 # This program is free software; you can redistribute it and/or
 # modify it under the terms of the GNU General Public License
@@ -117,7 +117,8 @@
                     lines = part.get_payload(decode=True)
                     if re.search(pattern, lines):
                         reset_payload(part, re.sub(pattern, '', lines))
-    if passwd is not missing and mlist.Authenticate((mm_cfg.AuthListModerator,
+    if passwd is not missing and mlist.Authenticate((mm_cfg.AuthListPoster,
+                                                     mm_cfg.AuthListModerator,
                                                      mm_cfg.AuthListAdmin),
                                                     passwd):
         # BAW: should we definitely deny if the password exists but does not

=== modified file 'Mailman/SecurityManager.py'
--- Mailman/SecurityManager.py	2011-04-25 22:40:16 +0000
+++ Mailman/SecurityManager.py	2011-04-25 23:52:35 +0000
@@ -83,6 +83,7 @@
         # self.password is really a SecurityManager attribute, but it's set in
         # MailList.InitVars().
         self.mod_password = None
+        self.post_password = None
         # Non configurable
         self.passwords = {}
 
@@ -106,6 +107,9 @@
             secret = self.getMemberPassword(user)
             userdata = urllib.quote(Utils.ObscureEmail(user), safe='')
             key += 'user+%s' % userdata
+        elif authcontext == mm_cfg.AuthListPoster:
+            secret = self.post_password
+            key += 'poster'
         elif authcontext == mm_cfg.AuthListModerator:
             secret = self.mod_password
             key += 'moderator'
@@ -200,6 +204,11 @@
                 key, secret = self.AuthContextInfo(ac)
                 if secret and sha_new(response).hexdigest() == secret:
                     return ac
+            elif ac == mm_cfg.AuthListPoster:
+                # The list poster password must be sha'd
+                key, secret = self.AuthContextInfo(ac)
+                if secret and sha_new(response).hexdigest() == secret:
+                    return ac
             elif ac == mm_cfg.AuthUser:
                 if user is not None:
                     try:

=== modified file 'Mailman/Version.py'
--- Mailman/Version.py	2010-09-20 18:06:58 +0000
+++ Mailman/Version.py	2011-04-25 23:52:35 +0000
@@ -1,4 +1,4 @@
-# Copyright (C) 1998-2010 by the Free Software Foundation, Inc.
+# Copyright (C) 1998-2011 by the Free Software Foundation, Inc.
 #
 # This program is free software; you can redistribute it and/or
 # modify it under the terms of the GNU General Public License
@@ -37,7 +37,7 @@
                (REL_LEVEL << 4)  | (REL_SERIAL << 0))
 
 # config.pck schema version number
-DATA_FILE_VERSION = 98
+DATA_FILE_VERSION = 99
 
 # qfile/*.db schema version number
 QFILE_SCHEMA_VERSION = 3

=== modified file 'Mailman/versions.py'
--- Mailman/versions.py	2010-07-03 20:59:22 +0000
+++ Mailman/versions.py	2011-04-25 23:52:35 +0000
@@ -1,4 +1,4 @@
-# Copyright (C) 1998-2010 by the Free Software Foundation, Inc.
+# Copyright (C) 1998-2011 by the Free Software Foundation, Inc.
 #
 # This program is free software; you can redistribute it and/or
 # modify it under the terms of the GNU General Public License
@@ -339,6 +339,7 @@
                         mm_cfg.DEFAULT_DIGEST_VOLUME_FREQUENCY)
     add_only_if_missing('digest_last_sent_at', 0)
     add_only_if_missing('mod_password', None)
+    add_only_if_missing('post_password', None)
     add_only_if_missing('moderator', [])
     add_only_if_missing('topics', [])
     add_only_if_missing('topics_enabled', 0)

=== modified file 'NEWS'
--- NEWS	2011-04-25 23:26:13 +0000
+++ NEWS	2011-04-25 23:52:35 +0000
@@ -12,6 +12,11 @@
 
   New Features
 
+    - A new list poster password has been implemented.  This password may only
+      be used in Approved: or X-Approved: headers for pre-approving posts.
+      Using this password for that purpose precludes compromise of a more
+      valuable password sent in plain text email.  Bug #770581.
+
     - A new mm_cfg.py setting AUTHENTICATION_COOKIE_LIFETIME has been added.
       If this is set to a non-zero value, web authentication cookies will
       expire that many seconds following their last use.  Its default value is

_______________________________________________
Mailman-checkins mailing list
Mailman-checkins@python.org
Unsubscribe: 
http://mail.python.org/mailman/options/mailman-checkins/archive%40jab.org

Reply via email to