1Messaging::Message(3) User Contributed Perl DocumentationMessaging::Message(3)
2
3
4
6 Messaging::Message - abstraction of a message
7
9 use Messaging::Message;
10
11 # constructor + setters
12 $msg = Messaging::Message->new();
13 $msg->body("hello world");
14 $msg->header({ subject => "test" });
15 $msg->header_field("message-id", 123);
16
17 # fancy constructor
18 $msg = Messaging::Message->new(
19 body => "hello world",
20 header => {
21 "subject" => "test",
22 "message-id" => 123,
23 },
24 );
25
26 # getters
27 if ($msg->body() =~ /something/) {
28 ...
29 }
30 $id = $msg->header_field("message-id");
31
33 This module provides an abstraction of a "message", as used in
34 messaging, see for instance:
35 <http://en.wikipedia.org/wiki/Enterprise_messaging_system>.
36
37 A Python implementation of the same messaging abstractions is available
38 at <https://github.com/cern-mig/python-messaging> so messaging
39 components can be written in different programming languages.
40
41 A message consists of header fields (collectively called "the header of
42 the message") and a body.
43
44 Each header field is a key/value pair where the key and the value are
45 text strings. The key is unique within the header so we can use a hash
46 table to represent the header of the message.
47
48 The body is either a text string or a binary string. This distinction
49 is needed because text may need to be encoded (for instance using
50 UTF-8) before being stored on disk or sent across the network.
51
52 To make things clear:
53
54 • a text string (aka character string) is a sequence of Unicode
55 characters
56
57 • a binary string (aka byte string) is a sequence of bytes
58
59 Both the header and the body can be empty.
60
62 In order to ease message manipulation (e.g. exchanging between
63 applications, maybe written in different programming languages), we
64 define here a standard mapping between a Messaging::Message object and
65 a JSON object.
66
67 A message as defined above naturally maps to a JSON object with the
68 following fields:
69
70 header
71 the message header as a JSON object (with all values being JSON
72 strings)
73
74 body
75 the message body as a JSON string
76
77 text
78 a JSON boolean specifying whether the body is text string (as
79 opposed to binary string) or not
80
81 encoding
82 a JSON string describing how the body has been encoded (see below)
83
84 All fields are optional and default to empty/false if not present.
85
86 Since JSON strings are text strings (they can contain any Unicode
87 character), the message header directly maps to a JSON object. There is
88 no need to use encoding here.
89
90 For the message body, this is more complex. A text body can be put as-
91 is in the JSON object but a binary body must be encoded beforehand
92 because JSON does not handle binary strings. Additionally, we want to
93 allow body compression in order to optionally save space. This is where
94 the encoding field comes into play.
95
96 The encoding field describes which transformations have been applied to
97 the message body. It is a "+" separated list of transformations that
98 can be:
99
100 "base64"
101 Base64 encoding (for binary body or compressed body)
102
103 "utf8"
104 UTF-8 encoding (only needed for a compressed text body)
105
106 "lz4" or "snappy" or "zlib"
107 LZ4 or Snappy or Zlib compression (only one can be specified)
108
109 Here is for instance the JSON object representing an empty message
110 (i.e. the result of Messaging::Message->new()):
111
112 {}
113
114 Here is a more complex example, with a binary body:
115
116 {
117 "header":{"subject":"demo","destination":"/topic/test"},
118 "body":"YWJj7g==",
119 "encoding":"base64"
120 }
121
122 You can use the jsonify() method to convert a Messaging::Message object
123 into a hash reference representing the equivalent JSON object.
124
125 Conversely, you can create a new Messaging::Message object from a
126 compatible JSON object (again, a hash reference) with the dejsonify()
127 method.
128
129 Using this JSON mapping of messages is very convenient because you can
130 easily put messages in larger JSON data structures. You can for
131 instance store several messages together using a JSON array of these
132 messages.
133
134 Here is for instance how you could construct a message containing in
135 its body another message along with error information:
136
137 use JSON qw(to_json);
138 # get a message from somewhere...
139 $msg1 = ...;
140 # jsonify it and put it into a simple structure
141 $body = {
142 message => $msg1->jsonify(),
143 error => "an error message",
144 time => time(),
145 };
146 # create a new message with this body
147 $msg2 = Messaging::Message->new(body => to_json($body));
148 $msg2->header_field("content-type", "message/error");
149 $msg2->text(1);
150
151 A receiver of such a message can easily decode it:
152
153 use JSON qw(from_json);
154 # get a message from somewhere...
155 $msg2 = ...;
156 # extract the body which is a JSON object
157 $body = from_json($msg2->body());
158 # extract the inner message
159 $msg1 = Messaging::Message->dejsonify($body->{message});
160
162 In addition to the JSON mapping described above, we also define how to
163 stringify and serialize a message.
164
165 A stringified message is the string representing its equivalent JSON
166 object. A stringified message is a text string and can for instance be
167 used in another message. See the stringify() and destringify() methods.
168
169 A serialized message is the UTF-8 encoding of its stringified
170 representation. A serialized message is a binary string and can for
171 instance be stored in a file. See the serialize() and deserialize()
172 methods.
173
174 For instance, here are the steps needed in order to store a message
175 into a file:
176
177 1. transform the programming language specific abstraction of the
178 message into a JSON object
179
180 2. transform the JSON object into its (text) string representing
181
182 3. transform the JSON text string into a binary string using UTF-8
183 encoding
184
185 "1" is called jsonify, "1 + 2" is called stringify and "1 + 2 + 3" is
186 called serialize.
187
188 To sum up:
189
190 Messaging::Message object
191 | ^
192 jsonify() | | dejsonify()
193 v |
194 JSON compatible hash reference
195 | ^
196 JSON encode | | JSON decode
197 v |
198 text string
199 | ^
200 UTF-8 encode | | UTF-8 decode
201 v |
202 binary string
203
205 The following methods are available:
206
207 new([OPTIONS])
208 return a new Messaging::Message object (class method)
209
210 dejsonify(HASHREF)
211 return a new Messaging::Message object from a compatible JSON
212 object (class method)
213
214 destringify(STRING)
215 return a new Messaging::Message object from its stringified
216 representation (class method)
217
218 deserialize(STRING)
219 return a new Messaging::Message object from its serialized
220 representation (class method)
221
222 jsonify([OPTIONS])
223 return the JSON object (a hash reference) representing the message
224
225 stringify([OPTIONS])
226 return the text string representation of the message
227
228 serialize([OPTIONS])
229 return the binary string representation of the message
230
231 body([STRING])
232 get/set the body attribute, which is a text or binary string
233
234 header([HASHREF])
235 get/set the header attribute, which is a hash reference (note: the
236 hash reference is used directly, without any deep copy)
237
238 header_field(NAME[, VALUE])
239 get/set the given header field, identified by its name
240
241 text([BOOLEAN])
242 get/set the text attribute, which is a boolean indicating whether
243 the message body is a text string or not, the default is false (so
244 binary body)
245
246 size()
247 get the approximate message size, which is the sum of the sizes of
248 its components: header key/value pairs and body, plus framing
249
250 copy()
251 return a new message which is a copy of the given one, with deep
252 copy of the header and body
253
254 The jsonify(), stringify() and serialize() methods can be given
255 options.
256
257 Currently, the only supported option is "compression" and it can
258 contain either an algorithm name like "zlib" (meaning: use this
259 algorithm only of the compressed body is indeed smaller) or an
260 algorithm name followed by an exclamation mark to always force
261 compression.
262
263 Here is for instance how to serialize a message, with forced
264 compression:
265
266 $bytes = $msg->serialize(compression => "zlib!");
267
268 In addition, in order to avoid string copies, the following methods are
269 also available:
270
271 body_ref([STRINGREF])
272 stringify_ref([OPTIONS])
273 destringify_ref(STRINGREF)
274 serialize_ref([OPTIONS])
275 deserialize_ref(STRINGREF)
276
277 They work like their counterparts but use as input or output string
278 references instead of strings, which can be more efficient for large
279 strings. Here is an example:
280
281 # get a copy of the body, yielding to internal string copy
282 $body = $msg->body();
283 # get a reference to the body, with no string copies
284 $body_ref = $msg->body_ref();
285
287 Compress::Snappy, Compress::LZ4, Compress::Zlib, Encode, JSON.
288
290 Lionel Cons <http://cern.ch/lionel.cons>
291
292 Copyright (C) CERN 2011-2021
293
294
295
296perl v5.38.0 2023-07-20 Messaging::Message(3)