[gmime] Added g_mime_message_get_body()



commit 33d36d93b0d232701d1094d6c073a563fc458d6e
Author: Jeffrey Stedfast <fejj gnome org>
Date:   Sat Oct 30 10:49:47 2010 -0400

    Added g_mime_message_get_body()
    
    2010-10-30  Jeffrey Stedfast  <fejj novell com>
    
    	* gmime/gmime-message.c (g_mime_message_get_body): New function
    	* to
    	try and guess which part (or multipart/alternative) represents
    the
    	message body.

 ChangeLog             |    6 +++
 TODO                  |    6 ++-
 gmime/gmime-message.c |   97 +++++++++++++++++++++++++++++++++++++++++++++++++
 gmime/gmime-message.h |    2 +
 4 files changed, 109 insertions(+), 2 deletions(-)
---
diff --git a/ChangeLog b/ChangeLog
index 28bf20b..576bfea 100644
--- a/ChangeLog
+++ b/ChangeLog
@@ -1,3 +1,9 @@
+2010-10-30  Jeffrey Stedfast  <fejj novell com>
+
+	* gmime/gmime-message.c (g_mime_message_guess_body): New function
+	to try and guess which part (or multipart/alternative) represents
+	the message body.
+
 2010-09-25  Jeffrey Stedfast  <fejj novell com>
 
 	* gmime/charset-map.c: According to rfc1557, it is suggested that
diff --git a/TODO b/TODO
index 4f8cd37..a3a4e39 100644
--- a/TODO
+++ b/TODO
@@ -26,7 +26,7 @@ GMime 2.6 Planning:
 - Consider GCancellable and GError for GMimeStreams and
   GMimeParser... GError being far more important than
   GCancellable. GCancellable could be nice to have for network
-  streams, though...
+  streams, though... [ POSTPONED ]
 
 - Add a GIO-backed GMimeStream and bump glib dep to 2.16 [ DONE ]
 
@@ -36,7 +36,7 @@ GMime 2.6 Planning:
 
   This might be a better name for the enum to reflect what it's
   actually meant for. Maybe also move it from gmime-filter-best.h to
-  gmime-encodings.h? [ DONE ]
+  gmime-encodings.h?
 
 - How about a g_mime_part_get_best_charset()? This one could be
   awkward since it depends on the content being text and also encoded
@@ -46,6 +46,8 @@ GMime 2.6 Planning:
   or else make sure that GMime.metadata 'fixes' the method name to be
   GetEncoding so that it will appear as a C# property getter.
 
+- Re-add a g_mime_message_get_body()?
+
 
 Other:
 ======
diff --git a/gmime/gmime-message.c b/gmime/gmime-message.c
index 638b93e..0051873 100644
--- a/gmime/gmime-message.c
+++ b/gmime/gmime-message.c
@@ -29,6 +29,8 @@
 
 #include "gmime-message.h"
 #include "gmime-multipart.h"
+#include "gmime-multipart-signed.h"
+#include "gmime-multipart-encrypted.h"
 #include "gmime-part.h"
 #include "gmime-utils.h"
 #include "gmime-stream-mem.h"
@@ -1502,3 +1504,98 @@ g_mime_message_foreach (GMimeMessage *message, GMimeObjectForeachFunc callback,
 	if (GMIME_IS_MULTIPART (message->mime_part))
 		g_mime_multipart_foreach ((GMimeMultipart *) message->mime_part, callback, user_data);
 }
+
+static gboolean
+part_is_textual (GMimeObject *mime_part)
+{
+	GMimeContentType *type;
+	
+	type = g_mime_object_get_content_type (mime_part);
+	
+	return g_mime_content_type_is_type (type, "text", "*");
+}
+
+static GMimeObject *
+multipart_guess_body (GMimeMultipart *multipart)
+{
+	GMimeContentType *type;
+	GMimeObject *mime_part;
+	int count, i;
+	
+	if (GMIME_IS_MULTIPART_ENCRYPTED (multipart)) {
+		/* check if this part has already been decrypted... */
+		if (!(mime_part = ((GMimeMultipartEncrypted *) multipart)->decrypted)) {
+			/* nothing more we can do */
+			return (GMimeObject *) multipart;
+		}
+		
+		if (GMIME_IS_MULTIPART (mime_part))
+			return multipart_guess_body ((GMimeMultipart *) mime_part);
+		else if (GMIME_IS_PART (mime_part) && part_is_textual (mime_part))
+			return mime_part;
+		else
+			return NULL;
+	}
+	
+	type = g_mime_object_get_content_type ((GMimeObject *) multipart);
+	if (g_mime_content_type_is_type (type, "multipart", "alternative")) {
+		/* very likely that this is the body - leave it up to
+		 * our caller to decide which format of the body it
+		 * wants to use. */
+		return (GMimeObject *) multipart;
+	}
+	
+	count = g_mime_multipart_get_count (multipart);
+	
+	if (!GMIME_IS_MULTIPART_SIGNED (mime_part)) {
+		/* if the body is in here, it has to be the first part */
+		count = 1;
+	}
+	
+	for (i = 0; i < count; i++) {
+		mime_part = g_mime_multipart_get_part (multipart, i);
+		
+		if (GMIME_IS_MULTIPART (mime_part)) {
+			if ((mime_part = multipart_guess_body ((GMimeMultipart *) mime_part)))
+				return mime_part;
+		} else if (GMIME_IS_PART (mime_part)) {
+			if (part_is_textual (mime_part))
+				return mime_part;
+		}
+	}
+	
+	return NULL;
+}
+
+
+/**
+ * g_mime_message_get_body:
+ * @message: MIME Message
+ *
+ * Attempts to identify the MIME part containing the body of the
+ * message.
+ *
+ * Returns: a #GMimeObject containing the textual content that appears
+ * to be the main body of the message.
+ *
+ * Note: This function is NOT guarenteed to always work as it
+ * makes some assumptions that are not necessarily true. It is
+ * recommended that you traverse the MIME structure yourself.
+ **/
+GMimeObject *
+g_mime_message_guess_body (GMimeMessage *message)
+{
+	GMimeObject *mime_part;
+	
+	g_return_val_if_fail (GMIME_IS_MESSAGE (message), NULL);
+	
+	if (!(mime_part = message->mime_part))
+		return NULL;
+	
+	if (GMIME_IS_MULTIPART (mime_part))
+		return multipart_guess_body ((GMimeMultipart *) mime_part);
+	else if (GMIME_IS_PART (mime_part) && part_is_textual (mime_part))
+		return mime_part;
+	
+	return NULL;
+}
diff --git a/gmime/gmime-message.h b/gmime/gmime-message.h
index e2bad72..4668209 100644
--- a/gmime/gmime-message.h
+++ b/gmime/gmime-message.h
@@ -126,6 +126,8 @@ void g_mime_message_set_mime_part (GMimeMessage *message, GMimeObject *mime_part
 void g_mime_message_foreach (GMimeMessage *message, GMimeObjectForeachFunc callback,
 			     gpointer user_data);
 
+GMimeObject *g_mime_message_get_body (GMimeMessage *message);
+
 G_END_DECLS
 
 #endif /* __GMIME_MESSAGE_H__ */



[Date Prev][Date Next]   [Thread Prev][Thread Next]   [Thread Index] [Date Index] [Author Index]