[libgdata] Bug 605699 — Add packet capture to test suite



commit 41ba653f9fdaa44b81b591183a67898791eb1821
Author: Philip Withnall <philip tecnocode co uk>
Date:   Sun Mar 7 21:09:51 2010 +0000

    Bug 605699 â?? Add packet capture to test suite
    
    Add a LIBGDATA_DEBUG environment variable which allows setting the debug
    output level (from none, through messages and headers, to full network
    logging). This variable is now used in the test suite, so that output from
    test programs can be piped to a log file and the network traces analysed
    later.
    
    The network logging uses libsoup's inbuilt logging facilities.
    Closes: bgo#605699

 README                           |   18 ++++++--
 docs/reference/gdata-docs.xml    |    1 +
 docs/reference/gdata-running.xml |   53 ++++++++++++++++++++++++++
 gdata/gdata-private.h            |   18 ++++++++-
 gdata/gdata-service.c            |   77 ++++++++++++++++++++++++++++++++++++++
 gdata/tests/Makefile.am          |    5 ++-
 gdata/tests/calendar.c           |    5 +--
 gdata/tests/common.c             |   36 ++++++++++++++++++
 gdata/tests/common.h             |    4 ++
 gdata/tests/contacts.c           |    5 +--
 gdata/tests/documents.c          |    5 +--
 gdata/tests/general.c            |    5 +-
 gdata/tests/picasaweb.c          |    5 +--
 gdata/tests/youtube.c            |    5 +--
 14 files changed, 212 insertions(+), 30 deletions(-)
---
diff --git a/README b/README
index 5fe0bb4..7a66aff 100644
--- a/README
+++ b/README
@@ -13,13 +13,13 @@ libgdata's API is currently unstable and is likely to change wildly.
 Dependencies
 ============
 
-* glib-2.0 >= 2.19.0
-* libxml-2.0
-* gio-2.0 >= 2.17.3
-* libsoup-2.4 >= 2.26.1
+ * glib-2.0 >= 2.19.0
+ * libxml-2.0
+ * gio-2.0 >= 2.17.3
+ * libsoup-2.4 >= 2.26.1
 
 If compiling with --enable-gnome (for GNOME support):
-* libsoup-gnome-2.4
+ * libsoup-gnome-2.4
 
 Environment variables
 =====================
@@ -28,6 +28,14 @@ If the environment variable LIBGDATA_FORCE_HTTP is defined, libgdata will
 force the use of HTTP for requests which would otherwise normally use
 HTTPS. This allows the network traffic to be debugged more easily.
 
+If the environment variable LIGDATA_DEBUG is set to one of the following
+values, libgdata will give debug output (at various levels):
+ 0: Output no debug messages or network logs
+ 1: Output debug messages, but not network logs
+ 2: Output debug messages and network traffic headers
+ 3: Output debug messages and full network traffic logs
+If LIBGDATA_DEBUG is unset, no debug output will be produced.
+
 Licensing
 =========
 
diff --git a/docs/reference/gdata-docs.xml b/docs/reference/gdata-docs.xml
index f2f241b..6c4a917 100644
--- a/docs/reference/gdata-docs.xml
+++ b/docs/reference/gdata-docs.xml
@@ -14,6 +14,7 @@
 	<part>
 		<title>GData Overview</title>
 		<xi:include href="gdata-overview.xml"/>
+		<xi:include href="gdata-running.xml"/>
 		<chapter>
 			<title>Object Hierarchy</title>
 			<xi:include href="xml/tree_index.sgml"/>
