Revert the addition of the mailinglist.style_name column, as well as the
[mailman.git] / src / mailman / interfaces / mailinglist.py
blob8a4436a21e5aaa9af6a1d9d7b6be248cd54a46c5
1 # Copyright (C) 2007-2012 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 """Interface for a mailing list."""
20 from __future__ import absolute_import, print_function, unicode_literals
22 __metaclass__ = type
23 __all__ = [
24 'IAcceptableAlias',
25 'IAcceptableAliasSet',
26 'IMailingList',
27 'Personalization',
28 'ReplyToMunging',
32 from flufl.enum import Enum
33 from zope.interface import Interface, Attribute
35 from mailman.interfaces.member import MemberRole
39 class Personalization(Enum):
40 none = 0
41 # Everyone gets a unique copy of the message, and there are a few more
42 # substitution variables, but no headers are modified.
43 individual = 1
44 # All of the 'individual' personalization plus recipient header
45 # modification.
46 full = 2
49 class ReplyToMunging(Enum):
50 # The Reply-To header is passed through untouched
51 no_munging = 0
52 # The mailing list's posting address is appended to the Reply-To header
53 point_to_list = 1
54 # An explicit Reply-To header is added
55 explicit_header = 2
59 class IMailingList(Interface):
60 """A mailing list."""
62 # List identity
64 created_at = Attribute(
65 """The date and time that the mailing list was created.""")
67 list_name = Attribute("""\
68 The read-only short name of the mailing list. Note that where a
69 Mailman installation supports multiple domains, this short name may
70 not be unique. Use the fqdn_listname attribute for a guaranteed
71 unique id for the mailing list. This short name is always the local
72 part of the posting email address. For example, if messages are
73 posted to mylist@example.com, then the list_name is 'mylist'.
74 """)
76 mail_host = Attribute("""\
77 The read-only domain name 'hosting' this mailing list. This is always
78 the domain name part of the posting email address, and it may bear no
79 relationship to the web url used to access this mailing list. For
80 example, if messages are posted to mylist@example.com, then the
81 mail_host is 'example.com'.
82 """)
84 list_id = Attribute("""\
85 The identity of the mailing list. This value will never change. It
86 is defined in RFC 2369.
87 """)
89 fqdn_listname = Attribute("""\
90 The read-only fully qualified name of the mailing list. This is the
91 guaranteed unique id for the mailing list, and it is always the
92 address to which messages are posted, e.g. mylist@example.com. It is
93 always comprised of the list_name + '@' + mail_host.
94 """)
96 domain = Attribute(
97 """The `IDomain` that this mailing list is defined in.""")
99 display_name = Attribute("""\
100 The short human-readable descriptive name for the mailing list. This
101 is used in locations such as the message footers and Subject prefix.
102 """)
104 description = Attribute("""\
105 A terse phrase identifying this mailing list.
107 This description is used when the mailing list is listed with other
108 mailing lists, or in headers, and so forth. It should be as succinct
109 as you can get it, while still identifying what the list is.""")
111 allow_list_posts = Attribute(
112 """Flag specifying posts to the list are generally allowed.
114 This controls the value of the RFC 2369 List-Post header. This is
115 usually set to True, except for announce-only lists. When False, the
116 List-Post is set to NO as per the RFC.
117 """)
119 include_rfc2369_headers = Attribute(
120 """Flag specifying whether to include any RFC 2369 header, including
121 the RFC 2919 List-ID header.""")
123 anonymous_list = Attribute(
124 """Flag controlling whether messages to this list are anonymized.
126 Anonymizing messages is not perfect, however setting this flag removes
127 the sender of the message (in the From, Sender, and Reply-To fields)
128 and replaces these with the list's posting address.
129 """)
131 advertised = Attribute(
132 """Advertise this mailing list when people ask for an overview of the
133 available mailing lists.""")
135 # Contact addresses
137 posting_address = Attribute(
138 """The address to which messages are posted for copying to the full
139 list membership, where 'full' of course means those members for which
140 delivery is currently enabled.
141 """)
143 no_reply_address = Attribute(
144 """The address to which all messages will be immediately discarded,
145 without prejudice or record. This address is specific to the ddomain,
146 even though it's available on the IMailingListAddresses interface.
147 Generally, humans should never respond directly to this address.
148 """)
150 owner_address = Attribute(
151 """The address which reaches the owners and moderators of the mailing
152 list. There is no address which reaches just the owners or just the
153 moderators of a mailing list.
154 """)
156 request_address = Attribute(
157 """The address which reaches the email robot for this mailing list.
158 This robot can process various email commands such as changing
159 delivery options, getting information or help about the mailing list,
160 or processing subscrptions and unsubscriptions (although for the
161 latter two, it's better to use the join_address and leave_address.
162 """)
164 bounces_address = Attribute(
165 """The address which reaches the automated bounce processor for this
166 mailing list. Generally, humans should never respond directly to this
167 address.
168 """)
170 join_address = Attribute(
171 """The address to which subscription requests should be sent.""")
173 leave_address = Attribute(
174 """The address to which unsubscription requests should be sent.""")
176 subscribe_address = Attribute(
177 """Deprecated address to which subscription requests may be sent.
178 This address is provided for backward compatibility only. See
179 `join_address` for the preferred alias.
180 """)
182 unsubscribe_address = Attribute(
183 """Deprecated address to which unsubscription requests may be sent.
184 This address is provided for backward compatibility only. See
185 `leave_address` for the preferred alias.
186 """)
188 def confirm_address(cookie=''):
189 """The address used for various forms of email confirmation."""
191 # Rosters and subscriptions.
193 owners = Attribute(
194 """The IUser owners of this mailing list.
196 This does not include the IUsers who are moderators but not owners of
197 the mailing list.""")
199 moderators = Attribute(
200 """The IUser moderators of this mailing list.
202 This does not include the IUsers who are owners but not moderators of
203 the mailing list.""")
205 administrators = Attribute(
206 """The IUser administrators of this mailing list.
208 This includes the IUsers who are both owners and moderators of the
209 mailing list.""")
211 members = Attribute(
212 """An iterator over all the members of the mailing list, regardless of
213 whether they are to receive regular messages or digests, or whether
214 they have their delivery disabled or not.""")
216 regular_members = Attribute(
217 """An iterator over all the IMembers who are to receive regular
218 postings (i.e. non-digests) from the mailing list, regardless of
219 whether they have their delivery disabled or not.""")
221 digest_members = Attribute(
222 """An iterator over all the IMembers who are to receive digests of
223 postings to this mailing list, regardless of whether they have their
224 deliver disabled or not, or of the type of digest they are to
225 receive.""")
227 subscribers = Attribute(
228 """An iterator over all IMembers subscribed to this list, with any
229 role.
230 """)
232 def get_roster(role):
233 """Return the appropriate roster for the given role.
235 :param role: The requested roster's role.
236 :type role: MemberRole
237 :return: The requested roster.
238 :rtype: Roster
241 def subscribe(subscriber, role=MemberRole.member):
242 """Subscribe the given address or user to the mailing list.
244 :param subscriber: The address or user to subscribe to the mailing
245 list. The user's preferred address receives deliveries, if she
246 has one, otherwise no address for the user appears in the rosters.
247 :type subscriber: `IUser` or `IAddress`
248 :param role: The role being subscribed to (e.g. a member, owner, or
249 moderator of a mailing list.
250 :type role: `MemberRole`
251 :return: The member object representing the subscription.
252 :rtype: `IMember`
253 :raises AlreadySubscribedError: If the address or user is already
254 subscribed to the mailing list with the given role. Note however
255 that it is possible to subscribe an address to a mailing list with
256 a particular role, and also subscribe a user with a matching
257 preferred address that is explicitly subscribed with the same role.
260 # Delivery.
262 archive_policy = Attribute(
263 """The policy for archiving messages to this mailing list.
265 The value is an `ArchivePolicy` enum. Use this to archive the mailing
266 list publicly, privately, or not at all.
267 """)
269 last_post_at = Attribute(
270 """The date and time a message was last posted to the mailing list.""")
272 post_id = Attribute(
273 """A monotonically increasing integer sequentially assigned to each
274 list posting.""")
276 personalize = Attribute(
277 """The type of personalization that is applied to postings.""")
279 reply_goes_to_list = Attribute(
280 """Reply-To: header munging policy.""")
282 # Digests.
284 digest_last_sent_at = Attribute(
285 """The date and time a digest of this mailing list was last sent.""")
287 volume = Attribute(
288 """A monotonically increasing integer sequentially assigned to each
289 new digest volume. The volume number may be bumped either
290 automatically (i.e. on a defined schedule) or manually. When the
291 volume number is bumped, the digest number is always reset to 1.""")
293 next_digest_number = Attribute(
294 """A sequence number for a specific digest in a given volume. When
295 the digest volume number is bumped, the digest number is reset to
296 1.""")
298 digest_size_threshold = Attribute(
299 """The maximum (approximate) size in kilobytes of the digest currently
300 being collected.""")
302 def send_one_last_digest_to(address, delivery_mode):
303 """Make sure to send one last digest to an address.
305 This is used when a person transitions from digest delivery to regular
306 delivery and wants to make sure they don't miss anything. By
307 indicating that they'd like to receive one last digest, they will
308 ensure continuity in receiving mailing lists posts.
310 :param address: The address of the person receiving one last digest.
311 :type address: `IAddress`
312 :param delivery_mode: The type of digest to receive.
313 :type delivery_mode: `DeliveryMode`
316 last_digest_recipients = Attribute(
317 """An iterator over the addresses that should receive one last digest.
319 Items are 2-tuples of (`IAddress`, `DeliveryMode`). The one last
320 digest recipients are cleared.
321 """)
323 # Web access.
325 scheme = Attribute(
326 """The protocol scheme used to contact this list's server.
328 The web server on this protocol provides the web interface for this
329 mailing list. The protocol scheme should be 'http' or 'https'.""")
331 web_host = Attribute(
332 """This list's web server's domain.
334 The read-only domain name of the host to contact for interacting with
335 the web interface of the mailing list.""")
337 def script_url(target, context=None):
338 """Return the url to the given script target.
340 If 'context' is not given, or is None, then an absolute url is
341 returned. If context is given, it must be an IMailingListRequest
342 object, and the returned url will be relative to that object's
343 'location' attribute.
346 # Autoresponses.
348 autoresponse_grace_period = Attribute(
349 """Time period (in days) between automatic responses.
351 When this mailing list is set to send an auto-response for messages
352 sent to mailing list posts, the mailing list owners, or the `-request`
353 address, such reponses will not be sent to the same user more than
354 once during the grace period. Set to zero (or a negative value) for
355 no grace period (i.e. auto-respond to every message).
356 """)
358 autorespond_owner = Attribute(
359 """How should the mailing list automatically respond to messages sent
360 to the -owner or -moderator address?
362 Options are:
363 * No response sent
364 * Send a response and discard the original messge
365 * Send a response and continue processing the original message
366 """)
368 autoresponse_owner_text = Attribute(
369 """The text sent in an autoresponse to the owner or moderator.""")
371 autorespond_postings = Attribute(
372 """How should the mailing list automatically respond to messages sent
373 to the list's posting address?
375 Options are:
376 * No response sent
377 * Send a response and discard the original messge
378 * Send a response and continue processing the original message
379 """)
381 autoresponse_postings_text = Attribute(
382 """The text sent in an autoresponse to the list's posting address.""")
384 autorespond_requests = Attribute(
385 """How should the mailing list automatically respond to messages sent
386 to the list's `-request` address?
388 Options are:
389 * No response sent
390 * Send a response and discard the original messge
391 * Send a response and continue processing the original message
392 """)
394 autoresponse_request_text = Attribute(
395 """The text sent in an autoresponse to the list's `-request`
396 address.""")
398 # Processing.
400 posting_chain = Attribute(
401 """This mailing list's posting moderation chain.
403 When messages are posted to a mailing list, it first goes through a
404 moderation chain to determine whether the message will be accepted.
405 This attribute names a chain for postings, which must exist.
406 """)
408 posting_pipeline = Attribute(
409 """This mailing list's posting pipeline.
411 Every mailing list has a processing pipeline that messages flow
412 through once they've been accepted for posting to the mailing list.
413 This attribute names a pipeline for postings, which must exist.
414 """)
416 owner_chain = Attribute(
417 """This mailing list's owner moderation chain.
419 When messages are posted to the owners of a mailing list, it first
420 goes through a moderation chain to determine whether the message will
421 be accepted. This attribute names a chain for postings, which must
422 exist.
423 """)
425 owner_pipeline = Attribute(
426 """This mailing list's owner posting pipeline.
428 Every mailing list has a processing pipeline that messages flow
429 through once they've been accepted for posting to the owners of a
430 mailing list. This attribute names a pipeline for postings, which
431 must exist.
432 """)
434 data_path = Attribute(
435 """The file system path to list-specific data.
437 An example of list-specific data is the temporary digest mbox file
438 that gets created to accumlate messages for the digest.
439 """)
441 administrative = Attribute(
442 """Flag controlling `administrivia` checks.
444 Administrivia tests check whether postings to the mailing list are
445 really meant for the -request address. Examples include messages with
446 `help`, `subscribe`, `unsubscribe`, and other commands. When such
447 messages are incorrectly posted to the general mailing list, they are
448 just noise, and when this flag is set will be intercepted and in
449 general held for moderator approval.
450 """)
452 filter_content = Attribute(
453 """Flag specifying whether to filter a message's content.
455 Filtering is performed on MIME type and file name extension.
456 """)
458 filter_action = Attribute(
459 """Action to take when the top-level content-type is filtered.
461 The value is a `FilterAction` enum.
462 """)
464 convert_html_to_plaintext = Attribute(
465 """Flag specifying whether text/html parts should be converted.
467 When True, after filtering, if there are any text/html parts left in
468 the original message, they are converted to text/plain.
469 """)
471 collapse_alternatives = Attribute(
472 """Flag specifying whether multipart/alternatives should be collapsed.
474 After all MIME content filtering is complete, collapsing alternatives
475 replaces the outer multipart/alternative parts with the first
476 subpart.
477 """)
479 filter_types = Attribute(
480 """Sequence of MIME types that should be filtered out.
482 These can be either main types or main/sub types. Set this attribute
483 to a sequence to change it, or to None to empty it.
484 """)
486 pass_types = Attribute(
487 """Sequence of MIME types to explicitly pass.
489 These can be either main types or main/sub types. Set this attribute
490 to a sequence to change it, or to None to empty it. Pass types are
491 consulted after filter types, and only if `pass_types` is non-empty.
492 """)
494 filter_extensions = Attribute(
495 """Sequence of file extensions that should be filtered out.
497 Set this attribute to a sequence to change it, or to None to empty it.
498 """)
500 pass_extensions = Attribute(
501 """Sequence of file extensions to explicitly pass.
503 Set this attribute to a sequence to change it, or to None to empty it.
504 Pass extensions are consulted after filter extensions, and only if
505 `pass_extensions` is non-empty.
506 """)
508 # Moderation.
510 default_member_action = Attribute(
511 """The default action to take for postings from members.
513 When an address is subscribed to the mailing list, this attribute sets
514 the initial moderation action (as an `Action`). When the action is
515 `Action.defer` (the default), then normal posting decisions are made.
516 When the action is `Action.accept`, the postings are accepted without
517 any other checks.
518 """)
520 default_nonmember_action = Attribute(
521 """The default action to take for postings from nonmembers.
523 When a nonmember address posts to the mailing list, this attribute
524 sets the initial moderation action (as an `Action`). When the action
525 is `Action.defer` (the default), then normal posting decisions are
526 made. When the action is `Action.accept`, the postings are accepted
527 without any other checks.
528 """)
530 newsgroup_moderation = Attribute(
531 """The moderation policy for the linked newsgroup, if there is one.""")
533 # Bounces.
535 forward_unrecognized_bounces_to = Attribute(
536 """What to do when a bounce contains no recognizable addresses.
538 This is an enumeration which specifies what to do with such bounce
539 messages. They can be discarded, forward to the list owner, or
540 forwarded to the site owner.
541 """)
543 process_bounces = Attribute(
544 """Whether or not the mailing list processes bounces.""")
546 # Notifications.
548 admin_immed_notify = Attribute(
549 """Flag controlling immediate notification of requests.
551 List moderators normally get daily notices about pending
552 administrative requests. This flag controls whether moderators also
553 receive immediate notification of such pending requests.
554 """)
556 admin_notify_mchanges = Attribute(
557 """Flag controlling notification of joins and leaves.
559 List moderators can receive notifications for every member that joins
560 or leaves their mailing lists. This flag controls those
561 notifications.
562 """)
564 send_welcome_message = Attribute(
565 """Flag indicating whether a welcome message should be sent.""")
567 welcome_message_uri = Attribute(
568 """URI for the list's welcome message.
570 This can be any URI supported by `urllib2` with the addition of
571 `mailman:` URIs, which reference internal default resources. This is
572 a template which can include the following placeholders:
574 $listname - the FQDN list name for this mailing list.
575 $language - the language code, usually the list's preferred language.
577 The resource will be downloaded and cached whenever the welcome
578 message is sent. The resource at this URI can contain the following
579 placeholders, which are also filled in through values on the mailing
580 list:
582 $fqdn_listname - the FQDN list name for this mailing list.
583 $list_name - the human readable name for the mailing list.
584 $listinfo_uri - the URI to the list's information page.
585 $list_requests - the address to the list's `-request` address.
586 $user_name - the name of the subscribing user.
587 $user_address - the email address of the subscribing user.
588 $user_options_uri - the URI to this member's options page.
589 """)
591 send_goodbye_message = Attribute(
592 """Flag indicating whether a goodbye message should be sent.""")
594 goodbye_message_uri = Attribute(
595 """URI for the list's goodbye message.
597 This can be any URI supported by `urllib2` with the addition of
598 `mailman:` URIs, which reference internal default resources. This is
599 a template which can include the following placeholders:
601 $listname - the FQDN list name for this mailing list.
602 $language - the language code, usually the list's preferred language.
604 The resource will be downloaded and cached whenever the goodbye
605 message is sent. The resource at this URI can contain the following
606 placeholders, which are also filled in through values on the mailing
607 list:
609 $fqdn_listname - the FQDN list name for this mailing list.
610 $list_name - the human readable name for the mailing list.
611 $listinfo_uri - the URI to the list's information page.
612 $list_requests - the address to the list's `-request` address.
613 $user_name - the name of the subscribing user.
614 $user_address - the email address of the subscribing user.
615 $user_options_uri - the URI to this member's options page.
616 """)
618 # Decorators.
620 header_uri = Attribute(
621 """URI for the header decorator on regular delivery messages.
623 This can be any URI supported by `urllib2` with the addition of
624 `mailman:` URIs, which reference internal default resources. This is
625 a template which can include the following placeholders:
627 $listname - the FQDN list name for this mailing list.
628 $language - the language code, usually the list's preferred language.
630 The resource will be downloaded and cached whenever the decorator is
631 needed. The resource at this URI can contain the following
632 placeholders, which are also filled in through values on the mailing
633 list:
635 $fqdn_listname - the FQDN list name for this mailing list.
636 $list_name - the human readable name for the mailing list.
637 $host_name - the mailing list's host name
638 $listinfo_uri - the URI to the list's information page.
639 $list_requests - the address to the list's `-request` address.
640 $description - the mailing list's description
641 $info - additional mailing list's information
643 Personalized messages will also have these placeholders available:
645 $user_name - the name of the subscribing user.
646 $user_address - the email address of the subscribing user.
647 $user_options_uri - the URI to this member's options page.
651 footer_uri = Attribute(
652 """URI for the footer decorator on regular delivery messages.
654 This can be any URI supported by `urllib2` with the addition of
655 `mailman:` URIs, which reference internal default resources. This is
656 a template which can include the following placeholders:
658 $listname - the FQDN list name for this mailing list.
659 $language - the language code, usually the list's preferred language.
661 The resource will be downloaded and cached whenever the decorator is
662 needed. The resource at this URI can contain the following
663 placeholders, which are also filled in through values on the mailing
664 list:
666 $fqdn_listname - the FQDN list name for this mailing list.
667 $list_name - the human readable name for the mailing list.
668 $host_name - the mailing list's host name
669 $listinfo_uri - the URI to the list's information page.
670 $list_requests - the address to the list's `-request` address.
671 $description - the mailing list's description
672 $info - additional mailing list's information
674 Personalized messages will also have these placeholders available:
676 $user_name - the name of the subscribing user.
677 $user_address - the email address of the subscribing user.
678 $user_options_uri - the URI to this member's options page.
682 digest_header_uri = Attribute(
683 """URI for the header decorator on digest messages.
685 This can be any URI supported by `urllib2` with the addition of
686 `mailman:` URIs, which reference internal default resources. This is
687 a template which can include the following placeholders:
689 $listname - the FQDN list name for this mailing list.
690 $language - the language code, usually the list's preferred language.
692 The resource will be downloaded and cached whenever the decorator is
693 needed. The resource at this URI can contain the following
694 placeholders, which are also filled in through values on the mailing
695 list:
697 $fqdn_listname - the FQDN list name for this mailing list.
698 $list_name - the human readable name for the mailing list.
699 $host_name - the mailing list's host name
700 $listinfo_uri - the URI to the list's information page.
701 $list_requests - the address to the list's `-request` address.
702 $description - the mailing list's description
703 $info - additional mailing list's information
705 Personalized messages will also have these placeholders available:
707 $user_name - the name of the subscribing user.
708 $user_address - the email address of the subscribing user.
709 $user_options_uri - the URI to this member's options page.
713 digest_footer_uri = Attribute(
714 """URI for the footer decorator on digest messages.
716 This can be any URI supported by `urllib2` with the addition of
717 `mailman:` URIs, which reference internal default resources. This is
718 a template which can include the following placeholders:
720 $listname - the FQDN list name for this mailing list.
721 $language - the language code, usually the list's preferred language.
723 The resource will be downloaded and cached whenever the decorator is
724 needed. The resource at this URI can contain the following
725 placeholders, which are also filled in through values on the mailing
726 list:
728 $fqdn_listname - the FQDN list name for this mailing list.
729 $list_name - the human readable name for the mailing list.
730 $host_name - the mailing list's host name
731 $listinfo_uri - the URI to the list's information page.
732 $list_requests - the address to the list's `-request` address.
733 $description - the mailing list's description
734 $info - additional mailing list's information
736 Personalized messages will also have these placeholders available:
738 $user_name - the name of the subscribing user.
739 $user_address - the email address of the subscribing user.
740 $user_options_uri - the URI to this member's options page.
746 class IAcceptableAlias(Interface):
747 """An acceptable alias for implicit destinations."""
749 mailing_list = Attribute('The associated mailing list.')
751 address = Attribute('The address or pattern to match against recipients.')
754 class IAcceptableAliasSet(Interface):
755 """The set of acceptable aliases for a mailing list."""
757 def clear():
758 """Clear the set of acceptable posting aliases."""
760 def add(alias):
761 """Add the given address as an acceptable aliases for posting.
763 :param alias: The email address to accept as a recipient for implicit
764 destination posting purposes. The alias is coerced to lower
765 case. If `alias` begins with a '^' character, it is interpreted
766 as a regular expression, otherwise it must be an email address.
767 :type alias: string
768 :raises ValueError: when the alias neither starts with '^' nor has an
769 '@' sign in it.
772 def remove(alias):
773 """Remove the given address as an acceptable aliases for posting.
775 :param alias: The email address to no longer accept as a recipient for
776 implicit destination posting purposes.
777 :type alias: string
780 aliases = Attribute(
781 """An iterator over all the acceptable aliases.""")