diff options
Diffstat (limited to '_examples')
-rw-r--r-- | _examples/README.md | 2 | ||||
-rw-r--r-- | _examples/common_test.go | 26 | ||||
-rw-r--r-- | _examples/context/main.go | 46 | ||||
-rw-r--r-- | _examples/pull/main.go | 36 | ||||
-rw-r--r-- | _examples/storage/README.md | 2 |
5 files changed, 110 insertions, 2 deletions
diff --git a/_examples/README.md b/_examples/README.md index 2e7d514..10594ab 100644 --- a/_examples/README.md +++ b/_examples/README.md @@ -6,12 +6,14 @@ Here you can find a list of annotated _go-git_ examples: - [showcase](showcase/main.go) - A small showcase of the capabilities of _go-git_ - [open](open/main.go) - Opening a existing repository cloned by _git_ - [clone](clone/main.go) - Cloning a repository +- [clone with context](context/main.go) - Cloning a repository with graceful cancellation. - [log](log/main.go) - Emulate `git log` command output iterating all the commit history from HEAD reference - [remotes](remotes/main.go) - Working with remotes: adding, removing, etc - [progress](progress/main.go) - Printing the progress information from the sideband - [push](push/main.go) - Push repository to default remote (origin) - [checkout](checkout/main.go) - check out a specific commit from a repository - [tag](tag/main.go) - list/print repository tags +- [pull](pull/main.go) - pull changes from a remote repository ### Advanced - [custom_http](custom_http/main.go) - Replacing the HTTP client using a custom one - [storage](storage/README.md) - Implementing a custom storage system diff --git a/_examples/common_test.go b/_examples/common_test.go index 86205fe..9eeb643 100644 --- a/_examples/common_test.go +++ b/_examples/common_test.go @@ -17,6 +17,7 @@ var defaultURL = "https://github.com/git-fixtures/basic.git" var args = map[string][]string{ "checkout": []string{defaultURL, tempFolder(), "35e85108805c84807bc66a02d91535e1e24b38b9"}, "clone": []string{defaultURL, tempFolder()}, + "context": []string{defaultURL, tempFolder()}, "commit": []string{cloneRepository(defaultURL, tempFolder())}, "custom_http": []string{defaultURL}, "open": []string{cloneRepository(defaultURL, tempFolder())}, @@ -24,6 +25,7 @@ var args = map[string][]string{ "push": []string{setEmptyRemote(cloneRepository(defaultURL, tempFolder()))}, "showcase": []string{defaultURL, tempFolder()}, "tag": []string{cloneRepository(defaultURL, tempFolder())}, + "pull": []string{createRepositoryWithRemote(tempFolder(), defaultURL)}, } var ignored = map[string]bool{} @@ -88,13 +90,28 @@ func cloneRepository(url, folder string) string { } func createBareRepository(dir string) string { - cmd := exec.Command("git", "init", "--bare", dir) + return createRepository(dir, true) +} + +func createRepository(dir string, isBare bool) string { + var cmd *exec.Cmd + if isBare { + cmd = exec.Command("git", "init", "--bare", dir) + } else { + cmd = exec.Command("git", "init", dir) + } err := cmd.Run() CheckIfError(err) return dir } +func createRepositoryWithRemote(local, remote string) string { + createRepository(local, false) + addRemote(local, remote) + return local +} + func setEmptyRemote(dir string) string { remote := createBareRepository(tempFolder()) setRemote(dir, remote) @@ -108,6 +125,13 @@ func setRemote(local, remote string) { CheckIfError(err) } +func addRemote(local, remote string) { + cmd := exec.Command("git", "remote", "add", "origin", remote) + cmd.Dir = local + err := cmd.Run() + CheckIfError(err) +} + func testExample(t *testing.T, name, example string) { cmd := exec.Command("go", append([]string{ "run", filepath.Join(example), diff --git a/_examples/context/main.go b/_examples/context/main.go new file mode 100644 index 0000000..72885ff --- /dev/null +++ b/_examples/context/main.go @@ -0,0 +1,46 @@ +package main + +import ( + "context" + "os" + "os/signal" + + "gopkg.in/src-d/go-git.v4" + . "gopkg.in/src-d/go-git.v4/_examples" +) + +// Gracefull cancellation example of a basic git operation such as Clone. +func main() { + CheckArgs("<url>", "<directory>") + url := os.Args[1] + directory := os.Args[2] + + // Clone the given repository to the given directory + Info("git clone %s %s", url, directory) + + stop := make(chan os.Signal, 1) + signal.Notify(stop, os.Interrupt) + + // The context is the mechanism used by go-git, to support deadlines and + // cancellation signals. + ctx, cancel := context.WithCancel(context.Background()) + defer cancel() // cancel when we are finished consuming integers + + go func() { + <-stop + Warning("\nSignal detected, canceling operation...") + cancel() + }() + + Warning("To gracefully stop the clone operation, push Crtl-C.") + + // Using PlainCloneContext we can provide to a context, if the context + // is cancelled, the clone operation stops gracefully. + _, err := git.PlainCloneContext(ctx, directory, false, &git.CloneOptions{ + URL: url, + Progress: os.Stdout, + }) + + // If the context was cancelled, an error is returned. + CheckIfError(err) +} diff --git a/_examples/pull/main.go b/_examples/pull/main.go new file mode 100644 index 0000000..ae751d2 --- /dev/null +++ b/_examples/pull/main.go @@ -0,0 +1,36 @@ +package main + +import ( + "fmt" + "os" + + "gopkg.in/src-d/go-git.v4" + . "gopkg.in/src-d/go-git.v4/_examples" +) + +// Pull changes from a remote repository +func main() { + CheckArgs("<path>") + path := os.Args[1] + + // We instance a new repository targeting the given path (the .git folder) + r, err := git.PlainOpen(path) + CheckIfError(err) + + // Get the working directory for the repository + w, err := r.Worktree() + CheckIfError(err) + + // Pull the latest changes from the origin remote and merge into the current branch + Info("git pull origin") + err = w.Pull(&git.PullOptions{RemoteName: "origin"}) + CheckIfError(err) + + // Print the latest commit that was just pulled + ref, err := r.Head() + CheckIfError(err) + commit, err := r.CommitObject(ref.Hash()) + CheckIfError(err) + + fmt.Println(commit) +} diff --git a/_examples/storage/README.md b/_examples/storage/README.md index b7207ee..fc72e6f 100644 --- a/_examples/storage/README.md +++ b/_examples/storage/README.md @@ -8,7 +8,7 @@ ### and what this means ... *git* has as very well defined storage system, the `.git` directory, present on any repository. This is the place where `git` stores al the [`objects`](https://git-scm.com/book/en/v2/Git-Internals-Git-Objects), [`references`](https://git-scm.com/book/es/v2/Git-Internals-Git-References) and [`configuration`](https://git-scm.com/docs/git-config#_configuration_file). This information is stored in plain files. -Our original **go-git** version was designed to work in memory, some time after we added support to read the `.git`, and now we have added support for fully customized [storages](https://godoc.org/github.com/src-d/go-git#Storer). +Our original **go-git** version was designed to work in memory, some time after we added support to read the `.git`, and now we have added support for fully customized [storages](https://godoc.org/gopkg.in/src-d/go-git.v4/storage#Storer). This means that the internal database of any repository can be saved and accessed on any support, databases, distributed filesystems, etc. This functionality is pretty similar to the [libgit2 backends](http://blog.deveo.com/your-git-repository-in-a-database-pluggable-backends-in-libgit2/) |