diff --git a/docs/reference/gdata-running.xml b/docs/reference/gdata-running.xml
new file mode 100644
index 0000000..4458497
--- /dev/null
+++ b/docs/reference/gdata-running.xml
@@ -0,0 +1,53 @@
+<?xml version="1.0"?>
+<!DOCTYPE book PUBLIC "-//OASIS//DTD DocBook XML V4.3//EN" "http://www.oasis-open.org/docbook/xml/4.3/docbookx.dtd";>
+<refentry id="gdata-running">
+	<refmeta>
+		<refentrytitle role="top_of_page" id="gdata-overview.top_of_page">Running GData Applications</refentrytitle>
+		<manvolnum>3</manvolnum>
+		<refmiscinfo>GDATA Library</refmiscinfo>
+	</refmeta>
+	<refnamediv>
+		<refname>Running GData Applications</refname>
+		<refpurpose>running and debugging GData applications</refpurpose>
+	</refnamediv>
+
+	<refsect1>
+		<title>Running and Debugging GData Applications</title>
+
+		<refsect2>
+			<title>Environment variables</title>
+			<para>libgdata makes use of a few environment variables which affect how it runs, mainly with respect to debugging.</para>
+
+			<formalpara id="LIBGDATA_FORCE_HTTP">
+				<title><envar>LIBGDATA_FORCE_HTTP</envar></title>
+				<para>If this environment variable is defined, libgdata will force the use of HTTP for requests which would otherwise
+					normally use HTTPS. This allows the network traffic to be debugged more easily.</para>
+			</formalpara>
+
+			<formalpara id="LIBGDATA_DEBUG">
+				<title><envar>LIBGDATA_DEBUG</envar></title>
+				<para>If this environment variable is set to one of the following values, libgdata will give debug output
+					(at various levels). If it's unset, no debug output will be produced.
+					<variablelist>
+						<varlistentry>
+							<term>0</term>
+							<listitem><para>Output no debug messages or network logs.</para></listitem>
+						</varlistentry>
+						<varlistentry>
+							<term>1</term>
+							<listitem><para>Output debug messages, but not network logs.</para></listitem>
+						</varlistentry>
+						<varlistentry>
+							<term>2</term>
+							<listitem><para>Output debug messages and network traffic headers.</para></listitem>
+						</varlistentry>
+						<varlistentry>
+							<term>3</term>
+							<listitem><para>Output debug messages and full network traffic logs.</para></listitem>
+						</varlistentry>
+					</variablelist>
+				</para>
+			</formalpara>
+		</refsect2>
+	</refsect1>
+</refentry>
diff --git a/gdata/gdata-private.h b/gdata/gdata-private.h
index 1c57a1c..68a4b7f 100644
--- a/gdata/gdata-private.h
+++ b/gdata/gdata-private.h
@@ -28,6 +28,22 @@
 
 G_BEGIN_DECLS
 
+/**
+ * GDataLogLevel:
+ * @GDATA_LOG_NONE: Output no debug messages or network logs
+ * @GDATA_LOG_MESSAGES: Output debug messages, but not network logs
+ * @GDATA_LOG_HEADERS: Output debug messages and network traffic headers
+ * @GDATA_LOG_FULL: Output debug messages and full network traffic logs
+ *
+ * Logging level.
+ **/
+typedef enum {
+	GDATA_LOG_NONE = 0,
+	GDATA_LOG_MESSAGES = 1,
+	GDATA_LOG_HEADERS = 2,
+	GDATA_LOG_FULL = 3
+} GDataLogLevel;
+
 #include "gdata-service.h"
 SoupSession *_gdata_service_get_session (GDataService *self);
 void _gdata_service_set_authenticated (GDataService *self, gboolean authenticated);
