aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authormsapiro <>2005-12-03 01:08:58 +0000
committermsapiro <>2005-12-03 01:08:58 +0000
commitd77d0dfed39748444d772bd1c1aacbdb4fbfd20a (patch)
tree21297fc61321b4d6fa51d0650da887fe856cd454
parent6dd2b7fdf06cb3a9e6bc461efe3ab17e73dbe939 (diff)
downloadmailman2-d77d0dfed39748444d772bd1c1aacbdb4fbfd20a.tar.gz
mailman2-d77d0dfed39748444d772bd1c1aacbdb4fbfd20a.tar.xz
mailman2-d77d0dfed39748444d772bd1c1aacbdb4fbfd20a.zip
Improving banned subscription logic to cover all invites, subscribes, address changes and confirmations of same.
-rw-r--r--Mailman/Cgi/admin.py5
-rw-r--r--Mailman/Cgi/admindb.py9
-rw-r--r--Mailman/Cgi/confirm.py13
-rw-r--r--Mailman/Cgi/options.py5
-rw-r--r--Mailman/MailList.py82
5 files changed, 88 insertions, 26 deletions
diff --git a/Mailman/Cgi/admin.py b/Mailman/Cgi/admin.py
index eb63e008..b75ff2df 100644
--- a/Mailman/Cgi/admin.py
+++ b/Mailman/Cgi/admin.py
@@ -1,4 +1,4 @@
-# Copyright (C) 1998-2004 by the Free Software Foundation, Inc.
+# Copyright (C) 1998-2005 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
@@ -1345,6 +1345,9 @@ def change_options(mlist, category, subcat, cgidata, doc):
except Errors.MMHostileAddress:
subscribe_errors.append(
(entry, _('Hostile address (illegal characters)')))
+ except Errors.MembershipIsBanned, pattern:
+ subscribe_errors.append(
+ (entry, _('Banned address (matched %(pattern)s)')))
else:
member = Utils.uncanonstr(formataddr((fullname, address)))
subscribe_success.append(Utils.websafe(member))
diff --git a/Mailman/Cgi/admindb.py b/Mailman/Cgi/admindb.py
index 1dd0e28a..3f421cfe 100644
--- a/Mailman/Cgi/admindb.py
+++ b/Mailman/Cgi/admindb.py
@@ -1,4 +1,4 @@
-# Copyright (C) 1998-2004 by the Free Software Foundation, Inc.
+# Copyright (C) 1998-2005 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
@@ -745,6 +745,7 @@ def process_form(mlist, doc, cgidata):
if sender not in mlist.ban_list:
mlist.ban_list.append(sender)
# Now, do message specific actions
+ banaddrs = []
erroraddrs = []
for k in cgidata.keys():
formv = cgidata[k]
@@ -794,8 +795,14 @@ def process_form(mlist, doc, cgidata):
continue
except Errors.MMAlreadyAMember, v:
erroraddrs.append(v)
+ except Errors.MembershipIsBanned, pattern:
+ sender = mlist.GetRecord(request_id)[1]
+ banaddrs.append((sender, pattern))
# save the list and print the results
doc.AddItem(Header(2, _('Database Updated...')))
if erroraddrs:
for addr in erroraddrs:
doc.AddItem(`addr` + _(' is already a member') + '<br>')
+ if banaddrs:
+ for addr, patt in banaddrs:
+ doc.AddItem(_('%(addr)s is banned (matched: %(patt)s)') + '<br>')
diff --git a/Mailman/Cgi/confirm.py b/Mailman/Cgi/confirm.py
index d2cf0cce..6238e72a 100644
--- a/Mailman/Cgi/confirm.py
+++ b/Mailman/Cgi/confirm.py
@@ -1,4 +1,4 @@
-# Copyright (C) 2001-2004 by the Free Software Foundation, Inc.
+# Copyright (C) 2001-2005 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
@@ -370,6 +370,11 @@ def subscription_confirm(mlist, doc, cookie, cgidata):
address that has already been unsubscribed.'''))
except Errors.MMAlreadyAMember:
doc.addError(_("You are already a member of this mailing list!"))
+ except Errors.MembershipIsBanned:
+ owneraddr = mlist.GetOwnerEmail()
+ doc.addError(_("""You are currently banned from subscribing to
+ this list. If you think this restriction is erroneous, please
+ contact the list owners at %(owneraddr)s."""))
except Errors.HostileSubscriptionError:
doc.addError(_("""\
You were not invited to this mailing list. The invitation has
@@ -517,6 +522,12 @@ def addrchange_confirm(mlist, doc, cookie):
bad_confirmation(doc, _('''Invalid confirmation string. It is
possible that you are attempting to confirm a request for an
address that has already been unsubscribed.'''))
+ except Errors.MembershipIsBanned:
+ owneraddr = mlist.GetOwnerEmail()
+ realname = mlist.real_name
+ doc.addError(_("""%(newaddr)s is banned from subscribing to the
+ %(realname)s list. If you think this restriction is erroneous,
+ please contact the list owners at %(owneraddr)s."""))
else:
# The response
listname = mlist.real_name
diff --git a/Mailman/Cgi/options.py b/Mailman/Cgi/options.py
index ed40e828..eb7adb67 100644
--- a/Mailman/Cgi/options.py
+++ b/Mailman/Cgi/options.py
@@ -399,6 +399,11 @@ address. Upon confirmation, any other mailing list containing the address
msg = _('Illegal email address provided')
except Errors.MMAlreadyAMember:
msg = _('%(newaddr)s is already a member of the list.')
+ except Errors.MembershipIsBanned:
+ owneraddr = mlist.GetOwnerEmail()
+ msg = _("""%(newaddr)s is banned from this list. If you
+ think this restriction is erroneous, please contact
+ the list owners at %(owneraddr)s.""")
if set_membername:
mlist.Lock()
diff --git a/Mailman/MailList.py b/Mailman/MailList.py
index 0a52567d..cf07c842 100644
--- a/Mailman/MailList.py
+++ b/Mailman/MailList.py
@@ -764,6 +764,10 @@ class MailList(HTMLFormatter, Deliverer, ListAdmin,
"""
invitee = userdesc.address
Utils.ValidateEmail(invitee)
+ # check for banned address
+ pattern = self.GetBannedPattern(invitee)
+ if pattern:
+ raise Errors.MembershipIsBanned, pattern
# Hack alert! Squirrel away a flag that only invitations have, so
# that we can do something slightly different when an invitation
# subscription is confirmed. In those cases, we don't need further
@@ -837,29 +841,13 @@ class MailList(HTMLFormatter, Deliverer, ListAdmin,
if email.lower() == self.GetListEmail().lower():
# Trying to subscribe the list to itself!
raise Errors.MMBadEmailError
-
+ realname = self.real_name
# Is the subscribing address banned from this list?
- ban = 0
- for pattern in self.ban_list:
- if pattern.startswith('^'):
- # This is a regular expression match
- try:
- if re.search(pattern, email, re.IGNORECASE):
- ban = 1
- break
- except re.error:
- # BAW: we should probably remove this pattern
- pass
- else:
- # Do the comparison case insensitively
- if pattern.lower() == email.lower():
- ban = 1
- break
- if ban:
- syslog('vette', 'banned subscription: %s (matched: %s)',
- email, pattern)
+ pattern = self.GetBannedPattern(email)
+ if pattern:
+ syslog('vette', '%s banned subscription: %s (matched: %s)',
+ realname, email, pattern)
raise Errors.MembershipIsBanned, pattern
-
# Sanity check the digest flag
if digest and not self.digestable:
raise Errors.MMCantDigestError
@@ -889,7 +877,6 @@ class MailList(HTMLFormatter, Deliverer, ListAdmin,
remote = _(' from %(remote)s')
recipient = self.GetMemberAdminEmail(email)
- realname = self.real_name
confirmurl = '%s/%s' % (self.GetScriptURL('confirm', absolute=1),
cookie)
text = Utils.maketext(
@@ -961,6 +948,11 @@ class MailList(HTMLFormatter, Deliverer, ListAdmin,
Utils.ValidateEmail(email)
if self.isMember(email):
raise Errors.MMAlreadyAMember, email
+ # Check for banned address here too for admin mass subscribes
+ # and confirmations.
+ pattern = self.GetBannedPattern(email)
+ if pattern:
+ raise Errors.MembershipIsBanned, pattern
# Do the actual addition
self.addNewMember(email, realname=name, digest=digest,
password=password, language=lang)
@@ -1073,12 +1065,21 @@ class MailList(HTMLFormatter, Deliverer, ListAdmin,
raise Errors.MMAlreadyAMember
if newaddr == self.GetListEmail().lower():
raise Errors.MMBadEmailError
+ realname = self.real_name
+ # Don't allow changing to a banned address. MAS: maybe we should
+ # unsubscribe the oldaddr too just for trying, but that's probably
+ # too harsh.
+ pattern = self.GetBannedPattern(newaddr)
+ if pattern:
+ syslog('vette',
+ '%s banned address change: %s -> %s (matched: %s)',
+ realname, oldaddr, newaddr, pattern)
+ raise Errors.MembershipIsBanned, pattern
# Pend the subscription change
cookie = self.pend_new(Pending.CHANGE_OF_ADDRESS,
oldaddr, newaddr, globally)
confirmurl = '%s/%s' % (self.GetScriptURL('confirm', absolute=1),
cookie)
- realname = self.real_name
lang = self.getMemberLanguage(oldaddr)
text = Utils.maketext(
'verify.txt',
@@ -1107,6 +1108,13 @@ class MailList(HTMLFormatter, Deliverer, ListAdmin,
msg.send(self)
def ApprovedChangeMemberAddress(self, oldaddr, newaddr, globally):
+ # Check here for banned address in case address was banned after
+ # confirmation was mailed. MAS: If it's global change should we just
+ # skip this list and proceed to the others? For now we'll throw the
+ # exception.
+ pattern = self.GetBannedPattern(newaddr)
+ if pattern:
+ raise Errors.MembershipIsBanned, pattern
# It's possible they were a member of this list, but choose to change
# their membership globally. In that case, we simply remove the old
# address.
@@ -1127,6 +1135,9 @@ class MailList(HTMLFormatter, Deliverer, ListAdmin,
continue
if not mlist.isMember(oldaddr):
continue
+ # If new address is banned from this list, just skip it.
+ if mlist.GetBannedPattern(newaddr):
+ continue
mlist.Lock()
try:
# Same logic as above, re newaddr is already a member
@@ -1454,6 +1465,31 @@ bad regexp in bounce_matching_header line: %s
self.hold_and_cmd_autoresponses[sender] = (today, count+1)
return 1
+ def GetBannedPattern(self, email):
+ """Returns matched entry in ban_list if email matches.
+ Otherwise returns None.
+ """
+ ban = 0
+ for pattern in self.ban_list:
+ if pattern.startswith('^'):
+ # This is a regular expression match
+ try:
+ if re.search(pattern, email, re.IGNORECASE):
+ ban = 1
+ break
+ except re.error:
+ # BAW: we should probably remove this pattern
+ pass
+ else:
+ # Do the comparison case insensitively
+ if pattern.lower() == email.lower():
+ ban = 1
+ break
+ if ban:
+ return pattern
+ else:
+ return None
+
#