reslop 0.1.9 → 0.2.1
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/CHANGELOG.md +25 -1
- package/README.md +3 -1
- package/bin/reslop.js +2 -2
- package/lib/ansi.js +148 -5
- package/lib/api.js +4 -2
- package/lib/capabilities.js +13 -14
- package/lib/cli.js +38 -49
- package/lib/clipboard.js +1 -1
- package/lib/{deps/changes.js → deps-diff.js} +309 -19
- package/lib/deps.js +498 -29
- package/lib/detect.js +1 -7
- package/lib/diff/align.js +7 -10
- package/lib/diff/diff.js +53 -0
- package/lib/diff/display.js +5 -4
- package/lib/diff/inline.js +26 -21
- package/lib/diff/items.js +6 -4
- package/lib/diff/patch.js +1 -3
- package/lib/diff/unit.js +392 -0
- package/lib/files.js +5 -8
- package/lib/{git/branches.js → git-branches.js} +191 -11
- package/lib/{git/dependencies.js → git-deps.js} +111 -38
- package/lib/git-reword-todo.js +20 -0
- package/lib/git.js +606 -68
- package/lib/github.js +28 -197
- package/lib/gitlab.js +24 -195
- package/lib/highlight/bash.js +1 -3
- package/lib/highlight/css.js +1 -3
- package/lib/highlight/js.js +11 -14
- package/lib/highlight.js +6 -9
- package/lib/keys.js +14 -8
- package/lib/manifest.js +330 -0
- package/lib/remote.js +374 -0
- package/lib/render/branches.js +18 -100
- package/lib/render/chrome.js +71 -14
- package/lib/render/commits.js +69 -60
- package/lib/render/diff.js +20 -20
- package/lib/render/files.js +6 -34
- package/lib/render/frame.js +36 -13
- package/lib/render/notes.js +26 -8
- package/lib/render/primitives.js +99 -11
- package/lib/{render.js → render/render.js} +8 -8
- package/lib/render/unit.js +41 -0
- package/lib/review-merge.js +270 -0
- package/lib/review.js +782 -14
- package/lib/select.js +5 -10
- package/lib/session/accessors.js +9 -1
- package/lib/session/actions.js +61 -18
- package/lib/session/branches.js +116 -128
- package/lib/session/change-actions.js +202 -123
- package/lib/session/commit.js +201 -115
- package/lib/session/compose.js +181 -15
- package/lib/session/dispatch.js +110 -60
- package/lib/session/files-pane.js +156 -148
- package/lib/session/items.js +22 -30
- package/lib/session/lifecycle.js +151 -54
- package/lib/session/load.js +19 -33
- package/lib/session/navigation.js +12 -1
- package/lib/session/ops.js +28 -41
- package/lib/session/pointer.js +57 -57
- package/lib/session/review.js +23 -37
- package/lib/session/terminal.js +6 -12
- package/lib/session/todos.js +37 -13
- package/lib/session/unit.js +208 -0
- package/lib/session/update.js +33 -46
- package/lib/session/view.js +78 -9
- package/lib/session/watch.js +128 -24
- package/lib/session.js +22 -246
- package/lib/source.js +3 -3
- package/lib/update.js +40 -75
- package/lib/{git/proc.js → utilities.js} +75 -11
- package/lib/wrap.js +1 -3
- package/package.json +2 -2
- package/lib/deps/items.js +0 -134
- package/lib/deps/manifest.js +0 -152
- package/lib/deps/merge.js +0 -120
- package/lib/deps/proposals.js +0 -164
- package/lib/deps/reports.js +0 -180
- package/lib/deps/rows.js +0 -176
- package/lib/deps/scan.js +0 -138
- package/lib/deps/usage.js +0 -68
- package/lib/deps/versions.js +0 -119
- package/lib/diff.js +0 -33
- package/lib/git/changes.js +0 -164
- package/lib/git/read.js +0 -253
- package/lib/git/run.js +0 -100
- package/lib/npm/commands.js +0 -100
- package/lib/remote/changes.js +0 -37
- package/lib/remote/headers.js +0 -36
- package/lib/remote/http.js +0 -122
- package/lib/remote/notes.js +0 -94
- package/lib/review/format.js +0 -434
- package/lib/review/storage.js +0 -150
- package/lib/review/store.js +0 -178
- package/lib/review/templates.js +0 -49
- package/lib/session/origins.js +0 -7
- package/lib/sys.js +0 -84
|
@@ -1,148 +1,154 @@
|
|
|
1
1
|
'use strict';
|
|
2
2
|
|
|
3
|
+
const ansi = require('../ansi.js');
|
|
3
4
|
const files = require('../files.js');
|
|
5
|
+
const { THEME_NAMES, setTheme, themeName } = ansi;
|
|
4
6
|
const { isTodosEntry, TODO_FILE } = files;
|
|
7
|
+
const unit = require('./unit.js');
|
|
8
|
+
const { setFileScope, openUnitFile, moveUnitBlock } = unit;
|
|
5
9
|
|
|
6
10
|
const LAYOUTS = ['unified', 'mixed', 'side'];
|
|
7
11
|
|
|
8
|
-
const current = (
|
|
9
|
-
options.nav.current(options.items(), options.todoItem());
|
|
12
|
+
const current = (ui) => ui.nav.current(ui.items, ui.todoItem);
|
|
10
13
|
|
|
11
|
-
const clampIndex = (
|
|
14
|
+
const clampIndex = (ui) => ui.nav.clampIndex(ui.items.length);
|
|
12
15
|
|
|
13
|
-
const syncReviewPath = (
|
|
14
|
-
options.nav.syncReviewPath(current(options));
|
|
16
|
+
const syncReviewPath = (ui) => ui.nav.syncReviewPath(current(ui));
|
|
15
17
|
|
|
16
|
-
const clampFileCursor = (
|
|
17
|
-
options.nav.clampFileCursor(options.fileList().length);
|
|
18
|
+
const clampFileCursor = (ui) => ui.nav.clampFileCursor(ui.fileList().length);
|
|
18
19
|
|
|
19
|
-
const followReviewPath = (
|
|
20
|
-
|
|
20
|
+
const followReviewPath = (ui) =>
|
|
21
|
+
ui.nav.followReviewPath(ui.fileList(), current(ui));
|
|
21
22
|
|
|
22
|
-
const syncFileCursor = (
|
|
23
|
-
if (
|
|
24
|
-
|
|
25
|
-
return;
|
|
26
|
-
}
|
|
27
|
-
followReviewPath(options);
|
|
23
|
+
const syncFileCursor = (ui) => {
|
|
24
|
+
if (ui.nav.pane === 'files') return void clampFileCursor(ui);
|
|
25
|
+
followReviewPath(ui);
|
|
28
26
|
};
|
|
29
27
|
|
|
30
|
-
const showFiles = (
|
|
31
|
-
|
|
32
|
-
|
|
33
|
-
|
|
34
|
-
|
|
28
|
+
const showFiles = (ui) => {
|
|
29
|
+
const nav = ui.nav;
|
|
30
|
+
const held =
|
|
31
|
+
nav.todoOpen === true || nav.pane === 'branches' || nav.pane === 'commits';
|
|
32
|
+
nav.pane = 'files';
|
|
33
|
+
nav.clearSelection();
|
|
34
|
+
followReviewPath(ui);
|
|
35
|
+
nav.todoOpen = false;
|
|
36
|
+
if (held) ui.lifecycle.catchUpWatch();
|
|
35
37
|
};
|
|
36
38
|
|
|
37
|
-
const onEscape = (
|
|
38
|
-
if (
|
|
39
|
-
showFiles(
|
|
40
|
-
return;
|
|
41
|
-
}
|
|
42
|
-
if (options.nav.pane === 'files') {
|
|
43
|
-
options.onQuit();
|
|
44
|
-
return;
|
|
39
|
+
const onEscape = (ui) => {
|
|
40
|
+
if (ui.nav.pane === 'branches' || ui.nav.pane === 'commits') {
|
|
41
|
+
return void showFiles(ui);
|
|
45
42
|
}
|
|
46
|
-
|
|
43
|
+
if (ui.nav.pane === 'files') return void ui.onQuit();
|
|
44
|
+
showFiles(ui);
|
|
47
45
|
};
|
|
48
46
|
|
|
49
|
-
const onFiles = (
|
|
50
|
-
if (
|
|
51
|
-
if (!
|
|
52
|
-
|
|
53
|
-
|
|
54
|
-
|
|
47
|
+
const onFiles = (ui) => {
|
|
48
|
+
if (ui.nav.pane === 'files') {
|
|
49
|
+
if (!ui.nav.reviewPath) return;
|
|
50
|
+
if (ui.nav.fileScope === 'file') {
|
|
51
|
+
const list = ui.fileList();
|
|
52
|
+
const entry = list[ui.nav.fileCursor];
|
|
53
|
+
if (entry && !isTodosEntry(entry)) openUnitFile(ui, entry);
|
|
54
|
+
return;
|
|
55
|
+
}
|
|
56
|
+
ui.nav.pane = 'diff';
|
|
57
|
+
ui.nav.clearSelection();
|
|
58
|
+
if (ui.nav.reviewPath === TODO_FILE) ui.composer.openTodoPage();
|
|
55
59
|
return;
|
|
56
60
|
}
|
|
57
|
-
showFiles(
|
|
61
|
+
showFiles(ui);
|
|
58
62
|
};
|
|
59
63
|
|
|
60
|
-
const onOpenFile = (
|
|
61
|
-
if (
|
|
62
|
-
return void
|
|
64
|
+
const onOpenFile = (ui) => {
|
|
65
|
+
if (ui.nav.pane === 'branches') {
|
|
66
|
+
return void ui.gitBranches.onCheckoutBranch();
|
|
63
67
|
}
|
|
64
|
-
if (
|
|
65
|
-
if (
|
|
66
|
-
if (
|
|
68
|
+
if (ui.nav.pane === 'commits') return;
|
|
69
|
+
if (ui.nav.pane !== 'files') {
|
|
70
|
+
if (ui.nav.todoOpen) ui.composer.editFocusedTodo();
|
|
67
71
|
return;
|
|
68
72
|
}
|
|
69
|
-
const list =
|
|
70
|
-
const entry = list[
|
|
73
|
+
const list = ui.fileList();
|
|
74
|
+
const entry = list[ui.nav.fileCursor];
|
|
71
75
|
if (!entry) return;
|
|
72
76
|
if (isTodosEntry(entry)) {
|
|
73
|
-
|
|
74
|
-
|
|
77
|
+
ui.composer.openTodoPage();
|
|
78
|
+
ui.status = '';
|
|
75
79
|
return;
|
|
76
80
|
}
|
|
77
|
-
|
|
78
|
-
|
|
79
|
-
|
|
80
|
-
|
|
81
|
-
|
|
82
|
-
|
|
83
|
-
|
|
81
|
+
ui.nav.todoOpen = false;
|
|
82
|
+
ui.nav.index = entry.openIndex ?? entry.firstIndex;
|
|
83
|
+
if (ui.nav.fileScope === 'file') {
|
|
84
|
+
return void openUnitFile(ui, entry);
|
|
85
|
+
}
|
|
86
|
+
ui.nav.pane = 'diff';
|
|
87
|
+
ui.nav.scroll = 0;
|
|
88
|
+
ui.status = '';
|
|
89
|
+
ui.nav.clearSelection();
|
|
90
|
+
syncReviewPath(ui);
|
|
84
91
|
};
|
|
85
92
|
|
|
86
|
-
const onFileMove = (
|
|
87
|
-
const list =
|
|
93
|
+
const onFileMove = (ui, delta) => {
|
|
94
|
+
const list = ui.fileList();
|
|
88
95
|
if (!list.length) {
|
|
89
|
-
|
|
96
|
+
ui.status = 'nothing to review';
|
|
90
97
|
return;
|
|
91
98
|
}
|
|
92
99
|
const last = list.length - 1;
|
|
93
|
-
const moved =
|
|
100
|
+
const moved = ui.nav.fileCursor + delta;
|
|
94
101
|
const next = Math.min(last, Math.max(0, moved));
|
|
95
|
-
if (next ===
|
|
96
|
-
|
|
102
|
+
if (next === ui.nav.fileCursor) return;
|
|
103
|
+
ui.nav.fileCursor = next;
|
|
97
104
|
const entry = list[next];
|
|
98
105
|
if (isTodosEntry(entry)) {
|
|
99
|
-
|
|
106
|
+
ui.nav.reviewPath = TODO_FILE;
|
|
100
107
|
} else {
|
|
101
|
-
|
|
102
|
-
|
|
108
|
+
ui.nav.reviewPath = entry.path;
|
|
109
|
+
ui.nav.index = entry.firstIndex;
|
|
103
110
|
}
|
|
104
|
-
|
|
111
|
+
ui.status = '';
|
|
105
112
|
};
|
|
106
113
|
|
|
107
|
-
const moveRemaining = (
|
|
108
|
-
const list =
|
|
114
|
+
const moveRemaining = (ui, step) => {
|
|
115
|
+
const list = ui.items;
|
|
109
116
|
if (!list.length) {
|
|
110
|
-
|
|
117
|
+
ui.status = 'nothing to review';
|
|
111
118
|
return;
|
|
112
119
|
}
|
|
113
|
-
const next =
|
|
120
|
+
const next = ui.nav.index + step;
|
|
114
121
|
if (next < 0 || next >= list.length) return;
|
|
115
|
-
|
|
116
|
-
|
|
117
|
-
|
|
118
|
-
|
|
119
|
-
syncReviewPath(
|
|
122
|
+
ui.nav.index = next;
|
|
123
|
+
ui.nav.scroll = 0;
|
|
124
|
+
ui.status = '';
|
|
125
|
+
ui.nav.clearSelection();
|
|
126
|
+
syncReviewPath(ui);
|
|
120
127
|
};
|
|
121
128
|
|
|
122
|
-
const onNext = (
|
|
123
|
-
if (
|
|
124
|
-
|
|
125
|
-
|
|
126
|
-
|
|
127
|
-
|
|
128
|
-
|
|
129
|
+
const onNext = (ui) => {
|
|
130
|
+
if (ui.nav.pane === 'unit') return void moveUnitBlock(ui, 1);
|
|
131
|
+
if (ui.nav.todoOpen) {
|
|
132
|
+
ui.composer.closeTodoPage();
|
|
133
|
+
if (ui.items.length) ui.nav.index = 0;
|
|
134
|
+
ui.nav.scroll = 0;
|
|
135
|
+
syncReviewPath(ui);
|
|
136
|
+
syncFileCursor(ui);
|
|
129
137
|
return;
|
|
130
138
|
}
|
|
131
|
-
moveRemaining(
|
|
139
|
+
moveRemaining(ui, 1);
|
|
132
140
|
};
|
|
133
141
|
|
|
134
|
-
const onPrev = (
|
|
135
|
-
if (
|
|
136
|
-
if (
|
|
137
|
-
|
|
138
|
-
|
|
139
|
-
}
|
|
140
|
-
moveRemaining(options, -1);
|
|
142
|
+
const onPrev = (ui) => {
|
|
143
|
+
if (ui.nav.pane === 'unit') return void moveUnitBlock(ui, -1);
|
|
144
|
+
if (ui.nav.todoOpen) return;
|
|
145
|
+
if (ui.nav.index <= 0) return void ui.composer.openTodoPage();
|
|
146
|
+
moveRemaining(ui, -1);
|
|
141
147
|
};
|
|
142
148
|
|
|
143
|
-
const scrollStep = (
|
|
144
|
-
const frame =
|
|
145
|
-
const size =
|
|
149
|
+
const scrollStep = (ui, fraction) => {
|
|
150
|
+
const frame = ui.lastFrame;
|
|
151
|
+
const size = ui.lastSize ?? ui.getSize();
|
|
146
152
|
const rows = size.height ?? 24;
|
|
147
153
|
const fallback = Math.max(1, rows - 4);
|
|
148
154
|
const bodyH = frame?.bodyH ?? fallback;
|
|
@@ -153,91 +159,93 @@ const scrollStep = (options, fraction) => {
|
|
|
153
159
|
return n;
|
|
154
160
|
};
|
|
155
161
|
|
|
156
|
-
const onScroll = (
|
|
157
|
-
if (
|
|
158
|
-
if (
|
|
159
|
-
return void
|
|
162
|
+
const onScroll = (ui, delta) => {
|
|
163
|
+
if (ui.nav.pane === 'files') return void onFileMove(ui, delta);
|
|
164
|
+
if (ui.nav.pane === 'branches') {
|
|
165
|
+
return void ui.gitBranches.onBranchMove(delta);
|
|
160
166
|
}
|
|
161
|
-
if (
|
|
162
|
-
return void
|
|
167
|
+
if (ui.nav.pane === 'commits') {
|
|
168
|
+
return void ui.commits.onCommitMove(delta);
|
|
163
169
|
}
|
|
164
|
-
if (
|
|
165
|
-
return void
|
|
170
|
+
if (ui.nav.todoOpen && ui.composer.todoRowCount() > 1) {
|
|
171
|
+
return void ui.composer.moveTodoFocus(delta);
|
|
166
172
|
}
|
|
167
|
-
const frame =
|
|
173
|
+
const frame = ui.lastFrame;
|
|
168
174
|
const max = frame ? frame.scrollMax : null;
|
|
169
|
-
const scroll =
|
|
175
|
+
const scroll = ui.nav.scroll;
|
|
170
176
|
const current = max === null ? scroll : Math.min(scroll, max);
|
|
171
177
|
const moved = current + delta;
|
|
172
178
|
const next = max === null ? moved : Math.min(max, moved);
|
|
173
|
-
|
|
174
|
-
|
|
179
|
+
ui.nav.scroll = Math.max(0, next);
|
|
180
|
+
ui.nav.clearSelection();
|
|
175
181
|
};
|
|
176
182
|
|
|
177
|
-
const onJump = (
|
|
178
|
-
if (
|
|
179
|
-
const list =
|
|
183
|
+
const onJump = (ui, toEnd) => {
|
|
184
|
+
if (ui.nav.pane === 'files') {
|
|
185
|
+
const list = ui.fileList();
|
|
180
186
|
if (!list.length) {
|
|
181
|
-
|
|
187
|
+
ui.status = 'nothing to review';
|
|
182
188
|
return;
|
|
183
189
|
}
|
|
184
190
|
const target = toEnd ? list.length - 1 : 0;
|
|
185
|
-
onFileMove(
|
|
186
|
-
return;
|
|
191
|
+
return void onFileMove(ui, target - ui.nav.fileCursor);
|
|
187
192
|
}
|
|
188
|
-
if (
|
|
193
|
+
if (ui.nav.pane === 'branches') {
|
|
189
194
|
const delta = toEnd ? Number.MAX_SAFE_INTEGER : -Number.MAX_SAFE_INTEGER;
|
|
190
|
-
|
|
191
|
-
return;
|
|
195
|
+
return void ui.gitBranches.onBranchMove(delta);
|
|
192
196
|
}
|
|
193
|
-
if (
|
|
197
|
+
if (ui.nav.pane === 'commits') {
|
|
194
198
|
const delta = toEnd ? Number.MAX_SAFE_INTEGER : -Number.MAX_SAFE_INTEGER;
|
|
195
|
-
|
|
196
|
-
return;
|
|
199
|
+
return void ui.commits.onCommitMove(delta);
|
|
197
200
|
}
|
|
198
|
-
if (
|
|
199
|
-
const last =
|
|
201
|
+
if (ui.nav.todoOpen && ui.composer.todoRowCount() > 0) {
|
|
202
|
+
const last = ui.composer.todoRowCount() - 1;
|
|
200
203
|
const target = toEnd ? last : 0;
|
|
201
|
-
const at =
|
|
202
|
-
|
|
203
|
-
return;
|
|
204
|
+
const at = ui.composer.clampedTodoFocus();
|
|
205
|
+
return void ui.composer.moveTodoFocus(target - at);
|
|
204
206
|
}
|
|
205
|
-
const frame =
|
|
207
|
+
const frame = ui.lastFrame;
|
|
206
208
|
const max = frame ? frame.scrollMax : 0;
|
|
207
|
-
|
|
208
|
-
|
|
209
|
+
ui.nav.scroll = toEnd ? max : 0;
|
|
210
|
+
ui.nav.clearSelection();
|
|
209
211
|
};
|
|
210
212
|
|
|
211
|
-
const onLayout = (
|
|
212
|
-
const i = LAYOUTS.indexOf(
|
|
213
|
+
const onLayout = (ui) => {
|
|
214
|
+
const i = LAYOUTS.indexOf(ui.layout);
|
|
213
215
|
const next = (i < 0 ? 0 : i + 1) % LAYOUTS.length;
|
|
214
|
-
|
|
216
|
+
ui.layout = LAYOUTS[next];
|
|
215
217
|
const name = LAYOUTS[next] === 'side' ? 'side-by-side' : LAYOUTS[next];
|
|
216
|
-
|
|
217
|
-
|
|
218
|
-
|
|
218
|
+
ui.status = name;
|
|
219
|
+
ui.nav.scroll = 0;
|
|
220
|
+
ui.nav.clearSelection();
|
|
221
|
+
};
|
|
222
|
+
|
|
223
|
+
const onTheme = (ui) => {
|
|
224
|
+
const i = THEME_NAMES.indexOf(themeName());
|
|
225
|
+
const next = THEME_NAMES[(i + 1) % THEME_NAMES.length];
|
|
226
|
+
setTheme(next);
|
|
227
|
+
ui.status = next;
|
|
219
228
|
};
|
|
220
229
|
|
|
221
|
-
const createFilesPane = (
|
|
222
|
-
|
|
223
|
-
|
|
224
|
-
|
|
225
|
-
|
|
226
|
-
|
|
227
|
-
|
|
228
|
-
|
|
229
|
-
|
|
230
|
-
|
|
231
|
-
|
|
232
|
-
|
|
233
|
-
|
|
234
|
-
|
|
235
|
-
|
|
236
|
-
|
|
237
|
-
|
|
238
|
-
|
|
239
|
-
|
|
240
|
-
onLayout: () => onLayout(options),
|
|
230
|
+
const createFilesPane = (ui) => ({
|
|
231
|
+
clampIndex: () => clampIndex(ui),
|
|
232
|
+
syncReviewPath: () => syncReviewPath(ui),
|
|
233
|
+
syncFileCursor: () => syncFileCursor(ui),
|
|
234
|
+
showFiles: () => showFiles(ui),
|
|
235
|
+
onEscape: () => onEscape(ui),
|
|
236
|
+
onFiles: () => onFiles(ui),
|
|
237
|
+
onOpenFile: () => onOpenFile(ui),
|
|
238
|
+
onFileMove: (delta) => onFileMove(ui, delta),
|
|
239
|
+
onNext: () => onNext(ui),
|
|
240
|
+
onPrev: () => onPrev(ui),
|
|
241
|
+
scrollStep: (fraction) => scrollStep(ui, fraction),
|
|
242
|
+
onScroll: (delta) => onScroll(ui, delta),
|
|
243
|
+
onHome: () => onJump(ui, false),
|
|
244
|
+
onEnd: () => onJump(ui, true),
|
|
245
|
+
onLayout: () => onLayout(ui),
|
|
246
|
+
onTheme: () => onTheme(ui),
|
|
247
|
+
onFileScope: () => setFileScope(ui, 'file'),
|
|
248
|
+
onDiffScope: () => setFileScope(ui, 'diff'),
|
|
241
249
|
});
|
|
242
250
|
|
|
243
251
|
module.exports = { LAYOUTS, createFilesPane };
|
package/lib/session/items.js
CHANGED
|
@@ -1,9 +1,11 @@
|
|
|
1
1
|
'use strict';
|
|
2
2
|
|
|
3
|
+
const { stateView } = require('./accessors.js');
|
|
4
|
+
|
|
3
5
|
const files = require('../files.js');
|
|
4
6
|
const { itemPath, TODO_FILE, isTodoItem } = files;
|
|
5
7
|
const { feedbackKey } = require('../review.js');
|
|
6
|
-
const { refreshIndexPatches } = require('../diff.js');
|
|
8
|
+
const { refreshIndexPatches } = require('../diff/diff.js');
|
|
7
9
|
|
|
8
10
|
const depChangeKey = (item) => {
|
|
9
11
|
const change = item.dep && item.dep.change;
|
|
@@ -74,12 +76,10 @@ const takeBucket = (map, key, used) => {
|
|
|
74
76
|
return null;
|
|
75
77
|
};
|
|
76
78
|
|
|
77
|
-
const pathOf = (item) => itemPath(item) || '';
|
|
78
|
-
|
|
79
79
|
const groupByPath = (items) => {
|
|
80
80
|
const groups = new Map();
|
|
81
81
|
for (const item of items) {
|
|
82
|
-
const rel =
|
|
82
|
+
const rel = itemPath(item) || '';
|
|
83
83
|
const list = groups.get(rel) ?? [];
|
|
84
84
|
list.push(item);
|
|
85
85
|
groups.set(rel, list);
|
|
@@ -225,18 +225,15 @@ const createItemCollection = () => {
|
|
|
225
225
|
state.dismissed.clear();
|
|
226
226
|
};
|
|
227
227
|
|
|
228
|
-
const findIndexByKey = (key) => {
|
|
229
|
-
if (!key) return -1;
|
|
230
|
-
return state.items.findIndex((item) => itemKey(item) === key);
|
|
231
|
-
};
|
|
232
|
-
|
|
233
228
|
const findRestoredIndex = (item) => restoredIndex(state.items, item);
|
|
234
229
|
|
|
235
230
|
const keepOrigin = (item, origin) => {
|
|
236
231
|
const next = { ...item, origin };
|
|
237
|
-
const
|
|
238
|
-
|
|
239
|
-
|
|
232
|
+
const { length } = state.items;
|
|
233
|
+
const replaced = new Array(length);
|
|
234
|
+
for (let i = 0; i < length; i++) {
|
|
235
|
+
const entry = state.items[i];
|
|
236
|
+
replaced[i] = sameBlock(entry, item) ? next : entry;
|
|
240
237
|
}
|
|
241
238
|
if (next.dep) {
|
|
242
239
|
state.items = replaced;
|
|
@@ -245,25 +242,20 @@ const createItemCollection = () => {
|
|
|
245
242
|
state.items = refreshIndexPatches(replaced, next);
|
|
246
243
|
};
|
|
247
244
|
|
|
248
|
-
return
|
|
249
|
-
|
|
250
|
-
|
|
245
|
+
return stateView(
|
|
246
|
+
state,
|
|
247
|
+
{
|
|
248
|
+
reset,
|
|
249
|
+
replace,
|
|
250
|
+
dismiss,
|
|
251
|
+
clearDismissed,
|
|
252
|
+
isDismissed,
|
|
253
|
+
findRestoredIndex,
|
|
254
|
+
keepOrigin,
|
|
251
255
|
},
|
|
252
|
-
|
|
253
|
-
|
|
254
|
-
|
|
255
|
-
get dismissed() {
|
|
256
|
-
return state.dismissed;
|
|
257
|
-
},
|
|
258
|
-
reset,
|
|
259
|
-
replace,
|
|
260
|
-
dismiss,
|
|
261
|
-
clearDismissed,
|
|
262
|
-
isDismissed,
|
|
263
|
-
findIndexByKey,
|
|
264
|
-
findRestoredIndex,
|
|
265
|
-
keepOrigin,
|
|
266
|
-
};
|
|
256
|
+
['items'],
|
|
257
|
+
['dismissed'],
|
|
258
|
+
);
|
|
267
259
|
};
|
|
268
260
|
|
|
269
261
|
module.exports = {
|