From 202a219d8261fd9051ec5eee3a799bdb3c2739e7 Mon Sep 17 00:00:00 2001 From: "Paul Gauthier (aider)" Date: Sat, 28 Sep 2024 14:44:00 -0700 Subject: [PATCH] test: add tests for the /copy command including success, no messages, and exception handling --- tests/basic/test_commands.py | 62 +++++++++++++++++++++++++++++++++++- 1 file changed, 61 insertions(+), 1 deletion(-) diff --git a/tests/basic/test_commands.py b/tests/basic/test_commands.py index 45b5dc90c..363efd1b5 100644 --- a/tests/basic/test_commands.py +++ b/tests/basic/test_commands.py @@ -3,6 +3,7 @@ import os import shutil import sys import tempfile +import pyperclip from io import StringIO from pathlib import Path from unittest import TestCase, mock @@ -45,7 +46,66 @@ class TestCommands(TestCase): self.assertTrue(os.path.exists("foo.txt")) self.assertTrue(os.path.exists("bar.txt")) - def test_cmd_add_bad_glob(self): + def test_cmd_copy(self): + # Initialize InputOutput and Coder instances + io = InputOutput(pretty=False, yes=True) + coder = Coder.create(self.GPT35, None, io) + commands = Commands(io, coder) + + # Add some assistant messages to the chat history + coder.done_messages = [ + {"role": "assistant", "content": "First assistant message"}, + {"role": "user", "content": "User message"}, + {"role": "assistant", "content": "Second assistant message"}, + ] + + # Mock pyperclip.copy and io.tool_output + with mock.patch("pyperclip.copy") as mock_copy, \ + mock.patch.object(io, 'tool_output') as mock_tool_output: + + # Invoke the /copy command + commands.cmd_copy("") + + # Assert pyperclip.copy was called with the last assistant message + mock_copy.assert_called_once_with("Second assistant message") + + # Assert that tool_output was called with the expected preview + expected_preview = "Copied last assistant message to clipboard. Preview: Second assistant message" + mock_tool_output.assert_any_call(expected_preview) + + def test_cmd_copy_no_assistant_messages(self): + io = InputOutput(pretty=False, yes=True) + coder = Coder.create(self.GPT35, None, io) + commands = Commands(io, coder) + + # Add only user messages + coder.done_messages = [ + {"role": "user", "content": "User message"}, + ] + + # Mock io.tool_error + with mock.patch.object(io, 'tool_error') as mock_tool_error: + commands.cmd_copy("") + # Assert tool_error was called indicating no assistant messages + mock_tool_error.assert_called_once_with("No assistant messages found to copy.") + + def test_cmd_copy_pyperclip_exception(self): + io = InputOutput(pretty=False, yes=True) + coder = Coder.create(self.GPT35, None, io) + commands = Commands(io, coder) + + coder.done_messages = [ + {"role": "assistant", "content": "Assistant message"}, + ] + + # Mock pyperclip.copy to raise an exception + with mock.patch("pyperclip.copy", side_effect=pyperclip.PyperclipException("Clipboard error")), \ + mock.patch.object(io, 'tool_error') as mock_tool_error: + + commands.cmd_copy("") + + # Assert that tool_error was called with the clipboard error message + mock_tool_error.assert_called_once_with("Failed to copy to clipboard: Clipboard error") # https://github.com/paul-gauthier/aider/issues/293 io = InputOutput(pretty=False, yes=False)