summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--.travis.yml12
-rw-r--r--reference.go38
-rw-r--r--reference_test.go27
-rw-r--r--repository.go67
-rwxr-xr-xscript/build-libgit2.sh17
5 files changed, 151 insertions, 10 deletions
diff --git a/.travis.yml b/.travis.yml
new file mode 100644
index 0000000..86f8265
--- /dev/null
+++ b/.travis.yml
@@ -0,0 +1,12 @@
+language: go
+
+go:
+ - 1.0
+ - 1.1
+ - tip
+
+env:
+ - PKG_CONFIG_PATH=libgit2/install/lib/pkgconfig LD_LIBRARY_PATH=libgit2/install/lib
+
+install:
+ - script/build-libgit2.sh
diff --git a/reference.go b/reference.go
index 45a3b22..d246c55 100644
--- a/reference.go
+++ b/reference.go
@@ -40,8 +40,13 @@ func (v *Reference) SetSymbolicTarget(target string, sig *Signature, msg string)
csig := sig.toC()
defer C.free(unsafe.Pointer(csig))
- cmsg := C.CString(msg)
- defer C.free(unsafe.Pointer(cmsg))
+ var cmsg *C.char
+ if msg == "" {
+ cmsg = nil
+ } else {
+ cmsg = C.CString(msg)
+ defer C.free(unsafe.Pointer(cmsg))
+ }
ret := C.git_reference_symbolic_set_target(&ptr, v.ptr, ctarget, csig, cmsg)
if ret < 0 {
@@ -60,8 +65,13 @@ func (v *Reference) SetTarget(target *Oid, sig *Signature, msg string) (*Referen
csig := sig.toC()
defer C.free(unsafe.Pointer(csig))
- cmsg := C.CString(msg)
- defer C.free(unsafe.Pointer(cmsg))
+ var cmsg *C.char
+ if msg == "" {
+ cmsg = nil
+ } else {
+ cmsg = C.CString(msg)
+ defer C.free(unsafe.Pointer(cmsg))
+ }
ret := C.git_reference_set_target(&ptr, v.ptr, target.toC(), csig, cmsg)
if ret < 0 {
@@ -93,8 +103,13 @@ func (v *Reference) Rename(name string, force bool, sig *Signature, msg string)
csig := sig.toC()
defer C.free(unsafe.Pointer(csig))
- cmsg := C.CString(msg)
- defer C.free(unsafe.Pointer(cmsg))
+ var cmsg *C.char
+ if msg == "" {
+ cmsg = nil
+ } else {
+ cmsg = C.CString(msg)
+ defer C.free(unsafe.Pointer(cmsg))
+ }
runtime.LockOSThread()
defer runtime.UnlockOSThread()
@@ -134,6 +149,17 @@ func (v *Reference) Delete() error {
return nil
}
+// Cmp compares both references, retursn 0 on equality, otherwise a
+// stable sorting.
+func (v *Reference) Cmp(ref2 *Reference) int {
+ return int(C.git_reference_cmp(v.ptr, ref2.ptr))
+}
+
+// Shorthand returns a "human-readable" short reference name
+func (v *Reference) Shorthand() string {
+ return C.GoString(C.git_reference_shorthand(v.ptr))
+}
+
func (v *Reference) Name() string {
return C.GoString(C.git_reference_name(v.ptr))
}
diff --git a/reference_test.go b/reference_test.go
index 156960a..ffa9f35 100644
--- a/reference_test.go
+++ b/reference_test.go
@@ -159,6 +159,33 @@ func TestIterator(t *testing.T) {
compareStringList(t, expected, list)
}
+func TestUtil(t *testing.T) {
+ repo := createTestRepo(t)
+ defer os.RemoveAll(repo.Workdir())
+
+ commitId, _ := seedTestRepo(t, repo)
+
+ ref, err := repo.CreateReference("refs/heads/foo", commitId, true, nil, "")
+ checkFatal(t, err)
+
+ ref2, err := repo.DwimReference("foo")
+ checkFatal(t, err)
+
+ if ref.Cmp(ref2) != 0 {
+ t.Fatalf("foo didn't dwim to the right thing")
+ }
+
+ if ref.Shorthand() != "foo" {
+ t.Fatalf("refs/heads/foo has no foo shorthand")
+ }
+
+ hasLog, err := repo.HasLog("refs/heads/foo")
+ checkFatal(t, err)
+ if !hasLog {
+ t.Fatalf("branches ahve logs by default")
+ }
+}
+
func compareStringList(t *testing.T, expected, actual []string) {
for i, v := range expected {
if actual[i] != v {
diff --git a/repository.go b/repository.go
index e78422e..6b7345d 100644
--- a/repository.go
+++ b/repository.go
@@ -153,8 +153,13 @@ func (v *Repository) CreateReference(name string, id *Oid, force bool, sig *Sign
csig := sig.toC()
defer C.free(unsafe.Pointer(csig))
- cmsg := C.CString(msg)
- defer C.free(unsafe.Pointer(cmsg))
+ var cmsg *C.char
+ if msg == "" {
+ cmsg = nil
+ } else {
+ cmsg = C.CString(msg)
+ defer C.free(unsafe.Pointer(cmsg))
+ }
var ptr *C.git_reference
@@ -179,8 +184,13 @@ func (v *Repository) CreateSymbolicReference(name, target string, force bool, si
csig := sig.toC()
defer C.free(unsafe.Pointer(csig))
- cmsg := C.CString(msg)
- defer C.free(unsafe.Pointer(cmsg))
+ var cmsg *C.char
+ if msg == "" {
+ cmsg = nil
+ } else {
+ cmsg = C.CString(msg)
+ defer C.free(unsafe.Pointer(cmsg))
+ }
var ptr *C.git_reference
@@ -332,3 +342,52 @@ func (v *Repository) RevparseSingle(spec string) (Object, error) {
return allocObject(ptr), nil
}
+
+// EnsureLog ensures that there is a reflog for the given reference
+// name and creates an empty one if necessary.
+func (v *Repository) EnsureLog(name string) error {
+ cname := C.CString(name)
+ defer C.free(unsafe.Pointer(cname))
+
+ runtime.LockOSThread()
+ defer runtime.UnlockOSThread()
+
+ if ret := C.git_reference_ensure_log(v.ptr, cname); ret < 0 {
+ return MakeGitError(ret)
+ }
+
+ return nil
+}
+
+// HasLog returns whether there is a reflog for the given reference
+// name
+func (v *Repository) HasLog(name string) (bool, error) {
+ cname := C.CString(name)
+ defer C.free(unsafe.Pointer(cname))
+
+ runtime.LockOSThread()
+ defer runtime.UnlockOSThread()
+
+ ret := C.git_reference_has_log(v.ptr, cname)
+ if ret < 0 {
+ return false, MakeGitError(ret)
+ }
+
+ return ret == 1, nil
+}
+
+// DwimReference looks up a reference by DWIMing its short name
+func (v *Repository) DwimReference(name string) (*Reference, error) {
+ cname := C.CString(name)
+ defer C.free(unsafe.Pointer(cname))
+
+ runtime.LockOSThread()
+ defer runtime.UnlockOSThread()
+
+ var ptr *C.git_reference
+ if ret := C.git_reference_dwim(&ptr, v.ptr, cname); ret < 0 {
+ return nil, MakeGitError(ret)
+ }
+
+ return newReferenceFromC(ptr), nil
+}
diff --git a/script/build-libgit2.sh b/script/build-libgit2.sh
new file mode 100755
index 0000000..aa43df5
--- /dev/null
+++ b/script/build-libgit2.sh
@@ -0,0 +1,17 @@
+#!/bin/sh
+
+set -ex
+
+git clone --depth 1 --single-branch git://github.com/libgit2/libgit2 libgit2
+
+cd libgit2
+cmake -DTHREADSAFE=ON \
+ -DBUILD_CLAR=OFF \
+ -DCMAKE_INSTALL_PREFIX=$PWD/install \
+ .
+
+make install
+
+# Let the Go build system know where to find libgit2
+export LD_LIBRARY_PATH="$TMPDIR/libgit2/install/lib"
+export PKG_CONFIG_PATH="$TMPDIR/libgit2/install/lib/pkgconfig"