02.GoReleaser配置-通用

GoReleaser配置 - 通用

GoReleaser 配置

配置文件

goreleaser init 会在当前目录生成一个示例配置,在日常的维护过程中,可以通过修改 .goreleaser.yaml 文件来自定义 GoReleaser 的行为。

出于简便起见,大多数文档都提到了 .goreleaser.yaml 这个文件名,但实际上还支持几种不同的变体。按优先级排序如下:

  • .config/goreleaser.yml
  • .config/goreleaser.yaml
  • .goreleaser.yml
  • .goreleaser.yaml
  • goreleaser.yml
  • goreleaser.yaml

配置检查

运行 goreleaser check 来检查配置是否有效,该命令会提示是否使用了已弃用或无效的选项。

JSON Schema

https://goreleaser.com/static/schema.json

可以在 .goreleaser.yml 配置文件中通过添加如下所示的注释来指定JSON Schema

# yaml-language-server: $schema=https://goreleaser.com/static/schema.json

指定版本

# yaml-language-server: $schema=https://raw.githubusercontent.com/goreleaser/goreleaser/v2.17.1/www/docs/static/schema.json

通用

带有 (Pro) 的部分表示只有 GoReleaser Pro 版本可以使用

项目名称

项目名称将用于Brew formula和归档等的命名。如果未指定,则会根据 GitHub、GitLab 或 Gitea 发布版本的名称推断出来。

project_name: project-name

元信息(Metadata)

metadata:
  # 文件的修改时间
  # 模板: 支持
  mod_timestamp: "{{ .CommitTimestamp }}"
  # 维护者 (Pro)
  # 模板: 支持
  maintainers:
    - "Foo Bar <foo@bar.com>"

  # license SPDX 标识 (Pro)
  # https://spdx.org/licenses/
  # 模板: 支持
  license: "MIT"

  # 主页 (Pro)
  # 模板: 支持
  homepage: "https://example.com/"

  # 简短描述 (Pro)
  # 模板: 支持
  description: "Software to create fast and easy drum rolls."

  # 完整描述 (Pro)
  # 可以是字符串,也可以从 `from_url` 或者 `from_file` 加载
  # 模板: 支持
  full_description:
    from_url:
      url: https://foo.bar/README.md
      headers:
        x-api-token: "${MYCOMPANY_TOKEN}"
    from_file:
      path: ./README.md

  # 用于向 AUR、Homebrew、Winget、Nix 等提交代码的默认 Git 作者。 (Pro)
  commit_author:
    # 提交人
    # 模板: 支持
    name: goreleaserbot
    # 电子邮箱
    # 模板: 支持
    email: bot@goreleaser.com
    # Git 提交签名配置
    signing:
      # 是否启用签名
      enabled: true
      # 签名Key 值可以是 GPG keyID, fingerprint, 电子邮箱地址或者 key 文件路径
      # 模板: 支持
      key: "{{ .Env.GPG_SIGNING_KEY }}"
      # 签名用的 GPG 可执行程序
      # 模板: 支持
      program: gpg2
      # 签名格式
      # Valid options: openpgp, x509, ssh.
      # Default: openpgp.
      format: openpgp

目标目录

默认情况下,GoReleaser 会将构建产物生成在 ./dist 文件夹中。如有必要,可以通过在 .goreleaser.yaml 文件中进行设置来更改此路径:

# Default: './dist'.
dist: another-folder-that-is-not-dist

Artifacts

GoReleaser 会在 dist 文件夹中生成一个名为 artifacts.json 的文件,其中包含发布过程中生成的所有构建产物的信息。

artifacts.json 文件中包含一个数组,数组中的每个元素有以下属性。

FieldDescription
nameartifact 文件名
pathartifact 路径
goos目标操作系统 (e.g., linux, darwin, windows)
goarch目标指令集架构 (e.g., amd64, arm64, 386)
goamd64amd64 微架构级别 (e.g., v1, v2, v3)
go386386 浮点指令集
goarmARM 版本 (e.g., 6, 7)
goarm64ARM64 版本
gomipsMIPS 浮点指令集
goppc64PPC64 版本
goriscv64RISC-V 64 版本
target完整的构建目标 (e.g., linux_amd64_v1)
typeartifact 类型 (see below)
extra附加元数据 (see below)

Artifact 类型

