From ce5289f43bedd953d1ccede7be18fd5bf39a2648 Mon Sep 17 00:00:00 2001 From: Art Cancro Date: Sat, 28 Oct 2006 16:05:12 +0000 Subject: [PATCH] New server command DLAT (DownLoad ATtachment) which is similar to OPNA (OPeN Attachment), except it outputs the entire MIME part in a single server operation instead of opening a download file for block transfer. This will be useful for grabbing small components such as calendar appointments and address book entries with substantialy less overhead. --- citadel/citserver.c | 4 +++ citadel/msgbase.c | 64 ++++++++++++++++++++++++++++++++++++ citadel/msgbase.h | 1 + citadel/server.h | 3 +- citadel/techdoc/protocol.txt | 8 +++++ 5 files changed, 79 insertions(+), 1 deletion(-) diff --git a/citadel/citserver.c b/citadel/citserver.c index e86b1e1bf..95eab2fc6 100644 --- a/citadel/citserver.c +++ b/citadel/citserver.c @@ -1077,6 +1077,10 @@ void do_command_loop(void) { cmd_opna(&cmdbuf[5]); } + else if (!strncasecmp(cmdbuf,"DLAT",4)) { + cmd_dlat(&cmdbuf[5]); + } + else if (!strncasecmp(cmdbuf,"INFO",4)) { cmd_info(); } diff --git a/citadel/msgbase.c b/citadel/msgbase.c index 1a1f984f1..2a6b775c8 100644 --- a/citadel/msgbase.c +++ b/citadel/msgbase.c @@ -969,6 +969,27 @@ void mime_download(char *name, char *filename, char *partnum, char *disp, +/* + * Callback function for mime parser that outputs a section all at once + */ +void mime_spew_section(char *name, char *filename, char *partnum, char *disp, + void *content, char *cbtype, char *cbcharset, size_t length, + char *encoding, void *cbuserdata) +{ + int *found_it = (int *)cbuserdata; + + /* ...or if this is not the desired section */ + if (strcasecmp(CC->download_desired_section, partnum)) + return; + + *found_it = 1; + + cprintf("%d %d\n", BINARY_FOLLOWS, length); + client_write(content, length); +} + + + /* * Load a message from disk into memory. * This is used by CtdlOutputMsg() and other fetch functions. @@ -1492,6 +1513,32 @@ int CtdlOutputPreLoadedMsg( return((CC->download_fp != NULL) ? om_ok : om_mime_error); } + /* MT_SPEW_SECTION is like MT_DOWNLOAD except it outputs the whole MIME part + * in a single server operation instead of opening a download file. + */ + if (mode == MT_SPEW_SECTION) { + if (TheMessage->cm_format_type != FMT_RFC822) { + if (do_proto) + cprintf("%d This is not a MIME message.\n", + ERROR + ILLEGAL_VALUE); + } else { + /* Parse the message text component */ + int found_it = 0; + + mptr = TheMessage->cm_fields['M']; + mime_parser(mptr, NULL, *mime_spew_section, NULL, NULL, (void *)&found_it, 0); + /* If section wasn't found, print an error + */ + if (!found_it) { + if (do_proto) cprintf( + "%d Section %s not found.\n", + ERROR + FILE_NOT_FOUND, + CC->download_desired_section); + } + } + return((CC->download_fp != NULL) ? om_ok : om_mime_error); + } + /* now for the user-mode message reading loops */ if (do_proto) cprintf("%d msg:\n", LISTING_FOLLOWS); @@ -1911,6 +1958,23 @@ void cmd_opna(char *cmdbuf) CtdlOutputMsg(msgid, MT_DOWNLOAD, 0, 1, 1, NULL); } + +/* + * Open a component of a MIME message and transmit it all at once + */ +void cmd_dlat(char *cmdbuf) +{ + long msgid; + char desired_section[128]; + + msgid = extract_long(cmdbuf, 0); + extract_token(desired_section, cmdbuf, 1, '|', sizeof desired_section); + safestrncpy(CC->download_desired_section, desired_section, + sizeof CC->download_desired_section); + CtdlOutputMsg(msgid, MT_SPEW_SECTION, 0, 1, 1, NULL); +} + + /* * Save one or more message pointers into a specified room * (Returns 0 for success, nonzero for failure) diff --git a/citadel/msgbase.h b/citadel/msgbase.h index 4295d7be3..d06c6398a 100644 --- a/citadel/msgbase.h +++ b/citadel/msgbase.h @@ -91,6 +91,7 @@ void cmd_msg3 (char *cmdbuf); void cmd_msg4 (char *cmdbuf); void cmd_msgp (char *cmdbuf); void cmd_opna (char *cmdbuf); +void cmd_dlat (char *cmdbuf); long send_message (struct CtdlMessage *); void loadtroom (void); long CtdlSubmitMsg(struct CtdlMessage *, struct recptypes *, char *); diff --git a/citadel/server.h b/citadel/server.h index 8061e3df0..e76fe1ac8 100644 --- a/citadel/server.h +++ b/citadel/server.h @@ -242,7 +242,8 @@ enum { MT_CITADEL, /* Citadel proprietary */ MT_RFC822, /* RFC822 */ MT_MIME, /* MIME-formatted message */ - MT_DOWNLOAD /* Download a component */ + MT_DOWNLOAD, /* Download a component */ + MT_SPEW_SECTION /* Download a component in a single operation */ }; /* diff --git a/citadel/techdoc/protocol.txt b/citadel/techdoc/protocol.txt index 0586e0bd2..8bba36148 100644 --- a/citadel/techdoc/protocol.txt +++ b/citadel/techdoc/protocol.txt @@ -1950,6 +1950,14 @@ appropriate ERROR code will be returned; otherwise, if the open is successful, this command will succeed returning the same information as an OPEN command. + DLAT (DownLoad ATtachment) + + Similar to OPNA, and with the same calling syntax. The difference is that +instead of opening a download file for block transfer, this command outputs the +entire decoded MIME section at once, using a BINARY_FOLLOWS response. This is +useful for outputting small objects such as calendar items. + + GEXP (Get instant messages) This is a more sophisticated way of retrieving instant messages than the old -- 2.30.2