[geary/wip/problem-report-logs: 22/22] Improve formatting of Inspector/problem report data for GitLab



commit fe754827494079462e26291bcd73605678b35507
Author: Michael Gratton <mike vee net>
Date:   Fri Jul 5 11:45:57 2019 +1000

    Improve formatting of Inspector/problem report data for GitLab
    
    Format Inspector and problem report data copied to the clipboard as
    Markdown so that people who copy and paste into bug reports have it
    automatically formatted properly.

 .../components-inspector-error-view.vala           | 63 +++++++++++++---------
 .../components/components-inspector-log-view.vala  | 11 +++-
 .../components-inspector-system-view.vala          | 21 +++++---
 src/client/components/components-inspector.vala    | 22 +++++---
 .../dialogs/dialogs-problem-details-dialog.vala    | 30 +++++++----
 5 files changed, 98 insertions(+), 49 deletions(-)
---
diff --git a/src/client/components/components-inspector-error-view.vala 
b/src/client/components/components-inspector-error-view.vala
index 2850701a..4ec50f74 100644
--- a/src/client/components/components-inspector-error-view.vala
+++ b/src/client/components/components-inspector-error-view.vala
@@ -15,58 +15,73 @@ public class Components.InspectorErrorView : Gtk.Grid {
     [GtkChild]
     private Gtk.TextView problem_text;
 
-    private string details;
+    private Geary.ErrorContext error;
+    private Geary.AccountInformation? account;
+    private Geary.ServiceInformation? service;
 
 
     public InspectorErrorView(Geary.ErrorContext error,
                               Geary.AccountInformation? account,
                               Geary.ServiceInformation? service) {
-        this.details = format_problem(error, account, service);
-        this.problem_text.buffer.text = this.details;
+        this.error = error;
+        this.account = account;
+        this.service = service;
+
+        this.problem_text.buffer.text = format_problem(
+            Inspector.TextFormat.PLAIN
+        );
     }
 
-    public void save(GLib.DataOutputStream out, GLib.Cancellable? cancellable)
+    public void save(GLib.DataOutputStream out,
+                     Inspector.TextFormat format,
+                     GLib.Cancellable? cancellable)
         throws GLib.Error {
-        out.put_string(this.details, cancellable);
+            out.put_string(format_problem(format), cancellable);
     }
 
-    private string format_problem(Geary.ErrorContext error,
-                                  Geary.AccountInformation? account,
-                                  Geary.ServiceInformation? service) {
+    private string format_problem(Inspector.TextFormat format) {
+        string line_sep = format.get_line_separator();
         StringBuilder details = new StringBuilder();
-        if (account != null) {
+        if (this.account != null) {
             details.append_printf(
-                "Account id: %s\n",
-                account.id
+                "Account identifier: %s", this.account.id
             );
+            details.append(line_sep);
             details.append_printf(
-                "Account provider: %s\n",
-                account.service_provider.to_string()
+                "Account provider: %s", this.account.service_provider.to_string()
             );
+            details.append(line_sep);
         }
-        if (service != null) {
+        if (this.service != null) {
             details.append_printf(
-                "Service type: %s\n",
-                service.protocol.to_string()
+                "Service type: %s", this.service.protocol.to_string()
             );
+            details.append(line_sep);
             details.append_printf(
-                "Service host: %s\n",
-                service.host
+                "Service host: %s", this.service.host
             );
+            details.append(line_sep);
         }
-        if (error == null) {
+        if (this.error == null) {
             details.append("No error reported");
+            details.append(line_sep);
         } else {
             details.append_printf(
-                "Error type: %s\n", error.format_error_type()
+                "Error type: %s", this.error.format_error_type()
             );
+            details.append(line_sep);
             details.append_printf(
-                "Message: %s\n", error.thrown.message
+                "Message: %s", this.error.thrown.message
             );
-            details.append("Back trace:\n");
+            details.append(line_sep);
+
+            details.append_c('\n');
+            details.append("Back trace:");
+            details.append(line_sep);
             foreach (Geary.ErrorContext.StackFrame frame in
-                     error.backtrace) {
-                details.append_printf(" - %s\n", frame.to_string());
+                     this.error.backtrace) {
+                details.append_printf(" * %s", frame.to_string());
+                details.append(line_sep);
             }
         }
         return details.str;
diff --git a/src/client/components/components-inspector-log-view.vala 
b/src/client/components/components-inspector-log-view.vala
index 8bb5cea4..e61895cf 100644
--- a/src/client/components/components-inspector-log-view.vala
+++ b/src/client/components/components-inspector-log-view.vala
@@ -155,9 +155,14 @@ public class Components.InspectorLogView : Gtk.Grid {
 
     /** Saves all log records to the given output stream. */
     public void save(GLib.DataOutputStream out,
+                     Inspector.TextFormat format,
                      bool save_all,
                      GLib.Cancellable? cancellable)
         throws GLib.Error {
+        if (format == MARKDOWN) {
+            out.put_string("```\n");
+        }
+        string line_sep = format.get_line_separator();
         Gtk.TreeModel model = this.logs_view.model;
         if (save_all) {
             // Save all rows selected
@@ -165,6 +170,7 @@ public class Components.InspectorLogView : Gtk.Grid {
             bool valid = model.get_iter_first(out iter);
             while (valid && !cancellable.is_cancelled()) {
                 save_record(model, iter, @out, cancellable);
+                out.put_string(line_sep);
                 valid = model.iter_next(ref iter);
             }
         } else {
@@ -175,6 +181,7 @@ public class Components.InspectorLogView : Gtk.Grid {
                     if (inner_err == null) {
                         try {
                             save_record(model, iter, @out, cancellable);
+                            out.put_string(line_sep);
                         } catch (GLib.Error err) {
                             inner_err = err;
                         }
@@ -185,6 +192,9 @@ public class Components.InspectorLogView : Gtk.Grid {
                 throw inner_err;
             }
         }
+        if (format == MARKDOWN) {
+            out.put_string("```\n");
+        }
     }
 
     private inline void save_record(Gtk.TreeModel model,
@@ -197,7 +207,6 @@ public class Components.InspectorLogView : Gtk.Grid {
         string? message = (string) value;
         if (message != null) {
             out.put_string(message);
-            out.put_byte('\n');
         }
     }
 
diff --git a/src/client/components/components-inspector-system-view.vala 
b/src/client/components/components-inspector-system-view.vala
index b4122e46..8c9d82df 100644
--- a/src/client/components/components-inspector-system-view.vala
+++ b/src/client/components/components-inspector-system-view.vala
@@ -60,24 +60,29 @@ public class Components.InspectorSystemView : Gtk.Grid {
     [GtkChild]
     private Gtk.ListBox system_list;
 
-    private string details;
+    private Gee.Collection<GearyApplication.RuntimeDetail?> details;
 
 
     public InspectorSystemView(GearyApplication application) {
-        StringBuilder details = new StringBuilder();
-        foreach (GearyApplication.RuntimeDetail? detail
-                 in application.get_runtime_information()) {
+        this.details = application.get_runtime_information();
+        foreach (GearyApplication.RuntimeDetail? detail in this.details) {
             this.system_list.add(
                 new DetailRow("%s:".printf(detail.name), detail.value)
             );
-            details.append_printf("%s: %s\n", detail.name, detail.value);
         }
-        this.details = details.str;
     }
 
-    public void save(GLib.DataOutputStream out, GLib.Cancellable? cancellable)
+    public void save(GLib.DataOutputStream out,
+                     Inspector.TextFormat format,
+                     GLib.Cancellable? cancellable)
         throws GLib.Error {
-        out.put_string(this.details, cancellable);
+        string line_sep = format.get_line_separator();
+        foreach (GearyApplication.RuntimeDetail? detail in this.details) {
+            out.put_string(detail.name);
+            out.put_string(": ");
+            out.put_string(detail.value);
+            out.put_string(line_sep);
+        }
     }
 
 }
diff --git a/src/client/components/components-inspector.vala b/src/client/components/components-inspector.vala
index b0eecd36..f7d1b1a4 100644
--- a/src/client/components/components-inspector.vala
+++ b/src/client/components/components-inspector.vala
@@ -12,6 +12,17 @@
 public class Components.Inspector : Gtk.ApplicationWindow {
 
 
+    /** Determines the format used when serialising inspector data. */
+    public enum TextFormat {
+        PLAIN,
+        MARKDOWN;
+
+        public string get_line_separator() {
+            return (this == MARKDOWN) ? "  \n" : "\n";
+        }
+    }
+
+
     private const string ACTION_CLOSE = "inspector-close";
     private const string ACTION_PLAY_TOGGLE = "toggle-play";
     private const string ACTION_SEARCH_TOGGLE = "toggle-search";
@@ -135,10 +146,9 @@ public class Components.Inspector : Gtk.ApplicationWindow {
             new GLib.BufferedOutputStream(dest_io.get_output_stream())
         );
 
-        this.system_pane.save(@out, cancellable);
-        out.put_byte('\n');
-        out.put_byte('\n');
-        this.log_pane.save(@out, true, cancellable);
+        this.system_pane.save(@out, TextFormat.PLAIN, cancellable);
+        out.put_string("\n");
+        this.log_pane.save(@out, TextFormat.PLAIN, true, cancellable);
 
         yield out.close_async();
         yield dest_io.close_async();
@@ -162,9 +172,9 @@ public class Components.Inspector : Gtk.ApplicationWindow {
         GLib.DataOutputStream out = new GLib.DataOutputStream(bytes);
         try {
             if (this.stack.visible_child == this.log_pane) {
-                this.log_pane.save(@out, false, null);
+                this.log_pane.save(@out, TextFormat.MARKDOWN, false, null);
             } else if (this.stack.visible_child == this.system_pane) {
-                this.system_pane.save(@out, null);
+                this.system_pane.save(@out, TextFormat.MARKDOWN, null);
             }
 
             // Ensure the data is a valid string
diff --git a/src/client/dialogs/dialogs-problem-details-dialog.vala 
b/src/client/dialogs/dialogs-problem-details-dialog.vala
index c5cead87..72478079 100644
--- a/src/client/dialogs/dialogs-problem-details-dialog.vala
+++ b/src/client/dialogs/dialogs-problem-details-dialog.vala
@@ -143,13 +143,17 @@ public class Dialogs.ProblemDetailsDialog : Hdy.Dialog {
             new GLib.BufferedOutputStream(dest_io.get_output_stream())
         );
 
-        this.error_pane.save(@out, cancellable);
-        out.put_byte('\n');
-        out.put_byte('\n');
-        this.system_pane.save(@out, cancellable);
-        out.put_byte('\n');
-        out.put_byte('\n');
-        this.log_pane.save(@out, true, cancellable);
+        this.error_pane.save(
+            @out, Components.Inspector.TextFormat.PLAIN, cancellable
+        );
+        out.put_string("\n");
+        this.system_pane.save(
+            @out, Components.Inspector.TextFormat.PLAIN, cancellable
+        );
+        out.put_string("\n");
+        this.log_pane.save(
+            @out, Components.Inspector.TextFormat.PLAIN, true, cancellable
+        );
 
         yield out.close_async();
         yield dest_io.close_async();
@@ -172,11 +176,17 @@ public class Dialogs.ProblemDetailsDialog : Hdy.Dialog {
         GLib.DataOutputStream out = new GLib.DataOutputStream(bytes);
         try {
             if (this.stack.visible_child == this.error_pane) {
-                this.error_pane.save(@out, null);
+                this.error_pane.save(
+                    @out, Components.Inspector.TextFormat.MARKDOWN, null
+                );
             } else if (this.stack.visible_child == this.log_pane) {
-                this.log_pane.save(@out, false, null);
+                this.log_pane.save(
+                    @out, Components.Inspector.TextFormat.MARKDOWN, false, null
+                );
             } else if (this.stack.visible_child == this.system_pane) {
-                this.system_pane.save(@out, null);
+                this.system_pane.save(
+                    @out, Components.Inspector.TextFormat.MARKDOWN, null
+                );
             }
 
             // Ensure the data is a valid string


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