@@ -37,8 +53,8 @@ SoupMessage *_gdata_service_query (GDataService *self, const gchar *feed_uri, GD
 void _gdata_service_query_async (GDataService *self, const gchar *feed_uri, GDataQuery *query, GType entry_type, GCancellable *cancellable,
 				 GDataQueryProgressCallback progress_callback, gpointer progress_user_data,
 				 GAsyncReadyCallback callback, gpointer user_data, GSimpleAsyncThreadFunc query_thread);
-
 const gchar *_gdata_service_get_scheme (void);
+GDataLogLevel _gdata_service_get_log_level (void);
 
 #include "gdata-query.h"
 void _gdata_query_set_next_uri (GDataQuery *self, const gchar *next_uri);
diff --git a/gdata/gdata-service.c b/gdata/gdata-service.c
index 72e6b49..94c8299 100644
--- a/gdata/gdata-service.c
+++ b/gdata/gdata-service.c
@@ -67,6 +67,8 @@ static void real_append_query_headers (GDataService *self, SoupMessage *message)
 static void real_parse_error_response (GDataService *self, GDataOperationType operation_type, guint status, const gchar *reason_phrase,
                                        const gchar *response_body, gint length, GError **error);
 static void notify_proxy_uri_cb (GObject *gobject, GParamSpec *pspec, GObject *self);
+static void debug_handler (const char *log_domain, GLogLevelFlags log_level, const char *message, gpointer user_data);
+static void soup_log_printer (SoupLogger *logger, SoupLoggerLogLevel level, char direction, const char *data, gpointer user_data);
 
 struct _GDataServicePrivate {
 	SoupSession *session;
@@ -205,6 +207,33 @@ gdata_service_init (GDataService *self)
 	soup_session_add_feature_by_type (self->priv->session, SOUP_TYPE_GNOME_FEATURES_2_26);
 #endif /* HAVE_GNOME */
 
+	/* Debug log handling */
+	g_log_set_handler (G_LOG_DOMAIN, G_LOG_LEVEL_DEBUG, (GLogFunc) debug_handler, self);
+
+	/* Log all libsoup traffic if debugging's turned on */
+	if (_gdata_service_get_log_level () > GDATA_LOG_MESSAGES) {
+		SoupLoggerLogLevel level;
+		SoupLogger *logger;
+
+		switch (_gdata_service_get_log_level ()) {
+			case GDATA_LOG_FULL:
+				level = SOUP_LOGGER_LOG_BODY;
+				break;
+			case GDATA_LOG_HEADERS:
+				level = SOUP_LOGGER_LOG_HEADERS;
+				break;
+			case GDATA_LOG_MESSAGES:
+			case GDATA_LOG_NONE:
+			default:
+				g_assert_not_reached ();
+		}
+
+		logger = soup_logger_new (level, -1);
+		soup_logger_set_printer (logger, (SoupLoggerPrinter) soup_log_printer, self, NULL);
+
+		soup_session_add_feature (self->priv->session, SOUP_SESSION_FEATURE (logger));
+	}
+
 	/* Proxy the SoupSession's proxy-uri property */
 	g_signal_connect (self->priv->session, "notify::proxy-uri", (GCallback) notify_proxy_uri_cb, self);
 }
@@ -1763,3 +1792,51 @@ _gdata_service_get_scheme (void)
 		return "http";
 	return "https";
 }
+
+/*
+ * debug_handler:
+ *
+ * GLib debug message handler, which is passed all messages from g_debug() calls, and decides whether to print them.
+ */
+static void
+debug_handler (const char *log_domain, GLogLevelFlags log_level, const char *message, gpointer user_data)
+{
+	if (_gdata_service_get_log_level () != GDATA_LOG_NONE)
+		g_log_default_handler (log_domain, log_level, message, NULL);
+}
+
+/*
+ * soup_log_printer:
+ *
+ * Log printer for the libsoup logging functionality, which just marshals all soup log output to the standard GLib logging framework
+ * (and thus to debug_handler(), above).
+ */
+static void
+soup_log_printer (SoupLogger *logger, SoupLoggerLogLevel level, char direction, const char *data, gpointer user_data)
+{
+	g_debug ("%c %s", direction, data);
+}
+
+/**
+ * _gdata_service_get_log_level:
+ *
+ * Returns the logging level for the library, currently set by an environment variable.
+ *
+ * Return value: the log level
+ *
+ * Since: 0.7.0
+ **/
+GDataLogLevel
+_gdata_service_get_log_level (void)
+{
+	static int level = -1;
+
+	if (level < 0) {
+		const gchar *envvar = g_getenv ("LIBGDATA_DEBUG");
+		if (envvar != NULL)
+			level = atoi (envvar);
+		level = MIN (MAX (level, 0), GDATA_LOG_FULL);
+	}
+
+	return level;
+}
diff --git a/gdata/tests/Makefile.am b/gdata/tests/Makefile.am
index 4bbc6f4..27ae57a 100644
--- a/gdata/tests/Makefile.am
+++ b/gdata/tests/Makefile.am
@@ -5,6 +5,7 @@ INCLUDES = \
 	-I$(top_srcdir)/gdata				\
 	$(GDK_CFLAGS)					\
 	-DTEST_FILE_DIR="\"$(top_srcdir)/gdata/tests/\""\
