[evolution-kolab] libekolabconv: added XFB decoding/validation util function
- From: Christian Hilberg <chilberg src gnome org>
- To: commits-list gnome org
- Cc:
- Subject: [evolution-kolab] libekolabconv: added XFB decoding/validation util function
- Date: Sat, 24 Nov 2012 19:51:02 +0000 (UTC)
commit 3ae441a9f7b3be69d71d408490ef43daff002611
Author: Christian Hilberg <hilberg kernelconcepts de>
Date: Sat Nov 24 19:40:51 2012 +0100
libekolabconv: added XFB decoding/validation util function
* new function to base64 decode and to (forcibly) make
UTF-8 conformant the XFB data contained in the F/B
responses from the Kolab server
* base64 decoding may be Kolab specific, so we need to
do that in the backend (other groupware servers may
not base64 encode XFB data, and Evolution expects
decoded data)
* (forced) UTF-8 validation is a bit of guessing. The
icalendar specs mandate that UTF-8 to be assumed if
no encoding hints are given (which is the case for
us)
src/libekolabconv/main/src/util.c | 116 +++++++++++++++++++++++++++++++++++++
src/libekolabconv/main/src/util.h | 5 ++
2 files changed, 121 insertions(+), 0 deletions(-)
---
diff --git a/src/libekolabconv/main/src/util.c b/src/libekolabconv/main/src/util.c
index 84313ef..ea50073 100644
--- a/src/libekolabconv/main/src/util.c
+++ b/src/libekolabconv/main/src/util.c
@@ -27,11 +27,21 @@
#define _BSD_SOURCE
+#ifdef HAVE_CONFIG_H
+#include <config.h>
+#endif
+
+#include <string.h>
+#include <libedataserver/libedataserver.h>
+
#include <ctype.h>
#include "util.h"
#include "logging.h"
#include "./structs/common.h"
+#define KOLAB_FREE_BUSY_XPROP_SUMMARY "X-SUMMARY"
+#define KOLAB_FREE_BUSY_XPROP_LOCATION "X-LOCATION"
+
/**
* Tokenize string.
*
@@ -290,3 +300,109 @@ time_gm(struct tm *tm)
return ret;
#endif
}
+
+static gchar*
+xfb_utf8_string_new_from_ical (const gchar *icalstring)
+{
+ guchar *u_tmp = NULL;
+ gchar *tmp = NULL;
+ gsize in_len = 0;
+ gsize out_len = 0;
+ GError *tmp_err = NULL;
+
+ if (icalstring == NULL)
+ return NULL;
+
+ /* The icalstring may or may not be base64 encoded,
+ * which leaves us with guessing - we try decoding, if
+ * that fails we try plain. If icalstring is meant to
+ * be plain, but is valid base64 nonetheless, then we've
+ * lost (since we cannot reliably detect that case)
+ */
+
+ u_tmp = g_base64_decode (icalstring, &out_len);
+ if (u_tmp == NULL)
+ u_tmp = (guchar *) g_strdup (icalstring);
+
+ /* ical does not carry charset hints, so we
+ * try UTF-8 first, then conversion using
+ * system locale info.
+ */
+
+ /* if we have valid UTF-8, we're done converting */
+ if (g_utf8_validate ((const gchar *) u_tmp, -1, NULL))
+ goto valid;
+
+ /* no valid UTF-8, trying to convert to it
+ * according to system locale
+ */
+ tmp = g_locale_to_utf8 ((const gchar *) u_tmp,
+ -1,
+ &in_len,
+ &out_len,
+ &tmp_err);
+
+ if (tmp_err == NULL)
+ goto valid;
+
+ g_warning ("%s: %s", G_STRFUNC, tmp_err->message);
+ g_error_free (tmp_err);
+
+ /* still no success, forcing it into UTF-8, using
+ * replacement chars to replace invalid ones
+ */
+ tmp = e_util_utf8_data_make_valid ((const gchar *) u_tmp,
+ strlen ((const gchar *) u_tmp));
+ valid:
+ if (tmp == NULL)
+ tmp = (gchar *) u_tmp;
+ else
+ g_free (u_tmp);
+
+ return tmp;
+}
+
+void
+klb_conv_xfb_base64_make_utf8_valid (icalcomponent *icalcomp_vfb)
+{
+ icalproperty *ip = NULL;
+#if 0
+ gchar *summary = NULL;
+ gchar *location = NULL;
+#endif
+
+ g_return_if_fail (icalcomp_vfb != NULL);
+
+ ip = icalcomponent_get_first_property (icalcomp_vfb,
+ ICAL_FREEBUSY_PROPERTY);
+ while (ip != NULL) {
+ const gchar *tmp = NULL;
+ gchar *summary = NULL;
+ gchar *location = NULL;
+
+ tmp = icalproperty_get_parameter_as_string (ip,
+ KOLAB_FREE_BUSY_XPROP_SUMMARY);
+ summary = xfb_utf8_string_new_from_ical (tmp);
+ tmp = icalproperty_get_parameter_as_string (ip,
+ KOLAB_FREE_BUSY_XPROP_LOCATION);
+ location = xfb_utf8_string_new_from_ical (tmp);
+
+ if ((summary == NULL) && (location == NULL))
+ goto skip;
+
+ if (summary != NULL)
+ icalproperty_set_parameter_from_string (ip,
+ KOLAB_FREE_BUSY_XPROP_SUMMARY,
+ summary);
+ if (location != NULL)
+ icalproperty_set_parameter_from_string (ip,
+ KOLAB_FREE_BUSY_XPROP_LOCATION,
+ location);
+ g_free (summary);
+ g_free (location);
+
+ skip:
+ ip = icalcomponent_get_next_property (icalcomp_vfb,
+ ICAL_FREEBUSY_PROPERTY);
+ }
+}
diff --git a/src/libekolabconv/main/src/util.h b/src/libekolabconv/main/src/util.h
index bcae115..a78fa26 100644
--- a/src/libekolabconv/main/src/util.h
+++ b/src/libekolabconv/main/src/util.h
@@ -53,4 +53,9 @@ Kolab_conv_mail_part* clone_kolab_conv_mail_part(Kolab_conv_mail_part *mpart);
GList *klb_conv_mail_to_g_list (const Kolab_conv_mail* klb_mail);
time_t time_gm(struct tm *tm);
+/*
+ * XFB helpers
+ */
+void klb_conv_xfb_base64_make_utf8_valid (icalcomponent *icalcomp_vfb);
+
#endif /* UTIL_H_ */
[
Date Prev][
Date Next] [
Thread Prev][
Thread Next]
[
Thread Index]
[
Date Index]
[
Author Index]