blob: 3633d1f188174d44bc3ce4cf312779d323ba256f [file] [log] [blame]
James Kuszmauld42edb42022-01-07 18:00:16 -08001#include "aos/starter/subprocess.h"
2
Philipp Schrader790cb542023-07-05 21:06:52 -07003#include "gtest/gtest.h"
4
James Kuszmauld42edb42022-01-07 18:00:16 -08005#include "aos/events/shm_event_loop.h"
6#include "aos/testing/path.h"
7#include "aos/testing/tmpdir.h"
8#include "aos/util/file.h"
James Kuszmauld42edb42022-01-07 18:00:16 -08009
10namespace aos::starter::testing {
11
12class SubprocessTest : public ::testing::Test {
13 protected:
14 SubprocessTest() : shm_dir_(aos::testing::TestTmpDir() + "/aos") {
15 FLAGS_shm_base = shm_dir_;
16
17 // Nuke the shm dir:
18 aos::util::UnlinkRecursive(shm_dir_);
19 }
20
21 gflags::FlagSaver flag_saver_;
22 std::string shm_dir_;
23};
24
25TEST_F(SubprocessTest, CaptureOutputs) {
26 const std::string config_file =
27 ::aos::testing::ArtifactPath("aos/events/pingpong_config.json");
28
29 aos::FlatbufferDetachedBuffer<aos::Configuration> config =
30 aos::configuration::ReadConfig(config_file);
31 aos::ShmEventLoop event_loop(&config.message());
32 bool observed_stopped = false;
33 Application echo_stdout(
34 "echo", "echo", &event_loop, [&observed_stopped, &echo_stdout]() {
35 if (echo_stdout.status() == aos::starter::State::STOPPED) {
36 observed_stopped = true;
37 }
38 });
39 ASSERT_FALSE(echo_stdout.autorestart());
40 echo_stdout.set_args({"abcdef"});
41 echo_stdout.set_capture_stdout(true);
42 echo_stdout.set_capture_stderr(true);
43
44 echo_stdout.Start();
45 aos::TimerHandler *exit_timer =
46 event_loop.AddTimer([&event_loop]() { event_loop.Exit(); });
47 event_loop.OnRun([&event_loop, exit_timer]() {
Austin Schuh63851a42022-05-16 13:31:37 -070048 // Note: we are using the backup poll in this test to capture SIGCHLD. This
49 // runs at 1 hz, so make sure we let it run at least once.
Philipp Schradera6712522023-07-05 20:25:11 -070050 exit_timer->Schedule(event_loop.monotonic_now() +
51 std::chrono::milliseconds(1500));
James Kuszmauld42edb42022-01-07 18:00:16 -080052 });
53
54 event_loop.Run();
55
James Kuszmauld42edb42022-01-07 18:00:16 -080056 ASSERT_EQ("abcdef\n", echo_stdout.GetStdout());
57 ASSERT_TRUE(echo_stdout.GetStderr().empty());
58 EXPECT_TRUE(observed_stopped);
59 EXPECT_EQ(aos::starter::State::STOPPED, echo_stdout.status());
60
61 observed_stopped = false;
62
63 // Run again, the output should've been cleared.
64 echo_stdout.set_args({"ghijkl"});
65 echo_stdout.Start();
66 event_loop.Run();
67 ASSERT_EQ("ghijkl\n", echo_stdout.GetStdout());
68 EXPECT_TRUE(observed_stopped);
69}
70
71TEST_F(SubprocessTest, CaptureStderr) {
72 const std::string config_file =
73 ::aos::testing::ArtifactPath("aos/events/pingpong_config.json");
74
75 aos::FlatbufferDetachedBuffer<aos::Configuration> config =
76 aos::configuration::ReadConfig(config_file);
77 aos::ShmEventLoop event_loop(&config.message());
78 bool observed_stopped = false;
79 Application echo_stderr(
80 "echo", "sh", &event_loop, [&observed_stopped, &echo_stderr]() {
81 if (echo_stderr.status() == aos::starter::State::STOPPED) {
82 observed_stopped = true;
83 }
84 });
85 echo_stderr.set_args({"-c", "echo abcdef >&2"});
86 echo_stderr.set_capture_stdout(true);
87 echo_stderr.set_capture_stderr(true);
88
89 echo_stderr.Start();
Austin Schuh63851a42022-05-16 13:31:37 -070090 // Note: we are using the backup poll in this test to capture SIGCHLD. This
91 // runs at 1 hz, so make sure we let it run at least once.
James Kuszmauld42edb42022-01-07 18:00:16 -080092 event_loop.AddTimer([&event_loop]() { event_loop.Exit(); })
Philipp Schradera6712522023-07-05 20:25:11 -070093 ->Schedule(event_loop.monotonic_now() + std::chrono::milliseconds(1500));
James Kuszmauld42edb42022-01-07 18:00:16 -080094
95 event_loop.Run();
96
97 ASSERT_EQ("abcdef\n", echo_stderr.GetStderr());
98 ASSERT_TRUE(echo_stderr.GetStdout().empty());
99 ASSERT_TRUE(observed_stopped);
100 ASSERT_EQ(aos::starter::State::STOPPED, echo_stderr.status());
101}
102
103} // namespace aos::starter::testing