+	-DG_LOG_DOMAIN=\"libgdata\"			\
 	$(DISABLE_DEPRECATED)				\
 	$(WARN_CFLAGS)					\
 	$(GDATA_CFLAGS)
@@ -16,7 +17,9 @@ LIBS = \
 
 noinst_PROGRAMS = $(TEST_PROGS)
 
-TEST_SRCS = common.h
+TEST_SRCS = \
+	common.c	\
+	common.h
 
 TEST_PROGS			+= general
 general_SOURCES			 = general.c $(TEST_SRCS)
diff --git a/gdata/tests/calendar.c b/gdata/tests/calendar.c
index 57104c9..80aebde 100644
--- a/gdata/tests/calendar.c
+++ b/gdata/tests/calendar.c
@@ -703,10 +703,7 @@ main (int argc, char *argv[])
 	gint retval;
 	GDataService *service;
 
-	g_type_init ();
-	g_thread_init (NULL);
-	g_test_init (&argc, &argv, NULL);
-	g_test_bug_base ("http://bugzilla.gnome.org/show_bug.cgi?id=";);
+	gdata_test_init (&argc, &argv);
 
 	service = GDATA_SERVICE (gdata_calendar_service_new (CLIENT_ID));
 	gdata_service_authenticate (service, USERNAME, PASSWORD, NULL, NULL);
diff --git a/gdata/tests/common.c b/gdata/tests/common.c
new file mode 100644
index 0000000..867a5b9
--- /dev/null
+++ b/gdata/tests/common.c
@@ -0,0 +1,36 @@
+/* -*- Mode: C; indent-tabs-mode: t; c-basic-offset: 8; tab-width: 8 -*- */
+/*
+ * GData Client
+ * Copyright (C) Philip Withnall 2010 <philip tecnocode co uk>
+ *
+ * GData Client is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU Lesser General Public
+ * License as published by the Free Software Foundation; either
+ * version 2.1 of the License, or (at your option) any later version.
+ *
+ * GData Client is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
+ * Lesser General Public License for more details.
+ *
+ * You should have received a copy of the GNU Lesser General Public
+ * License along with GData Client.  If not, see <http://www.gnu.org/licenses/>.
+ */
+
+#include <glib.h>
+#include <glib-object.h>
+#include <stdio.h>
+
+#include "common.h"
+
+void
+gdata_test_init (int *argc, char ***argv)
+{
+	g_type_init ();
+	g_thread_init (NULL);
+	g_test_init (argc, argv, NULL);
+	g_test_bug_base ("http://bugzilla.gnome.org/show_bug.cgi?id=";);
+
+	/* Enable full debugging */
+	g_setenv ("LIBGDATA_DEBUG", "3", FALSE);
+}
diff --git a/gdata/tests/common.h b/gdata/tests/common.h
index 745b9e8..56ce80d 100644
--- a/gdata/tests/common.h
+++ b/gdata/tests/common.h
@@ -17,6 +17,8 @@
  * License along with GData Client.  If not, see <http://www.gnu.org/licenses/>.
  */
 
+#include <glib.h>
+
 #ifndef GDATA_TEST_COMMON_H
 #define GDATA_TEST_COMMON_H
 
@@ -27,6 +29,8 @@ G_BEGIN_DECLS
 #define DOCUMENTS_USERNAME "libgdata documents gmail com"
 #define PASSWORD "gdata-libgdata"
 
+void gdata_test_init (int *argc, char ***argv);
+
 G_END_DECLS
 
 #endif /* !GDATA_TEST_COMMON_H */
