From bf5542f891893a1c38900bb4470ce2dadf57a29a Mon Sep 17 00:00:00 2001 From: Lennart Poettering Date: Fri, 28 Sep 2012 00:59:10 +0200 Subject: journal: add missing browse.html file --- src/journal/browse.html | 282 ++++++++++++++++++++++++++++++++++++++++++++++++ 1 file changed, 282 insertions(+) create mode 100644 src/journal/browse.html (limited to 'src/journal/browse.html') diff --git a/src/journal/browse.html b/src/journal/browse.html new file mode 100644 index 0000000000..b901d7a908 --- /dev/null +++ b/src/journal/browse.html @@ -0,0 +1,282 @@ + + + + Journal + + + + + + + +

+ +
+
+
+
+
+
+ +
+ +
+ + + + +      + + +
+ + + + -- cgit v1.2.3-54-g00ecf From 1dac8b797ce5404759c2b105c8d2292b22727d2e Mon Sep 17 00:00:00 2001 From: Lennart Poettering Date: Wed, 10 Oct 2012 02:41:27 +0200 Subject: gatewayd: beef up browse.html a bit --- src/journal/browse.html | 71 ++++++++++++++++++++++++++++++++++--------------- 1 file changed, 49 insertions(+), 22 deletions(-) (limited to 'src/journal/browse.html') diff --git a/src/journal/browse.html b/src/journal/browse.html index b901d7a908..5ceca26a5d 100644 --- a/src/journal/browse.html +++ b/src/journal/browse.html @@ -4,7 +4,7 @@ Journal @@ -49,7 +64,7 @@
-
+
@@ -196,8 +211,7 @@ (event.currentTarget.status != 200 && event.currentTarget.status != 0)) return; - var logs = document.getElementById("logs"); - logs.innerHTML = ""; + var logs = document.getElementById("tablelogs"); var lc = null; var fc = null; @@ -206,10 +220,12 @@ var l = event.currentTarget.responseText.split('\n'); if (l.length <= 1) { - logs.innerHTML = "No further entries..."; + logs.innerHTML = 'No further entries...'; return; } + var buf = ''; + for (i in l) { if (l[i] == '') @@ -230,34 +246,45 @@ priority = 6; if (priority <= 3) - clazz = "log-error"; + clazz = "message-error"; else if (priority <= 5) - clazz = "log-highlight"; + clazz = "message-highlight"; else - clazz = "log-normal"; + clazz = "message"; + + buf += ''; + + if (d.__REALTIME_TIMESTAMP != undefined) { + var timestamp = new Date(parseInt(d.__REALTIME_TIMESTAMP) / 1000); + buf += timestamp.toLocaleString(); + } - var line = '
'; + buf += ''; if (d.SYSLOG_IDENTIFIER != undefined) - line += d.SYSLOG_IDENTIFIER; + buf += d.SYSLOG_IDENTIFIER; else if (d._COMM != undefined) - line += d._COMM; + buf += d._COMM; if (d._PID != undefined) - line += "[" + d._PID + "]"; + buf += "[" + d._PID + "]"; else if (d.SYSLOG_PID != undefined) - line += "[" + d.SYSLOG_PID + "]"; + buf += "[" + d.SYSLOG_PID + "]"; + + buf += ''; if (d.MESSAGE == null) - line += ": [blob data]
"; + buf += "[blob data]"; else if (d.MESSAGE instanceof Array) - line += ": [" + formatBytes(d.MESSAGE.length) + " blob data]"; + buf += "[" + formatBytes(d.MESSAGE.length) + " blob data]"; else - line += ": " + d.MESSAGE + ""; + buf += d.MESSAGE; - logs.innerHTML += line; + buf += ''; } + logs.innerHTML = buf + ''; + if (fc != null) first_cursor = fc; if (lc != null) -- cgit v1.2.3-54-g00ecf From c6511e859c35b12de4e6fb5f58d7258d9de3b8f2 Mon Sep 17 00:00:00 2001 From: Lennart Poettering Date: Wed, 10 Oct 2012 22:39:45 +0200 Subject: journal: when browsing the journal via browse.html allow clicking on entries to show their details --- Makefile.am | 4 +- man/sd_journal_get_cursor.xml | 53 +++++++++++++++++------ man/sd_journal_seek_head.xml | 7 ++- src/journal/browse.html | 77 +++++++++++++++++++++++++++++---- src/journal/journal-gatewayd.c | 38 ++++++++++++++++ src/journal/libsystemd-journal.sym | 5 +++ src/journal/sd-journal.c | 88 ++++++++++++++++++++++++++++++++++++-- src/journal/test-journal-stream.c | 16 ++++++- src/systemd/sd-journal.h | 1 + 9 files changed, 263 insertions(+), 26 deletions(-) (limited to 'src/journal/browse.html') diff --git a/Makefile.am b/Makefile.am index 0b3013b444..c23afdf173 100644 --- a/Makefile.am +++ b/Makefile.am @@ -580,7 +580,8 @@ MANPAGES_ALIAS = \ man/sd_journal_seek_tail.3 \ man/sd_journal_seek_monotonic_usec.3 \ man/sd_journal_seek_realtime_usec.3 \ - man/sd_journal_seek_cursor.3 + man/sd_journal_seek_cursor.3 \ + man/sd_journal_test_cursor.3 man/reboot.8: man/halt.8 man/poweroff.8: man/halt.8 @@ -649,6 +650,7 @@ man/sd_journal_seek_tail.3: man/sd_journal_seek_head.3 man/sd_journal_seek_monotonic_usec.3: man/sd_journal_seek_head.3 man/sd_journal_seek_realtime_usec.3: man/sd_journal_seek_head.3 man/sd_journal_seek_cursor.3: man/sd_journal_seek_head.3 +man/sd_journal_test_cursor.3: man/sd_journal_get_cursor.3 XML_FILES = \ ${patsubst %.1,%.xml,${patsubst %.3,%.xml,${patsubst %.5,%.xml,${patsubst %.7,%.xml,${patsubst %.8,%.xml,$(MANPAGES)}}}}} diff --git a/man/sd_journal_get_cursor.xml b/man/sd_journal_get_cursor.xml index 9e00ef7c82..354168bee2 100644 --- a/man/sd_journal_get_cursor.xml +++ b/man/sd_journal_get_cursor.xml @@ -44,7 +44,8 @@ sd_journal_get_cursor - Get cursor string for the current journal entry + sd_journal_test_cursor + Get cursor string for or test cursor string against the current journal entry @@ -57,6 +58,12 @@ char ** cursor + + int sd_journal_test_cursor + sd_journal* j + const char * cursor + + @@ -66,7 +73,7 @@ sd_journal_get_cursor() returns a cursor string for the current journal entry. A cursor is a serialization of the current - journal position in text form. The string only + journal position formatted as text. The string only contains printable characters and can be passed around in text form. The cursor identifies a journal entry globally and in a stable way and may be used to later @@ -77,16 +84,33 @@ without the specific entry being available locally will seek to the next closest (in terms of time) available entry. The call takes two arguments: a - journal context object and a pointer to a - string pointer where the cursor string will be - placed. The string is allocated via libc malloc3 and should - be freed after use with + journal context object and a pointer to a string + pointer where the cursor string will be placed. The + string is allocated via libc + malloc3 + and should be freed after use with free3. - Note that this function will not work before + Note that + sd_journal_get_cursor() will not + work before sd_journal_next3 - (or related call) has been called at least - once, in order to position the read pointer at a valid entry. + (or related call) has been called at least once, in + order to position the read pointer at a valid + entry. + + sd_journal_test_cursor() + may be used to check whether the current position in + the journal matches the specified cursor. This is + useful since cursor strings do not uniquely identify + an entry: the same entry might be referred to by + multiple different cursor strings, and hence string + comparing cursors is not possible. Use this call to + verify after an invocation of + sd_journal_seek_cursor3 + whether the entry being seeked to was actually found + in the journal or the next closest entry was used + instead. @@ -94,15 +118,20 @@ sd_journal_get_cursor() returns 0 on success or a negative errno-style error - code. + code. sd_journal_test_cursor() + returns positive if the current entry matches the + specified cursor, 0 if it doesn't match the specified + cursor or a negative errno-style error code on + failure. Notes The sd_journal_get_cursor() - interface is available as shared library, which can be - compiled and linked to with the + and sd_journal_test_cursor() + interfaces are available as shared library, which can + be compiled and linked to with the libsystemd-journal pkg-config1 file. diff --git a/man/sd_journal_seek_head.xml b/man/sd_journal_seek_head.xml index f8a4eb1d20..b10f069e83 100644 --- a/man/sd_journal_seek_head.xml +++ b/man/sd_journal_seek_head.xml @@ -115,7 +115,12 @@ sd_journal_seek_cursor() seeks to the entry located at the specified cursor string. For details on cursors see - sd_journal_get_cursor3. + sd_journal_get_cursor3. If + no entry matching the specified cursor is found the + call will seek to the next closest entry (in terms of + time) instead. To verify whether the newly selected + entry actually matches the cursor use + sd_journal_test_cursor3. Note that these calls do not actually make any entry the new current entry, this needs to be done in diff --git a/src/journal/browse.html b/src/journal/browse.html index 5ceca26a5d..068b296da1 100644 --- a/src/journal/browse.html +++ b/src/journal/browse.html @@ -4,7 +4,7 @@ Journal @@ -65,6 +95,8 @@
+ +
@@ -271,7 +303,7 @@ else if (d.SYSLOG_PID != undefined) buf += "[" + d.SYSLOG_PID + "]"; - buf += ''; + buf += ''; if (d.MESSAGE == null) buf += "[blob data]"; @@ -280,10 +312,10 @@ else buf += d.MESSAGE; - buf += ''; + buf += ''; } - logs.innerHTML = buf + ''; + logs.innerHTML = '' + buf + ''; if (fc != null) first_cursor = fc; @@ -293,12 +325,41 @@ function entriesMore() { setNEntries(getNEntries() + 10); - entriesLoad(""); + entriesLoad(first_cursor); } function entriesLess() { setNEntries(getNEntries() - 10); - entriesLoad(""); + entriesLoad(first_cursor); + } + + function onResultMessageClick(event) { + if ((event.currentTarget.readyState != 4) || + (event.currentTarget.status != 200 && event.currentTarget.status != 0)) + return; + + var d = JSON.parse(event.currentTarget.responseText); + + document.getElementById("diventry").style.display = "block"; + + entry = document.getElementById("tableentry"); + + var buf = ""; + + for (var key in d){ + buf += '' + key + '' + d[key] + ''; + } + + entry.innerHTML = '' + buf + ''; + } + + function onMessageClick(t) { + var request = new XMLHttpRequest(); + request.open("GET", "/entries?discrete"); + request.onreadystatechange = onResultMessageClick; + request.setRequestHeader("Accept", "application/json"); + request.setRequestHeader("Range", "entries=" + t + ":0:1"); + request.send(null); } machineLoad(); diff --git a/src/journal/journal-gatewayd.c b/src/journal/journal-gatewayd.c index 274ef5ffeb..33dda266b6 100644 --- a/src/journal/journal-gatewayd.c +++ b/src/journal/journal-gatewayd.c @@ -49,6 +49,7 @@ typedef struct RequestMeta { int argument_parse_error; bool follow; + bool discrete; } RequestMeta; static const char* const mime_types[_OUTPUT_MODE_MAX] = { @@ -205,6 +206,19 @@ static ssize_t request_reader_entries( return MHD_CONTENT_READER_END_OF_STREAM; } + if (m->discrete) { + assert(m->cursor); + + r = sd_journal_test_cursor(m->journal, m->cursor); + if (r < 0) { + log_error("Failed to test cursor: %s", strerror(-r)); + return MHD_CONTENT_READER_END_WITH_ERROR; + } + + if (r == 0) + return MHD_CONTENT_READER_END_OF_STREAM; + } + pos -= m->size; m->delta += m->size; @@ -380,6 +394,22 @@ static int request_parse_arguments_iterator( return MHD_YES; } + if (streq(key, "discrete")) { + if (isempty(value)) { + m->discrete = true; + return MHD_YES; + } + + r = parse_boolean(value); + if (r < 0) { + m->argument_parse_error = r; + return MHD_NO; + } + + m->discrete = r; + return MHD_YES; + } + p = strjoin(key, "=", strempty(value), NULL); if (!p) { m->argument_parse_error = log_oom(); @@ -436,6 +466,14 @@ static int request_handler_entries( if (request_parse_arguments(m, connection) < 0) return respond_error(connection, MHD_HTTP_BAD_REQUEST, "Failed to parse URL arguments.\n"); + if (m->discrete) { + if (!m->cursor) + return respond_error(connection, MHD_HTTP_BAD_REQUEST, "Discrete seeks require a cursor specification.\n"); + + m->n_entries = 1; + m->n_entries_set = true; + } + if (m->cursor) r = sd_journal_seek_cursor(m->journal, m->cursor); else if (m->n_skip >= 0) diff --git a/src/journal/libsystemd-journal.sym b/src/journal/libsystemd-journal.sym index 7dfae2625f..77de862dcb 100644 --- a/src/journal/libsystemd-journal.sym +++ b/src/journal/libsystemd-journal.sym @@ -75,3 +75,8 @@ LIBSYSTEMD_JOURNAL_190 { global: sd_journal_get_usage; } LIBSYSTEMD_JOURNAL_188; + +LIBSYSTEMD_JOURNAL_195 { +global: + sd_journal_test_cursor; +} LIBSYSTEMD_JOURNAL_190; diff --git a/src/journal/sd-journal.c b/src/journal/sd-journal.c index 9e594a2cff..88b382f4cc 100644 --- a/src/journal/sd-journal.c +++ b/src/journal/sd-journal.c @@ -951,9 +951,8 @@ _public_ int sd_journal_get_cursor(sd_journal *j, char **cursor) { } _public_ int sd_journal_seek_cursor(sd_journal *j, const char *cursor) { - char *w; + char *w, *state; size_t l; - char *state; unsigned long long seqnum, monotonic, realtime, xor_hash; bool seqnum_id_set = false, @@ -966,7 +965,7 @@ _public_ int sd_journal_seek_cursor(sd_journal *j, const char *cursor) { if (!j) return -EINVAL; - if (!cursor) + if (isempty(cursor)) return -EINVAL; FOREACH_WORD_SEPARATOR(w, l, cursor, ";", state) { @@ -1057,6 +1056,89 @@ _public_ int sd_journal_seek_cursor(sd_journal *j, const char *cursor) { return 0; } +_public_ int sd_journal_test_cursor(sd_journal *j, const char *cursor) { + int r; + char *w, *state; + size_t l; + Object *o; + + if (!j) + return -EINVAL; + if (isempty(cursor)) + return -EINVAL; + + if (!j->current_file || j->current_file->current_offset <= 0) + return -EADDRNOTAVAIL; + + r = journal_file_move_to_object(j->current_file, OBJECT_ENTRY, j->current_file->current_offset, &o); + if (r < 0) + return r; + + FOREACH_WORD_SEPARATOR(w, l, cursor, ";", state) { + _cleanup_free_ char *item = NULL; + sd_id128_t id; + unsigned long long ll; + int k = 0; + + if (l < 2 || w[1] != '=') + return -EINVAL; + + item = strndup(w, l); + if (!item) + return -ENOMEM; + + switch (w[0]) { + + case 's': + k = sd_id128_from_string(item+2, &id); + if (k < 0) + return k; + if (!sd_id128_equal(id, j->current_file->header->seqnum_id)) + return 0; + break; + + case 'i': + if (sscanf(item+2, "%llx", &ll) != 1) + return -EINVAL; + if (ll != le64toh(o->entry.seqnum)) + return 0; + break; + + case 'b': + k = sd_id128_from_string(item+2, &id); + if (k < 0) + return k; + if (!sd_id128_equal(id, o->entry.boot_id)) + return 0; + break; + + case 'm': + if (sscanf(item+2, "%llx", &ll) != 1) + return -EINVAL; + if (ll != le64toh(o->entry.monotonic)) + return 0; + break; + + case 't': + if (sscanf(item+2, "%llx", &ll) != 1) + return -EINVAL; + if (ll != le64toh(o->entry.realtime)) + return 0; + break; + + case 'x': + if (sscanf(item+2, "%llx", &ll) != 1) + return -EINVAL; + if (ll != le64toh(o->entry.xor_hash)) + return 0; + break; + } + } + + return 1; +} + + _public_ int sd_journal_seek_monotonic_usec(sd_journal *j, sd_id128_t boot_id, uint64_t usec) { if (!j) return -EINVAL; diff --git a/src/journal/test-journal-stream.c b/src/journal/test-journal-stream.c index 707dcc178b..caea2b2c63 100644 --- a/src/journal/test-journal-stream.c +++ b/src/journal/test-journal-stream.c @@ -39,7 +39,7 @@ static void verify_contents(sd_journal *j, unsigned skip) { i = 0; SD_JOURNAL_FOREACH(j) { const void *d; - char *k; + char *k, *c; size_t l; unsigned u; @@ -61,6 +61,10 @@ static void verify_contents(sd_journal *j, unsigned skip) { } free(k); + + assert_se(sd_journal_get_cursor(j, &c) >= 0); + assert_se(sd_journal_test_cursor(j, c) > 0); + free(c); } if (skip > 0) @@ -122,17 +126,27 @@ int main(int argc, char *argv[]) { SD_JOURNAL_FOREACH_BACKWARDS(j) { const void *d; size_t l; + char *c; assert_se(sd_journal_get_data(j, "NUMBER", &d, &l) >= 0); printf("\t%.*s\n", (int) l, (const char*) d); + + assert_se(sd_journal_get_cursor(j, &c) >= 0); + assert_se(sd_journal_test_cursor(j, c) > 0); + free(c); } SD_JOURNAL_FOREACH(j) { const void *d; size_t l; + char *c; assert_se(sd_journal_get_data(j, "NUMBER", &d, &l) >= 0); printf("\t%.*s\n", (int) l, (const char*) d); + + assert_se(sd_journal_get_cursor(j, &c) >= 0); + assert_se(sd_journal_test_cursor(j, c) > 0); + free(c); } sd_journal_flush_matches(j); diff --git a/src/systemd/sd-journal.h b/src/systemd/sd-journal.h index 6c18c89425..9a2aab923a 100644 --- a/src/systemd/sd-journal.h +++ b/src/systemd/sd-journal.h @@ -104,6 +104,7 @@ int sd_journal_seek_realtime_usec(sd_journal *j, uint64_t usec); int sd_journal_seek_cursor(sd_journal *j, const char *cursor); int sd_journal_get_cursor(sd_journal *j, char **cursor); +int sd_journal_test_cursor(sd_journal *j, const char *cursor); int sd_journal_get_cutoff_realtime_usec(sd_journal *j, uint64_t *from, uint64_t *to); int sd_journal_get_cutoff_monotonic_usec(sd_journal *j, const sd_id128_t boot_id, uint64_t *from, uint64_t *to); -- cgit v1.2.3-54-g00ecf From 522795e07742b4e804896147a21e026bb34602ba Mon Sep 17 00:00:00 2001 From: Mantas Mikulėnas Date: Wed, 10 Oct 2012 23:00:25 +0200 Subject: journal: properly escape HTML entities in browse.html --- src/journal/browse.html | 6 +++++- 1 file changed, 5 insertions(+), 1 deletion(-) (limited to 'src/journal/browse.html') diff --git a/src/journal/browse.html b/src/journal/browse.html index 068b296da1..362611b1c2 100644 --- a/src/journal/browse.html +++ b/src/journal/browse.html @@ -177,6 +177,10 @@ return u.toString() + " B"; } + function escapeHTML(s) { + return s.replace(/&/g, "&").replace(//g, ">"); + } + function machineOnResult(event) { if ((event.currentTarget.readyState != 4) || (event.currentTarget.status != 200 && event.currentTarget.status != 0)) @@ -310,7 +314,7 @@ else if (d.MESSAGE instanceof Array) buf += "[" + formatBytes(d.MESSAGE.length) + " blob data]"; else - buf += d.MESSAGE; + buf += escapeHTML(d.MESSAGE); buf += ''; } -- cgit v1.2.3-54-g00ecf From 6c69cd8626d8ba9c879f6885122cf5f2eb855fda Mon Sep 17 00:00:00 2001 From: Lennart Poettering Date: Wed, 10 Oct 2012 23:14:32 +0200 Subject: journal: properly HTML escape more output in browse.html --- src/journal/browse.html | 37 ++++++++++++++++++++++--------------- 1 file changed, 22 insertions(+), 15 deletions(-) (limited to 'src/journal/browse.html') diff --git a/src/journal/browse.html b/src/journal/browse.html index 362611b1c2..f16e346d90 100644 --- a/src/journal/browse.html +++ b/src/journal/browse.html @@ -81,9 +81,10 @@ + - live display + - keyboard navigation + - localstorage + - show red lines for reboots -->

@@ -189,8 +190,8 @@ var d = JSON.parse(event.currentTarget.responseText); var title = document.getElementById("title"); - title.innerHTML = 'Journal of ' + d.hostname; - document.title = 'Journal of ' + d.hostname; + title.innerHTML = 'Journal of ' + escapeHTML(d.hostname); + document.title = 'Journal of ' + escapeHTML(d.hostname); var machine = document.getElementById("machine"); machine.innerHTML = 'Machine ID is ' + d.machine_id + ', current boot ID is ' + d.boot_id + '.'; @@ -204,10 +205,10 @@ usage.innerHTML = 'Disk usage is ' + formatBytes(parseInt(d.usage)) + '.'; var os = document.getElementById("os"); - os.innerHTML = 'Operating system is ' + d.os_pretty_name + '.'; + os.innerHTML = 'Operating system is ' + escapeHTML(d.os_pretty_name) + '.'; var virtualization = document.getElementById("virtualization"); - virtualization.innerHTML = d.virtualization == "bare" ? "Running on bare metal." : "Running on virtualization " + d.virtualization + "."; + virtualization.innerHTML = d.virtualization == "bare" ? "Running on bare metal." : "Running on virtualization " + escapeHTML(d.virtualization) + "."; } function entriesLoad(range) { @@ -298,14 +299,14 @@ buf += ''; if (d.SYSLOG_IDENTIFIER != undefined) - buf += d.SYSLOG_IDENTIFIER; + buf += escapeHTML(d.SYSLOG_IDENTIFIER); else if (d._COMM != undefined) - buf += d._COMM; + buf += escapeHTML(d._COMM); if (d._PID != undefined) - buf += "[" + d._PID + "]"; + buf += "[" + escapeHTML(d._PID) + "]"; else if (d.SYSLOG_PID != undefined) - buf += "[" + d.SYSLOG_PID + "]"; + buf += "[" + escapeHTML(d.SYSLOG_PID) + "]"; buf += ''; @@ -345,15 +346,21 @@ var d = JSON.parse(event.currentTarget.responseText); document.getElementById("diventry").style.display = "block"; - entry = document.getElementById("tableentry"); var buf = ""; - for (var key in d){ - buf += '' + key + '' + d[key] + ''; - } + var data = d[key]; + if (data == null) + data = "[blob data]"; + else if (data instanceof Array) + data = "[" + formatBytes(data.length) + " blob data]"; + else + data = escapeHTML(data); + + buf += '' + key + '' + data + ''; + } entry.innerHTML = '' + buf + ''; } -- cgit v1.2.3-54-g00ecf From 6d5f2f58033493a71402755944f46f09d990bad4 Mon Sep 17 00:00:00 2001 From: Lennart Poettering Date: Wed, 10 Oct 2012 23:49:21 +0200 Subject: journal: add keyboard navigation to browse.html --- src/journal/browse.html | 49 ++++++++++++++++++++++++++++++++++++++++++++++++- 1 file changed, 48 insertions(+), 1 deletion(-) (limited to 'src/journal/browse.html') diff --git a/src/journal/browse.html b/src/journal/browse.html index f16e346d90..5a161a13fb 100644 --- a/src/journal/browse.html +++ b/src/journal/browse.html @@ -76,13 +76,22 @@ td.data { padding-left: 5px; } + div#keynav { + text-align: center; + font-size: 7pt; + color: #818789; + padding-top: 50px; + } + .key { + font-weight: bold; + color: #313739; + } @@ -109,6 +118,15 @@ +
+ →, j, SPACE: Next Page      + ←, k, BACKSPACE: Previous Page      + g: First Page      + G: Last Page      + +: More entries      + -: Fewer entries +
+ -- cgit v1.2.3-54-g00ecf From 19f8efacc5ef96bd4f3553ff3dd3e94c4a1bd59c Mon Sep 17 00:00:00 2001 From: Kay Sievers Date: Wed, 10 Oct 2012 23:59:29 +0200 Subject: journal: add mousewheel scrolling to browse.html --- src/journal/browse.html | 11 +++++++++++ 1 file changed, 11 insertions(+) (limited to 'src/journal/browse.html') diff --git a/src/journal/browse.html b/src/journal/browse.html index 5a161a13fb..d5e0717c53 100644 --- a/src/journal/browse.html +++ b/src/journal/browse.html @@ -419,10 +419,21 @@ } } + function onMouseWheel(event) { + if (event.detail < 0 || event.wheelDelta > 0) + entriesLoadPrevious(); + else + entriesLoadNext(); + } + machineLoad(); entriesLoad(""); showNEntries(getNEntries()); document.onkeyup = onKeyUp; + + logs = document.getElementById("tablelogs"); + logs.addEventListener("mousewheel", onMouseWheel, false); + logs.addEventListener("DOMMouseScroll", onMouseWheel, false); -- cgit v1.2.3-54-g00ecf From 74bee4e336774e8dc537cf685b64c51490aa5ad3 Mon Sep 17 00:00:00 2001 From: Lennart Poettering Date: Thu, 11 Oct 2012 00:04:54 +0200 Subject: journal: move buttons to the center in browse.html --- src/journal/browse.html | 13 ++++++++++--- 1 file changed, 10 insertions(+), 3 deletions(-) (limited to 'src/journal/browse.html') diff --git a/src/journal/browse.html b/src/journal/browse.html index d5e0717c53..97fbcbf91d 100644 --- a/src/journal/browse.html +++ b/src/journal/browse.html @@ -80,12 +80,19 @@ text-align: center; font-size: 7pt; color: #818789; - padding-top: 50px; + padding-top: 2em; } .key { font-weight: bold; color: #313739; } + form { + text-align: center; + } + input { + font-size: 10pt; + font-weight: bold; + } @@ -119,9 +126,9 @@
- →, j, SPACE: Next Page      - ←, k, BACKSPACE: Previous Page      g: First Page      + ←, k, BACKSPACE: Previous Page      + →, j, SPACE: Next Page      G: Last Page      +: More entries      -: Fewer entries -- cgit v1.2.3-54-g00ecf From 04909b0f2c6a21284dbd4ff05186f9ef89caee17 Mon Sep 17 00:00:00 2001 From: Lennart Poettering Date: Thu, 11 Oct 2012 00:38:20 +0200 Subject: journal: use localstorage instead of cookies in browse.html and store where the current position --- src/journal/browse.html | 52 ++++++++++++++++++------------------------------- 1 file changed, 19 insertions(+), 33 deletions(-) (limited to 'src/journal/browse.html') diff --git a/src/journal/browse.html b/src/journal/browse.html index 97fbcbf91d..a49dcf243e 100644 --- a/src/journal/browse.html +++ b/src/journal/browse.html @@ -99,7 +99,6 @@

@@ -138,33 +137,17 @@ var first_cursor = null; var last_cursor = null; - function setCookie(name, value, msec) { - var d = new Date(); - d.setMilliseconds(d.getMilliseconds() + msec); - var v = escape(value) + "; expires=" + d.toUTCString(); - document.cookie = name + "=" + value; - } - - function getCookie(name) { - var i, l; - l = document.cookie.split(";"); - for (i in l) { - var x, y, j; - j = l[i].indexOf("="); - x = l[i].substr(0, j); - y = l[i].substr(j+1); - if (x == name) - return unescape(y); - } - return null; - } - function getNEntries() { var n; - n = getCookie("n_entries"); + n = localStorage["n_entries"]; if (n == null) return 50; - return parseInt(n); + n = parseInt(n); + if (n < 10) + return 10; + if (n > 1000) + return 1000; + return n; } function showNEntries(n) { @@ -173,12 +156,7 @@ } function setNEntries(n) { - if (n < 10) - n = 10; - else if (n > 1000) - n = 1000; - - setCookie("n_entries", n.toString(), 30*24*60*60*1000); + localStorage["n_entries"] = n.toString(); showNEntries(n); } @@ -237,6 +215,12 @@ } function entriesLoad(range) { + + if (range == null) + range = localStorage["cursor"]; + if (range == null) + range = ""; + var request = new XMLHttpRequest(); request.open("GET", "/entries"); request.onreadystatechange = entriesOnResult; @@ -333,7 +317,7 @@ else if (d.SYSLOG_PID != undefined) buf += "[" + escapeHTML(d.SYSLOG_PID) + "]"; - buf += '
'; + buf += ''; if (d.MESSAGE == null) buf += "[blob data]"; @@ -347,8 +331,10 @@ logs.innerHTML = '' + buf + ''; - if (fc != null) + if (fc != null) { first_cursor = fc; + localStorage["cursor"] = fc; + } if (lc != null) last_cursor = lc; } @@ -434,7 +420,7 @@ } machineLoad(); - entriesLoad(""); + entriesLoad(null); showNEntries(getNEntries()); document.onkeyup = onKeyUp; -- cgit v1.2.3-54-g00ecf From 33162605bb8b612cd047c1d817c1b3223aaa9add Mon Sep 17 00:00:00 2001 From: Lennart Poettering Date: Thu, 11 Oct 2012 01:52:35 +0200 Subject: journal: make buttons bigger in browse.html --- src/journal/browse.html | 26 +++++++++++++++----------- 1 file changed, 15 insertions(+), 11 deletions(-) (limited to 'src/journal/browse.html') diff --git a/src/journal/browse.html b/src/journal/browse.html index a49dcf243e..6532820668 100644 --- a/src/journal/browse.html +++ b/src/journal/browse.html @@ -90,7 +90,7 @@ text-align: center; } input { - font-size: 10pt; + font-size: 18pt; font-weight: bold; } @@ -115,13 +115,13 @@
- - - - + + + +      - - + +
@@ -139,7 +139,7 @@ function getNEntries() { var n; - n = localStorage["n_entries"]; + n = window.localStorage["n_entries"]; if (n == null) return 50; n = parseInt(n); @@ -156,7 +156,11 @@ } function setNEntries(n) { - localStorage["n_entries"] = n.toString(); + if (n < 10) + return 10; + if (n > 1000) + return 1000; + window.localStorage["n_entries"] = n.toString(); showNEntries(n); } @@ -217,7 +221,7 @@ function entriesLoad(range) { if (range == null) - range = localStorage["cursor"]; + range = window.localStorage["cursor"] + ":0"; if (range == null) range = ""; @@ -333,7 +337,7 @@ if (fc != null) { first_cursor = fc; - localStorage["cursor"] = fc; + window.localStorage["cursor"] = fc; } if (lc != null) last_cursor = lc; -- cgit v1.2.3-54-g00ecf From 33316dbf20d378e15d126d97d0415407853a7fb8 Mon Sep 17 00:00:00 2001 From: Lennart Poettering Date: Thu, 11 Oct 2012 01:57:36 +0200 Subject: journal: take scroll events in the entire white box in browse.html --- src/journal/browse.html | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) (limited to 'src/journal/browse.html') diff --git a/src/journal/browse.html b/src/journal/browse.html index 6532820668..2da0b0a46f 100644 --- a/src/journal/browse.html +++ b/src/journal/browse.html @@ -428,7 +428,7 @@ showNEntries(getNEntries()); document.onkeyup = onKeyUp; - logs = document.getElementById("tablelogs"); + logs = document.getElementById("divlogs"); logs.addEventListener("mousewheel", onMouseWheel, false); logs.addEventListener("DOMMouseScroll", onMouseWheel, false); -- cgit v1.2.3-54-g00ecf From 1cd8a002ff459791967122c2c8be2ccd44dafcf2 Mon Sep 17 00:00:00 2001 From: Lennart Poettering Date: Thu, 18 Oct 2012 22:33:39 +0200 Subject: journal: implement filtering in browse.html --- src/journal/browse.html | 158 ++++++++++++++++++++++++++++++++++++++++-------- 1 file changed, 133 insertions(+), 25 deletions(-) (limited to 'src/journal/browse.html') diff --git a/src/journal/browse.html b/src/journal/browse.html index 2da0b0a46f..3594f70c87 100644 --- a/src/journal/browse.html +++ b/src/journal/browse.html @@ -6,7 +6,7 @@ @@ -110,19 +118,27 @@
+
+ +      + Only current boot +
+
-
- - - - +
+ + + +      - - - + + +
g: First Page      @@ -139,7 +155,7 @@ function getNEntries() { var n; - n = window.localStorage["n_entries"]; + n = localStorage["n_entries"]; if (n == null) return 50; n = parseInt(n); @@ -160,7 +176,7 @@ return 10; if (n > 1000) return 1000; - window.localStorage["n_entries"] = n.toString(); + localStorage["n_entries"] = n.toString(); showNEntries(n); } @@ -221,12 +237,24 @@ function entriesLoad(range) { if (range == null) - range = window.localStorage["cursor"] + ":0"; + range = localStorage["cursor"] + ":0"; if (range == null) range = ""; + var url = "/entries"; + + if (localStorage["filter"] != "" && localStorage["filter"] != null) { + url += "?_SYSTEMD_UNIT=" + escape(localStorage["filter"]); + + if (localStorage["boot"] == "1") + url += "&boot"; + } else { + if (localStorage["boot"] == "1") + url += "?boot"; + } + var request = new XMLHttpRequest(); - request.open("GET", "/entries"); + request.open("GET", url); request.onreadystatechange = entriesOnResult; request.setRequestHeader("Accept", "application/json"); request.setRequestHeader("Range", "entries=" + range + ":" + getNEntries().toString()); @@ -266,8 +294,7 @@ var lc = null; var fc = null; - var i; - var l = event.currentTarget.responseText.split('\n'); + var i, l = event.currentTarget.responseText.split('\n'); if (l.length <= 1) { logs.innerHTML = 'No further entries...'; @@ -337,7 +364,7 @@ if (fc != null) { first_cursor = fc; - window.localStorage["cursor"] = fc; + localStorage["cursor"] = fc; } if (lc != null) last_cursor = lc; @@ -423,14 +450,95 @@ entriesLoadNext(); } + function onResultFilterFocus(event) { + if ((event.currentTarget.readyState != 4) || + (event.currentTarget.status != 200 && event.currentTarget.status != 0)) + return; + + f = document.getElementById("filter"); + + var l = event.currentTarget.responseText.split('\n'); + var buf = ''; + var j = -1; + + for (i in l) { + + if (l[i] == '') + continue; + + var d = JSON.parse(l[i]); + if (d._SYSTEMD_UNIT == undefined) + continue; + + buf += ''; + + if (d._SYSTEMD_UNIT == localStorage["filter"]) + j = i; + } + + if (j < 0) { + if (localStorage["filter"] != null && localStorage["filter"] != "") { + buf += ''; + j = i + 1; + } else + j = 0; + } + + f.innerHTML = buf; + f.selectedIndex = j; + } + + function onFilterFocus(w) { + var request = new XMLHttpRequest(); + request.open("GET", "/fields/_SYSTEMD_UNIT"); + request.onreadystatechange = onResultFilterFocus; + request.setRequestHeader("Accept", "application/json"); + request.send(null); + } + + function onFilterChange(w) { + if (w.selectedIndex <= 0) + localStorage["filter"] = ""; + else + localStorage["filter"] = unescape(w.options[w.selectedIndex].value); + + entriesLoadHead(); + } + + function onBootChange(w) { + localStorage["boot"] = w.checked ? "1" : "0"; + entriesLoadHead(); + } + + function initFilter() { + f = document.getElementById("filter"); + + var buf = ''; + + var filter = localStorage["filter"]; + if (filter != null && filter != "") { + buf += ''; + j = 1; + } else + j = 0; + + f.innerHTML = buf; + f.selectedIndex = j; + } + + function installHandlers() { + document.onkeyup = onKeyUp; + + logs = document.getElementById("divlogs"); + logs.addEventListener("mousewheel", onMouseWheel, false); + logs.addEventListener("DOMMouseScroll", onMouseWheel, false); + } + machineLoad(); entriesLoad(null); showNEntries(getNEntries()); - document.onkeyup = onKeyUp; - - logs = document.getElementById("divlogs"); - logs.addEventListener("mousewheel", onMouseWheel, false); - logs.addEventListener("DOMMouseScroll", onMouseWheel, false); + initFilter(); + installHandlers(); -- cgit v1.2.3-54-g00ecf