Couchbase C Client  2.10.3
Asynchronous C Client for Couchbase
Introduction



libcouchbase is an asynchronous library for connecting to a Couchbase server and performing data operations.

This contains the API documentation for the library. The documentation consists of both internal and public interfaces.

Using the library is comprised of these steps:

  1. Create an instance (See lcb_create())
  2. Install callbacks (See lcb_set_get_callback())
  3. Schedule an operation (e.g. lcb_get())
  4. Wait for the operation to complete (lcb_wait())

libcouchbase is an asynchronous library which means that operation results are passed to callbacks you define rather than being returned from functions.

Callbacks are passed a cookie parameter which is a user-defined pointer (i.e. your own pointer which can be NULL) to associate a specific command with a specific callback invocation.

For simple synchronous use, you will need to call lcb_wait() after each set of scheduled operations. During lcb_wait() the library will block for I/O and invoke your callbacks as the results for the operations arrive.

For non-synchronous use cases you can integrate with a variety of event loops via the various plugins, or integrate one yourself via the IOPS API (see Network I/O)

Modifying the library's settings (for example, timeout settings) may be done via the lcb_cntl() interface (see Setting List) or via some environment variables (see Environment Variables)

Using the headers and libraries

Using the libcouchbase headers is simple. Simply:

into your application.

To link, simply link against libcouchbase (e.g. -lcouchbase).

See Interface Attributes for interface stability taxonomy and Thread Safety for information on programming in threaded environments

Minimal example usage

/* -*- Mode: C; tab-width: 4; c-basic-offset: 4; indent-tabs-mode: nil -*- */
/*
* Copyright 2012-2013 Couchbase, Inc.
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
#include <stdio.h>
#include <libcouchbase/api3.h>
#include <stdlib.h>
#include <string.h> /* strlen */
#ifdef _WIN32
#define PRIx64 "I64x"
#else
#include <inttypes.h>
#endif
static void
die(lcb_t instance, const char *msg, lcb_error_t err)
{
fprintf(stderr, "%s. Received code 0x%X (%s)\n",
msg, err, lcb_strerror(instance, err));
exit(EXIT_FAILURE);
}
static void
op_callback(lcb_t instance, int cbtype, const lcb_RESPBASE *rb)
{
fprintf(stderr, "=== %s ===\n", lcb_strcbtype(cbtype));
if (rb->rc == LCB_SUCCESS) {
fprintf(stderr, "KEY: %.*s\n", (int)rb->nkey, rb->key);
fprintf(stderr, "CAS: 0x%"PRIx64"\n", rb->cas);
if (cbtype == LCB_CALLBACK_GET) {
const lcb_RESPGET *rg = (const lcb_RESPGET *)rb;
fprintf(stderr, "VALUE: %.*s\n", (int)rg->nvalue, rg->value);
fprintf(stderr, "FLAGS: 0x%x\n", rg->itmflags);
}
} else {
die(instance, lcb_strcbtype(cbtype), rb->rc);
}
}
int main(int argc, char *argv[])
{
lcb_t instance;
struct lcb_create_st create_options = { 0 };
lcb_CMDSTORE scmd = { 0 };
lcb_CMDGET gcmd = { 0 };
create_options.version = 3;
if (argc < 2) {
fprintf(stderr, "Usage: %s couchbase://host/bucket [ password [ username ] ]\n", argv[0]);
exit(EXIT_FAILURE);
}
create_options.v.v3.connstr = argv[1];
if (argc > 2) {
create_options.v.v3.passwd = argv[2];
}
if (argc > 3) {
create_options.v.v3.username = argv[3];
}
err = lcb_create(&instance, &create_options);
if (err != LCB_SUCCESS) {
die(NULL, "Couldn't create couchbase handle", err);
}
err = lcb_connect(instance);
if (err != LCB_SUCCESS) {
die(instance, "Couldn't schedule connection", err);
}
lcb_wait(instance);
err = lcb_get_bootstrap_status(instance);
if (err != LCB_SUCCESS) {
die(instance, "Couldn't bootstrap from cluster", err);
}
/* Assign the handlers to be called for the operation types */
lcb_install_callback3(instance, LCB_CALLBACK_GET, op_callback);
lcb_install_callback3(instance, LCB_CALLBACK_STORE, op_callback);
LCB_CMD_SET_KEY(&scmd, "key", strlen("key"));
LCB_CMD_SET_VALUE(&scmd, "value", strlen("value"));
err = lcb_store3(instance, NULL, &scmd);
if (err != LCB_SUCCESS) {
die(instance, "Couldn't schedule storage operation", err);
}
/* The store_callback is invoked from lcb_wait() */
fprintf(stderr, "Will wait for storage operation to complete..\n");
lcb_wait(instance);
/* Now fetch the item back */
LCB_CMD_SET_KEY(&gcmd, "key", strlen("key"));
err = lcb_get3(instance, NULL, &gcmd);
if (err != LCB_SUCCESS) {
die(instance, "Couldn't schedule retrieval operation", err);
}
/* Likewise, the get_callback is invoked from here */
fprintf(stderr, "Will wait to retrieve item..\n");
lcb_wait(instance);
/* Now that we're all done, close down the connection handle */
lcb_destroy(instance);
return 0;
}

Configuring and Tuning the library

The library may be configured either programmatically via lcb_cntl(), or via the environment (see Environment Variables)

Simple Usage Steps

  1. Create an lcb_t handle. This is done via lcb_create()
  2. Schedule the initial connection, this is done via lcb_connect()
  3. Wait for the initial connection to complete, via lcb_wait()
  4. Install the callbacks for retrieval and storage (lcb_set_get_callback(), lcb_set_stor_callback()).
  5. Set up a command structure for storing an item, i.e. lcb_store_cmd_t.
  6. Schedule the operation via lcb_store(). You will also likely want to pass a cookie parameter along with it so that you can associate your application's structures via the callback.
  7. Invoke lcb_wait(). Your callback will be invoked with the result of the storage operation.
Stability
Internal:

Public vs Internal APIs

The Public API section is where you should begin browsing to develop with the library. Any sections not contained within the public API are internal and are provided to aid in developing new features and fixing bugs within the library itself.

Internal Header Layouts

The internal headers are organized like so:

  • <lcbio/lcbio.h> - I/O Core
  • <mc/mcreq.h> - Memcached packet codecs
  • <netbuf/netbuf.h> - Write buffer implementation
  • <rdb/rope.h> - Read buffer implementation
  • <mcserver/mcserver.h> - Memcached client I/O
  • <mcserver/negotiate.h> - Memcached client initial SASL handling
  • <bucketconfig/clconfig.h> - Couchbase cluster configuration retrieval
  • <packetutils.h> - Utility for response packets
  • <src/retryq.h> - Retry queue for failed packets
  • <src/internal.h> - Other internal functions not in the above categories

In addition to these files, there are several non-core files which exist to provide simple utilities which are not specific to the library:

  • <list.h> - Double-linked list
  • <sllist.h>, <sllist-inl.h> - Single linked list
  • <genhash.h> - Hashtable
  • <hashset.h> - Set of unique elements
  • <hostlist.h> - Host/Port structures and lists

Prerequisite Knowledge

libcouchbase is a cross platform C library used to interact with Couchbase Server. It is assumed that you know about:

  • Key-Value stores
  • The C language
  • Asynchronous and non-blocking programming.

To develop with the I/O integration APIs, you will need to know about:

  • Socket APIs
  • Event loops