From 241c5c6da8303e31032646ff5bff7fd81f5200f8 Mon Sep 17 00:00:00 2001 From: Kevin Veen-Birkenbach Date: Wed, 16 Jul 2025 08:25:16 +0200 Subject: [PATCH] Optimized test_main.py --- tests/unit/test_main.py | 72 ++++++++++++++++++++++++++++++++++++ utils/test_main.py | 81 ----------------------------------------- 2 files changed, 72 insertions(+), 81 deletions(-) create mode 100644 tests/unit/test_main.py delete mode 100644 utils/test_main.py diff --git a/tests/unit/test_main.py b/tests/unit/test_main.py new file mode 100644 index 00000000..604c2618 --- /dev/null +++ b/tests/unit/test_main.py @@ -0,0 +1,72 @@ +import os +import sys +import tempfile +import unittest +from unittest import mock + +# Insert project root into import path so we can import main.py +sys.path.insert( + 0, + os.path.abspath(os.path.join(os.path.dirname(__file__), "../../")) +) + +import main # assumes main.py lives at the project root + + +class TestMainHelpers(unittest.TestCase): + def test_format_command_help_basic(self): + name = "cmd" + description = "A basic description" + output = main.format_command_help( + name, description, + indent=2, col_width=20, width=40 + ) + # Should start with two spaces and the command name + self.assertTrue(output.startswith(" cmd")) + # Description should appear somewhere in the wrapped text + self.assertIn("A basic description", output) + + def test_list_cli_commands_filters_and_sorts(self): + # Create a temporary directory with sample files containing argparse + with tempfile.TemporaryDirectory() as tmpdir: + # Create Python files that import argparse + one_path = os.path.join(tmpdir, "one.py") + with open(one_path, "w") as f: + f.write("import argparse\n# dummy CLI command\n") + + two_path = os.path.join(tmpdir, "two.py") + with open(two_path, "w") as f: + f.write("import argparse\n# another CLI command\n") + + # Non-Python and dunder files should be ignored + open(os.path.join(tmpdir, "__init__.py"), "w").close() + open(os.path.join(tmpdir, "ignore.txt"), "w").close() + + # Only 'one' and 'two' should be returned, in sorted order + commands = main.list_cli_commands(tmpdir) + self.assertEqual([(None, 'one'), (None, 'two')], commands) + + def test_git_clean_repo_invokes_git_clean(self): + with mock.patch('main.subprocess.run') as mock_run: + main.git_clean_repo() + mock_run.assert_called_once_with(['git', 'clean', '-Xfd'], check=True) + + @mock.patch('main.subprocess.run') + def test_extract_description_via_help_with_description(self, mock_run): + # Simulate subprocess returning help output with a description + mock_stdout = "usage: dummy.py [options]\n\nThis is a help description.\n" + mock_run.return_value = mock.Mock(stdout=mock_stdout) + description = main.extract_description_via_help("/fake/path/dummy.py") + self.assertEqual(description, "This is a help description.") + + @mock.patch('main.subprocess.run') + def test_extract_description_via_help_without_description(self, mock_run): + # Simulate subprocess returning help output without a description + mock_stdout = "usage: empty.py [options]\n" + mock_run.return_value = mock.Mock(stdout=mock_stdout) + description = main.extract_description_via_help("/fake/path/empty.py") + self.assertEqual(description, "-") + + +if __name__ == "__main__": + unittest.main() diff --git a/utils/test_main.py b/utils/test_main.py deleted file mode 100644 index 48db9489..00000000 --- a/utils/test_main.py +++ /dev/null @@ -1,81 +0,0 @@ -import os -import sys -import stat -import tempfile -import unittest -from unittest import mock - -# Insert project root into import path so we can import main.py -sys.path.insert( - 0, - os.path.abspath(os.path.join(os.path.dirname(__file__), "../../")) -) - -import main # assumes main.py lives at the project root - - -class TestMainHelpers(unittest.TestCase): - def test_format_command_help_basic(self): - name = "cmd" - description = "A basic description" - output = main.format_command_help( - name, description, - indent=2, col_width=20, width=40 - ) - # Should start with two spaces and the command name - self.assertTrue(output.startswith(" cmd")) - # Description should appear somewhere in the wrapped text - self.assertIn("A basic description", output) - - def test_list_cli_commands_filters_and_sorts(self): - # Create a temporary directory with sample files - with tempfile.TemporaryDirectory() as tmpdir: - open(os.path.join(tmpdir, "one.py"), "w").close() - open(os.path.join(tmpdir, "__init__.py"), "w").close() - open(os.path.join(tmpdir, "ignore.txt"), "w").close() - open(os.path.join(tmpdir, "two.py"), "w").close() - - # Only 'one' and 'two' should be returned, in sorted order - commands = main.list_cli_commands(tmpdir) - self.assertEqual(commands, ["one", "two"]) - - def test_git_clean_repo_invokes_git_clean(self): - with mock.patch('main.subprocess.run') as mock_run: - main.git_clean_repo() - mock_run.assert_called_once_with(['git', 'clean', '-Xfd'], check=True) - - def test_extract_description_via_help_with_description(self): - # Create a dummy script that prints a help description - with tempfile.TemporaryDirectory() as tmpdir: - script_path = os.path.join(tmpdir, "dummy.py") - with open(script_path, "w") as f: - f.write( - "#!/usr/bin/env python3\n" - "import sys\n" - "if '--help' in sys.argv:\n" - " print('usage: dummy.py [options]')\n" - " print()\n" - " print('This is a help description.')\n" - ) - # Make it executable - mode = os.stat(script_path).st_mode - os.chmod(script_path, mode | stat.S_IXUSR) - - description = main.extract_description_via_help(script_path) - self.assertEqual(description, "This is a help description.") - - def test_extract_description_via_help_without_description(self): - # Script that has no help description - with tempfile.TemporaryDirectory() as tmpdir: - script_path = os.path.join(tmpdir, "empty.py") - with open(script_path, "w") as f: - f.write( - "#!/usr/bin/env python3\n" - "print('no help here')\n" - ) - description = main.extract_description_via_help(script_path) - self.assertEqual(description, "-") - - -if __name__ == "__main__": - unittest.main()