Embed a server¶
Register the server, then the client¶
srv, err := server.Register(ctx, "nats", controller, log, gonats.ServerSettings{
InProcessOnly: true,
})
if err != nil {
return err
}
cli, err := client.Register(ctx, "nats-client", controller,
gonats.ClientSettings{Name: "my-service"}, nil,
client.InProcess(srv))
if err != nil {
return err
}
Neither is started yet. The controller starts them concurrently, so the client may dial while
the server is still starting. That is safe: an in-process dial waits for the server to finish
starting, up to ServerSettings.ReadyTimeout, and is refused if it does not.
The order matters for stopping. The controller stops services in reverse registration order, so the client drains before the server goes away underneath it.
The client connects at start, not at construction
client.Register validates its settings immediately, so a misconfiguration fails during wiring
where an operator is watching. It does not connect until the controller starts it.
Until then every method returns ErrNotConnected rather than dereferencing a nil connection.
That is not a limitation to work around — it is the only arrangement that works, because a
client constructed with InProcess(srv) at wiring time would be asking a server the controller
has not started yet for a connection, and would fail with failed to get in-process connection.
Register anything that uses the client after the client, for the same reason.
Readiness and liveness are different questions¶
For the server, Readiness asks whether it is accepting connections and Liveness asks whether
it is running at all. A server that is running but not yet accepting is starting, and restarting it
would only make it start again.
For the client, Readiness is false while reconnecting — the connection will recover on its own,
so it is not a liveness failure, but anything asking "can I publish?" wants the answer no. Liveness
is false only when the connection is closed, which is the state NATS reaches after it stops
trying to reconnect. Without that probe a process stays healthy for ever while carrying no traffic.
Turning on JetStream¶
gonats.ServerSettings{
InProcessOnly: true,
JetStream: true,
StoreDir: "/var/lib/myservice/nats",
MaxStore: 8 << 30,
}
StoreDir is required when JetStream is set, and construction fails without it. A JetStream
server with no store directory writes wherever it decides to, which differs by host and survives a
deployment differently on each one.
What you cannot do yet¶
// All refused with ErrNetworkModeUnsupported.
gonats.ServerSettings{} // not in-process
gonats.ServerSettings{InProcessOnly: true, Host: "0.0.0.0"} // a listener
gonats.ServerSettings{InProcessOnly: true, Port: 4222} // a port
gonats.ServerSettings{InProcessOnly: true, Routes: []string{...}} // a mesh
There is no TLS or authentication configuration in this module yet, so a listening server would accept any connection that could reach it, with no credential and nothing encrypted — and a token a client supplied would be neither required by the server nor protected in transit.
The fields are refused rather than ignored, so a configuration that sets them fails loudly instead of quietly doing something else.
If you need a broker on the network, run one and connect a client to it.