Files
UA-.NETStandard/docs/RedundancySampleTests.md
romanett d623007a3f Remove the Azure Pipelines CI and publishing definitions from master (#4575)
# Description

Removes the Azure Pipelines CI and package-publishing definitions from
`master`. GitHub Actions already owns all CI and package publishing for
`master`, but pushes to `master` still queued the Azure definitions.
They duplicated the Actions work and posted failing checks, for example
[`Nuget Preview (Push Nuget Preview Pack Nugets
Debug)`](https://github.com/OPCFoundation/UA-.NETStandard/runs/109065914524)
on `19dc504c5`.

## Removed

- `azure-pipelines.yml`, `azure-pipelines-preview.yml`
- `.azurepipelines/` templates: `ci.yml`, `coverage.yml`, `preview.yml`,
`sample-ha-longhaul.yml`, `sln.yml`, `test.yml`, `test-aot.yml`
- Helpers only those templates used: `get-matrix.ps1`, `get-root.ps1`,
`evaluate-test-results.ps1`
- `TrxGateScriptTests`: it tested only `evaluate-test-results.ps1`. The
Actions equivalent, `.github/scripts/get-test-verdict.ps1`, keeps its
own `CiTestVerdictTests`.

## Kept

**OneFuzz:** `.azurepipelines/onefuzz.yml` stays. Submitting to the
internal OneFuzz service needs the Azure DevOps-only `onefuzz-task`,
which has no GitHub Actions equivalent. The pipeline has no push, PR or
schedule trigger, so it never runs on `master` pushes. The public drop
build keeps running in the GitHub `fuzz-public-drop` job.

**Scripts GitHub Actions still invokes:** these stay in
`.azurepipelines/`, so every workflow path and `release.yml`'s
candidate-bound checkout keep working. Only `generate-slnx.ps1` changes,
and only its comment.

| Script | Used by |
| --- | --- |
| `set-version.ps1` | buildandtest, nightly, nuget-publish,
docker-image, stress / stability / long-haul, `run-dotnet-tests` action
|
| `generate-slnx.ps1`, `signlist{Debug,Release}.txt`,
`validate-source-generator-packages.ps1` (+ `expected-packages.txt`) |
nuget-publish |
| `package-version-policy.ps1`, `validate-nuget-package-set.ps1`,
`validate-preview-package-ordering.ps1`,
`assert-published-packages-match.ps1` | nuget-publish, release |
| `check-coverage.ps1` | buildandtest, nightly |
| `validate-migration-plugin.ps1` | buildandtest |

I didn't rename the directory on purpose. `release.yml` checks out the
candidate commit and runs `./.azurepipelines/package-version-policy.ps1`
from it, so moving the scripts would break promotion of any candidate
built before the move.

## Docs and comments

- `UA.slnx` drops the deleted files.
- `codecov.yml`, `coverage-thresholds.json`, `targets.props`, the
Redundancy sample test comments, the `.github` scripts and workflows,
`CONTRIBUTING.md`, `docs/` and `fuzzing/` no longer describe Azure as
running on `master` (`/azp run`, the `azure` Codecov flag, "the Azure
gate", the Azure long-haul and AoT legs).
- In the Developer Guide, the "Triggering a pipeline run" and "Migration
status" sections are replaced by "Pull requests from outside
contributors" and "Azure Pipelines on other branches".
- The new section names `onefuzz.yml` as the one remaining Azure
definition.
- It keeps the warning that the `Release` ruleset's Azure required check
must be lifted before cutting a new `release/2.<minor>` branch.
- `master` is merged in, including the #4555 docs rewrite. Its new
`docs/RedundancySampleTests.md` needed the Azure references removed
again. `docs/README.md` already had none.

## Reviewer notes

- **Azure DevOps side (admin action, not in this PR):** the definitions
are configured in the Azure DevOps portal. With the YAML gone, `master`
pushes give the CI and preview definitions nothing to run. Disabling
definition 14's push trigger/schedule, definition 16's build-completion
trigger, and the stale definition 13 stops any residual "file not found"
runs. Leave the OneFuzz definition enabled.
- `master378`, the 1.x `release/*` lines and the frozen `release/2.0.0`
keep their own `azure-pipelines.yml`. This PR only touches `master`.

## Related Issues

- Follow-up to #4513 (GitHub Actions for CI and nightly).

## Checklist

- [ ] I have signed the
[CLA](https://opcfoundation.org/license/cla/ContributorLicenseAgreementv1.0.pdf)
and read the
[CONTRIBUTING](https://github.com/OPCFoundation/UA-.NETStandard/blob/master/CONTRIBUTING.md)
doc.
- [ ] I have added tests that prove my fix is effective or that my
feature works and increased code coverage.
- [x] I have added all necessary documentation.
- [ ] I have verified that my changes do not introduce (new) build or
analyzer warnings.
- [ ] I ran **all** tests locally using the **UA.slnx** solution against
at least .net **framework** and .net **10**, and all passed.
- [ ] I fixed **all** failing and flaky tests in the CI pipelines and
**all** CodeQL warnings.
- [ ] I have addressed **all** PR feedback received.

This PR removes a test and adds none. Locally, at `9b00da817`, the full
`Opc.Ua.Tools.Tests` suite passed on net10.0: 884 passed, 1 skipped. The
later commits (OneFuzz restore, merge with `master`) touch only YAML and
docs.

🤖 Generated with [Claude Code](https://claude.com/claude-code)

---------

Co-authored-by: Claude Opus 5.5 <noreply@anthropic.com>
2026-09-29 07:44:36 +02:00

3.9 KiB

Redundant Sample Integration Tests

The Opc.Ua.Redundancy.Samples.Tests project runs process-level integration tests against the RedundantServer, RedundantClient, and RedundantPubSub sample applications. The tests launch the applications as external processes and assert on logged high-availability events such as FAILOVER:, DATA LOSS:, HA OK:, and reconnect messages. They cover supported sample configurations, catch regressions in end-to-end failover, and demonstrate when failover loses data.

The test project includes short-haul tests for normal pull-request validation and long-haul soak tests for extended runs on dedicated CI jobs.

Contents

Short-haul tests (pull-request validation)

Short-haul tests are deterministic and complete in seconds. The standard CI workflow discovers and runs them because the project follows the tests/Opc.Ua.*.Tests naming convention. They use the NUnit category SampleHaShortHaul:

  • PubSub demo, hot mode — runs RedundantPubSub --role demo --ha-mode hot and asserts the promoted publisher continues the SequenceNumber across failover with no reset (SIMULATED: HA OK: sequence continued ...).
  • PubSub demo, cold mode — runs the same demo in cold mode and asserts the SequenceNumber reset (data loss) is made visible (SIMULATED: DATA LOSS: sequence reset ...).
  • Server + client connectivity — launches a RedundantServer and a RedundantClient together and asserts the client connects and begins high-availability monitoring.

Run them locally from the repository root:

dotnet test tests/Opc.Ua.Redundancy.Samples.Tests/Opc.Ua.Redundancy.Samples.Tests.csproj --filter "Category=SampleHaShortHaul"

Long-haul tests (manual / scheduled soak)

Long-haul tests use [Explicit] and the NUnit category SampleHaLongHaul, so they do not run on pull requests. They loop for a configurable duration and check high-availability behavior across many failovers:

  • PubSub failover soak — repeatedly runs the PubSub demo in hot and cold modes for the whole duration, asserting the correct continuity (hot) and data-loss (cold) narrative every iteration.
  • Client reconnect soak — runs a RedundantClient against a RedundantServer for the entire duration. The test repeatedly stops and restarts the server, then checks that the client detects the outage, reconnects when the server returns, and does not crash.

The SAMPLE_HA_DURATION_MINUTES environment variable controls the soak duration (default: 60 minutes). Run a short local soak with:

$env:SAMPLE_HA_DURATION_MINUTES = "5"
dotnet test tests/Opc.Ua.Redundancy.Samples.Tests/Opc.Ua.Redundancy.Samples.Tests.csproj --filter "Category=SampleHaLongHaul"

The long-haul tests run in CI through the Sample HA Long-Haul Test GitHub Actions workflow (workflow_dispatch with a duration input, plus a weekly schedule).

Multi-replica leader-election failover

Full multi-replica leader-election topologies include strong (Raft) active/passive and eventual (CRDT gossip) active/active configurations. They use a stable virtual endpoint with DNS-based re-resolution to a surviving replica.

The Docker Compose setups under samples/Redundancy/RedundantServer and samples/Redundancy/RedundantClient run several replicas on a container network. Stop the active replica to observe cross-replica failover. The process-level long-haul soak above focuses on deterministic failover detection, reconnect, and data-loss visibility without container networking.