Previous | Contents | Index |
The programs shown in Examples 1-8 and 1-9 will loop through all messages in a message queue, converting the body of each message and re-enqueuing the converted message back to PMDF. The conversion process involves applying the "rot13" encoding used by many news readers to encode potentially offensive message content.
It is important to remember to define the PMDF_CHANNEL logical (OpenVMS) or environment variable (UNIX) to be the name of the channel (in lower case) to be serviced by this program. Also, if experimenting from your own account, do not leave this logical or environment variable defined while not experimenting --- PMDF can see it when you send mail and submit that mail as though it was enqueued by the channel given by PMDF_CHANNEL. (This is a debugging feature.) |
The following items of note are identified with callouts in each of the two programs:
get_message
is a routine which will return true (1) if PMDFgetMessage
successfully accesses a message or false (0) otherwise. If PMDFgetMessage
returns any error other than PMDF__EOF
, then the check routine is invoked.
read_line
is a routine which will return true (1) if PMDFgetLine
successfully reads a line from a message or false (0) otherwise. If PMDFreadLine
returns any error other than PMDF__EOF
, then the check
routine is invoked.
hdr
, and display any header lines stored in the structure. This routine
does not serve any real purpose here other than to illustrate how to
walk a header structure.
PMDFinitialize
is invoked with the ischannel argument true.
PMDFgetChannelName
is used to determine the name of the channel being processed. This information is later passed to PMDFstartMessageEnvelope
.
PMDFdequeueInitialize
creates and initializes a message dequeue context.
get_message
routine, the program loops over all messages to be processed.
PMDFgetRecipient
, the program loops over the envelope "To:" address list in an accessed
message.
PMDFgetRecipientFlags
. They are then copied over to the same envelope "To:" address in the new message by calling PMDFsetRecipientFlags
and then PMDFaddRecipient
.
PMDFreadHeader
and PMDFwriteHeader
is used to copy, without alteration, the message header from the old
message to the new message.
display_header_lines
to display, on the terminal, the contents of the header structure, hdr
. This is merely done as an example of walking through a header
structure; displaying the structure serves no other useful purpose in
this example.
read_line
routine, the program loops over the message body, reading each line
from the original messages, converting it, and then writing it to the
new message being enqueued.
Example 1-8 Message Dequeuing & Re-enqueuing (Pascal) |
---|
(* api_example5.pas -- Dequeue a message, rot13 the message body, and then requeue the message *) [inherit ('pmdf_exe:apidef')] program api_example5 (output); type uword = [word] 0..65535; string = packed array [1..ALFA_SIZE] of char; bigstring = packed array [1..BIGALFA_SIZE] of char; var channel, env_id, from_adr, orig_adr, to_adr : string; channel_len, env_id_len, from_adr_len, orig_adr_len, to_adr_len, txt_len : uword; dq_context : PMDF_dq; empty : varying [1] of char; hdr : PMDF_hdr; i, nflags, stat : integer; nq_context : PMDF_nq; outfile : text; txt : bigstring; function SYS$EXIT (%immed status : integer := %immed 1) : integer; extern; procedure check (stat : integer); (1) var reason : varying [20] of char; begin (* check *) if not odd (stat) then begin writev (reason, 'Reason ', stat:0); if dq_context <> nil then PMDF_defer_message (dq_context, true, reason); if nq_context <> nil then PMDF_abort_message (nq_context); if stat = 0 then SYS$EXIT (1) else SYS$EXIT (stat); end; (* if *) end; (* check *) function get_message : boolean; (2) var msg_file : string; msg_file_len : uword; begin (* get_message *) stat := PMDF_get_message (dq_context, msg_file, msg_file_len, from_adr, from_adr_len); get_message := odd (stat); if (not odd (stat)) and (stat <> PMDF__EOF) then check (stat); end; (* get_message *) function read_line : boolean; (3) begin (* read_line *) stat := PMDF_read_line (dq_context, txt, txt_len); read_line := odd (stat); if (not odd (stat)) and (stat <> PMDF__EOF) then check (stat); end; (* read_line *) procedure display_header_lines (hdr : PMDF_hdr); (4) var i : integer; hdr_line : PMDF_hdr_line_ptr; begin (* display_header_lines *) for i := HL_FIRST_HEADER to HL_LAST_HEADER do begin if hdr^[i] <> nil then begin hdr_line := hdr^[i]; while hdr_line <> nil do begin writeln (substr (hdr_line^.line^, 1, hdr_line^.line_length)); hdr_line := hdr_line^.next_line; end; (* while *) end; (* if *) end; (* for *) end; (* display_header_lines *) function rot13 (c : char) : char; (5) begin (* rot13 *) if c in ['A'..'Z'] then rot13 := chr (((ord (c) - ord ('A') + 13) mod 26) + ord ('A')) else if c in ['a'..'z'] then rot13 := chr (((ord (c) - ord ('a') + 13) mod 26) + ord ('a')) else rot13 := c; end; (* rot13 *) begin (* api_example5 *) empty := ''; hdr := nil; dq_context := nil; nq_context := nil; check (PMDF_initialize (true)); (6) check (PMDF_get_channel_name (channel, channel_len)); (7) check (PMDF_dequeue_initialize (dq_context)); (8) check (PMDF_enqueue_initialize); while get_message do begin (9) check (PMDF_get_envelope_id (dq_context, env_id, env_id_len)); (10) check (PMDF_start_message_envelope (nq_context, (11) substr (channel, 1, channel_len), substr (from_adr, 1, from_adr_len))); check (PMDF_set_envelope_id (nq_context, substr (env_id, 1, env_id_len))); (12) while odd (PMDF_get_recipient (dq_context, to_adr, to_adr_len, (13) orig_adr, orig_adr_len)) do begin check (PMDF_get_recipient_flags (dq_context, nflags)); (14) check (PMDF_set_recipient_flags (nq_context, nflags)); check (PMDF_add_recipient (nq_context, substr (to_adr, 1, to_adr_len), substr (orig_adr, 1, orig_adr_len))); check (PMDF_recipient_disposition (dq_context, nflags, (15) PMDF_DISP_DELIVERED, substr (to_adr, 1, to_adr_len), substr (orig_adr, 1, orig_adr_len), empty)); end; (* while *) check (PMDF_start_message_header (nq_context)); (16) check (PMDF_read_header (dq_context, hdr)); (17) display_header_lines (hdr); (18) check (PMDF_write_header (nq_context, hdr)); check (PMDF_dispose_header (hdr)); check (PMDF_start_message_body (nq_context)); while read_line do begin (19) for i := 1 to txt_len do txt[i] := rot13 (txt[i]); check (PMDF_write_line (nq_context, substr (txt, 1, txt_len))); end; (* while *) check (PMDF_enqueue_message (nq_context)); (20) check (PMDF_dequeue_message_end (dq_context, false, empty)); (21) end; (* while *) check (PMDF_dequeue_end (dq_context)); (22) check (PMDF_done); end. (* api_example5 *) |
Example 1-9 Message Dequeuing & Re-enqueuing (C) |
---|
/* api_example6.c -- Dequeue a message, rot13 the message body, and then requeue the message */ #include <stdio.h> #include <stdlib.h> #include <string.h> #ifdef __VMS #include "pmdf_com:apidef.h" #else #include "/pmdf/include/apidef.h" #endif typedef char string[ALFA_SIZE+1]; string from_adr, txt; int from_adr_len, txt_len; PMDF_nq *nq_context = 0; PMDF_dq *dq_context = 0; void check (int stat) (1) { char reason[20]; if (!(1 & stat)) { sprintf (reason, "Reason %d", stat); if (dq_context) PMDFdeferMessage (&dq_context, 1, reason, strlen (reason)); if (nq_context) PMDFabortMessage (&nq_context); if (!stat) exit (0); else exit (stat); } } int get_message (void) (2) { string msg_file; int msg_file_len, stat; msg_file_len = from_adr_len = ALFA_SIZE; stat = PMDFgetMessage (&dq_context, msg_file, &msg_file_len, from_adr, &from_adr_len); if (!(1 & stat) && stat != PMDF__EOF) check (stat); return (1 & stat); } int read_line (void) (3) { int stat; txt_len = BIGALFA_SIZE; stat = PMDFreadLine (&dq_context, txt, &txt_len); if ( !(1 & stat) && stat != PMDF__EOF) check (stat); return (1 & stat); } void display_header_lines (PMDF_hdr *hdr) (4) { int i; PMDF_hdr_line *hdr_line; for (i = HL_FIRST_HEADER; i <= HL_LAST_HEADER; i++) { if ((*hdr)[i]) { hdr_line = (*hdr)[i]; while (hdr_line) { printf ("%s\n", hdr_line->line); hdr_line = hdr_line->next_line; } } } } char rot13 (char c) (5) { if ('A' <= c && c <= 'Z') return (((c - 'A' + 13) % 26) + 'A'); else if ('a' <= c && c <= 'z') return (((c - 'a' + 13) % 26) + 'a'); else return (c); } main () { string channel, env_id, orig_adr, to_adr; int channel_len, env_id_len, nflags, i, orig_adr_len, to_adr_len; PMDF_hdr *hdr; unsigned int key; check (PMDFinitialize (1)); (6) channel_len = ALFA_SIZE; check (PMDFgetChannelName (channel, &channel_len, &key, &key)); (7) check (PMDFdequeueInitialize (&dq_context)); (8) check (PMDFenqueueInitialize ()); while (get_message ()) { (9) env_id_len = ALFA_SIZE; check (PMDFgetEnvelopeId (&dq_context, env_id, &env_id_len)); (10) check (PMDFstartMessageEnvelope (&nq_context, channel, channel_len, (11) from_adr, from_adr_len)); check (PMDFsetEnvelopeId (&nq_context, env_id, env_id_len)); (12) to_adr_len = orig_adr_len = ALFA_SIZE; while (1 & PMDFgetRecipient (&dq_context, to_adr, &to_adr_len, (13) orig_adr, &orig_adr_len)) { check (PMDFgetRecipientFlags (&dq_context, &nflags)); (14) check (PMDFsetRecipientFlags (&nq_context, nflags)); check (PMDFaddRecipient (&nq_context, to_adr, to_adr_len, orig_adr, orig_adr_len)); check (PMDFrecipientDisposition (&dq_context, nflags, (15) PMDF_DISP_DELIVERED, to_adr, to_adr_len, orig_adr, orig_adr_len, NULL, 0)); to_adr_len = orig_adr_len = ALFA_SIZE; } check (PMDFstartMessageHeader (&nq_context)); (16) check (PMDFreadHeader (&dq_context, &hdr)); (17) display_header_lines (hdr); (18) check (PMDFwriteHeader (&nq_context, hdr)); check (PMDFdisposeHeader (&hdr)); check (PMDFstartMessageBody (&nq_context)); while (read_line ()) { (19) for (i = 0; i < txt_len - 1; i++) txt[i] = rot13 (txt[i]); check (PMDFwriteLine (&nq_context, txt, txt_len)); } check (PMDFenqueueMessage (&nq_context)); (20) check (PMDFdequeueMessageEnd (&dq_context, 0, NULL, 0)); (21) } check (PMDFdequeueEnd (&dq_context)); (22) check (PMDFdone ()); } |
Previous | Next | Contents | Index |