From 8ce5791f49e446858c97f7c4317f2bffb16fc867 Mon Sep 17 00:00:00 2001 From: Joseph Doherty Date: Mon, 20 Apr 2026 00:04:35 -0400 Subject: [PATCH] =?UTF-8?q?Pin=20libplctag=20ab=5Fserver=20to=20v2.6.16=20?= =?UTF-8?q?=E2=80=94=20real=20release=20tag=20+=20SHA256=20hashes=20for=20?= =?UTF-8?q?all=20three=20Windows=20arches.=20Closes=20the=20"pick=20a=20cu?= =?UTF-8?q?rrent=20version=20+=20pin"=20deferral=20left=20by=20the=20#180?= =?UTF-8?q?=20PR=20docs=20stub.=20Verified=20the=20release=20lands=20ab=5F?= =?UTF-8?q?server.exe=20inside=20libplctag=5F2.6.16=5Fwindows=5F=5Ft?= =?UTF-8?q?ools.zip=20alongside=20plctag.dll=20+=20list=5Ftags=5F*=20helpe?= =?UTF-8?q?rs=20by=20downloading=20each=20tools=20zip=20+=20unzip=20-l'ing?= =?UTF-8?q?=20to=20confirm=20ab=5Fserver.exe=20is=20present=20at=20331264?= =?UTF-8?q?=20bytes.=20New=20ci/ab-server.lock.json=20is=20the=20single=20?= =?UTF-8?q?source=20of=20truth=20=E2=80=94=20one=20file=20the=20CI=20YAML?= =?UTF-8?q?=20reads=20via=20ConvertFrom-Json=20instead=20of=20duplicating?= =?UTF-8?q?=20the=20hash=20across=20the=20workflow=20+=20the=20docs.=20Str?= =?UTF-8?q?ucture:=20repo=20(libplctag/libplctag)=20+=20tag=20(v2.6.16)=20?= =?UTF-8?q?+=20published=20date=20(2026-03-29)=20+=20assets=20keyed=20by?= =?UTF-8?q?=20platform=20(windows-x64=20/=20windows-x86=20/=20windows-arm6?= =?UTF-8?q?4)=20each=20carrying=20filename=20+=20sha256.=20docs/v2/test-da?= =?UTF-8?q?ta-sources.md=20=C2=A72.CI=20updated=20=E2=80=94=20replaces=20t?= =?UTF-8?q?he=20prior=20placeholder=20(ver=20=3D=20'',=20expected=20=3D=20'')=20with?= =?UTF-8?q?=20the=20real=20v2.6.16=20+=209b78a3de...=20hashes=20pinned=20t?= =?UTF-8?q?able,=20and=20replaces=20the=20hardcoded=20URL=20with=20a=20loc?= =?UTF-8?q?kfile-driven=20pwsh=20step=20that=20picks=20windows-x64=20by=20?= =?UTF-8?q?default=20but=20swaps=20to=20x86/arm64=20by=20changing=20one=20?= =?UTF-8?q?line=20for=20non-x64=20CI=20runners.=20Hash-mismatch=20path=20t?= =?UTF-8?q?hrows=20with=20both=20the=20expected=20+=20actual=20values=20so?= =?UTF-8?q?=20on=20the=20first=20drift=20the=20CI=20log=20tells=20the=20ma?= =?UTF-8?q?intainer=20exactly=20what=20to=20update=20in=20the=20lockfile.?= =?UTF-8?q?=20Two=20verification=20notes=20from=20the=20release=20fetch:?= =?UTF-8?q?=20(1)=20libplctag=20v2.6.16=20tools=20zips=20ship=20ab=5Fserve?= =?UTF-8?q?r.exe=20+=20plctag.dll=20together=20=E2=80=94=20tests=20don't?= =?UTF-8?q?=20need=20a=20separate=20libplctag=20NuGet=20download=20for=20t?= =?UTF-8?q?he=20integration=20path,=20the=20extracted=20tools=20dir=20cove?= =?UTF-8?q?rs=20both=20the=20simulator=20+=20the=20driver's=20native=20dep?= =?UTF-8?q?endency;=20(2)=20the=20three=20Windows=20arches=20all=20carry?= =?UTF-8?q?=20ab=5Fserver.exe,=20so=20ARM64=20Windows=20GitHub=20runners?= =?UTF-8?q?=20(when=20they=20arrive)=20can=20run=20the=20integration=20sui?= =?UTF-8?q?te=20without=20changes=20beyond=20swapping=20the=20asset=20key.?= =?UTF-8?q?=20No=20code=20changes=20in=20this=20PR=20=E2=80=94=20purely=20?= =?UTF-8?q?docs=20+=20the=20new=20lockfile.=20Admin=20tests=20+=20Core=20t?= =?UTF-8?q?ests=20unchanged=20+=20passing=20per=20the=20prior=20commit.?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Co-Authored-By: Claude Opus 4.7 (1M context) --- ci/ab-server.lock.json | 20 ++++++++++++++++++++ docs/v2/test-data-sources.md | 30 +++++++++++++++++++----------- 2 files changed, 39 insertions(+), 11 deletions(-) create mode 100644 ci/ab-server.lock.json diff --git a/ci/ab-server.lock.json b/ci/ab-server.lock.json new file mode 100644 index 0000000..b78c589 --- /dev/null +++ b/ci/ab-server.lock.json @@ -0,0 +1,20 @@ +{ + "_comment": "Pinned libplctag release used by tests/ZB.MOM.WW.OtOpcUa.Driver.AbCip.IntegrationTests/AbServerFixture. ab_server.exe ships inside the *_tools.zip asset on every GitHub release. See docs/v2/test-data-sources.md §2.CI for the GitHub Actions step that consumes this file.", + "repo": "libplctag/libplctag", + "tag": "v2.6.16", + "published": "2026-03-29", + "assets": { + "windows-x64": { + "file": "libplctag_2.6.16_windows_x64_tools.zip", + "sha256": "9b78a3dee73d9cd28ca348c090f453dbe3ad9d07ad6bf42865a9dc3a79bc2232" + }, + "windows-x86": { + "file": "libplctag_2.6.16_windows_x86_tools.zip", + "sha256": "fdfefd58b266c5da9a1ded1a430985e609289c9e67be2544da7513b668761edf" + }, + "windows-arm64": { + "file": "libplctag_2.6.16_windows_arm64_tools.zip", + "sha256": "d747728e4c4958bb63b4ac23e1c820c4452e4778dfd7d58f8a0aecd5402d4944" + } + } +} diff --git a/docs/v2/test-data-sources.md b/docs/v2/test-data-sources.md index af8a1ff..1f2fd1c 100644 --- a/docs/v2/test-data-sources.md +++ b/docs/v2/test-data-sources.md @@ -196,22 +196,30 @@ The integration harness at `tests/ZB.MOM.WW.OtOpcUa.Driver.AbCip.IntegrationTest - **`AbServerFixture(AbServerProfile)`** — starts the simulator with the CLI args composed from the profile's `--plc` family + seed-tag set. One fixture instance per family, one simulator process per test case (smoke tier). For larger suites that can share a simulator across several reads/writes, use a `IClassFixture` wrapper per family. - **`KnownProfiles.{ControlLogix, CompactLogix, Micro800, GuardLogix}`** — the four per-family profiles. Drives the simulator's `--plc` mode + the preseed `--tag name:type[:size]` set. Micro800 + GuardLogix fall back to `controllogix` under the hood because ab_server has no dedicated mode for them — the driver-side family profile still enforces the narrower connection shape / safety classification separately. -**CI step (intended — fleet-ops to wire):** +**Pinned version** (recorded in `ci/ab-server.lock.json` so drift is one-file visible): + +- `libplctag` **v2.6.16** (published 2026-03-29) — `ab_server.exe` ships inside the `_tools.zip` asset alongside `plctag.dll` + two `list_tags_*` helpers. +- Windows x64: `libplctag_2.6.16_windows_x64_tools.zip` — SHA256 `9b78a3dee73d9cd28ca348c090f453dbe3ad9d07ad6bf42865a9dc3a79bc2232` +- Windows x86: `libplctag_2.6.16_windows_x86_tools.zip` — SHA256 `fdfefd58b266c5da9a1ded1a430985e609289c9e67be2544da7513b668761edf` +- Windows ARM64: `libplctag_2.6.16_windows_arm64_tools.zip` — SHA256 `d747728e4c4958bb63b4ac23e1c820c4452e4778dfd7d58f8a0aecd5402d4944` + +**CI step:** ```yaml # GitHub Actions step placed before `dotnet test`: -- name: Fetch ab_server +- name: Fetch ab_server (libplctag v2.6.16) shell: pwsh run: | - $ver = '' - $url = "https://github.com/libplctag/libplctag/releases/download/$ver/ab_server-windows-x64.zip" - Invoke-WebRequest $url -OutFile $env:RUNNER_TEMP/ab_server.zip - # SHA256 check against a pinned value recorded in this repo's CI lockfile — drift = fail closed - $expected = '' - $actual = (Get-FileHash -Algorithm SHA256 $env:RUNNER_TEMP/ab_server.zip).Hash - if ($expected -ne $actual) { throw "ab_server hash mismatch" } - Expand-Archive $env:RUNNER_TEMP/ab_server.zip -DestinationPath $env:RUNNER_TEMP/ab_server - echo "$env:RUNNER_TEMP/ab_server" >> $env:GITHUB_PATH + $pin = Get-Content ci/ab-server.lock.json | ConvertFrom-Json + $asset = $pin.assets.'windows-x64' # swap to windows-x86 / windows-arm64 on non-x64 runners + $url = "https://github.com/libplctag/libplctag/releases/download/$($pin.tag)/$($asset.file)" + $zip = Join-Path $env:RUNNER_TEMP 'libplctag-tools.zip' + Invoke-WebRequest $url -OutFile $zip + $actual = (Get-FileHash -Algorithm SHA256 $zip).Hash.ToLower() + if ($actual -ne $asset.sha256) { throw "libplctag tools SHA256 mismatch: expected $($asset.sha256), got $actual" } + $dest = Join-Path $env:RUNNER_TEMP 'libplctag-tools' + Expand-Archive $zip -DestinationPath $dest + Add-Content $env:GITHUB_PATH $dest ``` The fixture's `LocateBinary()` picks the binary up off PATH so the C# harness doesn't own the download — CI YAML is the right place for version pinning + hash verification. Developer workstations install the binary once from source (`cmake + make ab_server` under a libplctag clone) and the same fixture works identically.