第1章Hello world 3/5:Cargo.lock:确保构建稳定可靠:运行第一个程序

2024-06-11 08:29:54 浏览数 (3)

讲动人的故事,写懂人的代码

1.6 Cargo.lock:确保构建稳定可靠

“看!”席双嘉一边指着屏幕一边说,“终端窗口提示符的颜色,从绿变黄了。这就意味着代码在上次提交后有点变化。”

赵可菲:“但是我们只是运行了程序,代码应该没动呀。”

席双嘉敲了下git status -uall,这样就能显示出所有未被git跟踪的文件。

屏幕上出现了一个名叫Cargo.lock的文件。

代码语言:javascript复制
 zkf@mbp  ~/dicey_temperatures  ↱ main  git status -uall
On branch main
Your branch is ahead of 'origin/main' by 1 commit.
  (use "git push" to publish your local commits)

Untracked files:
  (use "git add <file>..." to include in what will be committed)
	Cargo.lock

nothing added to commit but untracked files present (use "git add" to track)

席双嘉:“看,只要一运行cargo run,Cargo.lock文件就被自动创建出来了嘛。”

他随便点开了这个文件。

代码语言:javascript复制
# This file is automatically @generated by Cargo.
# It is not intended for manual editing.
version = 3

[[package]]
name = "hello_world_rust"
version = "0.1.0"

赵可菲:“嘿,这个文件需要提交到版本库吗?”

贾克强:“对的,Cargo.lock文件得提交到版本库,让我们的构建更稳定和可靠。”

“就像咱们程序员最怕的那种情况,明明在自己这儿代码运行得好好的,但怎么在测试环境就犯傻了。”

“许多时候,这就是因为开发环境和测试环境不一致。”

“也就是说,虽然构建的是同一份代码,但由于构建环境差异,开发环境能跑的包,在测试环境再构建后就跑不通了。“

”这是因为,构建环境的差异,让这两个包本身就不一样。”

“Cargo.lock文件就是为了解决这个问题。”

“当你运行 cargo build 时,Cargo 会查看一下 Cargo.toml 文件,看看哪个版本的依赖项最合适。”

“然后它会把这些版本写入 Cargo.lock 文件。一旦有了这个文件,Cargo 会忽略所有的更新,只参考这个文件。”

“除非你想更新。那就得用 cargo update。”

“这个机制就保证了我们构建的包,无论过多久或是谁去构建,都是一致的,保护我们的项目不被新版本的依赖项带来的问题影响。”

赵可菲:“但我们并没有运行cargo build命令呀。”

贾克强:“哈哈!你刚才运行的cargo run命令呀。“

”它会先执行cargo build来编译你的项目。如果编译成功,cargo run接着就会运行编译后的二进制文件。”

贾克强话音未落,席双嘉已经把Cargo.lock文件提交到版本库了。

1.6.1 定义Rust项目元数据与依赖项的Cargo.toml文件

席双嘉指着屏幕问:“这个Cargo.toml文件,和Cargo.lock到底有啥不一样啊?”

代码语言:javascript复制
[package]
name = "hello_world_rust"
version = "0.1.0"
edition = "2021"

[dependencies]

贾克强:“在Rust中,Cargo.tomlCargo.lock就像项目的左右手,他们在Rust项目的构建和依赖管理中非常关键。”

Cargo.toml就像是我们的地图,它定义了项目的基本信息、依赖和配置。”

“你看这个文件,就像是个菜单,分成两个部分。“

[package]就像是我们的门牌号,写着项目的名称、版本、作者等。“

”[dependencies]就像是我们的购物清单,列出了项目需要的所有依赖和版本。“

Cargo.toml需要我们手动编辑,开发者通过它来告诉项目我们需要什么依赖和配置。”

Cargo.lock就像是自动更新的购物清单。它是由Cargo自动创建和管理的,用来记录项目实际使用的所有依赖和版本。“

“每当我们运行cargo buildcargo update等命令时,Cargo会读取Cargo.toml,就像查看我们的购物清单,然后更新Cargo.lock。”

“对于库(library)项目,通常我们不需要把Cargo.lock提交到版本控制系统(比如Git),因为库的用户会根据他们自己的Cargo.toml生成他们需要的Cargo.lock。”

“但对于可执行程序(binary)项目,我们通常会提交Cargo.lock,这样可以确保所有的开发者和部署环境都使用相同的依赖版本。”

“咱们的Hello world就是个可执行程序,所以别忘了把Cargo.lock提交到Git哦。“

1.6.2 Java世界如何确保构建稳定可靠

赵可菲笑着说:“在Java的世界里,要实现类似Rust中Cargo.lock的功能,我们得靠Maven和Gradle这两大神器了。”

“Maven就是通过pom.xml文件来管理项目的依赖。“

”要锁定依赖版本,保证我们构建的东西能稳稳地运行,Maven通常会在<dependencyManagement>里头指定依赖的具体版本,或者用Maven Enforcer插件之类的外部工具。“

”虽然Maven没有直接类似于Cargo.lock的文件,但我们可以在pom.xml中明确所有版本,并利用<dependencyManagement>来锁定它们。”

“此外,Maven的发行版和快照机制,也能分别帮我们管理稳定构建和开发构建。”

“然后是Gradle,它通过build.gradle文件来配置依赖。”

“和Maven一样,Gradle原来并不会自动产生锁文件,不过我们可以通过依赖约束等策略来达到类似的效果。”

“从Gradle 4.8版本开始,Gradle引入了依赖锁文件的概念,允许开发者明确锁定版本。”

“只要运行gradle dependencies --write-locks命令,Gradle就会生成一个锁文件,这个文件会固定依赖的版本,这在功能上就像Rust的Cargo.lock一样,保证了不同环境和时间下构建结果的一致性。”

1.6.3 C 世界如何确保构建稳定可靠

席双嘉:“在C 的世界里,我们也有类似Rust中的Cargo.lock机制,就是用Conan这个工具。”

“Conan,这可是专门为C 量身打造的包管理器哦,它能帮我们处理所有的依赖和版本控制问题,让项目构建得稳稳当当。”

“用Conan的话,它会给我们生成一个叫做conan.lock的文件,这个玩意儿和Rust的Cargo.lock差不多。”

“这个conan.lock文件的作用就是把项目依赖的版本给锁定住,这样无论在哪个环境下构建,依赖都能保持一致。”

“这样一来,就能避免因为依赖版本不同,在开发、测试和生产环境中出现的那些麻烦事儿。”

“虽然CMake本身并没有内建的生成锁文件的功能,但它可以找Conan这样的包管理器作为搭子,通过Conan来管理依赖和版本,也就能间接实现锁定机制了。”

“在CMake的项目里,你可以在CMakeLists.txt文件中包含Conan的配置,然后通过链接Conan管理的库来构建应用程序。”

(未完待续)

如果喜欢这篇文章,别忘了给文章点个赞,好鼓励我继续写哦~

0 人点赞