Not using the $GOPATH specified in "go env" - go

I've got
export GOPATH=$HOME/Documents/go
in my .zshrc.
When trying to build a project with the following:
sudo go build -o /usr/bin/
I get a
main.go:5:2: cannot find package "github.com/foo/bar" in any of:
/usr/local/go/src/github.com/foo/bar (from $GOROOT)
/Users/JoahJoah/go/src/github.com/foo/bar (from $GOPATH)
I am assuming the "(from $GOPATH)" means the path is whatever I've set my $GOPATH variable to. And
go env
outputs the following:
GOPATH="/Users/Johannes/Documents/go"
The "Documents" part of the path seems to be omitted when using go build.
Is build using a GOPATH from somewhere else?

Since I was running the the command
$ sudo go build -o /usr/bin/
with sudo prefixed, it was running as the root user, causing a different $GOPATH to be used.
As Eric said, I should instead build to /usr/local/bin where sudo can be omitted.
$ go build /usr/local/bin
Works!

Related

How to install Go package manually from source code

I'm living in China and is not able to download & install GO package through command (event I use the vpn network):
go get -u <repo_url>
but I can access the repo_url and downloand its source code.
So my question is can I put the scource code under src folder and run commamd ? :
go install
if yes, what's the different betweeen the two way ?
for example, you have the repo_url at https://github.com/hello/example
You can do go get manually by
$ cd $GOPATH
$ mkdir -p src/github.com/hello
$ cd src/github.com/hello
$ git clone https://github.com/hello/example.git
$ cd example
$ go install
the binary will install into $GOPATH/bin
if the go program of the repo_url depends on other go package. you have to manually get it and put it to correct path location too.
Two things are important when one looks to get a required package manually,
Path to the package repository; for example, github.com/golang/crypto.git package is hosted on Github. However, when using on code should import as golang.org/x/crypto/bcrypt
Google the required package
Path in the $GOPATH. In this example, the repository should be cloned inside golang.org directory and inside the appropriate directories. To me, the solution to find the path is running code and read the errors for missing modules/packages.

Golang equivalent of npm install -g

