[tracker-miners/wip/carlosg/cli-improvements: 14/30] tracker: Add pager integration to "tracker3 status"
- From: Carlos Garnacho <carlosg src gnome org>
- To: commits-list gnome org
- Cc:
- Subject: [tracker-miners/wip/carlosg/cli-improvements: 14/30] tracker: Add pager integration to "tracker3 status"
- Date: Tue, 18 Aug 2020 09:18:31 +0000 (UTC)
commit 3031a3c69a0a8c64133a02ceb26f1e65d7718219
Author: Carlos Garnacho <carlosg gnome org>
Date: Mon Aug 17 17:15:58 2020 +0200
tracker: Add pager integration to "tracker3 status"
Use the pager when listing errors, so the user can page through them
if they overflow the terminal size.
src/libtracker-miners-common/tracker-term-utils.c | 98 +++++++++++++++++++++++
src/libtracker-miners-common/tracker-term-utils.h | 6 ++
src/tracker/tracker-status.c | 12 +++
3 files changed, 116 insertions(+)
---
diff --git a/src/libtracker-miners-common/tracker-term-utils.c
b/src/libtracker-miners-common/tracker-term-utils.c
index 9de157cf8..96e90da5f 100644
--- a/src/libtracker-miners-common/tracker-term-utils.c
+++ b/src/libtracker-miners-common/tracker-term-utils.c
@@ -21,11 +21,18 @@
#include "tracker-term-utils.h"
+#include <gio/gio.h>
+#include <glib-unix.h>
#include <sys/ioctl.h>
#include <unistd.h>
+#include <fcntl.h>
+#include <stdio.h>
static guint n_columns = 0;
static guint n_rows = 0;
+static GSubprocess *pager = NULL;
+static gint stdout_fd = 0;
+static guint signal_handler_id = 0;
gchar *
tracker_term_ellipsize (const gchar *str,
@@ -87,3 +94,94 @@ tracker_term_dimensions (guint *columns,
if (rows)
*rows = n_rows;
}
+
+gboolean
+tracker_term_is_tty (void)
+{
+ return isatty (STDOUT_FILENO) > 0;
+}
+
+static gboolean
+ignore_signal_cb (gpointer user_data)
+{
+ return G_SOURCE_CONTINUE;
+}
+
+static gchar *
+best_pager (void)
+{
+ guint i;
+ gchar *command;
+ const gchar *pagers[] = {
+ "pager",
+ "less",
+ "most",
+ "more",
+ };
+
+ for (i = 0; i < G_N_ELEMENTS (pagers); i++) {
+ command = g_find_program_in_path (pagers[i]);
+ if (command)
+ return command;
+ }
+
+ return NULL;
+}
+
+gboolean
+tracker_term_pipe_to_pager (void)
+{
+ GSubprocessLauncher *launcher;
+ gchar *pager_command;
+ gint fds[2];
+
+ if (!tracker_term_is_tty ())
+ return FALSE;
+
+ if (pipe2 (fds, O_CLOEXEC) < 0)
+ return FALSE;
+
+ pager_command = best_pager ();
+ if (!pager_command)
+ return FALSE;
+
+ /* Ensure this is cached before we redirect to the pager */
+ tracker_term_dimensions (NULL, NULL);
+
+ launcher = g_subprocess_launcher_new (G_SUBPROCESS_FLAGS_NONE);
+ g_subprocess_launcher_take_stdin_fd (launcher, fds[0]);
+ g_subprocess_launcher_setenv (launcher, "LESS", "FRSXMK", TRUE);
+
+ pager = g_subprocess_launcher_spawn (launcher, NULL, pager_command, NULL);
+ g_free (pager_command);
+
+ stdout_fd = dup (STDOUT_FILENO);
+ close (fds[0]);
+
+ if (dup2(fds[1], STDOUT_FILENO) < 0)
+ return FALSE;
+
+ close (fds[1]);
+ signal_handler_id = g_unix_signal_add (SIGINT, ignore_signal_cb, NULL);
+
+ return TRUE;
+}
+
+gboolean
+tracker_term_pager_close (void)
+{
+ if (!pager)
+ return FALSE;
+
+ fflush (stdout);
+
+ /* Restore stdout */
+ dup2 (stdout_fd, STDOUT_FILENO);
+ close (stdout_fd);
+
+ g_subprocess_send_signal (pager, SIGCONT);
+ g_subprocess_wait (pager, NULL, NULL);
+ g_source_remove (signal_handler_id);
+
+ return TRUE;
+}
diff --git a/src/libtracker-miners-common/tracker-term-utils.h
b/src/libtracker-miners-common/tracker-term-utils.h
index e572b454e..1a4547d0b 100644
--- a/src/libtracker-miners-common/tracker-term-utils.h
+++ b/src/libtracker-miners-common/tracker-term-utils.h
@@ -23,6 +23,7 @@
#define __TRACKER_TERM_UTILS_H__
#include <glib.h>
+#include <gio/gio.h>
typedef enum {
TRACKER_ELLIPSIZE_START,
@@ -36,4 +37,9 @@ gchar * tracker_term_ellipsize (const gchar *str,
void tracker_term_dimensions (guint *columns,
guint *lines);
+gboolean tracker_term_is_tty (void);
+
+gboolean tracker_term_pipe_to_pager (void);
+gboolean tracker_term_pager_close (void);
+
#endif /* __TRACKER_TERM_UTILS_H__ */
diff --git a/src/tracker/tracker-status.c b/src/tracker/tracker-status.c
index 2b6e2d8ec..8e8ae8ff4 100644
--- a/src/tracker/tracker-status.c
+++ b/src/tracker/tracker-status.c
@@ -96,6 +96,8 @@ status_stat (void)
return EXIT_FAILURE;
}
+ tracker_term_pipe_to_pager ();
+
cursor = statistics_query (connection, &error);
g_object_unref (connection);
@@ -162,6 +164,8 @@ status_stat (void)
g_object_unref (cursor);
}
+ tracker_term_pager_close ();
+
return EXIT_SUCCESS;
}
@@ -611,6 +615,8 @@ get_no_args (void)
gint files, folders;
GList *keyfiles;
+ tracker_term_pipe_to_pager ();
+
/* How many files / folders do we have? */
if (get_file_and_folder_count (&files, &folders) != 0) {
return EXIT_FAILURE;
@@ -673,6 +679,8 @@ get_no_args (void)
g_list_free_full (keyfiles, (GDestroyNotify) g_key_file_unref);
}
+ tracker_term_pager_close ();
+
return EXIT_SUCCESS;
}
@@ -684,6 +692,8 @@ show_errors (gchar **terms)
guint i;
gboolean found = FALSE;
+ tracker_term_pipe_to_pager ();
+
keyfiles = get_error_keyfiles ();
for (i = 0; terms[i] != NULL; i++) {
@@ -722,6 +732,8 @@ show_errors (gchar **terms)
if (!found)
g_print (BOLD_BEGIN "%s" BOLD_END "\n", _("No reports found"));
+ tracker_term_pager_close ();
+
return EXIT_SUCCESS;
}
[
Date Prev][
Date Next] [
Thread Prev][
Thread Next]
[
Thread Index]
[
Date Index]
[
Author Index]