Obsidian API におけるリンクまわりの言葉遣いや扱いについて。
Obsidian API では、リンクの文字列のことを linktext という名前で呼ぶことが多い。
[[note]] なら note が linktext になる。[[note#heading]] なら note#heading。[[note#^block-id]] なら note#^block-id。linktext は、path と subpath の2つの部分に分けられる。path は linkpath と呼ばれることもある(getLinkpath, getFirstLinkpathDest)。
note → path: "note", subpath: ""note#heading → path: "note", subpath: "#heading"note#^block-id → path: "note", subpath: "#^block-id"linktext を path と subpath に分割するには parseLinktext を使う。linktext から path だけを得る(つまりファイルにしか興味がない)ときは getLinkpath を使う。
"New link format" 設定が "Shortest path when possible" (デフォルト) になっているとき、あるリンクがどのノートを指しているのかを決定する("resolve" する)には
に加え、
の情報も必要になる。これを表すのが sourcePath: string である。
"source" は source/target あるいは source/destination の source。リンクの出どころ、リンクの出ている源という意味。
基本的にはそのリンクが存在しているノートの、vault 内における相対パスになる。
ただし、このリンクは特にどのノートから出ているってわけでもないなあという場合には空文字列になる。たとえば、Canvas の " 非埋め込みカード "(正式名称がわからない)の場合がこれにあたる。
CodeMirror の extension を書いているときも、sourcePath に相当するものがほしくなるときがある。これは以下で取得できる。
const sourcePath = state.field(editorInfoField).file?.path ?? "";
export function resolveLinktext(app: App, linktext: string, sourcePath: string): { file: TFile, subpathResult: HeadingSubpathResult | BlockSubpathResult | null } | null {
const { path, subpath } = parseLinktext(linktext);
const targetFile = app.metadataCache.getFirstLinkpathDest(path, sourcePath);
if (!targetFile) return null;
const targetCache = app.metadataCache.getFileCache(targetFile);
if (!targetCache) return null;
const result = resolveSubpath(targetCache, subpath);
return { file: targetFile, subpathResult: result };
}