If I had a compiled Golang program that I wanted to install such that I could run it with a bash command from anywhere on my computer, how would I do that? For example, in nodejs
npm install -g express
Installs express such that I can run the command
express myapp
and express will generate a file directory for a node application called "myapp" in whatever my current directory is. Is there an equivalent command for go? I believe now with the "go install" command you have to be in the directory that contains the executable in order to run it
Thanks in advance!
Update: If you're using Go 1.16, this answer still works, but go install has changed and is now the recommended method for installing executable packages. See Karim's answer for an explanation: https://stackoverflow.com/a/68559728/10490740
Using Go >= 1.11, if your current directory is within a module-based project, or you've set GO111MODULE=on in your environment, go get will not install packages "globally". It will add them to your project's go.mod file instead.
As of Go 1.11.1, setting GO111MODULE=off works to circumvent this behavior:
GO111MODULE=off go get github.com/usr/repo
Basically, by disabling the module feature for this single command, it will install to GOPATH as expected.
Projects not using modules can still go get normally to install binaries to $GOPATH/bin.
There's a lengthy conversation and multiple issues logged about this change in behavior branching from here: golang/go - cmd/go: go get should not add a dependency to go.mod #27643.
Starting with Go >= 1.16 the recommended way to install an executable is to use
go install package#version
For example, go install github.com/fatih/gomodifytags#latest.
Executables (main packages) are installed to the directory named by the GOBIN environment variable, which defaults to $GOPATH/bin or $HOME/go/bin if the GOPATH environment variable is not set. You need to add this directory to your PATH variable to run executables globally. In my case, I've added this line to my ~/.zshrc file. (if you are using bash, add it to the ~/.bash_profile file):
export PATH="$HOME/go/bin:$PATH"
Go team published a blog post about this change, here's the explanation quote:
We used to recommend go get -u program to install an executable, but this use caused too much confusion with the meaning of go get for adding or changing module version requirements in go.mod.
Refer to go install documentation for more details
As far as I know, there is no direct equivalent to npm install -g. The closest equivalent would not be go install, but go get. From the help page (go help get):
usage: go get [-d] [-f] [-fix] [-insecure] [-t] [-u] [build flags] [packages]
Get downloads and installs the packages named by the import paths,
along with their dependencies.
By default, go get installs binaries to $GOPATH/bin, so the easiest way to make those binaries callable from everywhere is to add that directory to your $PATH.
For this, put the following line into your .bashrc (or .zshrc, depending on which shell you're using):
export PATH="$PATH:$GOPATH/bin"
Alternatively, you could also copy or link the executables to /usr/local/bin:
ln -s $GOPATH/bin/some-binary /usr/local/bin/some-binary
Short solution for Linux users:
Use the go get command as usual
Add the following lines to .bashrc:
# This is the default GOPATH, you should confirm with the 'go env' command
export GOPATH=$HOME/go
export PATH=$PATH:$GOROOT/bin:$GOPATH/bin
Restart terminal or source it. Installed binaries will be available globally.
For Go v1.8+
go install package_name#latest
Caveat: this answer is outdated following the 2020 deprecation of go get. The solution presented here won't work with newer Go runtime installs.
The closest analogue of this in Go would be go get. By default, it will fetch a Go package from a supplied repository URL, and requires a $GOPATH variable to be set in your shell so that Go knows where to store the packages (and subsequently where to find them when compiling code depending on go get-ted packages).
Example syntax:
$ go get github.com/user/repo
The behaviour supplied by npm's -g flag is default, and packages installed using go get are normally available globally.
See go get --help for more information about the command.
As mentioned by #helmbert, adding your $GOPATH to your $PATH is useful if you're installing standalone packages.
if you are using zsh :
first: install your package using :
go install package#version
then , you edit your .zshrc file
nano ~/.zshrc
Add this line to the end of .zshrc file :
export PATH="$HOME/go/bin:$PATH"
last but not least :
source ~/.zshrc
then open a new terminal and execute your command :)
TL;DR at the bottom. I'm going to walk you through how I came to this conclusion, and why the more obvious solutions don't work.
Upon seeing this question, I thought "If I could set root's GOPATH=/usr, it would install things in /usr/bin/ and /usr/src!"
So I tried the obvious thing:
Add GOPATH=/usr to root's .bashrc.
And it worked!
Sort of.
Not really.
Turns out, sudo doesn't execute root's .bashrc. For "security" or something like that.
Do env_set or something in /etc/sudoers
Turns out, /etc/sudoers can only remove environment variables. There's no env_set directive.
(As far as I can find)
Dig through man sudoers.
Where does sudo get it's default set of environment variables from?
Well, the first one in the list is /etc/environment, so that's the one I used.
sudo echo "GOPATH=/usr" >> /etc/environment
sudo go get <repo>
Binaries will be put in /usr/bin, and sources will be put in /usr/src.
Running go as non-root will use GOPATH the "normal" way.
If you don't have go installed, you may use the gobinaries. it builds an on-demand binary of the project from github repo.
The command to install the go package would be:
curl -sf https://gobinaries.com/rakyll/hey | sh

How do I install requirements in Go? "cannot find package"

I'm new to Go and I'm trying to set up a Go project with minimal documentation: https://github.com/alphagov/metadata-api
I've cloned it, but when I try go build I get the following warnings:
main.go:8:2: cannot find package "github.com/Sirupsen/logrus" in any of:
/usr/local/Cellar/go/1.3.3/libexec/src/pkg/github.com/Sirupsen/logrus (from $GOROOT)
/Users/me/go/src/github.com/Sirupsen/logrus (from $GOPATH)
main.go:14:2: cannot find package "github.com/alphagov/metadata-api/content_api" in any of:
/usr/local/Cellar/go/1.3.3/libexec/src/pkg/github.com/alphagov/metadata-api/content_api (from $GOROOT)
/Users/me/go/src/github.com/alphagov/metadata-api/content_api (from $GOPATH)
I'm guessing this is because I haven't installed the Go equivalent of requirements?
My GOPATH is set:
metadata-api$ echo $GOPATH
/Users/me/go
And the Go executable is in
metadata-ape$ echo $PATH
....:/Users/me/go/bin
What do I need to do to help Go find these packages?
You should install package first:
try
$ go get github.com/Sirupsen/logrus
and check you $GOPATH dir
This project use gom as the package manager,
Make sure you have installed gom
or try this command
$ gom install
I think your $GOPATH and $PATH settings are incorrect, the $GOPATH environment variable specifies the location of your workspace, these are my path settings:
export GOROOT=$HOME/bin/go
export GOBIN=$GOROOT/bin
export GOPATH=$HOME/golang
export PATH=$PATH:$GOBIN
I had similar issue and
export GO111MODULE=on
helped.
When you need your code to do something that might have been implemented by someone else (in Github or a package somewhere else), You should initialize a go mod file inside of your folder.)
For the purposes of this example, I'll just use example.com/module.
go mod init example.com/module
Add new module requirements and sums:
go mod tidy
Run your program:
go run .
For more details, see https://golang.org/doc/tutorial/getting-started.
Was able to fix the similar issue in Go 1.13.7 by typing:
export GOPATH=~/go
go get github.com/profile/repository
(e.g. github.com/Sirupsen/logrus)
"...Starting in Go 1.13, module mode will be the default for all development..."
"...When using modules, GOPATH is no longer used for resolving imports. However, it is still used to store downloaded source code (in GOPATH/pkg/mod) and compiled commands (in GOPATH/bin)..."

