I am doing a exercises for creating a module and then accessing global variable through main package.
tutorial at: https://www.golinuxcloud.com/golang-access-variable-from-another-package/
mkdir -p goexamples/global-vars
$ cd goexamples/global-vars
$ touch main.go
$ mkdir util
$ touch util/common.go
$ go mod init global-vars
go: creating new go.mod: module global-vars
go: to add module requirements and sums: go mod tidy
$ go mod tidy
$ cat go.mod
module global-vars
go 1.20
$ cd ..
tree .
.
└── global-vars
├── go.mod
├── main.go
└── util
└── common.go
I will try to access variable from common package into main package.
Here is the content of util/common.go
package util
var Mypath string <<< global variable
func init() {
Mypath = "/tmp"
}
Content of main.go:
package main
import (
"fmt"
"global-vars/util"
)
func main() {
fmt.Println("The path is: " + util.Mypath)
}
when I try to run:
PS C:UsersShawngovsCodeExamStudy_Gogoexamplesglobal-vars> go run main.go
I’ll get the error saying:
go: module golang.org/x/sys appears multiple times in workspace.
(vsCodeExam is the only workspace with both go.work & go.mod)
go.mod :
module golang.org/x/sys
go 1.17
go.work:
go 1.20
use (
.
./DebuggingEx
./DebuggingEx/TestFiles
./DebuggingEx/go-debugging
./Study_Go
)
My GOPATH: C:UsersShawngo
Please tell me how to fix the problem since if you remember I am fairly new to Golang.
2
Answers
result of go env:
Also I take your advise using the 'go run' only but I get an error shown below: PS C:UsersShawngovsCodeExamStudy_Go> go run go: no go files listed (surely there are two .go files in the study_go folder) but when I do: PS C:UsersShawngovsCodeExamStudy_Go> go run GoByExamples.go
How do I put a unique name in the go.mod which has a entry of golang.org/x/sys? where my id of DarkSideOfTheMoon fits in? Should I delete the go.mod and just leave the go.work in the below folder ? C:UsersShawngovsCodeExam ??? (since go.work and go.mod shouldn't be in one folder. I think I should because looking at go env result there's one in GOMOD=C:UsersShawngovsCodeExamStudy_Gogo.mod and one in C:UsersShawngovsCodeExam
Thanks
I believe your issue is something like the following:
You have a workspace (simplified):
and in each folder a
go.mod
:DebuggingEx/go.mod
:DebuggingEx/TestFiles/go.mod
:So when Go loads the workspace it retrieves the two folders and detects that you have two modules called
golang.org/x/sys
(in fact, asgolang.org/x/sys
is a real module and likely imported from the standard library, a single module with this name is likely to cause issues!).Your first question should be "Do I need a workspace". Workspaces are great when you are working on a complicated app and editing multiple modules at the same time. However they do add some complexity and you probably don’t need one (so deleting the
go.work
may be an option). Until you understand how modules work (and import path standards) using a workspace is likely to cause unnecessary confusion.I suspect a second question should be "Do I need multiple go.mod files"? In your case I’d guess that the answer is "no". Put a single
go.mod
at the root of your folder and forget about it (well you may need to rungo mod tidy
andgo get -u ./..."
from time to time). You do not need a separatego.mod
for each subfolder (there are occasions where this may be desirable but probably not worth worrying about now). Bear in mind that a module is "a collection of packages that are released, versioned, and distributed together" – so all of your code while learning can quite happily live within a single module (given that you are not releasing, versioning or distributing).Regardless of the above your module names (as used in
go mod init name
andmodule name
) should be unique. They identify your module (and the fact that you might be importinggolang.org/x/sys
is irrelevant). Calling your modulegolang.org/x/sys
will lead to issues because that is the name of an existing module (that will probably be needed!).Here is a sample module (called
temp3
) that usesgolang.org/x/sys
:It’s the
require
line that declares thatgolang.org/x/sys
is needed (and provides a minimum version).Using module names like
temp3
is valid. However if you want to share your code it becomes an issue (someone else may well use the same name) and prevents the Go tooling from automatically getting the module (it does not know where to findtemp3
; unless you use ago.work
). Because of this general practice is to use an import path that can "describe how to obtain the package source code using a revision control system such as Git or Mercurial" (e.g.github.com/DarkSideOfTheMoon/goexamples
). You don’t have to do this when working locally but it’s a good habit to get into (as is using a version control system such as Git).