conftest.py 3.1 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117
  1. from __future__ import annotations
  2. import json
  3. import shutil
  4. import subprocess
  5. import sys
  6. from collections.abc import Generator
  7. from contextlib import contextmanager
  8. from pathlib import Path
  9. import pytest
  10. import docker
  11. import docker.errors
  12. from sweagent.environment.swe_env import EnvironmentArguments, SWEEnv
  13. # this is a hack and should be removed when we have a better solution
  14. _this_dir = Path(__file__).resolve().parent
  15. root_dir = _this_dir.parent
  16. package_dir = root_dir / "sweagent"
  17. sys.path.insert(0, str(root_dir))
  18. sys.path.insert(1, str(package_dir))
  19. @pytest.fixture
  20. def test_data_path() -> Path:
  21. p = _this_dir / "test_data"
  22. assert p.is_dir()
  23. return p
  24. @pytest.fixture
  25. def test_trajectories_path(test_data_path) -> Path:
  26. p = test_data_path / "trajectories"
  27. assert p.is_dir()
  28. return p
  29. @pytest.fixture
  30. def test_ctf_trajectories_path(test_data_path) -> Path:
  31. p = test_data_path / "trajectories" / "ctf"
  32. assert p.is_dir()
  33. return p
  34. @pytest.fixture
  35. def ctf_data_path(test_data_sources_path) -> Path:
  36. p = test_data_sources_path / "ctf"
  37. assert p.is_dir()
  38. return p
  39. @pytest.fixture
  40. def test_data_sources_path(test_data_path) -> Path:
  41. p = test_data_path / "data_sources"
  42. assert p.is_dir()
  43. return p
  44. @pytest.fixture
  45. def test_trajectory_path(test_trajectories_path) -> Path:
  46. traj = (
  47. test_trajectories_path
  48. / "gpt4__swe-agent__test-repo__default_from_url__t-0.00__p-0.95__c-3.00__install-1"
  49. / "swe-agent__test-repo-i1.traj"
  50. )
  51. assert traj.exists()
  52. return traj
  53. @pytest.fixture
  54. def test_trajectory(test_trajectory_path):
  55. return json.loads(test_trajectory_path.read_text())
  56. @pytest.fixture(scope="module")
  57. def test_env_args(
  58. tmpdir_factory,
  59. ) -> Generator[EnvironmentArguments]:
  60. """This will use a persistent container"""
  61. local_repo_path = tmpdir_factory.getbasetemp() / "test-repo"
  62. clone_cmd = ["git", "clone", "https://github.com/swe-agent/test-repo", str(local_repo_path)]
  63. subprocess.run(clone_cmd, check=True)
  64. data_path = local_repo_path / "problem_statements" / "1.md"
  65. test_env_args = EnvironmentArguments(
  66. data_path=str(data_path),
  67. repo_path=str(local_repo_path),
  68. image_name="sweagent/swe-agent:latest",
  69. container_name="test-container-this-is-a-random-string",
  70. verbose=True,
  71. )
  72. yield test_env_args
  73. # Cleanup (after session ends)
  74. client = docker.from_env()
  75. # fixme (?): What happens if user changed container_name?
  76. try:
  77. assert test_env_args.container_name is not None # mypy
  78. container = client.containers.get(test_env_args.container_name)
  79. container.remove(force=True)
  80. except docker.errors.NotFound:
  81. # Can happen if this fixture never runs because we only do a partial
  82. # test run
  83. pass
  84. shutil.rmtree(local_repo_path)
  85. @contextmanager
  86. def swe_env_context(env_args):
  87. """Context manager to make sure we close the shell on the container
  88. so that we can reuse it.
  89. """
  90. env = SWEEnv(env_args)
  91. try:
  92. yield env
  93. finally:
  94. env.close()