xref: /5.5.2/couchdb/src/mapreduce/mapreduce.h (revision c75857af)
1/* -*- Mode: C++; tab-width: 4; c-basic-offset: 4; indent-tabs-mode: nil -*- */
2/**
3 * @copyright 2012 Couchbase, Inc.
4 *
5 * @author Filipe Manana  <filipe@couchbase.com>
6 *
7 * Licensed under the Apache License, Version 2.0 (the "License"); you may not
8 * use this file except in compliance with the License. You may obtain a copy of
9 * the License at
10 *
11 *  http://www.apache.org/licenses/LICENSE-2.0
12 *
13 * Unless required by applicable law or agreed to in writing, software
14 * distributed under the License is distributed on an "AS IS" BASIS, WITHOUT
15 * WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the
16 * License for the specific language governing permissions and limitations under
17 * the License.
18 **/
19
20#ifndef _MAPREDUCE_H
21#define _MAPREDUCE_H
22
23#include <cstddef>
24#include <iostream>
25#include <string>
26#include <list>
27#include <vector>
28#include <include/v8.h>
29#include <platform/platform.h>
30
31#include "erl_nif_compat.h"
32#include "nif_stl_allocator.h"
33
34class MapReduceError;
35
36typedef std::list<ErlNifBinary, NifStlAllocator<ErlNifBinary> >  json_results_list_t;
37typedef std::list<ErlNifBinary, NifStlAllocator<ErlNifBinary> >  log_results_list_t;
38typedef std::pair<ErlNifBinary, ErlNifBinary>  kv_pair_t;
39typedef std::list< kv_pair_t, NifStlAllocator< kv_pair_t > >  kv_pair_list_t;
40
41typedef enum {
42    VIEW_INDEX_TYPE_MAPREDUCE,
43    VIEW_INDEX_TYPE_SPATIAL
44}  view_index_type_t;
45
46typedef enum {
47    MAP_KVS,
48    MAP_ERROR
49} map_result_type_t;
50
51typedef struct {
52    map_result_type_t type;
53    union {
54        kv_pair_list_t *kvs;
55        ErlNifBinary *error;
56    } result;
57} map_result_t;
58
59typedef std::list< map_result_t,
60                   NifStlAllocator< map_result_t > >  map_results_list_t;
61
62typedef std::vector< v8::Persistent<v8::Function>*,
63                     NifStlAllocator< v8::Persistent<v8::Function>* > >  function_vector_t;
64
65typedef std::basic_string< char,
66                           std::char_traits<char>,
67                           NifStlAllocator<char> >  function_source_t;
68
69typedef std::list< function_source_t,
70                   NifStlAllocator< function_source_t > >  function_sources_list_t;
71
72class ArrayBufferAllocator : public v8::ArrayBuffer::Allocator {
73public:
74    virtual void* Allocate(size_t length) {
75        void* data = AllocateUninitialized(length);
76        return data == NULL ? data : memset(data, 0, length);
77    }
78
79    virtual void* AllocateUninitialized(size_t length) {
80        return malloc(length);
81    }
82
83    virtual void Free(void* data, size_t) {
84        free(data);
85    }
86};
87
88typedef struct {
89    v8::Persistent<v8::Context>                  jsContext;
90    v8::Isolate                                  *isolate;
91    ArrayBufferAllocator                         *bufAllocator;
92    function_vector_t                            *functions;
93    kv_pair_list_t                               *kvs;
94    unsigned int                                 key;
95    ErlNifEnv                                    *env;
96    hrtime_t                                     taskStartTime;
97    int                                          emitKvSize;
98    int                                          maxEmitKvSize;
99    log_results_list_t                           *logResults;
100    view_index_type_t                            viewType;
101} map_reduce_ctx_t;
102
103
104void initContext(map_reduce_ctx_t *ctx, const function_sources_list_t &funs,
105                 const view_index_type_t viewType);
106void destroyContext(map_reduce_ctx_t *ctx);
107
108map_results_list_t mapDoc(map_reduce_ctx_t *ctx,
109                          const ErlNifBinary &doc,
110                          const ErlNifBinary &meta);
111
112json_results_list_t runReduce(map_reduce_ctx_t *ctx,
113                              const json_results_list_t &keys,
114                              const json_results_list_t &values);
115
116ErlNifBinary runReduce(map_reduce_ctx_t *ctx, int reduceFunNum,
117                       const json_results_list_t &keys,
118                       const json_results_list_t &values);
119
120ErlNifBinary runRereduce(map_reduce_ctx_t *ctx,
121                         int reduceFunNum,
122                         const json_results_list_t &reductions);
123
124void terminateTask(map_reduce_ctx_t *ctx);
125
126/**
127* This API needs to be called once per process to initialize
128* v8 javascript engine. This needs to be called before
129* any v8 APIs like creating v8 isolate and v8 context.
130**/
131void initV8();
132
133/**
134* This API needs to be called once per process to cleanup
135* v8 resources. This needs to be called after disposing all
136* v8 thread contexts like v8 isolate and v8 context.
137**/
138void deinitV8();
139
140class MapReduceError {
141public:
142    MapReduceError(const char *msg) : _msg(msg) {
143    }
144
145    MapReduceError(const std::string &msg) : _msg(msg) {
146    }
147
148    const std::string& getMsg() const {
149        return _msg;
150    }
151
152private:
153    const std::string _msg;
154};
155
156
157#endif
158