Go | 浅谈包管理模式
任何一门编程语言都离不开对各种工具包的使用,工具包的管理就显得异常重要了。Go 的包管理方式是逐渐演进的,本文介绍Go语言的两种包管理模式。
GOPATH模式引包(不推荐)
在 1.5 版本之前,所有的依赖包都是存放在 GOPATH 下,没有多版本控制。
go的编译器会在 $GOPATH/src 下面寻找对应的模块,src 下的每一个目录都可以对应一个模块,目录中的目录也可以是一个模块
下面展示如何在入口文件main.go 里引入非标准库model包中的变量
- 目录层级如下
├───main
│ main.go
└───model
utils.go
main/main.go入口文件引入utils里面的Name变量model/utils.go文件声明package model,并定义变量var Name string = "xiao",变量必须是大写,否则报错name not exported by package model
- main.go 文件引model包
package main
import (
"fmt"
// 引包
// 省略GOPATH/src, Go编译的时候会自动在src目录下寻找
"go_code/pointer/model"
)
func main() {
fmt.Println(model.Name) // xiao
}
开启GO111MODULE后非module项目产生的问题
在GO111MODULE=on,并且已经设置GOPATH的条件下,写的代码在$GOPATH/src下,我想要使用另一个package里面的内容,并且这个package不是标准库,或者说不在GOROOT里(一般我们不会修改GOROOT中的内容),编译会报错,如下
package go_code/pointer/model is not in GOROOT

解决方法一:
设置GO111MODULE=off
go env -w GO111MODULE=off
设置完之后, go env查看
然后重新编译即可
解决方法二
使用go mod , 请看下文介绍
GO MODULE 模式引包(推荐)
go module 介绍
go modules 是 golang 1.11 新加的特性。
模块是相关Go包的集合
modules是源代码交换和版本控制的单元
go命令直接支持使用modules,包括记录和解析对其他模块的依赖性。modules替换旧的基于GOPATH的方法来指定在给定构建中使用哪些源文件。
GO111MODULE 有三个值:off, on和auto(默认值)。
GO111MODULE=off,go命令行将不会支持module功能,寻找依赖包的方式将会沿用旧版本那种通过vendor目录或者GOPATH模式来查找(也就是本文最开始介绍的方式)。
GO111MODULE=on,go命令行会使用modules,不会去GOPATH目录下查找所引用的包。
GO111MODULE=auto,默认值,go命令行将会根据当前目录来决定是否启用module功能。这种情况下可以分为两种情形:
当前目录在
GOPATH/src之外且该目录包含go.mod文件当前文件在包含go.mod文件的目录下面。
当modules功能启用时,依赖包的存放位置变更为
$GOPATH/pkg,允许同一个package多个版本并存,且多个项目可以共享缓存的module

利用GO111MODULE和GOPROXY,可以直接将Github上的第三方库直接下载到本地使用,不需要使用go get命令。执行 go run 运行时,GOMODULES包管理工具会自动帮我们下载github上面的包
使用 go mod 创建新项目
当开启GO111MODULE的时候,才可以使用go mod
1、初始化项目
mkdir test-mod
cd test-moe
go mod init maze-mod
在项目根目录生成 go.mod 文件
module test-mod
go 1.17
require github.com/astaxie/beego v1.12.1
require (
golang.org/x/net v0.0.0-20190620200207-3b0461eec859 // indirect
golang.org/x/text v0.3.0 // indirect
)
注意:
有
indirect注释的代表间接依赖,没有的代表直接依赖,前面是版本号+时间戳+hash(如:
v0.0.0-20190620200207-3b0461eec859)
go.mod文件一旦创建后,它的内容将会被go toolchain全面掌控。go toolchain会在各类命令执行时(比如go get、go build、go mod等),修改维护go.mod文件。go.mod提供了module, require、replace和exclude 四个命令module 语句指定包的名字(路径)
require 语句指定的依赖项模块
replace 语句可以替换依赖项模块
exclude 语句可以忽略依赖项模块
2、添加依赖
新建
main.go文件执行
go run main.go一般来说
go mod模式下,运行go run会自动安装所有依赖,但是没有安装运行
go get ./ ...可以自动查找并下载安装所有的包运行
go get package@version安装指定版本的依赖包
3、查看依赖
go list -m all查看当前模块所依赖的包列表go mod tidy从go.mod中移除不需要的依赖
4、go.sum文件
用来做包版本管理
go.sum文件与go.mod文件同级。go.sum文件是对导入的依赖包的特定版本的hash校验值,作用就是记录第一次下载的依赖版本号,防止有依赖版本升级带来的不兼容问题。所以,go.mod和go.sum文件都需要被加入版本管理中。
总结
GOPATH模式是 go在 1.5 版本之前的包管理模式,不具备版本控制功能,且所有项目的依赖都放在 GOPATH 里面,管理比较混乱GO MODULE模式是go在1.11 版本推出的,使用git的管理方式,直接从GitHub上下载所需要的依赖,可能会存在一些安全性问题,同时国内需要设置GOPROXY代理服务器才可使用,相对来说好用一点。
包管理模式一直是各个开发语言所面临的棘手问题,比如NPM和Yarn,设计一种完美的包管理模式还需要不断探索实践。

