1ZMSG(3) CZMQ Manual ZMSG(3)
2
3
4
6 zmsg - Class for working with multipart messages
7
9 // This is a stable class, and may not change except for emergencies. It
10 // is provided in stable builds.
11 // This class has draft methods, which may change over time. They are not
12 // in stable releases, by default. Use --enable-drafts to enable.
13 // Create a new empty message object
14 CZMQ_EXPORT zmsg_t *
15 zmsg_new (void);
16
17 // Receive message from socket, returns zmsg_t object or NULL if the recv
18 // was interrupted. Does a blocking recv. If you want to not block then use
19 // the zloop class or zmsg_recv_nowait or zmq_poll to check for socket input
20 // before receiving.
21 CZMQ_EXPORT zmsg_t *
22 zmsg_recv (void *source);
23
24 // Load/append an open file into new message, return the message.
25 // Returns NULL if the message could not be loaded.
26 CZMQ_EXPORT zmsg_t *
27 zmsg_load (FILE *file);
28
29 // Decodes a serialized message frame created by zmsg_encode () and returns
30 // a new zmsg_t object. Returns NULL if the frame was badly formatted or
31 // there was insufficient memory to work.
32 CZMQ_EXPORT zmsg_t *
33 zmsg_decode (zframe_t *frame);
34
35 // Generate a signal message encoding the given status. A signal is a short
36 // message carrying a 1-byte success/failure code (by convention, 0 means
37 // OK). Signals are encoded to be distinguishable from "normal" messages.
38 CZMQ_EXPORT zmsg_t *
39 zmsg_new_signal (byte status);
40
41 // Destroy a message object and all frames it contains
42 CZMQ_EXPORT void
43 zmsg_destroy (zmsg_t **self_p);
44
45 // Send message to destination socket, and destroy the message after sending
46 // it successfully. If the message has no frames, sends nothing but destroys
47 // the message anyhow. Nullifies the caller's reference to the message (as
48 // it is a destructor).
49 CZMQ_EXPORT int
50 zmsg_send (zmsg_t **self_p, void *dest);
51
52 // Send message to destination socket as part of a multipart sequence, and
53 // destroy the message after sending it successfully. Note that after a
54 // zmsg_sendm, you must call zmsg_send or another method that sends a final
55 // message part. If the message has no frames, sends nothing but destroys
56 // the message anyhow. Nullifies the caller's reference to the message (as
57 // it is a destructor).
58 CZMQ_EXPORT int
59 zmsg_sendm (zmsg_t **self_p, void *dest);
60
61 // Return size of message, i.e. number of frames (0 or more).
62 CZMQ_EXPORT size_t
63 zmsg_size (zmsg_t *self);
64
65 // Return total size of all frames in message.
66 CZMQ_EXPORT size_t
67 zmsg_content_size (zmsg_t *self);
68
69 // Push frame to the front of the message, i.e. before all other frames.
70 // Message takes ownership of frame, will destroy it when message is sent.
71 // Returns 0 on success, -1 on error. Deprecates zmsg_push, which did not
72 // nullify the caller's frame reference.
73 CZMQ_EXPORT int
74 zmsg_prepend (zmsg_t *self, zframe_t **frame_p);
75
76 // Add frame to the end of the message, i.e. after all other frames.
77 // Message takes ownership of frame, will destroy it when message is sent.
78 // Returns 0 on success. Deprecates zmsg_add, which did not nullify the
79 // caller's frame reference.
80 CZMQ_EXPORT int
81 zmsg_append (zmsg_t *self, zframe_t **frame_p);
82
83 // Remove first frame from message, if any. Returns frame, or NULL.
84 // Caller owns return value and must destroy it when done.
85 CZMQ_EXPORT zframe_t *
86 zmsg_pop (zmsg_t *self);
87
88 // Push block of memory to front of message, as a new frame.
89 // Returns 0 on success, -1 on error.
90 CZMQ_EXPORT int
91 zmsg_pushmem (zmsg_t *self, const void *data, size_t size);
92
93 // Add block of memory to the end of the message, as a new frame.
94 // Returns 0 on success, -1 on error.
95 CZMQ_EXPORT int
96 zmsg_addmem (zmsg_t *self, const void *data, size_t size);
97
98 // Push string as new frame to front of message.
99 // Returns 0 on success, -1 on error.
100 CZMQ_EXPORT int
101 zmsg_pushstr (zmsg_t *self, const char *string);
102
103 // Push string as new frame to end of message.
104 // Returns 0 on success, -1 on error.
105 CZMQ_EXPORT int
106 zmsg_addstr (zmsg_t *self, const char *string);
107
108 // Push formatted string as new frame to front of message.
109 // Returns 0 on success, -1 on error.
110 CZMQ_EXPORT int
111 zmsg_pushstrf (zmsg_t *self, const char *format, ...) CHECK_PRINTF (2);
112
113 // Push formatted string as new frame to end of message.
114 // Returns 0 on success, -1 on error.
115 CZMQ_EXPORT int
116 zmsg_addstrf (zmsg_t *self, const char *format, ...) CHECK_PRINTF (2);
117
118 // Pop frame off front of message, return as fresh string. If there were
119 // no more frames in the message, returns NULL.
120 // Caller owns return value and must destroy it when done.
121 CZMQ_EXPORT char *
122 zmsg_popstr (zmsg_t *self);
123
124 // Push encoded message as a new frame. Message takes ownership of
125 // submessage, so the original is destroyed in this call. Returns 0 on
126 // success, -1 on error.
127 CZMQ_EXPORT int
128 zmsg_addmsg (zmsg_t *self, zmsg_t **msg_p);
129
130 // Remove first submessage from message, if any. Returns zmsg_t, or NULL if
131 // decoding was not successful.
132 // Caller owns return value and must destroy it when done.
133 CZMQ_EXPORT zmsg_t *
134 zmsg_popmsg (zmsg_t *self);
135
136 // Remove specified frame from list, if present. Does not destroy frame.
137 CZMQ_EXPORT void
138 zmsg_remove (zmsg_t *self, zframe_t *frame);
139
140 // Set cursor to first frame in message. Returns frame, or NULL, if the
141 // message is empty. Use this to navigate the frames as a list.
142 CZMQ_EXPORT zframe_t *
143 zmsg_first (zmsg_t *self);
144
145 // Return the next frame. If there are no more frames, returns NULL. To move
146 // to the first frame call zmsg_first(). Advances the cursor.
147 CZMQ_EXPORT zframe_t *
148 zmsg_next (zmsg_t *self);
149
150 // Return the last frame. If there are no frames, returns NULL.
151 CZMQ_EXPORT zframe_t *
152 zmsg_last (zmsg_t *self);
153
154 // Save message to an open file, return 0 if OK, else -1. The message is
155 // saved as a series of frames, each with length and data. Note that the
156 // file is NOT guaranteed to be portable between operating systems, not
157 // versions of CZMQ. The file format is at present undocumented and liable
158 // to arbitrary change.
159 CZMQ_EXPORT int
160 zmsg_save (zmsg_t *self, FILE *file);
161
162 // Serialize multipart message to a single message frame. Use this method
163 // to send structured messages across transports that do not support
164 // multipart data. Allocates and returns a new frame containing the
165 // serialized message. To decode a serialized message frame, use
166 // zmsg_decode ().
167 // Caller owns return value and must destroy it when done.
168 CZMQ_EXPORT zframe_t *
169 zmsg_encode (zmsg_t *self);
170
171 // Create copy of message, as new message object. Returns a fresh zmsg_t
172 // object. If message is null, or memory was exhausted, returns null.
173 // Caller owns return value and must destroy it when done.
174 CZMQ_EXPORT zmsg_t *
175 zmsg_dup (zmsg_t *self);
176
177 // Send message to zsys log sink (may be stdout, or system facility as
178 // configured by zsys_set_logstream).
179 // Long messages are truncated.
180 CZMQ_EXPORT void
181 zmsg_print (zmsg_t *self);
182
183 // Return true if the two messages have the same number of frames and each
184 // frame in the first message is identical to the corresponding frame in the
185 // other message. As with zframe_eq, return false if either message is NULL.
186 CZMQ_EXPORT bool
187 zmsg_eq (zmsg_t *self, zmsg_t *other);
188
189 // Return signal value, 0 or greater, if message is a signal, -1 if not.
190 CZMQ_EXPORT int
191 zmsg_signal (zmsg_t *self);
192
193 // Probe the supplied object, and report if it looks like a zmsg_t.
194 CZMQ_EXPORT bool
195 zmsg_is (void *self);
196
197 // Self test of this class.
198 CZMQ_EXPORT void
199 zmsg_test (bool verbose);
200
201 #ifdef CZMQ_BUILD_DRAFT_API
202 // *** Draft method, for development use, may change without warning ***
203 // Return message routing ID, if the message came from a ZMQ_SERVER socket.
204 // Else returns zero.
205 CZMQ_EXPORT uint32_t
206 zmsg_routing_id (zmsg_t *self);
207
208 // *** Draft method, for development use, may change without warning ***
209 // Set routing ID on message. This is used if/when the message is sent to a
210 // ZMQ_SERVER socket.
211 CZMQ_EXPORT void
212 zmsg_set_routing_id (zmsg_t *self, uint32_t routing_id);
213
214 // *** Draft method, for development use, may change without warning ***
215 // Send message to zsys log sink (may be stdout, or system facility as
216 // configured by zsys_set_logstream).
217 // Message length is specified; no truncation unless length is zero.
218 // Backwards compatible with zframe_print when length is zero.
219 CZMQ_EXPORT void
220 zmsg_print_n (zmsg_t *self, size_t size);
221
222 #endif // CZMQ_BUILD_DRAFT_API
223 Please add '@interface' section in './../src/zmsg.c'.
224
226 The zmsg class provides methods to send and receive multipart messages
227 across 0MQ sockets. This class provides a list-like container
228 interface, with methods to work with the overall container. zmsg_t
229 messages are composed of zero or more zframe_t frames.
230
231 Please add @discuss section in ./../src/zmsg.c.
232
234 From zmsg_test method.
235
236 // Create two PAIR sockets and connect over inproc
237 zsock_t *output = zsock_new_pair ("@inproc://zmsg.test");
238 assert (output);
239 zsock_t *input = zsock_new_pair (">inproc://zmsg.test");
240 assert (input);
241
242 // Test send and receive of single-frame message
243 zmsg_t *msg = zmsg_new ();
244 assert (msg);
245 zframe_t *frame = zframe_new ("Hello", 5);
246 assert (frame);
247 zmsg_prepend (msg, &frame);
248 assert (zmsg_size (msg) == 1);
249 assert (zmsg_content_size (msg) == 5);
250 rc = zmsg_send (&msg, output);
251 assert (msg == NULL);
252 assert (rc == 0);
253
254 msg = zmsg_recv (input);
255 assert (msg);
256 assert (zmsg_size (msg) == 1);
257 assert (zmsg_content_size (msg) == 5);
258 zmsg_destroy (&msg);
259
260 // Test send and receive of multi-frame message
261 msg = zmsg_new ();
262 assert (msg);
263 rc = zmsg_addmem (msg, "Frame0", 6);
264 assert (rc == 0);
265 rc = zmsg_addmem (msg, "Frame1", 6);
266 assert (rc == 0);
267 rc = zmsg_addmem (msg, "Frame2", 6);
268 assert (rc == 0);
269 rc = zmsg_addmem (msg, "Frame3", 6);
270 assert (rc == 0);
271 rc = zmsg_addmem (msg, "Frame4", 6);
272 assert (rc == 0);
273 rc = zmsg_addmem (msg, "Frame5", 6);
274 assert (rc == 0);
275 rc = zmsg_addmem (msg, "Frame6", 6);
276 assert (rc == 0);
277 rc = zmsg_addmem (msg, "Frame7", 6);
278 assert (rc == 0);
279 rc = zmsg_addmem (msg, "Frame8", 6);
280 assert (rc == 0);
281 rc = zmsg_addmem (msg, "Frame9", 6);
282 assert (rc == 0);
283 zmsg_t *copy = zmsg_dup (msg);
284 assert (copy);
285 rc = zmsg_send (©, output);
286 assert (rc == 0);
287 rc = zmsg_send (&msg, output);
288 assert (rc == 0);
289
290 copy = zmsg_recv (input);
291 assert (copy);
292 assert (zmsg_size (copy) == 10);
293 assert (zmsg_content_size (copy) == 60);
294 zmsg_destroy (©);
295
296 msg = zmsg_recv (input);
297 assert (msg);
298 assert (zmsg_size (msg) == 10);
299 assert (zmsg_content_size (msg) == 60);
300
301 // Save to a file, read back
302 FILE *file = fopen ("zmsg.test", "w");
303 assert (file);
304 rc = zmsg_save (msg, file);
305 assert (rc == 0);
306 fclose (file);
307
308 file = fopen ("zmsg.test", "r");
309 rc = zmsg_save (msg, file);
310 assert (rc == -1);
311 fclose (file);
312 zmsg_destroy (&msg);
313
314 file = fopen ("zmsg.test", "r");
315 msg = zmsg_load (file);
316 assert (msg);
317 fclose (file);
318 remove ("zmsg.test");
319 assert (zmsg_size (msg) == 10);
320 assert (zmsg_content_size (msg) == 60);
321
322 // Remove all frames except first and last
323 int frame_nbr;
324 for (frame_nbr = 0; frame_nbr < 8; frame_nbr++) {
325 zmsg_first (msg);
326 frame = zmsg_next (msg);
327 zmsg_remove (msg, frame);
328 zframe_destroy (&frame);
329 }
330 // Test message frame manipulation
331 assert (zmsg_size (msg) == 2);
332 frame = zmsg_last (msg);
333 assert (zframe_streq (frame, "Frame9"));
334 assert (zmsg_content_size (msg) == 12);
335 frame = zframe_new ("Address", 7);
336 assert (frame);
337 zmsg_prepend (msg, &frame);
338 assert (zmsg_size (msg) == 3);
339 rc = zmsg_addstr (msg, "Body");
340 assert (rc == 0);
341 assert (zmsg_size (msg) == 4);
342 frame = zmsg_pop (msg);
343 zframe_destroy (&frame);
344 assert (zmsg_size (msg) == 3);
345 char *body = zmsg_popstr (msg);
346 assert (streq (body, "Frame0"));
347 freen (body);
348 zmsg_destroy (&msg);
349
350 // Test encoding/decoding
351 msg = zmsg_new ();
352 assert (msg);
353 byte *blank = (byte *) zmalloc (100000);
354 assert (blank);
355 rc = zmsg_addmem (msg, blank, 0);
356 assert (rc == 0);
357 rc = zmsg_addmem (msg, blank, 1);
358 assert (rc == 0);
359 rc = zmsg_addmem (msg, blank, 253);
360 assert (rc == 0);
361 rc = zmsg_addmem (msg, blank, 254);
362 assert (rc == 0);
363 rc = zmsg_addmem (msg, blank, 255);
364 assert (rc == 0);
365 rc = zmsg_addmem (msg, blank, 256);
366 assert (rc == 0);
367 rc = zmsg_addmem (msg, blank, 65535);
368 assert (rc == 0);
369 rc = zmsg_addmem (msg, blank, 65536);
370 assert (rc == 0);
371 rc = zmsg_addmem (msg, blank, 65537);
372 assert (rc == 0);
373 freen (blank);
374 assert (zmsg_size (msg) == 9);
375 frame = zmsg_encode (msg);
376 zmsg_destroy (&msg);
377 msg = zmsg_decode (frame);
378 assert (msg);
379 zmsg_destroy (&msg);
380 zframe_destroy (&frame);
381
382 // Test submessages
383 msg = zmsg_new ();
384 assert (msg);
385 zmsg_t *submsg = zmsg_new ();
386 zmsg_pushstr (msg, "matr");
387 zmsg_pushstr (submsg, "joska");
388 rc = zmsg_addmsg (msg, &submsg);
389 assert (rc == 0);
390 assert (submsg == NULL);
391 submsg = zmsg_popmsg (msg);
392 assert (submsg == NULL); // string "matr" is not encoded zmsg_t, so was discarded
393 submsg = zmsg_popmsg (msg);
394 assert (submsg);
395 body = zmsg_popstr (submsg);
396 assert (streq (body, "joska"));
397 freen (body);
398 zmsg_destroy (&submsg);
399 frame = zmsg_pop (msg);
400 assert (frame == NULL);
401 zmsg_destroy (&msg);
402
403 // Test comparison of two messages
404 msg = zmsg_new ();
405 zmsg_addstr (msg, "One");
406 zmsg_addstr (msg, "Two");
407 zmsg_addstr (msg, "Three");
408 zmsg_t *msg_other = zmsg_new ();
409 zmsg_addstr (msg_other, "One");
410 zmsg_addstr (msg_other, "Two");
411 zmsg_addstr (msg_other, "One-Hundred");
412 zmsg_t *msg_dup = zmsg_dup (msg);
413 zmsg_t *empty_msg = zmsg_new ();
414 zmsg_t *empty_msg_2 = zmsg_new ();
415 assert (zmsg_eq (msg, msg_dup));
416 assert (!zmsg_eq (msg, msg_other));
417 assert (zmsg_eq (empty_msg, empty_msg_2));
418 assert (!zmsg_eq (msg, NULL));
419 assert (!zmsg_eq (NULL, empty_msg));
420 assert (!zmsg_eq (NULL, NULL));
421 zmsg_destroy (&msg);
422 zmsg_destroy (&msg_other);
423 zmsg_destroy (&msg_dup);
424 zmsg_destroy (&empty_msg);
425 zmsg_destroy (&empty_msg_2);
426
427 // Test signal messages
428 msg = zmsg_new_signal (0);
429 assert (zmsg_signal (msg) == 0);
430 zmsg_destroy (&msg);
431 msg = zmsg_new_signal (-1);
432 assert (zmsg_signal (msg) == 255);
433 zmsg_destroy (&msg);
434
435 // Now try methods on an empty message
436 msg = zmsg_new ();
437 assert (msg);
438 assert (zmsg_size (msg) == 0);
439 assert (zmsg_unwrap (msg) == NULL);
440 assert (zmsg_first (msg) == NULL);
441 assert (zmsg_last (msg) == NULL);
442 assert (zmsg_next (msg) == NULL);
443 assert (zmsg_pop (msg) == NULL);
444 // Sending an empty message is valid and destroys the message
445 assert (zmsg_send (&msg, output) == 0);
446 assert (!msg);
447
448 zsock_destroy (&input);
449 zsock_destroy (&output);
450
451 #if defined (ZMQ_SERVER)
452 // Create server and client sockets and connect over inproc
453 zsock_t *server = zsock_new_server ("inproc://zmsg-test-routing");
454 assert (server);
455 zsock_t *client = zsock_new_client ("inproc://zmsg-test-routing");
456 assert (client);
457
458 // Send request from client to server
459 zmsg_t *request = zmsg_new ();
460 assert (request);
461 zmsg_addstr (request, "Hello");
462 rc = zmsg_send (&request, client);
463 assert (rc == 0);
464 assert (!request);
465
466 // Read request and send reply
467 request = zmsg_recv (server);
468 assert (request);
469 char *string = zmsg_popstr (request);
470 assert (streq (string, "Hello"));
471 assert (zmsg_routing_id (request));
472 zstr_free (&string);
473
474 zmsg_t *reply = zmsg_new ();
475 assert (reply);
476 zmsg_addstr (reply, "World");
477 zmsg_set_routing_id (reply, zmsg_routing_id (request));
478 rc = zmsg_send (&reply, server);
479 assert (rc == 0);
480 zmsg_destroy (&request);
481
482 // Read reply
483 reply = zmsg_recv (client);
484 string = zmsg_popstr (reply);
485 assert (streq (string, "World"));
486 assert (zmsg_routing_id (reply) == 0);
487 zmsg_destroy (&reply);
488 zstr_free (&string);
489
490 // Client and server disallow multipart
491 msg = zmsg_new ();
492 zmsg_addstr (msg, "One");
493 zmsg_addstr (msg, "Two");
494 rc = zmsg_send (&msg, client);
495 assert (rc == -1);
496 assert (zmsg_size (msg) == 2);
497 rc = zmsg_send (&msg, server);
498 assert (rc == -1);
499 assert (zmsg_size (msg) == 2);
500 zmsg_destroy (&msg);
501
502 zsock_destroy (&client);
503 zsock_destroy (&server);
504 #endif
505
506 // Test message length calculation after removal
507 msg = zmsg_new ();
508 zmsg_addstr (msg, "One");
509 zmsg_addstr (msg, "Two");
510 size_t size_before = zmsg_content_size (msg);
511 frame = zframe_new ("Three", strlen ("Three"));
512 assert (frame);
513 zmsg_remove (msg, frame);
514 size_t size_after = zmsg_content_size (msg);
515 assert (size_before == size_after);
516 zframe_destroy (&frame);
517 zmsg_destroy (&msg);
518
519 #if defined (__WINDOWS__)
520 zsys_shutdown();
521 #endif
522
523
525 The czmq manual was written by the authors in the AUTHORS file.
526
528 Main web site:
529
530 Report bugs to the email <zeromq-dev@lists.zeromq.org[1]>
531
533 Copyright (c) the Contributors as noted in the AUTHORS file. This file
534 is part of CZMQ, the high-level C binding for 0MQ:
535 http://czmq.zeromq.org. This Source Code Form is subject to the terms
536 of the Mozilla Public License, v. 2.0. If a copy of the MPL was not
537 distributed with this file, You can obtain one at
538 http://mozilla.org/MPL/2.0/. LICENSE included with the czmq
539 distribution.
540
542 1. zeromq-dev@lists.zeromq.org
543 mailto:zeromq-dev@lists.zeromq.org
544
545
546
547CZMQ 4.2.1 07/19/2023 ZMSG(3)