self-update-extras 0.2.0

Composable self-update helpers for CLI binaries: throttle, restart, and silence wrappers around any self_update ReleaseUpdate backend
Documentation
# cargo-deny configuration.
#
# Docs:        https://embarkstudios.github.io/cargo-deny/
# Run locally: `just security` or `cargo deny check`
#
# Editing rules of thumb:
#   * If a security advisory is unavoidable (e.g. transitive dep with no
#     fix yet), add it to `[advisories].ignore` *with a comment* linking
#     to the upstream issue and an estimated unblock date.
#   * If a new dep brings in a license not on the allow list below, prefer
#     replacing the dep over adding the license. License-graph drift is
#     hard to undo.
#   * `[bans].deny` is the place to record "we tried this crate and it was
#     bad" - keeps the lesson with the codebase.

[graph]
all-features = true

# ─────────────────────────────────────────────────────────────────────────
# Advisories - RustSec database checks. Overlaps with `cargo audit`; we
# keep both because they fail differently (audit is fast and focused;
# deny is policy-driven and can also catch yanked crates and unmaintained
# advisories).
# ─────────────────────────────────────────────────────────────────────────
[advisories]
db-urls = ["https://github.com/rustsec/advisory-db"]
yanked = "deny"

# Advisories we currently accept because the fix lives in an upstream crate we
# don't control. Re-evaluate when bumping the listed parent dep. Keep one entry
# per ID with a `reason` pointing at the blocker.
ignore = [
    # quick-xml: unbounded namespace-declaration allocation (DoS) and quadratic
    # run time on duplicate attribute names. Pulled in via self_update ->
    # ureq -> ureq-proto. No compatible fix in current dep tree.
    { id = "RUSTSEC-2026-0194", reason = "quick-xml 0.38.4 via self_update -> ureq; no compatible fix in current dep tree" },
    { id = "RUSTSEC-2026-0195", reason = "quick-xml 0.38.4 via self_update -> ureq; no compatible fix in current dep tree" },
]

# ─────────────────────────────────────────────────────────────────────────
# Licenses - allowlist model. This list is intentionally conservative for
# proprietary internal use: copyleft (GPL/AGPL/LGPL) is excluded so it
# can't sneak in transitively.
#
# When a new permissive license shows up in a dep, evaluate it explicitly
# rather than auto-allowing - the SPDX list is large.
# ─────────────────────────────────────────────────────────────────────────
[licenses]
confidence-threshold = 0.9
allow = [
    "0BSD",
    "Apache-2.0",
    "Apache-2.0 WITH LLVM-exception",
    "BSD-2-Clause",
    "BSD-3-Clause",
    "BSL-1.0",
    "CC0-1.0",
    # Linux Foundation's permissive data-licence. Permissive, not
    # copyleft, no patent grant, no copyleft-style propagation -
    # obligations equivalent to MIT/BSD-3. Currently used by
    # `webpki-roots`, which embeds the Mozilla CA bundle (a dataset)
    # and reaches us transitively via `hyper-rustls` from both
    # `gcp-bigquery-client` and `firestore`.
    "CDLA-Permissive-2.0",
    "ISC",
    "MIT",
    "MPL-2.0",
    "Unicode-3.0",
    "Zlib",
]
exceptions = []

# These transitive crates declare only `license-file` (no SPDX `license`
# expression) in their manifest. License detection from the bundled LICENSE
# text already succeeds, but we pin the expression via `clarify` so resolution
# is deterministic instead of depending on askalono's confidence score. The
# `hash` is a crc32 of the LICENSE file; if upstream changes it, the
# clarification stops applying and we re-verify.
#
# Note: cargo-deny still emits an informational `no-license-field` *warning*
# for these crates (it flags the missing manifest field regardless of how the
# license is resolved). There is no config switch to silence it short of the
# upstream crates adding a `license` field.
[[licenses.clarify]]
crate = "cfg_block"
expression = "Apache-2.0"
license-files = [{ path = "LICENSE", hash = 0x0fb72a18 }]

[[licenses.clarify]]
crate = "sigstore-protobuf-specs-derive"
expression = "Apache-2.0"
license-files = [{ path = "LICENSE", hash = 0x86e2b4b4 }]

# Don't require this crate (or any other `publish = false` workspace
# member) to declare a license - internal apps aren't published.
[licenses.private]
ignore = true

# ─────────────────────────────────────────────────────────────────────────
# Bans - duplicate versions, wildcards, blocklist.
#
# `multiple-versions = "warn"` because pinning the entire ecosystem to a
# single version of every transitive dep is a fight you can't win. Bump
# to "deny" only after consolidating duplicates.
# ─────────────────────────────────────────────────────────────────────────
[bans]
multiple-versions = "warn"
wildcards = "deny"
deny = []
skip = []
skip-tree = []

# ─────────────────────────────────────────────────────────────────────────
# Sources - only crates.io is allowed. Pulls from arbitrary git repos
# are denied; if you need one, list its URL under `allow-git` *with a
# comment* explaining why.
# ─────────────────────────────────────────────────────────────────────────
[sources]
unknown-registry = "deny"
unknown-git = "deny"
allow-registry = ["https://github.com/rust-lang/crates.io-index"]
allow-git = []