Documentation
¶
Overview ¶
Package autoupdate tells a user that a newer release exists, and nothing else.
It never installs. goselfupdate.Update installs, and the command wrapping it is where errors are printed; a failure here is recorded in the state file and swallowed. That single rule is what keeps a development build from printing an update failure on every invocation.
session := autoupdate.Start(ctx, autoupdate.Config{
Update: goselfupdate.Config{Owner: "you", Repo: "tool", Binary: "tool", Version: version},
})
err := rootCmd.ExecuteContext(ctx)
session.Finish()
The check runs concurrently with the caller's own work and the notice is printed afterwards, so a fast command pays nothing and the line is not buried in the command's output.
A separate package from goselfupdate so that a program wanting only the update half links none of this.
Index ¶
Constants ¶
const ( FleetDisable = "NO_AUTO_UPDATE" FleetInterval = "AUTO_UPDATE_INTERVAL" )
Environment variables. Presence-only, any value including empty -- the NO_COLOR convention -- so that NO_AUTO_UPDATE=0 cannot mean "on". The interval gets its own name precisely so presence and value never have to share one variable.
const DefaultInterval = 24 * time.Hour
DefaultInterval is how long a check is good for.
const DefaultTimeout = 5 * time.Second
DefaultTimeout bounds the check. It is generous because the check runs concurrently with the caller's own work and is abandoned if that finishes first, so the only thing this limits is how long Finish will wait.
const Schema = 1
Schema is the version of the on-disk state format.
The same schema is written by pyselfupdate and bashselfupdate, so any tool can read any other tool's state and one dashboard can glob ~/.local/state/*/autoupdate.json with no per-tool knowledge. Adding a field is safe; renaming or repurposing one breaks the other two.
const StateFilename = "autoupdate.json"
StateFilename is the file written inside the per-tool state directory.
Variables ¶
This section is empty.
Functions ¶
Types ¶
type Config ¶
type Config struct {
// Update is the underlying update configuration. Required.
Update goselfupdate.Config
// Tool names the state directory and the per-tool environment variables.
// Defaults to Update.Binary.
Tool string
// Interval between checks. Zero means DefaultInterval.
Interval time.Duration
// Timeout bounds the check. Zero means DefaultTimeout.
Timeout time.Duration
// Out receives the one line this package is allowed to print. Defaults to
// os.Stderr.
Out io.Writer
// Interactive overrides terminal detection. Nil detects. Set it to false
// from a program that already knows it is writing somewhere a human will
// not read -- into a pager, a log, a structured-output mode -- since
// nothing about the streams themselves reveals that.
Interactive *bool
// Suppress skips the check unconditionally. Intended for a command that
// must never trigger one: an update command, a shell-completion callback.
// See [cobracmd] for the list that matters in practice.
Suppress bool
// StateDir overrides where state is written. Defaults to [StateHome].
StateDir string
// Clock supplies the current time. Defaults to time.Now.
Clock func() time.Time
// Environ looks up an environment variable, as os.LookupEnv does.
Environ func(string) (string, bool)
}
Config describes one updatable tool.
type Outcome ¶
Outcome reports what happened. Returned for tests and dashboards, not for control flow: a caller has nothing useful to do with it.
func (Outcome) UpdateAvailable ¶
UpdateAvailable reports whether the check found a newer release.
type Session ¶
type Session struct {
// contains filtered or unexported fields
}
Session is an in-flight check.
func Start ¶
Start runs the gate and, if it passes, begins a check in the background.
It returns immediately and never blocks the command about to run. Call Session.Finish once that command has finished.
type Skip ¶
type Skip string
Skip explains why a check did not happen.
type State ¶
type State struct {
Schema int `json:"schema"`
Tool string `json:"tool"`
CheckedAt string `json:"checked_at"`
// CheckedAtEpoch is the same instant as CheckedAt. Redundant on purpose:
// BSD date on macOS cannot parse ISO-8601 without -j -f gymnastics, and the
// bash implementation has to do interval arithmetic with jq and date +%s
// alone. One duplicated field buys a portable bash sibling.
CheckedAtEpoch int64 `json:"checked_at_epoch"`
CurrentVersion string `json:"current_version"`
LatestVersion string `json:"latest_version"`
// LastError is non-empty when the last check failed. There is deliberately
// no separate "skip reason" field: a gate that declines to check does not
// write this file at all, which is what makes the absence of a state file
// observable proof that the network was never touched.
LastError string `json:"last_error"`
}
State is one tool's record of its last update check.
This is state, not configuration and not cache: it persists across runs, it is not authored by the user, and deleting it changes behavior rather than merely costing a recompute. That is XDG_STATE_HOME by the Base Directory specification, and it is where gh puts the same thing.