AT_BANNER([vlog])

AT_SETUP([vlog - Python3])
AT_CAPTURE_FILE([log_file])
AT_CAPTURE_FILE([stderr_log])
AT_CHECK([$PYTHON3 $srcdir/test-vlog.py --log-file log_file \
-v dbg module_1:info module_2:warn syslog:off 2>stderr_log])

AT_CHECK([sed -e 's/.*-.*-.*T..:..:..Z |//' \
-e 's/File ".*", line [[0-9]][[0-9]]*,/File <name>, line <number>,/' \
stderr_log], [0], [dnl
  0  | module_0 | EMER | emergency
  1  | module_0 | ERR | error
  2  | module_0 | WARN | warning
  3  | module_0 | INFO | information
  4  | module_0 | DBG | debug
  5  | module_0 | EMER | emergency exception
Traceback (most recent call last):
  File <name>, line <number>, in main
    assert fail
AssertionError
  6  | module_0 | ERR | error exception
Traceback (most recent call last):
  File <name>, line <number>, in main
    assert fail
AssertionError
  7  | module_0 | WARN | warn exception
Traceback (most recent call last):
  File <name>, line <number>, in main
    assert fail
AssertionError
  8  | module_0 | INFO | information exception
Traceback (most recent call last):
  File <name>, line <number>, in main
    assert fail
AssertionError
  9  | module_0 | DBG | debug exception
Traceback (most recent call last):
  File <name>, line <number>, in main
    assert fail
AssertionError
  10 | module_0 | ERR | exception
Traceback (most recent call last):
  File <name>, line <number>, in main
    assert fail
AssertionError
  11 | module_1 | EMER | emergency
  12 | module_1 | ERR | error
  13 | module_1 | WARN | warning
  14 | module_1 | INFO | information
  16 | module_1 | EMER | emergency exception
Traceback (most recent call last):
  File <name>, line <number>, in main
    assert fail
AssertionError
  17 | module_1 | ERR | error exception
Traceback (most recent call last):
  File <name>, line <number>, in main
    assert fail
AssertionError
  18 | module_1 | WARN | warn exception
Traceback (most recent call last):
  File <name>, line <number>, in main
    assert fail
AssertionError
  19 | module_1 | INFO | information exception
Traceback (most recent call last):
  File <name>, line <number>, in main
    assert fail
AssertionError
  21 | module_1 | ERR | exception
Traceback (most recent call last):
  File <name>, line <number>, in main
    assert fail
AssertionError
  22 | module_2 | EMER | emergency
  23 | module_2 | ERR | error
  24 | module_2 | WARN | warning
  27 | module_2 | EMER | emergency exception
Traceback (most recent call last):
  File <name>, line <number>, in main
    assert fail
AssertionError
  28 | module_2 | ERR | error exception
Traceback (most recent call last):
  File <name>, line <number>, in main
    assert fail
AssertionError
  29 | module_2 | WARN | warn exception
Traceback (most recent call last):
  File <name>, line <number>, in main
    assert fail
AssertionError
  32 | module_2 | ERR | exception
Traceback (most recent call last):
  File <name>, line <number>, in main
    assert fail
AssertionError
])

AT_CLEANUP

m4_divert_push([PREPARE_TESTS])
vlog_filt () {
    sed 's/.*\(opened log file\).*/\1/
s/.*|//' "$@"
}
m4_divert_pop([PREPARE_TESTS])

AT_SETUP([vlog - vlog/reopen - C])
# This test won't work as-is on Windows because Windows doesn't allow
# files that are open to be renamed.
AT_SKIP_IF([test "$IS_WIN32" = "yes"])
on_exit 'kill `cat test-unixctl.pid`'

AT_CAPTURE_FILE([log])
AT_CAPTURE_FILE([log.old])
AT_CHECK([ovstest test-unixctl --log-file=`pwd`/log --pidfile --detach --no-chdir],
  [0], [], [stderr])
AT_CHECK([vlog_filt stderr], [0],
  [opened log file
])

AT_CHECK([APPCTL -t test-unixctl log message])
mv log log.old
AT_CHECK([APPCTL -t test-unixctl log message2])
AT_CHECK([APPCTL -t test-unixctl vlog/reopen])
AT_CHECK([APPCTL -t test-unixctl log message3])
AT_CHECK([APPCTL -t test-unixctl exit])

AT_CHECK([vlog_filt log.old], [0], [dnl
opened log file
Entering run loop.
message
message2
closing log file
])
AT_CHECK([vlog_filt log], [0], [dnl
opened log file
message3
])
AT_CLEANUP

