journalctl: add --truncate-newline option

This commit is contained in:
zhmylove 2022-08-30 18:50:19 +03:00 committed by Lennart Poettering
parent 9a109e7cd6
commit 61cecfa0d8
8 changed files with 57 additions and 14 deletions

View file

@ -429,6 +429,13 @@
precision.</para></listitem>
</varlistentry>
<varlistentry>
<term><option>--truncate-newline</option></term>
<listitem><para>Truncate each log message at the first newline character on output, so that only the
first line of each message is displayed.</para></listitem>
</varlistentry>
<varlistentry>
<term><option>short-precise</option></term>
<listitem><para>is very similar, but shows classic syslog timestamps with full microsecond

View file

@ -170,10 +170,15 @@ char *delete_trailing_chars(char *s, const char *bad) {
return s;
}
char *truncate_nl(char *s) {
char *truncate_nl_full(char *s, size_t *ret_len) {
size_t n;
assert(s);
s[strcspn(s, NEWLINE)] = 0;
n = strcspn(s, NEWLINE);
s[n] = '\0';
if (ret_len)
*ret_len = n;
return s;
}

View file

@ -121,7 +121,10 @@ char *strjoin_real(const char *x, ...) _sentinel_;
char *strstrip(char *s);
char *delete_chars(char *s, const char *bad);
char *delete_trailing_chars(char *s, const char *bad);
char *truncate_nl(char *s);
char *truncate_nl_full(char *s, size_t *ret_len);
static inline char *truncate_nl(char *s) {
return truncate_nl_full(s, NULL);
}
static inline char *skip_leading_chars(const char *s, const char *bad) {
if (!s)

View file

@ -96,6 +96,7 @@ static bool arg_all = false;
static PagerFlags arg_pager_flags = 0;
static int arg_lines = ARG_LINES_DEFAULT;
static bool arg_no_tail = false;
static bool arg_truncate_newline = false;
static bool arg_quiet = false;
static bool arg_merge = false;
static bool arg_boot = false;
@ -367,6 +368,7 @@ static int help(void) {
" -a --all Show all fields, including long and unprintable\n"
" -f --follow Follow the journal\n"
" --no-tail Show all lines, even in follow mode\n"
" --truncate-newline Truncate entries by first newline character\n"
" -q --quiet Do not show info messages and privilege warning\n"
"\n%3$sPager Control Options:%4$s\n"
" --no-pager Do not pipe output into a pager\n"
@ -445,6 +447,7 @@ static int parse_argv(int argc, char *argv[]) {
ARG_RELINQUISH_VAR,
ARG_SMART_RELINQUISH_VAR,
ARG_ROTATE,
ARG_TRUNCATE_NEWLINE,
ARG_VACUUM_SIZE,
ARG_VACUUM_FILES,
ARG_VACUUM_TIME,
@ -465,6 +468,7 @@ static int parse_argv(int argc, char *argv[]) {
{ "full", no_argument, NULL, 'l' },
{ "no-full", no_argument, NULL, ARG_NO_FULL },
{ "lines", optional_argument, NULL, 'n' },
{ "truncate-newline", no_argument, NULL, ARG_TRUNCATE_NEWLINE },
{ "no-tail", no_argument, NULL, ARG_NO_TAIL },
{ "new-id128", no_argument, NULL, ARG_NEW_ID128 }, /* deprecated */
{ "quiet", no_argument, NULL, 'q' },
@ -622,6 +626,10 @@ static int parse_argv(int argc, char *argv[]) {
arg_no_tail = true;
break;
case ARG_TRUNCATE_NEWLINE:
arg_truncate_newline = true;
break;
case ARG_NEW_ID128:
arg_action = ACTION_NEW_ID128;
break;
@ -2229,6 +2237,7 @@ static int show(Context *c) {
colors_enabled() * OUTPUT_COLOR |
arg_catalog * OUTPUT_CATALOG |
arg_utc * OUTPUT_UTC |
arg_truncate_newline * OUTPUT_TRUNCATE_NEWLINE |
arg_no_hostname * OUTPUT_NO_HOSTNAME;
r = show_journal_entry(stdout, j, arg_output, 0, flags,

View file

@ -524,6 +524,9 @@ static int output_short(
if (!(flags & OUTPUT_SHOW_ALL))
strip_tab_ansi(&message, &message_len, highlight_shifted);
if (flags & OUTPUT_TRUNCATE_NEWLINE)
truncate_nl_full(message, &message_len);
if (priority_len == 1 && *priority >= '0' && *priority <= '7')
p = *priority - '0';

View file

@ -33,21 +33,22 @@ static inline bool OUTPUT_MODE_IS_JSON(OutputMode m) {
* logs output, others only to the process tree output. */
typedef enum OutputFlags {
OUTPUT_SHOW_ALL = 1 << 0,
OUTPUT_FULL_WIDTH = 1 << 1,
OUTPUT_COLOR = 1 << 2,
OUTPUT_SHOW_ALL = 1 << 0,
OUTPUT_FULL_WIDTH = 1 << 1,
OUTPUT_COLOR = 1 << 2,
/* Specific to log output */
OUTPUT_WARN_CUTOFF = 1 << 3,
OUTPUT_CATALOG = 1 << 4,
OUTPUT_BEGIN_NEWLINE = 1 << 5,
OUTPUT_UTC = 1 << 6,
OUTPUT_NO_HOSTNAME = 1 << 7,
OUTPUT_WARN_CUTOFF = 1 << 3,
OUTPUT_CATALOG = 1 << 4,
OUTPUT_BEGIN_NEWLINE = 1 << 5,
OUTPUT_UTC = 1 << 6,
OUTPUT_NO_HOSTNAME = 1 << 7,
OUTPUT_TRUNCATE_NEWLINE = 1 << 8,
/* Specific to process tree output */
OUTPUT_KERNEL_THREADS = 1 << 8,
OUTPUT_CGROUP_XATTRS = 1 << 9,
OUTPUT_CGROUP_ID = 1 << 10,
OUTPUT_KERNEL_THREADS = 1 << 9,
OUTPUT_CGROUP_XATTRS = 1 << 10,
OUTPUT_CGROUP_ID = 1 << 11,
} OutputFlags;
JsonFormatFlags output_mode_to_json_format_flags(OutputMode m);

View file

@ -14,6 +14,10 @@ test_append_files() {
cp -av "${TEST_BASE_DIR:?}/test-journals/"* "$workspace/test-journals/"
inst_binary unzstd
(
command -v logger >/dev/null 2>&1 && inst_binary logger
)
}
do_test "$@"

View file

@ -51,6 +51,17 @@ grep -q '^PRIORITY=6$' /tmp/output
(! grep '^FOO=' /tmp/output)
(! grep '^SYSLOG_FACILITY=' /tmp/output)
# --truncate shows only first line, skip under asan due to logger
if [ -z "${ASAN_OPTIONS+x}${UBSAN_OPTIONS+x}" ] && command -v logger >/dev/null 2>&1 ;then
ID=$(journalctl --new-id128 | sed -n 2p)
logger -t "$ID" $'HEAD\nTAIL\nTAIL'
journalctl --sync
journalctl -q -b -t "$ID" | grep -q HEAD
journalctl -q -b -t "$ID" | grep -q TAIL
journalctl -q -b -t "$ID" --truncate-newline | grep -q HEAD
journalctl -q -b -t "$ID" --truncate-newline | grep -q -v TAIL
fi
# '-b all' negates earlier use of -b (-b and -m are otherwise exclusive)
journalctl -b -1 -b all -m >/dev/null