From a6a7c43c14272d0353330fecdf9c8aa557afa6a0 Mon Sep 17 00:00:00 2001 From: M66B Date: Wed, 15 Jul 2020 18:58:03 +0200 Subject: [PATCH] Added sync stats --- .../email/BoundaryCallbackMessages.java | 2 +- app/src/main/java/eu/faircode/email/Core.java | 79 +++++++++++++++---- 2 files changed, 66 insertions(+), 15 deletions(-) diff --git a/app/src/main/java/eu/faircode/email/BoundaryCallbackMessages.java b/app/src/main/java/eu/faircode/email/BoundaryCallbackMessages.java index a37e657cb8..7d63fc03c9 100644 --- a/app/src/main/java/eu/faircode/email/BoundaryCallbackMessages.java +++ b/app/src/main/java/eu/faircode/email/BoundaryCallbackMessages.java @@ -499,7 +499,7 @@ public class BoundaryCallbackMessages extends PagedList.BoundaryCallback rules = db.rule().getEnabledRules(folder.id); try { + SyncStats stats = new SyncStats(); + MimeMessage imessage = (MimeMessage) ifolder.getMessageByUID(uid); if (imessage == null) throw new MessageRemovedException(); @@ -1115,7 +1117,7 @@ class Core { } ifolder.fetch(new Message[]{imessage}, fp); - EntityMessage message = synchronizeMessage(context, account, folder, istore, ifolder, imessage, false, download, rules, state); + EntityMessage message = synchronizeMessage(context, account, folder, istore, ifolder, imessage, false, download, rules, state, stats); if (message != null) { if (account.isGmail() && EntityFolder.USER.equals(folder.type)) try { @@ -1128,8 +1130,10 @@ class Core { } if (download) - downloadMessage(context, account, folder, istore, ifolder, imessage, message.id, state); + downloadMessage(context, account, folder, istore, ifolder, imessage, message.id, state, stats); } + + EntityLog.log(context, folder.name + " fetch stats " + stats); } finally { ((IMAPMessage) imessage).invalidateHeaders(); } @@ -1362,6 +1366,9 @@ class Core { parts.isPlainOnly(), HtmlHelper.getPreview(body), parts.getWarnings(message.warning)); + + if (body != null) + EntityLog.log(context, "Operation body size=" + body.length()); } private static void onAttachment(Context context, JSONArray jargs, EntityFolder folder, EntityMessage message, EntityOperation op, IMAPFolder ifolder) throws JSONException, MessagingException, IOException { @@ -1390,6 +1397,9 @@ class Core { // Download attachment parts.downloadAttachment(context, attachment); + + if (attachment.size != null) + EntityLog.log(context, "Operation attachment size=" + attachment.size); } private static void onExists(Context context, JSONArray jargs, EntityFolder folder, EntityMessage message, EntityOperation op, IMAPFolder ifolder) throws MessagingException { @@ -1950,6 +1960,8 @@ class Core { IMAPStore istore, final IMAPFolder ifolder, State state) throws JSONException, MessagingException, IOException { final DB db = DB.getInstance(context); try { + SyncStats stats = new SyncStats(); + // Legacy if (jargs.length() == 0) jargs = folder.getSyncArgs(); @@ -2059,9 +2071,11 @@ class Core { } if (imessages == null) imessages = new Message[0]; - Log.i(folder.name + " remote count=" + imessages.length + - " search=" + (SystemClock.elapsedRealtime() - search) + " ms"); + stats.search_ms = (SystemClock.elapsedRealtime() - search); + Log.i(folder.name + " remote count=" + imessages.length + " search=" + stats.search_ms + " ms"); + + long fetch = SystemClock.elapsedRealtime(); FetchProfile fp = new FetchProfile(); fp.add(UIDFolder.FetchProfileItem.UID); // To check if message exists fp.add(FetchProfile.Item.FLAGS); // To update existing messages @@ -2069,8 +2083,9 @@ class Core { fp.add(GmailFolder.FetchProfileItem.LABELS); ifolder.fetch(imessages, fp); - long fetch = SystemClock.elapsedRealtime(); - Log.i(folder.name + " remote fetched=" + (SystemClock.elapsedRealtime() - fetch) + " ms"); + stats.flags = imessages.length; + stats.flags_ms = (SystemClock.elapsedRealtime() - fetch); + Log.i(folder.name + " remote fetched=" + stats.flags_ms + " ms"); // Sort for finding referenced/replied-to messages // Sorting on date/time would be better, but requires fetching the headers @@ -2102,6 +2117,7 @@ class Core { if (!ifolder.isOpen()) throw new FolderClosedException(ifolder, "UID FETCH"); + long getuid = SystemClock.elapsedRealtime(); MessagingException ex = (MessagingException) ifolder.doCommand(new IMAPFolder.ProtocolCommand() { @Override public Object doCommand(IMAPProtocol protocol) { @@ -2173,8 +2189,9 @@ class Core { if (ex != null) throw ex; - long getuid = SystemClock.elapsedRealtime(); - Log.i(folder.name + " remote uids=" + (SystemClock.elapsedRealtime() - getuid) + " ms"); + stats.uids = uids.size(); + stats.uids_ms = (SystemClock.elapsedRealtime() - getuid); + Log.i(folder.name + " remote uids=" + stats.uids_ms + " ms"); } // Delete local messages not at remote @@ -2215,8 +2232,9 @@ class Core { if (full.size() > 0) { long headers = SystemClock.elapsedRealtime(); ifolder.fetch(full.toArray(new Message[0]), fp); - Log.i(folder.name + " fetched headers=" + full.size() + - " " + (SystemClock.elapsedRealtime() - headers) + " ms"); + stats.headers += full.size(); + stats.headers_ms += (SystemClock.elapsedRealtime() - headers); + Log.i(folder.name + " fetched headers=" + full.size() + " " + stats.headers_ms + " ms"); } int free = Log.getFreeMemMb(); @@ -2250,7 +2268,7 @@ class Core { account, folder, istore, ifolder, (MimeMessage) isub[j], false, download && initialize == 0, - rules, state); + rules, state, stats); ids[from + j] = (message == null || message.ui_hide ? null : message.id); } catch (MessageRemovedException ex) { Log.w(folder.name, ex); @@ -2318,7 +2336,8 @@ class Core { context, account, folder, istore, ifolder, - (MimeMessage) isub[j], ids[from + j], state); + (MimeMessage) isub[j], ids[from + j], + state, stats); } catch (FolderClosedException ex) { throw ex; } catch (Throwable ex) { @@ -2351,6 +2370,8 @@ class Core { db.folder().setFolderLastSync(folder.id, new Date().getTime()); db.folder().setFolderError(folder.id, null); + stats.total = (SystemClock.elapsedRealtime() - search); + EntityLog.log(context, folder.name + " sync stats " + stats); } finally { Log.i(folder.name + " end sync state=" + state); db.folder().setFolderSyncState(folder.id, null); @@ -2362,7 +2383,7 @@ class Core { EntityAccount account, EntityFolder folder, IMAPStore istore, IMAPFolder ifolder, MimeMessage imessage, boolean browsed, boolean download, - List rules, State state) throws MessagingException, IOException { + List rules, State state, SyncStats stats) throws MessagingException, IOException { long uid = ifolder.getUID(imessage); if (uid < 0) { @@ -2672,6 +2693,8 @@ class Core { parts.isPlainOnly(), HtmlHelper.getPreview(body), parts.getWarnings(message.warning)); + if (stats != null && body != null) + stats.content += body.length(); Log.i(folder.name + " inline downloaded message id=" + message.id + " size=" + message.size + "/" + (body == null ? null : body.length())); @@ -2996,7 +3019,7 @@ class Core { Context context, EntityAccount account, EntityFolder folder, IMAPStore istore, IMAPFolder ifolder, - MimeMessage imessage, long id, State state) throws MessagingException, IOException { + MimeMessage imessage, long id, State state, SyncStats stats) throws MessagingException, IOException { if (state.getNetworkState().isRoaming()) return; @@ -3060,6 +3083,8 @@ class Core { parts.isPlainOnly(), HtmlHelper.getPreview(body), parts.getWarnings(message.warning)); + if (stats != null && body != null) + stats.content += body.length(); Log.i(folder.name + " downloaded message id=" + message.id + " size=" + message.size + "/" + (body == null ? null : body.length())); @@ -3074,6 +3099,8 @@ class Core { (attachment.size != null && attachment.size < maxSize)) try { parts.downloadAttachment(context, attachment); + if (stats != null && attachment.size != null) + stats.attachments += attachment.size; } catch (Throwable ex) { Log.e(folder.name, ex); db.attachment().setError(attachment.id, Log.formatThrowable(ex, false)); @@ -4045,4 +4072,28 @@ class Core { } } } + + private static class SyncStats { + long search_ms; + int flags; + int uids; + long flags_ms; + long uids_ms; + int headers; + long headers_ms; + long content; + long attachments; + long total; + + @Override + public String toString() { + return "search=" + search_ms + " ms" + + " flags=" + flags + "/" + flags_ms + " ms" + + " uids=" + uids + "/" + uids_ms + " ms" + + " headers=" + headers + "/" + headers_ms + " ms" + + " content=" + Helper.humanReadableByteCount(content) + + " attachments=" + Helper.humanReadableByteCount(attachments) + + " total=" + total; + } + } }