Implemented checks to ensure files with uncommitted changes or not present in previous commit cannot be undone safely.

This commit is contained in:
Paul Gauthier 2024-07-18 16:32:45 +01:00 committed by Paul Gauthier (aider)
parent e7f29c2dbc
commit 3ce3799f8d
2 changed files with 22 additions and 12 deletions

View file

@ -306,16 +306,24 @@ class Commands:
return return
last_commit = self.coder.repo.repo.head.commit last_commit = self.coder.repo.repo.head.commit
changed_files_last_commit = [ prev_commit = last_commit.parents[0]
item.a_path for item in last_commit.diff(last_commit.parents[0]) changed_files_last_commit = [item.a_path for item in last_commit.diff(prev_commit)]
]
if any(self.coder.repo.repo.is_dirty(path=fname) for fname in changed_files_last_commit): for fname in changed_files_last_commit:
self.io.tool_error( if self.coder.repo.repo.is_dirty(path=fname):
"The repository has uncommitted changes in files that were modified in the last" self.io.tool_error(
" commit. Please commit or stash them before undoing." f"The file {fname} has uncommitted changes. Please stash them before undoing."
) )
return return
# Check if the file was in the repo in the previous commit
try:
prev_commit.tree[fname]
except KeyError:
self.io.tool_error(
f"The file {fname} was not in the repository in the previous commit. Cannot undo safely."
)
return
local_head = self.coder.repo.repo.git.rev_parse("HEAD") local_head = self.coder.repo.repo.git.rev_parse("HEAD")
current_branch = self.coder.repo.repo.active_branch.name current_branch = self.coder.repo.repo.active_branch.name
@ -346,6 +354,7 @@ class Commands:
# Reset only the files which are part of `last_commit` # Reset only the files which are part of `last_commit`
for file_path in changed_files_last_commit: for file_path in changed_files_last_commit:
self.coder.repo.repo.git.checkout("HEAD~1", file_path) self.coder.repo.repo.git.checkout("HEAD~1", file_path)
# Move the HEAD back before the latest commit # Move the HEAD back before the latest commit
self.coder.repo.repo.git.reset("--soft", "HEAD~1") self.coder.repo.repo.git.reset("--soft", "HEAD~1")

View file

@ -585,11 +585,12 @@ class TestCommands(TestCase):
last_commit_hash = repo.head.commit.hexsha[:7] last_commit_hash = repo.head.commit.hexsha[:7]
coder.aider_commit_hashes.add(last_commit_hash) coder.aider_commit_hashes.add(last_commit_hash)
# Attempt to undo the last commit # Attempt to undo the last commit, should refuse
commands.cmd_undo("") commands.cmd_undo("")
# Check that the last commit was undone # Check that the last commit was not undone
self.assertNotEqual(last_commit_hash, repo.head.commit.hexsha[:7]) self.assertEqual(last_commit_hash, repo.head.commit.hexsha[:7])
self.assertTrue(file_path.exists())
del coder del coder
del commands del commands