Problem: there's an awesome Golang project on GitHub which you want to fork. You want to develop & collaborate on that fork, but the golang import path, in your source code, still references the original path, breaking everything.
A couple solutions offered below. First, though, let's get some names.
A sample case, the problem at hand
There's an awesome tool on http://github.com/awsome-org/tool. You successfully fork it onto http://github.com/awesome-you/tool.
You want to collaborate on http://github.com/awesome-you/tool; you wish to pull, commit & push. Maybe you want to send pull requests to the origin.
The following is commonly found throughout .go files in the repository:
import (
"github.com/awesome-org/tool/config"
"github.com/awesome-org/tool/driver"
"github.com/awesome-org/tool/net"
"github.com/awesome-org/tool/util"
)
If you:
go get http://github.com/awesome-you/tool
golang creates your $GOPATH/src/github.com/awesome-you/tool/, which is awesome. However, as you resolve dependencies via
cd $GOPATH/src/github.com/awesome-you/tool/ ; go get ./...
golang digs into the source code, finds references to github.com/awesome-org/tool/config, github.com/awesome-org/tool/driver etc, and fetches those from http://github.com/awsome-org/tool and onto $GOPATH/src/github.com/awesome-org/tool/, which is not awesome. You actually have two copies of the code, one from your fork, one from the origin, and your own fork will be largely ignored as it mostly points back to the origin.
A bad solution
The dirty, bad solution would be for you to go over the source code and replace "github.com/awesome-org/tool" entries with "github.com/awesome-you/tool". It is bad for two reasons:
- You will not be able to further pull changes from upstream
- You will not be able to pull-request and push your own changes upstream
When I say "You will not be able" I mean "in a reasonable, developer-friendly manner". The code will be incompatible with upstream and you have effectively detached your code. You will need to keep editing and re-editing those entries anytime you wish to pull/push upstream.
Solution #1: add remote
Described in GitHub and Go: forking, pull requests, and go-getting, follow these procedures:
go get http://github.com/awesome-org/tool git remote add awesome-you-fork http://github.com/awesome-you/tool
You're adding your repository as remote. You will from now on need to explicitly:
git pull --rebase awesome-you-fork git push awesome-you-fork
If you forget to add the "awesome-you-fork" argument, you are pulling and pushing from upstream.
Solution #2: cheat "go get", DIY
The problem began with the go get command, which copied the URI path onto $GOPATH/src. However go get implicitly issues a git clone, and we can do the same ourselves. We will dirty our hands just once, and then benefit from an ambiguous-less environment.
We will now create our git repository in the name of awesome-org but with the contents of awesome-you:
cd $GOPATH
mkdir -p {src,bin,pkg}
mkdir -p src/github.com/awesome-org/
cd src/github.com/awesome-org/
git clone [email protected]:awesome-you/tool.git # OR: git clone https://github.com/awesome-you/tool.git
cd tool/
go get ./...
The mkdir -p {src,bin,pkg} is there just in case you do not have anything setup in your $GOPATH. We then create the repository path under the name of awesome-org, but once inside clone from awesome-you.
The source code's import path fits your directory layout now, but as you push/pull you are only speaking to your own awesome-you repository.