that's nice! - benoit
On Mon, Sep 27, 2010 at 10:06 PM, <[email protected]> wrote: > Author: jchris > Date: Mon Sep 27 20:06:22 2010 > New Revision: 1001895 > > URL: http://svn.apache.org/viewvc?rev=1001895&view=rev > Log: > CommonJS support in map functions > > Modified: > couchdb/trunk/share/server/loop.js > couchdb/trunk/share/server/state.js > couchdb/trunk/share/www/script/test/design_docs.js > couchdb/trunk/src/couchdb/couch_db.hrl > couchdb/trunk/src/couchdb/couch_query_servers.erl > couchdb/trunk/src/couchdb/couch_view_group.erl > couchdb/trunk/src/couchdb/couch_view_updater.erl > > Modified: couchdb/trunk/share/server/loop.js > URL: > http://svn.apache.org/viewvc/couchdb/trunk/share/server/loop.js?rev=1001895&r1=1001894&r2=1001895&view=diff > ============================================================================== > --- couchdb/trunk/share/server/loop.js (original) > +++ couchdb/trunk/share/server/loop.js Mon Sep 27 20:06:22 2010 > @@ -100,6 +100,7 @@ var Loop = function() { > // "view" : Views.handler, > "reset" : State.reset, > "add_fun" : State.addFun, > + "add_lib" : State.addLib, > "map_doc" : Views.mapDoc, > "reduce" : Views.reduce, > "rereduce" : Views.rereduce > > Modified: couchdb/trunk/share/server/state.js > URL: > http://svn.apache.org/viewvc/couchdb/trunk/share/server/state.js?rev=1001895&r1=1001894&r2=1001895&view=diff > ============================================================================== > --- couchdb/trunk/share/server/state.js (original) > +++ couchdb/trunk/share/server/state.js Mon Sep 27 20:06:22 2010 > @@ -14,6 +14,7 @@ var State = { > reset : function(config) { > // clear the globals and run gc > State.funs = []; > + State.lib = null; > State.query_config = config || {}; > init_sandbox(); > gc(); > @@ -21,7 +22,11 @@ var State = { > }, > addFun : function(newFun) { > // Compile to a function and add it to funs array > - State.funs.push(Couch.compileFunction(newFun)); > + State.funs.push(Couch.compileFunction(newFun, {views : {lib : > State.lib}})); > + print("true"); > + }, > + addLib : function(lib) { > + State.lib = lib; > print("true"); > } > } > > Modified: couchdb/trunk/share/www/script/test/design_docs.js > URL: > http://svn.apache.org/viewvc/couchdb/trunk/share/www/script/test/design_docs.js?rev=1001895&r1=1001894&r2=1001895&view=diff > ============================================================================== > --- couchdb/trunk/share/www/script/test/design_docs.js (original) > +++ couchdb/trunk/share/www/script/test/design_docs.js Mon Sep 27 20:06:22 > 2010 > @@ -54,7 +54,18 @@ function() { > summate2: {map:"function (doc) {emit(doc.integer, doc.integer)};", > reduce:"function (keys, values) { return sum(values); };"}, > huge_src_and_results: {map: "function(doc) { if (doc._id == \"1\") { > emit(\"" + makebigstring(16) + "\", null) }}", > - reduce:"function (keys, values) { return \"" + > makebigstring(16) + "\"; };"} > + reduce:"function (keys, values) { return \"" + > makebigstring(16) + "\"; };"}, > + lib : { > + baz : "exports.baz = 'bam';", > + foo : { > + foo : "exports.foo = 'bar';", > + boom : "exports.boom = 'ok';", > + zoom : "exports.zoom = 'yeah';" > + } > + }, > + commonjs : { > + map : "function(doc) { emit(null, > require('views/lib/foo/boom').boom)}" > + } > }, > shows: { > simple: "function() {return 'ok'};", > @@ -99,10 +110,14 @@ function() { > var vinfo = dinfo.view_index; > TEquals(51, vinfo.disk_size); > TEquals(false, vinfo.compact_running); > - TEquals("3f88e53b303e2342e49a66c538c30679", vinfo.signature); > + TEquals("dc3264b45b74cc6d94666e3043e07154", vinfo.signature, 'ddoc sig'); > > db.bulkSave(makeDocs(1, numDocs + 1)); > > + // test commonjs in map functions > + resp = db.view("test/commonjs", {limit:1}); > + T(resp.rows[0].value == 'ok'); > + > // test that the _all_docs view returns correctly with keys > var results = db.allDocs({startkey:"_design", endkey:"_design0"}); > T(results.rows.length == 1); > > Modified: couchdb/trunk/src/couchdb/couch_db.hrl > URL: > http://svn.apache.org/viewvc/couchdb/trunk/src/couchdb/couch_db.hrl?rev=1001895&r1=1001894&r2=1001895&view=diff > ============================================================================== > --- couchdb/trunk/src/couchdb/couch_db.hrl (original) > +++ couchdb/trunk/src/couchdb/couch_db.hrl Mon Sep 27 20:06:22 2010 > @@ -231,6 +231,7 @@ > def_lang, > design_options=[], > views, > + lib, > id_btree=nil, > current_seq=0, > purge_seq=0, > > Modified: couchdb/trunk/src/couchdb/couch_query_servers.erl > URL: > http://svn.apache.org/viewvc/couchdb/trunk/src/couchdb/couch_query_servers.erl?rev=1001895&r1=1001894&r2=1001895&view=diff > ============================================================================== > --- couchdb/trunk/src/couchdb/couch_query_servers.erl (original) > +++ couchdb/trunk/src/couchdb/couch_query_servers.erl Mon Sep 27 20:06:22 2010 > @@ -16,7 +16,7 @@ > -export([start_link/0]). > > -export([init/1, terminate/2, handle_call/3, handle_cast/2, > handle_info/2,code_change/3]). > --export([start_doc_map/2, map_docs/2, stop_doc_map/1]). > +-export([start_doc_map/3, map_docs/2, stop_doc_map/1]). > -export([reduce/3, rereduce/3,validate_doc_update/5]). > -export([filter_docs/5]). > > @@ -47,8 +47,13 @@ > start_link() -> > gen_server:start_link({local, couch_query_servers}, couch_query_servers, > [], []). > > -start_doc_map(Lang, Functions) -> > +start_doc_map(Lang, Functions, Lib) -> > Proc = get_os_process(Lang), > + case Lib of > + {[]} -> ok; > + Lib -> > + true = proc_prompt(Proc, [<<"add_lib">>, Lib]) > + end, > lists:foreach(fun(FunctionSource) -> > true = proc_prompt(Proc, [<<"add_fun">>, FunctionSource]) > end, Functions), > > Modified: couchdb/trunk/src/couchdb/couch_view_group.erl > URL: > http://svn.apache.org/viewvc/couchdb/trunk/src/couchdb/couch_view_group.erl?rev=1001895&r1=1001894&r2=1001895&view=diff > ============================================================================== > --- couchdb/trunk/src/couchdb/couch_view_group.erl (original) > +++ couchdb/trunk/src/couchdb/couch_view_group.erl Mon Sep 27 20:06:22 2010 > @@ -446,7 +446,7 @@ open_temp_group(DbName, Language, Design > reduce_funs= if RedSrc==[] -> []; true -> [{<<"_temp">>, RedSrc}] > end, > options=DesignOptions}, > > - {ok, Db, set_view_sig(#group{name = <<"_temp">>, db=Db, views=[View], > + {ok, Db, set_view_sig(#group{name = <<"_temp">>,lib={[]}, db=Db, > views=[View], > def_lang=Language, design_options=DesignOptions})}; > Error -> > Error > @@ -454,9 +454,26 @@ open_temp_group(DbName, Language, Design > > set_view_sig(#group{ > views=Views, > + lib={[]}, > def_lang=Language, > design_options=DesignOptions}=G) -> > - G#group{sig=couch_util:md5(term_to_binary({Views, Language, > DesignOptions}))}. > + G#group{sig=couch_util:md5(term_to_binary({Views, Language, > DesignOptions}))}; > +set_view_sig(#group{ > + views=Views, > + lib=Lib, > + def_lang=Language, > + design_options=DesignOptions}=G) -> > + G#group{sig=couch_util:md5(term_to_binary({Views, Language, > DesignOptions, sort_lib(Lib)}))}. > + > +sort_lib({Lib}) -> > + sort_lib(Lib, []). > +sort_lib([], LAcc) -> > + lists:keysort(1, LAcc); > +sort_lib([{LName, {LObj}}|Rest], LAcc) -> > + LSorted = sort_lib(LObj, []), % descend into nested object > + sort_lib(Rest, [{LName, LSorted}|LAcc]); > +sort_lib([{LName, LCode}|Rest], LAcc) -> > + sort_lib(Rest, [{LName, LCode}|LAcc]). > > open_db_group(DbName, GroupId) -> > case couch_db:open_int(DbName, []) of > @@ -505,33 +522,36 @@ design_doc_to_view_group(#doc{id=Id,body > Language = ?getv(<<"language">>, Fields, <<"javascript">>), > {DesignOptions} = ?getv(<<"options">>, Fields, {[]}), > {RawViews} = ?getv(<<"views">>, Fields, {[]}), > + Lib = ?getv(<<"lib">>, RawViews, {[]}), > % add the views to a dictionary object, with the map source as the key > DictBySrc = > lists:foldl( > fun({Name, {MRFuns}}, DictBySrcAcc) -> > - MapSrc = ?getv(<<"map">>, MRFuns), > - RedSrc = ?getv(<<"reduce">>, MRFuns, null), > - {ViewOptions} = ?getv(<<"options">>, MRFuns, {[]}), > - View = > - case dict:find({MapSrc, ViewOptions}, DictBySrcAcc) of > - {ok, View0} -> View0; > - error -> #view{def=MapSrc, options=ViewOptions} % create new > view object > - end, > - View2 = > - if RedSrc == null -> > - View#view{map_names=[Name|View#view.map_names]}; > - true -> > - View#view{reduce_funs=[{Name,RedSrc}|View#view.reduce_funs]} > - end, > - dict:store({MapSrc, ViewOptions}, View2, DictBySrcAcc) > + case ?getv(<<"map">>, MRFuns) of > + undefined -> DictBySrcAcc; > + MapSrc -> > + RedSrc = ?getv(<<"reduce">>, MRFuns, null), > + {ViewOptions} = ?getv(<<"options">>, MRFuns, {[]}), > + View = > + case dict:find({MapSrc, ViewOptions}, DictBySrcAcc) of > + {ok, View0} -> View0; > + error -> #view{def=MapSrc, options=ViewOptions} % create > new view object > + end, > + View2 = > + if RedSrc == null -> > + View#view{map_names=[Name|View#view.map_names]}; > + true -> > + > View#view{reduce_funs=[{Name,RedSrc}|View#view.reduce_funs]} > + end, > + dict:store({MapSrc, ViewOptions}, View2, DictBySrcAcc) > + end > end, dict:new(), RawViews), > % number the views > {Views, _N} = lists:mapfoldl( > fun({_Src, View}, N) -> > {View#view{id_num=N},N+1} > end, 0, lists:sort(dict:to_list(DictBySrc))), > - > - set_view_sig(#group{name=Id, views=Views, def_lang=Language, > design_options=DesignOptions}). > + set_view_sig(#group{name=Id, lib=Lib, views=Views, def_lang=Language, > design_options=DesignOptions}). > > reset_group(#group{views=Views}=Group) -> > Views2 = [View#view{btree=nil} || View <- Views], > > Modified: couchdb/trunk/src/couchdb/couch_view_updater.erl > URL: > http://svn.apache.org/viewvc/couchdb/trunk/src/couchdb/couch_view_updater.erl?rev=1001895&r1=1001894&r2=1001895&view=diff > ============================================================================== > --- couchdb/trunk/src/couchdb/couch_view_updater.erl (original) > +++ couchdb/trunk/src/couchdb/couch_view_updater.erl Mon Sep 27 20:06:22 2010 > @@ -203,12 +203,12 @@ view_insert_doc_query_results(#doc{id=Do > > view_compute(Group, []) -> > {Group, []}; > -view_compute(#group{def_lang=DefLang, query_server=QueryServerIn}=Group, > Docs) -> > +view_compute(#group{def_lang=DefLang, lib=Lib, > query_server=QueryServerIn}=Group, Docs) -> > {ok, QueryServer} = > case QueryServerIn of > nil -> % doc map not started > Definitions = [View#view.def || View <- Group#group.views], > - couch_query_servers:start_doc_map(DefLang, Definitions); > + couch_query_servers:start_doc_map(DefLang, Definitions, Lib); > _ -> > {ok, QueryServerIn} > end, > > >
