[evolution/webkit: 80/177] Port http data cache.
- From: Dan VrÃtil <dvratil src gnome org>
- To: commits-list gnome org
- Cc:
- Subject: [evolution/webkit: 80/177] Port http data cache.
- Date: Fri, 2 Mar 2012 11:36:22 +0000 (UTC)
commit f0e1cf429719b0926e44c1af93f5f2a5bfb809bf
Author: Dan VrÃtil <dvratil redhat com>
Date: Thu Dec 15 11:29:52 2011 +0100
Port http data cache.
EMFormatHTML used to have cache for external resources requested
via http protocol. Since EMFormat does not take care of these things
anymore, I moved the cache to EMailDisplay, which holds EWebViews
who do the http requests automatically, thus managing the cache from
there makes more sense.
mail/e-mail-display.c | 156 +++++++++++++++++++++++++++++++++-------
mail/em-format-html-display.c | 29 +++++---
mail/em-format-html.c | 31 +--------
mail/em-format-html.h | 4 -
4 files changed, 149 insertions(+), 71 deletions(-)
---
diff --git a/mail/e-mail-display.c b/mail/e-mail-display.c
index aca8265..fcefaed 100644
--- a/mail/e-mail-display.c
+++ b/mail/e-mail-display.c
@@ -38,6 +38,8 @@
#include "mail/e-mail-attachment-bar.h"
#include "widgets/misc/e-attachment-button.h"
+#include <camel/camel.h>
+
#include <libsoup/soup.h>
#include <libsoup/soup-requester.h>
@@ -70,6 +72,8 @@ enum {
static gpointer parent_class;
+static CamelDataCache *emd_global_http_cache = 0;
+
typedef void (*WebViewActionFunc) (EWebView *web_view);
static const gchar *ui =
@@ -358,6 +362,96 @@ mail_display_link_clicked (WebKitWebView *web_view,
}
static void
+webkit_request_load_from_file (WebKitNetworkRequest *request,
+ const gchar *path)
+{
+ gchar *data = NULL;
+ gsize length = 0;
+ gboolean status;
+ gchar *b64, *new_uri;
+ gchar *ct;
+
+ status = g_file_get_contents (path, &data, &length, NULL);
+ if (!status)
+ return;
+
+ b64 = g_base64_encode ((guchar*) data, length);
+ ct = g_content_type_guess (path, NULL, 0, NULL);
+
+ new_uri = g_strdup_printf ("data:%s;base64,%s", ct, b64);
+ webkit_network_request_set_uri (request, new_uri);
+
+ g_free (b64);
+ g_free (new_uri);
+ g_free (ct);
+ g_free (data);
+}
+
+static void
+add_resource_to_cache (WebKitWebResource *resource)
+{
+
+ /* Make sure this URI is not yet in cache */
+ if (!camel_data_cache_get (emd_global_http_cache, "http",
+ webkit_web_resource_get_uri (resource), NULL)) {
+
+ CamelStream *stream;
+ GString *data;
+ gssize len = 0;
+
+ /* Create cache item */
+ stream = camel_data_cache_add (emd_global_http_cache, "http",
+ webkit_web_resource_get_uri (resource), NULL);
+ if (!stream)
+ return;
+
+ /* Write content of the resource to the cache */
+ data = webkit_web_resource_get_data (resource);
+ len = camel_stream_write_string (stream, data->str, NULL, NULL);
+
+ /* Don't store invalid data in cache */
+ if (len != data->len) {
+ camel_data_cache_remove (emd_global_http_cache, "http",
+ webkit_web_resource_get_uri (resource), NULL);
+ }
+ }
+}
+
+static void
+mail_display_webkit_finished (GObject *object,
+ GParamSpec *pspec,
+ gpointer user_data)
+{
+ WebKitLoadStatus status;
+ WebKitWebView *web_view;
+ WebKitWebFrame *frame;
+ WebKitWebDataSource *data_source;
+ WebKitWebResource *subresource;
+ GList *iter, *subresources;
+
+ /* Wait until all resources in webview are fully downloaded. */
+ g_object_get (object, "load-status", &status, NULL);
+ if (status != WEBKIT_LOAD_FINISHED)
+ return;
+
+ web_view = WEBKIT_WEB_VIEW (object);
+ frame = webkit_web_view_get_main_frame (web_view);
+ data_source = webkit_web_frame_get_data_source (frame);
+
+ /* Store in cache the main resource, content of the frame itself */
+ subresource = webkit_web_data_source_get_main_resource (data_source);
+ add_resource_to_cache (subresource);
+
+ /* Store all subresources (images, subframes, ...) */
+ subresources = webkit_web_data_source_get_subresources (data_source);
+ for (iter = subresources; iter; iter = iter->next) {
+ subresource = iter->data;
+ add_resource_to_cache (subresource);
+ }
+}
+
+
+static void
mail_display_resource_requested (WebKitWebView *web_view,
WebKitWebFrame *frame,
WebKitWebResource *resource,
@@ -371,7 +465,7 @@ mail_display_resource_requested (WebKitWebView *web_view,
/* Redirect cid:part_id to mail://mail_id/cid:part_id */
if (g_str_has_prefix (uri, "cid:")) {
- gchar *new_uri = em_format_build_mail_uri (EM_FORMAT (formatter)->folder,
+ gchar *new_uri = em_format_build_mail_uri (EM_FORMAT (formatter)->folder,
EM_FORMAT (formatter)->message_uid,
"part_id", G_TYPE_STRING, uri, NULL);
@@ -382,33 +476,28 @@ mail_display_resource_requested (WebKitWebView *web_view,
/* WebKit won't allow to load a local file when displaing "remote" mail://,
protocol, so we need to handle this manually */
} else if (g_str_has_prefix (uri, "file:")) {
- gchar *data = NULL;
- gsize length = 0;
- gboolean status;
- gchar *path;
-
- path = g_filename_from_uri (uri, NULL, NULL);
- if (!path)
- return;
-
- status = g_file_get_contents (path, &data, &length, NULL);
- if (status) {
- gchar *b64, *new_uri;
- gchar *ct;
-
- b64 = g_base64_encode ((guchar*) data, length);
- ct = g_content_type_guess (path, NULL, 0, NULL);
-
- new_uri = g_strdup_printf ("data:%s;base64,%s", ct, b64);
- webkit_network_request_set_uri (request, new_uri);
-
- g_free (b64);
- g_free (new_uri);
- g_free (ct);
- }
- g_free (data);
- g_free (path);
- }
+ gchar *path;
+
+ path = g_filename_from_uri (uri, NULL, NULL);
+ if (!path)
+ return;
+
+ webkit_request_load_from_file (request, path);
+
+ g_free (path);
+
+ /* Try to lookup content of any http(s) request in camel cache. */
+ } else if (g_str_has_prefix (uri, "http:") || g_str_has_prefix (uri, "https")) {
+
+ gchar *path = camel_data_cache_get_filename (emd_global_http_cache,
+ "http", uri, NULL);
+
+ /* Found cache file, load the request from cache. */
+ if (path) {
+ webkit_request_load_from_file (request, path);
+ g_free (path);
+ }
+ }
}
static void
@@ -455,6 +544,8 @@ mail_display_setup_webview (EMailDisplay *display)
G_CALLBACK (mail_display_resource_requested), display);
g_signal_connect (web_view, "process-mailto",
G_CALLBACK (mail_display_process_mailto), display);
+ g_signal_connect (web_view, "notify::load-status",
+ G_CALLBACK (mail_display_webkit_finished), NULL);
/* EWebView's action groups are added during its instance
* initialization function (like what we're in now), so it
@@ -786,6 +877,7 @@ mail_display_init (EMailDisplay *display)
{
SoupSession *session;
SoupSessionFeature *feature;
+ const gchar *user_cache_dir;
display->priv = E_MAIL_DISPLAY_GET_PRIVATE (display);
@@ -804,6 +896,14 @@ mail_display_init (EMailDisplay *display)
soup_session_feature_add_feature (feature, E_TYPE_MAIL_REQUEST);
soup_session_add_feature (session, feature);
g_object_unref (feature);
+
+ /* cache expiry - 2 hour access, 1 day max */
+ user_cache_dir = e_get_user_cache_dir ();
+ emd_global_http_cache = camel_data_cache_new (user_cache_dir, NULL);
+ if (emd_global_http_cache) {
+ camel_data_cache_set_expire_age (emd_global_http_cache, 24*60*60);
+ camel_data_cache_set_expire_access (emd_global_http_cache, 2*60*60);
+ }
}
GType
diff --git a/mail/em-format-html-display.c b/mail/em-format-html-display.c
index 6cd4beb..3672674 100644
--- a/mail/em-format-html-display.c
+++ b/mail/em-format-html-display.c
@@ -700,12 +700,18 @@ action_image_save_cb (GtkAction *action,
} else {
CamelStream *image_stream;
CamelDataWrapper *dw;
+ CamelDataCache *cache;
const gchar *filename;
-
- image_stream = em_format_html_get_cached_image (
- EM_FORMAT_HTML (efhd), image_src);
- if (!image_stream)
+ const gchar *user_cache_dir;
+
+ /* Open cache and find the file there */
+ user_cache_dir = e_get_user_cache_dir ();
+ cache = camel_data_cache_new (user_cache_dir, NULL);
+ image_stream = camel_data_cache_get (cache, "http", image_src, NULL);
+ if (!image_stream) {
+ g_object_unref (cache);
return;
+ }
filename = strrchr (image_src, '/');
if (filename && strchr (filename, '?'))
@@ -729,6 +735,7 @@ action_image_save_cb (GtkAction *action,
part, CAMEL_TRANSFER_ENCODING_BASE64);
g_object_unref (image_stream);
+ g_object_unref (cache);
}
file = e_shell_run_save_dialog (
@@ -764,14 +771,20 @@ efhd_web_view_update_actions_cb (EWebView *web_view,
image_src = e_web_view_get_cursor_image_src (web_view);
visible = image_src && g_str_has_prefix (image_src, "cid:");
if (!visible && image_src) {
+ CamelDataCache *cache;
CamelStream *image_stream;
+ const gchar *user_cache_dir;
+
+ user_cache_dir = e_get_user_cache_dir ();
+ cache = camel_data_cache_new (user_cache_dir, NULL);
+ image_stream = camel_data_cache_get (cache, "http", image_src, NULL);
- image_stream = em_format_html_get_cached_image (
- EM_FORMAT_HTML (efhd), image_src);
visible = image_stream != NULL;
if (image_stream)
g_object_unref (image_stream);
+
+ g_object_unref (cache);
}
action = e_web_view_get_action (web_view, "efhd-image-save");
@@ -1005,8 +1018,6 @@ efhd_attachment_button (EMFormat *emf,
GCancellable *cancellable)
{
EMFormatAttachmentPURI *info = (EMFormatAttachmentPURI *) puri;
- EMFormatHTML *efh = (EMFormatHTML *) emf;
- EMFormatHTMLDisplay *efhd = (EMFormatHTMLDisplay *) efh;
GtkWidget *widget;
/* FIXME: handle default shown case */
@@ -1034,7 +1045,6 @@ efhd_attachment_bar (EMFormat *emf,
EMFormatPURI *puri,
GCancellable *cancellable)
{
- EMFormatHTMLDisplay *efhd = (EMFormatHTMLDisplay*) emf;
EMFormatAttachmentBarPURI *abp = (EMFormatAttachmentBarPURI *) puri;
GtkWidget *widget;
@@ -1083,7 +1093,6 @@ efhd_message_add_bar (EMFormat *emf,
EMFormatParserInfo *info,
GCancellable *cancellable)
{
- gchar *classid;
EMFormatAttachmentBarPURI *puri;
gint len;
diff --git a/mail/em-format-html.c b/mail/em-format-html.c
index b6610c7..dbb31b1 100644
--- a/mail/em-format-html.c
+++ b/mail/em-format-html.c
@@ -1425,16 +1425,7 @@ efh_class_init (EMFormatHTMLClass *class)
GDK_TYPE_COLOR,
G_PARAM_READWRITE));
- /* cache expiry - 2 hour access, 1 day max */
-
- /* FIXME WEBKIT - this emfh_http_cache is not used anywhere - remove?
- user_cache_dir = e_get_user_cache_dir ();
- emfh_http_cache = camel_data_cache_new (user_cache_dir, NULL);
- if (emfh_http_cache) {
- camel_data_cache_set_expire_age (emfh_http_cache, 24*60*60);
- camel_data_cache_set_expire_access (emfh_http_cache, 2*60*60);
- }
- */
+
}
static void
@@ -2509,22 +2500,4 @@ efh_format_full_headers (EMFormatHTML *efh,
g_string_append (output_buffer, ">");
g_string_append (output_buffer, cinfo->email);
}
- }
-
-/* unref returned pointer with g_object_unref(), if not NULL */
-CamelStream *
-em_format_html_get_cached_image (EMFormatHTML *efh,
- const gchar *image_uri)
-{
- g_return_val_if_fail (efh != NULL, NULL);
- g_return_val_if_fail (image_uri != NULL, NULL);
-
- /* FIXME WEBKIT This has not been ported yet
- if (!emfh_http_cache)
- return NULL;
-
- return camel_data_cache_get (
- emfh_http_cache, EMFH_HTTP_CACHE_PATH, image_uri, NULL);
- */
- return NULL;
-}
+ }
\ No newline at end of file
diff --git a/mail/em-format-html.h b/mail/em-format-html.h
index 56b67ec..f3fb33d 100644
--- a/mail/em-format-html.h
+++ b/mail/em-format-html.h
@@ -184,10 +184,6 @@ CamelMimePart * em_format_html_file_part (EMFormatHTML *efh,
gchar * em_format_html_format_cert_infos
(CamelCipherCertInfo *first_cinfo);
-CamelStream *
- em_format_html_get_cached_image (EMFormatHTML *efh,
- const gchar *image_uri);
-
void em_format_html_format_message (EMFormatHTML *efh,
CamelStream *stream,
GCancellable *cancellable);
[
Date Prev][
Date Next] [
Thread Prev][
Thread Next]
[
Thread Index]
[
Date Index]
[
Author Index]