[build-system] requires = ["hatchling", "hatch-vcs"] build-backend = "hatchling.build" [project] name = "mcp-server-for-oscal" dynamic = ["version"] readme = "README.md" dependencies = [ # Put your dependencies here! "boto3>=1.42.7", "mcp>=1.23.3", "strands-agents>=1.19.0", "compliance-trestle>=4.0.1", "regex>=2024.0.0", ] requires-python = ">=3.11" description = "AI agent tools for Open Security Controls Assessment Language (OSCAL)." license = "Apache-2.0" license-files = ["LICENSE"] keywords = [ "OSCAL", "compliance as code", "security as code", "compliance automation", "continuous compliance", "security assurance", "mcp server", "strands agents", "grc engineering", ] classifiers = [ "Programming Language :: Python :: 3", "Programming Language :: Python :: 3.11", "Programming Language :: Python :: 3.12", ] [dependency-groups] devtest = ["pytest", "mypy", "boto3-stubs", "bandit", "pytest-asyncio", "hypothesis", "bedrock-agentcore-starter-toolkit"] [project.scripts] server = "mcp_server_for_oscal.main:main" mcp-server-for-oscal = "mcp_server_for_oscal.main:main" mcp_server_for_oscal = "mcp_server_for_oscal.main:main" oscal-agent = "mcp_server_for_oscal.oscal_agent:main" oscal_agent = "mcp_server_for_oscal.oscal_agent:main" [project.urls] GitHub = "https://github.com/awslabs/mcp-server-for-oscal/" PyPI = "https://pypi.org/project/mcp-server-for-oscal/" [tool.hatch.version] source = "vcs" [tool.hatch.version.raw-options] version_scheme = "no-guess-dev" # local_scheme = "no-local-version" # see also: tool.hatch.build.hooks.vcs below [tool.hatch.build.hooks.vcs] version-file = "_version.py" [tool.hatch.envs.default] # This controls what version of Python you want to be the default # when running any scripts or tools to do things like debug test failures # or do general development. python = "3.12" dependency-groups = ["devtest"] [tool.pytest.ini_options] addopts = ["--durations=5", "--color=yes"] testpaths = ["tests"] filterwarnings = [] [tool.coverage.run] source_pkgs = ["mcp_server_for_oscal"] branch = true parallel = true [tool.coverage.paths] "mcp_server_for_oscal" = [ "src/mcp_server_for_oscal", "**/site-packages/mcp_server_for_oscal", ] [tool.coverage.report] exclude_lines = ["no cov", "if __name__ == .__main__.:", "if TYPE_CHECKING:"] show_missing = true # fail_under = 99 [tool.coverage.xml] output = "private/docs/coverage/coverage.xml" [tool.coverage.html] directory = "private/docs/coverage/" [tool.ruff] line-length = 88 target-version = "py311" [tool.ruff.format] quote-style = "double" indent-style = "space" [tool.ruff.lint] isort.known-first-party = ["mcp_server_for_oscal"] exclude = ["./build", ".hatch", "private"] [tool.ruff.lint.per-file-ignores] # Tests can use magic values, assertions, and relative imports "tests/**/*" = ["PLR2004", "S101", "TID252", "PLC0415"] [tool.hatch.build] directory = "./build" [tool.hatch.build.targets.wheel] packages = ["src/mcp_server_for_oscal"] artifacts = ["src/mcp_server_for_oscal/oscal_store.db", "src/mcp_server_for_oscal/hashes.json"] [tool.hatch.env] python = "3.12" [tool.hatch.envs.default.scripts] # These are scripts you can run using `hatch run ` update = [ # Update project dependencies in this file, then compile to requirements.txt # to ensure deterministic/reproducible builds. "uv pip install -U -r pyproject.toml", "uv pip compile --upgrade -o requirements.txt pyproject.toml" ] rehash = [ # Regenerate hash files for bundled content "hatch run bin/update_hashes.py src/mcp_server_for_oscal/oscal_schemas", "git add src/mcp_server_for_oscal/oscal_schemas/hashes.json", "hatch run bin/update_hashes.py data/oscal_docs", "git add data/oscal_docs/hashes.json", "hatch run bin/update_hashes.py data/component_definitions", "git add data/component_definitions/hashes.json", # Bundled OSCAL SQLite database hash is managed by build-db script # (updates hashes.json at package root level) "git add src/mcp_server_for_oscal/hashes.json" ] # TODO: monitor OSCAL GitHub project for changes and trigger PRs in our project # Updates contents of `src/mcp_server_for_oscal/oscal_schemas`, overwriting existing files update-oscal-schemas = ["bin/update-oscal-schemas.sh"] # TODO: monitor Awesome OSCAL GitHub project for changes and trigger PRs in our project # https://github.com/awslabs/mcp-server-for-oscal/issues/20 update-awesome-oscal = [ '''curl -L -o data/oscal_docs/awesome-oscal.md \ https://raw.githubusercontent.com/oscal-club/awesome-oscal/refs/heads/main/README.md''', ] release = ["hatch run tests", "git status", "./bin/refresh-nist-docs.sh", "build-db", "hatch build"] typing = [ # Type checking using mypy "rm -rf .mypy_cache && mkdir -p .mypy_cache", "mypy --install-types --non-interactive src/mcp_server_for_oscal tests", ] # Start the MCP server for remote testing/development http-server = [ "python -m mcp_server_for_oscal.main --transport streamable-http", ] # Start the OSCAL agent in interactive mode oscal-agent = [ "python -m mcp_server_for_oscal.oscal_agent {args}", ] bandito = [ # Run bandit security scanner against src, then tests. This cannot be # named `bandit` because it creates a circular reference that hatch can't resolve. "mkdir -p private/docs/bandit", "bandit -r src/mcp_server_for_oscal | tee private/docs/bandit/src.txt", "bandit -s B101 -r tests | tee private/docs/bandit/tests.txt", ] checkout-oscal-steering = [ "git submodule update --init --depth 1 conf/powers/oscal/steering/oscal-pages", "cd conf/powers/oscal/steering/oscal-pages && git sparse-checkout set --no-cone && git sparse-checkout set src/content/learn/concepts" ] tests = ["typing", "hatch test --exitfirst --all --cover --junitxml private/docs/pytest.xml", "hatch run bandito"] build-db = [ "python bin/build_oscal_db.py", ] build-agentcore-container = [ "finch build -f conf/agentcore/Dockerfile -t bedrock-agentcore-oscal --build-arg VERSION=$(hatch version) ." ] [tool.hatch.envs.hatch-test] parallel = true extra-dependencies = ["pytest-asyncio", "hypothesis"] [tool.hatch.envs.hatch-test.scripts] run = "pytest{env:HATCH_TEST_ARGS:} {args}" run-cov = "coverage run -m pytest{env:HATCH_TEST_ARGS:} {args}" cov-combine = "coverage combine" cov-report = ["coverage report", "coverage html", "coverage xml"] [[tool.hatch.envs.hatch-test.matrix]] python = ["3.11", "3.12"] # This is necessary to use 'uv' as the resolver if this is the top-level package # in a monorepo (which is usually the case). Remove this if copying the # package into a monorepo [tool.uv.workspace]