Properties2
| Type | Practice |
| Note created | Jun 23, 2026 |
Obsidian Web Clipper keeps its templates in the browser’s chrome.storage.sync LevelDB (…/Sync Extension Settings/<ext-id>/), LZString-compressed and split into 8000-char chunks — one template_<id> key per template, ordered by a template_list key.
To edit programmatically (with a script or agentic programming): quit the browser first (LevelDB holds an exclusive lock), then drive it with Node.js classic-level + lz-string.
Read a template:
const chunks = JSON.parse(await db.get(`template_${id}`));
const tpl = JSON.parse(decompressFromUTF16(chunks.join("")));Write it back (re-chunk to stay under the 8 KB-per-item sync quota):
const c = compressToUTF16(JSON.stringify(tpl));
const chunks = [];
for (let i = 0; i < c.length; i += 8000) chunks.push(c.slice(i, i + 8000));
await db.put(`template_${id}`, JSON.stringify(chunks));Gotchas: the template engine un-escapes \" → ", so a JSON-array property value must use \\" to emit a literal \"; and the browser’s file-watcher may reset note mtime after a clip, so restore them from a backup if dates matter.