~andrea-crotti-0/mailman/readthedocs

« back to all changes in this revision

Viewing changes to src/mailman/pipeline/docs/decorate.rst

  • Committer: Barry Warsaw
  • Date: 2012-03-04 23:39:08 UTC
  • Revision ID: barry@list.org-20120304233908-upzd5p38b8rbh3gl
Template indirection now also in effect for regular and digest headers and
footers, using the same semantics and algorithm as for welcome and goodbye
messages.

Additional schema changes:

   - msg_header       -> header_uri
   - msg_footer       -> footer_uri
   - digest_header    -> digest_header_uri
   - digest_footer    -> digest_footer_uri

Show diffs side-by-side

added added

removed removed

Lines of Context:
36
36
    Here is a message.
37
37
 
38
38
 
39
 
Decorating simple text messages
40
 
===============================
41
 
 
42
 
Text messages that have no declared content type character set are by default,
43
 
encoded in us-ascii.  When the mailing list's preferred language is ``en``
44
 
(i.e. English), the character set of the mailing list and of the message will
45
 
match.  In this case, and when the header and footer have no interpolation
46
 
placeholder variables, the message's payload will be prepended by the verbatim
47
 
header, and appended with the verbatim footer.
48
 
 
49
 
    >>> msg = message_from_string(msg_text)
50
 
    >>> mlist.msg_header = 'header\n'
51
 
    >>> mlist.msg_footer = 'footer'
 
39
Simple decorations
 
40
==================
 
41
 
 
42
Message decorations are specified by URI and can be specialized by the mailing
 
43
list and language.  Internal Mailman decorations can be referenced by using
 
44
the ``mailman://`` URL scheme.  Here we create a simple English header and
 
45
footer for all mailing lists in our site.
 
46
::
 
47
 
 
48
    >>> import os, tempfile
 
49
    >>> template_dir = tempfile.mkdtemp()
 
50
    >>> site_dir = os.path.join(template_dir, 'site', 'en')
 
51
    >>> os.makedirs(site_dir)
 
52
    >>> config.push('templates', """
 
53
    ... [paths.testing]
 
54
    ... template_dir: {0}
 
55
    ... """.format(template_dir))
 
56
 
 
57
    >>> myheader_path = os.path.join(site_dir, 'myheader.txt')
 
58
    >>> with open(myheader_path, 'w') as fp:
 
59
    ...     print >> fp, 'header'
 
60
    >>> myfooter_path = os.path.join(site_dir, 'myfooter.txt')
 
61
    >>> with open(myfooter_path, 'w') as fp:
 
62
    ...     print >> fp, 'footer'
 
63
 
 
64
Setting these attributes on the mailing list causes it to use these
 
65
templates.  Since these are site-global templates, we can use a shorter path.
 
66
 
 
67
    >>> mlist.header_uri = 'mailman:///myheader.txt'
 
68
    >>> mlist.footer_uri = 'mailman:///myfooter.txt'
 
69
 
 
70
Text messages that have no declared content type are, by default encoded in
 
71
ASCII.  When the mailing list's preferred language is ``en`` (i.e. English),
 
72
the character set of the mailing list and of the message will match, allowing
 
73
Mailman to simply prepend the header and append the footer verbatim.
 
74
 
52
75
    >>> mlist.preferred_language = 'en'
53
76
    >>> process(mlist, msg, {})
54
77
    >>> print msg.as_string()
63
86
header and footer for information to be filled in with mailing list specific
64
87
data.  An example of such information is the mailing list's `real name` (a
65
88
short descriptive name for the mailing list).
 
89
::
 
90
 
 
91
    >>> with open(myheader_path, 'w') as fp:
 
92
    ...     print >> fp, '$list_name header'
 
93
    >>> with open(myfooter_path, 'w') as fp:
 
94
    ...     print >> fp, '$list_name footer'
66
95
 
67
96
    >>> msg = message_from_string(msg_text)
68
 
    >>> mlist.msg_header = '$real_name header\n'
69
 
    >>> mlist.msg_footer = '$real_name footer'
70
97
    >>> mlist.real_name = 'XTest'
71
98
    >>> process(mlist, msg, {})
72
99
    >>> print msg.as_string()
78
105
 
79
106
You can't just pick any interpolation variable though; if you do, the variable
80
107
will remain in the header or footer unchanged.
 
108
::
 
109
 
 
110
    >>> with open(myheader_path, 'w') as fp:
 
111
    ...     print >> fp, '$dummy header'
 
112
    >>> with open(myfooter_path, 'w') as fp:
 
113
    ...     print >> fp, '$dummy footer'
81
114
 
82
115
    >>> msg = message_from_string(msg_text)
83
 
    >>> mlist.msg_header = '$dummy header\n'
84
 
    >>> mlist.msg_footer = '$dummy footer'
85
116
    >>> process(mlist, msg, {})
86
117
    >>> print msg.as_string()
