← Back to team overview

zorba-coders team mailing list archive

[Merge] lp:~zorba-coders/zorba/couchbase-fn-private into lp:zorba

 

Markos Zaharioudakis has proposed merging lp:~zorba-coders/zorba/couchbase-fn-private into lp:zorba.

Commit message:
fn prefix not allowed in annotations

Requested reviews:
  Markos Zaharioudakis (markos-za)

For more details, see:
https://code.launchpad.net/~zorba-coders/zorba/couchbase-fn-private/+merge/161468

fn prefix not allowed in annotations
-- 
https://code.launchpad.net/~zorba-coders/zorba/couchbase-fn-private/+merge/161468
Your team Zorba Coders is subscribed to branch lp:zorba.
=== added file 'CMakeLists.txt'
--- CMakeLists.txt	1970-01-01 00:00:00 +0000
+++ CMakeLists.txt	2013-04-29 18:32:40 +0000
@@ -0,0 +1,54 @@
+# Copyright 2012 The FLWOR Foundation.
+# 
+# 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.
+
+CMAKE_MINIMUM_REQUIRED(VERSION 2.6)
+
+PROJECT (zorba_couchbase_module)
+ENABLE_TESTING ()
+INCLUDE (CTest)
+
+IF (WIN32)
+  # On Windows we use proxy modules that try to guess first the location
+  # of the required third party libraries. This will search in order in:
+  # 1. the path pointed by ZORBA_THIRD_PARTY_REQUIREMENTS
+  # 2. the Program Files directory available on the users computer
+  # 3. the PATH environment variable
+  # The logic is implemented by the macros in the ProxyFindModule.cmake module.
+  LIST (APPEND CMAKE_MODULE_PATH "${PROJECT_SOURCE_DIR}/cmake_modules/Windows")
+ENDIF (WIN32)
+LIST (APPEND CMAKE_MODULE_PATH "${PROJECT_SOURCE_DIR}/cmake_modules")
+
+FIND_PACKAGE (Zorba REQUIRED HINTS "${ZORBA_BUILD_DIR}")
+MESSAGE(STATUS "Zorba_USE_FILE ${Zorba_USE_FILE}")
+INCLUDE ("${Zorba_USE_FILE}")
+
+IF (ZORBA_SUPPRESS_LIBCOUCHBASE)
+  MESSAGE (STATUS "ZORBA_SUPRESS_COUCHBASE is true - not searching for LibCouchbase.")
+ELSE (ZORBA_SUPRESS_LIBCOUCHBASE)
+  
+  MESSAGE (STATUS "Looking for LibCouchbase")
+  FIND_PACKAGE ("LibCouchbase")
+
+  IF (LIBCOUCHBASE_FOUND)
+    MESSAGE (STATUS "Found LibCouchbase --" ${LIBCOUCHBASE_LIBRARIES})
+    INCLUDE_DIRECTORIES (${LIBCOUCHBASE_INCLUDE_DIR})  
+
+    ADD_SUBDIRECTORY("src")
+    ADD_TEST_DIRECTORY("${PROJECT_SOURCE_DIR}/test")
+  ELSE (LIBCOUCHBASE_FOUND)
+    MESSAGE (STATUS "LibCouchbase library not found; couchbase module skipped")
+  ENDIF (LIBCOUCHBASE_FOUND)
+ENDIF (ZORBA_SUPPRESS_LIBCOUCHBASE)
+
+DONE_DECLARING_ZORBA_URIS()

=== renamed file 'CMakeLists.txt' => 'CMakeLists.txt.moved'
=== added directory 'cmake_modules'
=== renamed directory 'cmake_modules' => 'cmake_modules.moved'
=== added file 'cmake_modules/FindLibCouchbase.cmake'
--- cmake_modules/FindLibCouchbase.cmake	1970-01-01 00:00:00 +0000
+++ cmake_modules/FindLibCouchbase.cmake	2013-04-29 18:32:40 +0000
@@ -0,0 +1,47 @@
+# Copyright 2012 The FLWOR Foundation.
+# 
+# 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.
+
+IF (LIBCOUCHBASE_INCLUDE_DIR)
+  SET (LIBCOUCHBASE_FIND_QUIETLY TRUE)
+ENDIF (LIBCOUCHBASE_INCLUDE_DIR)
+
+FIND_PATH (
+  LIBCOUCHBASE_INCLUDE_DIR
+  libcouchbase/couchbase.h
+  PATHS /opt/local/include)
+MARK_AS_ADVANCED (LIBCOUCHBASE_INCLUDE_DIR)
+
+FIND_LIBRARY (
+  LIBCOUCHBASE_LIBRARY
+  NAMES couchbase
+  PATHS /opt/local/lib)
+MARK_AS_ADVANCED (LIBCOUCHBASE_LIBRARY)
+
+IF (LIBCOUCHBASE_INCLUDE_DIR AND LIBCOUCHBASE_LIBRARY)
+  SET (LIBCOUCHBASE_FOUND 1)
+  SET (LIBCOUCHBASE_LIBRARIES ${LIBCOUCHBASE_LIBRARY})
+  SET (LIBCOUCHBASE_INCLUDE_DIRS ${LIBCOUCHBASE_INCLUDE_DIR})
+  IF (NOT LIBCOUCHBASE_FIND_QUIETLY)
+    MESSAGE (STATUS "Found libcouchbase library: " ${LIBCOUCHBASE_LIBRARY})
+    MESSAGE (STATUS "Found libcouchbase include path : " ${LIBCOUCHBASE_INCLUDE_DIR})
+  ENDIF (NOT LIBCOUCHBASE_FIND_QUIETLY)
+
+  SET(CMAKE_REQUIRED_INCLUDES "${LIBCOUCHBASE_INCLUDE_DIR}")
+  SET(CMAKE_REQUIRED_LIBRARIES "${LIBCOUCHBASE_LIBRARY}")
+
+ELSE (LIBCOUCHBASE_INCLUDE_DIR AND LIBCOUCHBASE_LIBRARY)
+  SET (LIBCOUCHBASE_FOUND 0)
+  SET (LIBCOUCHBASE_LIBRARIES)
+  SET (LIBCOUCHBASE_INCLUDE_DIRS)
+ENDIF (LIBCOUCHBASE_INCLUDE_DIR AND LIBCOUCHBASE_LIBRARY)  

=== added directory 'cmake_modules/Windows'
=== added file 'cmake_modules/Windows/findLibCouchbase.cmake'
--- cmake_modules/Windows/findLibCouchbase.cmake	1970-01-01 00:00:00 +0000
+++ cmake_modules/Windows/findLibCouchbase.cmake	2013-04-29 18:32:40 +0000
@@ -0,0 +1,21 @@
+# Copyright 2012 The FLWOR Foundation.
+# 
+# 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.
+
+FIND_PACKAGE_WIN32 (NAME LibCouchbase FOUND_VAR LIBCOUCHBASE_FOUND SEARCH_NAMES libcouchbase)
+
+IF (LIBCOUCHBASE_FOUND)
+  FIND_PACKAGE_DLLS_WIN32 (${FOUND_LOCATION} libcouchbase.dll)
+  SET(CMAKE_REQUIRED_INCLUDES "${LIBCOUCHBASE_INCLUDE_DIR}")
+  SET(CMAKE_REQUIRED_LIBRARIES "${LIBCOUCHBASE_LIBRARY}")
+ENDIF (LIBCOUCHBASE_FOUND)  

=== added directory 'examples'
=== added file 'examples/example-put-data.xq'
--- examples/example-put-data.xq	1970-01-01 00:00:00 +0000
+++ examples/example-put-data.xq	2013-04-29 18:32:40 +0000
@@ -0,0 +1,12 @@
+import module namespace cb = "http://www.zorba-xquery.com/modules/couchbase";;
+import module namespace http = "http://www.zorba-xquery.com/modules/http-client";;
+
+variable $instance := cb:connect({
+  "host": "localhost:8091",
+  "username" : null,
+  "password" : null,
+  "bucket" : "default"});
+
+variable $json-zip := jn:parse-json(http:get-text("http://media.mongodb.org/zips.json";)[2]);
+for $result in $json-zip
+  return cb:put-text($instance, $result("_id"), fn:serialize($result), {"expiration-time" : 60*60*24});

=== added file 'examples/example.xq'
--- examples/example.xq	1970-01-01 00:00:00 +0000
+++ examples/example.xq	2013-04-29 18:32:40 +0000
@@ -0,0 +1,19 @@
+import module namespace cb = "http://www.zorba-xquery.com/modules/couchbase";;
+import module namespace http = "http://www.zorba-xquery.com/modules/http-client";;
+
+variable $instance := cb:connect({
+  "host": "localhost:8091",
+  "username" : null,
+  "password" : null,
+  "bucket" : "default"});
+variable $view-name := cb:create-view($instance, "zip", "zip", {"key" : "doc.state", "values" : "doc.pop"});
+variable $data := cb:view($instance, $view-name, {"stale" : "false"});
+for $d in jn:members($data("rows"))
+let $state := $d("key")
+group by $state
+where $d("value") > 0
+let $population := sum($d("value"))
+order by $population
+where $population > 10000000
+return { "state" : $state, "total population" : $population }
+

=== added file 'examples/example2.xq'
--- examples/example2.xq	1970-01-01 00:00:00 +0000
+++ examples/example2.xq	2013-04-29 18:32:40 +0000
@@ -0,0 +1,19 @@
+import module namespace cb = "http://www.zorba-xquery.com/modules/couchbase";;
+import module namespace http = "http://www.zorba-xquery.com/modules/http-client";;
+
+variable $instance := cb:connect({
+  "host": "localhost:8091",
+  "username" : null,
+  "password" : null,
+  "bucket" : "default"});
+
+variable $view-name := cb:create-view($instance, "zip", "zip", {"key" : "doc.state", "values" : "doc.pop"});
+variable $data := cb:view($instance, $view-name);
+for $d in jn:members($data("rows"))
+let $state := $d("key")
+group by $state
+let $zip := $d("id")
+let $number-zip := count($zip)
+order by $number-zip descending
+return { "state" : $state, "zip count" : $number-zip }
+

=== added file 'examples/example3.xq'
--- examples/example3.xq	1970-01-01 00:00:00 +0000
+++ examples/example3.xq	2013-04-29 18:32:40 +0000
@@ -0,0 +1,23 @@
+import module namespace cb = "http://www.zorba-xquery.com/modules/couchbase";;
+import module namespace http = "http://www.zorba-xquery.com/modules/http-client";;
+
+variable $instance := cb:connect({
+  "host": "localhost:8091",
+  "username" : null,
+  "password" : null,
+  "bucket" : "default"});
+
+variable $view-name := cb:create-view($instance, "zip", "zip", {"key" : "doc.state", "values" : "doc.pop"});
+variable $data := cb:view($instance, $view-name);
+for $d in jn:members($data("rows"))
+let $state := $d("key")
+group by $state
+where $d("value") > 0
+let $zip := $d("id")
+let $population := sum($d("value"))
+let $number-zip := count($zip)
+let $avarage-pop := $population div $number-zip
+order by $avarage-pop descending
+return { "state" : $state , "avarage population" : round-half-to-even($avarage-pop, 2) }
+
+

=== added file 'examples/example4.xq'
--- examples/example4.xq	1970-01-01 00:00:00 +0000
+++ examples/example4.xq	2013-04-29 18:32:40 +0000
@@ -0,0 +1,44 @@
+import module namespace cb = "http://www.zorba-xquery.com/modules/couchbase";;
+import module namespace http = "http://www.zorba-xquery.com/modules/http-client";;
+
+variable $instance := cb:connect({
+  "host": "localhost:8091",
+  "username" : null,
+  "password" : null,
+  "bucket" : "default"});
+
+variable $view-name := cb:create-view($instance, "zip", "zip", {"key" : "doc.state", "values" : ["doc.pop", "doc.city"]});
+variable $data := cb:view($instance, $view-name);
+
+
+let $city-pop :=
+  for $d in jn:members($data("rows"))
+  let $state := $d("key")
+  let $pop := $d("value")(1)
+  let $city := $d("value")(2)
+  where $pop > 0
+  group by $city, $state
+  let $total-pop := sum($pop)
+  return {"state" : $state, "city" : $city, "pop" : $total-pop} 
+let $result :=
+  for $i in $city-pop
+  let $state := $i("state")
+  let $city := $i("city")
+  let $pop := $i("pop")
+  group by $state
+  let $largest-city := max($pop)
+  let $smallest-city := min ($pop)
+  return 
+    { 
+      "state" : $state , 
+      "largest city" : 
+        for $e in $city-pop
+        where $e("pop") eq $largest-city
+        return $e("city"),
+      "smallest city" : 
+        for $e in $city-pop
+        where $e("pop") eq $smallest-city
+        return $e("city")
+    }
+return $result
+

