151 lines
4.5 KiB
Python
151 lines
4.5 KiB
Python
"""Tests for project state detection functionality."""
|
|
|
|
import os
|
|
|
|
import pytest
|
|
|
|
from ra_aid.project_state import (
|
|
DirectoryAccessError,
|
|
DirectoryNotFoundError,
|
|
ProjectStateError,
|
|
is_new_project,
|
|
)
|
|
|
|
|
|
@pytest.fixture
|
|
def empty_dir(tmp_path):
|
|
"""Create an empty temporary directory."""
|
|
return tmp_path
|
|
|
|
|
|
@pytest.fixture
|
|
def git_only_dir(tmp_path):
|
|
"""Create a directory with only git files."""
|
|
git_dir = tmp_path / ".git"
|
|
git_dir.mkdir(exist_ok=True)
|
|
gitignore = tmp_path / ".gitignore"
|
|
gitignore.write_text("*.pyc\n")
|
|
return tmp_path
|
|
|
|
|
|
@pytest.fixture
|
|
def ra_aid_only_dir(tmp_path):
|
|
"""Create a directory with only a .ra-aid directory."""
|
|
ra_aid_dir = tmp_path / ".ra-aid"
|
|
ra_aid_dir.mkdir(exist_ok=True)
|
|
return tmp_path
|
|
|
|
|
|
@pytest.fixture
|
|
def mixed_allowed_dir(tmp_path):
|
|
"""Create a directory with all allowed items (.git, .gitignore, and .ra-aid)."""
|
|
git_dir = tmp_path / ".git"
|
|
git_dir.mkdir(exist_ok=True)
|
|
gitignore = tmp_path / ".gitignore"
|
|
gitignore.write_text("*.pyc\n")
|
|
ra_aid_dir = tmp_path / ".ra-aid"
|
|
ra_aid_dir.mkdir(exist_ok=True)
|
|
return tmp_path
|
|
|
|
|
|
@pytest.fixture
|
|
def project_dir(tmp_path):
|
|
"""Create a directory with some project files."""
|
|
(tmp_path / "src").mkdir()
|
|
(tmp_path / "README.md").write_text("# Test Project")
|
|
return tmp_path
|
|
|
|
|
|
def test_empty_directory(empty_dir):
|
|
"""Test that an empty directory is considered a new project."""
|
|
assert is_new_project(str(empty_dir)) is True
|
|
|
|
|
|
def test_git_only_directory(git_only_dir):
|
|
"""Test that a directory with only git files is considered a new project."""
|
|
assert is_new_project(str(git_only_dir)) is True
|
|
|
|
|
|
def test_ra_aid_only_directory(ra_aid_only_dir):
|
|
"""Test that a directory with only a .ra-aid directory is considered a new project."""
|
|
assert is_new_project(str(ra_aid_only_dir)) is True
|
|
|
|
|
|
def test_mixed_allowed_directory(mixed_allowed_dir):
|
|
"""Test that a directory with all allowed items is considered a new project."""
|
|
assert is_new_project(str(mixed_allowed_dir)) is True
|
|
|
|
|
|
@pytest.fixture
|
|
def git_dir_with_contents(tmp_path):
|
|
"""Create a directory with .git containing files and .gitignore."""
|
|
git_dir = tmp_path / ".git"
|
|
git_dir.mkdir()
|
|
# Add some files inside .git
|
|
(git_dir / "HEAD").write_text("ref: refs/heads/main")
|
|
(git_dir / "config").write_text("[core]\n\trepositoryformatversion = 0")
|
|
(git_dir / "refs").mkdir()
|
|
# Add .gitignore
|
|
gitignore = tmp_path / ".gitignore"
|
|
gitignore.write_text("*.pyc\n")
|
|
return tmp_path
|
|
|
|
|
|
def test_git_directory_with_contents(git_dir_with_contents):
|
|
"""Test that a directory is considered new even with files inside .git."""
|
|
assert is_new_project(str(git_dir_with_contents)) is True
|
|
|
|
|
|
def test_existing_project_directory(project_dir):
|
|
"""Test that a directory with project files is not considered new."""
|
|
assert is_new_project(str(project_dir)) is False
|
|
|
|
|
|
def test_nonexistent_directory():
|
|
"""Test that a non-existent directory raises appropriate error."""
|
|
with pytest.raises(DirectoryNotFoundError):
|
|
is_new_project("/nonexistent/path/123456")
|
|
|
|
|
|
def test_file_as_directory(tmp_path):
|
|
"""Test that passing a file instead of directory raises error."""
|
|
test_file = tmp_path / "test.txt"
|
|
test_file.write_text("test")
|
|
|
|
with pytest.raises(ProjectStateError):
|
|
is_new_project(str(test_file))
|
|
|
|
|
|
@pytest.mark.skipif(os.name == "nt", reason="Permission tests unreliable on Windows")
|
|
def test_permission_error(tmp_path):
|
|
"""Test handling of permission errors."""
|
|
try:
|
|
# Make directory unreadable
|
|
os.chmod(tmp_path, 0o000)
|
|
|
|
with pytest.raises(DirectoryAccessError):
|
|
is_new_project(str(tmp_path))
|
|
finally:
|
|
# Restore permissions to allow cleanup
|
|
os.chmod(tmp_path, 0o755)
|
|
|
|
|
|
def test_verify_fix(tmp_path):
|
|
"""
|
|
Verify fix: a project with only .ra-aid directory is considered new,
|
|
but adding other files makes it recognized as an existing project.
|
|
"""
|
|
# Create a .ra-aid directory inside the temporary directory
|
|
ra_aid_dir = tmp_path / ".ra-aid"
|
|
ra_aid_dir.mkdir(exist_ok=True)
|
|
|
|
# Check that is_new_project() returns True (only .ra-aid directory)
|
|
assert is_new_project(str(tmp_path)) is True
|
|
|
|
# Add a README.md file to the directory
|
|
readme_file = tmp_path / "README.md"
|
|
readme_file.write_text("# Test Project")
|
|
|
|
# Check that is_new_project() now returns False (has actual content)
|
|
assert is_new_project(str(tmp_path)) is False
|