Delete CloudInitService.GetCloudInitConfig, ClusterConfigService.GetTotem/
GetQdevice/GetApiVersion, ContainerService.GetContainer, HaService.GetManagerStatus,
NodeService.GetVersion, TaskService.GetTaskLog, UserService.GetUser, and
VmService.ShutdownVm. #207 found these had no caller outside tests/; re-confirmed by
grep against main at 3ea0e11 before this change. Also deletes the xUnit tests that
existed only to exercise each method, CloudInitService's now-unused CloudInitFields
array, and HaService's now-unused JsonHelper using directive.
Co-authored-by: goodolclint-claude[bot] <323206664+goodolclint-claude[bot]@users.noreply.github.com>
* test: drop the null-session guard tests only a test can reach (#154, part C)
Deletes xUnit tests across tests/PSProxmoxVE.Core.Tests/Services/ that
assert ArgumentNullException for a null PveSession, or for a null
string identifier fed only from a cmdlet parameter PowerShell's
mandatory binding already blocks from being null. Both are paths only
a test's null! literal can trigger; the guard code in src/ stays as
documentation. Kept: constructor null-dependency guards, a null action
to PveServiceBase.Invoke, null-argument tests on optional parameters
or on service methods with no cmdlet caller, and whitespace-guard
tests a real caller can still produce (mandatory binding blocks
null/empty but not whitespace-only strings).
* test: drop the null-session guard tests only a test can reach (#154, part C) [2/2]
* test: drop the null-session guard tests only a test can reach (#154, part C) [3/3]
* test: drop the null-session guard tests only a test can reach (#154, part C) [4/4]
---------
Co-authored-by: goodolclint-claude[bot] <323206664+goodolclint-claude[bot]@users.noreply.github.com>
Every service method built and disposed its own PveHttpClient, and each
client owned a fresh HttpClientHandler, so every API call was a TCP connect
plus a TLS handshake and WaitForTask paid that 300 times over a ten-minute
wait.
PveServiceBase now owns the injected-or-fresh client lifetime behind one
Invoke helper; the 201 hand-written try/finally blocks across the 16
services collapse to calls on it, and the nested NodeService/VmService
instances receive the injected client. PveHttpClient takes its handler
from a process-wide PveHandlerCache keyed on (host, port,
skipCertificateCheck) and never disposes it, so the connection pool
outlives any one client. WaitForTask holds one client for the whole wait
and, when no pollInterval is supplied, backs off from 1 s toward a 10 s
cap, never sleeping past the deadline.
Co-authored-by: goodolclint-claude[bot] <323206664+goodolclint-claude[bot]@users.noreply.github.com>
WaitPveTaskCmdlet hand-rolled its own poll loop (while(true) /
Thread.Sleep / JObject.Parse), the exact pattern ADR 0001 forbids.
It now delegates to TaskService.WaitForTask, passing a progress
callback that drives WriteProgress — the seam WaitForTask was built
for and that nothing called until now.
Preserves the cmdlet's own documented contract (an omitted -Timeout
waits indefinitely) by passing a 100-year sentinel instead of null,
since TaskService.WaitForTask treats a null timeout as its own
10-minute default, not infinite. Reuses one PveHttpClient for the
whole wait instead of letting TaskService open a fresh one per poll.
Also strips the redundant trailing 'null, null, null' default
arguments from 12 other WaitForTask call sites so they use the short
form, per the issue. Left CopyPveContainerCmdlet.cs,
ImportPveOvaCmdlet.cs and NewPveVmCmdlet.cs alone — issue #135 is
touching those concurrently.
Adds three xUnit tests to TaskServiceTests.cs proving the behavior
the inline loop got wrong: no sleep before the first status check,
the 1-second MinPollInterval clamp, and the progress callback firing
on every poll. Mutation-tested by breaking each behavior in turn and
confirming the corresponding test fails.
Closes#140
Co-authored-by: goodolclint-claude[bot] <323206664+goodolclint-claude[bot]@users.noreply.github.com>