TypeDescription
Archive压缩文件(tar.gz、zip 等)
Binary已编译的二进制文件
File通用可上传文件
Linux Package由 nfpm 生成的软件包(deb、rpm 等)
SnapSnapcraft 软件包
Docker ImageDocker 镜像
Published Docker Image已发布的 Docker 镜像
Docker ManifestDocker 清单文件
Checksum校验和文件
Signature签名文件
Certificate签名证书
Source源代码归档
Homebrew FormulaHomebrew 配方文件
Homebrew CaskHomebrew cask 文件
Krew Plugin ManifestKrew 插件清单文件
Scoop ManifestScoop 清单文件
SBOM软件物料清单
PKGBUILDArch Linux 的 PKGBUILD 文件
SRCINFOArch Linux 的 .SRCINFO 文件
ChocolateyChocolatey 软件包
C HeaderC 头文件
C Archive LibraryC 静态库
C Shared LibraryC 共享库
Winget ManifestWinget 清单文件
NixpkgNix 软件包
WheelPython wheel 软件包
Source DistPython 源代码发行版
Makeself PackageMakeself 自解压归档文件
App BundlemacOS .app 软件包
DMGmacOS 磁盘映像
MacOS PackagemacOS 安装程序包
MSIWindows MSI 安装程序
NPM PackageNPM 软件包

Extra fields

extra 字段包含根据构建产物类型而异的附加元数据。根据工件类型和配置的不同,extra中可能还包含其他字段。最常见的字段如下。