diff --git a/gdata/tests/contacts.c b/gdata/tests/contacts.c
index 3e4deb1..e30427c 100644
--- a/gdata/tests/contacts.c
+++ b/gdata/tests/contacts.c
@@ -626,10 +626,7 @@ main (int argc, char *argv[])
 	GDataService *service;
 	gint retval;
 
-	g_type_init ();
-	g_thread_init (NULL);
-	g_test_init (&argc, &argv, NULL);
-	g_test_bug_base ("http://bugzilla.gnome.org/show_bug.cgi?id=";);
+	gdata_test_init (&argc, &argv);
 
 	service = GDATA_SERVICE (gdata_contacts_service_new (CLIENT_ID));
 	gdata_service_authenticate (service, USERNAME, PASSWORD, NULL, NULL);
diff --git a/gdata/tests/documents.c b/gdata/tests/documents.c
index 7129b49..e00b520 100644
--- a/gdata/tests/documents.c
+++ b/gdata/tests/documents.c
@@ -593,10 +593,7 @@ main (int argc, char *argv[])
 	GDataService *service;
 	gint retval;
 
-	g_type_init ();
-	g_thread_init (NULL);
-	g_test_init (&argc, &argv, NULL);
-	g_test_bug_base ("http://bugzilla.gnome.org/show_bug.cgi?id=";);
+	gdata_test_init (&argc, &argv);
 
 	service = GDATA_SERVICE (gdata_documents_service_new (CLIENT_ID));
 	gdata_service_authenticate (service, DOCUMENTS_USERNAME, PASSWORD, NULL, NULL);
diff --git a/gdata/tests/general.c b/gdata/tests/general.c
index 412248e..7c6b176 100644
--- a/gdata/tests/general.c
+++ b/gdata/tests/general.c
@@ -21,6 +21,7 @@
 #include <locale.h>
 
 #include "gdata.h"
+#include "common.h"
 
 static void
 test_entry_get_xml (void)
@@ -2219,9 +2220,7 @@ test_media_thumbnail (void)
 int
 main (int argc, char *argv[])
 {
-	g_type_init ();
-	g_test_init (&argc, &argv, NULL);
-	g_test_bug_base ("http://bugzilla.gnome.org/show_bug.cgi?id=";);
+	gdata_test_init (&argc, &argv);
 
 	g_test_add_func ("/entry/get_xml", test_entry_get_xml);
 	g_test_add_func ("/entry/parse_xml", test_entry_parse_xml);
diff --git a/gdata/tests/picasaweb.c b/gdata/tests/picasaweb.c
index 371bd5b..083bca5 100644
--- a/gdata/tests/picasaweb.c
+++ b/gdata/tests/picasaweb.c
@@ -1292,10 +1292,7 @@ main (int argc, char *argv[])
 	GDataService *service;
 	gint retval;
 
-	g_type_init ();
-	g_thread_init (NULL);
-	g_test_init (&argc, &argv, NULL);
-	g_test_bug_base ("http://bugzilla.gnome.org/show_bug.cgi?id=";);
+	gdata_test_init (&argc, &argv);
 
 	service = GDATA_SERVICE (gdata_picasaweb_service_new (CLIENT_ID));
 	gdata_service_authenticate (service, PW_USERNAME, PASSWORD, NULL, NULL);
diff --git a/gdata/tests/youtube.c b/gdata/tests/youtube.c
index 755779f..557ac8a 100644
--- a/gdata/tests/youtube.c
+++ b/gdata/tests/youtube.c
@@ -653,10 +653,7 @@ main (int argc, char *argv[])
 	gint retval;
 	GDataService *service;
 
-	g_type_init ();
-	g_thread_init (NULL);
-	g_test_init (&argc, &argv, NULL);
-	g_test_bug_base ("http://bugzilla.gnome.org/show_bug.cgi?id=";);
+	gdata_test_init (&argc, &argv);
 
 	service = GDATA_SERVICE (gdata_youtube_service_new (DEVELOPER_KEY, CLIENT_ID));
 	gdata_service_authenticate (service, YT_USERNAME, YT_PASSWORD, NULL, NULL);



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