1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
|
defmodule ViewCompactionTest do
use CouchTestCase
@moduledoc """
Test CouchDB View Compaction Behavior
This is a port of the view_compaction.js suite
"""
@num_docs 1000
@ddoc %{
_id: "_design/foo",
language: "javascript",
views: %{
view1: %{
map: "function(doc) { emit(doc._id, doc.value) }"
},
view2: %{
map:
"function(doc) { if (typeof(doc.integer) === 'number') {emit(doc._id, doc.integer);} }",
reduce: "function(keys, values, rereduce) { return sum(values); }"
}
}
}
defp bulk_save_for_update(db_name, docs) do
resp = bulk_save(db_name, docs)
revs = resp.body
Enum.map(docs, fn m ->
rev = Enum.at(revs, String.to_integer(m["_id"]))["rev"]
m
|> Map.put("_rev", rev)
|> Map.update!("integer", &(&1 + 1))
end)
end
@tag :with_db
test "view compaction", context do
db_name = context[:db_name]
create_doc(db_name, @ddoc)
docs = make_docs(0..(@num_docs - 1))
docs = bulk_save_for_update(db_name, docs)
resp = view(db_name, "foo/view1")
assert length(resp.body["rows"]) == @num_docs
resp = view(db_name, "foo/view2")
assert length(resp.body["rows"]) == 1
resp = Couch.get("/#{db_name}/_design/foo/_info")
assert resp.body["view_index"]["update_seq"] == @num_docs + 1
docs = bulk_save_for_update(db_name, docs)
resp = view(db_name, "foo/view1")
assert length(resp.body["rows"]) == @num_docs
resp = view(db_name, "foo/view2")
assert length(resp.body["rows"]) == 1
resp = Couch.get("/#{db_name}/_design/foo/_info")
assert resp.body["view_index"]["update_seq"] == 2 * @num_docs + 1
bulk_save(db_name, docs)
resp = view(db_name, "foo/view1")
assert length(resp.body["rows"]) == @num_docs
resp = view(db_name, "foo/view2")
assert length(resp.body["rows"]) == 1
resp = Couch.get("/#{db_name}/_design/foo/_info")
assert resp.body["view_index"]["update_seq"] == 3 * @num_docs + 1
disk_size_before_compact = resp.body["view_index"]["sizes"]["file"]
data_size_before_compact = resp.body["view_index"]["sizes"]["active"]
assert is_integer(disk_size_before_compact)
assert data_size_before_compact < disk_size_before_compact
resp = Couch.post("/#{db_name}/_compact/foo")
assert resp.body["ok"] == true
retry_until(fn ->
resp = Couch.get("/#{db_name}/_design/foo/_info")
resp.body["view_index"]["compact_running"] == false
end)
resp = view(db_name, "foo/view1")
assert length(resp.body["rows"]) == @num_docs
resp = view(db_name, "foo/view2")
assert length(resp.body["rows"]) == 1
resp = Couch.get("/#{db_name}/_design/foo/_info")
assert resp.body["view_index"]["update_seq"] == 3 * @num_docs + 1
disk_size_after_compact = resp.body["view_index"]["sizes"]["file"]
data_size_after_compact = resp.body["view_index"]["sizes"]["active"]
assert disk_size_after_compact < disk_size_before_compact
assert is_integer(data_size_after_compact)
assert data_size_after_compact < disk_size_after_compact
end
end
|