=== added directory 'install_couchbase'
=== added file 'install_couchbase/install.cmake'
--- install_couchbase/install.cmake	1970-01-01 00:00:00 +0000
+++ install_couchbase/install.cmake	2013-04-29 18:32:40 +0000
@@ -0,0 +1,83 @@
+# Script for Downloading and configuring the Couchbase Server to
+#run with the Module tests.
+#
+# Usage: cmake [ -Dsystem=value ...]
+#          -P install.cmake
+#   Be sure all -D options come before -P !
+#   Valid options:
+#     system = system to indetify the couchbase server to download and 
+#              install, currently only ubuntu32 and ubuntu64 are valid 
+#              options.
+#
+# Example: cmake -Dsystem=ubuntu64 -P install.cmake
+
+
+# uninstalling couchbase server
+# run:
+# sudo dpkg -r couchbase-server
+# sudo --purge couchbase-server
+# sudo rm -rf /opt/couchbase/
+
+#Figure out what directory we're running in
+get_filename_component(cwd ${CMAKE_CURRENT_LIST_FILE} PATH)
+
+FIND_PROGRAM(WGET wget DOC "tool for downloading couchbase server")
+
+IF(SKIP_COUCHBASE_DOWNLOAD)
+  SET(COUCHBASE_DOWNLOAD OFF)
+ELSE(SKIP_COUCHBASE_DOWNLOAD)
+  SET(COUCHBASE_DOWNLOAD ON)
+ENDIF(SKIP_COUCHBASE_DOWNLOAD)
+
+#Couchbase Configure
+  #Check what version of couchbase server to download
+  IF(system)
+    SET(DOWNLOAD_PATH "http://packages.couchbase.com/releases/2.0.0-beta";)
+    IF (${system} STREQUAL "ubuntu32")
+      SET(COUCHBASE_DEB_NAME "couchbase-server-community_x86_2.0.0-beta.deb")
+    ELSE (${system} STREQUAL "ubuntu32")
+      IF (${system} STREQUAL "ubuntu64")
+        SET(COUCHBASE_DEB_NAME "couchbase-server-community_x86_64_2.0.0-beta.deb")
+      ELSE (${system} STREQUAL "ubuntu64")
+        MESSAGE(FATAL_ERROR "Invalid value for system (available values ubuntu32 and ubuntu64")
+      ENDIF (${system} STREQUAL "ubuntu64")
+    ENDIF (${system} STREQUAL "ubuntu32")  
+  ELSE(system)
+    MESSAGE(FATAL_ERROR "the variable 'system' must be set")
+  ENDIF(system)
+
+#Couchbase Download
+IF(COUCHBASE_DOWNLOAD)
+  IF(WGET)
+  MESSAGE(STATUS "wget found")
+  MESSAGE(STATUS "Starting Download...")
+  EXECUTE_PROCESS(COMMAND "${WGET}" "${DOWNLOAD_PATH}/${COUCHBASE_DEB_NAME}")
+  ELSE(WGET)
+  MESSAGE(FATAL_ERROR "Wget was not found, cannot download Couchbase Server")
+  ENDIF(WGET)
+ENDIF(COUCHBASE_DOWNLOAD)
+
+#Couchbase Install
+MESSAGE(STATUS "Installing Couchbase Server...")
+EXECUTE_PROCESS(COMMAND sudo dpkg -i ${COUCHBASE_DEB_NAME})
+EXECUTE_PROCESS(COMMAND sudo apt-get install -f)
+
+#Couchbase C SDK Install
+MESSAGE(STATUS "Installing Couchbase C SDK...")
+EXECUTE_PROCESS(COMMAND sudo "${WGET}" -O/etc/apt/sources.list.d/couchbase.list http://packages.couchbase.com/ubuntu/couchbase-ubuntu1110.list)
+EXECUTE_PROCESS(COMMAND "${WGET}" -O- http://packages.couchbase.com/ubuntu/couchbase.key
+  COMMAND sudo apt-key add -)
+EXECUTE_PROCESS(COMMAND apt-get update)
+EXECUTE_PROCESS(COMMAND apt-get install libcouchbase2 libcouchbase-dev)
+
+#Couchbase Setup
+MESSAGE(STATUS "Starting Setup...")
+MESSAGE(STATUS "Running node-init...")
+EXECUTE_PROCESS(COMMAND /opt/couchbase/bin/couchbase-cli node-init -c 127.0.0.1 --node-init-data-path=/opt/couchbase/var/lib/couchbase/data/ -u admin -p password)
+MESSAGE(STATUS "Running cluster-init...")
+EXECUTE_PROCESS(COMMAND /opt/couchbase/bin/couchbase-cli cluster-init -c 127.0.0.1 --cluster-init-ramsize=2048 -u admin -p password)
+MESSAGE(STATUS "Running create-bucket...")
+EXECUTE_PROCESS(COMMAND /opt/couchbase/bin/couchbase-cli bucket-create -c 127.0.0.1 --bucket=default --bucket-type=couchbase --bucket-port=11211 --bucket-ramsize=200 --bucket-replica=1 -u admin -p password)
+MESSAGE(STATUS "Couchbase Server Configure for testing, Username=admin Password=password bucket-name=default")
+EXECUTE_PROCESS(COMMAND rm ${COUCHBASE_DEB_NAME})
+

=== added directory 'src'
=== renamed directory 'src' => 'src.moved'
=== added file 'src/CMakeLists.txt'
--- src/CMakeLists.txt	1970-01-01 00:00:00 +0000
+++ src/CMakeLists.txt	2013-04-29 18:32:40 +0000
@@ -0,0 +1,22 @@
+# Copyright 2012 The FLWOR Foundation.
+# 
+# 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_DIRECTORIES("${CMAKE_CURRENT_BINARY_DIR}/couchbase.xq.src")
+  
+DECLARE_ZORBA_MODULE (
+  URI "http://www.zorba-xquery.com/modules/couchbase";
+  VERSION 1.0
+  FILE "couchbase.xq"
+  LINK_LIBRARIES "${LIBCOUCHBASE_LIBRARIES}")
+

=== added file 'src/couchbase.xq'
--- src/couchbase.xq	1970-01-01 00:00:00 +0000
+++ src/couchbase.xq	2013-04-29 18:32:40 +0000
@@ -0,0 +1,491 @@
+xquery version "3.0";
+
+(:
+ : Copyright 2012 The FLWOR Foundation.
+ :
+ : 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.
+ :)
+
+(:~
+ : This module provides minimal functionality to interact with the
+ : Couchbase NoSQL database.
+ :
+ : The module is built using the libcouchbase C client library and
+ : exposes most of its functionality in XQuery with JSONiq extensions.
+ : Beyond just allowing for basic key-value store operations (e.g.
+ : put-/get-text or put-/get-binary, this module also allows to work
+ : with Couchbase views in order to allow for complex JSON query
+ : operations.
+ :
+ : @author Juan Zacarias
+ :
+ :)
+module namespace cb = "http://www.zorba-xquery.com/modules/couchbase";;
+
+declare namespace jn = "http://jsoniq.org/functions";;
+declare namespace an = "http://www.zorba-xquery.com/annotations";;
+
+declare namespace ver = "http://www.zorba-xquery.com/options/versioning";;
+declare option ver:module-version "1.0";
+
+(:~
+ : Connect to the Couchbase server and return an opaque identifier
+ : representing the established connection.
+ :
+ : @param $host address of the couchbase server (e.g. "localhost:8091")
+ : @param $username username used for the connection
+ : @param $password password used for the connection
+ : @param $bucket name of the bucket to use (e.g. "default")
+ :
+ : @error cb:LCB0001 if the connection to the given host/bucket
+ :   could not be established.
+ :
+ : @return an identifier for the established connection.
+ :)
+
+declare %an:sequential function cb:connect(
+  $host as xs:string, 
+  $username as xs:string?, 
+  $password as xs:string?, 
+  $bucket as xs:string)
+    as xs:anyURI
+{
+  cb:connect({"host" : $host, 
+              "username" : $username,
+              "password" : $password, 
+              "bucket" : $bucket })
+};
+
+(:~
+ : Connect to the Couchbase server and return an opaque identifier
+ : representing the established connection.
+ :
+ : @param $options a JSONiq object that contains the host, bucket,
+ :   and user information.
+ :
+ : @option "host" endpoint of the Couchbase server (mandatory)
+ : @option "username" username used for the connection (optional)
+ : @option "password" password used for the connection (optional)
+ : @option "bucket" name of an existing bucket (mandatory)
+ :
+ : @error cb:LCB0001 if the connection to the given host/bucket
+ :   could not be established.
+ : @error cb:CB0001 if mandatory connection information is missing.
+ : @error cb:CB0007 if a given option is not supported.
+ :
+ : @return an identifier for the established connection.
+ :
+ : Example:
+ : <code>
+ : {
+ :   "host": "localhost:8091",
+ :   "username" : null,
+ :   "password" : null,
+ :   "bucket" : "default"
+ : }
+ : </code>
+ :)
+declare %an:sequential function cb:connect($options as object())
+    as xs:anyURI external;
+
+(:~
+ : Return the values of the given keys (type xs:string) as string.
+ : 
+ : @param $db connection reference
+ : @param $key the requested keys
+ :
+ : @error cb:LCB0002 if any error occurs in the communication with
+ :   the server.
+ :
+ : @return A sequence of string Items corresponding to the key
+ :)
+
+declare %an:sequential function cb:get-text(
+  $db as xs:anyURI,
+  $key as xs:string*)
+as xs:string* external;
+
+(:~
+ : Return the values of the given keys (type xs:string) as string.
+ : 
+ : @param $db connection reference
+ : @param $key the requested keys
+ : @param $options JSONiq object with additional options
+ :
+ : @option "expiration-time" xs:integer value for refreshing the expiration
+ :   time in seconds. 
+ : @option "encoding" string with the name of the encoding of the returned
+ :   string (if not UTF-8).
+ : 
+ : @error cb:LCB0002 if any error occurs in the communication with
+ :   the server.
+ : @error cb:CB0006 if the given encoding is not supported.
+ : @error cb:CB0007 if any of the options is not supported.
+ : @error cb:CB0009 if the given expiration time is not an xs:integer.
+ :
+ : @return a sequence of strings for the given keys.
+ :)
+
+declare %an:sequential function cb:get-text(
+  $db as xs:anyURI,
+  $key as xs:string*,
+  $options as object())
+as xs:string* external;
+
+(:~
+ : Return the values of the given keys (type xs:string) as base64Binary.
+ : 
+ : @param $db connection reference
+ : @param $key the requested keys
+ :
+ : @error cb:LCB0002 if any error occurs in the communication with
+ :   the server.
+ :
+ : @return a sequence of xs:base64Binary items for the given keys.
+ :)
+declare %an:sequential function cb:get-binary(
+  $db as xs:anyURI,
+  $key as xs:string*)
+as xs:base64Binary* external;
+
+(:~
+ : Return the values of the given keys (type xs:string) as base64Binary.
+ : 
+ : @param $db connection reference
+ : @param $key the requested keys
+ : @param $options JSONiq object with additional options
+ :
+ : @option "expiration-time" xs:integer value for refreshing the expiration
+ :   time in seconds. 
+ : 
+ : @error cb:LCB0002 if any error occurs in the communication with
+ :   the server.
+ : @error cb:CB0007 if any of the options is not supported.
+ : @error cb:CB0009 if the given expiration time is not an xs:integer.
+ :
+ : @return a sequence of xs:base64Binary items for the given keys.
+ :)
+declare %an:sequential function cb:get-binary(
+  $db as xs:anyURI,
+  $key as xs:string*,
+  $options as object())
+as xs:base64Binary* external;
+
+(:~
+ : Remove the values matching the given keys (xs:string) from the server.
+ :
+ : @param $db connection reference
+ : @param $key the keys of the values that should be removed.
+ :
+ : @error cb:LCB0002 if any error occurs in the communication with
+ :   the server.
+ : @return a empty sequence.
+ :)
+declare %an:sequential function cb:remove($db as xs:anyURI, $key as xs:string*)
+    as empty-sequence() external;
+
+(:~
+ : Store the given key-value bindings.
+ :
+ : The values are stored with the UTF-8 encoding and a default
+ : expiration time of 60 seconds.
+ :
+ : @param $db connection reference
+ : @param $key the keys to store
+ : @param $value the values (as xs:string) to be stored.
+ :
+ : @error cb:LCB0002 if any error occurs in the communication with
+ :   the server.
+ : @error cb:CB0005 if the number of keys doesn't match the number
+ :   of values.
+ : @return a empty sequence.
+ :)  
+declare %an:sequential function cb:put-text(
+  $db as xs:anyURI,
+  $key as xs:string*,
+  $value as xs:string*)
+as empty-sequence()
+{
+  cb:put-text($db, $key, $value, { "expiration-time" : 60, "encoding" : "UTF-8" })
+};
+
+(:~
+ : Store the given key-value bindings.
+ :
+ : @param $db connection reference
+ : @param $key the keys to store
+ : @param $value the values (as xs:string) to be stored.
+ : @param $options JSONiq object with additional options
+ :
+ : @option "expiration-time" integer value that represent the 
+ :         expiration time in seconds.
+ : @option "operation" type of operation, possible values are 
+ :         "add", "replace", "set", "append" and "prepend".
+ : @option "encoding" the encoding that should be used for the
+ :         value (default is UTF-8).
+ : @option "wait" variable for setting if a wait for persistancy in 
+ :         the storing key is needed, possible values are "persist" 
+ :         and "false".
+ : 
+ : @error cb:LCB0002 if any error occurs in the communication with
+ :   the server.
+ : @error cb:CB0005 if the number of keys doesn't match the number
+ :   of values.
+ : @error cb:CB0006 if the given encoding is not supported.
+ : @error cb:CB0007 if any of the options is not supported.
+ : @error cb:CB0009 if the given expiration time is not an xs:integer. 
+ : @error cb:CB0011 if the stored Variable was not stored
+ :
+ : @return a empty sequence.
+ :)  
+declare %an:sequential function cb:put-text(
+            $db as xs:anyURI,
+            $key as xs:string*,
+            $value as xs:string*,
+            $options as object())
+    as empty-sequence() external;
+
+(:~
+ : Store the given key-value bindings.
+ :
+ : @param $db connection reference
+ : @param $key the keys to store
+ : @param $value the values (as xs:base64binary) to be stored.
+ :
+ : @error cb:LCB0002 if any error occurs in the communication with
+ :   the server.
+ : @error cb:CB0005 if the number of keys doesn't match the number
+ :   of values.
+ :
+ : @return a empty sequence.
+ :)  
+declare %an:sequential function cb:put-binary(
+  $db as xs:anyURI,
+  $key as xs:string*,
+  $value as xs:base64Binary*)
+as empty-sequence() 
+{
+  cb:put-binary($db, $key, $value, { "expiration-time" : 60 })
+};
+
+(:~
+ : Store the given key-value bindings.
+ :
+ : @param $db connection reference
+ : @param $key the keys to store
+ : @param $value the values (as xs:base64binary) to be stored.
+ : @param $options JSONiq object with additional options
+
+ : @option "expiration-time" integer value that represent the 
+ :         expiration time in seconds.
+ : @option "operation" type of operation, possible values are 
+ :         "add", "replace", "set", "append" and "prepend".
+ : @option "wait" variable for setting if a wait for persistancy in 
+ :         the storing key is needed, possible values are "persist" 
+ :         and "false".
+ :
+ : @error cb:LCB0002 if any error occurs in the communication with
+ :   the server.
+ : @error cb:CB0005 if the number of keys doesn't match the number
+ :   of values.
+ : @error cb:CB0007 if any of the options is not supported.
+ : @error cb:CB0009 if the given expiration time is not an xs:integer.
+ : @error cb:CB0011 if the stored Variable was not stored
+ :
+ : @return a empty sequence.
+ :)  
+declare %an:sequential function cb:put-binary(
+  $db as xs:anyURI,
+  $key as xs:string*,
+  $value as xs:base64Binary*,
+  $options as object())
+as empty-sequence() external;
+
+
+(:~
+ : Remove all key/value pairs from the cluster
+ :
+ : @param $db connection reference
+ :
+ : @error cb:LCB0002 if any error occurs in the communication with
+ :   the server.
+ :
+ : @return a empty sequence.
+ :)
+declare %an:sequential function cb:flush($db as xs:anyURI)
+as empty-sequence() external;
+
+(:~
+ : Refresh the expiration time of the given keys.
+ :
+ : @param $db connection reference
+ : @param $key the keys to touch
+ : @param $exp-time new expieration time in seconds
+ :
+ : @error cb:LCB0002 if any error occurs in the communication with
+ :   the server.
+ :
+ : @return a empty sequence.
+ :)
+declare %an:sequential function cb:touch(
+  $db as xs:anyURI,
+  $key as xs:string*,
+  $exp-time as xs:integer)
+as empty-sequence() external; 
+
+(:~
+ : Retrieve the content of existing views.
+ :
+ : @param $db connection reference
+ : @param $path contains the string of a view path 
+ :        (e.g. "_design/test/_view/vies").
+ :
+ : @error cb:LCB0002 if any error occurs in the communication with
+ :   the server.
+ :
+ : @return a sequence of strings (as JSON) containing information of the views.
+ :)
+declare %an:sequential function cb:view($db as xs:anyURI, $path as xs:string*)
+  as object()*
+{
+  jn:parse-json(cb:view-text($db, $path))
+};
+
+declare %fn:private %an:sequential function cb:view-text($db as xs:anyURI, $path as xs:string*)
+  as xs:string* external;
+
+
+(:~
+ : Retrieve the content of existing views.
+ :
+ : @param $db connection reference
+ : @param $path contains the string of a view path 
+ :        (e.g. "_design/test/_view/vies").
+ : @param $options JSONiq object with additional options
+ :
+ : @option Json object whith options for the querying the view. available options:
+ :         "encoding" string with the name of the encoding of the returned
+ :         strings (if not UTF-8).
+ :         "stale" option's value is a string with the type of stale to be used. 
+ :         Valid values:
+ :           "ok" : the view is not updated
+ :           "false" : the view is updated before the function view is executed, 
+ :            this options needs the key to be on disk before the call of the 
+ :            view function.
+ :           "update_after" : the view is updated after the call of view
+ :         "limit" option's value is an integer which sets a number of how many 
+ :         rows the view will show.  
+ :
+ : @error cb:LCB0002 if any error occurs in the communication with
+ :   the server.
+ : @error cb:CB0007 if any of the options is not supported.
+ :
+ : @return a sequence of strings (as JSON) containing information of the views.
+ :)
+declare %an:sequential function cb:view(
+  $db as xs:anyURI,
+  $path as xs:string*,
+  $options as object())
+as object()*
+{
+  jn:parse-json(cb:view-text($db, $path, $options))
+};
+
+declare %fn:private %an:sequential function cb:view-text(
+  $db as xs:anyURI,
+  $path as xs:string*,
+  $options as object())
+as xs:string* external; 
+
+
+(:~
+ : Create a document/view.
+ 
+ : If the document already exists, it is replaced. A document can hold several
+ : views that must be specified in the same call of cb:create-view. 
+ :
+ : @param $db connection reference
+ : @param $doc-name name of the document to create.
+ : @param $view-names names of the views to create in the document.
+ :
+ : @error cb:LCB0002 if any error occurs in the communication with
+ :   the server.
+ :
+ : @return the names of the paths for the views that have been
+ :   created.
+ :)
+declare %an:sequential function cb:create-view(
+  $db as xs:anyURI,
+  $doc-name as xs:string,
+  $view-names as xs:string*)
+as xs:string* external;
+
+(:~
+ : Create a document/view.
+ 
+ : If the document already exists, it is replaced. A document can hold several
+ : views that must be specified in the same call of cb:create-view. 
+ :
+ : @param $db connection reference
+ : @param $doc-name name of the document to create.
+ : @param $view-names names of the views to create in the document.
+ : @param $options options describing how to create the view.
+ :
+ : @option "key" value must be a string containing the name of the value
+ :         in the json object stored in couchbase that is wanted to be 
+ :         displayed as the value of "key" in the resulting json.
+ : @option "values" value must be a string or an array of strings containing
+ :         the name of the value in the json object stored in couchbase that 
+ :         is wanted to be displayed as the value of "value" in the resulting
+ :         json.
+ : @option "function" string with a javascript function describing the 
+ :         map function of the view. cb:create-view won't throw an error
+ :         if the javascript function is not compilable or functional. If
+ :         this option is set the "key" and "values" options are ignored.
+ :
+ : @error cb:LCB0002 if any error occurs in the communication with
+ :   the server.
+ : @error cb:CB0005 if the number of options doesn't match the number of
+ :   view-names.
+ : @error cb:CB0007 if any of the options is not supported.
+ : @error cb:CB0010 if any of the given options has an invalid type.
+ :
+ : @return the names of the paths for the views that have been
+ :   created.
+ :)
+declare %an:sequential function cb:create-view(
+  $db as xs:anyURI,
+  $doc-name as xs:string,
+  $view-names as xs:string*,
+  $options as object()*)
+as xs:string* external;
+
+
+(:~
+ : Delete a document/view.
+ 
+ : If the document doesn't exists, function does nothing. All the views hold in the
+ : Document are deleted, this function can't delete single views. 
+ :
+ : @param $db connection reference
+ : @param $doc-name name of the document to create.
+ :
+ : @error cb:LCB0002 if any error occurs in the communication with
+ :   the server.
+ :
+ : @return empty sequence.
+ :)
+declare %an:sequential function cb:delete-view(
+  $db as xs:anyURI,
+  $doc as xs:string*)
+as xs:string* external;

=== added directory 'src/couchbase.xq.src'
=== added file 'src/couchbase.xq.src/couchbase.cpp'
--- src/couchbase.xq.src/couchbase.cpp	1970-01-01 00:00:00 +0000
+++ src/couchbase.xq.src/couchbase.cpp	2013-04-29 18:32:40 +0000
@@ -0,0 +1,1474 @@
+
+/*
+ * Copyright 2012 The FLWOR Foundation.
+ * 
+ * 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 <zorba/item_factory.h>
+#include <zorba/singleton_item_sequence.h>
+#include <zorba/empty_sequence.h>
+#include <zorba/store_manager.h>
+#include <zorba/user_exception.h>
+#include <zorba/transcode_stream.h>
+#include <zorba/serializer.h>
+#include <zorba/vector_item_sequence.h>
+#include <stdio.h>
+#include <iostream>
+#include <algorithm>
+
+
+#include <zorba/util/uuid.h>
+
+
+#include <libcouchbase/couchbase.h>
+
+#include "couchbase.h"
+
+namespace zorba { namespace couchbase {
+
+/*******************************************************************************
+ ******************************************************************************/
+
+zorba::ExternalFunction*
+  CouchbaseModule::getExternalFunction(const zorba::String& localname)
+{
+  FuncMap_t::iterator lIte = theFunctions.find(localname);
+
+  ExternalFunction*& lFunc = theFunctions[localname];
+
+  if (lIte == theFunctions.end())
+  {
+    if (localname == "connect")
+    {
+      lFunc = new ConnectFunction(this);
+    }
+    else if (localname == "get-text")
+    {
+      lFunc = new GetTextFunction(this);
+    }
+    else if (localname == "get-binary")
+    {
+      lFunc = new GetBinaryFunction(this);
+    }
+    else if (localname == "put-text")
+    {
+      lFunc = new PutTextFunction(this);
+    }
+    else if (localname == "put-binary")
+    {
+      lFunc = new PutBinaryFunction(this);
+    }
+    else if (localname == "remove")
+    {
+      lFunc = new RemoveFunction(this);
+    }
+    else if (localname == "flush")
+    {
+      lFunc = new FlushFunction(this);
+    }
+    else if (localname == "touch")
+    {
+      lFunc = new TouchFunction(this);
+    }
+    else if (localname == "view-text")
+    {
+      lFunc = new ViewFunction(this);
+    }
+    else if (localname == "create-view")
+    {
+      lFunc = new CreateViewFunction(this);
+    }
+    else if (localname == "delete-view")
+    {
+      lFunc = new DeleteViewFunction(this);
+    }
+  }
+
+  return lFunc;
+}
+
+void CouchbaseModule::destroy()
+{
+  delete this;
+}
+
+CouchbaseModule::~CouchbaseModule()
+{
+  for (FuncMap_t::const_iterator lIter = theFunctions.begin();
+    lIter != theFunctions.end(); ++lIter)
+  {
+    delete lIter->second;
+  }
+  theFunctions.clear();
+
+}
+
+/*******************************************************************************
+ ******************************************************************************/
+
+CouchbaseFunction::CouchbaseFunction(const CouchbaseModule* aModule)
+  : theModule(aModule)
+{
+}
+
+CouchbaseFunction::~CouchbaseFunction()
+{
+}
+
+String
+CouchbaseFunction::getURI() const
+{
+  return theModule->getURI();
+}
+
+String
+CouchbaseFunction::getOneStringArgument(const Arguments_t& aArgs, int aPos) const
+{
+  Item lItem = getOneItemArgument(aArgs, aPos);
+  String lTmpString = lItem.getStringValue();
+  return lTmpString;
+}
+
+Item
+CouchbaseFunction::getOneItemArgument(const Arguments_t& aArgs, int aPos) const
+{
+  Item lItem;
+  Iterator_t args_iter = getIterArgument(aArgs, aPos);
+  args_iter->open();
+  args_iter->next(lItem);
+  args_iter->close();
+  return lItem;
+}
+
+Iterator_t
+CouchbaseFunction::getIterArgument(const Arguments_t& aArgs, int aPos) const
+{
+  Iterator_t args_iter = aArgs[aPos]->getIterator();
+  return args_iter;
+}
+
+void
+CouchbaseFunction::throwError(const char *aLocalName, const char* aErrorMessage)
+{
+  String errName(aLocalName);
+  Item errQName = CouchbaseModule::getItemFactory()->createQName(COUCHBASE_MODULE_NAMESPACE, errName);
+  String errDescription(aErrorMessage);
+  throw USER_EXCEPTION(errQName, errDescription);
+}
+
+void 
+CouchbaseFunction::isNotJSONError() 
+{ 
+  throwError("CB0002", "Options parameter is not a JSON object"); 
+}
+
+void
+CouchbaseFunction::libCouchbaseError(lcb_t aInstance, lcb_error_t aError) 
+{ 
+  throwError("LCB0002", lcb_strerror(aInstance, aError)); 
+} 
+
+
+lcb_t
+CouchbaseFunction::getInstance(const DynamicContext* aDctx, const String& aIdent) const
+{
+  InstanceMap* lInstanceMap;
+  lcb_t lInstance;
+  if ((lInstanceMap = dynamic_cast<InstanceMap*>(aDctx->getExternalFunctionParameter("couchbaseInstanceMap"))))
+  {
+    if ((lInstance = lInstanceMap->getInstance(aIdent)))
+      return lInstance;
+  }
+  throwError("CB0000", "No instance of couchbase with the given identifier was found.");
+  return NULL;
+}
+
+String
+  CouchbaseFunction::ViewOptions::getPathOptions()
+{
+  String lPathOptions("?");
+  bool lAmp = false;
+  if (theStaleOption != "")
+  {
+    lPathOptions.append(theStaleOption);
+    lAmp = true;
+  }
+  if (theLimitOption != "")
+  {
+    if(lAmp)
+      lPathOptions.append("&");
+    lPathOptions.append(theLimitOption);
+    lAmp = true;
+  }
+
+  if (lPathOptions == "?")
+    lPathOptions = "";
+
+  return lPathOptions;
+}
+
+void
+  CouchbaseFunction::ViewOptions::setOptions(Item& aOptions)
+{
+  if (!aOptions.isJSONItem())
+    isNotJSONError();
+
+  Iterator_t lIter = aOptions.getObjectKeys();
+  Item lItem;
+  lIter->open();
+  while (lIter->next(lItem))
+  {
+    String lStrKey = lItem.getStringValue();
+    std::transform(
+      lStrKey.begin(), lStrKey.end(),
+      lStrKey.begin(), tolower);
+    if (lStrKey == "encoding")
+    {
+      Item lValue = aOptions.getObjectValue(lStrKey);
+      theEncoding = lValue.getStringValue();
+      if (!transcode::is_supported(theEncoding.c_str()))
+      {
+        std::ostringstream lMsg;
+        lMsg << theEncoding << ": unsupported encoding";
+        throwError("CB0006", lMsg.str().c_str());
+      }
+    }
+    else if (lStrKey == "stale")
+    {
+      Item lValue = aOptions.getObjectValue(lStrKey);
+      String lString = lValue.getStringValue();
+      if (lString == "false")
+      {
+        theStaleOption ="stale=false";
+      }
+      else if (lString == "ok")
+      {
+        theStaleOption ="stale=ok";
+      }
+      else if (lString == "update_after")
+      {
+        theStaleOption ="stale=update_after";
+      }
+      else
+      {
+        std::ostringstream lMsg;
+        lMsg << lStrKey << "=" << lString << ": option not supported";
+        throwError("CB0007", lMsg.str().c_str());
+      }
+    }
+    else if (lStrKey == "limit")
+    {
+      Item lValue = aOptions.getObjectValue(lStrKey);
+      try
+      {
+        int lLimit = lValue.getIntValue();
+        theLimitOption = "limit=" + lLimit;  
+      }
+      catch (ZorbaException& e)
+      {
+        throwError("CB0009", " limit option must be an integer value");
+      } 
+    }
+    else
+    {
+      std::ostringstream lMsg;
+      lMsg << lStrKey << ": option not supported";
+      throwError("CB0007", lMsg.str().c_str());
+    }
+  }
+  lIter->close();
+}
+
+void 
+  CouchbaseFunction::GetOptions::setOptions(Item& aOptions)
+{
+  if (!aOptions.isJSONItem())
+    isNotJSONError();
+
+  Iterator_t lIter = aOptions.getObjectKeys();
+  Item lItem;
+  lIter->open();
+  while (lIter->next(lItem))
+  {
+    String lStrKey = lItem.getStringValue();
+    std::transform(
+      lStrKey.begin(), lStrKey.end(),
+      lStrKey.begin(), tolower);
+    if (lStrKey == "type")
+    {
+      Item lValue = aOptions.getObjectValue(lStrKey);
+      String lStrValue = lValue.getStringValue();
+      std::transform(
+        lStrValue.begin(), lStrValue.end(),
+        lStrValue.begin(), tolower);
+      if (lStrValue == "text")
+      {
+        theType = LCB_TEXT;
+      }
+      else if (lStrValue == "binary")
+      {
+        theType = LCB_BASE64;
+      }
+    }
+    else if (lStrKey == "expiration-time")
+    {
+      Item lValue = aOptions.getObjectValue(lStrKey);
+      try
+      {      
+        theExpTime = lValue.getUnsignedIntValue();
+      }
+      catch (ZorbaException& e)
+      {
+        throwError("CB0009", " expiration-time option must be an integer value");
+      }
+    }
+    else if (lStrKey == "encoding")
+    {
+      Item lValue = aOptions.getObjectValue(lStrKey);
+      theEncoding = lValue.getStringValue();
+      if (!transcode::is_supported(theEncoding.c_str()))
+      {
+        std::ostringstream lMsg;
+        lMsg << theEncoding << ": unsupported encoding";
+        throwError("CB0006", lMsg.str().c_str());
+      }
+    }
+    else
+    {
+      std::ostringstream lMsg;
+      lMsg << lStrKey << ": option not supported";
+      throwError("CB0007", lMsg.str().c_str());
+    }
+  }
+  lIter->close();
+
+}
+
+void 
+CouchbaseFunction::PutOptions::setOptions(Item& aOptions)
+{
+  if (!aOptions.isJSONItem())
+    isNotJSONError();
+
+  Iterator_t lIter = aOptions.getObjectKeys();
+  Item lItem;
+  lIter->open();
+  while (lIter->next(lItem))
+  {
+    String lStrKey = lItem.getStringValue();
+    std::transform(
+      lStrKey.begin(), lStrKey.end(),
+      lStrKey.begin(), tolower);
+    if (lStrKey == "operation")
+    {
+      Item lValue = aOptions.getObjectValue(lStrKey);
+      String lStrValue = lValue.getStringValue();
+      std::transform(
+        lStrValue.begin(), lStrValue.end(),
+        lStrValue.begin(), tolower);
+      if (lStrValue == "add")
+      {
+        theOperation = LCB_ADD;
+      }
+      else if (lStrValue == "replace")
+      {
+        theOperation = LCB_REPLACE;
+      }
+      else if (lStrValue == "set")
+      {
+        theOperation = LCB_SET;
+      }
+      else if (lStrValue == "append")
+      {
+        theOperation = LCB_APPEND;
+      }
+      else if (lStrValue == "prepend")
+      {
+        theOperation = LCB_PREPEND;
+      }
+    }
+    else if (lStrKey == "type")
+    {
+      Item lValue = aOptions.getObjectValue(lStrKey);
+      String lStrValue = lValue.getStringValue();
+      if (lStrValue == "text")
+      {
+        theType = LCB_TEXT;
+      }
+      else if (lStrValue == "binary")
+      {
+        theType = LCB_BASE64;
+      }
+    }
+    else if (lStrKey == "expiration-time")
+    {
+      Item lValue = aOptions.getObjectValue(lStrKey);
+
+      try
+      {      
+        theExpTime = lValue.getUnsignedIntValue();
+      }
+      catch (ZorbaException& e)
+      {
+        throwError("CB0009", " expiration-time option must be an integer value");
+      }
+    }
+    else if (lStrKey == "encoding")
+    {
+      Item lValue = aOptions.getObjectValue(lStrKey);
+      theEncoding = lValue.getStringValue();
+      if (!transcode::is_supported(theEncoding.c_str()))
+      {
+            std::ostringstream lMsg;
+            lMsg << theEncoding << ": unsupported encoding";
+            throwError("CB0006", lMsg.str().c_str());
+      }
+    }
+    else if (lStrKey == "wait")
+    {
+      Item lValue = aOptions.getObjectValue(lStrKey);
+      String lStrValue = lValue.getStringValue();
+      std::transform(
+        lStrValue.begin(), lStrValue.end(),
+        lStrValue.begin(), tolower);
+      if (lStrValue == "persist")
+      {
+        theWaitType = CB_WAIT_PERSIST;
+      }
+      else if (lStrValue == "false")
+      {
+        theWaitType = CB_WAIT_FALSE;
+      }
+      else
+      {
+        std::ostringstream lMsg;
+        lMsg << lStrKey << "=" << lStrValue << " : option not supported";
+        throwError("CB0007", lMsg.str().c_str());
+      }
+    }
+    else
+    {
+      std::ostringstream lMsg;
+      lMsg << lStrKey << ": option not supported";
+      throwError("CB0007", lMsg.str().c_str());
+    }
+  }
+  lIter->close();
+
+}
+/*******************************************************************************
+ ******************************************************************************/
+
+InstanceMap::InstanceMap()
+{   
+  InstanceMap::instanceMap = new InstanceMap_t();
+}
+
+bool
+InstanceMap::storeInstance(const String& aKeyName, lcb_t aInstance)
+{
+  std::pair<InstanceMap_t::iterator, bool> ret;
+  ret = instanceMap->insert(std::pair<String, lcb_t>(aKeyName, aInstance));
+  return ret.second;
+}
+
+lcb_t
+InstanceMap::getInstance(const String& aKeyName)
+{
+  InstanceMap::InstanceMap_t::iterator lIter = instanceMap->find(aKeyName);
+  
+  if (lIter == instanceMap->end())
+    return NULL;
+  
+  lcb_t lInstance = lIter->second;
+
+  return lInstance;
+}
+
+bool
+InstanceMap::deleteInstance(const String& aKeyName)
+{
+  InstanceMap::InstanceMap_t::iterator lIter = instanceMap->find(aKeyName);
+
+  if (lIter == instanceMap->end())
+    return false;
+
+  lcb_destroy(lIter->second);
+
+  instanceMap->erase(lIter);
+
+  return true;
+}
+
+/*******************************************************************************
+ ******************************************************************************/
+
+zorba::ItemSequence_t
+ConnectFunction::evaluate(
+  const Arguments_t& aArgs,
+  const zorba::StaticContext* aSctx,
+  const zorba::DynamicContext* aDctx) const
+{
+  DynamicContext* lDctx = const_cast<DynamicContext*>(aDctx);
+  
+  InstanceMap* lInstanceMap;
+  if (!(lInstanceMap = dynamic_cast<InstanceMap*>(lDctx->getExternalFunctionParameter("couchbaseInstanceMap"))))
+  {
+    lInstanceMap = new InstanceMap();
+    lDctx->addExternalFunctionParameter("couchbaseInstanceMap", lInstanceMap);
+  }
+
+  Item lHost;
+  Item lUserName;
+  Item lPassword;
+  Item lBucket;
+
+  Item lOptions = getOneItemArgument(aArgs, 0);
+
+  if (lOptions.isJSONItem())
+  {
+    Iterator_t lKeys = lOptions.getObjectKeys();
+    lKeys->open();
+    Item lKey;
+    while (lKeys->next(lKey))
+    {
+      String lStrKey = lKey.getStringValue();
+      if (lStrKey == "host")
+      {
+        lHost = lOptions.getObjectValue(lStrKey);
+      }
+      else if (lStrKey == "username")
+      {
+        lUserName = lOptions.getObjectValue(lStrKey);
+      }
+      else if (lStrKey == "password")
+      {
+        lPassword = lOptions.getObjectValue(lStrKey);
+      }
+      else if (lStrKey == "bucket")
+      {
+        lBucket = lOptions.getObjectValue(lStrKey);
+      }
+      else
+      {
+        std::ostringstream lMsg;
+        lMsg << lStrKey << ": option not supported";
+        throwError("CB0007", lMsg.str().c_str());
+      }
+    }
+    lKeys->close();
+  }
+  else
+  {
+    isNotJSONError();
+  }
+  
+  struct lcb_create_st create_options;
+  memset(&create_options, 0, sizeof(create_options));
+  
+  if (lHost.isNull())
+    throwError ("CB0001", "Missing declaration of the couchbase server host");
+  String lStrHost = lHost.getStringValue();
+  create_options.v.v0.host = lStrHost.c_str();
+
+  if (lBucket.isNull())
+    throwError ("CB0001", "Missing declaration of the couchbase bucket");
+  String lStrBucket = lBucket.getStringValue();
+  create_options.v.v0.bucket = lStrBucket.c_str();
+
+  if (!lUserName.isNull())
+  {
+    String lStrUserName = lUserName.getStringValue();
+    if (lStrUserName != "null")
+      create_options.v.v0.user = lStrUserName.c_str();
+  }
+
+  if (!lPassword.isNull())
+  {
+    String lStrPassword = lPassword.getStringValue();
+    if (lStrPassword != "null")
+      create_options.v.v0.passwd = lStrPassword.c_str();
+  }
+
+  lcb_t lInstance;
+  lcb_error_t lError;
+  
+  lError = lcb_create(&lInstance, &create_options);
+  if (lError != LCB_SUCCESS)
+  {
+    throwError("LCB0001", "Error creating a libcouchbase Instance");
+    lcb_strerror(NULL, lError);
+  }
+
+  //Connect to couchbase
+  if ((lError = lcb_connect(lInstance)) != LCB_SUCCESS)
+  {
+    throwError("LCB0001", "Error connecting to the couchbase server");
+    lcb_strerror(NULL, lError);
+  }
+
+  lcb_wait(lInstance);
+  
+  uuid lUUID;
+  uuid::create(&lUUID);
+  
+  std::stringstream lStream;
+  lStream << lUUID;
+
+  String lStrUUID = lStream.str();
+
+  lInstanceMap->storeInstance(lStrUUID, lInstance);
+
+  return ItemSequence_t(new SingletonItemSequence(CouchbaseModule::getItemFactory()->createAnyURI(lStrUUID)));   
+}
+
+/*******************************************************************************
+ ******************************************************************************/
+
+zorba::ItemSequence_t
+RemoveFunction::evaluate(
+  const Arguments_t& aArgs,
+  const zorba::StaticContext* aSctx,
+  const zorba::DynamicContext* aDctx) const
+{
+  String lInstanceID = getOneStringArgument(aArgs, 0);
+  lcb_t lInstance = getInstance(aDctx, lInstanceID);
+  Iterator_t lKeys = getIterArgument(aArgs, 1);
+
+
+  lcb_error_t lError;
+  Item lKey;
+  lKeys->open();
+  while (lKeys->next(lKey))
+  {
+    lcb_remove_cmd_st lCmd;
+    String lStrKey = lKey.getStringValue();
+    lCmd.v.v0.key = lStrKey.c_str();
+    lCmd.v.v0.nkey = lStrKey.size(); 
+    lcb_remove_cmd_st *lCommand[1] = {&lCmd};
+
+    lError = lcb_remove(lInstance, NULL, 1, lCommand);
+    if (lError != LCB_SUCCESS)
+    {
+      CouchbaseFunction::libCouchbaseError (lInstance, lError);
+    } 
+    
+    lcb_wait(lInstance);
+  }
+  lKeys->close();
+
+  return ItemSequence_t(new EmptySequence());  
+}
+
+/*******************************************************************************
+ ******************************************************************************/
+
+void
+CouchbaseFunction::GetItemSequence::get_callback(lcb_t instance, const void *cookie, lcb_error_t error, const lcb_get_resp_t *resp)
+{
+  if (error != LCB_SUCCESS)
+  {
+    libCouchbaseError (instance, error);
+  }
+  
+  GetOptions* lRes = (GetOptions*)cookie;
+  
+  lcb_storage_type_t lType = lRes->getGetType();
+
+  if (lType == LCB_TEXT)
+  {
+    String lEncoding = lRes->getEncoding();
+    String lTmp((const char*)resp->v.v0.bytes, resp->v.v0.nbytes);
+    if (lEncoding != "" && transcode::is_necessary(lEncoding.c_str()))
+    {    
+      transcode::stream<std::istringstream> lTranscoder(lEncoding.c_str(), lTmp.c_str());
+      lTmp.clear();
+
+      char buf[1024];
+      while (lTranscoder.good())
+      {
+        lTranscoder.read(buf, 1024);
+        lTmp.append(buf, lTranscoder.gcount());
+      }      
+    }
+    lRes->theItem = CouchbaseModule::getItemFactory()->createString(lTmp);
+  }
+  else if (lType == LCB_BASE64)
+  {
+    //unsigned char lData[resp->v.v0.nbytes];
+    //size_t lLen = resp->v.v0.nbytes;
+    //memcpy(lData, resp->v.v0.bytes, lLen);
+    lRes->theItem = CouchbaseModule::getItemFactory()->createBase64Binary((const unsigned char*)resp->v.v0.bytes, resp->v.v0.nbytes);
+  }
+  else
+  {
+    throwError ("CB0004", "The requested collection has a not recognized type");
+  }
+}
+
+void
+CouchbaseFunction::GetItemSequence::GetIterator::open()
+{
+  lcb_set_get_callback(theInstance, GetItemSequence::get_callback);
+  theKeys->open();
+}
+
+void
+CouchbaseFunction::GetItemSequence::GetIterator::close()
+{
+  theKeys->close();
+}
+
+bool
+CouchbaseFunction::GetItemSequence::GetIterator::next(Item& aItem)
+{
+  Item lKey;
+  if (theKeys->next(lKey))
+  {
+    GetOptions* lValue = &theOptions;
+    String lStrKey = lKey.getStringValue();
+    lcb_get_cmd_st lGet;
+    lGet.v.v0.key = lStrKey.c_str();
+    lGet.v.v0.nkey = lStrKey.size();
+    unsigned int lExpTime = theOptions.getExpTime();
+    if (lExpTime > 0)
+    {
+      lGet.v.v0.exptime = lExpTime;
+    }
+
+    lcb_get_cmd_st *lCommand[1] = {&lGet};
+
+    theError = lcb_get(theInstance, lValue, 1, lCommand);
+
+    if (theError != LCB_SUCCESS)
+    {
+      libCouchbaseError (theInstance, theError);
+    } 
+    lcb_wait(theInstance);
+    
+    if (lValue->theItem.isNull())
+      return false;
+
+    aItem = lValue->theItem;
+
+    return true;
+  }
+  else
+  {
+    return false;
+  }
+}
+
+/*******************************************************************************
+ ******************************************************************************/
+
+zorba::ItemSequence_t
+GetTextFunction::evaluate(
+  const Arguments_t& aArgs,
+  const zorba::StaticContext* aSctx,
+  const zorba::DynamicContext* aDctx) const
+{
+  String lInstanceID = getOneStringArgument(aArgs, 0);
+  lcb_t lInstance = getInstance(aDctx, lInstanceID);
+  Iterator_t lKeys = getIterArgument(aArgs, 1);
+  GetOptions lOptions(LCB_TEXT);
+  if (aArgs.size() > 2)
+  {
+    Item lOptionsArg = getOneItemArgument(aArgs, 2);
+    lOptions.setOptions(lOptionsArg);
+  }
+ 
+  return ItemSequence_t(new GetItemSequence(lInstance,lKeys, lOptions));   
+}
+
+/*******************************************************************************
+ ******************************************************************************/
+
+zorba::ItemSequence_t
+GetBinaryFunction::evaluate(
+  const Arguments_t& aArgs,
+  const zorba::StaticContext* aSctx,
+  const zorba::DynamicContext* aDctx) const
+{
+  String lInstanceID = getOneStringArgument(aArgs, 0);
+  lcb_t lInstance = getInstance(aDctx, lInstanceID);
+  Iterator_t lKeys = getIterArgument(aArgs, 1);
+  GetOptions lOptions(LCB_BASE64);
+  if (aArgs.size() > 2)
+  {
+    Item lOptionsArg = getOneItemArgument(aArgs, 2);
+    lOptions.setOptions(lOptionsArg);
+  }
+ 
+  return ItemSequence_t(new GetItemSequence(lInstance,lKeys, lOptions));   
+}
+
+/*******************************************************************************
+ ******************************************************************************/
+
+void CouchbaseFunction::observe_callback(lcb_t instance, const void *cookie, lcb_error_t error, const lcb_observe_resp_t *resp)
+{
+  if (error != LCB_SUCCESS)
+  {
+    libCouchbaseError (instance, error);
+  }
+  
+  PutOptions* lWait = (PutOptions*) cookie;
+  //verify is coming from the master
+  if (resp->v.v0.from_master > 0)
+  {
+    lcb_observe_t lStatus = resp->v.v0.status;if (lStatus == LCB_OBSERVE_NOT_FOUND)
+    {
+      throwError("CB0011", "Variable stored not found.");
+    }
+    //check for flag of persisntancy
+    lWait->setWaiting(lStatus & LCB_OBSERVE_PERSISTED?false:true);
+  }
+}
+
+void CouchbaseFunction::put (lcb_t aInstance, Iterator_t aKeys, Iterator_t aValues, PutOptions aOptions)
+{
+  lcb_error_t lError;
+  Item lKey;
+  Item lValue;
+
+  aKeys->open();
+  aValues->open();
+  while (aKeys->next(lKey))
+  {
+    if (!aValues->next(lValue))
+      throwError("CB0005", "The number of key/value's on the save function is not the same.");
+
+    String lStrKey = lKey.getStringValue();
+
+    //TODO: add more options
+    lcb_store_cmd_st lPut;
+    lPut.v.v0.key = lStrKey.c_str();
+    lPut.v.v0.nkey = lStrKey.size();
+    
+    const char* lData;
+    size_t lLen = 0;
+    lPut.v.v0.datatype = aOptions.getOperationType();
+    String lStrValue;
+    if (lPut.v.v0.datatype == LCB_TEXT)
+    {
+      String lEncoding = aOptions.getEncoding();
+      lStrValue = lValue.getStringValue();
+      if (lEncoding != "" && transcode::is_necessary(lEncoding.c_str()))
+      {
+        std::stringstream lStream;        
+        transcode::attach(lStream, lEncoding.c_str());
+        lStream << lStrValue.c_str();
+        lStrValue.clear();
+        lStrValue = lStream.str();
+        lData = lStrValue.c_str();
+        lLen = lStrValue.size();
+      }
+      else
+      {
+        lData = lStrValue.c_str();
+        lLen = lStrValue.size();
+      }
+    }
+    else if (lPut.v.v0.datatype == LCB_BASE64)
+    {
+      lData = lValue.getBase64BinaryValue(lLen);
+    }
+    else
+    {
+      throwError ("CB0004", " Storing type not recognized");
+    }
+
+    lPut.v.v0.bytes = lData;
+    lPut.v.v0.nbytes = lLen;
+    lPut.v.v0.operation = aOptions.getOperation();
+    unsigned int lExpTime = aOptions.getExmpTime();
+    if (lExpTime > 0)
+    {
+      lPut.v.v0.exptime = lExpTime;
+    }
+
+    lcb_store_cmd_st *lCommands[1] = {&lPut};
+    lError = lcb_store(aInstance, NULL, 1, lCommands);
+    
+    if (lError != LCB_SUCCESS)
+    {
+      libCouchbaseError (aInstance, lError);
+    } 
+    //Wait for store
+    lcb_wait(aInstance);
+    //Check if wait for disk
+    if (aOptions.getWaitType() != CB_WAIT_FALSE)
+    {     
+      lcb_set_observe_callback(aInstance, observe_callback);
+      PutOptions* lOptions = &aOptions;
+      do {
+        lcb_observe_cmd_t lObserve;
+        lObserve.version = 0;
+        lObserve.v.v0.key = lStrKey.c_str();
+        lObserve.v.v0.nkey = lStrKey.size();
+        lcb_observe_cmd_t* lCommands[1] = { &lObserve };
+        lcb_observe(aInstance, lOptions, 1, lCommands);
+        lcb_wait(aInstance);
+      }while(lOptions->isWaiting());
+    }
+  }
+
+  if (aValues->next(lValue))
+    throwError("CB0005", "The number of key/value's on the save function is not the same.");
+
+  aKeys->close();
+  aValues->close();
+
+}
+
+/*******************************************************************************
+ ******************************************************************************/
+
+zorba::ItemSequence_t
+PutTextFunction::evaluate(
+  const Arguments_t& aArgs,
+  const zorba::StaticContext* aSctx,
+  const zorba::DynamicContext* aDctx) const
+{
+  String lInstanceID = CouchbaseFunction::getOneStringArgument(aArgs, 0);
+  lcb_t lInstance = getInstance(aDctx, lInstanceID);
+  Iterator_t lKeys = getIterArgument(aArgs, 1);
+  Iterator_t lValues = getIterArgument(aArgs, 2);
+  
+  PutOptions lOptions(LCB_TEXT);
+  if (aArgs.size() > 3)
+  {
+    Item lOptionsArg = getOneItemArgument(aArgs, 3);
+    lOptions.setOptions(lOptionsArg);
+  }
+
+  put(lInstance, lKeys, lValues, lOptions);
+  return ItemSequence_t(new EmptySequence());  
+}
+
+/*******************************************************************************
+ ******************************************************************************/
+
+zorba::ItemSequence_t
+PutBinaryFunction::evaluate(
+  const Arguments_t& aArgs,
+  const zorba::StaticContext* aSctx,
+  const zorba::DynamicContext* aDctx) const
+{
+  String lInstanceID = CouchbaseFunction::getOneStringArgument(aArgs, 0);
+  lcb_t lInstance = getInstance(aDctx, lInstanceID);
+  Iterator_t lKeys = getIterArgument(aArgs, 1);
+  Iterator_t lValues = getIterArgument(aArgs, 2);
+  
+  PutOptions lOptions(LCB_BASE64);
+  if (aArgs.size() > 3)
+  {
+    Item lOptionsArg = getOneItemArgument(aArgs, 3);
+    lOptions.setOptions(lOptionsArg);
+  }
+
+  put(lInstance, lKeys, lValues, lOptions);
+  return ItemSequence_t(new EmptySequence());  
+}
+
+/*******************************************************************************
+ ******************************************************************************/
+
+zorba::ItemSequence_t
+FlushFunction::evaluate(
+  const Arguments_t& aArgs,
+  const zorba::StaticContext* aSctx,
+  const zorba::DynamicContext* aDctx) const
+{
+  String lInstanceID = CouchbaseFunction::getOneStringArgument(aArgs, 0);
+  lcb_t lInstance = getInstance(aDctx, lInstanceID);
+  lcb_error_t lError;
+
+
+  lcb_flush_cmd_st lFlush;
+  lFlush.version=0;
+  lcb_flush_cmd_st* lCommand[] = {&lFlush};
+
+  lError =  lcb_flush(lInstance, NULL, 1, lCommand);
+  if (lError != LCB_SUCCESS)
+  {
+    std::stringstream lErrorMessage;
+    lErrorMessage << "Flush error : " <<  lcb_strerror(lInstance, lError);
+    throwError("LCB0003", lErrorMessage.str().c_str());
+  } 
+    
+  lcb_wait(lInstance);
+
+  return ItemSequence_t(new EmptySequence());  
+}
+
+/*******************************************************************************
+ ******************************************************************************/
+
+zorba::ItemSequence_t
+TouchFunction::evaluate(
+  const Arguments_t& aArgs,
+  const zorba::StaticContext* aSctx,
+  const zorba::DynamicContext* aDctx) const
+{
+  String lInstanceID = getOneStringArgument(aArgs, 0);
+  lcb_t lInstance = getInstance(aDctx, lInstanceID);
+  Iterator_t lKeys = getIterArgument(aArgs, 1);
+  Item lExp = getOneItemArgument(aArgs, 2);
+  unsigned int lInt;
+  try
+  {
+    lInt = lExp.getUnsignedIntValue();
+  }
+  catch (ZorbaException& e)
+  {
+    throwError("CB0009", " expiration-time option must be an integer value");
+  }
+  lcb_error_t lError;
+  Item lKey;
+  lKeys->open();
+  while (lKeys->next(lKey))
+  {
+    lcb_touch_cmd_t lCmd;
+    String lStrKey = lKey.getStringValue();
+    lCmd.v.v0.key = lStrKey.c_str();
+    lCmd.v.v0.nkey = lStrKey.size(); 
+    lCmd.v.v0.exptime = lInt;
+    lcb_touch_cmd_t *lCommand[1] = {&lCmd};
+
+    lError = lcb_touch(lInstance, NULL, 1, lCommand);
+    if (lError != LCB_SUCCESS)
+    {
+      libCouchbaseError (lInstance, lError);
+    } 
+    
+    lcb_wait(lInstance);
+  }
+  lKeys->close();
+
+  return ItemSequence_t(new EmptySequence());  
+}
+
+/*******************************************************************************
+ ******************************************************************************/
+static void streamReleaser(std::istream* aStream)
+{
+  delete aStream;
+}
+  
+void CouchbaseFunction::ViewItemSequence::view_callback( lcb_http_request_t request, lcb_t instance, const void* cookie, lcb_error_t error, const lcb_http_resp_t* resp)
+{
+  if (error != LCB_SUCCESS)
+  {
+    libCouchbaseError (instance, error);
+  }
+
+  ViewOptions* lRes = (ViewOptions*) cookie;
+
+  String lEncoding = lRes->getEncoding();
+  if (resp->v.v0.nbytes > 0)
+  {
+    String lTmp = String((const char*)resp->v.v0.bytes, resp->v.v0.nbytes);
+
+    if (transcode::is_necessary(lEncoding.c_str()))
+    {
+      transcode::stream<std::istringstream> lTranscoder(lEncoding.c_str(), lTmp.c_str());
+      lTmp.clear();
+
+      char buf[1024];
+      while (lTranscoder.good())
+      {
+        lTranscoder.read(buf, 1024);
+        lTmp.append(buf, lTranscoder.gcount());
+      }
+    }
+    
+    if(!lRes->theStream)
+    {
+      lRes->theStream = new std::unique_ptr<std::stringstream>(new std::stringstream(""));
+    }
+
+    *(lRes->theStream->get()) << lTmp.c_str();
+    
+  }
+}
+
+void 
+CouchbaseFunction::ViewItemSequence::ViewIterator::open()
+{
+  lcb_set_http_data_callback(theInstance, ViewItemSequence::view_callback);
+  thePaths->open();
+}
+
+void
+CouchbaseFunction::ViewItemSequence::ViewIterator::close()
+{
+  thePaths->close();
+}
+
+bool
+CouchbaseFunction::ViewItemSequence::ViewIterator::next(Item& aItem)
+{
+  Item lPath;
+  if (thePaths->next(lPath))
+  {
+    ViewOptions* lOptions = &theOptions;
+    String lPathOptions = lOptions->getPathOptions();
+    String lPathString = lPath.getStringValue();    
+    if (lPathOptions != "")
+    {
+      lPathString.append(lPathOptions);
+    }    
+    lcb_http_request_t lReq;
+    lcb_http_cmd_t lCmd;
+    lCmd.version = 0;
+    lCmd.v.v0.path = lPathString.c_str();
+    lCmd.v.v0.npath = lPathString.size();
+    lCmd.v.v0.body = NULL;
+    lCmd.v.v0.nbody = 0;
+    lCmd.v.v0.method = LCB_HTTP_METHOD_GET;
+    lCmd.v.v0.chunked = 1;
+    lCmd.v.v0.content_type = "application/json";
+    lcb_error_t err = lcb_make_http_request(theInstance, lOptions, LCB_HTTP_TYPE_VIEW, &lCmd, &lReq);
+    if (err != LCB_SUCCESS)
+    {
+      libCouchbaseError (theInstance, err);
+    }
+
+    lcb_wait(theInstance);
+
+    if (lOptions->theStream)
+      aItem = CouchbaseModule::getItemFactory()->createStreamableString(*lOptions->theStream->release(), &streamReleaser);
+
+    if (aItem.isNull())
+      return false;
+
+    return true;
+  }
+  else
+  {
+    return false;
+  }
+}
+
+/*******************************************************************************
+ ******************************************************************************/
+
+zorba::ItemSequence_t
+ViewFunction::evaluate(
+  const Arguments_t& aArgs,
+  const zorba::StaticContext* aSctx,
+  const zorba::DynamicContext* aDctx) const
+{
+  String lInstanceID = getOneStringArgument(aArgs, 0);
+  lcb_t lInstance = getInstance(aDctx, lInstanceID);
+
+  Iterator_t lPaths = getIterArgument(aArgs, 1);
+  ViewOptions lOptions;
+
+  if (aArgs.size() > 2)
+  {
+    Item lOptionsArg = getOneItemArgument(aArgs, 2);
+    lOptions.setOptions(lOptionsArg);
+  }
+
+  return ItemSequence_t(new ViewItemSequence(lInstance, lPaths, lOptions));  
+}
+
+/*******************************************************************************
+ ******************************************************************************/
+void DeleteViewFunction::delete_view_callback(lcb_http_request_t request, lcb_t instance, const void* cookie, lcb_error_t error, const lcb_http_resp_t* resp)
+{
+     if (resp->v.v0.status == 401)
+    {
+      std::ostringstream lMsg;
+      lMsg << "The item requested was not available using the supplied authorization, or authorization was not supplied.";
+      throwError("CB0012", lMsg.str().c_str());
+    } else if (resp->v.v0.status == 404)
+    {
+      std::ostringstream lMsg;
+      lMsg << "The requested content could not be found. The returned content will include further information, as a JSON object, if available.";
+      throwError("CB0012", lMsg.str().c_str());
+    }
+    else if (resp->v.v0.status > 400)
+    {
+      std::ostringstream lMsg;
+      lMsg << "HTTP communication with couchbase server throwed error " << (int)resp->v.v0.status << ".";
+      throwError("CB0012", lMsg.str().c_str());
+    }     
+}
+
+zorba::ItemSequence_t
+DeleteViewFunction::evaluate(
+  const Arguments_t& aArgs,
+  const zorba::StaticContext* aSctx,
+  const zorba::DynamicContext* aDctx) const
+{
+  String lInstanceID = getOneStringArgument(aArgs, 0);
+  lcb_t lInstance = getInstance(aDctx, lInstanceID);
+
+  Iterator_t lDocNames = getIterArgument(aArgs, 1);
+  Item lDoc;  
+  lDocNames->open();
+  while(lDocNames->next(lDoc))
+  {
+    lcb_set_http_complete_callback(lInstance, DeleteViewFunction::delete_view_callback);
+    String lPath = "_design/" + lDoc.getStringValue();
+    lcb_http_request_t req;
+    lcb_http_cmd_t cmd;
+    cmd.version = 0;
+    cmd.v.v0.path = lPath.c_str();
+    cmd.v.v0.npath = lPath.size();
+    cmd.v.v0.body = NULL;
+    cmd.v.v0.nbody = 0;
+    cmd.v.v0.method = LCB_HTTP_METHOD_DELETE;
+    cmd.v.v0.chunked = 0;
+    cmd.v.v0.content_type = "application/json";
+    lcb_error_t err = lcb_make_http_request(lInstance, NULL,
+                           LCB_HTTP_TYPE_VIEW, &cmd, &req);
+
+    if (err != LCB_SUCCESS)
+      libCouchbaseError (lInstance, err);
+
+    lcb_wait(lInstance);
+  }
+  lDocNames->close();
+
+  return ItemSequence_t(new EmptySequence());  
+}
+
+/*******************************************************************************
+ ******************************************************************************/
+void CreateViewFunction::create_view_callback(lcb_http_request_t request, lcb_t instance, const void* cookie, lcb_error_t error, const lcb_http_resp_t* resp)
+{
+    if (resp->v.v0.status == 401)
+    {
+      std::ostringstream lMsg;
+      lMsg << "The item requested was not available using the supplied authorization, or authorization was not supplied.";
+      throwError("CB0012", lMsg.str().c_str());
+    } else if (resp->v.v0.status == 404)
+    {
+      std::ostringstream lMsg;
+      lMsg << "The requested content could not be found. The returned content will include further information, as a JSON object, if available.";
+      throwError("CB0012", lMsg.str().c_str());
+    }
+    else if (resp->v.v0.status > 400)
+    {
+      std::ostringstream lMsg;
+      lMsg << "HTTP communication with couchbase server throwed error " << (int)resp->v.v0.status << ".";
+      throwError("CB0012", lMsg.str().c_str());
+    }    
+}
+
+zorba::ItemSequence_t
+CreateViewFunction::evaluate(
+  const Arguments_t& aArgs,
+  const zorba::StaticContext* aSctx,
+  const zorba::DynamicContext* aDctx) const
+{
+  String lInstanceID = getOneStringArgument(aArgs, 0);
+  lcb_t lInstance = getInstance(aDctx, lInstanceID);
+
+  String lDocName = getOneStringArgument(aArgs, 1);
+  String lPath = "_design/" + lDocName;
+
+  String lBody = "{\"views\": {";
+  Iterator_t lViewNames = getIterArgument(aArgs, 2);
+  Item lView;
+
+  std::vector<Item> lResult;
+
+  Iterator_t lOptions;
+  if (aArgs.size() > 3)
+  {
+    lOptions = getIterArgument(aArgs, 3);
+    Item lOption;
+    lOptions->open();
+    lViewNames->open();
+    bool lIsFirstView = true;
+    while (lViewNames->next(lView))
+    {
+      if (!lOptions->next(lOption))
+        throwError("CB0005", "The number of options is not the same as the number of views.");
+
+      //variables used to form the body
+      String lBodyKey;
+      String lBodyValues;
+      String lBodyFunction;
+
+      String lViewName = lView.getStringValue();
+      if (lOption.isJSONItem())
+      {
+        Iterator_t lKeys = lOption.getObjectKeys();
+        lKeys->open();
+        Item lKey;
+        while (lKeys->next(lKey))
+        {
+          String lStrKey = lKey.getStringValue();
+          std::transform(
+            lStrKey.begin(), lStrKey.end(),
+            lStrKey.begin(), tolower);
+          if (lStrKey == "key")
+          {
+            Item lValue = lOption.getObjectValue(lStrKey);
+            if (lValue.isJSONItem())
+            {
+              std::ostringstream lMsg;
+              lMsg << lStrKey << ": value must be of type string.";
+              throwError("CB0010", lMsg.str().c_str());
+            }
+            String lStrValue = lValue.getStringValue();
+            std::transform(
+              lStrValue.begin(), lStrValue.end(),
+              lStrValue.begin(), tolower);
+            lBodyKey = lStrValue;
+          }
+          else if (lStrKey == "values")
+          {
+            Item lValue = lOption.getObjectValue(lStrKey);
+            if (lValue.isJSONItem())
+            { 
+              lBodyValues = "[";
+              bool lIsFirstView = true;
+              int lSize = lValue.getArraySize()+1;
+              for (int i = 1; i < lSize; i++)
+              {
+                Item lArrValue = lValue.getArrayValue(i);
+                String lStrArrValue = lArrValue.getStringValue();
+                std::transform(
+                  lStrArrValue.begin(), lStrArrValue.end(),
+                  lStrArrValue.begin(), tolower);
+
+                if (lIsFirstView)
+                  lIsFirstView = false;
+                else
+                  lBodyValues += ", ";
+
+                lBodyValues += lStrArrValue;
+              }
+              lBodyValues += "]";
+            }
+            else
+            {
+              String lStrValue = lValue.getStringValue();
+              std::transform(
+                lStrValue.begin(), lStrValue.end(),
+                lStrValue.begin(), tolower);
+              lBodyValues = lStrValue;
+            }
+          }
+          else if (lStrKey == "function")
+          {
+            Item lValue = lOption.getObjectValue(lStrKey);
+            if (lValue.isJSONItem())
+            {
+              std::ostringstream lMsg;
+              lMsg << lStrKey << ": value must be of type string.";
+              throwError("CB0010", lMsg.str().c_str());
+            }
+            String lStrValue = lValue.getStringValue();
+            std::transform(
+              lStrValue.begin(), lStrValue.end(),
+              lStrValue.begin(), tolower);
+            lBodyFunction = lStrValue;
+          }
+          else
+          {
+            std::ostringstream lMsg;
+            lMsg << lStrKey << ": option not supported";
+            throwError("CB0007", lMsg.str().c_str());
+          }
+        }
+        lKeys->close();
+      }
+      if (lIsFirstView)
+        lIsFirstView = false;
+      else
+        lBody += " , ";
+      if (lBodyFunction.size() < 1)
+      {
+        if (lBodyKey.size() < 1)
+          lBodyKey = "null";
+        if (lBodyValues.size() <1)
+          lBodyValues = "null";
+        lBodyFunction = "function(doc, meta) { emit("+lBodyKey+", "+lBodyValues+");}";
+      }
+      lBody += "\"" + lViewName + "\": {\"map\": \""+lBodyFunction+"\"}";
+
+      String lStrRes = "_design/" + lDocName + "/_view/" + lViewName;
+      Item lRes = CouchbaseModule::getItemFactory()->createString(lStrRes);
+      lResult.push_back(lRes);
+
+    }
+    if (lOptions->next(lOption))
+      throwError("CB0005", "The number of options is not the same as the number of views.");
+    lViewNames->close();
+    lOptions->close();
+    lBody += "}}";
+  }
+  else
+  {
+    bool lIsFirstView = true;
+    lViewNames->open();
+    while (lViewNames->next(lView))
+    {
+      if (lIsFirstView)
+        lIsFirstView = false;
+      else
+        lBody += " , ";
+      String lViewName = lView.getStringValue();
+      lBody += "\"" + lViewName + "\": {\"map\": \"function(doc, meta) { emit(meta.id, null);}\"}";
+
+      String lStrRes = "_design/" + lDocName + "/_view/" + lViewName;
+      Item lRes = CouchbaseModule::getItemFactory()->createString(lStrRes);
+      lResult.push_back(lRes);
+
+    }
+    lViewNames->close();
+    lBody += "}}";
+  }
+  lcb_set_http_complete_callback(lInstance, CreateViewFunction::create_view_callback);
+  lcb_http_request_t lReq;
+  lcb_http_cmd_t lCmd;
+  lCmd.v.v0.path = lPath.c_str();
+  lCmd.v.v0.npath = lPath.size();
+  lCmd.v.v0.content_type = "application/json";
+  lCmd.v.v0.method = LCB_HTTP_METHOD_PUT;
+  lCmd.v.v0.body = lBody.c_str();
+  lCmd.v.v0.nbody = lBody.size();
+  lCmd.v.v0.chunked = 0;
+  lcb_error_t err = lcb_make_http_request(lInstance, NULL, LCB_HTTP_TYPE_VIEW, &lCmd, &lReq);
+
+  if (err != LCB_SUCCESS)
+    libCouchbaseError (lInstance, err);
+
+  lcb_wait(lInstance);
+
+  return ItemSequence_t(new VectorItemSequence(lResult));  
+}
+
+
+} /*namespace couchbase*/ } /*namespace zorba*/
+
+
+#ifdef WIN32
+#  define DLL_EXPORT __declspec(dllexport)
+#else
+#  define DLL_EXPORT __attribute__ ((visibility("default")))
+#endif
+
+extern "C" DLL_EXPORT zorba::ExternalModule* createModule() {
+  return new zorba::couchbase::CouchbaseModule();
+}

