From 3358668c079c85968d51b5c55f08cfba48bb88d4 Mon Sep 17 00:00:00 2001 From: AlexanderKaraberov <3254818+AlexanderKaraberov@users.noreply.github.com> Date: Thu, 31 May 2018 10:23:40 +0200 Subject: fix(_view changes feed): fix function_clause crash in couch_native_process. Crash was caused by a missing implementation of ddoc function for <<"views">> FunPath, implementation is based on FilterFun but matches return values of the erlang:put() which is called in the native Emit function and also expects ok and false when docs were not emitted. --- src/couch/src/couch_native_process.erl | 12 ++++++++++++ 1 file changed, 12 insertions(+) diff --git a/src/couch/src/couch_native_process.erl b/src/couch/src/couch_native_process.erl index 6d66c936b..8f8ce8b1d 100644 --- a/src/couch/src/couch_native_process.erl +++ b/src/couch/src/couch_native_process.erl @@ -226,6 +226,18 @@ ddoc(State, {_, Fun}, [<<"filters">>|_], [Docs, Req]) -> end, Resp = lists:map(FilterFunWrapper, Docs), {State, [true, Resp]}; +ddoc(State, {_, Fun}, [<<"views">>|_], [Docs]) -> + MapFunWrapper = fun(Doc) -> + case catch Fun(Doc) of + undefined -> true; + ok -> false; + false -> false; + [_|_] -> true; + {'EXIT', Error} -> couch_log:error("~p", [Error]) + end + end, + Resp = lists:map(MapFunWrapper, Docs), + {State, [true, Resp]}; ddoc(State, {_, Fun}, [<<"shows">>|_], Args) -> Resp = case (catch apply(Fun, Args)) of FunResp when is_list(FunResp) -> -- cgit v1.2.1 From 0377e53ce82c758fe5ee16aa105639fc813a5c77 Mon Sep 17 00:00:00 2001 From: AlexanderKaraberov <3254818+AlexanderKaraberov@users.noreply.github.com> Date: Wed, 20 Jun 2018 17:49:18 +0200 Subject: tests(couch_changes): add tests for changes feed filtering using an Erlang view --- src/couch/test/couch_changes_tests.erl | 38 +++++++++++++++++++++++++++++++++- 1 file changed, 37 insertions(+), 1 deletion(-) diff --git a/src/couch/test/couch_changes_tests.erl b/src/couch/test/couch_changes_tests.erl index 673f2faad..e4ea76167 100644 --- a/src/couch/test/couch_changes_tests.erl +++ b/src/couch/test/couch_changes_tests.erl @@ -47,9 +47,11 @@ setup() -> save_doc(Db1, {[{<<"_id">>, <<"doc7">>}]}), save_doc(Db1, {[{<<"_id">>, <<"doc8">>}]}) ]], + config:set("native_query_servers", "erlang", "{couch_native_process, start_link, []}", _Persist=false), {DbName, list_to_tuple(Revs2)}. teardown({DbName, _}) -> + config:delete("native_query_servers", "erlang", _Persist=false), delete_db(DbName), ok. @@ -153,7 +155,8 @@ filter_by_view() -> fun setup/0, fun teardown/1, [ fun should_filter_by_view/1, - fun should_filter_by_fast_view/1 + fun should_filter_by_fast_view/1, + fun should_filter_by_erlang_view/1 ] } }. @@ -733,6 +736,39 @@ should_filter_by_fast_view({DbName, _}) -> ?assertEqual(UpSeq, ViewUpSeq) end). +should_filter_by_erlang_view({DbName, _}) -> + ?_test( + begin + DDocId = <<"_design/app">>, + DDoc = couch_doc:from_json_obj({[ + {<<"_id">>, DDocId}, + {<<"language">>, <<"erlang">>}, + {<<"views">>, {[ + {<<"valid">>, {[ + {<<"map">>, <<"fun({Doc}) ->" + " case lists:keyfind(<<\"_id\">>, 1, Doc) of" + " {<<\"_id\">>, <<\"doc3\">>} -> Emit(Doc, null); " + " false -> ok" + " end " + "end.">>} + ]}} + ]}} + ]}), + ChArgs = #changes_args{filter = "_view"}, + Req = {json_req, {[{ + <<"query">>, {[ + {<<"view">>, <<"app/valid">>} + ]} + }]}}, + ok = update_ddoc(DbName, DDoc), + {Rows, LastSeq, UpSeq} = run_changes_query(DbName, ChArgs, Req), + ?assertEqual(1, length(Rows)), + [#row{seq = Seq, id = Id}] = Rows, + ?assertEqual(<<"doc3">>, Id), + ?assertEqual(6, Seq), + ?assertEqual(UpSeq, LastSeq) + end). + update_ddoc(DbName, DDoc) -> {ok, Db} = couch_db:open_int(DbName, [?ADMIN_CTX]), {ok, _} = couch_db:update_doc(Db, DDoc, []), -- cgit v1.2.1 From 5bbfbeb707a9dbae93597544b59abc259dae1865 Mon Sep 17 00:00:00 2001 From: Eric Avdey Date: Fri, 29 Jun 2018 18:31:55 -0300 Subject: Don't set context for compaction files during db delete (#1419) When we delete files with context option set to `delete`, `couch_file` respects configuration flag "enable_database_recovery" and just renames the files in case it's set to true. This change removes context for compaction files deleted during database deletion to make sure we are actually erasing them and not just renaming and leaving behind. --- src/couch/src/couch_bt_engine.erl | 4 ++-- src/couch/src/couch_server.erl | 2 +- 2 files changed, 3 insertions(+), 3 deletions(-) diff --git a/src/couch/src/couch_bt_engine.erl b/src/couch/src/couch_bt_engine.erl index 43a77b071..a42d116f8 100644 --- a/src/couch/src/couch_bt_engine.erl +++ b/src/couch/src/couch_bt_engine.erl @@ -114,7 +114,7 @@ delete(RootDir, FilePath, Async) -> %% Delete any leftover compaction files. If we don't do this a %% subsequent request for this DB will try to open them to use %% as a recovery. - delete_compaction_files(RootDir, FilePath, [{context, delete}]), + delete_compaction_files(RootDir, FilePath, [{context, compaction}]), % Delete the actual database file couch_file:delete(RootDir, FilePath, Async). @@ -765,7 +765,7 @@ set_default_security_object(Fd, Header, Compression, Options) -> delete_compaction_files(FilePath) -> RootDir = config:get("couchdb", "database_dir", "."), - DelOpts = [{context, delete}], + DelOpts = [{context, compaction}], delete_compaction_files(RootDir, FilePath, DelOpts). diff --git a/src/couch/src/couch_server.erl b/src/couch/src/couch_server.erl index 903eb09cd..002f08ebb 100644 --- a/src/couch/src/couch_server.erl +++ b/src/couch/src/couch_server.erl @@ -525,7 +525,7 @@ handle_call({delete, DbName, Options}, _From, Server) -> DelOpt = [{context, delete} | Options], % Make sure and remove all compaction data - delete_compaction_files(DbNameList, DelOpt), + delete_compaction_files(DbNameList, Options), {ok, {Engine, FilePath}} = get_engine(Server, DbNameList), RootDir = Server#server.root_dir, -- cgit v1.2.1 From 73f15655d46bf9bb4b47e363379c9e2fe030dd26 Mon Sep 17 00:00:00 2001 From: Jan Lehnardt Date: Wed, 16 May 2018 18:44:16 +0200 Subject: remove mention of os daemons and externals in ini files --- rel/overlay/etc/default.ini | 24 +----------------------- rel/overlay/etc/local.ini | 14 -------------- 2 files changed, 1 insertion(+), 37 deletions(-) diff --git a/rel/overlay/etc/default.ini b/rel/overlay/etc/default.ini index 8b47cb04a..5f77e7b5d 100644 --- a/rel/overlay/etc/default.ini +++ b/rel/overlay/etc/default.ini @@ -8,7 +8,7 @@ database_dir = {{data_dir}} view_index_dir = {{view_index_dir}} ; util_driver_dir = ; plugin_dir = -os_process_timeout = 5000 ; 5 seconds. for view and external servers. +os_process_timeout = 5000 ; 5 seconds. for view servers. max_dbs_open = 500 delayed_commits = false ; Method used to compress everything that is appended to database and view index files, except @@ -277,7 +277,6 @@ os_process_limit = 100 [daemons] index_server={couch_index_server, start_link, []} -external_manager={couch_external_manager, start_link, []} query_servers={couch_proc_manager, start_link, []} vhosts={couch_httpd_vhost, start_link, []} httpd={couch_httpd, start_link, []} @@ -322,12 +321,6 @@ _design = {couch_httpd_db, handle_design_req} _temp_view = {couch_mrview_http, handle_temp_view_req} _view_cleanup = {couch_mrview_http, handle_cleanup_req} -; The external module takes an optional argument allowing you to narrow it to a -; single script. Otherwise the script name is inferred from the first path section -; after _external's own path. -; _mypath = {couch_httpd_external, handle_external_req, <<"mykey">>} -; _external = {couch_httpd_external, handle_external_req} - [httpd_design_handlers] _compact = {couch_mrview_http, handle_compact_req} _info = {couch_mrview_http, handle_info_req} @@ -338,21 +331,6 @@ _update = {couch_mrview_show, handle_doc_update_req} _view = {couch_mrview_http, handle_view_req} _view_changes = {couch_mrview_http, handle_view_changes_req} -; enable external as an httpd handler, then link it with commands here. -; note, this api is still under consideration. -; [external] -; mykey = /path/to/mycommand - -; Here you can setup commands for CouchDB to manage -; while it is alive. It will attempt to keep each command -; alive if it exits. -; [os_daemons] -; some_daemon_name = /path/to/script -with args -; [os_daemon_settings] -; max_retries = 3 -; retry_time = 5 - - [uuids] ; Known algorithms: ; random - 128 bits of random awesome diff --git a/rel/overlay/etc/local.ini b/rel/overlay/etc/local.ini index 6b46f0fa1..e3b7b1502 100644 --- a/rel/overlay/etc/local.ini +++ b/rel/overlay/etc/local.ini @@ -46,23 +46,12 @@ [query_servers] ;nodejs = /usr/local/bin/couchjs-node /path/to/couchdb/share/server/main.js - -[httpd_global_handlers] -;_google = {couch_httpd_proxy, handle_proxy_req, <<"http://www.google.com">>} - [couch_httpd_auth] ; If you set this to true, you should also uncomment the WWW-Authenticate line ; above. If you don't configure a WWW-Authenticate header, CouchDB will send ; Basic realm="server" in order to prevent you getting logged out. ; require_valid_user = false -[os_daemons] -; For any commands listed here, CouchDB will attempt to ensure that -; the process remains alive. Daemons should monitor their environment -; to know when to exit. This can most easily be accomplished by exiting -; when stdin is closed. -;foo = /path/to/command -with args - [daemons] ; enable SSL support by uncommenting the following line and supply the PEM's below. ; the default ssl port CouchDB listens on is 6984 @@ -103,9 +92,6 @@ [vhosts] ;example.com = /database/ -[update_notification] -;unique notifier name=/full/path/to/exe -with "cmd line arg" - ; To create an admin account uncomment the '[admins]' section below and add a ; line in the format 'username = password'. When you next start CouchDB, it ; will change the password to a hash (so that your passwords don't linger -- cgit v1.2.1