AT_SETUP([vlog - vlog/reopen - Python3])
# This test won't work as-is on Windows because Windows doesn't allow
# files that are open to be renamed.
AT_SKIP_IF([test "$IS_WIN32" = "yes"])
on_exit 'kill `cat test-unixctl.py.pid`'

AT_CAPTURE_FILE([log])
AT_CAPTURE_FILE([log.old])
AT_CHECK([$PYTHON3 $srcdir/test-unixctl.py --log-file=`pwd`/log --pidfile --detach --no-chdir])

AT_CHECK([APPCTL -t test-unixctl.py log message])
mv log log.old
AT_CHECK([APPCTL -t test-unixctl.py log message2])
AT_CHECK([APPCTL -t test-unixctl.py vlog/reopen])
AT_CHECK([APPCTL -t test-unixctl.py log message3])
AT_CHECK([APPCTL -t test-unixctl.py exit])

AT_CHECK([sed 's/.*|//' log.old], [0], [dnl
 Entering run loop.
 message
 message2
])
AT_CHECK([sed 's/.*|//' log], [0], [dnl
 message3
])
AT_CLEANUP

AT_SETUP([vlog - vlog/reopen without log file - C])
on_exit 'kill `cat test-unixctl.pid`'

AT_CHECK([ovstest test-unixctl --pidfile --detach --no-chdir])

AT_CHECK([APPCTL -t test-unixctl vlog/reopen], [2], [],
  [Logging to file not configured
ovs-appctl: test-unixctl: server returned an error
])
OVS_APP_EXIT_AND_WAIT([test-unixctl])
AT_CLEANUP

AT_SETUP([vlog - vlog/reopen without log file - Python3])
on_exit 'kill `cat test-unixctl.py.pid`'

AT_CHECK([$PYTHON3 $srcdir/test-unixctl.py --pidfile --detach --no-chdir])

AT_CHECK([APPCTL -t test-unixctl.py vlog/reopen], [0],
  [Logging to file not configured
])
AT_CLEANUP