=== added file 'src/couchbase.xq.src/couchbase.h'
--- src/couchbase.xq.src/couchbase.h	1970-01-01 00:00:00 +0000
+++ src/couchbase.xq.src/couchbase.h	2013-04-29 18:32:40 +0000
@@ -0,0 +1,628 @@
+/*
+ * Copyright 2012 The FLWOR Foundation.
+ * 
+ * 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.
+ */
+
+#ifndef _COM_ZORBA_WWW_MODULES_COUCHBASE_H_
+#define _COM_ZORBA_WWW_MODULES_COUCHBASE_H_
+
+#include <map>
+
+#include <zorba/zorba.h>
+#include <zorba/external_module.h>
+#include <zorba/function.h>
+#include <zorba/dynamic_context.h>
+
+#define COUCHBASE_MODULE_NAMESPACE "http://www.zorba-xquery.com/modules/couchbase";
+
+namespace zorba { namespace couchbase {
+
+/*******************************************************************************
+ ******************************************************************************/
+
+class CouchbaseModule : public ExternalModule {
+  protected:
+    class ltstr
+    {
+    public:
+      bool operator()(const String& s1, const String& s2) const
+      {
+        return s1.compare(s2) < 0;
+      }
+    };
+
+    typedef std::map<String, ExternalFunction*, ltstr> FuncMap_t;
+    FuncMap_t theFunctions;
+
+  public:
+    
+    virtual ~CouchbaseModule();
+
+    virtual String
+      getURI() const { return COUCHBASE_MODULE_NAMESPACE; }  
+
+    virtual zorba::ExternalFunction*
+      getExternalFunction(const String& localName);
+
+    virtual void destroy();
+
+    static ItemFactory*
+      getItemFactory()
+    {
+      return Zorba::getInstance(0)->getItemFactory();
+    }
+
+    static XmlDataManager*
+      getXmlDataManager()
+    {
+      return Zorba::getInstance(0)->getXmlDataManager();
+    }
+};
+
+/*******************************************************************************
+ ******************************************************************************/
+
+class CouchbaseFunction : public ContextualExternalFunction
+{
+  protected:
+
+    typedef enum
+    {
+      LCB_TEXT = 0x01,
+      LCB_JSON = 0x02,
+      LCB_XML = 0x03,
+      LCB_BASE64 = 0x04
+
+    } lcb_storage_type_t;
+
+    typedef enum
+    {
+      CB_WAIT_FALSE = 0x00,
+      CB_WAIT_PERSIST = 0x01,
+      CB_WAIT_REPLICATE = 0x02
+    } cb_wait_type_t;
+
+    class ViewOptions
+    {
+      protected:
+        String theEncoding;
+        String thePath;
+        String theStaleOption;
+        String theLimitOption;
+
+      public:
+        std::unique_ptr<std::stringstream>* theStream;
+
+        ViewOptions() : theEncoding("UTF-8"), thePath(""), theStaleOption(""), theLimitOption("") { theStream = NULL; }
+
+        ViewOptions(String& aPath) : theEncoding("UTF-8"), thePath(aPath) {}
+
+        void setOptions(Item& aOptions);
+
+        ~ViewOptions() { if(theStream) delete theStream; }
+
+        String getEncoding() { return theEncoding; }
+
+        String getPath() { return thePath; }
+
+        String getPathOptions();
+    };
+
+    class GetOptions
+    {
+      protected:
+        lcb_storage_type_t theType;
+        unsigned int theExpTime;
+        String theEncoding;
+
+      public:
+        Item theItem;
+
+        GetOptions() : theType(LCB_JSON), theExpTime(0), theEncoding("") {}
+
+        GetOptions(lcb_storage_type_t aType) : theType(aType), theExpTime(0) {} 
+
+        void setOptions(Item& aOptions);
+
+        ~GetOptions() {}
+
+        lcb_storage_type_t getGetType() { return theType; }
+
+        unsigned int getExpTime() { return theExpTime; }
+
+        String getEncoding() { return theEncoding; }
+
+    };
+
+    class PutOptions
+    {
+      protected:
+        lcb_storage_t theOperation;
+        lcb_storage_type_t theType;
+        unsigned int theExpTime;
+        String theEncoding;
+        cb_wait_type_t theWaitType;
+        bool theIsWaiting;
+
+      public:
+
+        PutOptions() : theOperation(LCB_ADD), theType(LCB_JSON), theExpTime(0), theEncoding(""), theWaitType(CB_WAIT_FALSE), theIsWaiting(false){ }
+
+        PutOptions(lcb_storage_type_t aType) : theOperation(LCB_SET), theType(aType), theExpTime(0), theWaitType(CB_WAIT_FALSE), theIsWaiting(false) { }
+
+        void setOptions(Item& aOptions);
+
+        ~PutOptions() {}
+
+        lcb_storage_t getOperation() { return theOperation; }
+
+        lcb_storage_type_t getOperationType() { return theType; }
+
+        unsigned int getExmpTime() { return theExpTime; }
+
+        String getEncoding() { return theEncoding; }
+
+        cb_wait_type_t getWaitType() { return theWaitType; }
+
+        bool isWaiting() { return theIsWaiting; }
+
+        void setWaiting(bool isWaiting) { theIsWaiting = isWaiting; }
+    };
+
+    class ViewItemSequence : public ItemSequence
+    {
+      protected:
+        lcb_t theInstance;
+        Iterator_t thePaths;
+        ViewOptions theOptions;
+
+      public:
+
+        class ViewIterator : public Iterator
+        {
+          protected:
+            lcb_t theInstance;
+            Iterator_t thePaths;
+            lcb_error_t theError;
+            ViewOptions theOptions;
+
+          public:
+            ViewIterator(lcb_t& aInstance, Iterator_t& aPaths, ViewOptions& aOptions)
+              : theInstance(aInstance),
+                thePaths(aPaths),
+                theOptions(aOptions){}
+            
+            void 
+              open();
+
+            bool
+              next(zorba::Item &aItem);
+
+            void
+              close();
+
+            bool
+              isOpen() const{ return thePaths->isOpen(); }
+
+        };
+
+        ViewItemSequence(lcb_t& aInstance, Iterator_t& aPaths, ViewOptions aOptions)
+          : theInstance(aInstance),
+            thePaths(aPaths),
+            theOptions(aOptions) {}
+
+        virtual ~ViewItemSequence() {}
+
+        zorba::Iterator_t
+          getIterator() { return new ViewIterator(theInstance, thePaths, theOptions); }
+
+      protected:
+        static void
+          view_callback( 
+            lcb_http_request_t request,
+            lcb_t instance,
+            const void *cookie,
+            lcb_error_t error,
+            const lcb_http_resp_t *resp);
+    };
+
+    class GetItemSequence : public ItemSequence
+    {
+      protected:
+        lcb_t theInstance;
+        Iterator_t theKeys;
+        GetOptions theOptions;
+    
+      public:
+
+        class GetIterator : public Iterator
+        {
+          protected:            
+            lcb_t theInstance;
+            lcb_error_t theError;
+            Iterator_t theKeys;
+            GetOptions theOptions;
+
+          public:
+            GetIterator(lcb_t& aInstance, Iterator_t& aKeys, GetOptions& aOptions) 
+              : theInstance(aInstance),
+                theKeys(aKeys),
+                theOptions(aOptions) {}
+
+            virtual ~GetIterator() {}
+
+            void
+              open();
+
+            bool 
+              next(zorba::Item &aItem);
+
+            void
+              close();
+
+            bool
+              isOpen() const { return theKeys->isOpen(); }
+        };
+
+      public:
+        GetItemSequence(lcb_t& aInstance, Iterator_t& aKeys, GetOptions aOptions) 
+          : theInstance(aInstance),
+            theKeys(aKeys),
+            theOptions(aOptions){}
+
+        virtual ~GetItemSequence(){}
+
+        zorba::Iterator_t
+          getIterator() { return new GetIterator(theInstance, theKeys, theOptions); }
+
+      protected:
+        static void 
+          get_callback(lcb_t instance, const void *cookie, lcb_error_t error, const lcb_get_resp_t *resp);
+    };
+
+    const CouchbaseModule* theModule;
+
+    String
+      getOneStringArgument(const Arguments_t&, int) const;
+    
+    Item
+      getOneItemArgument(const Arguments_t&, int) const;
+
+    Iterator_t
+      getIterArgument(const Arguments_t&, int) const;
+
+    static void
+      throwError(const char*, const char*);
+
+    static void 
+      isNotJSONError();
+
+    static void
+      libCouchbaseError(lcb_t aInstance, lcb_error_t aError);
+
+    lcb_t
+      getInstance (const DynamicContext*, const String& aIdent) const;
+
+    static void
+      put (lcb_t aInstance, Iterator_t aKeys, Iterator_t aValues, PutOptions aOptions);
+
+    
+    static void
+      observe_callback(
+        lcb_t instance, 
+        const void *cookie,
+        lcb_error_t error,
+        const lcb_observe_resp_t *resp);
+
+  public:
+    
+    CouchbaseFunction(const CouchbaseModule* module);
+
+    virtual ~CouchbaseFunction();
+
+    virtual String
+      getURI() const;
+ 
+};
+
+
+/*******************************************************************************
+ ******************************************************************************/
+
+class InstanceMap : public ExternalFunctionParameter
+{
+  private:
+    typedef std::map<String, lcb_t> InstanceMap_t;
+    InstanceMap_t* instanceMap;
+
+  public:
+    InstanceMap();
+    
+    bool
+    storeInstance(const String&, lcb_t);
+
+    lcb_t
+    getInstance(const String&);
+
+    bool 
+    deleteInstance(const String&);
+
+    virtual void
+    destroy() throw()
+    {
+      if (instanceMap)
+      {
+        for (InstanceMap_t::const_iterator lIter = instanceMap->begin();
+             lIter != instanceMap->end(); ++lIter)
+        {
+          lcb_destroy(lIter->second);
+        }
+        instanceMap->clear();
+        delete instanceMap;
+      }
+      delete this;
+    };
+
+};
+
+/*******************************************************************************
+ ******************************************************************************/
+
+class ConnectFunction : public CouchbaseFunction
+{
+  public:
+    ConnectFunction(const CouchbaseModule* aModule)
+      : CouchbaseFunction(aModule) {}
+
+    virtual ~ConnectFunction(){}
+
+    virtual zorba::String
+      getLocalName() const { return "connect"; }
+
+    virtual zorba::ItemSequence_t
+      evaluate( const Arguments_t&,
+                const zorba::StaticContext*,
+                const zorba::DynamicContext*) const;
+};
+
+/*******************************************************************************
+ ******************************************************************************/
+
+class GetTextFunction : public CouchbaseFunction
+{
+  public:
+    GetTextFunction(const CouchbaseModule* aModule)
+      : CouchbaseFunction(aModule) 
+    {
+    }
+
+    virtual ~GetTextFunction(){}
+
+    virtual zorba::String
+      getLocalName() const { return "get-text"; }
+
+    virtual zorba::ItemSequence_t
+      evaluate( const Arguments_t&,
+                const zorba::StaticContext*,
+                const zorba::DynamicContext*) const;
+
+    static void get_callback(lcb_t instance, const void *cookie, lcb_error_t error, const lcb_get_resp_t *resp);
+    static std::vector<Item> theVectorItem;
+};
+
+/*******************************************************************************
+ ******************************************************************************/
+
+class GetBinaryFunction : public CouchbaseFunction
+{
+  public:
+    GetBinaryFunction(const CouchbaseModule* aModule)
+      : CouchbaseFunction(aModule) 
+    {
+    }
+
+    virtual ~GetBinaryFunction(){}
+
+    virtual zorba::String
+      getLocalName() const { return "get-binary"; }
+
+    virtual zorba::ItemSequence_t
+      evaluate( const Arguments_t&,
+                const zorba::StaticContext*,
+                const zorba::DynamicContext*) const;
+
+    static void get_callback(lcb_t instance, const void *cookie, lcb_error_t error, const lcb_get_resp_t *resp);
+    static std::vector<Item> theVectorItem;
+};
+
+/*******************************************************************************
+ ******************************************************************************/
+
+class RemoveFunction : public CouchbaseFunction
+{
+  public:
+    RemoveFunction(const CouchbaseModule* aModule)
+      : CouchbaseFunction(aModule) {}
+
+    virtual ~RemoveFunction(){}
+
+    virtual zorba::String
+      getLocalName() const { return "remove"; }
+
+    virtual zorba::ItemSequence_t
+      evaluate( const Arguments_t&,
+                const zorba::StaticContext*,
+                const zorba::DynamicContext*) const;
+};
+
+/*******************************************************************************
+ ******************************************************************************/
+
+class PutTextFunction : public CouchbaseFunction
+{
+  public:
+    PutTextFunction(const CouchbaseModule* aModule)
+      : CouchbaseFunction(aModule) {}
+
+    virtual ~PutTextFunction(){}
+
+    virtual zorba::String
+      getLocalName() const { return "put-text"; }
+
+    virtual zorba::ItemSequence_t
+      evaluate( const Arguments_t&,
+                const zorba::StaticContext*,
+                const zorba::DynamicContext*) const;
+};
+
+/*******************************************************************************
+ ******************************************************************************/
+
+class PutBinaryFunction : public CouchbaseFunction
+{
+  public:
+    PutBinaryFunction(const CouchbaseModule* aModule)
+      : CouchbaseFunction(aModule) {}
+
+    virtual ~PutBinaryFunction(){}
+
+    virtual zorba::String
+      getLocalName() const { return "put-binary"; }
+
+    virtual zorba::ItemSequence_t
+      evaluate( const Arguments_t&,
+                const zorba::StaticContext*,
+                const zorba::DynamicContext*) const;
+};
+
+/*******************************************************************************
+ ******************************************************************************/
+
+class FlushFunction : public CouchbaseFunction
+{
+  public:
+    FlushFunction(const CouchbaseModule* aModule)
+      : CouchbaseFunction(aModule) {}
+
+    virtual ~FlushFunction(){}
+
+    virtual zorba::String
+      getLocalName() const { return "flush"; }
+
+    virtual zorba::ItemSequence_t
+      evaluate( const Arguments_t&,
+                const zorba::StaticContext*,
+                const zorba::DynamicContext*) const;
+};
+
+/*******************************************************************************
+ ******************************************************************************/
+
+class TouchFunction : public CouchbaseFunction
+{
+  public:
+    TouchFunction(const CouchbaseModule* aModule)
+      : CouchbaseFunction(aModule) {}
+
+    virtual ~TouchFunction(){}
+
+    virtual zorba::String
+      getLocalName() const { return "touch"; }
+
+    virtual zorba::ItemSequence_t
+      evaluate( const Arguments_t&,
+                const zorba::StaticContext*,
+                const zorba::DynamicContext*) const;
+};
+
+/*******************************************************************************
+ ******************************************************************************/
+
+class ViewFunction : public CouchbaseFunction
+{
+  public:
+    ViewFunction(const CouchbaseModule* aModule)
+      : CouchbaseFunction(aModule) {}
+
+    virtual ~ViewFunction(){}
+
+    virtual zorba::String
+      getLocalName() const { return "view-text"; }
+
+    virtual zorba::ItemSequence_t
+      evaluate( const Arguments_t&,
+                const zorba::StaticContext*,
+                const zorba::DynamicContext*) const;
+};
+
+/*******************************************************************************
+ ******************************************************************************/
+
+class CreateViewFunction : public CouchbaseFunction
+{
+  private:
+    static void create_view_callback(
+      lcb_http_request_t request, 
+      lcb_t instance, 
+      const void* cookie, 
+      lcb_error_t error, 
+      const lcb_http_resp_t* resp);
+
+  public:
+    CreateViewFunction(const CouchbaseModule* aModule)
+      : CouchbaseFunction(aModule) {}
+
+    virtual ~CreateViewFunction(){}
+
+    virtual zorba::String
+      getLocalName() const { return "create-view"; }
+
+    virtual zorba::ItemSequence_t
+      evaluate( const Arguments_t&,
+                const zorba::StaticContext*,
+                const zorba::DynamicContext*) const;
+};
+
+/*******************************************************************************
+ ******************************************************************************/
+
+class DeleteViewFunction : public CouchbaseFunction
+{
+  private:
+    static void delete_view_callback(
+      lcb_http_request_t request, 
+      lcb_t instance, 
+      const void* cookie, 
+      lcb_error_t error, 
+      const lcb_http_resp_t* resp);
+
+  public:
+    DeleteViewFunction(const CouchbaseModule* aModule)
+      : CouchbaseFunction(aModule) {}
+
+    virtual ~DeleteViewFunction(){}
+
+    virtual zorba::String
+      getLocalName() const { return "delete-view"; }
+
+    virtual zorba::ItemSequence_t
+      evaluate( const Arguments_t&,
+                const zorba::StaticContext*,
+                const zorba::DynamicContext*) const;
+};
+} /*namespace couchbase*/ } /*namespace zorba*/
+
+
+#endif //_COM_ZORBA_WWW_MODULES_COUCHBASE_H_
+