87
118
    From: aperson@example.org
103
134
When Mailman sees text/plain messages with such RFC 3676 parameters, it
104
135
preserves these parameters when it concatenates headers and footers to the
105
136
message payload.
106
 
 
107
 
    >>> mlist.msg_header = 'header'
108
 
    >>> mlist.msg_footer = 'footer'
 
137
::
 
138
 
 
139
    >>> with open(myheader_path, 'w') as fp:
 
140
    ...     print >> fp, 'header'
 
141
    >>> with open(myfooter_path, 'w') as fp:
 
142
    ...     print >> fp, 'footer'
 
143
 
109
144
    >>> mlist.preferred_language = 'en'
110
145
    >>> msg = message_from_string("""\
111
146
    ... From: aperson@example.org
112
147
    ... Content-Type: text/plain; format=flowed; delsp=no
113
 
    ... 
 
148
    ...
114
149
    ... Here is a message\x20
115
150
    ... with soft line breaks.
116
151
    ... """)
120
155
    >>> # message' line will be retained in the output.
121
156
    >>> print msg['content-type']
122
157
    text/plain; format="flowed"; delsp="no"; charset="us-ascii"
123
 
    >>> [line for line in msg.get_payload().splitlines()]
124
 
    ['header', 'Here is a message ', 'with soft line breaks.', 'footer']
 
158
    >>> for line in msg.get_payload().splitlines():
 
159
    ...     print '>{0}<'.format(line)
 
160
    >header<
 
161
    >Here is a message <
 
162
    >with soft line breaks.<
 
163
    >footer<
125
164
 
126
165
 
127
166
Decorating mixed-charset messages
128
167
=================================
129
168
 
130
 
When a message has no explicit character set, it is assumed to be us-ascii.
 
169
When a message has no explicit character set, it is assumed to be ASCII.
131
170
However, if the mailing list's preferred language has a different character
132
171
set, Mailman will still try to concatenate the header and footer, but it will
133
172
convert the text to utf-8 and base-64 encode the message payload.
135
174
 
136
175
    # 'ja' = Japanese; charset = 'euc-jp'
137
176
    >>> mlist.preferred_language = 'ja'
138
 
    >>> mlist.msg_header = '$description header'
139
 
    >>> mlist.msg_footer = '$description footer'
 
177
 
 
178
    >>> with open(myheader_path, 'w') as fp:
 
179
    ...     print >> fp, '$description header'
 
180
    >>> with open(myfooter_path, 'w') as fp:
 
181
    ...     print >> fp, '$description footer'
140
182
    >>> mlist.description = '\u65e5\u672c\u8a9e'
141
183
 
142
184
    >>> from email.message import Message
154
196
    Content-Type: text/plain; charset="utf-8"
155
197
    Content-Transfer-Encoding: base64
156
198
    <BLANKLINE>
157
 
    5pel5pys6KqeIGhlYWRlcgpGcmFuw6dhaXNlCuaXpeacrOiqniBmb290ZXI=
 
199
    5pel5pys6KqeIGhlYWRlcgpGcmFuw6dhaXNlCuaXpeacrOiqniBmb290ZXIK
158
200
 
159
201
Sometimes the message even has an unknown character set.  In this case,
160
202
Mailman has no choice but to decorate the original message with MIME
161
203
attachments.
 
204
::
162
205
 
163
206
    >>> mlist.preferred_language = 'en'
164
 
    >>> mlist.msg_header = 'header'
165
 
    >>> mlist.msg_footer = 'footer'
 
207
    >>> with open(myheader_path, 'w') as fp:
 
208
    ...     print >> fp, 'header'
 
209
    >>> with open(myfooter_path, 'w') as fp:
 
210
    ...     print >> fp, 'footer'
 
211
 
166
212
    >>> msg = message_from_string("""\
167
213
    ... From: aperson@example.org
168
214
    ... Content-Type: text/plain; charset=unknown
170
216
    ...
171
217
    ... Here is a message.
172
218
    ... """)
 
219
 
173
220
    >>> process(mlist, msg, {})
174
221
    >>> msg.set_boundary('BOUNDARY')
175
222
    >>> print msg.as_string()
211
258
``Content-Disposition`` of ``inline`` so that MUAs can display these headers
212
259
as if they were simply concatenated.
213
260
 
214
 
    >>> mlist.preferred_language = 'en'
215
 
    >>> mlist.msg_header = 'header'
216
 
    >>> mlist.msg_footer = 'footer'
217
261
    >>> part_1 = message_from_string("""\
218
262
    ... From: aperson@example.org
219
263
    ...
296
340
    <BLANKLINE>
297
341
    footer
298
342
    --BOUNDARY--
 
343
 
 
344
.. Clean up
 
345
 
 
346
    >>> config.pop('templates')
 
347
    >>> import shutil
 
348
    >>> shutil.rmtree(template_dir)