migrating from dep2Go modules
Tags: go, devops
Published: 2019-10-21 18:38:08


# TL;DR
Go modules was introduced at 1.11 before that people used to package thier dependencies using dep package. in order for us to migrate from the dep package manager to go modules all you have to do is follow those steps:

* move your code outside of GOPATH
* `go mod init [module path]`
* `go mod tidy` ; this will remove unnecessary imports and add indirect ones.
* `rm -rf vendor/`; this folder is created by dep package and holds all dependencies.
* `go build`; this commands ensures that everything is okay.
* `rm -f Gopkg.lock Gopkg.toml`
* `git commit -m "migration from dep to go modules"`

# Introduction

before go 1.11, dependencies management was not an easy task to handle. the go community came up with various solution for it and one of the popular was [dep](https://golang.github.io/dep/)

similar to many dependencies management tools dep has a file that keeps track of all dependencies which called `Gopkg.toml` as well as a file to lock the exact version used which is `Gopkg.lock`. the folder `vendor` holds the dependency files, executing the command `dep ensure` will make all the nessecary checks for the application.

before go 1.11, your project need to be places in `GOPATH` and you had to respect the workplace layout

[workplace layout](https://golang.org/doc/code.html)

after go 1.11 your code can be places anywhere, go can handle directly you dependencies with the introduction of go [modules](https://github.com/golang/go/wiki/Modules).


# Migration

after installing go1.1x start moving your code outside of `GOPATH`

(my GOPATH was `~/Desktop/go`)

`~/Desktop/go $ mv ~/go/src/github.com/houssemcharf/vengine .`

now the project is located in `~/Desktop/go/vengine`

executing go modules

`go mod init`

after executing the command you'll notice that 2 files appeared in your directory.

`go.mod | go.sum`

the first one will contain all the dependencies required for your application to run 
it should be structured this way.

```
module vengine

go 1.13

require (

	vengine/config v0.0.0
	vengine/utils v0.0.0
	github.com/davecgh/go-spew v1.1.1
	github.com/hashicorp/vault/api v1.0.4 // indirect
	github.com/nlopes/slack v0.6.0
	github.com/sirupsen/logrus v1.4.2 // indirect
	github.com/spf13/viper v1.4.0 // indirect
	github.com/tidwall/gjson v1.3.2 // indirect

)

replace (
	vengine/config v0.0.0 => ./config
	vengine/utils v0.0.0 => ./utils

)

```

the second file will contain checksum of different depencies to ensure it integrete as well as the it version. it should look something like this

```
github.com/hashicorp/go-cleanhttp v0.5.0/go.mod h1:JpRdi6/HCYpAwUzNwuwqhbovhLtngrth3wmdIIUrZ80=
github.com/hashicorp/go-cleanhttp v0.5.1 h1:dH3aiDG9Jvb5r5+bYHsikaOUIpcM0xvgMXVoDkXMzJM=
github.com/hashicorp/go-cleanhttp v0.5.1/go.mod h1:JpRdi6/HCYpAwUzNwuwqhbovhLtngrth3wmdIIUrZ80=
github.com/hashicorp/go-hclog v0.0.0-20180709165350-ff2cf002a8dd/go.mod h1:9bjs9uLqI8l75knNv3lV1kA55veR+WUPSiKIWcQHudI=

```


lets go through the first file the `module` refers to your application name`go 1.13` is the go version. within the `require` we ll find a list of dependencies.
to avoid any duplicated dependencies we can execute `go mod tidy` followed by `go build`.


** **Optional** ** 
sometimes you need to structure your project in different packages and in my case i had two seperate modules that i needed in my project. to avoid having difficulties during the build specially in this case it is recommended to create different modules within the different packages by executing `go mod init` . 
```
.
├── main.go
├── config
│   ├── config.go
│   ├── config.json
│   └── go.mod
├── go.mod
├── go.sum
├── LICENSE
├── Makefile
├── README.md
├── utils
   ├── go.mod
   ├── utils.go
   └── utils_test.go

```
as we can see `go.mod` is placed in different packages
- config
- utils

notice that in the previous `go.mod` we used replace which point to our freshly created `go.mod` within the different packages.
```
replace (
	vengine/config v0.0.0 => ./config
	vengine/utils v0.0.0 => ./utils
)
```
it's also worth to mention that those packages are also mentioned in the go.mod within the required directory.
check the example above.
for a final check execute `go build`.