Skip to content

Commit df1265a

Browse files
committed
add scanner to upgrade nouveau indexes
1 parent f25dfa5 commit df1265a

File tree

3 files changed

+148
-3
lines changed

3 files changed

+148
-3
lines changed

rel/overlay/etc/default.ini

Lines changed: 7 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1021,6 +1021,7 @@ url = {{nouveau_url}}
10211021
;couch_scanner_plugin_find = false
10221022
;couch_scanner_plugin_conflict_finder = false
10231023
;couch_quickjs_scanner_plugin = false
1024+
;nouveau_index_upgrader = false
10241025

10251026
; The following [$plugin*] settings apply to all plugins
10261027

@@ -1127,6 +1128,12 @@ url = {{nouveau_url}}
11271128
; Scanner settings to skip dbs and docs would also work:
11281129
;[couch_quickjs_scanner_plugin.skip_{dbs,ddoc,docs}]
11291130

1131+
[nouveau_index_upgrader]
1132+
; Common scanner scheduling settings
1133+
;after = restart
1134+
;repeat = restart
1135+
1136+
11301137
[chttpd_auth_lockout]
11311138
; CouchDB can temporarily lock out IP addresses that repeatedly fail authentication
11321139
; mode can be set to one of three recognised values;

src/nouveau/src/nouveau_fabric_search.erl

Lines changed: 3 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -15,7 +15,7 @@
1515

1616
-module(nouveau_fabric_search).
1717

18-
-export([go/4]).
18+
-export([go/3, go/4]).
1919

2020
-include_lib("mem3/include/mem3.hrl").
2121
-include_lib("couch/include/couch_db.hrl").
@@ -38,12 +38,12 @@ go(DbName, GroupId, IndexName, QueryArgs0) when is_binary(GroupId) ->
3838
go(DbName, #doc{} = DDoc, IndexName, QueryArgs0) ->
3939
case nouveau_util:design_doc_to_index(DbName, DDoc, IndexName) of
4040
{ok, Index} ->
41-
go(DbName, DDoc, IndexName, QueryArgs0, Index);
41+
go(DbName, QueryArgs0, Index);
4242
{error, Reason} ->
4343
{error, Reason}
4444
end.
4545

46-
go(DbName, #doc{} = _DDoc, _IndexName, QueryArgs0, Index) ->
46+
go(DbName, QueryArgs0, Index) ->
4747
Shards = get_shards(DbName, QueryArgs0),
4848
{PackedBookmark, #{limit := Limit, sort := Sort} = QueryArgs1} =
4949
maps:take(bookmark, QueryArgs0),
Lines changed: 138 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,138 @@
1+
% Licensed under the Apache License, Version 2.0 (the "License"); you may not
2+
% use this file except in compliance with the License. You may obtain a copy of
3+
% the License at
4+
%
5+
% http://www.apache.org/licenses/LICENSE-2.0
6+
%
7+
% Unless required by applicable law or agreed to in writing, software
8+
% distributed under the License is distributed on an "AS IS" BASIS, WITHOUT
9+
% WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the
10+
% License for the specific language governing permissions and limitations under
11+
% the License.
12+
13+
-module(nouveau_index_upgrader).
14+
-behaviour(couch_scanner_plugin).
15+
16+
-export([
17+
start/2,
18+
resume/2,
19+
complete/1,
20+
checkpoint/1,
21+
db/2,
22+
ddoc/3
23+
]).
24+
25+
-include("nouveau.hrl").
26+
-include_lib("couch_scanner/include/couch_scanner_plugin.hrl").
27+
28+
start(ScanId, #{}) ->
29+
St = init_config(ScanId),
30+
case should_run() of
31+
true ->
32+
?INFO("Starting.", [], St),
33+
{ok, St};
34+
false ->
35+
?INFO("Not starting.", [], St),
36+
skip
37+
end.
38+
39+
resume(ScanId, #{}) ->
40+
St = init_config(ScanId),
41+
case should_run() of
42+
true ->
43+
?INFO("Resuming.", [], St),
44+
{ok, St};
45+
false ->
46+
?INFO("Not resuming.", [], St),
47+
skip
48+
end.
49+
50+
complete(St) ->
51+
?INFO("Completed", [], St),
52+
{ok, #{}}.
53+
54+
checkpoint(_St) ->
55+
{ok, #{}}.
56+
57+
db(St, _DbName) ->
58+
{ok, St}.
59+
60+
ddoc(St, _DbName, #doc{id = <<"_design/_", _/binary>>}) ->
61+
{ok, St};
62+
ddoc(St, DbName, #doc{} = DDoc0) ->
63+
case update_ddoc_versions(DDoc0) of
64+
DDoc0 ->
65+
ok;
66+
DDoc1 ->
67+
Indexes = nouveau_util:design_doc_to_indexes(DbName, DDoc1),
68+
case upgrade_indexes(DbName, Indexes) of
69+
true ->
70+
save_ddoc(DbName, DDoc1);
71+
false ->
72+
ok
73+
end
74+
end,
75+
{ok, St}.
76+
77+
upgrade_indexes(_DbName, []) ->
78+
true;
79+
upgrade_indexes(DbName, [Index | Rest]) ->
80+
case upgrade_index(DbName, Index) of
81+
true ->
82+
upgrade_indexes(DbName, Rest);
83+
false ->
84+
false
85+
end.
86+
87+
upgrade_index(DbName, #index{} = Index) ->
88+
?INFO("Upgrading ~s/~s to version ~B", [
89+
DbName,
90+
Index#index.name,
91+
?TARGET_LUCENE_VERSION
92+
]),
93+
case
94+
nouveau_fabric_search:go(
95+
DbName,
96+
#{query => <<"*:*">>, bookmark => null, sort => null, limit => 1},
97+
Index#index{lucene_version = ?TARGET_LUCENE_VERSION}
98+
)
99+
of
100+
{ok, _SearchResults} ->
101+
true;
102+
{error, _Reason} ->
103+
false
104+
end.
105+
106+
update_ddoc_versions(#doc{} = Doc) ->
107+
#doc{body = {Fields0}} = Doc,
108+
{Indexes0} = couch_util:get_value(<<"nouveau">>, Fields0),
109+
Indexes1 = lists:map(fun update_version/1, Indexes0),
110+
Fields1 = couch_util:set_value(<<"nouveau">>, Fields0, {Indexes1}),
111+
Doc#doc{body = {Fields1}}.
112+
113+
save_ddoc(DbName, #doc{} = DDoc) ->
114+
{Pid, Ref} = spawn_monitor(fun() ->
115+
case fabric:update_doc(DbName, DDoc, [?ADMIN_CTX]) of
116+
{ok, _} ->
117+
exit(ok);
118+
Else ->
119+
exit(Else)
120+
end
121+
end),
122+
receive
123+
{'DOWN', Ref, process, Pid, ok} ->
124+
?INFO(
125+
"Updated ~s/~s indexes to version ~B", [DbName, DDoc#doc.id, ?TARGET_LUCENE_VERSION]
126+
);
127+
{'DOWN', Ref, process, Pid, Else} ->
128+
?INFO("Failed to update ~s/~s for reason ~p", [DbName, DDoc#doc.id, Else])
129+
end.
130+
131+
update_version({IndexName, {Index}}) ->
132+
{IndexName, {couch_util:set_value(<<"lucene_version">>, Index, ?TARGET_LUCENE_VERSION)}}.
133+
134+
init_config(ScanId) ->
135+
#{sid => ScanId}.
136+
137+
should_run() ->
138+
couch_scanner_util:on_first_node().

0 commit comments

Comments
 (0)