Packages
Module
A module is a collection of related Go packages that are released together.
A Go repository typically contains only one module, located at the root of the repository.
- You can technically have multiple modules in one repository, but this is not recommended.
- You preferably want to keep one moduleper eachrepository.
A moudle path defined in the go.mod file declares the import path prefix for all packages within the module.
- Moduleis a collection of Go- packages.
- moduleis the way to- importand- exportGo files to external scopes.
The module contains the packages in the directory containing its go.mod file as well as subdirectories of that directory, up to the next subdirectory containing another go.mod file.
- packageis a directory of- .gofiles.
- packageis scoped within a- module.
project-repository/ |-go.mod # module1, does not include module2 |-modname.go # package in module1, doesn't matter outside context of module1 |-modname_test.go # 1 mod per 1 repo project-repo-2/ |-module2 # module2 |-go.mod # uses package1 and package2 |-package1 # reusable within module2 |-funcs.go |-package2 # reusable within module2 |-variables.go
Package
A package is a collection of source files in the same directory that are compiled together.
- Functions, types, variables, and constants defined in one source file are visible to all other source files within the same package.
Package vs Module
Packages within the same module can be imported by other packages via a name path reference.
External packages are installed via a go get command (imported as a module).
Although module defines how a code is versioned and which dependencies are included, you can only import a package of an imported module.
import "github.com/module/package1" import "github.com/module/package2"
Import
You cannot import a file in Go lang.
- You can only import packageswithin amodule.
If you want to extract shared common variables out of a file that is consumed in multiple places, they must be declared in a separate package (can't be a file path like Javascript).
One repository = one module.
- One module= manypackages.
One directory = one package.
- packageis what can be imported by other files.
get
go get is used to reference and install an external package (module).
go get github.com/some/module
Running the go get command will install the target package/module and its dependencies (as defined in the go.mod file of the target package/module).
In your current project mod file, require() method will list the dependencies and versions (automatically listed once compiled).
- getdownloads the- packagesnamed by the- import paths, along with their dependencies.
require ( github.com/some/module v0.14.0 // indirect )
You can update a package by getting it again.
go get -u example.com/some-module
Why are Go packages Github URLs?
The Go path ($GOPATH) is used to resolve import statements.
The statement import "github.com/stretchr/testify/assert" doesn't mean that the package is directly imported from github website (through http).
It's imported from your local, from github.com/stretchr/testify path under $GOPATH/src. The package was downloaded and stored there before, so it can be imported into any project.
- Inital fetching of package would reference the Github URL.
alias package import
import ( "text/template" // this is imported as htmltemplate to avoid collision htmltemplate "html/template" )
Go Does Not Support Circular Dependencies
Do not import packages in tests
When the test is written for a same package method/type, you don't re-import or reference it via Package_Name.method.
- Go has low tolerance for circular dependencies- Golang programs must be acyclic.
- In Golang cyclic imports are not allowed
- That is its import graph must not contain any loops
 
 
- Golang programs must be 
// foo.go package foo func Foo() {...} // foo_test.go package foo // try to access Foo() foo.Foo() // WRONG <== This was the issue. You are already in package foo, there is no need to use foo.Foo() to access Foo() Foo() // CORRECT