worker.ts (@takker/ScrapJupyter)
@takker/ScrapJupyterで以下の責務を追うworker code
コードブロック記法を探索する処理
たくさんコードブロック記法を使っているページを編集するとfreezeする (@takker/ScrapJupyter)
コードブロックが更新されたかどうか判定する処理
一度bundleしたコードを使い回す (@takker/ScrapJupyter)
更新されている場合は、onUpdate callbackを呼び出す
実装
まずはcodeFile.tsからwindow.scrapboxを切り出さないと
window.scrapboxはUI threadからしか使えない
こんな感じか?
code:ts
import type { Scrapbox } from "./deps/scrapbox.ts";
import { toLc } from "./utils.ts";
typeよりinterfaceの方がいい
doc.deno.landでJSDocを読める
コードブロックの塊ごとにlinesを分けておきたいところだが、それは別のPRでやろう
別threadで計算することと関係ない
code:ts
interface File {
filename?: string;
dir: string;
lang: string;
/** コードブロックの開始行のid */ startIds: string[];
lines: string[];
};
CodeBlockLineはtypeof scrapbox.Page.lines[0]のうち、codeBlockをもつobjectの型
あらかじめUI threadの方でcodeBlockをもつ行だけ抜き出しておく
code:ts
export interface CodeBlockLine {
// ...
}
export function getCodeFiles(lines: CodeBlockLine[]) {
return lines.reduce((acc: File[], { codeBlock, text, id }) => {
const sameFileIndex = acc.findIndex(({ filename }) =>
filename !== undefined && filename === codeBlock.filename
);
// code blockの先頭かつ新しいコードブロックのときのみ新しいfileを追加する
if (codeBlock.start && sameFileIndex < 0) {
return [...acc, {
filename: codeBlock.filename,
dir: `https://scrpabox.io/api/code/${scrapbox.Project.name}/${
toLc(scrapbox.Page.title ?? "")
}`,
lang: codeBlock.lang,
startIds: id,
lines: [] as string[],
}];
}
if (codeBlock.start) {
acc.at(sameFileIndex)?.startIds?.push?.(id);
} else {
// 既存のコードブロックもしくは末尾のコードブロックに追記する
acc.at(sameFileIndex)?.lines?.push?.(text);
}
return acc;
}, []);
}
worker.tsで↑を読み込む
最終的にはiife形式でbundleする
code:worker.ts
import {getCodeFiles} from "./codeFiles.ts";
self.addEventListener("message", (e) => {
switch (e.data.type) {
case "split":
self.postMessage({
uid: e.data.uid,
files: getCodeFiles(e.data.lines),
});
return;
default:
break;
}
});
UI threadでの処理
これこそgetCodeFiles.tsとしておきたいな
postMessage云々とか、UI threadからは関係ないことだし
UI threadに関係するのは「コードブロックを含んだ行を投げると、ファイルごとに分割されたデータが帰ってくる」という一番外側の振る舞い。内部がどうなっているかなんてどうでもいい
UI threadからは非同期関数getCodeFiles()を呼び出すだけにし、その内部でworkerとの通信を行うようにしよう
責務の分離を軸にmoduleを整理したいな
#2021-09-22
#2021-09-18 12:10:51