我是 甜点cc
热爱前端开发,也喜欢专研各种跟本职工作关系不大的技术,技术、产品兴趣广泛且浓厚。本号主要致力于分享个人经验总结,希望可以给一小部分人一些微小帮助。
希望能和大家一起努力营造一个良好的学习氛围,为了个人和家庭、为了我国的互联网物联网技术、数字化转型、数字经济发展做一点点贡献。数风流人物还看中国、看今朝、看你我。
Go | 浅谈包管理模式的更多相关文章
- 浅谈JS严格模式
浅谈JS严格模式 简介 何为严格模式?严格模式(strict mode)即在严格的条件下运行,在严格模式下,很多正常情况下不会报错的问题语句,将会报错并阻止运行. 但是,严格模式可以显著提高代码的健壮 ...
- C学习笔记(11)--- 可变参数,浅谈内存管理 【C基础概念系列完结】
1.可变参数(variable arguments): 可变参数允许您定义一个函数,能根据具体的需求接受可变数量的参数. int func(int, ... ) (函数 fun ...
- Linux浅谈磁盘管理及案例
磁盘管理 MBR原理图 从该图可理解到为什么主分区只能是四个. 可以不分区,但为了统一管理,提高访问效率 设备不同,生成设备名称不同 管理分区命令: lsblk查看块设备 fdisk创建MBR分区 f ...
- 浅谈java代理模式
讲解java代理模式 目录 讲解java代理模式 何谓代理模式 静态代理 动态代理 JDK动态代理 CGLIB动态代理 何谓代理模式 代理模式,即Proxy Pattern,23种java常用设计模式 ...
- 浅谈设计模式--组合模式(Composite Pattern)
组合模式(Composite Pattern) 组合模式,有时候又叫部分-整体结构(part-whole hierarchy),使得用户对单个对象和对一组对象的使用具有一致性.简单来说,就是可以像使用 ...
- 【python】浅谈包
python中的包可以理解为模块的集合.每个包也既可以为单包也可以有多个小包组成. Python中的package定义很简单,其层次结构与目录的层次结构相同,但是每个package必须包含一个__in ...
- 浅谈jquery插件开发模式
首先根据<jQuery高级编程>的描述来看,jQuery插件开发方式主要有三种: 通过$.extend()来扩展jQuery 通过$.fn 向jQuery添加新的方法 通过$.widget ...
- 【monkeyrunner】浅谈包名和activity名
概念理解 包名:顾名思义,包名即为程序app的包名. activity名:每个界面都是一个activity. 两者关系:一个包有多个activity. Monkeyrunner中 device.sta ...
- 浅谈JavaScript严格模式(use strict)
"use strict" 的目的是指定代码在严格条件下执行. 严格模式下你不能使用未声明的变量. 严格模式声明 严格模式通过在脚本或函数的头部添加 "use strict ...
- 拜拜了,GOPATH君!新版本Golang的包管理入门教程
Go 1.11和1.12实现了对包管理的初步支持,Go的新依赖管理系统使依赖版本信息明确且易于管理.Using Go Modules - The Go Blog 新的包管理模式有什么不同? 作为Go语 ...
随机推荐
- Ubuntu22.04 将EFI启动分区迁移到另一块硬盘
机器上有两块硬盘, 一块已经安装了Win10, 另一块新装Ubuntu22.04, 在新硬盘上划分分区的时候, 有分出256M给 BOOT EFI, 但是安装的时候没注意, 启动分区不知道怎的跑到 W ...
- 数据抽取平台pydatax介绍
缘起一: 公司现有数据仓库,是通过kettle从mysql抽取到目标库,运行多年,主要有以下问题, 1,效率低:kettle抽取行数少 2,容错性差:一个表抽取出错就导致后续计算 ...
- 《系列一》-- 4、xml配置文件解析之[默认]命名空间[标签]的解析
阅读之前要注意的东西:本文就是主打流水账式的源码阅读,主导的是一个参考,主要内容需要看官自己去源码中验证.全系列文章基于 spring 源码 5.x 版本. Spring源码阅读系列--全局目录.md ...
- Python函数每日一讲 - 一文让你彻底掌握Python中的frozenset函数
引言 在 Python 中,frozenset() 函数是一个重要的工具,用于创建不可变的集合对象.本文将介绍 frozenset() 函数的语法.用法示例以及实际应用场景,帮助大家更好地理解和应用这 ...
- React时间转换为具体的年月日上午下午
export default class index extends Component { constructor() { super(); this.state = { date: new Dat ...
- 【Azure Webjob + Redis】WebJob一直链接Azure Redis一直报错 Timeout Exception
问题描述 运行在App Service上的Webjob连接Azure Redis出现Timeout Exception. 错误截图: 参考Azure Redis对于超时问题的排查建议, 在修改Min ...
- 【Azure API 管理】APIM关闭开发者门户的办法
问题描述 APIM默认提供了开发者门户,可以让用户体验如何来调用接口.但如果不想开发这个功能的情况下,是否有办法关闭呢? 问题解答 答案是:开发人员门户是没有办法关闭的.但是作为另一种的代替方案,如自 ...
- PHP项目&TP框架&SQL&XSS&架构&路由&调试&写法
开发基础-TP框架-入口&调试&路由&写法等 参考手册-TP5开发手册-为了掌握了解框架 首页文件看APP_PATH定义-为了后期分析核心代码 全局搜索:THINK_VERSI ...
- [C++逆向] 8 数组和指针的寻址
目录 数组在函数中 字符串 数组作为参数 下标寻址和指针寻址 多维数组 存放指针类型数据的数组 指向数组的指针变量 函数指针 数组是相同类型数据的集合,以先行方式连续储存在内冲中 而指针只是一个保存地 ...
- Java 异常整合练习
1 package com.bytezero.throwable2; 2 3 /** 4 * 5 * @Description 异常练习 6 * @author Bytezero·zhenglei! ...