cannot download, $GOPATH not set

I want to install json2csv using go get github.com/jehiah/json2csv but I receive this error:
package github.com/jehiah/json2csv: cannot download, $GOPATH not set. For more details see: go help go path
Any help on how to fix this on MacOS?
[Update: as of Go 1.8, GOPATH defaults to $HOME/go, but you may still find this useful if you want to understand the GOPATH layout, customize it, etc.]
The official Go site discusses GOPATH and how to lay out a workspace directory.
export GOPATH="$HOME/your-workspace-dir/" -- run it in your shell, then add it to ~/.bashrc or equivalent so it will be set for you in the future. Go will install packages under src/, bin/, and pkg/, subdirectories there. You'll want to put your own packages somewhere under $GOPATH/src, like $GOPATH/src/github.com/myusername/ if you want to publish to GitHub. You'll also probably want export PATH=$PATH:$GOPATH/bin in your .bashrc so you can run compiled programs under $GOPATH.
Optionally, via Rob Pike, you can also set CDPATH so it's faster to cd to package dirs in bash: export CDPATH=.:$GOPATH/src/github.com:$GOPATH/src/golang.org/x means you can just type cd net/html instead of cd $GOPATH/src/golang.org/x/net/html.
Keith Rarick notes you can set GOPATH=$HOME to put Go's src/, pkg/ and bin/ directories right under your homedir. That can be nice (for instance, you might already have $HOME/bin in your path) but of course some folks use multiple workspaces, etc.
This one worked
Setting up Go development environment on Ubuntu, and how to fix $GOPATH / $GOROOT
Steps
mkdir ~/go
Set $GOPATH in .bashrc,
export GOPATH=~/go
export PATH=$PATH:$GOPATH/bin
Using brew
I installed it using brew.
$ brew install go
When it was done if you run this brew command it'll show the following info:
$ brew info go
go: stable 1.4.2 (bottled), HEAD
Go programming environment
https://golang.org
/usr/local/Cellar/go/1.4.2 (4676 files, 158M) *
Poured from bottle
From: https://github.com/Homebrew/homebrew/blob/master/Library/Formula/go.rb
==> Options
--with-cc-all
Build with cross-compilers and runtime support for all supported platforms
--with-cc-common
Build with cross-compilers and runtime support for darwin, linux and windows
--without-cgo
Build without cgo
--without-godoc
godoc will not be installed for you
--without-vet
vet will not be installed for you
--HEAD
Install HEAD version
==> Caveats
As of go 1.2, a valid GOPATH is required to use the `go get` command:
https://golang.org/doc/code.html#GOPATH
You may wish to add the GOROOT-based install location to your PATH:
export PATH=$PATH:/usr/local/opt/go/libexec/bin
The important pieces there are these lines:
/usr/local/Cellar/go/1.4.2 (4676 files, 158M) *
export PATH=$PATH:/usr/local/opt/go/libexec/bin
Setting up GO's environment
That shows where GO was installed. We need to do the following to setup GO's environment:
$ export PATH=$PATH:/usr/local/opt/go/libexec/bin
$ export GOPATH=/usr/local/opt/go/bin
You can then check using GO to see if it's configured properly:
$ go env
GOARCH="amd64"
GOBIN=""
GOCHAR="6"
GOEXE=""
GOHOSTARCH="amd64"
GOHOSTOS="darwin"
GOOS="darwin"
GOPATH="/usr/local/opt/go/bin"
GORACE=""
GOROOT="/usr/local/Cellar/go/1.4.2/libexec"
GOTOOLDIR="/usr/local/Cellar/go/1.4.2/libexec/pkg/tool/darwin_amd64"
CC="clang"
GOGCCFLAGS="-fPIC -m64 -pthread -fno-caret-diagnostics -Qunused-arguments -fmessage-length=0 -fno-common"
CXX="clang++"
CGO_ENABLED="1"
Setting up json2csv
Looks good, so lets install json2csv:
$ go get github.com/jehiah/json2csv
$
What just happened? It installed it. You can check like this:
$ $ ls -l $GOPATH/bin
total 5248
-rwxr-xr-x 1 sammingolelli staff 2686320 Jun 9 12:28 json2csv
OK, so why can't I type json2csv in my shell? That's because the /bin directory under $GOPATH isn't on your $PATH.
$ type -f json2csv
-bash: type: json2csv: not found
So let's temporarily add it:
$ export PATH=$GOPATH/bin:$PATH
And re-check:
$ type -f json2csv
json2csv is hashed (/usr/local/opt/go/bin/bin/json2csv)
Now it's there:
$ json2csv --help
Usage of json2csv:
-d=",": delimiter used for output values
-i="": /path/to/input.json (optional; default is stdin)
-k=[]: fields to output
-o="": /path/to/output.json (optional; default is stdout)
-p=false: prints header to output
-v=false: verbose output (to stderr)
-version=false: print version string
Add the modifications we've made to $PATH and $GOPATH to your $HOME/.bash_profile to make them persist between reboots.
Watch a Video
In general, I always recommend this official video from Go to get a quick overview on the matter:
http://www.youtube.com/watch?v=XCsL89YtqCs
It's easier to be shown than to be told.
#jwfearn paraphrased the important part of the video:
export GOPATH="${HOME}/gocode"; export PATH="${PATH}:${GOPATH}/bin"; mkdir -p "${GOPATH}"
I found easier to do it like this:
export GOROOT=$HOME/go
export GOPATH=$GOROOT/bin
export PATH=$PATH:$GOPATH
For MAC this worked well for me.
sudo nano /etc/bashrc
and add the below at the end of the file
export PATH=$PATH:/usr/local/opt/go/libexec/bin
export GOPATH=/usr/local/opt/go/bin
This should fix the problem. Try opening a new terminal and echo $GOPATH you should see the correct value.
(for MAC)
I tried all these answers and, for some still unknown reason, none of them worked.
I had to "force feed" the GOPATH by setting the environment variable per every command that required it. For example:
sudo env GOPATH=$HOME/goWorkDirectory go build ...
Even glide was giving me the GOPATH not set error. Resolved it, again, by "force feeding":
I tried all these answers and, for some still unknown reason, none of them worked.
I had to "force feed" the GOPATH by setting the environment variable per every command that required it.
sudo env GOPATH=$HOME/goWorkDirectory glide install
Hope this helps someone.
Your $GOROOT should not be set up.
You $GOPATH should be set to $HOME/go by typing export $GOPATH=$HOME/go
Please type export GOROOT="" to fix your problem.
Just do export GOPATH="/whatever/you/like/your/GOPATH/to/be".
If you run into this problem after having $GOPATH set up, it may be because you're running it with an unsupported shell. I was using fish and it did not work, launching it with bash worked fine.
You can use the "export" solution just like what other guys have suggested. I'd like to provide you with another solution for permanent convenience: you can use any path as GOPATH when running Go commands.
Firstly, you need to download a small tool named gost : https://github.com/byte16/gost/releases . If you use ubuntu, you can download the linux version(https://github.com/byte16/gost/releases/download/v0.1.0/gost_linux_amd64.tar.gz).
Then you need to run the commands below to unpack it :
$ cd /path/to/your/download/directory
$ tar -xvf gost_linux_amd64.tar.gz
You would get an executable gost. You can move it to /usr/local/bin for convenient use:
$ sudo mv gost /usr/local/bin
Run the command below to add the path you want to use as GOPATH into the pathspace gost maintains. It is required to give the path a name which you would use later.
$ gost add foo /home/foobar/bar # 'foo' is the name and '/home/foobar/bar' is the path
Run any Go command you want in the format:
gost goCommand [-p {pathName}] -- [goFlags...] [goArgs...]
For example, you want to run go get github.com/go-sql-driver/mysql with /home/foobar/bar as the GOPATH, just do it as below:
$ gost get -p foo -- github.com/go-sql-driver/mysql # 'foo' is the name you give to the path above.
It would help you to set the GOPATH and run the command. But remember that you have added the path into gost's pathspace. If you are under any level of subdirectories of /home/foobar/bar, you can even just run the command below which would do the same thing for short :
$ gost get -- github.com/go-sql-driver/mysql
gost is a Simple Tool of Go which can help you to manage GOPATHs and run Go commands. For more details about how to use it to run other Go commands, you can just run gost help goCmdName. For example you want to know more about install, just type words below in:
$ gost help install
You can also find more details in the README of the project: https://github.com/byte16/gost/blob/master/README.md
Run 'go env' and see where your GOPATH is currently pointing towards. If you change to that directory, your 'go get..etc' command should work.
This problem occured to me in raspberry pi. I had logged in through VNC client
The problem persisted despite setting and exporting the GOPATH.
Then Ran the "go get" command without sudo and it worked perfectly.
I am using vim to edit my .bashrc file but you code use a gui editor such as gedit.
Steps:
Kindly subsitute /path/to/golang/projects below with your actual path location where you will store your golang projects.
Open .bashrc file in vim that is vim ~/.bashrc. Then add below lines at the end of the file.
# Setup Golang Development Environment ::
export GOROOT=/usr/local/go
export PATH=$PATH:$GOROOT/bin
# Third party go libraries will live under "~/golib" directory
export GOPATH="$HOME/golib"
export PATH="$PATH:$GOPATH/bin"
# Where your golang project code lives
export GOPATH=$GOPATH:/path/to/golang/projects
Save the file and type source ~/.bashrc to refresh your terminal session.
Now try getting a package e.g. go get github.com/pilu/fresh and check your ~/golib/bin directory it should have fresh package in it.
Navigate to your /path/to/golang/projects and create three folders in there i.e. bin,src and pkg
Now place your project folder inside /path/to/golang/projects/src e.g. /path/to/golang/projects/src/myfancygolangprojectand you should be good to go. Put all your golang codebase in there mate.
I had to run an application as root (to open a webserver on port 80), this produced the error for me, because the sudo user has a different environment than the normal user, hence GOPATH was not set.
If someone else is having this problem, add -E to the command, this will preserve the user environment.
sudo -E go run main.go
For more infos see discussion here: Google Groups – GOPATH Problem

