Adds Framework/Database.wsc (WscMvc.Database): explicit, request-scoped
ADODB connection/transaction/command lifecycle, parameterized commands
via ADO positional placeholders (never string-concatenated SQL), and
Null-safe value handling. Proven via tests/Test-Components.vbs against a
real database, including a single-quote-containing value round-tripped
through a parameterized INSERT/SELECT to demonstrate no injection risk.
LocalDB was tried first (zero-install) but failed under the real IIS
ApplicationPoolIdentity ("SQL Server Network Interfaces" - LocalDB isn't
supported for IIS-hosted use per Microsoft's own guidance, confirmed
experimentally via a dedicated SelfTestController check, not assumed).
Pivoted to a real network-reachable SQL Server with SQL auth, which has
no dependency on the caller's Windows identity and was verified to work
under the real app-pool identity via the same check.
The live connection string lives only in an untracked db.connectionstring
file (.gitignore'd before it was ever written to disk) and is threaded
through Application.Run exactly like the existing logDir/viewsDir
pattern - Database.wsc itself never touches the filesystem or ASP
intrinsics. No new production route/view was added, per SPEC's
"database-backed example" non-goal - proven the same way M1-M4 proved
their components, via direct component tests plus one diagnostic-only
self-test check.
Co-Authored-By: Claude Sonnet 5 <noreply@anthropic.com>
Adds Framework/ViewRenderer.wsc (WscMvc.ViewRenderer), loading separate
.html templates and substituting {{Key}} placeholders with HTML-encoded
values from a Scripting.Dictionary. Wires /hello through the new pipeline
(HomeController -> Application -> ViewRenderer -> Views/Home.html) while
preserving the exact pre-M4 response body, so the M1 acceptance test
doubles as a live regression check for the render pipeline.
Views/ is unreachable over HTTP by the same physical-separation guarantee
already used for Framework/ and Controllers/ (sibling of public/, never
inside it) - verified directly, not assumed.
Co-Authored-By: Claude Sonnet 5 <noreply@anthropic.com>
- Controllers/SelfTestController.wsc: runs the same checks as
tests/Test-Components.vbs in-process, returns JSON
({ok, checks:[{name,pass,detail}]}) - no PowerShell/cscript/SSH needed
- Application.wsc routes /self-test to it; always HTTP 200 (pass/fail lives
in the JSON body, matching conventional health-check design)
- tests/run-self-test.sh: pure curl + python3 wrapper, verified working
directly from the Linux host with zero Windows tooling
- tests/Test-Http.ps1: now also calls /self-test and folds each check into
its own PASS/FAIL output
- Verified both the happy path and a genuine failure path (deliberately
broke HomeController's registration, confirmed /self-test correctly
reported ok:false with the specific failing check pinpointed, then
re-registered and confirmed full recovery)
- docs updated: ARCHITECTURE.md, DECISIONS.md, TEST-RESULTS.md