目录
- 程序结构
- 程序代码
- 使用和建立包
- 建立目录
- 模块参考中的身份验证
- 计算哈希值
- go.sum文件
- Checksum database
程序结构
声明一个main包(包是对函数进行分组的一种方法,它由同一目录中的所有文件组成)。
导入流行的fmt包,它包含格式化文本的函数,包括打印到控制台。这个包是安装Go时得到的标准库包之一。
实现main函数将消息打印到控制台。当运行主包时,默认执行main函数。
程序代码
package main
import "fmt"
func main() {
fmt.Println("Hello, World!")
}
编译运行
使用geany
或者控制台运行
PS F:\learn\go-learn> go run test.go
Hello, World!
PS F:\learn\go-learn>
使用和建立包
当您需要您的代码执行一些可能已经由其他人实现的事情时,您可以寻找具有可以在您的代码中使用的功能的包。
首先创建一个Go模块。在模块中,您为一组离散而有用的函数收集一个或多个相关包。
Go代码被分组到包中,包被分组到模块中。您的模块指定了运行代码所需的依赖项,包括Go版本和它所需的其他模块集。
当您在模块中添加或改进功能时,您将发布模块的新版本。编写调用模块中函数的代码的开发人员可以导入模块的更新包,并在将其投入生产使用之前使用新版本进行测试。
建立目录
PS F:\learn\go-learn> mkdir mymode
PS F:\learn\go-learn> ls
目录: F:\learn\go-learn
Mode LastWriteTime Length Name
---- ------------- ------ ----
d----- 2022/12/4 22:38 mymode
-a---- 2022/12/4 22:18 84 test.go
PS F:\learn\go-learn> cd mymode
PS F:\learn\go-learn\mymode> go mod init myexample/mymode
go: creating new go.mod: module myexample/mymode
PS F:\learn\go-learn\mymode> ls
目录: F:\learn\go-learn\mymode
Mode LastWriteTime Length Name
---- ------------- ------ ----
-a---- 2022/12/4 22:39 33 go.mod
PS F:\learn\go-learn\mymode>
模块参考中的身份验证
计算哈希值
当go命令下载一个模块zip文件或go。Mod文件到模块缓存中,它计算一个加密散列,并将其与一个已知值进行比较,以验证文件自第一次下载以来没有更改过。如果下载的文件没有正确的散列,go命令会报告安全错误。
Mod文件,go命令从文件内容计算哈希值。对于模块zip文件,go命令以确定的顺序从存档中文件的名称和内容计算哈希值。哈希不受文件顺序、压缩、对齐和其他元数据的影响。
go命令将每个散列与main模块的go. sum文件中每个对应的行进行比较,如果哈希值与go.Sum中的哈希值不同, go命令报告一个安全错误并删除下载的文件,而不将其添加到模块缓存中。
如果go.sum不存在或者如果它不包含下载文件的散列,go命令可以使用校验和数据库验证散列,校验和数据库是公共可用模块的全局散列源。一旦哈希得到验证,go命令将其添加到go中。并将下载的文件添加到模块缓存中。如果一个模块是私有的(由GOPRIVATE或GONOSUMDB环境变量匹配),或者如果校验和数据库被禁用(通过设置GOSUMDB=off), go命令接受散列并将文件添加到模块缓存中,而不进行验证。
go.sum文件
模块可以有一个名为go.Sum的文本文件。在它的根目录中,在它的go.mod文件旁边。
go.Sum包含模块的直接和间接依赖项的加密散列。当go命令将模块的.mod或.zip文件下载到模块缓存中时,它会计算一个散列,并检查该散列是否与主模块的go.sum中的相应散列相匹配。如果模块没有依赖项,或者所有依赖项都使用replace指令替换为本地目录,Sum可能为空或不存在。
模块路径是散列所属模块的名称。
go.sum有三个用空格分隔的字段:模块路径、版本(可能以/go.mod结尾)和散列。
块路径是散列所属模块的名称。
版本是散列所属模块的版本。如果版本以/go.Mod结束,哈希是为了模块的运行。只有Mod文件;否则,该散列是针对模块的.zip文件中的文件。
哈希列由一个算法名(如h1)和一个base64编码的加密哈希组成,用冒号(:)分隔。目前支持的哈希算法只有SHA-256 (h1)。如果未来发现SHA-256中的漏洞,将增加对另一种算法(命名为h2等)的支持。
go.Sum文件可能包含一个模块的多个版本的散列。go命令可能需要从依赖项的多个版本的文件加载go.Mod,以便进行最小版本选择。还可能包含不再需要的模块版本的散列(例如,升级后)。
Go mod tidy将添加丢失的散列,并从Go .sum中删除不必要的散列。
Checksum database
校验的数据库是go的一个全局源。
go命令可以在许多情况下使用它来检测代理或源服务器的不当行为。
校验和数据库允许所有公开可用模块版本的全局一致性和可靠性。它使得不可信的代理成为可能,因为它们不可能在不被发现的情况下提供错误的代码。它还确保与特定版本相关的位不会在一天到一天之间发生变化,即使模块的作者随后更改了他们存储库中的标记。
校验和数据库由sum.golang.org提供服务,该数据库由谷歌运行。
它是go.sum行散列的Transparent Log,它由Trillian支持。默克尔树的主要优点是独立审计员可以验证它没有被篡改,因此它比简单的数据库更值得信任。
如果go命令查询校验和数据库,那么第一步是通过/lookup端点检索记录数据。如果模块版本还没有记录在日志中,校验和数据库将在回复之前尝试从源服务器获取它。
这个/lookup数据提供了这个模块版本的和 (sum)以及它在日志中的位置,它通知客户端应该获取哪些块来执行证明。
在添加新的go.sum行去main主模块的go前,go命令执行“inclusion”证明(日志中存在特定的记录)和“一致性”证明(树没有被篡改)。
重要的是,在使用/lookup数据之前,首先要根据已签名树散列对其进行身份验证,然后根据已签名树散列的客户时间轴对已签名树散列进行身份验证。