mirror of
https://github.com/mvt-project/mvt.git
synced 2026-09-03 00:21:07 +02:00
mvt.plugin re-exports the names a plugin needs from MVT under one import path. It holds the module base classes and Command, the alert and result types, the database errors a module raises, the timestamp converters, the plugin settings API, MVT's settings, get_plugin_logger() and MVT_VERSION. The names it exports are kept working on a best-effort basis. Changes to them are announced in the release notes. Anything else in mvt can still be imported, and may change between releases without notice. get_plugin_logger(__name__) returns a logger under mvt.ext for plugin code outside a module class. Its records then reach the console and the command.log file of a run. A file loaded with --load-module or --load-command is named after the file.
87 lines
3.0 KiB
Python
87 lines
3.0 KiB
Python
# Mobile Verification Toolkit (MVT)
|
|
# Copyright (c) 2021-2026 The MVT Authors.
|
|
# Use of this software is governed by the MVT License 1.1 that can be found at
|
|
# https://license.mvt.re/1.1/
|
|
|
|
"""Helpers building throwaway plugin distributions for the tests.
|
|
|
|
Some plugin behaviour only shows up in a fresh interpreter: what an import
|
|
executes, and what a plugin sees when MVT is imported before or after it.
|
|
These helpers write an importable distribution with a real entry point and
|
|
run a script against it in a subprocess, with a temporary home so that the
|
|
subprocess cannot touch the configuration of whoever runs the tests.
|
|
"""
|
|
|
|
import os
|
|
import subprocess
|
|
import sys
|
|
from pathlib import Path
|
|
from typing import Optional
|
|
|
|
FIXTURE_COMMAND_NAME = "fixture-plugin"
|
|
FIXTURE_MODULE_NAME = "fixture_cli_plugin"
|
|
FIXTURE_DISTRIBUTION_NAME = "fixture-cli-plugin"
|
|
|
|
|
|
def write_cli_plugin_distribution(
|
|
site_path: Path,
|
|
entry_point_group: str,
|
|
module_source: str,
|
|
) -> Path:
|
|
"""Write a distribution registering a CLI plugin entry point.
|
|
|
|
:param site_path: Folder to write the distribution into, to be added to
|
|
the import path of the interpreter loading it.
|
|
:param entry_point_group: Entry-point group to register the command in.
|
|
:param module_source: Source of the plugin module, which must define a
|
|
Click command named `cli`.
|
|
:returns: The folder the distribution was written to.
|
|
"""
|
|
site_path.mkdir(parents=True, exist_ok=True)
|
|
(site_path / f"{FIXTURE_MODULE_NAME}.py").write_text(
|
|
module_source, encoding="utf-8"
|
|
)
|
|
|
|
dist_info = (
|
|
site_path / f"{FIXTURE_DISTRIBUTION_NAME.replace('-', '_')}-1.0.dist-info"
|
|
)
|
|
dist_info.mkdir(exist_ok=True)
|
|
(dist_info / "METADATA").write_text(
|
|
f"Metadata-Version: 2.1\nName: {FIXTURE_DISTRIBUTION_NAME}\nVersion: 1.0\n",
|
|
encoding="utf-8",
|
|
)
|
|
(dist_info / "entry_points.txt").write_text(
|
|
f"[{entry_point_group}]\n{FIXTURE_COMMAND_NAME} = {FIXTURE_MODULE_NAME}:cli\n",
|
|
encoding="utf-8",
|
|
)
|
|
return site_path
|
|
|
|
|
|
def run_isolated_python(
|
|
script: str,
|
|
home: Path,
|
|
site_path: Optional[Path] = None,
|
|
**environment: str,
|
|
) -> subprocess.CompletedProcess:
|
|
"""Run a script in a fresh interpreter with its own configuration folder.
|
|
|
|
Importing MVT writes its configuration file, so the subprocess gets a
|
|
temporary home and no MVT environment variables from the test session.
|
|
"""
|
|
isolated_environment = {
|
|
key: value for key, value in os.environ.items() if not key.startswith("MVT_")
|
|
}
|
|
isolated_environment["HOME"] = str(home)
|
|
isolated_environment["XDG_CONFIG_HOME"] = str(home / "config")
|
|
isolated_environment["XDG_DATA_HOME"] = str(home / "data")
|
|
if site_path is not None:
|
|
isolated_environment["PYTHONPATH"] = str(site_path)
|
|
isolated_environment.update(environment)
|
|
|
|
return subprocess.run(
|
|
[sys.executable, "-c", script],
|
|
capture_output=True,
|
|
text=True,
|
|
env=isolated_environment,
|
|
)
|