Repository navigation
feat: add windows support - #96
Merged
Merged
Conversation
Forward the Windows variables terraform needs to start, create directory symlinks with the right flag and explain permission failures, keep LF endings, mark POSIX-only tests, and run the test job on windows-latest.
Resource group rel paths and the backend state key are now always slash-separated, so plan files and state keys match across hosts. Plan and apply temp files are closed before terraform opens them, which Windows requires. The fake terraform env capture is looked up case-insensitively on Windows.
Run python through sys.executable instead of echo, sleep, cat and sh, generate the runbook e2e conf dirs with python entrypoints, and fake the permission probe for the unreadable manifest test. Runbooks now also receive the variables a Windows process needs to start.
Add a windows PyInstaller spec, pick the right spec, exe name and architecture in the build task, and zip the bundle. The CI build matrix gets a windows-2025 runner with a zip install check, and contrib adds an install.ps1 installer documented in the README.
Add an opt-in e2e test driving init, validate, plan, apply, output and destroy through a real terraform with only built-in resources, and a CI job running it on Linux from the sources and on Windows against the frozen terranova.exe bundle.
Terraform only accepts options before the positional plan file, so `terranova apply <plan> --auto-approve` failed with "Too many command line arguments" against a real terraform. The fake terraform used by the other tests never checked argument order, so nothing caught it.
Piped or redirected streams default to the ANSI code page there, which cannot encode the markers terranova prints, and rich took its legacy windows renderer for them. Reconfigure such streams to UTF-8 and disable the legacy renderer when the output is not a terminal.
Add session-scoped fixtures that install a pinned terraform through EngineManager into a cache shared by the xdist workers, and a function fixture that puts it first on PATH. The real-terraform e2e now runs with the rest of the suite, so the opt-in variable, the setup-terraform step and the dedicated CI job go away. On Windows the test job points the e2e at the frozen terranova.exe bundle.
Drop the steps that unpacked the frozen bundle for the test job, and the TERRANOVA_BIN switch they were the only user of. The packaged build keeps its own --version check in the sanitize-zip job.
Replace the early return and the conditional expression with a match on the system, and move the shared renaming of the bundle into a helper.
plan and apply both created a closed-but-kept temporary file so terraform could open it, which Windows requires. Share it as a context manager and cover it with tests.
Add IS_WINDOWS and use it instead of repeated os.name and sys.platform checks. The Windows environment variables helper moves next to it, which also removes the import cycle between resources and binds.
Replace zip(chain, chain[1:]) with pairwise(chain), as ruff RUF007 recommends.
The module already postpones annotation evaluation with `from __future__ import annotations`, so the quotes are redundant.
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
Add this suggestion to a batch that can be applied as a single commit.This suggestion is invalid because no changes were made to the code.Suggestions cannot be applied while the pull request is closed.Suggestions cannot be applied while viewing a subset of changes.Only one suggestion per line can be applied in a batch.Add this suggestion to a batch that can be applied as a single commit.Applying suggestions on deleted lines is not supported.You must change the existing code in this line in order to create a valid suggestion.Outdated suggestions cannot be applied.This suggestion has been applied or marked resolved.Suggestions cannot be applied from pending reviews.Suggestions cannot be applied on multi-line comments.Suggestions cannot be applied while the pull request is queued to merge.Suggestion cannot be applied right now. Please check back later.
🧑💻What is the change being made?
Adds Windows support: runtime fixes, portable tests, a Windows bundle and installer, and CI that tests it against a real terraform.
SYSTEMROOT,USERPROFILE,TEMP,TMP,PATHEXT,COMSPEC,APPDATA,LOCALAPPDATA,PROGRAMDATA,SYSTEMDRIVE) to terraform, only when running on Windows.initwith the righttarget_is_directoryflag, and fail with an explained error (pointing to Developer Mode) when symlink creation is not permitted..gitattributesso fixtures and scripts do not turn into CRLF on Windows checkouts.terraform.cmdshim on Windows, and add aposix_onlymarker for tests that depend onsh,sleep,cat, shebangs or POSIX file modes.testCI job on bothubuntu-latestandwindows-latest./-separated, so state keys and.tnplanfiles match across hosts, and close the plan/apply temp files before terraform opens them.sys.executablehelpers and generated runbook fixtures, so they run on Windows too.terranova apply <plan> --auto-approveon every platform: terraform only accepts options before the positional saved plan, so the plan path now goes last.⇒/✓markers, so they are reconfigured to UTF-8 andrich's legacy Windows renderer is disabled when the output is not a terminal.tests/e2e/test_real_terraform.py) driving init, validate, plan, apply, output and destroy with only built-in resources. A session-scoped fixture installs a pinned terraform through theEngineManager(cache shared by the xdist workers; skipped locally when offline, failing on CI), so it runs with the rest of the suite..exepath and zip in the build task, awindows-2025build job andsanitize-zipinstall check in CI, andcontrib/install.ps1with README instructions.IS_WINDOWSflag inutils.py(with the Windows environment variables helper next to it) replaces the scatteredos.name/sys.platformchecks, the Windows-safe temporary file used byplanandapplybecomes anio.temp_file()context manager, and the build task uses amatchon the system.❓ Why is the change being made?
Terranova is only built and tested on macOS and Linux. Terraform cannot even start on Windows with the current environment allow-list, state keys and plan files would differ between hosts, and there is no CI signal or released Windows binary. This PR removes the known runtime blockers, ships a Windows bundle, and adds Windows test and real-terraform jobs so regressions show up in CI. Running against a real terraform also surfaced two bugs, one of which affects every platform.
✅ How has this been tested?
ruff,basedpyrightand the full test suite pass locally on macOS (487 passed, including the real-terraform e2e, which downloads terraform on first use). In CI:test (ubuntu-latest)andtest (windows-latest)pass, including the real-terraform e2e: on Windows it runs the full lifecycle against a real terraform, which is what found theapplyargument order and redirected output bugs above (the one Windows skip is the POSIX file-mode test).windows-2025build produces a bundle, andsanitize-zipextracts the zip and runsterranova.exe --version.Not covered by CI:
install.ps1, Windows arm64, and a runbook run against a real terraform. Terraform is also not stopped gracefully on Windows yet (terminate()equalskill()), so it cannot release its state lock if terranova stops it.