dnl This checks that if vlog/reopen can't reopen the log file,
dnl nothing particularly bad (e.g. a crash) happens.
AT_SETUP([vlog - vlog/reopen can't reopen log file - C])
# Verify that /dev/full is a character device that fails writes.
AT_SKIP_IF([test ! -c /dev/full])
AT_SKIP_IF([echo > /dev/full])

on_exit 'kill `cat test-unixctl.pid`'

AT_CHECK([ovstest test-unixctl --log-file=`pwd`/log --pidfile --detach --no-chdir],
  [0], [], [stderr])
AT_CHECK([vlog_filt stderr], [0], [opened log file
])

AT_CHECK([APPCTL -t test-unixctl log message])
mv log log.old
ln -s /dev/full log
AT_CHECK([APPCTL -t test-unixctl vlog/reopen])
AT_CHECK([APPCTL -t test-unixctl log message2])
rm log
AT_CHECK([APPCTL -t test-unixctl vlog/reopen])
AT_CHECK([APPCTL -t test-unixctl log message3])
AT_CHECK([APPCTL -t test-unixctl exit])
AT_CHECK([vlog_filt log.old], [0], [dnl
opened log file
Entering run loop.
message
closing log file
])
AT_CHECK([vlog_filt log], [0], [dnl
opened log file
message3
])
AT_CLEANUP

dnl This checks that if vlog/reopen can't reopen the log file,
dnl nothing particularly bad (e.g. Python throws an exception and
dnl aborts the program) happens.
AT_SETUP([vlog - vlog/reopen can't reopen log file - Python3])

# Verify that /dev/full is a character device that fails writes.
AT_SKIP_IF([test ! -c /dev/full])
AT_SKIP_IF([echo > /dev/full])

on_exit 'kill `cat test-unixctl.py.pid`'

AT_CHECK([$PYTHON3 $srcdir/test-unixctl.py --log-file=`pwd`/log --pidfile --detach --no-chdir])
AT_CHECK([APPCTL -t test-unixctl.py log message])
mv log log.old
ln -s /dev/full log
AT_CHECK([APPCTL -t test-unixctl.py vlog/reopen])
AT_CHECK([APPCTL -t test-unixctl.py log message2])
rm log
AT_CHECK([APPCTL -t test-unixctl.py vlog/reopen])
AT_CHECK([APPCTL -t test-unixctl.py log message3])
AT_CHECK([APPCTL -t test-unixctl.py exit])
AT_CHECK([sed 's/.*|//' log.old], [0], [dnl
 Entering run loop.
 message
])
AT_CHECK([sed 's/.*|//' log], [0], [dnl
 message3
])
AT_CLEANUP

AT_SETUP([vlog - vlog/close - C])
on_exit 'kill `cat test-unixctl.pid`'

AT_CAPTURE_FILE([log])
AT_CAPTURE_FILE([log.old])
AT_CHECK([ovstest test-unixctl --log-file=`pwd`/log --pidfile --detach --no-chdir],
  [0], [], [ignore])
AT_CHECK([vlog_filt log], [0], [opened log file
Entering run loop.
])

AT_CHECK([APPCTL -t test-unixctl log message])
AT_CHECK([APPCTL -t test-unixctl log message2])

# After closing the log file, message3 won't appear anywhere.
AT_CHECK([APPCTL -t test-unixctl vlog/close])
mv log log.old
AT_CHECK([APPCTL -t test-unixctl log message3])

# Closing the log file again is harmless.
AT_CHECK([APPCTL -t test-unixctl vlog/close])
AT_CHECK([APPCTL -t test-unixctl log message4])

# After reopening the log file, further messages start appearing again.
AT_CHECK([APPCTL -t test-unixctl vlog/reopen])
AT_CHECK([APPCTL -t test-unixctl log message5])
AT_CHECK([APPCTL -t test-unixctl exit])

AT_CHECK([vlog_filt log.old], [0], [dnl
opened log file
Entering run loop.
message
message2
])
AT_CHECK([vlog_filt log], [0], [dnl
opened log file
message5
])
AT_CLEANUP

AT_SETUP([vlog - vlog/close - Python3])
on_exit 'kill `cat test-unixctl.py.pid`'

AT_CAPTURE_FILE([log])
AT_CAPTURE_FILE([log.old])
AT_CHECK([$PYTHON3 $srcdir/test-unixctl.py --log-file=`pwd`/log --pidfile --detach --no-chdir])

AT_CHECK([APPCTL -t test-unixctl.py log message])
AT_CHECK([APPCTL -t test-unixctl.py log message2])

# After closing the log file, message3 won't appear anywhere.
AT_CHECK([APPCTL -t test-unixctl.py vlog/close])
mv log log.old
AT_CHECK([APPCTL -t test-unixctl.py log message3])

# Closing the log file again is harmless.
AT_CHECK([APPCTL -t test-unixctl.py vlog/close])
AT_CHECK([APPCTL -t test-unixctl.py log message4])

# After reopening the log file, further messages start appearing again.
AT_CHECK([APPCTL -t test-unixctl.py vlog/reopen])
AT_CHECK([APPCTL -t test-unixctl.py log message5])
AT_CHECK([APPCTL -t test-unixctl.py exit])

AT_CHECK([sed 's/.*|//' log.old], [0], [dnl
 Entering run loop.
 message
 message2
])
AT_CHECK([sed 's/.*|//' log], [0], [dnl
 message5
])
AT_CLEANUP

AT_SETUP([vlog - vlog/set and vlog/list - C])
on_exit 'kill `cat test-unixctl.pid`'

AT_CAPTURE_FILE([log])
AT_CHECK([ovstest test-unixctl --log-file=`pwd`/log --pidfile --detach --no-chdir],
  [0], [], [ignore])
AT_CHECK([vlog_filt log], [0], [opened log file
Entering run loop.
])

AT_CHECK([APPCTL -t test-unixctl vlog/list | sed -n '1,2p
/test_unixctl /p; /daemon /p'], [0], [dnl
                 console    syslog    file
                 -------    ------    ------
daemon             OFF       INFO       INFO
test_unixctl       OFF       INFO       INFO
])

AT_CHECK([APPCTL -t test-unixctl vlog/set daemon:syslog:err])
AT_CHECK([APPCTL -t test-unixctl vlog/set file:dbg])
AT_CHECK([APPCTL -t test-unixctl vlog/set nonexistent], [2], [],
  [no destination, level, or module "nonexistent"
ovs-appctl: test-unixctl: server returned an error
])
AT_CHECK([APPCTL -t test-unixctl vlog/list | sed -n '1,2p
/test_unixctl /p; /daemon /p'], [0], [dnl
                 console    syslog    file
                 -------    ------    ------
daemon             OFF        ERR        DBG
test_unixctl       OFF       INFO        DBG
])

AT_CHECK([APPCTL -t test-unixctl vlog/set pattern], [2], [],
  [missing destination
ovs-appctl: test-unixctl: server returned an error
])
AT_CHECK([APPCTL -t test-unixctl vlog/set pattern:nonexistent], [2], [],
  [unknown destination "nonexistent"
ovs-appctl: test-unixctl: server returned an error
])
AT_CHECK([APPCTL -t test-unixctl vlog/set pattern:file:'I<3OVS|%m'])
AT_CHECK([APPCTL -t test-unixctl log patterntest])
AT_CHECK([grep -q 'I<3OVS' log])
OVS_APP_EXIT_AND_WAIT([test-unixctl])
AT_CLEANUP

AT_SETUP([vlog - vlog/set and vlog/list - Python3])
on_exit 'kill `cat test-unixctl.py.pid`'

AT_CAPTURE_FILE([log])
AT_CHECK([$PYTHON3 $srcdir/test-unixctl.py --log-file=`pwd`/log --pidfile --detach --no-chdir])

AT_CHECK([APPCTL -t test-unixctl.py vlog/list], [0], [dnl
                 console    syslog    file
                 -------    ------    ------
daemon            info       info       info
fatal-signal      info       info       info
jsonrpc           info       info       info
poller            info       info       info
reconnect         info       info       info
socket_util       info       info       info
stream            info       info       info
test-unixctl      info       info       info
unixctl_server    info       info       info
])

   AT_CHECK([APPCTL -t test-unixctl.py vlog/set daemon:syslog:err])
   AT_CHECK([APPCTL -t test-unixctl.py vlog/set file:dbg])
   AT_CHECK([APPCTL -t test-unixctl.py vlog/set nonexistent], [0],
  [no destination, level, or module "nonexistent"
])
   AT_CHECK([APPCTL -t test-unixctl.py vlog/list], [0], [dnl
                 console    syslog    file
                 -------    ------    ------
daemon            info        err        dbg
fatal-signal      info       info        dbg
jsonrpc           info       info        dbg
poller            info       info        dbg
reconnect         info       info        dbg
socket_util       info       info        dbg
stream            info       info        dbg
test-unixctl      info       info        dbg
unixctl_server    info       info        dbg
])

AT_CHECK([APPCTL -t test-unixctl.py vlog/set pattern], [0],
  [Please supply a valid pattern and destination
])
AT_CHECK([APPCTL -t test-unixctl.py vlog/set pattern:nonexistent], [0],
  [Destination nonexistent does not exist
])
AT_CHECK([APPCTL -t test-unixctl.py vlog/set pattern:file:'I<3OVS|%m'])
AT_CHECK([APPCTL -t test-unixctl.py log patterntest])
AT_CHECK([grep -q 'I<3OVS' log])
AT_CLEANUP

AT_SETUP([vlog - RFC5424 facility])
on_exit 'kill `cat ovsdb-server.pid`'

dnl Create database.
touch .conf.db.~lock~
AT_CHECK([ovsdb-tool create conf.db $abs_top_srcdir/vswitchd/vswitch.ovsschema])

AT_CHECK([ovsdb-server --detach --no-chdir --pidfile \
          --remote=punix:$OVS_RUNDIR/db.sock -vPATTERN:file:"<%B>1 %A %m" \
          --log-file], [0], [], [stderr])
OVS_APP_EXIT_AND_WAIT([ovsdb-server])

# A default facility of LOG_LOCAL0 while writing to file.
AT_CHECK([head -1 ovsdb-server.log | awk '{print $1}'], [0], [<133>1
])
rm ovsdb-server.log

AT_CHECK([ovsdb-server --detach --no-chdir --pidfile \
          --remote=punix:$OVS_RUNDIR/db.sock -vPATTERN:file:"<%B>1 %A %m" \
          -vFACILITY:daemon --log-file], [0], [], [stderr])

AT_CHECK([head -1 ovsdb-server.log | awk '{print $1}'], [0], [<29>1
])

AT_CHECK([ovs-appctl -t ovsdb-server vlog/set FACILITY:invalid], [2], [],
[invalid facility
ovs-appctl: ovsdb-server: server returned an error
])

AT_CHECK([ovs-appctl -t ovsdb-server vlog/set FACILITY:local7])
AT_CHECK([ovs-appctl -t ovsdb-server vlog/set ANY:file:DBG])
OVS_APP_EXIT_AND_WAIT([ovsdb-server])

AT_CHECK([tail -1 ovsdb-server.log | awk '{print $1}'], [0], [<191>1
])
AT_CLEANUP

AT_SETUP([vlog - RFC5424 facility - Python3])
on_exit 'kill `cat test-unixctl.py.pid`'

AT_CHECK([$PYTHON3 $srcdir/test-unixctl.py --log-file=`pwd`/log --pidfile \
-vFACILITY:invalid --detach --no-chdir], [1], [], [test-unixctl.py: processing "FACILITY:invalid": Facility invalid is invalid
])

AT_CHECK([$PYTHON3 $srcdir/test-unixctl.py --log-file=`pwd`/log --pidfile \
-vFACILITY:daemon --detach --no-chdir])

AT_CHECK([ovs-appctl -t test-unixctl.py vlog/set FACILITY:invalid], [0],
[Facility invalid is invalid
])

AT_CHECK([ovs-appctl -t test-unixctl.py vlog/set FACILITY:local0])
AT_CLEANUP
