/// /// /// import { deletePage, getPage, patch } from "../scrapbox-userscript-std/mod.ts"; import { isErr, unwrapErr, unwrapOk } from "npm:option-t@49/plain_result"; export interface TransportInit { /** 転送元project */ from: string; /** 転送先project */ to: string; /** 転送先に同じタイトルのページがあったときの挙動 * * - `true`: 末尾に追記する * - `false`: 何もしない * @default false */ merge?: boolean; } export type TransportResult = { success: true; /** 同名のページが転送先にあったらtrue */ dup: boolean; } | { success: false; at: "from" | "to"; name: string; message: string; }; export async function transport(title: string, { from, to, merge, }: TransportInit): Promise { if (from === to) return { success: true, dup: false }; // 転送するページを取得 const res = await getPage(from, title); if (isErr(res)) { return { success: false, at: "from", name: unwrapErr(res).name, message: unwrapErr(res).message, }; } const page = unwrapOk(res); if (!page.persistent) { return { success: false, at: "from", name: "EmptyPageError", message: "The request page is empty.", }; } // 転送先ページがあるかどうかを調べる const res2 = await getPage(to, title); if (isErr(res2)) { return { success: false, at: "to", name: unwrapErr(res2).name, message: unwrapErr(res2).message, }; } const page2 = unwrapOk(res); if (page2.persistent && !merge) { return { success: false, at: "to", name: "NoEmptyPageError", message: `The same page already exists in "/${to}"`, }; } // 転送する await patch( to, title, (lines) => [...lines, ...page.lines.slice(1)].map((line) => line.text), ); await deletePage(from, title); return { success: true, dup: page2.persistent }; }