=== added directory 'test'
=== renamed directory 'test' => 'test.moved'
=== added directory 'test/ExpQueryResults'
=== added directory 'test/ExpQueryResults/couchbase_module'
=== added file 'test/ExpQueryResults/couchbase_module/append-text.xml.res'
--- test/ExpQueryResults/couchbase_module/append-text.xml.res	1970-01-01 00:00:00 +0000
+++ test/ExpQueryResults/couchbase_module/append-text.xml.res	2013-04-29 18:32:40 +0000
@@ -0,0 +1,1 @@
+foofoo2

=== added file 'test/ExpQueryResults/couchbase_module/connect.xml.res'
--- test/ExpQueryResults/couchbase_module/connect.xml.res	1970-01-01 00:00:00 +0000
+++ test/ExpQueryResults/couchbase_module/connect.xml.res	2013-04-29 18:32:40 +0000
@@ -0,0 +1,1 @@
+true

=== added file 'test/ExpQueryResults/couchbase_module/create-view.xml.res'
--- test/ExpQueryResults/couchbase_module/create-view.xml.res	1970-01-01 00:00:00 +0000
+++ test/ExpQueryResults/couchbase_module/create-view.xml.res	2013-04-29 18:32:40 +0000
@@ -0,0 +1,1 @@
+_design/dev_view/_view/test1 _design/dev_view/_view/test2

