Skip to content
Snippets Groups Projects
Commit fb9ab6d1 authored by Simon Rose's avatar Simon Rose
Browse files

Move Wrapper test class from conftest.py

parent afeded38
No related branches found
No related tags found
No related merge requests found
import os
import subprocess
from pathlib import Path
from random import choice
from string import ascii_lowercase
import pytest
from git import Repo
class Wrapper:
def __init__(self, root_path: Path, name=None, include_dbd=True, **kwargs):
test_env = os.environ.copy()
assert "EPICS_BASE" in test_env
assert "E3_REQUIRE_VERSION" in test_env
e3_require_config = (
Path(os.environ.get("EPICS_BASE"))
/ "require"
/ os.environ.get("E3_REQUIRE_VERSION")
/ "configure"
)
assert e3_require_config.is_dir()
if name is None:
name = "test_mod_" + "".join(choice(ascii_lowercase) for _ in range(16))
self.path = root_path / f"e3-{name}"
self.name = name
self.version = "0.0.0+0"
module_path = (
name if "E3_MODULE_SRC_PATH" not in kwargs else kwargs["E3_MODULE_SRC_PATH"]
)
self.module_dir = self.path / module_path
self.module_dir.mkdir(parents=True)
self.config_dir = self.path / "configure"
self.config_dir.mkdir()
self.config_module = self.config_dir / "CONFIG_MODULE"
self.config_module.touch()
self.makefile = self.path / "Makefile"
makefile_contents = f"""
TOP:=$(CURDIR)
E3_MODULE_NAME:={name}
E3_MODULE_VERSION:={self.version}
E3_MODULE_SRC_PATH:={module_path}
E3_MODULE_MAKEFILE:={name}.Makefile
include $(TOP)/configure/CONFIG_MODULE
-include $(TOP)/configure/CONFIG_MODULE.local
REQUIRE_CONFIG:={e3_require_config}
include $(REQUIRE_CONFIG)/CONFIG
include $(REQUIRE_CONFIG)/RULES_SITEMODS
"""
(self.makefile).write_text(makefile_contents)
self.module_makefile = self.path / f"{name}.Makefile"
module_makefile_contents = """
where_am_I := $(dir $(abspath $(lastword $(MAKEFILE_LIST))))
include $(E3_REQUIRE_TOOLS)/driver.makefile
EXCLUDE_ARCHS+=debug
"""
(self.module_makefile).write_text(module_makefile_contents)
if include_dbd:
self.add_file("test.dbd")
Repo.init(self.path)
def add_file(self, name):
(self.module_dir / name).touch()
def write_dot_local_data(self, config_file: str, config_vars: dict):
"""Write config data to the specific .local file."""
with open(self.config_dir / f"{config_file}.local", "w") as f:
for var, value in config_vars.items():
f.write(f"{var} = {value}\n")
def add_var_to_config_module(self, makefile_var: str, value: str, modifier="+"):
with open(self.config_module, "a") as f:
f.write(f"export {makefile_var} {modifier}= {value}\n")
def add_var_to_module_makefile(self, makefile_var: str, value: str, modifier="+"):
with open(self.module_makefile, "a") as f:
f.write(f"{makefile_var} {modifier}= {value}\n")
def get_env_var(self, var: str):
"""Fetch an environment variable from the module build environment."""
_, out, _ = self.run_make("cellvars")
for line in out.split("\n"):
if line.startswith(var):
return line.split("=")[1].strip()
return ""
def run_make(
self,
target: str,
*args,
module_version: str = "",
cell_path: str = "",
**kwargs,
):
"""Attempt to run `make <target> <args>` for the current wrapper."""
# We should not install in the global environment during tests
if target == "install":
target = "cellinstall"
if target == "uninstall":
target = "celluninstall"
env = os.environ.copy()
env.update(kwargs)
args = list(args)
if module_version:
args.append(f"E3_MODULE_VERSION={module_version}")
if cell_path:
self.write_dot_local_data("CONFIG_CELL", {"E3_CELL_PATH": cell_path})
make_cmd = ["make", "-C", self.path, target] + args
p = subprocess.Popen(
make_cmd,
stdout=subprocess.PIPE,
stderr=subprocess.PIPE,
encoding="utf-8",
env=env,
)
outs, errs = p.communicate()
return p.returncode, outs, errs
from .utils import Wrapper
@pytest.fixture
......
......@@ -4,8 +4,7 @@ from pathlib import Path
import pytest
from .conftest import Wrapper
from .utils import run_ioc_get_output
from .utils import Wrapper, run_ioc_get_output
RE_MISSING_FILE = "No rule to make target [`']{filename}'"
RE_MISSING_VERSION = "Module '{module}' version '{version}' does not exist."
......
from .conftest import Wrapper
from .utils import Wrapper
def test_loc(wrappers):
......
import subprocess
from .conftest import Wrapper
from .utils import Wrapper
def test_can_run_make_in_wrapper_directory(wrapper: Wrapper):
......
import re
from .conftest import Wrapper
from .utils import run_ioc_get_output
from .utils import Wrapper, run_ioc_get_output
def test_multiple_cell_paths(wrapper: Wrapper):
......
......@@ -2,8 +2,7 @@ import re
import pytest
from .conftest import Wrapper
from .utils import run_ioc_get_output
from .utils import Wrapper, run_ioc_get_output
RE_MODULE_LOADED = "Loaded {module} version {version}"
RE_MODULE_NOT_LOADED = "Module {module} (not available|version {required} not available|version {required} not available \\(but other versions are available\\))"
......
import os
import subprocess
import time
from pathlib import Path
from random import choice
from string import ascii_lowercase
from git import Repo
from run_iocsh import IOC
class Wrapper:
def __init__(self, root_path: Path, name=None, include_dbd=True, **kwargs):
test_env = os.environ.copy()
assert "EPICS_BASE" in test_env
assert "E3_REQUIRE_VERSION" in test_env
e3_require_config = (
Path(os.environ.get("EPICS_BASE"))
/ "require"
/ os.environ.get("E3_REQUIRE_VERSION")
/ "configure"
)
assert e3_require_config.is_dir()
if name is None:
name = "test_mod_" + "".join(choice(ascii_lowercase) for _ in range(16))
self.path = root_path / f"e3-{name}"
self.name = name
self.version = "0.0.0+0"
module_path = (
name if "E3_MODULE_SRC_PATH" not in kwargs else kwargs["E3_MODULE_SRC_PATH"]
)
self.module_dir = self.path / module_path
self.module_dir.mkdir(parents=True)
self.config_dir = self.path / "configure"
self.config_dir.mkdir()
self.config_module = self.config_dir / "CONFIG_MODULE"
self.config_module.touch()
self.makefile = self.path / "Makefile"
makefile_contents = f"""
TOP:=$(CURDIR)
E3_MODULE_NAME:={name}
E3_MODULE_VERSION:={self.version}
E3_MODULE_SRC_PATH:={module_path}
E3_MODULE_MAKEFILE:={name}.Makefile
include $(TOP)/configure/CONFIG_MODULE
-include $(TOP)/configure/CONFIG_MODULE.local
REQUIRE_CONFIG:={e3_require_config}
include $(REQUIRE_CONFIG)/CONFIG
include $(REQUIRE_CONFIG)/RULES_SITEMODS
"""
(self.makefile).write_text(makefile_contents)
self.module_makefile = self.path / f"{name}.Makefile"
module_makefile_contents = """
where_am_I := $(dir $(abspath $(lastword $(MAKEFILE_LIST))))
include $(E3_REQUIRE_TOOLS)/driver.makefile
EXCLUDE_ARCHS+=debug
"""
(self.module_makefile).write_text(module_makefile_contents)
if include_dbd:
self.add_file("test.dbd")
Repo.init(self.path)
def add_file(self, name):
(self.module_dir / name).touch()
def write_dot_local_data(self, config_file: str, config_vars: dict):
"""Write config data to the specific .local file."""
with open(self.config_dir / f"{config_file}.local", "w") as f:
for var, value in config_vars.items():
f.write(f"{var} = {value}\n")
def add_var_to_config_module(self, makefile_var: str, value: str, modifier="+"):
with open(self.config_module, "a") as f:
f.write(f"export {makefile_var} {modifier}= {value}\n")
def add_var_to_module_makefile(self, makefile_var: str, value: str, modifier="+"):
with open(self.module_makefile, "a") as f:
f.write(f"{makefile_var} {modifier}= {value}\n")
def get_env_var(self, var: str):
"""Fetch an environment variable from the module build environment."""
_, out, _ = self.run_make("cellvars")
for line in out.split("\n"):
if line.startswith(var):
return line.split("=")[1].strip()
return ""
def run_make(
self,
target: str,
*args,
module_version: str = "",
cell_path: str = "",
**kwargs,
):
"""Attempt to run `make <target> <args>` for the current wrapper."""
# We should not install in the global environment during tests
if target == "install":
target = "cellinstall"
if target == "uninstall":
target = "celluninstall"
env = os.environ.copy()
env.update(kwargs)
args = list(args)
if module_version:
args.append(f"E3_MODULE_VERSION={module_version}")
if cell_path:
self.write_dot_local_data("CONFIG_CELL", {"E3_CELL_PATH": cell_path})
make_cmd = ["make", "-C", self.path, target] + args
p = subprocess.Popen(
make_cmd,
stdout=subprocess.PIPE,
stderr=subprocess.PIPE,
encoding="utf-8",
env=env,
)
outs, errs = p.communicate()
return p.returncode, outs, errs
def run_ioc_get_output(*args, **kwargs):
"""
Run an IOC and try to load the test module
......
0% Loading or .
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment