summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorCarlos Martín Nieto <[email protected]>2016-04-21 16:34:51 +0200
committerCarlos Martín Nieto <[email protected]>2016-04-23 15:35:22 +0200
commit9163ca7d5072114975bed794226dd90d37d856b4 (patch)
treec71496b0bb41b83f45520129c1e1543b1f260677
parent652a14f732bb3b96fc77baf53f78d74175ac2e0a (diff)
Update to 1dc4491
-rw-r--r--blob.go74
-rw-r--r--remote.go55
-rw-r--r--remote_test.go8
m---------vendor/libgit20
-rw-r--r--wrapper.c28
5 files changed, 126 insertions, 39 deletions
diff --git a/blob.go b/blob.go
index 1a86e60..2daebe9 100644
--- a/blob.go
+++ b/blob.go
@@ -4,15 +4,13 @@ package git
#include <git2.h>
#include <string.h>
-extern int _go_git_blob_create_fromchunks(git_oid *id,
- git_repository *repo,
- const char *hintpath,
- void *payload);
-
+int _go_git_writestream_write(git_writestream *stream, const char *buffer, size_t len);
+void _go_git_writestream_free(git_writestream *stream);
*/
import "C"
import (
"io"
+ "reflect"
"runtime"
"unsafe"
)
@@ -78,27 +76,71 @@ func blobChunkCb(buffer *C.char, maxLen C.size_t, handle unsafe.Pointer) int {
return len(goBuf)
}
-func (repo *Repository) CreateBlobFromChunks(hintPath string, callback BlobChunkCallback) (*Oid, error) {
- runtime.LockOSThread()
- defer runtime.UnlockOSThread()
-
+func (repo *Repository) CreateFromStream(hintPath string) (*BlobWriteStream, error) {
var chintPath *C.char = nil
+ var stream *C.git_writestream
+
if len(hintPath) > 0 {
chintPath = C.CString(hintPath)
defer C.free(unsafe.Pointer(chintPath))
}
- oid := C.git_oid{}
- payload := &BlobCallbackData{Callback: callback}
- handle := pointerHandles.Track(payload)
- defer pointerHandles.Untrack(handle)
+ runtime.LockOSThread()
+ defer runtime.UnlockOSThread()
+
+ ecode := C.git_blob_create_fromstream(&stream, repo.ptr, chintPath)
+ if ecode < 0 {
+ return nil, MakeGitError(ecode)
+ }
+
+ return newBlobWriteStreamFromC(stream), nil
+}
+
+type BlobWriteStream struct {
+ ptr *C.git_writestream
+}
+
+func newBlobWriteStreamFromC(ptr *C.git_writestream) *BlobWriteStream {
+ stream := &BlobWriteStream{
+ ptr: ptr,
+ }
+
+ runtime.SetFinalizer(stream, (*BlobWriteStream).Free)
+ return stream
+}
+
+// Implement io.Writer
+func (stream *BlobWriteStream) Write(p []byte) (int, error) {
+ header := (*reflect.SliceHeader)(unsafe.Pointer(&p))
+ ptr := (*C.char)(unsafe.Pointer(header.Data))
+ size := C.size_t(header.Len)
- ecode := C._go_git_blob_create_fromchunks(&oid, repo.ptr, chintPath, handle)
- if payload.Error != nil {
- return nil, payload.Error
+ runtime.LockOSThread()
+ defer runtime.UnlockOSThread()
+
+ ecode := C._go_git_writestream_write(stream.ptr, ptr, size)
+ if ecode < 0 {
+ return 0, MakeGitError(ecode)
}
+
+ return len(p), nil
+}
+
+func (stream *BlobWriteStream) Free() {
+ runtime.SetFinalizer(stream, nil)
+ C._go_git_writestream_free(stream.ptr)
+}
+
+func (stream *BlobWriteStream) Commit() (*Oid, error) {
+ oid := C.git_oid{}
+
+ runtime.LockOSThread()
+ defer runtime.UnlockOSThread()
+
+ ecode := C.git_blob_create_fromstream_commit(&oid, stream.ptr)
if ecode < 0 {
return nil, MakeGitError(ecode)
}
+
return newOidFromC(&oid), nil
}
diff --git a/remote.go b/remote.go
index 8a57280..bacdfa3 100644
--- a/remote.go
+++ b/remote.go
@@ -117,6 +117,30 @@ type FetchOptions struct {
Headers []string
}
+type ProxyType uint
+
+const (
+ // Do not attempt to connect through a proxy
+ //
+ // If built against lbicurl, it itself may attempt to connect
+ // to a proxy if the environment variables specify it.
+ ProxyTypeNone ProxyType = C.GIT_PROXY_NONE
+
+ // Try to auto-detect the proxy from the git configuration.
+ ProxyTypeAuto ProxyType = C.GIT_PROXY_AUTO
+
+ // Connect via the URL given in the options
+ ProxyTypeSpecified ProxyType = C.GIT_PROXY_SPECIFIED
+)
+
+type ProxyOptions struct {
+ // The type of proxy to use (or none)
+ Type ProxyType
+
+ // The proxy's URL
+ Url string
+}
+
type Remote struct {
ptr *C.git_remote
callbacks RemoteCallbacks
@@ -320,6 +344,20 @@ func pushUpdateReferenceCallback(refname, status *C.char, data unsafe.Pointer) i
return int(callbacks.PushUpdateReferenceCallback(C.GoString(refname), C.GoString(status)))
}
+func populateProxyOptions(ptr *C.git_proxy_options, opts *ProxyOptions) {
+ C.git_proxy_init_options(ptr, C.GIT_PROXY_OPTIONS_VERSION)
+ if opts == nil {
+ return
+ }
+
+ ptr._type = C.git_proxy_t(opts.Type)
+ ptr.url = C.CString(opts.Url)
+}
+
+func freeProxyOptions(ptr *C.git_proxy_options) {
+ C.free(unsafe.Pointer(ptr.url))
+}
+
func RemoteIsValidName(name string) bool {
cname := C.CString(name)
defer C.free(unsafe.Pointer(cname))
@@ -654,12 +692,12 @@ func (o *Remote) Fetch(refspecs []string, opts *FetchOptions, msg string) error
return nil
}
-func (o *Remote) ConnectFetch(callbacks *RemoteCallbacks, headers []string) error {
- return o.Connect(ConnectDirectionFetch, callbacks, headers)
+func (o *Remote) ConnectFetch(callbacks *RemoteCallbacks, proxyOpts *ProxyOptions, headers []string) error {
+ return o.Connect(ConnectDirectionFetch, callbacks, proxyOpts, headers)
}
-func (o *Remote) ConnectPush(callbacks *RemoteCallbacks, headers []string) error {
- return o.Connect(ConnectDirectionPush, callbacks, headers)
+func (o *Remote) ConnectPush(callbacks *RemoteCallbacks, proxyOpts *ProxyOptions, headers []string) error {
+ return o.Connect(ConnectDirectionPush, callbacks, proxyOpts, headers)
}
// Connect opens a connection to a remote.
@@ -669,19 +707,24 @@ func (o *Remote) ConnectPush(callbacks *RemoteCallbacks, headers []string) error
// starts up a specific binary which can only do the one or the other.
//
// 'headers' are extra HTTP headers to use in this connection.
-func (o *Remote) Connect(direction ConnectDirection, callbacks *RemoteCallbacks, headers []string) error {
+func (o *Remote) Connect(direction ConnectDirection, callbacks *RemoteCallbacks, proxyOpts *ProxyOptions, headers []string) error {
var ccallbacks C.git_remote_callbacks
populateRemoteCallbacks(&ccallbacks, callbacks)
+ var cproxy C.git_proxy_options
+ populateProxyOptions(&cproxy, proxyOpts)
+ defer freeProxyOptions(&cproxy)
+
cheaders := C.git_strarray{}
cheaders.count = C.size_t(len(headers))
cheaders.strings = makeCStringsFromStrings(headers)
defer freeStrarray(&cheaders)
+
runtime.LockOSThread()
defer runtime.UnlockOSThread()
- if ret := C.git_remote_connect(o.ptr, C.git_direction(direction), &ccallbacks, &cheaders); ret != 0 {
+ if ret := C.git_remote_connect(o.ptr, C.git_direction(direction), &ccallbacks, &cproxy, &cheaders); ret != 0 {
return MakeGitError(ret)
}
return nil
diff --git a/remote_test.go b/remote_test.go
index 978b803..539b4b1 100644
--- a/remote_test.go
+++ b/remote_test.go
@@ -58,7 +58,7 @@ func TestRemoteConnect(t *testing.T) {
remote, err := repo.Remotes.Create("origin", "https://github.com/libgit2/TestGitRepository")
checkFatal(t, err)
- err = remote.ConnectFetch(nil, nil)
+ err = remote.ConnectFetch(nil, nil, nil)
checkFatal(t, err)
}
@@ -69,7 +69,7 @@ func TestRemoteLs(t *testing.T) {
remote, err := repo.Remotes.Create("origin", "https://github.com/libgit2/TestGitRepository")
checkFatal(t, err)
- err = remote.ConnectFetch(nil, nil)
+ err = remote.ConnectFetch(nil, nil, nil)
checkFatal(t, err)
heads, err := remote.Ls()
@@ -87,7 +87,7 @@ func TestRemoteLsFiltering(t *testing.T) {
remote, err := repo.Remotes.Create("origin", "https://github.com/libgit2/TestGitRepository")
checkFatal(t, err)
- err = remote.ConnectFetch(nil, nil)
+ err = remote.ConnectFetch(nil, nil, nil)
checkFatal(t, err)
heads, err := remote.Ls("master")
@@ -166,7 +166,7 @@ func TestRemotePrune(t *testing.T) {
rr, err := repo.Remotes.Lookup("origin")
checkFatal(t, err)
- err = rr.ConnectFetch(nil, nil)
+ err = rr.ConnectFetch(nil, nil, nil)
checkFatal(t, err)
err = rr.Prune(nil)
diff --git a/vendor/libgit2 b/vendor/libgit2
-Subproject 785d8c48ea8725691da3c50e7dae8751523d4c3
+Subproject 1dc449105b329ea4f8ea9982bc2da869d231c04
diff --git a/wrapper.c b/wrapper.c
index e39665a..7407611 100644
--- a/wrapper.c
+++ b/wrapper.c
@@ -108,19 +108,6 @@ void _go_git_setup_callbacks(git_remote_callbacks *callbacks) {
callbacks->push_update_reference = (push_update_reference_cb) pushUpdateReferenceCallback;
}
-int _go_blob_chunk_cb(char *buffer, size_t maxLen, void *payload)
-{
- return blobChunkCb(buffer, maxLen, payload);
-}
-
-int _go_git_blob_create_fromchunks(git_oid *id,
- git_repository *repo,
- const char *hintpath,
- void *payload)
-{
- return git_blob_create_fromchunks(id, repo, hintpath, _go_blob_chunk_cb, payload);
-}
-
int _go_git_index_add_all(git_index *index, const git_strarray *pathspec, unsigned int flags, void *callback) {
git_index_matched_path_cb cb = callback ? (git_index_matched_path_cb) &indexMatchedPathCallback : NULL;
return git_index_add_all(index, pathspec, flags, cb, callback);
@@ -172,4 +159,19 @@ int _go_git_stash_foreach(git_repository *repo, void *payload) {
return git_stash_foreach(repo, (git_stash_cb)&stashForeachCb, payload);
}
+int _go_git_writestream_write(git_writestream *stream, const char *buffer, size_t len)
+{
+ return stream->write(stream, buffer, len);
+}
+
+int _go_git_writestream_close(git_writestream *stream)
+{
+ return stream->close(stream);
+}
+
+void _go_git_writestream_free(git_writestream *stream)
+{
+ stream->free(stream);
+}
+
/* EOF */