=== added file 'test/ExpQueryResults/couchbase_module/create-view2.xml.res'
--- test/ExpQueryResults/couchbase_module/create-view2.xml.res	1970-01-01 00:00:00 +0000
+++ test/ExpQueryResults/couchbase_module/create-view2.xml.res	2013-04-29 18:32:40 +0000
@@ -0,0 +1,1 @@
+_design/dev_view2/_view/test1 _design/dev_view2/_view/test2

=== added file 'test/ExpQueryResults/couchbase_module/expiration-time.xml.res'
--- test/ExpQueryResults/couchbase_module/expiration-time.xml.res	1970-01-01 00:00:00 +0000
+++ test/ExpQueryResults/couchbase_module/expiration-time.xml.res	2013-04-29 18:32:40 +0000
@@ -0,0 +1,1 @@
+foo

=== added file 'test/ExpQueryResults/couchbase_module/prepend-text.xml.res'
--- test/ExpQueryResults/couchbase_module/prepend-text.xml.res	1970-01-01 00:00:00 +0000
+++ test/ExpQueryResults/couchbase_module/prepend-text.xml.res	2013-04-29 18:32:40 +0000
@@ -0,0 +1,1 @@
+foo2foo

=== added file 'test/ExpQueryResults/couchbase_module/replace-text.xml.res'
--- test/ExpQueryResults/couchbase_module/replace-text.xml.res	1970-01-01 00:00:00 +0000
+++ test/ExpQueryResults/couchbase_module/replace-text.xml.res	2013-04-29 18:32:40 +0000
@@ -0,0 +1,1 @@
+foo2