Error "cannot download, $GOPATH not set."

Setup:
Have a look at my configuration:
$ echo $GOPATH && ls -r $GOPATH
/home/cyrus/.go
src pkg bin
$ echo $GOROOT && ls $GOROOT
/usr/local/go
api AUTHORS bin CONTRIBUTORS doc favicon.ico include lib LICENSE misc PATENTS pkg README robots.txt src test VERSION
You can see that I've set a path for $GOPATH. In addition, I've created subdirectories that I may not need.
Question:
Why does the following command generate this error message?
$ go get code.google.com/p/go-tour/gotour
package code.google.com/p/go-tour/gotour: cannot download, $GOPATH not set. For more details see: go help gopath
If you set a variable like this:
GOPATH=$HOME/go
It won't be exported to any subprocesses. It's only available to that process. If you want to export it to subprocesses, use export:
export GOPATH
You can also combine the assignment and export:
export GOPATH=$HOME/go
My $GOROOT directory was created with owner: root and group: wheel instead having me as the owner and admin as the group. I'll guess that I used sudo when I shouldn't have (or some tool did it for me). As such go get could not write the packages to $GOROOT and hence the $GOPATH not set and permission denied errors.
By using chown and chgrp on my $GOROOT (with -R to get subfolders) 'go get...' worked. In my case VS Code was now able to install the Go components I was after.
When you run go env, you should be able to see if your GOPATH has been set.
On my case though, this command solves it when I had it run on my terminal.
export GOPATH=/usr/local/bin
i had setup GOPATH and it showed correctly with command go env. i had to give the correct permissions to the go directory using chmod and install gb by go get github.com/constabulary/gb/....
First do a `go env' and check the path GOROOT. Accordingly set the GOPATH.
In my case, it had to set GOPATH to /usr/lib/go. Earlier i tried it with /usr/share/go and /usr/bin/go but it didn't work.
$GOPATH should be your current workspace , a folder where your project resides.
or just cd ~/go and try to run those commands.
Or you can just update $GOPATH in ~/.bashrc or ~/.bashrc_profile on ubuntu

Resources