From 4316a4c08110da89966952bea3a37881178e296f Mon Sep 17 00:00:00 2001 From: Julien Olivain Date: Tue, 16 Jan 2024 19:35:12 +0100 Subject: [PATCH] support/testing: add sed runtime test Signed-off-by: Julien Olivain Signed-off-by: Yann E. MORIN --- DEVELOPERS | 1 + support/testing/tests/package/test_sed.py | 118 ++++++++++++++++++++++ 2 files changed, 119 insertions(+) create mode 100644 support/testing/tests/package/test_sed.py diff --git a/DEVELOPERS b/DEVELOPERS index 9d2b9a11ea..9528837dd0 100644 --- a/DEVELOPERS +++ b/DEVELOPERS @@ -1818,6 +1818,7 @@ F: support/testing/tests/package/test_python_spake2.py F: support/testing/tests/package/test_rdma_core.py F: support/testing/tests/package/test_rdma_core/ F: support/testing/tests/package/test_screen.py +F: support/testing/tests/package/test_sed.py F: support/testing/tests/package/test_stress_ng.py F: support/testing/tests/package/test_tcl.py F: support/testing/tests/package/test_tcl/ diff --git a/support/testing/tests/package/test_sed.py b/support/testing/tests/package/test_sed.py new file mode 100644 index 0000000000..0a0fdb890a --- /dev/null +++ b/support/testing/tests/package/test_sed.py @@ -0,0 +1,118 @@ +import os + +import infra.basetest + + +class TestSed(infra.basetest.BRTest): + config = infra.basetest.BASIC_TOOLCHAIN_CONFIG + \ + """ + BR2_PACKAGE_BUSYBOX_SHOW_OTHERS=y + BR2_PACKAGE_SED=y + BR2_TARGET_ROOTFS_CPIO=y + # BR2_TARGET_ROOTFS_TAR is not set + """ + + def check_gnu_sed(self): + in_file = "testfile.txt" + + # We create a test file for this test. + self.assertRunOk(f"echo 'This is a test' > {in_file}") + + # Check we have the GNU sed by testing a GNU extension likely + # not present in other implementation. See: + # https://www.gnu.org/software/sed/manual/sed.html#Extended-Commands + # Note: we cannot search for "GNU sed" in sed --version, + # because busybox sed --version outputs: "This is not GNU sed + # version 4.0". The 'F' and 'Q' sed commands are known to be + # unimplemented in BusyBox 1.36.1. + expected_code = 123 + sed_script = f"F;Q {expected_code}" + cmd = f"sed '{sed_script}' {in_file}" + output, exit_code = self.emulator.run(cmd) + self.assertEqual(exit_code, expected_code) + self.assertEqual(output, [in_file]) + + def check_sed_substitute(self): + testfile_num = 5 + + # We create few different test files for this test. + cmd = f'for i in $(seq {testfile_num}) ; do ' + cmd += 'echo "=== $i Hello ===" > file$i.txt ; ' + cmd += 'done' + self.assertRunOk(cmd) + + # We reformat file content, in-place. + sed_script = "s/^=== \\([0-9]*\\) \\(Hello\\) ===$/\\2 \\1/" + cmd = f"sed -i '{sed_script}' file[0-9]*.txt" + self.assertRunOk(cmd) + + # We substitute numbers with the string "Buildroot". We use an + # extended regular expression (with the '+'), so we test with + # the '-r' option. + sed_script = "s/[0-9]+/Buildroot/g" + cmd = f"sed -r -i '{sed_script}' file[0-9]*.txt" + self.assertRunOk(cmd) + + # Our previous text manipulations are expected to end up with + # the "Hello Buildroot" string in all files. + cmd = "cat file[0-9]*.txt" + output, exit_code = self.emulator.run(cmd) + self.assertEqual(exit_code, 0) + self.assertEqual(output, ["Hello Buildroot"] * testfile_num) + + def check_sed_line_count(self): + # We use the '=' command to count lines. + line_count = 1234 + cmd = f"seq {line_count} | sed -n '$='" + output, exit_code = self.emulator.run(cmd) + self.assertEqual(exit_code, 0) + self.assertEqual(int(output[0]), line_count) + + def check_sed_line_address(self): + input_file = "strings.txt" + expected_file = "expected.txt" + + # We create simple data for this test. + strings = ["one", "two", "three", "four", "five"] + content = '\\n'.join(strings) + cmd = f"echo -e \"{content}\" > {input_file}" + self.assertRunOk(cmd) + + # The manipulation in this tests are expected to extract the + # first and last of the input. We create the expected data for + # comparison. + expected_output = [strings[0], strings[-1]] + content = '\\n'.join(expected_output) + cmd = f"echo -e \"{content}\" > {expected_file}" + self.assertRunOk(cmd) + + # We remove lines between strings "two" and "four" included. + cmd = f"sed '/two/,/four/d' {input_file} > output1.txt" + self.assertRunOk(cmd) + + # We check output is the same as the expected data. + cmd = f"cmp {expected_file} output1.txt" + self.assertRunOk(cmd) + + # We redo the same manipulation using line number addresses. + cmd = f"sed -n '1p;5p' {input_file} > output2.txt" + self.assertRunOk(cmd) + + # We check again output is correct. + cmd = f"cmp {expected_file} output2.txt" + self.assertRunOk(cmd) + + def test_run(self): + cpio_file = os.path.join(self.builddir, "images", "rootfs.cpio") + self.emulator.boot(arch="armv5", + kernel="builtin", + options=["-initrd", cpio_file]) + self.emulator.login() + + # Check the program can execute + self.assertRunOk("sed --version") + + self.check_gnu_sed() + self.check_sed_substitute() + self.check_sed_line_count() + self.check_sed_line_address()