=== added file 'test/ExpQueryResults/couchbase_module/store-binary.xml.res'
--- test/ExpQueryResults/couchbase_module/store-binary.xml.res	1970-01-01 00:00:00 +0000
+++ test/ExpQueryResults/couchbase_module/store-binary.xml.res	2013-04-29 18:32:40 +0000
@@ -0,0 +1,1 @@
+aW1wb3J0IG1vZHVsZSBuYW1lc3BhY2UgY2IgPSAiaHR0cDovL3d3dy56b3JiYS14cXVlcnkuY29tL21vZHVsZXMvY291Y2hiYXNlIjsKCnZhcmlhYmxlICRpbnN0YW5jZSA6PSBjYjpjb25uZWN0KHsKICAiaG9zdCI6ICJsb2NhbGhvc3Q6ODA5MSIsCiAgInVzZXJuYW1lIiA6IGpuOm51bGwoKSwKICAicGFzc3dvcmQiIDogam46bnVsbCgpLAogICJidWNrZXQiIDogImRlZmF1bHQifSk7CmlmICgkaW5zdGFuY2UpCiB0aGVuIHRydWUoKQogZWxzZSBmYWxzZSgpCgo=

=== added file 'test/ExpQueryResults/couchbase_module/store-binary2.xml.res'
--- test/ExpQueryResults/couchbase_module/store-binary2.xml.res	1970-01-01 00:00:00 +0000
+++ test/ExpQueryResults/couchbase_module/store-binary2.xml.res	2013-04-29 18:32:40 +0000
@@ -0,0 +1,11 @@
+import module namespace cb = "http://www.zorba-xquery.com/modules/couchbase";;
+
+variable $instance := cb:connect({
+  "host": "localhost:8091",
+  "username" : jn:null(),
+  "password" : jn:null(),
+  "bucket" : "default"});
+if ($instance)
+ then true()
+ else false()
+

