Add per list member roster visibility option
[mailman.git] / src / mailman / rest / bans.py
blob137f9b1754f0eab6376852ee5bc9c8913a500c89
1 # Copyright (C) 2016-2019 by the Free Software Foundation, Inc.
3 # This file is part of GNU Mailman.
5 # GNU Mailman is free software: you can redistribute it and/or modify it under
6 # the terms of the GNU General Public License as published by the Free
7 # Software Foundation, either version 3 of the License, or (at your option)
8 # any later version.
10 # GNU Mailman is distributed in the hope that it will be useful, but WITHOUT
11 # ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
12 # FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for
13 # more details.
15 # You should have received a copy of the GNU General Public License along with
16 # GNU Mailman. If not, see <http://www.gnu.org/licenses/>.
18 """REST for banned emails."""
20 from mailman.interfaces.bans import IBanManager
21 from mailman.rest.helpers import (
22 CollectionMixin, bad_request, child, created, etag, no_content, not_found,
23 okay)
24 from mailman.rest.validator import Validator
25 from public import public
28 class _BannedBase:
29 """Common base class."""
31 def __init__(self, mlist):
32 self._mlist = mlist
33 self.ban_manager = IBanManager(self._mlist)
35 def _location(self, email):
36 if self._mlist is None:
37 base_location = ''
38 else:
39 base_location = 'lists/{}/'.format(self._mlist.list_id)
40 return self.api.path_to('{}bans/{}'.format(base_location, email))
43 @public
44 class BannedEmail(_BannedBase):
45 """A banned email."""
47 def __init__(self, mlist, email):
48 super().__init__(mlist)
49 self._email = email
51 def on_get(self, request, response):
52 """Get a banned email."""
53 if self.ban_manager.is_banned(self._email):
54 resource = dict(
55 email=self._email,
56 self_link=self._location(self._email),
58 if self._mlist is not None:
59 resource['list_id'] = self._mlist.list_id
60 okay(response, etag(resource))
61 else:
62 not_found(response, 'Email is not banned: {}'.format(self._email))
64 def on_delete(self, request, response):
65 """Remove an email from the ban list."""
66 if self.ban_manager.is_banned(self._email):
67 self.ban_manager.unban(self._email)
68 no_content(response)
69 else:
70 not_found(response, 'Email is not banned: {}'.format(self._email))
73 @public
74 class BannedEmails(_BannedBase, CollectionMixin):
75 """The list of all banned emails."""
77 def _resource_as_dict(self, ban):
78 """See `CollectionMixin`."""
79 resource = dict(
80 email=ban.email,
81 self_link=self._location(ban.email),
83 if ban.list_id is not None:
84 resource['list_id'] = ban.list_id
85 return resource
87 def _get_collection(self, request):
88 """See `CollectionMixin`."""
89 return self.ban_manager.bans
91 def on_get(self, request, response):
92 """/bans"""
93 resource = self._make_collection(request)
94 okay(response, etag(resource))
96 def on_post(self, request, response):
97 """Ban some email from subscribing."""
98 validator = Validator(email=str)
99 try:
100 email = validator(request)['email']
101 except ValueError as error:
102 bad_request(response, str(error))
103 return
104 if self.ban_manager.is_banned(email):
105 bad_request(response, b'Address is already banned')
106 else:
107 self.ban_manager.ban(email)
108 created(response, self._location(email))
110 @child(r'^(?P<email>[^/]+)')
111 def email(self, context, segments, **kw):
112 return BannedEmail(self._mlist, kw['email'])