@khorsheed/dsh-reader 0.2.1 → 0.3.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 +27 -0
- package/README.en.md +26 -121
- package/README.i18n.yaml +3 -3
- package/README.md +26 -121
- package/cordis.patch.yml +7 -0
- package/lib/client.js +30580 -6892
- package/lib/index.js +4189 -621
- package/lib/typert.host.js +2265 -319
- package/lib/typert.remote-client.d.ts +99 -3
- package/lib/typert.remote-client.js +1618 -240
- package/lib/types/captions.d.ts +99 -0
- package/lib/types/captions.js +236 -0
- package/lib/types/client/MediaPlayer.d.ts +55 -0
- package/lib/types/client/MediaPlayer.js +106 -0
- package/lib/types/client/NotesView.d.ts +57 -0
- package/lib/types/client/NotesView.js +124 -0
- package/lib/types/client/ReaderPane.d.ts +20 -3
- package/lib/types/client/ReaderPane.js +905 -164
- package/lib/types/client/SpeakerLegend.d.ts +18 -0
- package/lib/types/client/SpeakerLegend.js +26 -0
- package/lib/types/client/canvas-sync.d.ts +84 -0
- package/lib/types/client/canvas-sync.js +59 -0
- package/lib/types/client/contract.d.ts +138 -3
- package/lib/types/client/extract-article.d.ts +38 -1
- package/lib/types/client/extract-article.js +501 -28
- package/lib/types/client/icons.d.ts +1 -1
- package/lib/types/client/icons.js +1 -1
- package/lib/types/client/index.js +82 -2
- package/lib/types/client/locales.d.ts +279 -11
- package/lib/types/client/locales.js +278 -10
- package/lib/types/client/notes.d.ts +142 -0
- package/lib/types/client/notes.js +334 -0
- package/lib/types/client/parse-rss.js +40 -0
- package/lib/types/client/preset-visibility.d.ts +93 -0
- package/lib/types/client/preset-visibility.js +115 -0
- package/lib/types/client/selectors.d.ts +5 -0
- package/lib/types/client/selectors.js +5 -0
- package/lib/types/client/session.d.ts +21 -1
- package/lib/types/client/session.js +12 -0
- package/lib/types/client/store.js +4 -1
- package/lib/types/client/translate.d.ts +26 -1
- package/lib/types/client/translate.js +29 -12
- package/lib/types/client/useLocalTranscript.d.ts +43 -0
- package/lib/types/client/useLocalTranscript.js +129 -0
- package/lib/types/client/useMedia.d.ts +68 -0
- package/lib/types/client/useMedia.js +299 -0
- package/lib/types/client/useMediaStates.d.ts +9 -0
- package/lib/types/client/useMediaStates.js +43 -0
- package/lib/types/client/useNotes.d.ts +110 -0
- package/lib/types/client/useNotes.js +423 -0
- package/lib/types/client/usePolish.d.ts +47 -0
- package/lib/types/client/usePolish.js +162 -0
- package/lib/types/image-fetch.d.ts +81 -0
- package/lib/types/image-fetch.js +385 -0
- package/lib/types/index.d.ts +6 -0
- package/lib/types/index.js +3 -0
- package/lib/types/local-transcribe.d.ts +171 -0
- package/lib/types/local-transcribe.js +473 -0
- package/lib/types/media-host.d.ts +91 -0
- package/lib/types/media-host.js +230 -0
- package/lib/types/media.d.ts +100 -0
- package/lib/types/media.js +207 -0
- package/lib/types/notes-types.d.ts +158 -0
- package/lib/types/notes-types.js +8 -0
- package/lib/types/notes.d.ts +213 -0
- package/lib/types/notes.js +718 -0
- package/lib/types/polish.d.ts +41 -0
- package/lib/types/polish.js +136 -0
- package/lib/types/remote.d.ts +127 -1
- package/lib/types/remote.js +162 -1
- package/lib/types/service.d.ts +100 -1
- package/lib/types/service.js +320 -59
- package/lib/types/skill.d.ts +20 -0
- package/lib/types/skill.js +78 -0
- package/lib/types/store.js +30 -8
- package/lib/types/tool.d.ts +23 -0
- package/lib/types/tool.js +40 -0
- package/lib/types/tools.d.ts +69 -0
- package/lib/types/tools.js +400 -0
- package/lib/types/types.d.ts +106 -0
- package/lib/types/types.js +66 -0
- package/lib/types/xiaoyuzhou.d.ts +43 -0
- package/lib/types/xiaoyuzhou.js +134 -0
- package/lib/types/ytdlp.d.ts +111 -0
- package/lib/types/ytdlp.js +269 -0
- package/package.json +29 -20
- package/lib/invariant.js +0 -38
- package/lib/types/invariant.d.ts +0 -29
- package/lib/types/invariant.js +0 -38
|
@@ -0,0 +1,41 @@
|
|
|
1
|
+
import type { ReaderPolishView } from './types.ts';
|
|
2
|
+
/**
|
|
3
|
+
* What a layer belongs to: the paragraphs' text without their time and
|
|
4
|
+
* speaker prefixes, hashed.
|
|
5
|
+
*/
|
|
6
|
+
export declare function sourceKey(paragraphs: readonly string[]): string;
|
|
7
|
+
/**
|
|
8
|
+
* Parse the model's write-back: lines `¶12:译文…` (a line without a ¶
|
|
9
|
+
* continues the paragraph before it).
|
|
10
|
+
*
|
|
11
|
+
* @param text - what the model sent.
|
|
12
|
+
*/
|
|
13
|
+
export declare function parsePolish(text: string): Map<number, string>;
|
|
14
|
+
/** The per-article 润色 layers. */
|
|
15
|
+
export declare class ReaderPolishStore {
|
|
16
|
+
private readonly dir;
|
|
17
|
+
private readonly memory;
|
|
18
|
+
constructor(stateRoot: string);
|
|
19
|
+
private fileOf;
|
|
20
|
+
private load;
|
|
21
|
+
private save;
|
|
22
|
+
/**
|
|
23
|
+
* An article's layer, when it belongs to the text now captured.
|
|
24
|
+
*
|
|
25
|
+
* @param entryId - the article.
|
|
26
|
+
* @param key - the current text's {@link sourceKey}.
|
|
27
|
+
*/
|
|
28
|
+
view(entryId: string, key: string | undefined): ReaderPolishView | undefined;
|
|
29
|
+
/**
|
|
30
|
+
* Merge the model's translations into the layer (a different text starts a
|
|
31
|
+
* fresh one).
|
|
32
|
+
*
|
|
33
|
+
* @returns the layer after the write.
|
|
34
|
+
*/
|
|
35
|
+
write(entryId: string, key: string, total: number, updates: ReadonlyMap<number, string>): ReaderPolishView;
|
|
36
|
+
/** Turn one paragraph back to (or away from) the machine translation. */
|
|
37
|
+
setOff(entryId: string, key: string | undefined, paragraph: number, off: boolean): ReaderPolishView | undefined;
|
|
38
|
+
/** Forget an article's layer. */
|
|
39
|
+
drop(entryId: string): void;
|
|
40
|
+
}
|
|
41
|
+
//# sourceMappingURL=polish.d.ts.map
|
|
@@ -0,0 +1,136 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* The 润色 layer: an agent's paragraph-by-paragraph translation of an
|
|
3
|
+
* article, written back through `reader_translate` and shown in place of the
|
|
4
|
+
* browser's sentence-by-sentence machine translation.
|
|
5
|
+
*
|
|
6
|
+
* Keyed to the article's text as the model read it (the snapshot): a
|
|
7
|
+
* re-transcription changes the text and so drops the layer; renaming a
|
|
8
|
+
* speaker only changes the "[mm:ss] 名字:" prefixes and keeps it.
|
|
9
|
+
*
|
|
10
|
+
* One JSON file per article under `<state>/polish/`, memory-only when the
|
|
11
|
+
* state root cannot be written.
|
|
12
|
+
*
|
|
13
|
+
* @module @khorsheed/dsh-reader/polish
|
|
14
|
+
*/
|
|
15
|
+
import { createHash } from 'node:crypto';
|
|
16
|
+
import { mkdirSync, readFileSync, renameSync, rmSync, writeFileSync } from 'node:fs';
|
|
17
|
+
import { join } from 'node:path';
|
|
18
|
+
/** The time / speaker prefix of a transcript paragraph in the snapshot. */
|
|
19
|
+
const PREFIX = /^\[\d+(?::\d+){1,2}\]\s*(?:[^:\n]{1,40}:)?/;
|
|
20
|
+
/**
|
|
21
|
+
* What a layer belongs to: the paragraphs' text without their time and
|
|
22
|
+
* speaker prefixes, hashed.
|
|
23
|
+
*/
|
|
24
|
+
export function sourceKey(paragraphs) {
|
|
25
|
+
const hash = createHash('sha1');
|
|
26
|
+
hash.update(String(paragraphs.length));
|
|
27
|
+
for (const paragraph of paragraphs)
|
|
28
|
+
hash.update(`\n${paragraph.replace(PREFIX, '')}`);
|
|
29
|
+
return hash.digest('hex').slice(0, 24);
|
|
30
|
+
}
|
|
31
|
+
/**
|
|
32
|
+
* Parse the model's write-back: lines `¶12:译文…` (a line without a ¶
|
|
33
|
+
* continues the paragraph before it).
|
|
34
|
+
*
|
|
35
|
+
* @param text - what the model sent.
|
|
36
|
+
*/
|
|
37
|
+
export function parsePolish(text) {
|
|
38
|
+
const out = new Map();
|
|
39
|
+
let current;
|
|
40
|
+
for (const line of text.split(/\r?\n/)) {
|
|
41
|
+
const head = /^\s*¶\s*(\d+)\s*[::]\s*(.*)$/.exec(line);
|
|
42
|
+
if (head !== null) {
|
|
43
|
+
current = Number(head[1]);
|
|
44
|
+
out.set(current, head[2].trim());
|
|
45
|
+
}
|
|
46
|
+
else if (current !== undefined && line.trim() !== '') {
|
|
47
|
+
out.set(current, `${out.get(current) ?? ''}${line.trim()}`);
|
|
48
|
+
}
|
|
49
|
+
}
|
|
50
|
+
for (const [key, value] of out)
|
|
51
|
+
if (value === '')
|
|
52
|
+
out.delete(key);
|
|
53
|
+
return out;
|
|
54
|
+
}
|
|
55
|
+
/** The per-article 润色 layers. */
|
|
56
|
+
export class ReaderPolishStore {
|
|
57
|
+
dir;
|
|
58
|
+
memory = new Map();
|
|
59
|
+
constructor(stateRoot) {
|
|
60
|
+
this.dir = join(stateRoot, 'polish');
|
|
61
|
+
}
|
|
62
|
+
fileOf(entryId) {
|
|
63
|
+
return join(this.dir, `${createHash('sha1').update(entryId).digest('hex').slice(0, 32)}.json`);
|
|
64
|
+
}
|
|
65
|
+
load(entryId) {
|
|
66
|
+
const cached = this.memory.get(entryId);
|
|
67
|
+
if (cached !== undefined)
|
|
68
|
+
return cached;
|
|
69
|
+
try {
|
|
70
|
+
const parsed = JSON.parse(readFileSync(this.fileOf(entryId), 'utf8'));
|
|
71
|
+
if (parsed.entryId !== entryId)
|
|
72
|
+
return undefined;
|
|
73
|
+
this.memory.set(entryId, parsed);
|
|
74
|
+
return parsed;
|
|
75
|
+
}
|
|
76
|
+
catch {
|
|
77
|
+
return undefined;
|
|
78
|
+
}
|
|
79
|
+
}
|
|
80
|
+
save(file) {
|
|
81
|
+
this.memory.set(file.entryId, file);
|
|
82
|
+
try {
|
|
83
|
+
mkdirSync(this.dir, { recursive: true });
|
|
84
|
+
const target = this.fileOf(file.entryId);
|
|
85
|
+
writeFileSync(`${target}.tmp`, JSON.stringify(file));
|
|
86
|
+
renameSync(`${target}.tmp`, target);
|
|
87
|
+
}
|
|
88
|
+
catch {
|
|
89
|
+
// Memory-only: the layer lasts this process.
|
|
90
|
+
}
|
|
91
|
+
}
|
|
92
|
+
/**
|
|
93
|
+
* An article's layer, when it belongs to the text now captured.
|
|
94
|
+
*
|
|
95
|
+
* @param entryId - the article.
|
|
96
|
+
* @param key - the current text's {@link sourceKey}.
|
|
97
|
+
*/
|
|
98
|
+
view(entryId, key) {
|
|
99
|
+
const file = this.load(entryId);
|
|
100
|
+
if (file === undefined || key === undefined || file.sourceKey !== key)
|
|
101
|
+
return undefined;
|
|
102
|
+
const done = Object.keys(file.paragraphs).length;
|
|
103
|
+
return { total: file.total, done, paragraphs: { ...file.paragraphs }, off: [...file.off], updatedAt: file.updatedAt, complete: done >= file.total };
|
|
104
|
+
}
|
|
105
|
+
/**
|
|
106
|
+
* Merge the model's translations into the layer (a different text starts a
|
|
107
|
+
* fresh one).
|
|
108
|
+
*
|
|
109
|
+
* @returns the layer after the write.
|
|
110
|
+
*/
|
|
111
|
+
write(entryId, key, total, updates) {
|
|
112
|
+
const before = this.load(entryId);
|
|
113
|
+
const fresh = before === undefined || before.sourceKey !== key;
|
|
114
|
+
const paragraphs = fresh ? {} : { ...before.paragraphs };
|
|
115
|
+
for (const [index, value] of updates)
|
|
116
|
+
if (index >= 1 && index <= total)
|
|
117
|
+
paragraphs[String(index)] = value;
|
|
118
|
+
const file = { entryId, sourceKey: key, total, paragraphs, off: fresh ? [] : before.off, updatedAt: new Date().toISOString() };
|
|
119
|
+
this.save(file);
|
|
120
|
+
return this.view(entryId, key);
|
|
121
|
+
}
|
|
122
|
+
/** Turn one paragraph back to (or away from) the machine translation. */
|
|
123
|
+
setOff(entryId, key, paragraph, off) {
|
|
124
|
+
const file = this.load(entryId);
|
|
125
|
+
if (file === undefined || key === undefined || file.sourceKey !== key)
|
|
126
|
+
return undefined;
|
|
127
|
+
const rest = file.off.filter(item => item !== paragraph);
|
|
128
|
+
this.save({ ...file, off: off ? [...rest, paragraph] : rest });
|
|
129
|
+
return this.view(entryId, key);
|
|
130
|
+
}
|
|
131
|
+
/** Forget an article's layer. */
|
|
132
|
+
drop(entryId) {
|
|
133
|
+
this.memory.delete(entryId);
|
|
134
|
+
rmSync(this.fileOf(entryId), { force: true });
|
|
135
|
+
}
|
|
136
|
+
}
|
package/lib/types/remote.d.ts
CHANGED
|
@@ -11,7 +11,8 @@
|
|
|
11
11
|
*/
|
|
12
12
|
import type { Context } from '@deepseek-ai/cordis';
|
|
13
13
|
import { TypertRemoteService } from '@deepseek-ai/dsh-typert-protocol';
|
|
14
|
-
import type {
|
|
14
|
+
import type { LocalTranscriptStatus, MediaCardStates, ReaderEntryIdentity, ReaderPolishView, ReaderEntryNotes, ReaderMedia, ReaderNote, ReaderNoteInput, ReaderNoteOutcome } from './types.ts';
|
|
15
|
+
import type { ReaderAddFailure, ReaderAddOutcome, ReaderAddRefusal, ReaderAnnotationOutcome, ReaderBackfillCandidate, ReaderEntryBodyView, ReaderImageResult, ReaderEntryFetchState, ReaderBody, ReaderCapabilities, ReaderEntryTranslationView, ReaderMutationOutcome, ReaderRecentEntry, ReaderRefreshResult, ReaderSentenceLearn, ReaderSourceSummary, ReaderStorageStats, ReaderTag } from './types.ts';
|
|
15
16
|
declare module '@deepseek-ai/cordis' {
|
|
16
17
|
interface Context {
|
|
17
18
|
readerRemote: ReaderRemoteService;
|
|
@@ -26,6 +27,8 @@ export declare class ReaderRemoteService extends TypertRemoteService<ReaderRemot
|
|
|
26
27
|
constructor(ctx: Context, _config?: ReaderRemoteConfig);
|
|
27
28
|
/** The service core this face delegates to. */
|
|
28
29
|
private get core();
|
|
30
|
+
/** The notes store this face delegates to. */
|
|
31
|
+
private get notes();
|
|
29
32
|
/** Capability handshake: what the browser may rely on in this composition. */
|
|
30
33
|
capabilities(): Promise<ReaderCapabilities>;
|
|
31
34
|
/** The configured sources, without payloads. */
|
|
@@ -80,6 +83,14 @@ export declare class ReaderRemoteService extends TypertRemoteService<ReaderRemot
|
|
|
80
83
|
truncated?: boolean;
|
|
81
84
|
error?: string;
|
|
82
85
|
}>;
|
|
86
|
+
/**
|
|
87
|
+
* Fetch one image the browser could not load cross-origin (CORP /
|
|
88
|
+
* hotlink-protected), so the pane can re-point the failed `<img>` at the
|
|
89
|
+
* bytes. Called per failed image, never for a healthy one.
|
|
90
|
+
*/
|
|
91
|
+
fetchImage(request: {
|
|
92
|
+
url: string;
|
|
93
|
+
}): Promise<ReaderImageResult>;
|
|
83
94
|
/** Cache the markup the browser extracted for one entry. */
|
|
84
95
|
storeEntryBody(request: {
|
|
85
96
|
entryId: string;
|
|
@@ -219,6 +230,121 @@ export declare class ReaderRemoteService extends TypertRemoteService<ReaderRemot
|
|
|
219
230
|
label: string;
|
|
220
231
|
text: string;
|
|
221
232
|
}): Promise<'ok' | 'unavailable'>;
|
|
233
|
+
/** One article's notes and the conversations that discussed it. */
|
|
234
|
+
entryNotes(request: {
|
|
235
|
+
entryId: string;
|
|
236
|
+
}): Promise<{
|
|
237
|
+
entry?: ReaderEntryNotes;
|
|
238
|
+
}>;
|
|
239
|
+
/** How many notes each article carries. */
|
|
240
|
+
noteCounts(): Promise<{
|
|
241
|
+
counts: Record<string, number>;
|
|
242
|
+
}>;
|
|
243
|
+
/** Keep one excerpt (and its comment). */
|
|
244
|
+
addNote(request: ReaderNoteInput): Promise<ReaderNote | 'empty' | 'full'>;
|
|
245
|
+
/** Change or clear one note's comment. */
|
|
246
|
+
updateNote(request: {
|
|
247
|
+
entryId: string;
|
|
248
|
+
noteId: string;
|
|
249
|
+
comment: string;
|
|
250
|
+
}): Promise<ReaderNoteOutcome>;
|
|
251
|
+
/** Delete one note. */
|
|
252
|
+
deleteNote(request: {
|
|
253
|
+
entryId: string;
|
|
254
|
+
noteId: string;
|
|
255
|
+
}): Promise<ReaderNoteOutcome>;
|
|
256
|
+
/** Remember that a conversation discussed this article. */
|
|
257
|
+
recordDiscussion(request: ReaderEntryIdentity & {
|
|
258
|
+
sessionId: string;
|
|
259
|
+
sessionTitle?: string;
|
|
260
|
+
}): Promise<'ok' | 'empty'>;
|
|
261
|
+
/** Add the reader's own line under a note. */
|
|
262
|
+
addReply(request: {
|
|
263
|
+
entryId: string;
|
|
264
|
+
noteId: string;
|
|
265
|
+
text: string;
|
|
266
|
+
}): Promise<ReaderNoteOutcome>;
|
|
267
|
+
/** Rewrite (or, with empty text, remove) one line under a note. */
|
|
268
|
+
editReply(request: {
|
|
269
|
+
entryId: string;
|
|
270
|
+
noteId: string;
|
|
271
|
+
index: number;
|
|
272
|
+
text: string;
|
|
273
|
+
}): Promise<ReaderNoteOutcome>;
|
|
274
|
+
/** Remember that a note or a discussion note became a canvas card. */
|
|
275
|
+
markSynced(request: {
|
|
276
|
+
entryId: string;
|
|
277
|
+
noteId?: string;
|
|
278
|
+
discussionId?: string;
|
|
279
|
+
canvasId: string;
|
|
280
|
+
cardId: string;
|
|
281
|
+
canvasTitle: string;
|
|
282
|
+
}): Promise<ReaderNoteOutcome>;
|
|
283
|
+
/** Delete one discussion note. */
|
|
284
|
+
deleteDiscussion(request: {
|
|
285
|
+
entryId: string;
|
|
286
|
+
discussionId: string;
|
|
287
|
+
}): Promise<ReaderNoteOutcome>;
|
|
288
|
+
/** A video entry's transcript from its platform captions (stored; `none` when it has none). */
|
|
289
|
+
mediaTranscript(request: {
|
|
290
|
+
entryId: string;
|
|
291
|
+
url: string;
|
|
292
|
+
}): Promise<{
|
|
293
|
+
entryId: string;
|
|
294
|
+
html?: string;
|
|
295
|
+
captions: 'platform' | 'none' | 'failed';
|
|
296
|
+
language?: string;
|
|
297
|
+
error?: string;
|
|
298
|
+
}>;
|
|
299
|
+
/**
|
|
300
|
+
* Start (or rejoin) local transcription of an entry without captions.
|
|
301
|
+
* Answers `unavailable` without the transcription plugin and `needs-models`
|
|
302
|
+
* until the first model download is confirmed.
|
|
303
|
+
*/
|
|
304
|
+
startLocalTranscript(request: {
|
|
305
|
+
entryId: string;
|
|
306
|
+
url: string;
|
|
307
|
+
media: ReaderMedia;
|
|
308
|
+
title?: string;
|
|
309
|
+
confirmModels?: boolean;
|
|
310
|
+
}): Promise<LocalTranscriptStatus>;
|
|
311
|
+
/** Where an entry's local transcription stands, with the transcript so far. */
|
|
312
|
+
localTranscript(request: {
|
|
313
|
+
entryId: string;
|
|
314
|
+
}): Promise<LocalTranscriptStatus>;
|
|
315
|
+
/** The reader's names for a transcript's speakers, by index. */
|
|
316
|
+
speakerNames(request: {
|
|
317
|
+
entryId: string;
|
|
318
|
+
}): Promise<Record<string, string>>;
|
|
319
|
+
/** Name one speaker of a transcript (empty: back to 说话人 A…); answers all the names. */
|
|
320
|
+
nameSpeaker(request: {
|
|
321
|
+
entryId: string;
|
|
322
|
+
speaker: number;
|
|
323
|
+
name: string;
|
|
324
|
+
}): Promise<Record<string, string>>;
|
|
325
|
+
/** The wall's video / audio cards: what each one's transcript is (captions, local, transcribing…). */
|
|
326
|
+
mediaStates(request: {
|
|
327
|
+
entryIds: string[];
|
|
328
|
+
}): Promise<MediaCardStates>;
|
|
329
|
+
/** Leave (withdraws a queued job) or, with `force`, stop an entry's local transcription. */
|
|
330
|
+
cancelLocalTranscript(request: {
|
|
331
|
+
entryId: string;
|
|
332
|
+
force: boolean;
|
|
333
|
+
}): Promise<LocalTranscriptStatus>;
|
|
334
|
+
/** The article's 润色 layer (the agent's translation), when there is one for its current text. */
|
|
335
|
+
polish(request: {
|
|
336
|
+
entryId: string;
|
|
337
|
+
}): Promise<ReaderPolishView | null>;
|
|
338
|
+
/** Show one paragraph's machine translation instead of the 润色 (or back). */
|
|
339
|
+
setPolishOff(request: {
|
|
340
|
+
entryId: string;
|
|
341
|
+
paragraph: number;
|
|
342
|
+
off: boolean;
|
|
343
|
+
}): Promise<ReaderPolishView | null>;
|
|
344
|
+
/** Hand the host the article's original text, block by block, for the model to read. */
|
|
345
|
+
snapshotEntry(request: ReaderEntryIdentity & {
|
|
346
|
+
paragraphs: string[];
|
|
347
|
+
}): Promise<'ok' | 'empty'>;
|
|
222
348
|
}
|
|
223
349
|
export default ReaderRemoteService;
|
|
224
350
|
//# sourceMappingURL=remote.d.ts.map
|
package/lib/types/remote.js
CHANGED
|
@@ -46,6 +46,7 @@ let ReaderRemoteService = (() => {
|
|
|
46
46
|
let _getBodies_decorators;
|
|
47
47
|
let _getEntryBody_decorators;
|
|
48
48
|
let _fetchEntryBody_decorators;
|
|
49
|
+
let _fetchImage_decorators;
|
|
49
50
|
let _storeEntryBody_decorators;
|
|
50
51
|
let _entryFetchStates_decorators;
|
|
51
52
|
let _getRawBody_decorators;
|
|
@@ -68,6 +69,26 @@ let ReaderRemoteService = (() => {
|
|
|
68
69
|
let _listRecent_decorators;
|
|
69
70
|
let _clearRecent_decorators;
|
|
70
71
|
let _quoteToSideChat_decorators;
|
|
72
|
+
let _entryNotes_decorators;
|
|
73
|
+
let _noteCounts_decorators;
|
|
74
|
+
let _addNote_decorators;
|
|
75
|
+
let _updateNote_decorators;
|
|
76
|
+
let _deleteNote_decorators;
|
|
77
|
+
let _recordDiscussion_decorators;
|
|
78
|
+
let _addReply_decorators;
|
|
79
|
+
let _editReply_decorators;
|
|
80
|
+
let _markSynced_decorators;
|
|
81
|
+
let _deleteDiscussion_decorators;
|
|
82
|
+
let _mediaTranscript_decorators;
|
|
83
|
+
let _startLocalTranscript_decorators;
|
|
84
|
+
let _localTranscript_decorators;
|
|
85
|
+
let _speakerNames_decorators;
|
|
86
|
+
let _nameSpeaker_decorators;
|
|
87
|
+
let _mediaStates_decorators;
|
|
88
|
+
let _cancelLocalTranscript_decorators;
|
|
89
|
+
let _polish_decorators;
|
|
90
|
+
let _setPolishOff_decorators;
|
|
91
|
+
let _snapshotEntry_decorators;
|
|
71
92
|
return class ReaderRemoteService extends _classSuper {
|
|
72
93
|
static {
|
|
73
94
|
const _metadata = typeof Symbol === "function" && Symbol.metadata ? Object.create(_classSuper[Symbol.metadata] ?? null) : void 0;
|
|
@@ -80,6 +101,7 @@ let ReaderRemoteService = (() => {
|
|
|
80
101
|
_getBodies_decorators = [Remote('getBodies')];
|
|
81
102
|
_getEntryBody_decorators = [Remote('getEntryBody')];
|
|
82
103
|
_fetchEntryBody_decorators = [Remote('fetchEntryBody')];
|
|
104
|
+
_fetchImage_decorators = [Remote('fetchImage')];
|
|
83
105
|
_storeEntryBody_decorators = [Remote('storeEntryBody')];
|
|
84
106
|
_entryFetchStates_decorators = [Remote('entryFetchStates')];
|
|
85
107
|
_getRawBody_decorators = [Remote('getRawBody')];
|
|
@@ -102,6 +124,26 @@ let ReaderRemoteService = (() => {
|
|
|
102
124
|
_listRecent_decorators = [Remote('listRecent')];
|
|
103
125
|
_clearRecent_decorators = [Remote('clearRecent')];
|
|
104
126
|
_quoteToSideChat_decorators = [Remote('quoteToSideChat')];
|
|
127
|
+
_entryNotes_decorators = [Remote('entryNotes')];
|
|
128
|
+
_noteCounts_decorators = [Remote('noteCounts')];
|
|
129
|
+
_addNote_decorators = [Remote('addNote')];
|
|
130
|
+
_updateNote_decorators = [Remote('updateNote')];
|
|
131
|
+
_deleteNote_decorators = [Remote('deleteNote')];
|
|
132
|
+
_recordDiscussion_decorators = [Remote('recordDiscussion')];
|
|
133
|
+
_addReply_decorators = [Remote('addReply')];
|
|
134
|
+
_editReply_decorators = [Remote('editReply')];
|
|
135
|
+
_markSynced_decorators = [Remote('markSynced')];
|
|
136
|
+
_deleteDiscussion_decorators = [Remote('deleteDiscussion')];
|
|
137
|
+
_mediaTranscript_decorators = [Remote('mediaTranscript')];
|
|
138
|
+
_startLocalTranscript_decorators = [Remote('startLocalTranscript')];
|
|
139
|
+
_localTranscript_decorators = [Remote('localTranscript')];
|
|
140
|
+
_speakerNames_decorators = [Remote('speakerNames')];
|
|
141
|
+
_nameSpeaker_decorators = [Remote('nameSpeaker')];
|
|
142
|
+
_mediaStates_decorators = [Remote('mediaStates')];
|
|
143
|
+
_cancelLocalTranscript_decorators = [Remote('cancelLocalTranscript')];
|
|
144
|
+
_polish_decorators = [Remote('polish')];
|
|
145
|
+
_setPolishOff_decorators = [Remote('setPolishOff')];
|
|
146
|
+
_snapshotEntry_decorators = [Remote('snapshotEntry')];
|
|
105
147
|
__esDecorate(this, null, _capabilities_decorators, { kind: "method", name: "capabilities", static: false, private: false, access: { has: obj => "capabilities" in obj, get: obj => obj.capabilities }, metadata: _metadata }, null, _instanceExtraInitializers);
|
|
106
148
|
__esDecorate(this, null, _listSources_decorators, { kind: "method", name: "listSources", static: false, private: false, access: { has: obj => "listSources" in obj, get: obj => obj.listSources }, metadata: _metadata }, null, _instanceExtraInitializers);
|
|
107
149
|
__esDecorate(this, null, _addSource_decorators, { kind: "method", name: "addSource", static: false, private: false, access: { has: obj => "addSource" in obj, get: obj => obj.addSource }, metadata: _metadata }, null, _instanceExtraInitializers);
|
|
@@ -111,6 +153,7 @@ let ReaderRemoteService = (() => {
|
|
|
111
153
|
__esDecorate(this, null, _getBodies_decorators, { kind: "method", name: "getBodies", static: false, private: false, access: { has: obj => "getBodies" in obj, get: obj => obj.getBodies }, metadata: _metadata }, null, _instanceExtraInitializers);
|
|
112
154
|
__esDecorate(this, null, _getEntryBody_decorators, { kind: "method", name: "getEntryBody", static: false, private: false, access: { has: obj => "getEntryBody" in obj, get: obj => obj.getEntryBody }, metadata: _metadata }, null, _instanceExtraInitializers);
|
|
113
155
|
__esDecorate(this, null, _fetchEntryBody_decorators, { kind: "method", name: "fetchEntryBody", static: false, private: false, access: { has: obj => "fetchEntryBody" in obj, get: obj => obj.fetchEntryBody }, metadata: _metadata }, null, _instanceExtraInitializers);
|
|
156
|
+
__esDecorate(this, null, _fetchImage_decorators, { kind: "method", name: "fetchImage", static: false, private: false, access: { has: obj => "fetchImage" in obj, get: obj => obj.fetchImage }, metadata: _metadata }, null, _instanceExtraInitializers);
|
|
114
157
|
__esDecorate(this, null, _storeEntryBody_decorators, { kind: "method", name: "storeEntryBody", static: false, private: false, access: { has: obj => "storeEntryBody" in obj, get: obj => obj.storeEntryBody }, metadata: _metadata }, null, _instanceExtraInitializers);
|
|
115
158
|
__esDecorate(this, null, _entryFetchStates_decorators, { kind: "method", name: "entryFetchStates", static: false, private: false, access: { has: obj => "entryFetchStates" in obj, get: obj => obj.entryFetchStates }, metadata: _metadata }, null, _instanceExtraInitializers);
|
|
116
159
|
__esDecorate(this, null, _getRawBody_decorators, { kind: "method", name: "getRawBody", static: false, private: false, access: { has: obj => "getRawBody" in obj, get: obj => obj.getRawBody }, metadata: _metadata }, null, _instanceExtraInitializers);
|
|
@@ -133,9 +176,29 @@ let ReaderRemoteService = (() => {
|
|
|
133
176
|
__esDecorate(this, null, _listRecent_decorators, { kind: "method", name: "listRecent", static: false, private: false, access: { has: obj => "listRecent" in obj, get: obj => obj.listRecent }, metadata: _metadata }, null, _instanceExtraInitializers);
|
|
134
177
|
__esDecorate(this, null, _clearRecent_decorators, { kind: "method", name: "clearRecent", static: false, private: false, access: { has: obj => "clearRecent" in obj, get: obj => obj.clearRecent }, metadata: _metadata }, null, _instanceExtraInitializers);
|
|
135
178
|
__esDecorate(this, null, _quoteToSideChat_decorators, { kind: "method", name: "quoteToSideChat", static: false, private: false, access: { has: obj => "quoteToSideChat" in obj, get: obj => obj.quoteToSideChat }, metadata: _metadata }, null, _instanceExtraInitializers);
|
|
179
|
+
__esDecorate(this, null, _entryNotes_decorators, { kind: "method", name: "entryNotes", static: false, private: false, access: { has: obj => "entryNotes" in obj, get: obj => obj.entryNotes }, metadata: _metadata }, null, _instanceExtraInitializers);
|
|
180
|
+
__esDecorate(this, null, _noteCounts_decorators, { kind: "method", name: "noteCounts", static: false, private: false, access: { has: obj => "noteCounts" in obj, get: obj => obj.noteCounts }, metadata: _metadata }, null, _instanceExtraInitializers);
|
|
181
|
+
__esDecorate(this, null, _addNote_decorators, { kind: "method", name: "addNote", static: false, private: false, access: { has: obj => "addNote" in obj, get: obj => obj.addNote }, metadata: _metadata }, null, _instanceExtraInitializers);
|
|
182
|
+
__esDecorate(this, null, _updateNote_decorators, { kind: "method", name: "updateNote", static: false, private: false, access: { has: obj => "updateNote" in obj, get: obj => obj.updateNote }, metadata: _metadata }, null, _instanceExtraInitializers);
|
|
183
|
+
__esDecorate(this, null, _deleteNote_decorators, { kind: "method", name: "deleteNote", static: false, private: false, access: { has: obj => "deleteNote" in obj, get: obj => obj.deleteNote }, metadata: _metadata }, null, _instanceExtraInitializers);
|
|
184
|
+
__esDecorate(this, null, _recordDiscussion_decorators, { kind: "method", name: "recordDiscussion", static: false, private: false, access: { has: obj => "recordDiscussion" in obj, get: obj => obj.recordDiscussion }, metadata: _metadata }, null, _instanceExtraInitializers);
|
|
185
|
+
__esDecorate(this, null, _addReply_decorators, { kind: "method", name: "addReply", static: false, private: false, access: { has: obj => "addReply" in obj, get: obj => obj.addReply }, metadata: _metadata }, null, _instanceExtraInitializers);
|
|
186
|
+
__esDecorate(this, null, _editReply_decorators, { kind: "method", name: "editReply", static: false, private: false, access: { has: obj => "editReply" in obj, get: obj => obj.editReply }, metadata: _metadata }, null, _instanceExtraInitializers);
|
|
187
|
+
__esDecorate(this, null, _markSynced_decorators, { kind: "method", name: "markSynced", static: false, private: false, access: { has: obj => "markSynced" in obj, get: obj => obj.markSynced }, metadata: _metadata }, null, _instanceExtraInitializers);
|
|
188
|
+
__esDecorate(this, null, _deleteDiscussion_decorators, { kind: "method", name: "deleteDiscussion", static: false, private: false, access: { has: obj => "deleteDiscussion" in obj, get: obj => obj.deleteDiscussion }, metadata: _metadata }, null, _instanceExtraInitializers);
|
|
189
|
+
__esDecorate(this, null, _mediaTranscript_decorators, { kind: "method", name: "mediaTranscript", static: false, private: false, access: { has: obj => "mediaTranscript" in obj, get: obj => obj.mediaTranscript }, metadata: _metadata }, null, _instanceExtraInitializers);
|
|
190
|
+
__esDecorate(this, null, _startLocalTranscript_decorators, { kind: "method", name: "startLocalTranscript", static: false, private: false, access: { has: obj => "startLocalTranscript" in obj, get: obj => obj.startLocalTranscript }, metadata: _metadata }, null, _instanceExtraInitializers);
|
|
191
|
+
__esDecorate(this, null, _localTranscript_decorators, { kind: "method", name: "localTranscript", static: false, private: false, access: { has: obj => "localTranscript" in obj, get: obj => obj.localTranscript }, metadata: _metadata }, null, _instanceExtraInitializers);
|
|
192
|
+
__esDecorate(this, null, _speakerNames_decorators, { kind: "method", name: "speakerNames", static: false, private: false, access: { has: obj => "speakerNames" in obj, get: obj => obj.speakerNames }, metadata: _metadata }, null, _instanceExtraInitializers);
|
|
193
|
+
__esDecorate(this, null, _nameSpeaker_decorators, { kind: "method", name: "nameSpeaker", static: false, private: false, access: { has: obj => "nameSpeaker" in obj, get: obj => obj.nameSpeaker }, metadata: _metadata }, null, _instanceExtraInitializers);
|
|
194
|
+
__esDecorate(this, null, _mediaStates_decorators, { kind: "method", name: "mediaStates", static: false, private: false, access: { has: obj => "mediaStates" in obj, get: obj => obj.mediaStates }, metadata: _metadata }, null, _instanceExtraInitializers);
|
|
195
|
+
__esDecorate(this, null, _cancelLocalTranscript_decorators, { kind: "method", name: "cancelLocalTranscript", static: false, private: false, access: { has: obj => "cancelLocalTranscript" in obj, get: obj => obj.cancelLocalTranscript }, metadata: _metadata }, null, _instanceExtraInitializers);
|
|
196
|
+
__esDecorate(this, null, _polish_decorators, { kind: "method", name: "polish", static: false, private: false, access: { has: obj => "polish" in obj, get: obj => obj.polish }, metadata: _metadata }, null, _instanceExtraInitializers);
|
|
197
|
+
__esDecorate(this, null, _setPolishOff_decorators, { kind: "method", name: "setPolishOff", static: false, private: false, access: { has: obj => "setPolishOff" in obj, get: obj => obj.setPolishOff }, metadata: _metadata }, null, _instanceExtraInitializers);
|
|
198
|
+
__esDecorate(this, null, _snapshotEntry_decorators, { kind: "method", name: "snapshotEntry", static: false, private: false, access: { has: obj => "snapshotEntry" in obj, get: obj => obj.snapshotEntry }, metadata: _metadata }, null, _instanceExtraInitializers);
|
|
136
199
|
if (_metadata) Object.defineProperty(this, Symbol.metadata, { enumerable: true, configurable: true, writable: true, value: _metadata });
|
|
137
200
|
}
|
|
138
|
-
static inject = ['reader'];
|
|
201
|
+
static inject = ['reader', 'readerNotes'];
|
|
139
202
|
constructor(ctx, _config = {}) {
|
|
140
203
|
super(ctx, 'readerRemote', { namespace: 'reader' });
|
|
141
204
|
__runInitializers(this, _instanceExtraInitializers);
|
|
@@ -144,6 +207,10 @@ let ReaderRemoteService = (() => {
|
|
|
144
207
|
get core() {
|
|
145
208
|
return this.ctx.reader;
|
|
146
209
|
}
|
|
210
|
+
/** The notes store this face delegates to. */
|
|
211
|
+
get notes() {
|
|
212
|
+
return this.ctx.readerNotes;
|
|
213
|
+
}
|
|
147
214
|
/** Capability handshake: what the browser may rely on in this composition. */
|
|
148
215
|
capabilities() {
|
|
149
216
|
return this.core.capabilities();
|
|
@@ -181,6 +248,14 @@ let ReaderRemoteService = (() => {
|
|
|
181
248
|
fetchEntryBody(request) {
|
|
182
249
|
return this.core.fetchEntryBody(request);
|
|
183
250
|
}
|
|
251
|
+
/**
|
|
252
|
+
* Fetch one image the browser could not load cross-origin (CORP /
|
|
253
|
+
* hotlink-protected), so the pane can re-point the failed `<img>` at the
|
|
254
|
+
* bytes. Called per failed image, never for a healthy one.
|
|
255
|
+
*/
|
|
256
|
+
fetchImage(request) {
|
|
257
|
+
return this.core.fetchImage(request);
|
|
258
|
+
}
|
|
184
259
|
/** Cache the markup the browser extracted for one entry. */
|
|
185
260
|
storeEntryBody(request) {
|
|
186
261
|
return this.core.storeEntryBody(request);
|
|
@@ -269,6 +344,92 @@ let ReaderRemoteService = (() => {
|
|
|
269
344
|
quoteToSideChat(request) {
|
|
270
345
|
return this.core.quoteToSideChat(request);
|
|
271
346
|
}
|
|
347
|
+
/* ------------------------------------------------------------------ notes */
|
|
348
|
+
/** One article's notes and the conversations that discussed it. */
|
|
349
|
+
async entryNotes(request) {
|
|
350
|
+
const entry = this.notes.entry(request.entryId);
|
|
351
|
+
return entry === undefined ? {} : { entry };
|
|
352
|
+
}
|
|
353
|
+
/** How many notes each article carries. */
|
|
354
|
+
async noteCounts() {
|
|
355
|
+
return { counts: this.notes.counts() };
|
|
356
|
+
}
|
|
357
|
+
/** Keep one excerpt (and its comment). */
|
|
358
|
+
addNote(request) {
|
|
359
|
+
return this.notes.addNote(request);
|
|
360
|
+
}
|
|
361
|
+
/** Change or clear one note's comment. */
|
|
362
|
+
updateNote(request) {
|
|
363
|
+
return this.notes.updateNote(request);
|
|
364
|
+
}
|
|
365
|
+
/** Delete one note. */
|
|
366
|
+
deleteNote(request) {
|
|
367
|
+
return this.notes.deleteNote(request);
|
|
368
|
+
}
|
|
369
|
+
/** Remember that a conversation discussed this article. */
|
|
370
|
+
recordDiscussion(request) {
|
|
371
|
+
return this.notes.recordSession(request);
|
|
372
|
+
}
|
|
373
|
+
/** Add the reader's own line under a note. */
|
|
374
|
+
addReply(request) {
|
|
375
|
+
return this.notes.addReply({ ...request, by: 'user' });
|
|
376
|
+
}
|
|
377
|
+
/** Rewrite (or, with empty text, remove) one line under a note. */
|
|
378
|
+
editReply(request) {
|
|
379
|
+
return this.notes.editReply(request);
|
|
380
|
+
}
|
|
381
|
+
/** Remember that a note or a discussion note became a canvas card. */
|
|
382
|
+
markSynced(request) {
|
|
383
|
+
return this.notes.markSynced(request);
|
|
384
|
+
}
|
|
385
|
+
/** Delete one discussion note. */
|
|
386
|
+
deleteDiscussion(request) {
|
|
387
|
+
return this.notes.deleteDiscussion(request);
|
|
388
|
+
}
|
|
389
|
+
/** A video entry's transcript from its platform captions (stored; `none` when it has none). */
|
|
390
|
+
mediaTranscript(request) {
|
|
391
|
+
return this.core.mediaTranscript(request);
|
|
392
|
+
}
|
|
393
|
+
/**
|
|
394
|
+
* Start (or rejoin) local transcription of an entry without captions.
|
|
395
|
+
* Answers `unavailable` without the transcription plugin and `needs-models`
|
|
396
|
+
* until the first model download is confirmed.
|
|
397
|
+
*/
|
|
398
|
+
startLocalTranscript(request) {
|
|
399
|
+
return this.core.local.start(request);
|
|
400
|
+
}
|
|
401
|
+
/** Where an entry's local transcription stands, with the transcript so far. */
|
|
402
|
+
localTranscript(request) {
|
|
403
|
+
return Promise.resolve(this.core.local.status(request.entryId));
|
|
404
|
+
}
|
|
405
|
+
/** The reader's names for a transcript's speakers, by index. */
|
|
406
|
+
speakerNames(request) {
|
|
407
|
+
return Promise.resolve(this.core.speakerNames(request));
|
|
408
|
+
}
|
|
409
|
+
/** Name one speaker of a transcript (empty: back to 说话人 A…); answers all the names. */
|
|
410
|
+
nameSpeaker(request) {
|
|
411
|
+
return Promise.resolve(this.core.nameSpeaker(request));
|
|
412
|
+
}
|
|
413
|
+
/** The wall's video / audio cards: what each one's transcript is (captions, local, transcribing…). */
|
|
414
|
+
mediaStates(request) {
|
|
415
|
+
return Promise.resolve(this.core.mediaStates(request));
|
|
416
|
+
}
|
|
417
|
+
/** Leave (withdraws a queued job) or, with `force`, stop an entry's local transcription. */
|
|
418
|
+
cancelLocalTranscript(request) {
|
|
419
|
+
return Promise.resolve(this.core.local.cancel(request.entryId, request.force));
|
|
420
|
+
}
|
|
421
|
+
/** The article's 润色 layer (the agent's translation), when there is one for its current text. */
|
|
422
|
+
polish(request) {
|
|
423
|
+
return Promise.resolve(this.notes.polishView(request.entryId) ?? null);
|
|
424
|
+
}
|
|
425
|
+
/** Show one paragraph's machine translation instead of the 润色 (or back). */
|
|
426
|
+
setPolishOff(request) {
|
|
427
|
+
return Promise.resolve(this.notes.setPolishOff(request.entryId, request.paragraph, request.off) ?? null);
|
|
428
|
+
}
|
|
429
|
+
/** Hand the host the article's original text, block by block, for the model to read. */
|
|
430
|
+
snapshotEntry(request) {
|
|
431
|
+
return this.notes.snapshot(request);
|
|
432
|
+
}
|
|
272
433
|
};
|
|
273
434
|
})();
|
|
274
435
|
export { ReaderRemoteService };
|