FieldTypeDescription
IDstring配置中的 Artifacts ID
Binarystring二进制文件名称(适用于仅包含一个二进制文件的归档文件)
Binaries[]string二进制文件名称列表(适用于包含多个二进制文件的归档文件)
Extstring文件扩展名(包括前缀 .
Formatstring归档格式(例如,tar.gzzip
WrappedInstring文件所在的目录名称
Checksumstringalgorithm:hash 格式表示的校验和
Sizeint文件大小(以字节为单位,当 report_sizes 启用时)
DigeststringDocker 镜像摘要
Platforms[]stringDocker (v2) 镜像所针对的架构
Replacesbool通用二进制文件是否取代了单架构二进制文件
Files[]string归档文件中可能包含的任何额外文件
DynamicallyLinkedbool二进制文件是否为动态链接

include (Pro)

GoReleaser 允许通过从 URL 或文件路径引入配置文件以复用一些通用的配置文件。

includes:
  - from_file:
      path: ./config/goreleaser.yaml
  - from_url:
      url: https://raw.githubusercontent.com/goreleaser/goreleaser/main/.goreleaser.yaml
  - from_url:
      url: caarlos0/goreleaserfiles/main/packages.yml # the https://raw.githubusercontent.com/ prefix may be omitted
  - from_url:
      url: https://api.mycompany.com/configs/goreleaser.yaml
      headers:
        # header values are expanded in case they are environment variables
        x-api-token: "${MYCOMPANY_TOKEN}"

模板

GoReleaser 的配置文件中有几个字段支持模板功能。这些字段通常以 _template 结尾,但有时可能没有。

常用字段

KeyDescription
.ProjectName项目名称
.Version即将发布的版本,前缀“v”已被移除,且在 snapshotnightly 中可能会发生变化。
.Branch当前的 Git 分支
.Tag当前的 Git 标签
.PreviousTag上一个 Git 标签(如果没有上一个标签,则为空)
.ShortCommitGit 提交的短哈希值
.FullCommitGit 提交的完整哈希值
.CommitGit 提交的哈希值 (已弃用)
.CommitDateRFC 3339 格式的 UTC 提交日期
.CommitTimestampUnix 格式的 UTC 提交日期
.GitURLGit 远程 URL
.GitTreeState“clean” 或 “dirty”
.IsGitClean当前 Git 状态是否为干净状态
.IsGitDirty当前 Git 状态是否为脏状态
.Major版本号的主版本号,假设 Tag 是有效的 SemVer,否则为空或清零。
.Minor版本号的次版本部分,假设 Tag 是有效的 SemVer,否则为空或清零。
.Patch版本号的补丁部分,假设 Tag 是有效的 SemVer,否则为空或清零。
.Prerelease版本的预发布部分,例如 beta.1,假设 Tag 是有效的 SemVer,否则为空或清零。
.RawVersion{Major}.{Minor}.{Patch} 组成 ,假设 Tag 是有效的 SemVer,否则为空或清零。
.ReleaseNotes生成的发布说明,在执行完变更日志步骤后可用
.IsDraft如果配置中设置了 release.draft,则为 true,否则为 false
.IsSnapshot若设置了 --snapshot 则为 true,否则为 false
.IsNightly若设置了 --nightly 则为 true,否则为 false
.IsSingleTarget若设置了 --single-target 则为 true,否则为 false
.Env包含系统环境变量的映射
.Date当前 UTC 日期(RFC 3339 格式)
.Now当前 UTC 日期(time.Time 结构体形式),支持所有 time.Time 函数(例如 {{ .Now.Format “2006” }}
.Timestamp当前 UTC 时间(Unix 格式)
.ModulePathGo 模块路径,由 go list -m 报告
.ReleaseURL当前版本的下载网址
.SummaryGit 摘要,例如 v1.0.0-10-g34f56g3 该信息由 git describe --dirty --always --tags 命令生成
.TagSubject注释标签的消息主题,或其所指向的提交的消息主题 git tag -l --format='%(contents:subject)'
.TagContents注释标签的消息正文,或其所指向的提交的消息正文 git tag -l --format='%(contents)'
.TagBody注释标签的消息正文,或其所指向的提交的消息正文 git tag -l --format='%(contents)'
.Runtime.Goos等同于 runtime.GOOS
.Runtime.Goarch等同于 runtime.GOARCH
.Outputs自定义输出
.Dist已配置的 dist 目录的绝对路径

常用字段 (Pro)

KeyDescription
.PrefixedTag当前 Git 标签,前缀为单仓库配置中的标签前缀(如有)
.PrefixedPreviousTag上一个 Git 标签,前缀为单仓库配置中的标签前缀(如有)
.PrefixedSummaryGit 摘要,前缀为单仓库配置中的标签前缀(如有)
.IsRelease如果是常规发布(非夜间构建或快照),则为 true
.IsMerging若使用 --merge 运行,则返回 true
.Artifacts参见 Artifacts
.Metadata参见 Metadata

Metadata (Pro)

如果使用 .Metadata 字段,其结果为项目元数据配置。

KeyDescription
.Metadata.Description项目描述
.Metadata.Homepage项目主页网址
.Metadata.License项目许可协议
.Metadata.Maintainers项目维护者列表
.Metadata.ModTimestamp修改时间戳模板

Artifacts (Pro)

如果使用 .Artifacts 字段,其计算结果为 artifact.Artifact列表

  • .Name
  • .Path
  • .Goos
  • .Goarch
  • .Goarm
  • .Gomips
  • .Goamd64
  • .Goarm64
  • .Gomips64
  • .Goppc64
  • .Goriscv64
  • .Go386
  • .Target
  • .Type
  • .Extra

Single-artifact 扩展字段

在与单个 artifact 相关的字段(例如二进制名称)中,可能会包含一些扩展字段:

KeyDescription
.OsGOOS
.ArchGOARCH
.ArmGOARM
.MipsGOMIPS
.Amd64GOAMD64
.Arm64GOARM64
.Mips64GOMIPS64
.Ppc64GOPPC64
.Riscv64GORISCV64
.I386GO386
.Target整个目标
.BinaryArtifact 名称(不包含扩展名)
.ArtifactIDArtifact ID (Pro)
.ArtifactNameArtifact 名称
.ArtifactPathArtifact 的绝对路径
.ArtifactExtArtifact 扩展名(例如 .exe.dmg 等)

nFPM 扩展字段

在 nFPM 的名称模板字段中,可以使用以下扩展字段:

KeyDescription
.Release来自 nFPM 配置的发布版本
.Epoch来自 nFPM 配置的epoch
.PackageName包名。如果未被覆盖,则与 ProjectName 相同。
.ConventionalFileName由 nFPM 提供的标准包文件名。
.ConventionalExtension由 nFPM 提供的标准包扩展名
.Format包格式

Release body 扩展字段

release.body 字段中, 可以使用以下扩展字段:

KeyDescription
.Checksums当前校验和文件的内容,或者如果设置了 checksum.split,则为文件名与校验和内容的映射关系。仅在发布正文中可用

函数

在所有字段中,您可以使用以下功能:

UsageDescription
replace "v1.2" "v" ""替换所有匹配项。参见 ReplaceAll
split "1.2" "."按分隔符拆分字符串。参见 Split
time "01/02/2006"以指定格式返回当前 UTC 时间(此结果非确定性,每次调用返回的时间均不同)
contains "foobar" "foo"检查第一个字符串是否包含第二个字符串。参见 Contains
tolower "V1.2"将输入字符串转换为小写。参见 ToLower
toupper "v1.2"将输入字符串转换为大写。参见 ToUpper
trim " v1.2 "移除所有开头和结尾的空格。参见 TrimSpace
trimprefix "v1.2" "v"移除指定的开头前缀字符串(如果存在)。参见 TrimPrefix
trimsuffix "1.2v" "v"移除指定的结尾后缀字符串(如果存在)。参见 TrimSuffix
dir .Path返回 path 中除最后一个元素以外的所有元素,通常是路径中的目录。参见 Dir
base .Path返回 path 的最后一个元素。参见 Base
abs .ArtifactPath返回 path 的绝对表示形式。参见 Abs
filter "text" "regex"仅保留匹配给定正则表达式的行,类似于 grep -E
reverseFilter "text" "regex"仅保留匹配给定正则表达式的行,类似于 grep -vE
title "foo"使用英语作为语言对字符串进行“标题化”。参见 Title
mdv2escape "foo"根据 MarkdownV2 进行转义,在 Telegram 集成中尤为有用
envOrDefault "NAME" "value"获取给定环境变量的值,或给定的默认值
isEnvSet "NAME"如果环境变量已设置且不为空,则返回 true,否则返回 false
$m := map "KEY" "VALUE"根据键值对列表创建一个映射。键和值都必须是 string 类型
indexOrDefault $m "KEY" "value"从给定的映射中获取指定键的值或给定的默认值
incpatch "v1.2.4"递增给定版本的补丁号[^panic-if-not-semver]
incminor "v1.2.4"递增给定版本的次版本号[^panic-if-not-semver]
incmajor "v1.2.4"递增给定版本的主版本号[^panic-if-not-semver]
urlPathEscape "foo/bar"对 URL 路径进行转义。参见 PathEscape
blake2b .ArtifactPath构建产物的 blake2b 校验和。参见 Blake2b
blake2s .ArtifactPath构建产物的 blake2s 校验和。参见 Blake2s
blake3 .ArtifactPath构建产物的 blake3 校验和。参见 Blake3
crc32 .ArtifactPath构建产物的 crc32 校验和。参见 CRC32
md5 .ArtifactPath构建产物的 md5 校验和。参见 MD5
sha224 .ArtifactPath构建产物的 sha224 校验和。参见 SHA224
sha384 .ArtifactPath构建产物的 sha384 校验和。参见 SHA384
sha256 .ArtifactPath构建产物的 sha256 校验和。参见 SHA256
sha1 .ArtifactPath构建产物的 sha1 校验和。参见 SHA1
sha512 .ArtifactPath构建产物的 sha512 校验和。参见 SHA512
sha3_224 .ArtifactPath构建产物的 sha3_224 校验和。参见 SHA3-224
sha3_384 .ArtifactPath构建产物的 sha3_384 校验和。参见 SHA3-384
sha3_256 .ArtifactPath构建产物的 sha3_256 校验和。参见 SHA3-256
sha3_512 .ArtifactPath构建产物的 sha3_512 校验和。参见 SHA3-512
mustReadFile "/foo/bar.txt"读取文件内容;若无法读取则返回失败
readFile "/foo/bar.txt"若能读取文件内容则读取,否则返回空字符串
englishJoin将多个项目用空格分隔
list "a" "b" "c"创建一个字符串列表

函数 (Pro)

UsageDescription
in (list "a" "b" "c") "b"检查一个切片是否包含某个值
reReplaceAll "(.*)" "foo" "bar-$1"使用 regexp.Compile 编译第一个参数,然后使用 [ReplaceAllString]( https://pkg.go.dev/regexp#Regexp . ReplaceAllStringFunc) 并传入以下参数
list "a" "b" "c" | listExclude "^a$"从列表中移除与给定正则表达式匹配的项

有了这些字段,基本上可以按照自己的意愿来组合工件的名称:

example_template: '{{ tolower .ProjectName }}_{{ .Env.USER }}_{{ time "2006" }}'

例如:如果想在某个构建产物中添加 Go 版本信息

foo_template: "foo_{{ .Env.GOVERSION }}"

运行:

GOVERSION=$(go version | awk '{print $3;}') goreleaser

请注意,这些只是假设性的示例,字段 foo_templateexample_template 并非有效的 GoReleaser 配置。

自定义变量 (Pro)

您还可以声明自定义变量。此功能在处理 [include] 时特别有用,可以编写拥有更通用的配置文件。

variables:
  description: my project description
  somethingElse: yada yada yada
  empty: ""

然后,就可以将这些字段作为 {{ .Var.description }} 来使用,例如。

环境变量

将传递给所有钩子和构建的全局环境变量。

如果你有一个名为 FOOBAR 的环境变量,其值为 on,那么你的 .goreleaser.yaml 文件可以像这样使用它:

env:
  - FOO={{ .Env.FOOBAR }}
  - ENV_WITH_DEFAULT={{ if index .Env "ENV_WITH_DEFAULT"  }}{{ .Env.ENV_WITH_DEFAULT }}{{ else }}default_value{{ end }}
before:
  hooks:
    - go mod tidy
builds:
  - binary: program

这样一来,无论是预处理钩子(在本例中为 go mod tidy),还是底层的构建操作(使用 go build),FOO 都会被设置为 on

根级别的 env 部分也支持模板。

全局钩子

某些发布周期可能需要在其他所有操作之前或之后执行某些操作。GoReleaser 通过全局钩子功能支持这一需求。

before 部分支持全局钩子,这些钩子将在发布开始前执行。

before:
  # Templates for the commands to be ran.
  hooks:
    - make clean
    - go generate ./...
    - go mod tidy
    - touch {{ .Env.FILE_TO_TOUCH }}

注意

如果任何一个钩子执行失败,Release将被立刻中止。

如果需要执行更复杂的操作,建议编写一个 shell 脚本并调用它

Git

git 的配置可以更改某些 git 命令的行为。

git:
  # 如果同一个提交中包含多个标签,在收集当前标签和上一个标签时,应使用什么标准对标签进行排序?
  #
  # See: https://git-scm.com/docs/git-tag#Documentation/git-tag.txt---sortltkeygt
  #
  # Default: '-version:refname'.
  tag_sort: -version:creatordate

  # 当同一提交中包含多个标签时,在收集当前和上一个标签并按标签排序时,应使用什么来指定预发布后缀?
  prerelease_suffix: "-"


  # GoReleaser 将忽略的标签。
  # 这意味着 GoReleaser 不会将与所提供值中的任何一个匹配的标签作为先前标签或当前标签进行识别。
  #
  # 支持通配符模式。 (Pro)
  # 
  # 模板: 支持
  ignore_tags:
    - nightly
    - "*-nightly"
    - "{{.Env.IGNORE_TAG}}"

  # 以这些前缀开头的标签将被忽略。 (Pro)
  # 
  # 模板: 支持
  ignore_tag_prefixes:
    - foo/
    - "{{.Env.IGNORE_TAG_PREFIX}}/bar"

重试

大多数外部服务调用都会经过重试机制,对于被判定为可重试的失败情况,将采用指数退避策略。

这包括:

  • Git 服务提供商 — GitHub、GitLab 和 Gitea 的 API 调用(发布、上传、里程碑、拉取请求等)
  • 公告渠道 — Discord、Telegram、Slack、Mastodon、Teams、Reddit、Twitter、Bluesky、LinkedIn、Discourse、Mattermost、Webhook、OpenCollective 和 MCP
  • HTTP 上传 — Artifactory、自定义 HTTP 上传及类似操作
  • Docker — 镜像构建和推送(包括 dockers 和 dockers_v2),其中包含临时基础镜像拉取以及 RUN 步骤中的包安装

临时性失败(网络错误、HTTP 5xx 错误和 429 请求过多)会自动重试。永久性失败(4xx 错误、文件未找到等)则不会重试。

配置如下:

retry:
  # Set max retry count.
  # Setting to 1 disables retries (single attempt).
  #
  # Default: 10
  attempts: 15

  # Set delay between retry
  #
  # Default: 10s
  delay: 10s

  # Default: 5m
  max_delay: 3m