Files
Michael Kriese 55a7341be2 test(manager): close long-tail branch coverage gaps (#45954)
* test(manager): close azure-pipelines, bundler and cocoapods gaps

Adds a pipeline whose step task is not versioned, so nothing is
extracted, and a gem lock line carrying no version, which is skipped.

Marks four guards that cannot be false: `extractContainer()` always
returns a dep, `getLockFilePath()` always returns a path, and the
cocoapods dep name, spec name and git account all derive from values
their enclosing check already proved present.

Co-Authored-By: Claude Opus 5 <michael.kriese+claude-code@mend.io>

* test(manager): close cargo, composer and cpanfile gaps

Adds a composer repository map that disables something other than
packagist, which is dropped rather than recorded.

Marks five guards: the cargo warning only fires for a crate dep and its
retry only runs when a dep was already current, a gitlab rule without a
token never passes the auth check, and both cpanfile handlers run only
once their match produced a value.

Two implicit elses stay counted, in the cargo version resolver and the
composer repository mapper, since a coverage-ignore hint does not attach
to an `else if`.

Co-Authored-By: Claude Opus 5 <michael.kriese+claude-code@mend.io>

* test(manager): close deps-edn, docker-compose and dockerfile gaps

Adds three extractions: a deps.edn alias whose value is not a map, a
compose extension carrying no image, and a dockerfile escape directive
naming a character other than a backtick, which leaves the default in
place.

Marks the deps-edn repository name check, since object keys are always
strings, and notes the repository spec chain, where a coverage-ignore
hint does not attach to an `else if`.

Co-Authored-By: Claude Opus 5 <michael.kriese+claude-code@mend.io>

* test(manager/flux): close the flux coverage gaps

Adds two GitRepository resources whose url is ssh rather than http, one
pinned to a tag and one to a commit. Neither yields a source url, since
only http urls can be turned into one.

Marks the Kustomization image guard: the schema rejects an image without
a name, so `extractImage()` cannot return null there.

Co-Authored-By: Claude Opus 5 <michael.kriese+claude-code@mend.io>

* test(manager): mark github-actions, gitlabci and glasskube guards

None of these six needs a test. A parsed action ref is either a docker
or a repository ref, `getDep()` always returns a dep for a job container
and a service, and the remaining three need a listed file that cannot be
read, a listed file that yields no deps, or a manifest whose
repositories match no name.

The glasskube resource kind chain stays counted, since a coverage-ignore
hint does not attach to an `else if`.

Co-Authored-By: Claude Opus 5 <michael.kriese+claude-code@mend.io>

* test(manager): mark gomod and gradle-wrapper guards

Four guards that need setups no test provides: a removed dep that is not
added back, a go.mod the replace massaging leaves unchanged, and a
daemon-jvm file carrying no toolchain version. A parsed go directive
always yields a version.

The additional-dependency count chain stays counted, since a
coverage-ignore hint does not attach to an `else if`.

Co-Authored-By: Claude Opus 5 <michael.kriese+claude-code@mend.io>

---------

Co-authored-by: Claude Opus 5 <michael.kriese+claude-code@mend.io>
2026-09-15 07:10:10 +00:00
..

Updating of Go mod and toolchain directives

In go.mod, the go directive essentially means "Compatible with this version or later". It is generally recommended for Go projects to not bump this version unless necessary, and therefore Renovate's default behavior is not to propose upgrades to it. If you need to update it once or irregularly, it's recommended to do it manually. If you are sure you want to always bump it to latest, then you need the following configuration:

{
  "packageRules": [
    {
      "matchManagers": ["gomod"],
      "matchDepNames": ["go"],
      "matchDepTypes": ["golang"],
      "rangeStrategy": "bump"
    }
  ]
}

In go.mod, the toolchain directive essentially means "Use this exact version of go". Unlike the go directive, it's valid to keep bumping this, and you should see updates to it proposed by default.

Only suggesting updates that match your go directive

In go.mod, the go directive essentially means "Compatible with this version or later". It is generally recommended for Go projects to not bump this version unless necessary.

As noted above, Renovate doesn't update this directly, but dependency updates can lead to a package you rely on bumping their go directive, which means you can't accept the proposed update without also bumping your go directive.

To make this simpler, you can use constraintsFiltering=strict to make sure that Renovate will only propose updates that match the constraints you specify.

For example, given the go.mod:

module example

go 1.24.0

require golang.org/x/mod v0.32.0

We can then configure Renovate to set the same constraint when updating any Go dependencies:

{
  "$schema": "https://docs.renovatebot.com/renovate-schema.json",
  "packageRules": [
    {
      "description": "Ensure source compatibility with Go version used by this project",
      "matchManagers": ["gomod"],
      "constraintsFiltering": "strict"
    }
  ]
}

In this case, Renovate would only propose an update to a version of golang.org/x/mod that supports Go 1.24.x.

!!! note It is recommended to read the constraintsFiltering documentation and Language constraints and upgrading for more information about how the filtering works and how strict this can be.

Post-Update Options

You might be interested in the following postUpdateOptions:

  1. gomodTidy - if you'd like Renovate to run go mod tidy after every update before raising the PR
  2. This is implicitly enabled for major updates if the user has enabled the option gomodUpdateImportPaths
  3. gomodTidy1.17 - if you'd like Renovate to run go mod tidy -compat=1.17 after every update before raising the PR
  4. gomodTidyE - if you'd like Renovate to run go mod tidy -e after every update before raising the PR
  5. gomodTidyAll - if you'd like Renovate to also run go mod tidy on every other module which depends on the updated one through a local replace directive
    • This implies gomodTidy, needs Go 1.20 or later, and should not be combined with gomodMassage
  6. gomodUpdateImportPaths - if you'd like Renovate to update your source import paths on major updates before raising the PR
  7. gomodMassage - to enable massaging of all replace statements prior to running go so that they will be ignored
  8. goGenerate - to run go generate ./... after vendoring.
    • Will only run if the allowedUnsafeExecutions global option includes goGenerate
    • This will not install any additional tools required to run go generate, you can use tools as one option
    • If gomodTidy is not set, you may encounter failures in the Go toolchain due to missing go.sum entry

When Renovate is running using binarySource=install (such as in the Mend Renovate App) then it will pick the latest compatible version of Go to run, i.e. the latest 1.x release. Even if the go.mod has a version like go 1.22, Renovate will treat it as a ^1.22 constraint and not =1.22.

Unless matching tool directives exist, indirect updates are disabled by default. To enable them, add a package rule such as:

{
  "packageRules": [
    {
      "matchManagers": ["gomod"],
      "matchDepTypes": ["indirect"],
      "enabled": true
    }
  ]
}

Private Modules Authentication

Before running the go commands to update the go.sum, Renovate exports git insteadOf directives in environment variables.

The following logic is executed prior to "artifacts" updating:

The token from the hostRules entry matching hostType=github and matchHost=api.github.com is added as the default authentication for github.com. For those running against github.com, this token will be the default platform token.

Next, all hostRules with both a token or username/password and matchHost will be fetched, except for any github.com one from above.

Rules from this list are converted to environment variable directives if they match any of the following characteristics:

  • No hostType is defined, or
  • hostType is go, or
  • hostType is a platform (github, gitlab, azure, etc.)

Major upgrades of dependencies

Major upgrades in Go are different from most other ecosystems, because both the version and module name need to be changed. It is very common that such upgrades require changes to application code, which Renovate doesn't do.

By default, Renovate will make such change in the go.mod files but nothing else - the rest is up to you. If you add gomodUpdateImportPaths to postUpdateOptions then Renovate will also use a third-party tool to migrate import paths within application code, but there may still be actual application logic which needs to be changed too.

Ultimately: it is known and unavoidable that the majority of major Go upgrades won't be immediately mergeable. You might prefer to configure such major updates with dependencyDashboardApproval=true so that you can request them on demand, on supported platforms.