Skip to main content
Welcome. This site supports keyboard navigation and screen readers. Press ? at any time for keyboard shortcuts. Press [ to focus the sidebar, ] to focus the content. High-contrast themes are available via the toolbar.
serard@dev00:~/cv

Podman: From Versioned Inputs to Typed Observations

Podman supplies container-engine operations through the same shared command and output contracts as other wrappers. Its wire events and configuration names are its own; Docker-like command names do not establish identical formats.

The consumer separates generated invocation types from the concrete process transport and the reviewed schemas of Podman output.

Acquisition and build ownership

The Design entry point collects containers/podman releases, resolves version-dependent image recipes and parses Cobra help. Its default minimum is 4.1.0.

The pipeline has live version-image/container acquisition and cached-help replay. PodmanEnvironmentCatalog.ReadProcessEnvironment provides declared variables to Design.

Roslyn generates commands in Podman.Contracts and builders/client in the implementation. Contracts also owns environment records, output events, results and its runner interface.

A complete event example

This offline example constructs the generated events command and feeds the reviewed event shape to the real parser factory. It runs no container engine.

using FrenchExDev.Net.BinaryWrapper;
using FrenchExDev.Net.BinaryWrapper.Lib;
using FrenchExDev.Net.BinaryWrapper.Testing;
using FrenchExDev.Net.Podman;

var binding = new BinaryBinding
{
    Identifier = new BinaryIdentifier("podman"),
    ExecutablePath = "unused",
    DetectedVersion = SemanticVersion.Parse("5.8.1"),
};
var command = await Podman.Create(binding).EventsAsync(builder => builder
    .WithFormat("json")
    .WithEnvironment(new PodmanEnvironment { Connection = "example" }));
var source = new OutputLine(
    """{"Type":"container","Status":"start","ID":"c1","Name":"web"}""",
    OutputSource.StdOut);
var executor = new CommandExecutor(new DictionaryBinaryResolver(binding),
    new FakeProcessRunner([source]));
await foreach (var evt in executor.StreamAsync(
    binding.Identifier, command, PodmanOutputStrategies.Default))
{
    if (evt is PodmanContainerStarted started)
        Console.WriteLine($"{started.ContainerName}: {started.ContainerId}");
    if (evt.OutputLine is { } original)
        Console.WriteLine($"{original.Source}: {original.Text}");
    if (evt is PodmanCommandExited exited)
        Console.WriteLine($"CLI exit: {exited.ExitCode}");
}

A live events invocation normally follows indefinitely. Choose a finite stream/window configuration or explicit cancellation. Ending enumeration stops the owned process.

Format selection

PodmanOutputStrategies.Default considers command path and the final format selection. Reviewed event JSON, container arrays, pull/copy progress and diagnostics have different decoding paths.

EventsJson and ContainersJson allow deliberate format selection. They do not add format options to a command. Custom templates, unknown versions and unrelated commands retain generic or raw output.

For container JSON, preserve complete evidence and validate required identity/status fields before projecting. Do not fill missing resource fields from assumptions about what a healthy container “should” report.

Event fields and lifecycle meanings

The source catalogue pins Podman 5.8.1 at c6077f645788743258a1a749f8005b4fb3cbe533. Event records cover reviewed object types and status names, retaining IDs, names, attributes, timestamps and related identities when supplied.

Known container statuses produce typed lifecycle observations. Unknown types/statuses or malformed field kinds remain raw or generic evidence.

PodmanContainerExited.ExitCode belongs to a container event. PodmanCommandExited belongs to the CLI process. A copy/transfer-completed report is another local milestone, not a universal process-success signal.

Event time may be absent in a simplified valid shape. The parser does not manufacture a wire timestamp just because execution has a host clock.

Typed Environment

The catalogue includes CONTAINER_HOST, CONTAINER_CONNECTION, SSH key selection and container configuration, registry and storage files.

Host and Connection describe the tool's connection configuration. A named connection is resolved by Podman configuration and can identify a different endpoint on another machine.

The shared serializer tracks explicit assignments and availability. Bindings supply defaults; commands override them. Process variables remain distinct from a container's configured environment or from the contents of a containers.conf file.

Version policy

The implemented output contract is pinned to the stable 5.8.1 patch, [5.8.1, 5.8.2-0). Its help snapshots can span other releases, so command construction can succeed while semantic output parsing falls back.

Remote engine behavior and extensions can introduce independent protocol concerns. Keep full JSON evidence and register another reviewed profile when meanings or formats change; simply changing a binding version is not an implementation of support.

Verification and consumption

Tests cover source-shaped events, all reviewed names, object fields, evidence identity, channels, malformed/unknown input, format selection, profile limits and fresh buffered state.

The offline example proves the invocation/parser boundary. It does not prove connection resolution, container deployment or health. A start event records a lifecycle transition; supported state queries and health observations provide additional evidence when an application needs it.

Compare Docker for similar responsibilities with different wire schemas, and Podman Compose for Python orchestration around the engine.

Source snapshot

Source inspection: 2 October 2026. These implementation paths are relative to Net/FrenchExDev in the local ecosystem checkout. The v2 changes are largely uncommitted; these paths identify inspected code, without claiming that public branch links contain it.

  • Podman/src/FrenchExDev.Net.Podman.Design/Program.cs
  • Podman/src/FrenchExDev.Net.Podman.Contracts/FrenchExDev.Net.Podman.Contracts.csproj
  • Podman/src/FrenchExDev.Net.Podman/FrenchExDev.Net.Podman.csproj
  • Podman/doc/TYPED-OUTPUT.md
  • Podman/test/FrenchExDev.Net.Podman.Tests

Previous: Packer · Implementation index · Series index · Next: PodmanCompose

⬇ Download