=== added file 'test/ExpQueryResults/couchbase_module/store-text-encoding.xml.res'
--- test/ExpQueryResults/couchbase_module/store-text-encoding.xml.res	1970-01-01 00:00:00 +0000
+++ test/ExpQueryResults/couchbase_module/store-text-encoding.xml.res	2013-04-29 18:32:40 +0000
@@ -0,0 +1,1 @@
+true

=== added file 'test/ExpQueryResults/couchbase_module/store-text-encoding2.xml.res'
--- test/ExpQueryResults/couchbase_module/store-text-encoding2.xml.res	1970-01-01 00:00:00 +0000
+++ test/ExpQueryResults/couchbase_module/store-text-encoding2.xml.res	2013-04-29 18:32:40 +0000
@@ -0,0 +1,1 @@
+false

=== added file 'test/ExpQueryResults/couchbase_module/store-text.xml.res'
--- test/ExpQueryResults/couchbase_module/store-text.xml.res	1970-01-01 00:00:00 +0000
+++ test/ExpQueryResults/couchbase_module/store-text.xml.res	2013-04-29 18:32:40 +0000
@@ -0,0 +1,1 @@
+foo

=== added file 'test/ExpQueryResults/couchbase_module/touch.xml.res'
--- test/ExpQueryResults/couchbase_module/touch.xml.res	1970-01-01 00:00:00 +0000
+++ test/ExpQueryResults/couchbase_module/touch.xml.res	2013-04-29 18:32:40 +0000
@@ -0,0 +1,1 @@
+foo

