diff options
author | Jan Lehnardt <jan@apache.org> | 2018-09-14 10:42:02 +0200 |
---|---|---|
committer | Jan Lehnardt <jan@apache.org> | 2018-11-09 09:57:11 +0100 |
commit | 1cfe6222e8d29672111d207f23fb295ee0286cec (patch) | |
tree | 431f999dcd9a7739d003c8d00a3c9708f9115836 | |
parent | 28f2f780ffa01d12ed554c2883e69e47bee6bd17 (diff) | |
download | couchdb-1cfe6222e8d29672111d207f23fb295ee0286cec.tar.gz |
feat: move [native_]query_server & os_daemons setup out of runtime config
CouchDB ships with two default query_servers (javascript and coffeescript)
as well as one default native_query_server (query aka mango). These used
to be configured in default.ini in these sections:
```
[query_servers]
javascript = {{prefix}}/bin/couchjs {{prefix}}/share/server/main.js
coffeescript = {{prefix}}/bin/couchjs {{prefix}}/share/server/main-coffee.js
; enable mango query engine
[native_query_servers]
query = {mango_native_proc, start_link, []}
; erlang query server
; erlang = {couch_native_process, start_link, []}
```
This allowed end-users post-install and even runtime-changes to which
query servers are enabled and where their binaries live.
This patch changes things, so only a post-install, but not at-runtime
changes are possible from now on.
This still allows people to configure their CouchDB to run a third-
party query server like the somewhat popular Python query server,
but it changes the way the setup is done.
Query Servers
The javascript and coffeescript query servers continue to be enabled
by default. Setup differences have been moved from default.ini to
the couchdb and couchdb.cmd start scripts respectively.
Additional query servers can now be configured using environment
variables:
```
export COUCHDB_QUERY_SERVER_PYTHON="/path/to/python/query/server.py with args"
couchdb
```
Where the last segment in the environment variable matches the usual
lowercase(!) query language in the design doc `language` field.
Multiple query servers can be configured by using more environment
variables.
Native Query Servers
The mango query server continues to be enabled by default. The erlang
query server continues to be disabled by default. This patch adds
a `[native_query_servers] enable_erlang_query_server = BOOL` setting
(defaults to `"false"`) to enable the erlang query server.
If the legacy configuration for enabling the query server is detected,
that is counted as a `true` setting as well, so existing configurations
continue to work just fine.
Windows
Since the setting of the `./configure` time `PREFIX` happens during
`make release`, I had to adapt the `couchdb` and `couchdb.cmd` scripts
to have the correct env vars set and the `PREFIX` replaced there.
I did this to the best of my abilities and research, but this needs
review from the Windows team (Hi Joan! :).
OS Daemons
Although deprecated in 2.2.0, we’re keeping support for this until 3.x,
but the configuration changes analogous to query servers.
Previously, configuration looked like this:
```
[os_daemons]
name = /path/to/daemon with args
```
With this patch, setup looks like this:
```
COUCHDB_OS_DAEMON_NAME="/path/to/daemon with args"
couchdb
```
Multiple OS Daemons can be started with multiple env vars. The final
segment in the env var becomes the daemon identifier inside CouchDB
as lowercase(!).
-rwxr-xr-x | dev/run | 24 | ||||
-rw-r--r-- | rel/files/couchdb.cmd.in (renamed from rel/overlay/bin/couchdb.cmd) | 3 | ||||
-rwxr-xr-x | rel/files/couchdb.in (renamed from rel/overlay/bin/couchdb) | 4 | ||||
-rw-r--r-- | rel/overlay/etc/default.ini | 8 | ||||
-rw-r--r-- | rel/reltool.config | 4 | ||||
-rw-r--r-- | src/couch/src/couch_os_daemons.erl | 21 | ||||
-rw-r--r-- | src/couch/src/couch_proc_manager.erl | 52 |
7 files changed, 91 insertions, 25 deletions
@@ -273,16 +273,6 @@ def boot_haproxy(ctx): def hack_default_ini(ctx, node, contents): - # Replace couchjs command - couchjs = os.path.join(ctx['rootdir'], "src", "couch", "priv", "couchjs") - mainjs = os.path.join(ctx['rootdir'], "share", "server", "main.js") - coffeejs = os.path.join(ctx['rootdir'], "share", "server", "main-coffee.js") - - repl = toposixpath("javascript = %s %s" % (couchjs, mainjs)) - contents = re.sub("(?m)^javascript.*$", repl, contents) - - repl = toposixpath("coffeescript = %s %s" % (couchjs, coffeejs)) - contents = re.sub("(?m)^coffeescript.*$", repl, contents) if ctx['enable_erlang_views']: contents = re.sub( @@ -413,15 +403,29 @@ def check_node_alive(url): if error is not None: raise error +def set_boot_env(ctx): + + # fudge default query server paths + couchjs = os.path.join(ctx['rootdir'], "src", "couch", "priv", "couchjs") + mainjs = os.path.join(ctx['rootdir'], "share", "server", "main.js") + coffeejs = os.path.join(ctx['rootdir'], "share", "server", "main-coffee.js") + + qs_javascript = toposixpath("%s %s" % (couchjs, mainjs)) + qs_coffescript = toposixpath("%s %s" % (couchjs, coffeejs)) + + os.environ['COUCHDB_QUERY_SERVER_JAVASCRIPT'] = qs_javascript + os.environ['COUCHDB_QUERY_SERVER_COFFEESCRIPT'] = qs_coffescript @log('Start node {node}') def boot_node(ctx, node): erl_libs = os.path.join(ctx['rootdir'], "src") + set_boot_env(ctx) env = os.environ.copy() env["ERL_LIBS"] = os.pathsep.join([erl_libs]) node_etcdir = os.path.join(ctx['devdir'], "lib", node, "etc") reldir = os.path.join(ctx['rootdir'], "rel") + cmd = [ "erl", "-args_file", os.path.join(node_etcdir, "vm.args"), diff --git a/rel/overlay/bin/couchdb.cmd b/rel/files/couchdb.cmd.in index 5e5f2cfe6..9438872c6 100644 --- a/rel/overlay/bin/couchdb.cmd +++ b/rel/files/couchdb.cmd.in @@ -25,6 +25,9 @@ set EMU=beam set PROGNAME=%~n0 set PATH=%PATH%;%COUCHDB_BIN_DIR% +set COUCHDB_QUERY_SERVER_JAVASCRIPT="{{prefix}}/bin/couchjs {{prefix}}/share/server/main.js" +set COUCHDB_QUERY_SERVER_COFFEESCRIPT="{{prefix}}/bin/couchjs {{prefix}}/share/server/main-coffee.js" + "%BINDIR%\erl" -boot "%ROOTDIR%\releases\%APP_VSN%\couchdb" ^ -args_file "%ROOTDIR%\etc\vm.args" ^ -config "%ROOTDIR%\releases\%APP_VSN%\sys.config" %* diff --git a/rel/overlay/bin/couchdb b/rel/files/couchdb.in index a9e6e9bea..aae179aa7 100755 --- a/rel/overlay/bin/couchdb +++ b/rel/files/couchdb.in @@ -26,10 +26,12 @@ export BINDIR="$ROOTDIR/erts-$ERTS_VSN/bin" export EMU=beam export PROGNAME=`echo $0 | sed 's/.*\///'` +export COUCHDB_QUERY_SERVER_JAVASCRIPT="{{prefix}}/bin/couchjs {{prefix}}/share/server/main.js" +export COUCHDB_QUERY_SERVER_COFFEESCRIPT="{{prefix}}/bin/couchjs {{prefix}}/share/server/main-coffee.js" + ARGS_FILE="${COUCHDB_ARGS_FILE:-$ROOTDIR/etc/vm.args}" SYSCONFIG_FILE="${COUCHDB_SYSCONFIG_FILE:-$ROOTDIR/releases/$APP_VSN/sys.config}" exec "$BINDIR/erlexec" -boot "$ROOTDIR/releases/$APP_VSN/couchdb" \ -args_file "${ARGS_FILE}" \ -config "${SYSCONFIG_FILE}" "$@" - diff --git a/rel/overlay/etc/default.ini b/rel/overlay/etc/default.ini index 215d7eabe..f384de3aa 100644 --- a/rel/overlay/etc/default.ini +++ b/rel/overlay/etc/default.ini @@ -260,13 +260,9 @@ credentials = false ; List of hosts separated by a comma. * means accept all ; hosts = -[query_servers] -javascript = {{prefix}}/bin/couchjs {{prefix}}/share/server/main.js -coffeescript = {{prefix}}/bin/couchjs {{prefix}}/share/server/main-coffee.js - -; enable mango query engine [native_query_servers] -query = {mango_native_proc, start_link, []} +; erlang query server +; enable_erlang_query_server = false ; Changing reduce_limit to false will disable reduce_limit. ; If you think you're hitting reduce_limit with a "good" reduce function, diff --git a/rel/reltool.config b/rel/reltool.config index 2c55d0900..bf4ae448b 100644 --- a/rel/reltool.config +++ b/rel/reltool.config @@ -125,5 +125,7 @@ {copy, "files/sys.config", "releases/\{\{rel_vsn\}\}/sys.config"}, {copy, "files/vm.args", "releases/\{\{rel_vsn\}\}/vm.args"}, {template, "overlay/etc/default.ini", "etc/default.ini"}, - {template, "overlay/etc/vm.args", "etc/vm.args"} + {template, "overlay/etc/vm.args", "etc/vm.args"}, + {template, "files/couchdb.in", "bin/couchdb"}, + {template, "files/couchdb.cmd.in", "bin/couchdb.cmd"} ]}. diff --git a/src/couch/src/couch_os_daemons.erl b/src/couch/src/couch_os_daemons.erl index cd019dbb5..2427d67ab 100644 --- a/src/couch/src/couch_os_daemons.erl +++ b/src/couch/src/couch_os_daemons.erl @@ -72,10 +72,6 @@ handle_call(Msg, From, Table) -> handle_cast({config_change, Sect, Key}, Table) -> restart_daemons(Table, Sect, Key), - case Sect of - "os_daemons" -> reload_daemons(Table); - _ -> ok - end, {noreply, Table}; handle_cast(stop, Table) -> {stop, normal, Table}; @@ -288,9 +284,24 @@ handle_log_message(Name, Msg, Level) -> % Daemon management helpers % +get_daemons() -> + % map all COUCHDB_OS_DAEMON_* vars out of os:getenv + lists:filtermap(fun(Var) -> + case string:split(Var, "=") of + [VarName, Cmd] -> + case string:find(VarName, "COUCHDB_OS_DAEMON_") of + nomatch -> + false; + "COUCHDB_OS_DAEMON_" ++ Name -> + {true, {string:lowercase(Name), Cmd}} + end; + _Else -> false + end + end, os:getenv()). + reload_daemons(Table) -> % List of daemons we want to have running. - Configured = lists:sort(config:get("os_daemons")), + Configured = lists:sort(get_daemons()), % Remove records for daemons that were halted. MSpecHalted = #daemon{name='$1', cmd='$2', status=halted, _='_'}, diff --git a/src/couch/src/couch_proc_manager.erl b/src/couch/src/couch_proc_manager.erl index 04101f240..b6639288f 100644 --- a/src/couch/src/couch_proc_manager.erl +++ b/src/couch/src/couch_proc_manager.erl @@ -372,12 +372,60 @@ new_proc(Client) -> end, exit(Resp). +get_env_for_spec(Spec, Target) -> + % loop over os:getenv(), match SPEC_TARGET + lists:filtermap(fun(VarName) -> + SpecStr = Spec ++ Target, + case string:split(VarName, "=") of + [SpecStr, Cmd] -> {true, Cmd}; + _Else -> false + end + end, os:getenv()). + +get_query_server(LangStr) -> + % look for COUCH_QUERY_SERVER_LANGSTR in env + % if exists, return value, else undefined + UpperLangString = string:uppercase(LangStr), + case get_env_for_spec("COUCHDB_QUERY_SERVER_", UpperLangString) of + [] -> undefined; + [Command] -> Command + end. + +native_query_server_enabled() -> + % 1. [native_query_server] enable_erlang_query_server = true | false + % 2. if [native_query_server] erlang == {couch_native_process, start_link, []} -> pretend true as well + NativeEnabled = config:get_boolean("native_query_server", "enable_erlang_query_server", false), + NativeLegacyConfig = config:get("native_query_server", "erlang", ""), + NativeLegacyEnabled = NativeLegacyConfig =:= "{couch_native_process, start_link, []}", + + % there surely is a more elegant way to do this that eludes me at present + case {NativeEnabled, NativeLegacyEnabled} of + {true, true} -> true; + {true, _} -> true; + {_, true} -> true; + _ -> false + end. + +get_native_query_server("query") -> % mango query server + "{mango_native_proc, start_link, []}"; +get_native_query_server("erlang") -> % erlang query server + case native_query_server_enabled() of + true -> "{couch_native_process, start_link, []}"; + _Else -> undefined + end; +get_native_query_server(LangStr) -> + % same as above, but COUCH_NATIVE_QUERY_SERVER_LANGSTR + UpperLangString = string:uppercase(LangStr), + case get_env_for_spec("COUCHDB_NATIVE_QUERY_SERVER_", UpperLangString) of + [] -> undefined; + [Command] -> Command + end. new_proc_int(From, Lang) when is_binary(Lang) -> LangStr = binary_to_list(Lang), - case config:get("query_servers", LangStr) of + case get_query_server(LangStr) of undefined -> - case config:get("native_query_servers", LangStr) of + case get_native_query_server(LangStr) of undefined -> gen_server:reply(From, {unknown_query_language, Lang}); SpecStr -> |