《Cargo 参考手册》第二十二章:发布命令

cargo-login(登录到仓库)

名称

cargo-login --- 登录到仓库

语法

cargo login 选项 -- 参数

说明

这个命令会调用一个凭证提供程序来保存令牌,这样像 cargo-publish(1) 这类需要认证的命令,就能自动完成认证了。

两个短横线(--)后面的所有参数,都会传递给凭证提供程序。

对于默认的 cargo:token 凭证提供程序,令牌会保存在 $CARGO_HOME/credentials.toml 里。CARGO_HOME 的默认路径是你用户目录下的 .cargo 文件夹。

如果某个仓库指定了凭证提供程序,就会用这个指定的;要是没指定,就会尝试用配置项 registry.global-credential-providers 里的提供程序,从列表的最后一个开始试。

令牌需要从标准输入(stdin)读取。

crates.io 的 API 令牌可以从这个链接获取:https://crates.io/me

一定要注意保护令牌安全,别跟任何人分享。

选项

登录选项
  • --registry registry:指定要使用的仓库名称。仓库名称在 Cargo 配置文件里定义。如果没指定,就用默认仓库,默认仓库由配置项 registry.default 决定,这个配置项的默认值是 crates-io
显示选项
  • -v / --verbose:输出详细信息。加两次可以输出 "非常详细" 的内容,包括依赖警告、构建脚本输出等。也可以通过配置项 term.verbose 来设置。
  • -q / --quiet:不打印 Cargo 的日志信息。也可以通过配置项 term.quiet 来设置。
  • --color when:控制是否使用彩色输出,可选值有:
    • auto(默认):自动检测终端是否支持彩色输出。
    • always:始终显示彩色。
    • never:从不显示彩色。也可以通过配置项 term.color 来设置。