=== added file 'test/ExpQueryResults/couchbase_module/view.xml.res'
--- test/ExpQueryResults/couchbase_module/view.xml.res	1970-01-01 00:00:00 +0000
+++ test/ExpQueryResults/couchbase_module/view.xml.res	2013-04-29 18:32:40 +0000
@@ -0,0 +1,1 @@
+{ "id" : "view", "key" : 1, "value" : null }

=== added directory 'test/Queries'
=== added directory 'test/Queries/couchbase_module'
=== added file 'test/Queries/couchbase_module/append-text.xq'
--- test/Queries/couchbase_module/append-text.xq	1970-01-01 00:00:00 +0000
+++ test/Queries/couchbase_module/append-text.xq	2013-04-29 18:32:40 +0000
@@ -0,0 +1,12 @@
+import module namespace cb = "http://www.zorba-xquery.com/modules/couchbase";;
+
+variable $instance := cb:connect({
+  "host": "localhost:8091",
+  "username" : jn:null(),
+  "password" : jn:null(),
+  "bucket" : "default"});
+
+cb:put-text($instance, "append", "foo");
+cb:put-text($instance, "append", "foo2", { "operation" : "append" });
+variable $result := cb:get-text($instance, "append");
+$result

=== added file 'test/Queries/couchbase_module/connect.xq'
--- test/Queries/couchbase_module/connect.xq	1970-01-01 00:00:00 +0000
+++ test/Queries/couchbase_module/connect.xq	2013-04-29 18:32:40 +0000
@@ -0,0 +1,11 @@
+import module namespace cb = "http://www.zorba-xquery.com/modules/couchbase";;
+
+variable $instance := cb:connect({
+  "host": "localhost:8091",
+  "username" : jn:null(),
+  "password" : jn:null(),
+  "bucket" : "default"});
+if ($instance)
+ then true()
+ else false()
+

=== added file 'test/Queries/couchbase_module/connect2.spec'
--- test/Queries/couchbase_module/connect2.spec	1970-01-01 00:00:00 +0000
+++ test/Queries/couchbase_module/connect2.spec	2013-04-29 18:32:40 +0000
@@ -0,0 +1,1 @@
+Error: http://www.zorba-xquery.com/modules/couchbase:LCB0001

=== added file 'test/Queries/couchbase_module/connect2.xq'
--- test/Queries/couchbase_module/connect2.xq	1970-01-01 00:00:00 +0000
+++ test/Queries/couchbase_module/connect2.xq	2013-04-29 18:32:40 +0000
@@ -0,0 +1,11 @@
+import module namespace cb = "http://www.zorba-xquery.com/modules/couchbase";;
+
+variable $instance := cb:connect({
+  "host": "12492873009",
+  "username" : jn:null(),
+  "password" : jn:null(),
+  "bucket" : "default"});
+if ($instance)
+ then true()
+ else false()
+

=== added file 'test/Queries/couchbase_module/create-view.xq'
--- test/Queries/couchbase_module/create-view.xq	1970-01-01 00:00:00 +0000
+++ test/Queries/couchbase_module/create-view.xq	2013-04-29 18:32:40 +0000
@@ -0,0 +1,10 @@
+import module namespace cb = "http://www.zorba-xquery.com/modules/couchbase";;
+
+variable $instance := cb:connect({
+  "host": "localhost:8091",
+  "username" : jn:null(),
+  "password" : jn:null(),
+  "bucket" : "default"});
+
+variable $view-name := cb:create-view($instance, "dev_view", ("test1", "test2"));
+$view-name

=== added file 'test/Queries/couchbase_module/create-view2.xq'
--- test/Queries/couchbase_module/create-view2.xq	1970-01-01 00:00:00 +0000
+++ test/Queries/couchbase_module/create-view2.xq	2013-04-29 18:32:40 +0000
@@ -0,0 +1,10 @@
+import module namespace cb = "http://www.zorba-xquery.com/modules/couchbase";;
+
+variable $instance := cb:connect({
+  "host": "localhost:8091",
+  "username" : jn:null(),
+  "password" : jn:null(),
+  "bucket" : "default"});
+
+variable $view-name := cb:create-view($instance, "dev_view2", ("test1", "test2"), ({"key" : "meta.id", "values" : "doc.value"},{ "key" : "meta.id", "values" : ["doc.value", "doc.value2"] }));
+$view-name

=== added file 'test/Queries/couchbase_module/expiration-time.xq'
--- test/Queries/couchbase_module/expiration-time.xq	1970-01-01 00:00:00 +0000
+++ test/Queries/couchbase_module/expiration-time.xq	2013-04-29 18:32:40 +0000
@@ -0,0 +1,11 @@
+import module namespace cb = "http://www.zorba-xquery.com/modules/couchbase";;
+
+variable $instance := cb:connect({
+  "host": "localhost:8091",
+  "username" : jn:null(),
+  "password" : jn:null(),
+  "bucket" : "default"});
+
+cb:put-text($instance, "exp-time", "foo", { "expiration-time" : 1 });
+variable $result := cb:get-text($instance, "exp-time");
+$result

=== added file 'test/Queries/couchbase_module/prepend-text.xq'
--- test/Queries/couchbase_module/prepend-text.xq	1970-01-01 00:00:00 +0000
+++ test/Queries/couchbase_module/prepend-text.xq	2013-04-29 18:32:40 +0000
@@ -0,0 +1,12 @@
+import module namespace cb = "http://www.zorba-xquery.com/modules/couchbase";;
+
+variable $instance := cb:connect({
+  "host": "localhost:8091",
+  "username" : jn:null(),
+  "password" : jn:null(),
+  "bucket" : "default"});
+
+cb:put-text($instance, "prepend", "foo");
+cb:put-text($instance, "prepend", "foo2", { "operation" : "prepend" });
+variable $result := cb:get-text($instance, "prepend");
+$result

=== added file 'test/Queries/couchbase_module/remove.spec'
--- test/Queries/couchbase_module/remove.spec	1970-01-01 00:00:00 +0000
+++ test/Queries/couchbase_module/remove.spec	2013-04-29 18:32:40 +0000
@@ -0,0 +1,1 @@
+Error: http://www.zorba-xquery.com/modules/couchbase:LCB0002

=== added file 'test/Queries/couchbase_module/remove.xq'
--- test/Queries/couchbase_module/remove.xq	1970-01-01 00:00:00 +0000
+++ test/Queries/couchbase_module/remove.xq	2013-04-29 18:32:40 +0000
@@ -0,0 +1,12 @@
+import module namespace cb = "http://www.zorba-xquery.com/modules/couchbase";;
+
+variable $instance := cb:connect({
+  "host": "localhost:8091",
+  "username" : jn:null(),
+  "password" : jn:null(),
+  "bucket" : "default"});
+
+cb:put-text($instance, "remove", "foo");
+cb:remove($instance, "remove");
+variable $result := cb:get-text($instance, "remove");
+$result

=== added file 'test/Queries/couchbase_module/replace-text.xq'
--- test/Queries/couchbase_module/replace-text.xq	1970-01-01 00:00:00 +0000
+++ test/Queries/couchbase_module/replace-text.xq	2013-04-29 18:32:40 +0000
@@ -0,0 +1,12 @@
+import module namespace cb = "http://www.zorba-xquery.com/modules/couchbase";;
+
+variable $instance := cb:connect({
+  "host": "localhost:8091",
+  "username" : jn:null(),
+  "password" : jn:null(),
+  "bucket" : "default"});
+
+cb:put-text($instance, "replace", "foo");
+cb:put-text($instance, "replace", "foo2", { "operation" : "replace" });
+variable $result := cb:get-text($instance, "replace");
+$result

=== added file 'test/Queries/couchbase_module/store-binary.xq'
--- test/Queries/couchbase_module/store-binary.xq	1970-01-01 00:00:00 +0000
+++ test/Queries/couchbase_module/store-binary.xq	2013-04-29 18:32:40 +0000
@@ -0,0 +1,13 @@
+import module namespace cb = "http://www.zorba-xquery.com/modules/couchbase";;
+import module namespace f = "http://expath.org/ns/file";;
+
+variable $instance := cb:connect({
+  "host": "localhost:8091",
+  "username" : jn:null(),
+  "password" : jn:null(),
+  "bucket" : "default"});
+
+variable $binary := f:read-binary(resolve-uri("connect.xq"));
+cb:put-binary($instance, "binary-file", $binary);
+variable $result := cb:get-binary($instance, "binary-file");
+$result

=== added file 'test/Queries/couchbase_module/store-binary2.xq'
--- test/Queries/couchbase_module/store-binary2.xq	1970-01-01 00:00:00 +0000
+++ test/Queries/couchbase_module/store-binary2.xq	2013-04-29 18:32:40 +0000
@@ -0,0 +1,13 @@
+import module namespace cb = "http://www.zorba-xquery.com/modules/couchbase";;
+import module namespace f = "http://expath.org/ns/file";;
+
+variable $instance := cb:connect({
+  "host": "localhost:8091",
+  "username" : jn:null(),
+  "password" : jn:null(),
+  "bucket" : "default"});
+
+variable $binary := f:read-binary(resolve-uri("connect.xq"));
+cb:put-binary($instance, "binary-file2", $binary);
+variable $result := cb:get-text($instance, "binary-file2");
+$result

=== added file 'test/Queries/couchbase_module/store-text-encoding.xq'
--- test/Queries/couchbase_module/store-text-encoding.xq	1970-01-01 00:00:00 +0000
+++ test/Queries/couchbase_module/store-text-encoding.xq	2013-04-29 18:32:40 +0000
@@ -0,0 +1,13 @@
+import module namespace cb = "http://www.zorba-xquery.com/modules/couchbase";;
+
+variable $instance := cb:connect({
+  "host": "localhost:8091",
+  "username" : jn:null(),
+  "password" : jn:null(),
+  "bucket" : "default"});
+
+cb:put-text($instance, "encoding", "äüö", { "encoding" : "ISO-8859-1" });
+variable $result := cb:get-text($instance, "encoding", { "encoding" : "ISO-8859-1" });
+if ($result = "äüö")
+then true()
+else false()

=== added file 'test/Queries/couchbase_module/store-text-encoding2.xq'
--- test/Queries/couchbase_module/store-text-encoding2.xq	1970-01-01 00:00:00 +0000
+++ test/Queries/couchbase_module/store-text-encoding2.xq	2013-04-29 18:32:40 +0000
@@ -0,0 +1,13 @@
+import module namespace cb = "http://www.zorba-xquery.com/modules/couchbase";;
+
+variable $instance := cb:connect({
+  "host": "localhost:8091",
+  "username" : jn:null(),
+  "password" : jn:null(),
+  "bucket" : "default"});
+
+cb:put-text($instance, "encoding2", "äüö", { "encoding" : "ISO-8859-1" });
+variable $result := cb:get-text($instance, "encoding2", { "encoding" : "UTF-8" });
+if ($result = "äüö")
+then true()
+else false()

=== added file 'test/Queries/couchbase_module/store-text.xq'
--- test/Queries/couchbase_module/store-text.xq	1970-01-01 00:00:00 +0000
+++ test/Queries/couchbase_module/store-text.xq	2013-04-29 18:32:40 +0000
@@ -0,0 +1,11 @@
+import module namespace cb = "http://www.zorba-xquery.com/modules/couchbase";;
+
+variable $instance := cb:connect({
+  "host": "localhost:8091",
+  "username" : jn:null(),
+  "password" : jn:null(),
+  "bucket" : "default"});
+
+cb:put-text($instance, "store", "foo");
+variable $result := cb:get-text($instance, "store");
+$result

=== added file 'test/Queries/couchbase_module/store-text2.spec'
--- test/Queries/couchbase_module/store-text2.spec	1970-01-01 00:00:00 +0000
+++ test/Queries/couchbase_module/store-text2.spec	2013-04-29 18:32:40 +0000
@@ -0,0 +1,1 @@
+Error: http://www.zorba-xquery.com/modules/couchbase:CB0006

=== added file 'test/Queries/couchbase_module/store-text2.xq'
--- test/Queries/couchbase_module/store-text2.xq	1970-01-01 00:00:00 +0000
+++ test/Queries/couchbase_module/store-text2.xq	2013-04-29 18:32:40 +0000
@@ -0,0 +1,11 @@
+import module namespace cb = "http://www.zorba-xquery.com/modules/couchbase";;
+
+variable $instance := cb:connect({
+  "host": "localhost:8091",
+  "username" : jn:null(),
+  "password" : jn:null(),
+  "bucket" : "default"});
+
+cb:put-text($instance, "store2", "foo", { "encoding" : "foo" });
+variable $result := cb:get-text($instance, "store2", { "encoding" : "UTF-8" });
+$result

=== added file 'test/Queries/couchbase_module/touch.xq'
--- test/Queries/couchbase_module/touch.xq	1970-01-01 00:00:00 +0000
+++ test/Queries/couchbase_module/touch.xq	2013-04-29 18:32:40 +0000
@@ -0,0 +1,12 @@
+import module namespace cb = "http://www.zorba-xquery.com/modules/couchbase";;
+
+variable $instance := cb:connect({
+  "host": "localhost:8091",
+  "username" : jn:null(),
+  "password" : jn:null(),
+  "bucket" : "default"});
+
+cb:put-text($instance, "touch", "foo");
+cb:touch($instance, "touch", 1);
+variable $result := cb:get-text($instance, "touch");
+$result

=== added file 'test/Queries/couchbase_module/view.xq'
--- test/Queries/couchbase_module/view.xq	1970-01-01 00:00:00 +0000
+++ test/Queries/couchbase_module/view.xq	2013-04-29 18:32:40 +0000
@@ -0,0 +1,19 @@
+import module namespace cb = "http://www.zorba-xquery.com/modules/couchbase";;
+
+variable $instance := cb:connect({
+  "host": "localhost:8091",
+  "username" : jn:null(),
+  "password" : jn:null(),
+  "bucket" : "default"});
+
+cb:remove($instance, "view");
+cb:put-text($instance, "view", '{ "view" : 1 }', { "wait" : "persist" });
+
+variable $cb-document := "dev_test_view";
+variable $cb-view := "view";
+variable $view-name := cb:create-view($instance, $cb-document, $cb-view, {"key":"doc.view"});
+variable $data := cb:view($instance, $view-name, {"stale" : "false"});
+for $d in jn:members($data("rows"))
+let $key := $d("key")
+where not(jn:is-null($key)) and $key >0
+return $d