Couchbase client in Go

Overview

A smart client for couchbase in go

This is a unoffical version of a Couchbase Golang client. If you are looking for the Offical Couchbase Golang client please see [CB-go])[https://github.com/couchbaselabs/gocb].

This is an evolving package, but does provide a useful interface to a couchbase server including all of the pool/bucket discovery features, compatible key distribution with other clients, and vbucket motion awareness so application can continue to operate during rebalances.

It also supports view querying with source node randomization so you don't bang on all one node to do all the work.

Install

go get github.com/couchbase/go-couchbase

Example

c, err := couchbase.Connect("http://dev-couchbase.example.com:8091/")
if err != nil {
	log.Fatalf("Error connecting:  %v", err)
}

pool, err := c.GetPool("default")
if err != nil {
	log.Fatalf("Error getting pool:  %v", err)
}

bucket, err := pool.GetBucket("default")
if err != nil {
	log.Fatalf("Error getting bucket:  %v", err)
}

bucket.Set("someKey", 0, []string{"an", "example", "list"})
Issues
  • Does not work with Docker

    Does not work with Docker

    I'm running my Couchbase server in Docker with port mapping to my local machine for development. This works fine for the .NET SDK, however, when using this Go SDK, the SDK tries to talk to the Docker IP.

    2016/09/26 09:03:27 dial tcp 172.17.0.2:11210: connectex: A connection attempt failed because the connected party did not properly respond after a period of time, or established connection failed because connected host has failed to respond.
    exit status 1
    

    The 172.17.0.2 is the internal IP for the container, and is not accessible from the outside. Do note that this is not the IP I provided when trying to connect to the server: I provided http://localhost:8091,

    Does this mean that we cannot use Couchbase hosted in Docker for development environments?

    opened by rogeralsing 12
  • fatal error: all goroutines are asleep - deadlock!

    fatal error: all goroutines are asleep - deadlock!

    Hello,

    I would like to report an error encountered recently after update with golang v1.9.1 . The following error frequently happens when it calls. Not always, but sometime happens. Can anybody please look into this and hopefully fix this soon?

    Thank you!

    fatal error: all goroutines are asleep - deadlock!

    goroutine 1 [select]: net/http.(*persistConn).roundTrip(0xc042092fc0, 0xc04206aae0, 0x0, 0x0, 0x0) C:/Go/src/net/http/transport.go:1970 +0x60f net/http.(*Transport).RoundTrip(0x8008a0, 0xc0420fa000, 0x8008a0, 0x0, 0x0) C:/Go/src/net/http/transport.go:413 +0x999 net/http.send(0xc0420fa000, 0x7ceca0, 0x8008a0, 0x0, 0x0, 0x0, 0xc042076048, 0x4 1034d, 0xc042073390, 0x1) C:/Go/src/net/http/client.go:249 +0x1b0 net/http.(*Client).send(0x7fc020, 0xc0420fa000, 0x0, 0x0, 0x0, 0xc042076048, 0x0 , 0x1, 0x12200ffffffff) C:/Go/src/net/http/client.go:173 +0x104 net/http.(*Client).Do(0x7fc020, 0xc0420fa000, 0x0, 0xc0420735c8, 0x4437de) C:/Go/src/net/http/client.go:602 +0x294 github.com/couchbase/go-couchbase.doHTTPRequest(0xc0420fa000, 0x0, 0x0, 0x0) C:/goproject/src/github.com/couchbase/go-couchbase/pools.go:534 +0x9f github.com/couchbase/go-couchbase.queryRestAPI(0xc042080100, 0x6a6c3a, 0x6, 0x0, 0x0, 0x638a40, 0xc0420ec1f8, 0x0, 0x0) C:/goproject/src/github.com/couchbase/go-couchbase/pools.go:632 +0x26a github.com/couchbase/go-couchbase.(*Client).parseURLResponse(0xc0420ec1e0, 0x6a6 c3a, 0x6, 0x638a40, 0xc0420ec1f8, 0x0, 0x410801) C:/goproject/src/github.com/couchbase/go-couchbase/pools.go:652 +0x6f github.com/couchbase/go-couchbase.ConnectWithAuth(0xc042074030, 0x24, 0x0, 0x0, 0x346010, 0x0, 0x0, 0x805280, 0x3406a8, 0x0, ...) C:/goproject/src/github.com/couchbase/go-couchbase/pools.go:773 +0xdf github.com/couchbase/go-couchbase.Connect(0xc042074030, 0x24, 0x0, 0x0, 0x0, 0x0 , 0x0, 0x0, 0x0, 0x0, ...) C:/goproject/src/github.com/couchbase/go-couchbase/pools.go:792 +0xcd main.(repoCouchbase3).open(0xc042073cc8, 0xc042074030, 0x24, 0xc0420560c0, 0x7, 0xc0420d8660, 0x20) C:/goproject/src/****:298 +0xd9 main.bucketsImpl(0xc042074030, 0x24, 0xc0420560c0, 0x7, 0xc0420521f0, 0x1, 0x1, 0x0, 0x0) C:/goproject/src/*:245 +0xcf laszlo/tree.Main(0x6bab10, 0x6bab20, 0x6baaf8, 0x6bab00, 0x6bab30, 0x6baae8, 0x6 87000) C:/goproject/src/*:194 +0x13c9 main.main() C:/goproject/src/*****:32 +0x222

    goroutine 22 [IO wait]: internal/poll.runtime_pollWait(0xb24f70, 0x72, 0x0) C:/Go/src/runtime/netpoll.go:173 +0x5e internal/poll.(*pollDesc).wait(0xc042094c98, 0x72, 0x7cd200, 0x0, 0x0) C:/Go/src/internal/poll/fd_poll_runtime.go:85 +0xb5 internal/poll.(*ioSrv).ExecIO(0x802d78, 0xc042094b58, 0x6baa30, 0x0, 0x0, 0x0) C:/Go/src/internal/poll/fd_windows.go:195 +0x13a internal/poll.(*FD).Read(0xc042094b40, 0xc04210a000, 0x1000, 0x1000, 0x0, 0x0, 0 x0) C:/Go/src/internal/poll/fd_windows.go:439 +0x266 net.(*netFD).Read(0xc042094b40, 0xc04210a000, 0x1000, 0x1000, 0x345430, 0x0, 0x0 ) C:/Go/src/net/fd_windows.go:151 +0x59 net.(*conn).Read(0xc042076058, 0xc04210a000, 0x1000, 0x1000, 0x0, 0x0, 0x0) C:/Go/src/net/net.go:176 +0x74 net/http.(*persistConn).Read(0xc042092fc0, 0xc04210a000, 0x1000, 0x1000, 0x20, 0 x677300, 0xc042105b68) C:/Go/src/net/http/transport.go:1391 +0x147 bufio.(*Reader).fill(0xc0420ec600) C:/Go/src/bufio/bufio.go:97 +0x121 bufio.(*Reader).Peek(0xc0420ec600, 0x1, 0xc042016060, 0xc042105c80, 0x805280, 0x 3406a8, 0x0) C:/Go/src/bufio/bufio.go:129 +0x41 net/http.(*persistConn).readLoop(0xc042092fc0) C:/Go/src/net/http/transport.go:1539 +0x18c created by net/http.(*Transport).dialConn C:/Go/src/net/http/transport.go:1186 +0xa35

    goroutine 23 [select]: net/http.(*persistConn).writeLoop(0xc042092fc0) C:/Go/src/net/http/transport.go:1759 +0x16c created by net/http.(*Transport).dialConn C:/Go/src/net/http/transport.go:1187 +0xa5a

    opened by taekwonv 10
  • cannot get or set values to a 'Memcached' type bucket

    cannot get or set values to a 'Memcached' type bucket

    Using the following stub code below against a cluster with a 'Memcached' type bucket called 'memcached_bucket' I get the following error everytime I try to read or write a value:

    ahurt1:local ahurt$ go build cb-test.go; ./cb-test
    2015/03/16 17:08:05 Error setting key: go-couchbase: vbmap smaller than vbucket list: 6536 vs. []
    

    Thank you in advance!

    package main
    
    import (
        "bytes"
        "github.com/couchbase/go-couchbase"
        "log"
    )
    
    const (
        CB_HOST   = "http://some-host:8091/"
        CB_BUCKET = "memcached_bucket"
    )
    
    func main() {
        c, err := couchbase.Connect(CB_HOST)
        if err != nil {
            log.Fatalf("Error connecting:  %v", err)
        }
    
        pool, err := c.GetPool("default")
        if err != nil {
            log.Fatalf("Error getting pool:  %v", err)
        }
    
        bucket, err := pool.GetBucket(CB_BUCKET)
        if err != nil {
            log.Fatalf("Error getting bucket:  %v", err)
        }
    
        buff := bytes.NewBufferString("someValue")
    
        err = bucket.SetRaw("someKey", 0, buff.Bytes())
        if err != nil {
            log.Fatalf("Error setting key: %v", err)
        }
    }
    
    opened by leprechau 7
  • Support for creating/deleting buckets

    Support for creating/deleting buckets

    Would you be interested in adding support for creating / deleting buckets? If so, does the API change in the attached patch look reasonable? If yes, I'd be happy to clean up the implementation as needed, add docs, tests, etc.

    This functionality would be useful for writing integration tests.

    opened by felixge 5
  • Auth issue when connecting to default bucket via cbdatasource

    Auth issue when connecting to default bucket via cbdatasource

    I'm connecting to a default bucket via CBGT, which uses the go-couchbase cbdatasource connection library.

    The problem appears to be in this method:

    func maybeAddAuth(req *http.Request, ah AuthHandler) error {
        if hah, ok := ah.(HTTPAuthHandler); ok {
            return hah.SetCredsForRequest(req)
        }
        if ah != nil {
            user, pass, _ := ah.GetCredentials()
            req.Header.Set("Authorization", "Basic "+
                base64.StdEncoding.EncodeToString([]byte(user+":"+pass)))
        }
        return nil
    }
    

    Even though user and pass are both empty, it tries to add the Basic Authorization header, which ends up failing to connect with 401 errors.

    A workaround that appears to work is:

    func maybeAddAuth(req *http.Request, ah AuthHandler) error {
        if hah, ok := ah.(HTTPAuthHandler); ok {
            return hah.SetCredsForRequest(req)
        }
        if ah != nil {
            user, pass, _ := ah.GetCredentials()
            if user != "" {
                req.Header.Set("Authorization", "Basic "+
                    base64.StdEncoding.EncodeToString([]byte(user+":"+pass)))
            }
        }
        return nil
    }
    

    This works around the issue by only adding the Basic Auth header if the user is non-empty.

    I'm not sure why it has a non-nil AuthHandler if the username and password are both empty. That might be a bug somewhere up in the callstack of the code that calls this method. Even so, checking for a non-empty user seems like good defensive coding, since it doesn't seem like a valid use case to set a Basic Auth header with an empty user.

    opened by tleyden 4
  • Modified go get README because new URL doesn't work

    Modified go get README because new URL doesn't work

    I've got that weird error when I use github.com/couchbase/go-couchbase as couchbase package:

    github.com/couchbase/go-couchbase/conn_pool.go:56: conn.SetKeepAliveOptions undefined (type *memcached.Client has no field or method SetKeepAliveOptions)
    

    I am using now github.com/couchbaselabs/go-couchbase in all my projects and it works better.

    Let me now what you think

    opened by tehmoon 4
  • Adding new interface AuthWithSaslHandler

    Adding new interface AuthWithSaslHandler

    It is required to pass the auth for memcached with http auth. So added a new interface couchbase.AuthWithSaslHandler.

    Change-Id: Id8541e0a1b8559c5c141e595bb629e4f66e964c5

    opened by nimishzynga 3
  • avoid nil being json marshaled

    avoid nil being json marshaled

    Since nil is JSON marshaled to null, b.Set(key, exp, nil) will store a blank value (not even a { }) for the key, which is both a bit confusing and different from func Write's comments

    • A nil value causes a delete
    • If Raw is not given, v will be marshaled as JSON before being written. It must be JSON-marshalable and it must not be nil.

    The change I made was first

    if opt&Raw == 0 && v != nil {
        data, err = json.Marshal(v)
        if err != nil {
            return err
        }
    } else if v != nil {
        data = v.([]byte)
    }
    

    then I refactor it to current way.

    opened by codingsince1985 3
  • implemented more flexible auth support

    implemented more flexible auth support

    Specifically it's now possible to have different kind of auth on per bucket basis. As well as perform special auth exchange on freshly established memcached connections.

    This is going to be used by cbauth integration.

    opened by alk 3
  • # github.com/couchbaselabs/go-couchbase ../../src/github.com/couchbaselabs/go-couchbase/upr.go:150: too many arguments in call to singleFeed.uprFeed.UprRequestStream

    # github.com/couchbaselabs/go-couchbase ../../src/github.com/couchbaselabs/go-couchbase/upr.go:150: too many arguments in call to singleFeed.uprFeed.UprRequestStream

    After commit cf12df69ce. I am unable to build.

    github.com/couchbaselabs/go-couchbase ../../src/github.com/couchbaselabs/go-couchbase/upr.go:150: too many arguments in call to singleFeed.uprFeed.UprRequestStream

    opened by keithballdotnet 3
  • Fixing issues with gomemcached dependency

    Fixing issues with gomemcached dependency

    Appears that the go.mod entry for the github.com/couchbase/gomemcached package is invalid.

    This simply fixes the reference.

    Note: it's good practice to include the go.sum file.

    opened by kenshaw 2
  • Misleading license info

    Misleading license info

    I'd like to bring up an issue and ask if this is intentional or a mistake.

    The "go-couchbase" repo says it's MIT licensed. However this looks quite misleading because at various places code from goutils is used. The license of that repo [1] is clearly a proprietary license and not anything alike a MIT license.

    This essentially means every package including go-couchbase will inadvertently include non-free code. This came up in a discussion at Gentoo due to the Gitea package including that code [2]. I also reported this to Gitea [3].

    Please either consider relicensing goutils or make at least clear that go-couchbase is not just "MIT-licensed", but also includes proprietary code.

    [1] https://github.com/couchbase/goutils/blob/master/LICENSE.md [2] https://github.com/gentoo/gentoo/pull/12597 [3] https://github.com/go-gitea/gitea/issues/8575

    opened by hannob 0
  • possible race condition in connection pool

    possible race condition in connection pool

    see conn_pool.go see connectionPool see connectionPool --> connCount see func (cp *connectionPool) connCloser()

    You are using connCloser() as a go routine. Inside connCloser there is the assignment connCount = cp.connCount

    Please consider using connCount = atomic.LoadUint64(&cp.connCount) instead, as the current solution might lead to race conditions.

    I am not using/invested in couchbase, so please forgive the bad report style.

    opened by burner-account 0
  • Can't get clusterName

    Can't get clusterName

    The default Pool data structure can not match the Couchbase RESTful API pool/default. Pool struct can not only cover 3 fields while the API(Version: EE6.0.0) has more.

    // A Pool of nodes and buckets.
    type Pool struct {
    	BucketMap map[string]*Bucket
    	Nodes     []Node
    
    	BucketURL map[string]string `json:"buckets"`
    
    	client Client
    }
    

    I think ClusterName is an important field for cluster overview, and the structure can match the API better if the other fields in the API have been added.

    opened by MarsBighead 0
  • bad strings.Replace call arguments

    bad strings.Replace call arguments

    https://github.com/couchbase/go-couchbase/pull/87

    - strings.Replace(buf.String(), "`", "` + \"`\" + `", 0))
    + strings.Replace(buf.String(), "`", "` + \"`\" + `", -1))
    

    Reporting an issue, but it's not convenient for me to send a gerrit CL. You can see a fix in a referenced PR.

    opened by quasilyte 0
  • perf/perf.go:101:10: assignment mismatch: 2 variables but 3 values

    perf/perf.go:101:10: assignment mismatch: 2 variables but 3 values

    perf does not build with Go 1.10 x86_64

    cd /builddir/build/BUILD/go-couchbase-a064ca416844fb169255a76fbdac7e80101b6049/_build/src/github.com/couchbase/go-couchbase/perf
    /usr/lib/golang/pkg/tool/linux_amd64/compile -o $WORK/b001/_pkg_.a -trimpath $WORK/b001 -shared -p main -complete -installsuffix shared -bui
    ldid xg8dqXZtFmAoDE_d3Yjw/xg8dqXZtFmAoDE_d3Yjw -goversion go1.10 -D "" -importcfg $WORK/b001/importcfg -pack ./generate-json.go ./perf.go
    # github.com/couchbase/go-couchbase/perf
    perf/perf.go:101:10: assignment mismatch: 2 variables but 3 values
    perf/perf.go:101:22: not enough arguments in call to b.GetBulk
            have ([]string)
            want ([]string, time.Time, []string)
    error: Bad exit status from /var/tmp/rpm-tmp.tCh9vC (%build)
    
    opened by nim-nim 0
Releases(v20.08)
Aerospike Client Go

Aerospike Go Client An Aerospike library for Go. This library is compatible with Go 1.9+ and supports the following operating systems: Linux, Mac OS X

Aerospike 394 Aug 1, 2022
Go client library for Pilosa

Go Client for Pilosa Go client for Pilosa high performance distributed index. What's New? See: CHANGELOG Requirements Go 1.12 and higher. Install Down

Pilosa 53 Jun 9, 2022
Golang client for redislabs' ReJSON module with support for multilple redis clients (redigo, go-redis)

Go-ReJSON - a golang client for ReJSON (a JSON data type for Redis) Go-ReJSON is a Go client for ReJSON Redis Module. ReJSON is a Redis module that im

Nitish Malhotra 274 Aug 5, 2022
redis client implement by golang, inspired by jedis.

godis redis client implement by golang, refers to jedis. this library implements most of redis command, include normal redis command, cluster command,

piaohao 105 Jul 20, 2022
Go Memcached client library #golang

About This is a memcache client library for the Go programming language (http://golang.org/). Installing Using go get $ go get github.com/bradfitz/gom

Brad Fitzpatrick 1.5k Aug 5, 2022
Neo4j Rest API Client for Go lang

neo4j.go Implementation of client package for communication with Neo4j Rest API. For more information and documentation please read Godoc Neo4j Page s

Cihangir 27 Jan 26, 2022
Neo4j REST Client in golang

DEPRECATED! Consider these instead: https://github.com/johnnadratowski/golang-neo4j-bolt-driver https://github.com/go-cq/cq Install: If you don't ha

null 76 Mar 14, 2022
Neo4j client for Golang

neoism - Neo4j client for Go Package neoism is a Go client library providing access to the Neo4j graph database via its REST API. Status System Status

Jason McVetta 388 Aug 2, 2022
Go client for Redis

Redigo Redigo is a Go client for the Redis database. Features A Print-like API with support for all Redis commands. Pipelining, including pipelined tr

null 9.2k Aug 9, 2022
Type-safe Redis client for Golang

Redis client for Golang ❤️ Uptrace.dev - distributed traces, logs, and errors in one place Join Discord to ask questions. Documentation Reference Exam

null 15k Aug 2, 2022
Go Redis Client

xredis Built on top of github.com/garyburd/redigo with the idea to simplify creating a Redis client, provide type safe calls and encapsulate the low l

Raed Shomali 18 Jan 23, 2022
godis - an old Redis client for Go

godis Implements a few database clients for Redis. There is a stable client and an experimental client, redis and exp, respectively. To use any of the

Simon Zimmermann 86 Apr 16, 2022
Google Go Client and Connectors for Redis

Go-Redis Go Clients and Connectors for Redis. The initial release provides the interface and implementation supporting the (~) full set of current Red

Joubin Houshyar 440 Jul 9, 2022
Redis client library for Go

go-redis go-redis is a Redis client library for the Go programming language. It's built on the skeleton of gomemcache. It is safe to use by multiple g

Alexandre Fiori 45 Jul 15, 2020
Type-safe Redis client for Golang

Redis client for Golang ❤️ Uptrace.dev - distributed traces, logs, and errors in one place Join Discord to ask questions. Documentation Reference Exam

null 15.1k Aug 11, 2022
Redis client Mock Provide mock test for redis query

Redis client Mock Provide mock test for redis query, Compatible with github.com/go-redis/redis/v8 Install Confirm that you are using redis.Client the

null 129 Aug 2, 2022
GoBigdis is a persistent database that implements the Redis server protocol. Any Redis client can interface with it and start to use it right away.

GoBigdis GoBigdis is a persistent database that implements the Redis server protocol. Any Redis client can interface with it and start to use it right

Riccardo 5 Apr 27, 2022
HDFS for Go - This is a native golang client for hdfs.

HDFS for Go This is a native golang client for hdfs. It connects directly to the namenode using the protocol buffers API. It tries to be idiomatic by

Colin Marc 1.2k Aug 4, 2022
PostgreSQL API Client

PostgreSQL API language search PostgreSQL API functions response: We don't use PostgreSQL in the usual way. We do everything through API functions, wh

Derek Sivers 14 May 9, 2022