Skip to content

FAQ

Do I need cgo, libsystemd or varlinkctl installed?

No. sdvarlink is pure Go and speaks the protocol itself over Unix sockets. Binaries build with CGO_ENABLED=0. varlinkctl is handy for poking at services, but not required.

Which systemd versions are supported?

v257 and newer. Bindings are generated for v257, v258 and v260, and systemd/latest points at v260. On older systemd, a service's socket doesn't exist and Dial returns an error matching varlink.ErrUnsupported, which is your cue to fall back to D-Bus. See Versioning & feature detection.

Why is there no v259 package?

sdvarlink generates bindings for selected releases (v257, v258, v260). Each package works against any newer systemd too, because newer releases accept older calls and unknown reply fields land in Extra. For v259 hosts, import v258 packages (or v260 and feature-detect what's new).

Should I import systemd/v257/... or systemd/latest/...?

Libraries and daemons that run on many hosts: the oldest release you support, plus Supports for anything newer. Tools for a known fleet: latest is fine. Details in Versioning.

Does it work on macOS or in CI without systemd?

The core, the IDL parser and the varlinktest fake build and run on macOS (and other Unix systems), so unit tests built on fakes run anywhere. Talking to systemd itself requires Linux. Recorded golden files (record & replay) let CI exercise real systemd responses without systemd.

Is a client safe for concurrent use?

Yes. Clients from pkg.Dial and pkg.DialPath wrap a connection pool. A single varlink.Conn serializes calls, as the protocol requires. See Concurrency & pools.

How do I cancel a call?

Cancel its context, or break out of a stream. Varlink can't cancel a call on the server, so sdvarlink closes that connection; pools discard it and dial a fresh one for the next call.

My call fails with permission denied or PermissionDenied.

systemd authorizes every call by your process's credentials and polkit. Run as root, add a polkit rule, or set AllowInteractiveAuthentication: varlink.Ptr(true) on methods that support it when running from a terminal. See the Security model.

A newer systemd sends fields my bindings don't know. Are they lost?

No. Every generated struct has an Extra map[string]json.RawMessage holding unknown fields. See Typed clients: unknown fields.

A reply fails to decode with a JSON type error.

A field changed type between systemd releases (rare, but it happens, e.g. io.systemd.Hostname's OperatingSystemImageID was ?int in v258's IDL and ?string in v260's). Use the package of the release whose types match, or decode that method with a raw call. See Versioning: when a field changes type.

Can I use sdvarlink for my own Varlink services?

Yes, on both sides. The varlink core calls any Varlink service, and varlink.Server serves your own interfaces (or systemd's, such as io.systemd.Metrics) with typed handlers; see Serving Varlink. sdvarlink-gen can generate client bindings from your own IDL with a custom generate.json, and varlinktest can fake any interface in tests.

Does it support TCP or remote hosts?

No, by design. systemd's Varlink services listen on local Unix sockets. For remote access, use a bridge such as varlink-http-bridge with its own authentication.

How do I start or stop a unit?

Not over Varlink yet: systemd's io.systemd.Unit offers List and SetProperties, but unit lifecycle control is still D-Bus. Use go-systemd's dbus package for that. See When to keep D-Bus.

How is this different from other Go Varlink libraries?

Other libraries are protocol layers. sdvarlink adds curated, generated, versioned bindings for systemd, first-class file-descriptor passing in both directions, streaming as Go iterators, typed errors and a fake server for tests. The core is purpose-built because fd passing had to be designed in. See Design.

What does the name mean?

systemd + varlink.