通用选项
  • +toolchain:如果 Cargo 是用 rustup 安装的,而且 cargo 命令的第一个参数以 + 开头,这个参数会被解析成 rustup 的工具链名称(比如 +stable+nightly)。想了解工具链覆盖的工作原理,可以看 rustup 的文档。
  • --config KEY=VALUE 或 PATH:覆盖某个 Cargo 配置值。参数要符合 TOML 语法,格式是 KEY=VALUE,也可以传一个额外配置文件的路径。这个选项可以多次使用,更多信息看 "命令行覆盖" 相关章节。
  • -C PATH:执行指定操作前,先切换当前工作目录。这会影响很多事情,比如 Cargo 默认去哪里找项目清单文件(Cargo.toml),还有去哪里找 .cargo/config.toml 等。这个选项必须放在命令名称前面,比如 cargo -C path/to/my-project build。该选项仅在 nightly 频道可用,而且需要加 -Z unstable-options 标志才能启用(详见 #10098)。
  • -h / --help:打印帮助信息。
  • -Z flag:Cargo 的不稳定(仅 nightly 可用)标志。运行 cargo -Z help 可查看详情。

环境变量

Cargo 会读取哪些环境变量,详情可参考官方文档。

退出状态

  • 0:Cargo 执行成功。
  • 101:Cargo 执行失败。

示例

  • 保存默认仓库的令牌:cargo login
  • 保存指定仓库的令牌:cargo login --registry my-registry

cargo-logout(从本地仓库移除 API 令牌)

名称

cargo-logout --- 从本地仓库移除 API 令牌

语法

cargo logout 选项

说明

这个命令会调用一个凭证提供程序,删除已保存的令牌。

对于默认的 cargo:token 凭证提供程序,凭证保存在 $CARGO_HOME/credentials.toml 里。CARGO_HOME 的默认路径是你用户目录下的 .cargo 文件夹。

如果某个仓库指定了凭证提供程序,就会用这个指定的;要是没指定,就会尝试用配置项 registry.global-credential-providers 里的提供程序,从列表的最后一个开始试。

如果没加 --registry 选项,就会删除默认仓库的凭证(默认仓库由 registry.default 配置,默认值是 https://crates.io/)。

注意,这个命令不会在服务器上吊销令牌。如果需要吊销令牌,得去仓库的官网按提示操作(比如 crates.io 的令牌吊销,可访问 https://crates.io/me)。

选项

登出选项
  • --registry registry:指定要使用的仓库名称。仓库名称在 Cargo 配置文件里定义。如果没指定,就用默认仓库,默认仓库由配置项 registry.default 决定,这个配置项的默认值是 crates-io
显示选项(同 cargo-login)
  • -v / --verbose:输出详细信息,加两次可显示 "非常详细" 内容。也可通过 term.verbose 配置。
  • -q / --quiet:不打印 Cargo 日志。也可通过 term.quiet 配置。
  • --color when:控制彩色输出,可选 auto/always/never。也可通过 term.color 配置。
通用选项(同 cargo-login)

包括 +toolchain--config-C PATH-h/--help-Z flag,功能完全一致,不再重复说明。

环境变量

Cargo 会读取哪些环境变量,详情可参考官方文档。

退出状态

  • 0:Cargo 执行成功。
  • 101:Cargo 执行失败。

示例

  • 删除默认仓库的令牌:cargo logout
  • 删除指定仓库的令牌:cargo logout --registry my-registry

cargo-owner(管理仓库中某个 crate 的所有者)

名称

cargo-owner --- 管理仓库中某个 crate 的所有者

语法

cargo owner 选项 --add 用户名 crate 名cargo owner 选项 --remove 用户名 crate 名cargo owner 选项 --list crate 名

说明

这个命令用来修改仓库中某个 crate 的所有者。crate 的所有者可以上传新版本、撤回旧版本。注意,非团队所有者也能修改所有者列表,操作时一定要谨慎!

使用这个命令需要认证,要么通过 --token 选项传令牌,要么用 cargo-login(1) 提前登录。

如果没指定 crate 名,就会用当前目录下项目清单里的包名。

想了解更多关于所有者和发布的信息,可参考官方文档。

选项

所有者选项
  • -a / --add login...:邀请指定用户或团队成为所有者。
  • -r / --remove login...:移除指定用户或团队的所有者身份。
  • -l / --list:列出某个 crate 的所有所有者。
  • --token token:认证用的 API 令牌。这个令牌会覆盖凭证文件(由 cargo-login(1) 创建)里保存的令牌。Cargo 配置相关的环境变量也能覆盖凭证文件里的令牌:crates.io 的令牌可通过 CARGO_REGISTRY_TOKEN 环境变量指定;其他仓库的令牌,格式是 CARGO_REGISTRIES_仓库名_TOKEN(仓库名要全大写)。
  • --index index:指定仓库索引的 URL。
  • --registry registry:指定要使用的仓库名称。仓库名称在 Cargo 配置文件里定义。如果没指定,就用默认仓库(由 registry.default 配置,默认值 crates-io)。
显示选项、通用选项(同 cargo-login)

功能与 cargo-login 完全一致,不再重复说明。

环境变量

Cargo 会读取哪些环境变量,详情可参考官方文档。

退出状态

  • 0:Cargo 执行成功。
  • 101:Cargo 执行失败。

示例

  • 列出某个包的所有者:cargo owner --list foo
  • 邀请某个用户成为包的所有者:cargo owner --add username foo
  • 移除某个用户的包所有者身份:cargo owner --remove username foo

cargo-package(将本地包打包成可分发的压缩包)

名称

cargo-package --- 将本地包打包成可分发的压缩包

语法

cargo package 选项

说明

这个命令会把当前目录下的包,打包成一个可分发的 .crate 压缩文件(包含源代码),生成的文件会存在 target/package 目录里。整个过程分以下几步:

  1. 加载并检查当前工作区,做一些基础校验。
    • 路径依赖必须有版本号,否则不允许使用。Cargo 会忽略已发布包依赖中的 path 配置项,但开发依赖(dev-dependencies)没有这个限制。
  2. 生成 .crate 压缩文件。
    • 原始的 Cargo.toml 会被重写并标准化。
    • 清单文件中的 [patch][replace][workspace] 段落会被删除。
    • 一定会包含 Cargo.lock 锁文件:如果锁文件不存在,会生成一个新的(除非加了 --exclude-lockfile 标志)。如果用 cargo-install(1) 时加了 --locked 标志,会使用打包后的锁文件。
    • 会包含一个 .cargo_vcs_info.json 文件:如果能获取到当前版本控制(VCS)的检出哈希值,会存在这个文件里;同时还有一个标志,表示工作区是否有未提交的修改(dirty)。
    • 符号链接(symlinks)会被展开成目标文件。
    • 文件和目录是否包含在压缩包里,由清单文件中 [include][exclude] 字段的规则决定。
  3. 解压 .crate 文件并构建,验证它能否正常构建。
    • 这一步会重新构建包,确保从 "干净状态" 开始也能构建成功。加 --no-verify 标志可以跳过这一步。
  4. 检查构建脚本是否修改了任何源代码。

清单文件中的 includeexclude 字段,可以控制压缩包中包含哪些文件。想了解更多打包和发布的细节,可参考官方文档。

.cargo_vcs_info.json 格式

打包时会生成 .cargo_vcs_info.json 文件,格式如下:

json

复制代码
{
 "git": {
   "sha1": "aac20b6e7e543e6dd4118b246c77225e3a3a1302",
   "dirty": true
 },
 "path_in_vcs": ""
}
  • dirty:表示打包时 Git 工作区是否有未提交的修改。
  • path_in_vcs:如果包在版本控制仓库的子目录里,这个字段会设为仓库相对路径。

这个文件的兼容性遵循与 cargo-metadata(1) JSON 输出相同的策略。注意,这个文件只是对版本控制信息的 "尽力快照",不会验证包的来源,无法保证压缩包中的源代码和版本控制信息完全匹配。

选项

打包选项
  • -l / --list:只打印包中包含的文件,不实际生成压缩包。
  • --no-verify:不通过构建来验证压缩包内容。
  • --no-metadata:忽略 "缺少人工可读元数据"(比如描述、许可证)的警告。
  • --allow-dirty:允许工作区有未提交的版本控制修改时进行打包。
  • --exclude-lockfile:打包时不包含锁文件。这个标志不建议常规使用,有些工具(比如 cargo install --locked)会期望锁文件存在,使用前请考虑其他替代方案。
  • --index index:指定仓库索引的 URL。
  • --registry registry:指定打包针对的仓库(查看 cargo publish --help 可了解仓库名称配置细节)。包不会发布到这个仓库,但如果打包多个相互依赖的 crate,生成锁文件时会假设依赖会发布到这个仓库。
  • --message-format fmt:指定输出消息格式。目前只对 --list 生效,影响文件列表的显示格式。这个功能不稳定,需要加 -Zunstable-options 标志。可选格式:
    • human(默认):每行显示一个文件。

    • json:输出机器可读的 JSON 信息(每行一个 JSON 对象,即换行分隔的 JSON),格式示例如下:

      json

      复制代码
      {
        "id": "path+file:///home/foo#0.0.0",  /* 包的 ID 规格 */
        "files": {  /* 包包含的文件 */
          "Cargo.toml.orig": {  /* 压缩包中的相对路径 */
            "kind": "copy",  /* 文件来源类型:"generate" 表示打包时生成,"copy" 表示从其他位置复制 */
            "path": "/home/foo/Cargo.toml"  /* "copy" 类型:文件实际路径;"generate" 类型:生成文件的原始模板路径 */
          },
          "Cargo.toml": {
            "kind": "generate",
            "path": "/home/foo/Cargo.toml"
          },
          "src/main.rs": {
            "kind": "copy",
            "path": "/home/foo/src/main.rs"
          }
        }
      }
包选择选项

默认情况下,如果没加包选择选项,选中的包由清单文件决定(如果没加 --manifest-path,就基于当前工作目录):

  • 如果清单文件是工作区的根目录,就选中工作区的 "默认成员";
  • 否则,只选中清单文件定义的单个包。

工作区的默认成员可通过根清单文件的 workspace.default-members 配置显式设置。如果没设置:

  • 虚拟工作区会包含所有工作区成员(相当于加 --workspace 标志);

  • 非虚拟工作区只包含根 crate 本身。

  • -p spec... / --package spec...:只打包指定的包。spec 格式参考 cargo-pkgid(1)。这个选项可以多次使用,支持 *?[] 等 Unix 通配符,但为了避免 Shell 提前解析通配符,需要用单引号或双引号把每个模式包起来。

  • --workspace:打包工作区的所有成员。

  • --exclude SPEC...:排除指定的包。必须和 --workspace 一起用。这个选项可以多次使用,支持 Unix 通配符,使用时需用引号包裹模式。

编译选项、功能选择选项、清单选项、杂项选项、显示选项、通用选项

均与 cargo-login 或上述命令中同类选项功能一致,不再重复说明。

环境变量

Cargo 会读取哪些环境变量,详情可参考官方文档。

退出状态

  • 0:Cargo 执行成功。
  • 101:Cargo 执行失败。

示例

  • 将当前包打包成 .crate 压缩文件:cargo package

cargo-publish(把包上传到仓库)

名称

cargo-publish --- 把包上传到仓库

语法

cargo publish 选项

说明

这个命令会把当前目录下的包,打包成可分发的 .crate 压缩文件(包含源代码),然后上传到仓库。默认仓库是 https://crates.io。整个过程分以下几步:

  1. 执行一些检查,包括:
    • 检查清单文件中 package.publish 字段,确认是否限制了可发布的仓库。
  2. 按照 cargo-package(1) 的步骤生成 .crate 文件。
  3. 把压缩包上传到仓库,服务器会对包做额外检查。
  4. 客户端会轮询等待包出现在仓库索引中,这个过程可能会超时。超时不影响上传,超时后需要手动检查是否完成。

使用这个命令需要认证,要么通过 --token 选项传令牌,要么用 cargo-login(1) 提前登录。想了解更多打包和发布的细节,可参考官方文档。

选项

发布选项
  • --dry-run:执行所有检查,但不实际上传。
  • --token token:认证用的 API 令牌,会覆盖凭证文件(cargo-login(1) 创建)里的令牌。环境变量也能覆盖凭证文件令牌:crates.ioCARGO_REGISTRY_TOKEN,其他仓库用 CARGO_REGISTRIES_仓库名_TOKEN(仓库名全大写)。
  • --no-verify:不通过构建验证压缩包内容。
  • --allow-dirty:允许工作区有未提交的版本控制修改时进行打包(并上传)。
  • --index index:指定仓库索引的 URL。
  • --registry registry:指定要发布到的仓库名称。仓库名称在 Cargo 配置文件里定义。如果没指定:
    • Cargo.tomlpackage.publish 字段只指定了一个仓库,就发布到那个仓库;
    • 否则用默认仓库(registry.default 配置,默认 crates-io)。
包选择选项、编译选项、功能选择选项、清单选项、杂项选项、显示选项、通用选项

均与 cargo-package 中同类选项功能一致,不再重复说明。

环境变量

Cargo 会读取哪些环境变量,详情可参考官方文档。

退出状态

  • 0:Cargo 执行成功。
  • 101:Cargo 执行失败。

示例

  • 发布当前包:cargo publish

cargo-yank( 从仓库索引中移除已推送的 crate)

名称

cargo-yank --- 从仓库索引中移除已推送的 crate

语法

cargo yank 选项 crate@版本cargo yank 选项 --version 版本 crate 名

说明

yank 命令会把之前发布的某个 crate 版本,从服务器索引中移除。但它不会删除任何数据,这个 crate 仍然能通过仓库的下载链接获取。

对于新创建的项目,或者没有预存锁文件的项目,Cargo 不会使用被 yank 的版本;如果没有其他兼容版本可用,会直接报错。

使用这个命令需要认证,要么通过 --token 选项传令牌,要么用 cargo-login(1) 提前登录。

如果没指定 crate 名,就会用当前目录下项目清单里的包名。

Yank 的工作原理

举个例子:假设 foo crate 发布了 1.5.0 版本,另一个 bar crate 依赖了 foo = "1.5"。后来 foo 发布了不兼容 SemVer 的 2.0.0 版本,又发现 1.5.0 有严重问题。如果把 1.5.0 yank 了,所有新项目或没有锁文件的项目,都无法使用依赖 foo 1.5bar 了。

所以正确的做法是:foo 的维护者应该先发布一个兼容 SemVer 的版本(比如 1.5.1),再 yank 1.5.0,这样 bar 和所有依赖 bar 的项目才能继续正常工作。

再看一个具体场景:bar crate 已发布 1.5.0、1.5.1、1.5.2、2.0.0、3.0.0 版本。下表展示了 "某个版本被 yank 后",不同 SemVer 依赖要求下,Cargo 会选择哪些版本(无锁文件时):

被 Yank 的版本 / SemVer 要求 bar = "1.5.0" bar = "=1.5.0" bar = "2.0.0"
1.5.0 用 1.5.1 或 1.5.2 报错 用 2.0.0
1.5.1 用 1.5.0 或 1.5.2 用 1.5.0 用 2.0.0
2.0.0 用 1.5.0、1.5.1 或 1.5.2 用 1.5.0 报错

什么时候该用 Yank

只有在特殊情况下才需要 yank,比如:

  • 不小心发布了错误的版本;
  • 发布的版本违反了 SemVer 兼容性;
  • 版本存在严重问题,完全无法使用。

如果是安全漏洞,更推荐用 RustSec 来通知用户升级 ------ 这种方式对下游的影响更小,不会让不涉及漏洞的项目也无法编译。

常见的操作流程是:先发布一个兼容 SemVer 的修复版本,再 yank 有问题的版本,这样能最大程度减少对依赖项目的影响。

另外要注意:

  • 如果是版权、许可证或个人数据问题,只 yank 可能不够,需要联系仓库维护者。比如 crates.io,可参考其政策并发送邮件到 help@crates.io
  • 如果凭证泄露,正确做法是立即吊销凭证。一旦 crate 发布,无法确定泄露的凭证是否已被复制,yank 只能阻止新用户下载,无法阻止已下载用户保留或传播凭证。

选项

Yank 选项
  • --vers version / --version version:指定要 yank 或取消 yank 的版本。
  • --undo:取消之前的 yank 操作,把版本重新加回索引。
  • --token token:认证用的 API 令牌,会覆盖凭证文件(cargo-login(1) 创建)里的令牌。环境变量也能覆盖凭证文件令牌:crates.ioCARGO_REGISTRY_TOKEN,其他仓库用 CARGO_REGISTRIES_仓库名_TOKEN(仓库名全大写)。
  • --index index:指定仓库索引的 URL。
  • --registry registry:指定要使用的仓库名称。仓库名称在 Cargo 配置文件里定义。如果没指定,就用默认仓库(registry.default 配置,默认 crates-io)。
显示选项、通用选项

均与 cargo-login 中同类选项功能一致,不再重复说明。

环境变量

Cargo 会读取哪些环境变量,详情可参考官方文档。

退出状态

  • 0:Cargo 执行成功。
  • 101:Cargo 执行失败。

示例

  • 从索引中移除某个 crate 的指定版本:cargo yank foo@1.0.7
相关推荐
Scott9999HH3 小时前
【IIoT流量实战】蒸汽管道阀门全关却仍有流量?用 Python 实现涡街信号 FFT 频谱分析与温压全补偿积算网关,深度拆解靠谱的涡街流量计厂家硬核技术标准
开发语言·python
码智社4 小时前
AES加密原理详解及Java实现加解密实战
java·开发语言
AI云海4 小时前
python 列表、元组、集合和字典
开发语言·python
萧瑟余晖5 小时前
JDK 26 新特性详解
java·开发语言
马优晨5 小时前
Freemarker 完整讲解(后端 Java 模板引擎)
java·开发语言·freemarker·freemarker 完整讲解·freemarker模板引擎
doiito7 小时前
【AI 应用】从“外国人味”到地道中文:kokoroi-rs v0.1.2 架构升级深度解析
ai·rust·系统设计
人邮异步社区7 小时前
怎么把C语言学到精通?
c语言·开发语言
心平气和量大福大8 小时前
C#-WPF-控件-TextBox 数据绑定
开发语言·c#·wpf
ttwuai8 小时前
Cursor 生成 CRUD 后,Go 后台接口别只测 200:JWT、RBAC 和 tenant_id 怎么验
开发语言·后端·golang
এ慕ོ冬℘゜8 小时前
前端基础:什么是时间戳?JS获取时间戳三种方法与实战用途
开发语言·前端·javascript