From b335230498860845ae8a0e32a3640b052b977b5d Mon Sep 17 00:00:00 2001 From: Joseph Doherty Date: Thu, 26 Feb 2026 08:03:21 -0500 Subject: [PATCH] chore: scaffold .NET solution structure for Phase 6 Creates the four-project .NET 10 solution (ZB.MOM.NatsNet.slnx): - ZB.MOM.NatsNet.Server: main library with MEL, BCrypt.Net-Next, IronSnappy - ZB.MOM.NatsNet.Server.Host: console host with Serilog + Microsoft.Extensions.Hosting - ZB.MOM.NatsNet.Server.Tests: xUnit 2.9 / Shouldly / NSubstitute / BenchmarkDotNet - ZB.MOM.NatsNet.Server.IntegrationTests: same test stack, separate project Also adds Phase 6 porting plan and task-tracking JSON. --- docs/plans/2026-02-26-phase-6-porting.md | 741 ++++++++++++++++++ .../2026-02-26-phase-6-porting.md.tasks.json | 36 + dotnet/ZB.MOM.NatsNet.slnx | 10 + .../src/ZB.MOM.NatsNet.Server.Host/Program.cs | 2 + .../ZB.MOM.NatsNet.Server.Host.csproj | 22 + .../ZB.MOM.NatsNet.Server.csproj | 18 + .../UnitTest1.cs | 10 + ...MOM.NatsNet.Server.IntegrationTests.csproj | 28 + .../ZB.MOM.NatsNet.Server.Tests/UnitTest1.cs | 10 + .../ZB.MOM.NatsNet.Server.Tests.csproj | 29 + reports/current.md | 2 +- reports/report_023a5dd.md | 33 + 12 files changed, 940 insertions(+), 1 deletion(-) create mode 100644 docs/plans/2026-02-26-phase-6-porting.md create mode 100644 docs/plans/2026-02-26-phase-6-porting.md.tasks.json create mode 100644 dotnet/ZB.MOM.NatsNet.slnx create mode 100644 dotnet/src/ZB.MOM.NatsNet.Server.Host/Program.cs create mode 100644 dotnet/src/ZB.MOM.NatsNet.Server.Host/ZB.MOM.NatsNet.Server.Host.csproj create mode 100644 dotnet/src/ZB.MOM.NatsNet.Server/ZB.MOM.NatsNet.Server.csproj create mode 100644 dotnet/tests/ZB.MOM.NatsNet.Server.IntegrationTests/UnitTest1.cs create mode 100644 dotnet/tests/ZB.MOM.NatsNet.Server.IntegrationTests/ZB.MOM.NatsNet.Server.IntegrationTests.csproj create mode 100644 dotnet/tests/ZB.MOM.NatsNet.Server.Tests/UnitTest1.cs create mode 100644 dotnet/tests/ZB.MOM.NatsNet.Server.Tests/ZB.MOM.NatsNet.Server.Tests.csproj create mode 100644 reports/report_023a5dd.md diff --git a/docs/plans/2026-02-26-phase-6-porting.md b/docs/plans/2026-02-26-phase-6-porting.md new file mode 100644 index 0000000..93c4499 --- /dev/null +++ b/docs/plans/2026-02-26-phase-6-porting.md @@ -0,0 +1,741 @@ +# Phase 6: Initial Porting Implementation Plan + +> **For Claude:** REQUIRED SUB-SKILL: Use superpowers-extended-cc:executing-plans to implement this plan task-by-task. + +**Goal:** Port all 3632 Go features and 3257 tests across 12 modules from the Go NATS server to idiomatic .NET 10 C#, working bottom-up through the dependency graph. + +**Architecture:** Port leaf modules (11 small modules, 279 features total) in parallel first, then tackle the server module (3394 features) in functional batches. The `dependency ready` command drives porting order. Every feature gets a stub before implementation; tests are ported alongside. + +**Tech Stack:** .NET 10, C# latest, xUnit 3, Shouldly, NSubstitute, Microsoft.Extensions.Logging, Serilog, System.IO.Pipelines, BCrypt.Net-Next, IronSnappy, Tpm2Lib + +--- + +## Dependency Graph Summary + +``` +Leaf modules (all unblocked — port in parallel): + ats module 1 4 features, 3 tests → AccessTimeService + avl module 2 36 features, 16 tests → SequenceSet (AVL tree) + certidp module 3 14 features, 2 tests → CertificateIdentityProvider + certstore module 4 36 features, 0 tests → CertificateStore + elastic module 5 5 features, 0 tests → ElasticEncoding + gsl module 6 26 features, 21 tests → GenericSubjectList + pse module 7 28 features, 3 tests → ProcessStatsProvider + stree module 9 101 features, 59 tests → SubjectTree + sysmem module 10 9 features, 0 tests → SystemMemory + thw module 11 12 features, 14 tests → TimeHashWheel + tpm module 12 8 features, 2 tests → TpmKeyProvider + +Server module (blocked on all leaf modules): + server module 8 3394 features, ~3137 tests → NatsServer (347K Go LOC) +``` + +--- + +## TDD Porting Pattern (repeat for every feature) + +1. `dotnet run --project tools/NatsNet.PortTracker -- feature update --status stub --db porting.db` +2. Write failing test (translate Go test, Shouldly assertions, xUnit `[Fact]`/`[Theory]`) +3. Run test: confirm FAIL +4. Implement feature: idiomatic C# from Go source (coordinates in `feature show `) +5. Run test: confirm PASS +6. `dotnet run --project tools/NatsNet.PortTracker -- feature update --status complete --db porting.db` + +After all features in a module: `dotnet run --project tools/NatsNet.PortTracker -- module update --status complete --db porting.db` + +--- + +## Go→.NET Translation Reference + +| Go pattern | .NET equivalent | +|-----------|-----------------| +| `goroutine` + `channel` | `Task` + `Channel` or `async/await` | +| `sync.Mutex` | `lock` or `SemaphoreSlim` | +| `sync.RWMutex` | `ReaderWriterLockSlim` | +| `sync.WaitGroup` | `Task.WhenAll` or `CountdownEvent` | +| `defer` | `try/finally` or `using` | +| `interface{}` / `any` | `object` or generics | +| `[]byte` | `byte[]`, `ReadOnlySpan`, or `ReadOnlyMemory` | +| `map[K]V` | `Dictionary` or `ConcurrentDictionary` | +| `error` return | Exceptions or `Result` | +| `panic/recover` | Exceptions | +| `select` on channels | `Task.WhenAny` or `Channel` reader | +| `context.Context` | `CancellationToken` | +| `io.Reader/Writer` | `Stream`, `PipeReader/PipeWriter` | +| `init()` | Static constructor or DI registration | + +--- + +## Task 0: Create .NET Solution Structure + +**Files to create:** +- `dotnet/ZB.MOM.NatsNet.sln` +- `dotnet/src/ZB.MOM.NatsNet.Server/ZB.MOM.NatsNet.Server.csproj` +- `dotnet/src/ZB.MOM.NatsNet.Server.Host/ZB.MOM.NatsNet.Server.Host.csproj` +- `dotnet/tests/ZB.MOM.NatsNet.Server.Tests/ZB.MOM.NatsNet.Server.Tests.csproj` +- `dotnet/tests/ZB.MOM.NatsNet.Server.IntegrationTests/ZB.MOM.NatsNet.Server.IntegrationTests.csproj` + +**Step 1: Scaffold projects** + +```bash +cd /Users/dohertj2/Desktop/natsnet/dotnet +dotnet new sln -n ZB.MOM.NatsNet +dotnet new classlib -n ZB.MOM.NatsNet.Server -o src/ZB.MOM.NatsNet.Server --framework net10.0 +dotnet new console -n ZB.MOM.NatsNet.Server.Host -o src/ZB.MOM.NatsNet.Server.Host --framework net10.0 +dotnet new xunit -n ZB.MOM.NatsNet.Server.Tests -o tests/ZB.MOM.NatsNet.Server.Tests --framework net10.0 +dotnet new xunit -n ZB.MOM.NatsNet.Server.IntegrationTests -o tests/ZB.MOM.NatsNet.Server.IntegrationTests --framework net10.0 +dotnet sln add src/ZB.MOM.NatsNet.Server/ZB.MOM.NatsNet.Server.csproj +dotnet sln add src/ZB.MOM.NatsNet.Server.Host/ZB.MOM.NatsNet.Server.Host.csproj +dotnet sln add tests/ZB.MOM.NatsNet.Server.Tests/ZB.MOM.NatsNet.Server.Tests.csproj +dotnet sln add tests/ZB.MOM.NatsNet.Server.IntegrationTests/ZB.MOM.NatsNet.Server.IntegrationTests.csproj +``` + +**Step 2: Configure server library .csproj** + +Replace contents of `dotnet/src/ZB.MOM.NatsNet.Server/ZB.MOM.NatsNet.Server.csproj`: + +```xml + + + net10.0 + enable + enable + latest + true + + + + + + + + + +``` + +Note: Tpm2Lib is Windows-only; add it in Task 11 for the tpm module with a conditional reference. + +**Step 3: Configure Host .csproj** + +Replace contents of `dotnet/src/ZB.MOM.NatsNet.Server.Host/ZB.MOM.NatsNet.Server.Host.csproj`: + +```xml + + + Exe + net10.0 + enable + enable + latest + + + + + + + + + +``` + +**Step 4: Configure Tests .csproj** + +Replace contents of `dotnet/tests/ZB.MOM.NatsNet.Server.Tests/ZB.MOM.NatsNet.Server.Tests.csproj`: + +```xml + + + net10.0 + enable + enable + latest + false + + + + + + + + + + + +``` + +Apply the same to `dotnet/tests/ZB.MOM.NatsNet.Server.IntegrationTests/ZB.MOM.NatsNet.Server.IntegrationTests.csproj`. + +**Step 5: Clean boilerplate, add placeholder Program.cs, verify build** + +```bash +rm -f dotnet/src/ZB.MOM.NatsNet.Server/Class1.cs +# Program.cs for Host (placeholder) +# Write: Console.WriteLine("ZB.MOM.NatsNet.Server"); to Program.cs +dotnet build /Users/dohertj2/Desktop/natsnet/dotnet/ZB.MOM.NatsNet.sln +dotnet test /Users/dohertj2/Desktop/natsnet/dotnet/ZB.MOM.NatsNet.sln +``` + +Expected: build succeeds, 0 tests (or default xUnit tests pass). + +**Step 6: Commit** + +```bash +git add dotnet/ +git commit -m "chore: scaffold .NET solution structure for Phase 6" +``` + +--- + +## Task 1: Port `avl` Module — SequenceSet + +**Go source:** `golang/nats-server/server/avl/seqset.go` (678 LOC) +**Go tests:** `golang/nats-server/server/avl/seqset_test.go`, `norace_test.go` +**Target:** `dotnet/src/ZB.MOM.NatsNet.Server/Internal/DataStructures/SequenceSet.cs` +**Tests:** `dotnet/tests/ZB.MOM.NatsNet.Server.Tests/Internal/DataStructures/SequenceSetTests.cs` +**Namespace:** `ZB.MOM.NatsNet.Server.Internal.DataStructures` +**Features:** 36 (IDs 5–40) | **Tests:** 16 | **Module ID:** 2 + +**Step 1: Mark all stubs** + +```bash +dotnet run --project tools/NatsNet.PortTracker -- feature update 0 --status stub --all-in-module 2 --db porting.db +``` + +**Step 2: Lookup source coordinates for key features** + +```bash +dotnet run --project tools/NatsNet.PortTracker -- feature show 5 --db porting.db # Insert (line 44) +dotnet run --project tools/NatsNet.PortTracker -- feature show 6 --db porting.db # Exists +dotnet run --project tools/NatsNet.PortTracker -- feature show 8 --db porting.db # Delete +dotnet run --project tools/NatsNet.PortTracker -- feature show 22 --db porting.db # Encode +dotnet run --project tools/NatsNet.PortTracker -- feature show 23 --db porting.db # Decode +``` + +**Step 3: Create the class skeleton** + +Create `dotnet/src/ZB.MOM.NatsNet.Server/Internal/DataStructures/SequenceSet.cs`. + +Key type mappings: +- `SequenceSet` struct → `public sealed class SequenceSet` +- `node` struct → `private sealed class Node` +- Go `uint64` → C# `ulong` +- Go pointer receivers on `node` → C# methods on `Node` + +All methods: `throw new NotImplementedException()` initially. + +**Step 4: Write failing tests** + +Create `SequenceSetTests.cs` translating from `seqset_test.go`. Example: + +```csharp +// Go: TestSeqSetBasics +[Fact] +public void SeqSetBasics_ShouldSucceed() +{ + var ss = new SequenceSet(); + ss.IsEmpty().ShouldBeTrue(); + ss.Insert(1); + ss.Exists(1).ShouldBeTrue(); + ss.Exists(2).ShouldBeFalse(); + ss.Size().ShouldBe(1); + ss.Delete(1); + ss.IsEmpty().ShouldBeTrue(); +} +``` + +Run: `dotnet test dotnet/tests/ZB.MOM.NatsNet.Server.Tests/ --filter "FullyQualifiedName~SequenceSetTests"` +Expected: FAIL with NotImplementedException. + +**Step 5: Implement SequenceSet** + +Port AVL tree logic from `seqset.go`. Critical Go→.NET: +- `uint64` → `ulong` +- nil checks → null checks +- `Range(f func(uint64, uint64) bool)` → `Range(Func f)` +- Encode/Decode using `ReadOnlySpan` and `BinaryPrimitives` + +**Step 6: Run tests** + +```bash +dotnet test dotnet/tests/ZB.MOM.NatsNet.Server.Tests/ --filter "FullyQualifiedName~SequenceSetTests" +``` + +Expected: all 16 tests pass. + +**Step 7: Update DB** + +```bash +for id in 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40; do + dotnet run --project tools/NatsNet.PortTracker -- feature update $id --status complete --db porting.db +done +dotnet run --project tools/NatsNet.PortTracker -- test list --module 2 --db porting.db +# mark each test complete +dotnet run --project tools/NatsNet.PortTracker -- module update 2 --status complete --db porting.db +``` + +**Step 8: Commit** + +```bash +git add dotnet/ +git commit -m "feat: port avl module - SequenceSet AVL tree" +``` + +--- + +## Task 2: Port `ats` Module — AccessTimeService + +**Go source:** `golang/nats-server/server/ats/ats.go` (186 LOC) +**Go tests:** `golang/nats-server/server/ats/ats_test.go` +**Target:** `dotnet/src/ZB.MOM.NatsNet.Server/Internal/AccessTimeService.cs` +**Tests:** `dotnet/tests/ZB.MOM.NatsNet.Server.Tests/Internal/AccessTimeServiceTests.cs` +**Namespace:** `ZB.MOM.NatsNet.Server.Internal` +**Features:** IDs 1–4 | **Tests:** IDs 1–3 | **Module ID:** 1 + +Tracks access times; `init()` → static initialization. Follow TDD pattern. + +```bash +dotnet run --project tools/NatsNet.PortTracker -- feature update 0 --status stub --all-in-module 1 --db porting.db +# implement Register, Unregister, AccessTime, Init +for id in 1 2 3 4; do dotnet run --project tools/NatsNet.PortTracker -- feature update $id --status complete --db porting.db; done +dotnet run --project tools/NatsNet.PortTracker -- module update 1 --status complete --db porting.db +git commit -m "feat: port ats module - AccessTimeService" +``` + +--- + +## Task 3: Port `elastic` Module — ElasticEncoding + +**Go source:** `golang/nats-server/server/elastic/elastic.go` (61 LOC) +**Target:** `dotnet/src/ZB.MOM.NatsNet.Server/Internal/ElasticEncoding.cs` +**Namespace:** `ZB.MOM.NatsNet.Server.Internal` +**Features:** 5 | **Tests:** 0 | **Module ID:** 5 + +```bash +dotnet run --project tools/NatsNet.PortTracker -- feature update 0 --status stub --all-in-module 5 --db porting.db +dotnet run --project tools/NatsNet.PortTracker -- feature list --module 5 --db porting.db +# implement features; no tests to port +dotnet run --project tools/NatsNet.PortTracker -- module update 5 --status complete --db porting.db +git commit -m "feat: port elastic module - ElasticEncoding" +``` + +--- + +## Task 4: Port `sysmem` Module — SystemMemory + +**Go source:** `golang/nats-server/server/sysmem/mem_*.go` (platform-specific) +**Target:** `dotnet/src/ZB.MOM.NatsNet.Server/Internal/SystemMemory.cs` +**Namespace:** `ZB.MOM.NatsNet.Server.Internal` +**Features:** 9 | **Tests:** 0 | **Module ID:** 10 + +Use `System.Diagnostics.Process` and `GC.GetTotalMemory` for cross-platform memory. Mark platform-specific Go variants (BSD, Solaris, WASM, z/OS) as N/A with reason. + +```bash +dotnet run --project tools/NatsNet.PortTracker -- feature update 0 --status stub --all-in-module 10 --db porting.db +dotnet run --project tools/NatsNet.PortTracker -- feature list --module 10 --db porting.db +# implement; mark n/a for platform variants +dotnet run --project tools/NatsNet.PortTracker -- module update 10 --status complete --db porting.db +git commit -m "feat: port sysmem module - SystemMemory" +``` + +--- + +## Task 5: Port `thw` Module — TimeHashWheel + +**Go source:** `golang/nats-server/server/thw/` (656 LOC) +**Target:** `dotnet/src/ZB.MOM.NatsNet.Server/Internal/TimeHashWheel.cs` +**Namespace:** `ZB.MOM.NatsNet.Server.Internal` +**Features:** 12 | **Tests:** 14 | **Module ID:** 11 + +```bash +dotnet run --project tools/NatsNet.PortTracker -- feature update 0 --status stub --all-in-module 11 --db porting.db +dotnet run --project tools/NatsNet.PortTracker -- test list --module 11 --db porting.db +# TDD: write tests first, then implement hash wheel +dotnet run --project tools/NatsNet.PortTracker -- module update 11 --status complete --db porting.db +git commit -m "feat: port thw module - TimeHashWheel" +``` + +--- + +## Task 6: Port `certidp` Module — CertificateIdentityProvider + +**Go source:** `golang/nats-server/server/certidp/` (600 LOC) +**Target:** `dotnet/src/ZB.MOM.NatsNet.Server/Auth/CertificateIdentityProvider.cs` +**Namespace:** `ZB.MOM.NatsNet.Server.Auth` +**Features:** 14 | **Tests:** 2 | **Module ID:** 3 + +Use `System.Security.Cryptography.X509Certificates`. + +```bash +dotnet run --project tools/NatsNet.PortTracker -- feature update 0 --status stub --all-in-module 3 --db porting.db +dotnet run --project tools/NatsNet.PortTracker -- module update 3 --status complete --db porting.db +git commit -m "feat: port certidp module - CertificateIdentityProvider" +``` + +--- + +## Task 7: Port `certstore` Module — CertificateStore + +**Go source:** `golang/nats-server/server/certstore/` (1197 LOC) +**Target:** `dotnet/src/ZB.MOM.NatsNet.Server/Auth/CertificateStore.cs` +**Namespace:** `ZB.MOM.NatsNet.Server.Auth` +**Features:** 36 | **Tests:** 0 | **Module ID:** 4 + +```bash +dotnet run --project tools/NatsNet.PortTracker -- feature update 0 --status stub --all-in-module 4 --db porting.db +dotnet run --project tools/NatsNet.PortTracker -- module update 4 --status complete --db porting.db +git commit -m "feat: port certstore module - CertificateStore" +``` + +--- + +## Task 8: Port `gsl` Module — GenericSubjectList + +**Go source:** `golang/nats-server/server/gsl/` (936 LOC) +**Target:** `dotnet/src/ZB.MOM.NatsNet.Server/Subscriptions/GenericSubjectList.cs` +**Namespace:** `ZB.MOM.NatsNet.Server.Subscriptions` +**Features:** 26 | **Tests:** 21 | **Module ID:** 6 + +Performance-sensitive. Use `ReadOnlySpan` for subject matching. + +```bash +dotnet run --project tools/NatsNet.PortTracker -- feature update 0 --status stub --all-in-module 6 --db porting.db +dotnet run --project tools/NatsNet.PortTracker -- test list --module 6 --db porting.db +dotnet run --project tools/NatsNet.PortTracker -- module update 6 --status complete --db porting.db +git commit -m "feat: port gsl module - GenericSubjectList" +``` + +--- + +## Task 9: Port `pse` Module — ProcessStatsProvider + +**Go source:** `golang/nats-server/server/pse/` (1150 LOC, platform-specific) +**Target:** `dotnet/src/ZB.MOM.NatsNet.Server/Internal/ProcessStatsProvider.cs` +**Namespace:** `ZB.MOM.NatsNet.Server.Internal` +**Features:** 28 | **Tests:** 3 | **Module ID:** 7 + +Use `System.Diagnostics.Process`. Mark Go-specific syscall wrappers N/A where replaced. + +```bash +dotnet run --project tools/NatsNet.PortTracker -- feature update 0 --status stub --all-in-module 7 --db porting.db +dotnet run --project tools/NatsNet.PortTracker -- module update 7 --status complete --db porting.db +git commit -m "feat: port pse module - ProcessStatsProvider" +``` + +--- + +## Task 10: Port `stree` Module — SubjectTree + +**Go source:** `golang/nats-server/server/stree/` (3628 LOC) +**Target:** `dotnet/src/ZB.MOM.NatsNet.Server/Subscriptions/SubjectTree.cs` +**Namespace:** `ZB.MOM.NatsNet.Server.Subscriptions` +**Features:** 101 | **Tests:** 59 | **Module ID:** 9 + +Largest leaf module. Performance-critical NATS routing trie. Use `ReadOnlySpan` throughout. + +```bash +dotnet run --project tools/NatsNet.PortTracker -- feature update 0 --status stub --all-in-module 9 --db porting.db +dotnet run --project tools/NatsNet.PortTracker -- test list --module 9 --db porting.db +# write 59 tests first, implement trie, iterate until all pass +dotnet run --project tools/NatsNet.PortTracker -- module update 9 --status complete --db porting.db +git commit -m "feat: port stree module - SubjectTree" +``` + +--- + +## Task 11: Port `tpm` Module — TpmKeyProvider + +**Go source:** `golang/nats-server/server/tpm/` (387 LOC) +**Target:** `dotnet/src/ZB.MOM.NatsNet.Server/Auth/TpmKeyProvider.cs` +**Namespace:** `ZB.MOM.NatsNet.Server.Auth` +**Features:** 8 | **Tests:** 2 | **Module ID:** 12 + +Add conditional Tpm2Lib reference (Windows-only). If unavailable on current platform, throw `PlatformNotSupportedException`. + +```bash +dotnet run --project tools/NatsNet.PortTracker -- feature update 0 --status stub --all-in-module 12 --db porting.db +dotnet run --project tools/NatsNet.PortTracker -- module update 12 --status complete --db porting.db +git commit -m "feat: port tpm module - TpmKeyProvider" +``` + +--- + +## Task 12: Verify Wave 1 (All Leaf Modules Complete) + +```bash +dotnet run --project tools/NatsNet.PortTracker -- report summary --db porting.db +dotnet run --project tools/NatsNet.PortTracker -- dependency ready --db porting.db | head -5 +dotnet build /Users/dohertj2/Desktop/natsnet/dotnet/ZB.MOM.NatsNet.sln +dotnet test /Users/dohertj2/Desktop/natsnet/dotnet/tests/ZB.MOM.NatsNet.Server.Tests/ +``` + +Expected: 11 modules complete, server module appears in `dependency ready`, build green. + +--- + +## Task 13: Port Server Module — Batch A: Core Types + +**Go sources:** `server/const.go`, `server/errors.go`, `server/errors_gen.go`, `server/proto.go`, `server/util.go` +**Targets:** +- `dotnet/src/ZB.MOM.NatsNet.Server/Constants.cs` +- `dotnet/src/ZB.MOM.NatsNet.Server/NatsErrors.cs` +- `dotnet/src/ZB.MOM.NatsNet.Server/Protocol/ProtocolConstants.cs` +- `dotnet/src/ZB.MOM.NatsNet.Server/Internal/Utilities.cs` + +```bash +dotnet run --project tools/NatsNet.PortTracker -- dependency ready --db porting.db +# identify IDs for const/errors/proto/util features; stub them +dotnet build /Users/dohertj2/Desktop/natsnet/dotnet/ZB.MOM.NatsNet.sln +git commit -m "feat: port server core types (const, errors, proto, util)" +``` + +--- + +## Task 14: Port Server Module — Batch B: Options & Config + +**Go sources:** `server/opts.go`, `server/reload.go` +**Targets:** +- `dotnet/src/ZB.MOM.NatsNet.Server/Configuration/NatsServerOptions.cs` +- `dotnet/src/ZB.MOM.NatsNet.Server/Configuration/NatsServerReload.cs` + +```bash +git commit -m "feat: port server options and reload configuration" +``` + +--- + +## Task 15: Port Server Module — Batch C: Parser & Protocol + +**Go sources:** `server/parser.go`, `server/ring.go`, `server/rate_counter.go` +**Targets:** +- `dotnet/src/ZB.MOM.NatsNet.Server/Protocol/NatsParser.cs` +- `dotnet/src/ZB.MOM.NatsNet.Server/Internal/RingBuffer.cs` +- `dotnet/src/ZB.MOM.NatsNet.Server/Internal/RateCounter.cs` + +Parser is performance-critical. Use `ReadOnlySpan` and `System.IO.Pipelines`. + +```bash +git commit -m "feat: port server parser, ring buffer, rate counter" +``` + +--- + +## Task 16: Port Server Module — Batch D: Client & Connection + +**Go sources:** `server/client.go`, `server/client_proxyproto.go`, `server/sendq.go`, `server/ipqueue.go` +**Targets:** +- `dotnet/src/ZB.MOM.NatsNet.Server/Connections/NatsClient.cs` +- `dotnet/src/ZB.MOM.NatsNet.Server/Connections/ProxyProtocolHandler.cs` +- `dotnet/src/ZB.MOM.NatsNet.Server/Connections/SendQueue.cs` +- `dotnet/src/ZB.MOM.NatsNet.Server/Internal/IpQueue.cs` + +Use `Channel` for send queue. All async I/O via `PipeWriter`/`PipeReader`. + +```bash +git commit -m "feat: port server client, connection, send queue" +``` + +--- + +## Task 17: Port Server Module — Batch E: Auth & Security + +**Go sources:** `server/auth.go`, `server/auth_callout.go`, `server/jwt.go`, `server/nkey.go`, `server/ciphersuites.go` +**Targets:** +- `dotnet/src/ZB.MOM.NatsNet.Server/Auth/AuthHandler.cs` +- `dotnet/src/ZB.MOM.NatsNet.Server/Auth/AuthCallout.cs` +- `dotnet/src/ZB.MOM.NatsNet.Server/Auth/JwtValidator.cs` +- `dotnet/src/ZB.MOM.NatsNet.Server/Auth/NkeyProvider.cs` +- `dotnet/src/ZB.MOM.NatsNet.Server/Auth/CipherSuiteMapper.cs` + +```bash +git commit -m "feat: port server auth, JWT, nkeys, cipher suites" +``` + +--- + +## Task 18: Port Server Module — Batch F: Accounts & Events + +**Go sources:** `server/accounts.go`, `server/events.go`, `server/dirstore.go` +**Targets:** +- `dotnet/src/ZB.MOM.NatsNet.Server/Auth/AccountManager.cs` +- `dotnet/src/ZB.MOM.NatsNet.Server/Events/NatsEventBus.cs` +- `dotnet/src/ZB.MOM.NatsNet.Server/Auth/DirectoryAccountStore.cs` + +```bash +git commit -m "feat: port server accounts, events, directory store" +``` + +--- + +## Task 19: Port Server Module — Batch G: Sublist & Subject Transform + +**Go sources:** `server/sublist.go`, `server/subject_transform.go` +**Targets:** +- `dotnet/src/ZB.MOM.NatsNet.Server/Subscriptions/SubList.cs` +- `dotnet/src/ZB.MOM.NatsNet.Server/Subscriptions/SubjectTransform.cs` + +Hot path. Use `ReadOnlySpan`, avoid allocations in `Match`. + +```bash +git commit -m "feat: port server sublist and subject transform" +``` + +--- + +## Task 20: Port Server Module — Batch H: Clustering + +**Go sources:** `server/route.go`, `server/gateway.go`, `server/leafnode.go`, `server/raft.go`, `server/sdm.go`, `server/scheduler.go` +**Targets:** +- `dotnet/src/ZB.MOM.NatsNet.Server/Cluster/RouteHandler.cs` +- `dotnet/src/ZB.MOM.NatsNet.Server/Cluster/GatewayHandler.cs` +- `dotnet/src/ZB.MOM.NatsNet.Server/Cluster/LeafNodeHandler.cs` +- `dotnet/src/ZB.MOM.NatsNet.Server/Cluster/RaftConsensus.cs` +- `dotnet/src/ZB.MOM.NatsNet.Server/Cluster/StreamDomainManager.cs` +- `dotnet/src/ZB.MOM.NatsNet.Server/Cluster/Scheduler.cs` + +```bash +git commit -m "feat: port server clustering (routes, gateway, leaf nodes, raft)" +``` + +--- + +## Task 21: Port Server Module — Batch I: JetStream Core + +**Go sources:** `server/jetstream.go`, `server/jetstream_api.go`, `server/jetstream_errors.go`, `server/jetstream_errors_generated.go`, `server/jetstream_events.go`, `server/jetstream_versioning.go` +**Targets:** +- `dotnet/src/ZB.MOM.NatsNet.Server/JetStream/JetStreamEngine.cs` +- `dotnet/src/ZB.MOM.NatsNet.Server/JetStream/JetStreamApi.cs` +- `dotnet/src/ZB.MOM.NatsNet.Server/JetStream/JetStreamErrors.cs` +- `dotnet/src/ZB.MOM.NatsNet.Server/JetStream/JetStreamEvents.cs` + +```bash +git commit -m "feat: port JetStream core engine and API" +``` + +--- + +## Task 22: Port Server Module — Batch J: JetStream Storage + +**Go sources:** `server/store.go`, `server/filestore.go`, `server/memstore.go` +**Targets:** +- `dotnet/src/ZB.MOM.NatsNet.Server/JetStream/Storage/IMessageStore.cs` +- `dotnet/src/ZB.MOM.NatsNet.Server/JetStream/Storage/FileMessageStore.cs` +- `dotnet/src/ZB.MOM.NatsNet.Server/JetStream/Storage/MemoryMessageStore.cs` + +Define `IMessageStore` from `store.go` first, then implement. + +```bash +git commit -m "feat: port JetStream storage (file store, memory store)" +``` + +--- + +## Task 23: Port Server Module — Batch K: JetStream Streams & Consumers + +**Go sources:** `server/stream.go`, `server/consumer.go`, `server/jetstream_batching.go`, `server/jetstream_cluster.go` +**Targets:** +- `dotnet/src/ZB.MOM.NatsNet.Server/JetStream/StreamManager.cs` +- `dotnet/src/ZB.MOM.NatsNet.Server/JetStream/ConsumerManager.cs` +- `dotnet/src/ZB.MOM.NatsNet.Server/JetStream/BatchProcessor.cs` +- `dotnet/src/ZB.MOM.NatsNet.Server/JetStream/JetStreamCluster.cs` + +```bash +git commit -m "feat: port JetStream streams, consumers, batching, cluster" +``` + +--- + +## Task 24: Port Server Module — Batch L: Monitoring + +**Go sources:** `server/monitor.go`, `server/monitor_sort_opts.go`, `server/msgtrace.go` +**Targets:** +- `dotnet/src/ZB.MOM.NatsNet.Server/Monitoring/NatsMonitor.cs` +- `dotnet/src/ZB.MOM.NatsNet.Server/Monitoring/MonitorSortOptions.cs` +- `dotnet/src/ZB.MOM.NatsNet.Server/Monitoring/MessageTracer.cs` + +`log.go` features → mark N/A: replaced by `Microsoft.Extensions.Logging` + Serilog. + +```bash +git commit -m "feat: port server monitoring, message tracing (log.go → N/A)" +``` + +--- + +## Task 25: Port Server Module — Batch M: MQTT & WebSocket + +**Go sources:** `server/mqtt.go`, `server/websocket.go` +**Targets:** +- `dotnet/src/ZB.MOM.NatsNet.Server/Protocol/MqttHandler.cs` +- `dotnet/src/ZB.MOM.NatsNet.Server/Protocol/WebSocketHandler.cs` + +```bash +git commit -m "feat: port MQTT and WebSocket protocol handlers" +``` + +--- + +## Task 26: Port Server Module — Batch N: OCSP & TLS + +**Go sources:** `server/ocsp.go`, `server/ocsp_peer.go`, `server/ocsp_responsecache.go` +**Targets:** +- `dotnet/src/ZB.MOM.NatsNet.Server/Auth/OcspValidator.cs` +- `dotnet/src/ZB.MOM.NatsNet.Server/Auth/OcspResponseCache.cs` + +```bash +git commit -m "feat: port OCSP validation and response cache" +``` + +--- + +## Task 27: Port Server Module — Batch O: Platform-Specific & N/A + +**Go sources:** `server/disk_avail_*.go`, `server/signal.go`, `server/signal_*.go`, `server/service.go`, `server/service_windows.go` + +- Signal handling → mark N/A: replaced by `IHostApplicationLifetime` +- Windows service → port using `System.ServiceProcess` +- Disk availability → port using `System.IO.DriveInfo`; platform variants → N/A + +```bash +git commit -m "feat: port platform-specific features, mark N/A where replaced" +``` + +--- + +## Task 28: Port Server Module — Batch P: Server Core + +**Go source:** `server/server.go` +**Target:** `dotnet/src/ZB.MOM.NatsNet.Server/NatsServer.cs` + +Main `Server` struct and lifecycle. Final piece of the server module. + +```bash +dotnet run --project tools/NatsNet.PortTracker -- module update 8 --status complete --db porting.db +git commit -m "feat: port server core lifecycle - server module complete" +``` + +--- + +## Task 29: Final Verification & Close Phase 6 + +```bash +dotnet build /Users/dohertj2/Desktop/natsnet/dotnet/ZB.MOM.NatsNet.sln +dotnet test /Users/dohertj2/Desktop/natsnet/dotnet/ZB.MOM.NatsNet.sln +dotnet run --project tools/NatsNet.PortTracker -- dependency blocked --db porting.db +dotnet run --project tools/NatsNet.PortTracker -- report summary --db porting.db +dotnet run --project tools/NatsNet.PortTracker -- phase check 6 --db porting.db + +# Close Gitea issues 39-44 +for issue in 39 40 41 42 43 44; do + curl -s -X PATCH "https://gitea.dohertylan.com/api/v1/repos/dohertj2/natsnet/issues/$issue" \ + -H "Content-Type: application/json" \ + -H "Authorization: token $GITEA_TOKEN" \ + -d '{"state":"closed"}' +done + +# Close Phase 6 milestone +curl -s -X PATCH "https://gitea.dohertylan.com/api/v1/repos/dohertj2/natsnet/milestones/6" \ + -H "Content-Type: application/json" \ + -H "Authorization: token $GITEA_TOKEN" \ + -d '{"state":"closed"}' + +git commit -m "chore: complete phase 6 - initial porting complete" +``` diff --git a/docs/plans/2026-02-26-phase-6-porting.md.tasks.json b/docs/plans/2026-02-26-phase-6-porting.md.tasks.json new file mode 100644 index 0000000..437f6de --- /dev/null +++ b/docs/plans/2026-02-26-phase-6-porting.md.tasks.json @@ -0,0 +1,36 @@ +{ + "planPath": "docs/plans/2026-02-26-phase-6-porting.md", + "tasks": [ + {"id": 0, "subject": "Task 0: Create .NET Solution Structure", "status": "pending"}, + {"id": 1, "subject": "Task 1: Port avl module - SequenceSet", "status": "pending", "blockedBy": [0]}, + {"id": 2, "subject": "Task 2: Port ats module - AccessTimeService", "status": "pending", "blockedBy": [0]}, + {"id": 3, "subject": "Task 3: Port elastic module - ElasticEncoding", "status": "pending", "blockedBy": [0]}, + {"id": 4, "subject": "Task 4: Port sysmem module - SystemMemory", "status": "pending", "blockedBy": [0]}, + {"id": 5, "subject": "Task 5: Port thw module - TimeHashWheel", "status": "pending", "blockedBy": [0]}, + {"id": 6, "subject": "Task 6: Port certidp module - CertificateIdentityProvider", "status": "pending", "blockedBy": [0]}, + {"id": 7, "subject": "Task 7: Port certstore module - CertificateStore", "status": "pending", "blockedBy": [0]}, + {"id": 8, "subject": "Task 8: Port gsl module - GenericSubjectList", "status": "pending", "blockedBy": [0]}, + {"id": 9, "subject": "Task 9: Port pse module - ProcessStatsProvider", "status": "pending", "blockedBy": [0]}, + {"id": 10, "subject": "Task 10: Port stree module - SubjectTree", "status": "pending", "blockedBy": [0]}, + {"id": 11, "subject": "Task 11: Port tpm module - TpmKeyProvider", "status": "pending", "blockedBy": [0]}, + {"id": 12, "subject": "Task 12: Verify Wave 1 (all leaf modules complete)", "status": "pending", "blockedBy": [1,2,3,4,5,6,7,8,9,10,11]}, + {"id": 13, "subject": "Task 13: Port server Batch A - Core Types", "status": "pending", "blockedBy": [12]}, + {"id": 14, "subject": "Task 14: Port server Batch B - Options & Config", "status": "pending", "blockedBy": [13]}, + {"id": 15, "subject": "Task 15: Port server Batch C - Parser & Protocol", "status": "pending", "blockedBy": [14]}, + {"id": 16, "subject": "Task 16: Port server Batch D - Client & Connection", "status": "pending", "blockedBy": [15]}, + {"id": 17, "subject": "Task 17: Port server Batch E - Auth & Security", "status": "pending", "blockedBy": [16]}, + {"id": 18, "subject": "Task 18: Port server Batch F - Accounts & Events", "status": "pending", "blockedBy": [17]}, + {"id": 19, "subject": "Task 19: Port server Batch G - Sublist & Subject Transform", "status": "pending", "blockedBy": [18]}, + {"id": 20, "subject": "Task 20: Port server Batch H - Clustering", "status": "pending", "blockedBy": [19]}, + {"id": 21, "subject": "Task 21: Port server Batch I - JetStream Core", "status": "pending", "blockedBy": [20]}, + {"id": 22, "subject": "Task 22: Port server Batch J - JetStream Storage", "status": "pending", "blockedBy": [21]}, + {"id": 23, "subject": "Task 23: Port server Batch K - JetStream Streams & Consumers", "status": "pending", "blockedBy": [22]}, + {"id": 24, "subject": "Task 24: Port server Batch L - Monitoring", "status": "pending", "blockedBy": [23]}, + {"id": 25, "subject": "Task 25: Port server Batch M - MQTT & WebSocket", "status": "pending", "blockedBy": [24]}, + {"id": 26, "subject": "Task 26: Port server Batch N - OCSP & TLS", "status": "pending", "blockedBy": [25]}, + {"id": 27, "subject": "Task 27: Port server Batch O - Platform-Specific & N/A", "status": "pending", "blockedBy": [26]}, + {"id": 28, "subject": "Task 28: Port server Batch P - Server Core", "status": "pending", "blockedBy": [27]}, + {"id": 29, "subject": "Task 29: Final Verification & Close Phase 6", "status": "pending", "blockedBy": [28]} + ], + "lastUpdated": "2026-02-26T00:00:00Z" +} diff --git a/dotnet/ZB.MOM.NatsNet.slnx b/dotnet/ZB.MOM.NatsNet.slnx new file mode 100644 index 0000000..647dc62 --- /dev/null +++ b/dotnet/ZB.MOM.NatsNet.slnx @@ -0,0 +1,10 @@ + + + + + + + + + + diff --git a/dotnet/src/ZB.MOM.NatsNet.Server.Host/Program.cs b/dotnet/src/ZB.MOM.NatsNet.Server.Host/Program.cs new file mode 100644 index 0000000..7b2cfe9 --- /dev/null +++ b/dotnet/src/ZB.MOM.NatsNet.Server.Host/Program.cs @@ -0,0 +1,2 @@ +// Entry point placeholder - will be populated during server module porting +Console.WriteLine("ZB.MOM.NatsNet.Server"); diff --git a/dotnet/src/ZB.MOM.NatsNet.Server.Host/ZB.MOM.NatsNet.Server.Host.csproj b/dotnet/src/ZB.MOM.NatsNet.Server.Host/ZB.MOM.NatsNet.Server.Host.csproj new file mode 100644 index 0000000..dd31724 --- /dev/null +++ b/dotnet/src/ZB.MOM.NatsNet.Server.Host/ZB.MOM.NatsNet.Server.Host.csproj @@ -0,0 +1,22 @@ + + + + Exe + net10.0 + enable + enable + latest + + + + + + + + + + + + + + diff --git a/dotnet/src/ZB.MOM.NatsNet.Server/ZB.MOM.NatsNet.Server.csproj b/dotnet/src/ZB.MOM.NatsNet.Server/ZB.MOM.NatsNet.Server.csproj new file mode 100644 index 0000000..04c1046 --- /dev/null +++ b/dotnet/src/ZB.MOM.NatsNet.Server/ZB.MOM.NatsNet.Server.csproj @@ -0,0 +1,18 @@ + + + + net10.0 + enable + enable + latest + true + + + + + + + + + + diff --git a/dotnet/tests/ZB.MOM.NatsNet.Server.IntegrationTests/UnitTest1.cs b/dotnet/tests/ZB.MOM.NatsNet.Server.IntegrationTests/UnitTest1.cs new file mode 100644 index 0000000..0ce94ae --- /dev/null +++ b/dotnet/tests/ZB.MOM.NatsNet.Server.IntegrationTests/UnitTest1.cs @@ -0,0 +1,10 @@ +namespace ZB.MOM.NatsNet.Server.IntegrationTests; + +public class UnitTest1 +{ + [Fact] + public void Test1() + { + + } +} diff --git a/dotnet/tests/ZB.MOM.NatsNet.Server.IntegrationTests/ZB.MOM.NatsNet.Server.IntegrationTests.csproj b/dotnet/tests/ZB.MOM.NatsNet.Server.IntegrationTests/ZB.MOM.NatsNet.Server.IntegrationTests.csproj new file mode 100644 index 0000000..cc34c34 --- /dev/null +++ b/dotnet/tests/ZB.MOM.NatsNet.Server.IntegrationTests/ZB.MOM.NatsNet.Server.IntegrationTests.csproj @@ -0,0 +1,28 @@ + + + + net10.0 + enable + enable + latest + false + + + + + + + + + + + + + + + + + + + + diff --git a/dotnet/tests/ZB.MOM.NatsNet.Server.Tests/UnitTest1.cs b/dotnet/tests/ZB.MOM.NatsNet.Server.Tests/UnitTest1.cs new file mode 100644 index 0000000..4f711d4 --- /dev/null +++ b/dotnet/tests/ZB.MOM.NatsNet.Server.Tests/UnitTest1.cs @@ -0,0 +1,10 @@ +namespace ZB.MOM.NatsNet.Server.Tests; + +public class UnitTest1 +{ + [Fact] + public void Test1() + { + + } +} diff --git a/dotnet/tests/ZB.MOM.NatsNet.Server.Tests/ZB.MOM.NatsNet.Server.Tests.csproj b/dotnet/tests/ZB.MOM.NatsNet.Server.Tests/ZB.MOM.NatsNet.Server.Tests.csproj new file mode 100644 index 0000000..364ff8e --- /dev/null +++ b/dotnet/tests/ZB.MOM.NatsNet.Server.Tests/ZB.MOM.NatsNet.Server.Tests.csproj @@ -0,0 +1,29 @@ + + + + net10.0 + enable + enable + latest + false + + + + + + + + + + + + + + + + + + + + + diff --git a/reports/current.md b/reports/current.md index eaf61d6..b15adfa 100644 --- a/reports/current.md +++ b/reports/current.md @@ -1,6 +1,6 @@ # NATS .NET Porting Status Report -Generated: 2026-02-26 12:45:05 UTC +Generated: 2026-02-26 13:03:21 UTC ## Modules (12 total) diff --git a/reports/report_023a5dd.md b/reports/report_023a5dd.md new file mode 100644 index 0000000..b15adfa --- /dev/null +++ b/reports/report_023a5dd.md @@ -0,0 +1,33 @@ +# NATS .NET Porting Status Report + +Generated: 2026-02-26 13:03:21 UTC + +## Modules (12 total) + +| Status | Count | +|--------|-------| +| not_started | 12 | + +## Features (3673 total) + +| Status | Count | +|--------|-------| +| n_a | 41 | +| not_started | 3632 | + +## Unit Tests (3257 total) + +| Status | Count | +|--------|-------| +| not_started | 3257 | + +## Library Mappings (36 total) + +| Status | Count | +|--------|-------| +| mapped | 36 | + + +## Overall Progress + +**41/6942 items complete (0.6%)**