obsidian-headless 0.0.3 → 0.0.5
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/README.md +1 -10
- package/cli.js +12 -12
- package/package.json +1 -1
package/README.md
CHANGED
|
@@ -21,16 +21,6 @@ ob login
|
|
|
21
21
|
|
|
22
22
|
If already logged in, `ob login` displays your account info. To switch accounts, pass `--email` and/or `--password` to log in again.
|
|
23
23
|
|
|
24
|
-
### Environment variable
|
|
25
|
-
|
|
26
|
-
For non-interactive use (CI, scripts, servers), set the `OBSIDIAN_AUTH_TOKEN` environment variable instead of using `ob login`:
|
|
27
|
-
|
|
28
|
-
```bash
|
|
29
|
-
export OBSIDIAN_AUTH_TOKEN="your-auth-token"
|
|
30
|
-
```
|
|
31
|
-
|
|
32
|
-
When set, all commands that require authentication will use this token automatically.
|
|
33
|
-
|
|
34
24
|
## Quick start
|
|
35
25
|
|
|
36
26
|
```bash
|
|
@@ -132,6 +122,7 @@ Run with no options to display the current configuration.
|
|
|
132
122
|
| Option | Description |
|
|
133
123
|
|---|---|
|
|
134
124
|
| `--path` | Local vault path (default: current directory) |
|
|
125
|
+
| `--mode` | Sync mode: `bidirectional` (default), `pull-only` (only download, ignore local changes), or `mirror-remote` (only download, revert local changes) |
|
|
135
126
|
| `--conflict-strategy` | `merge` or `conflict` |
|
|
136
127
|
| `--file-types` | Attachment types to sync: `image`, `audio`, `video`, `pdf`, `unsupported` (comma-separated, empty to clear) |
|
|
137
128
|
| `--configs` | Config categories to sync: `app`, `appearance`, `appearance-data`, `hotkey`, `core-plugin`, `core-plugin-data`, `community-plugin`, `community-plugin-data` (comma-separated, empty to disable config syncing) |
|
package/cli.js
CHANGED
|
@@ -1,17 +1,17 @@
|
|
|
1
1
|
#!/usr/bin/env node
|
|
2
|
-
var
|
|
3
|
-
`)}return console.log=(...l)=>{i(...l),a(...l)},console.warn=(...l)=>{r(...l),a(...l)},console.error=(...l)=>{n(...l),a(...l)},console.debug=(...l)=>{o(...l),a(...l)},()=>{console.log=i,console.warn=r,console.error=n,console.debug=o,t.end()}}var xt=W(require("better-sqlite3"));var _i=1,ge=class{constructor(e){let t=P.default.dirname(e);D.default.existsSync(t)||D.default.mkdirSync(t,{recursive:!0}),this.db=new xt.default(e),this.db.pragma("journal_mode = WAL"),this.db.exec("CREATE TABLE IF NOT EXISTS meta (key TEXT PRIMARY KEY, value TEXT );"),this.db.exec("CREATE TABLE IF NOT EXISTS local_files (path TEXT PRIMARY KEY, data TEXT NOT NULL);"),this.db.exec("CREATE TABLE IF NOT EXISTS server_files (path TEXT PRIMARY KEY, data TEXT NOT NULL);"),this.db.exec("CREATE TABLE IF NOT EXISTS pending_files (uid INTEGER PRIMARY KEY, path TEXT, data TEXT NOT NULL)"),this.stmts={getMeta:this.db.prepare("SELECT value FROM meta WHERE key = ?"),setMeta:this.db.prepare("INSERT OR REPLACE INTO meta (key, value) VALUES (?, ?)"),getLocalFile:this.db.prepare("SELECT data FROM local_files WHERE path = ?"),setLocalFile:this.db.prepare("INSERT OR REPLACE INTO local_files (path, data) VALUES (?, ?)"),deleteLocalFile:this.db.prepare("DELETE FROM local_files WHERE path = ?"),getAllLocalFiles:this.db.prepare("SELECT path, data FROM local_files"),getServerFile:this.db.prepare("SELECT data FROM server_files WHERE path = ?"),setServerFile:this.db.prepare("INSERT OR REPLACE INTO server_files (path, data) VALUES (?, ?)"),deleteServerFile:this.db.prepare("DELETE FROM server_files WHERE path = ?"),getAllServerFiles:this.db.prepare("SELECT path, data FROM server_files"),addPendingFile:this.db.prepare("INSERT OR REPLACE INTO pending_files (uid, path, data) VALUES (?, ?, ?)"),deletePendingFile:this.db.prepare("DELETE FROM pending_files WHERE path = ?"),getPendingFiles:this.db.prepare("SELECT data FROM pending_files ORDER BY uid")},this.getMetaValue("schema_version")===null&&this.setMetaValue("schema_version",String(_i))}getMetaValue(e){let t=this.stmts.getMeta.get(e);return t?t.value:null}setMetaValue(e,t){this.stmts.setMeta.run(e,t)}getVersion(){let e=this.getMetaValue("version"),t=e?parseInt(e,10):0;return isNaN(t)&&(t=0),t}setVersion(e){this.setMetaValue("version",String(e))}isInitial(){return this.getMetaValue("initial")!=="false"}setInitial(e){this.setMetaValue("initial",e?"true":"false")}getLocalFile(e){let t=this.stmts.getLocalFile.get(e);if(!t)return null;try{return JSON.parse(t.data)}catch{return null}}setLocalFile(e){this.stmts.setLocalFile.run(e.path,JSON.stringify(e))}deleteLocalFile(e){this.stmts.deleteLocalFile.run(e)}getAllLocalFiles(){let e=this.stmts.getAllLocalFiles.all(),t={};for(let i of e)try{t[i.path]=JSON.parse(i.data)}catch{}return t}getServerFile(e){let t=this.stmts.getServerFile.get(e);if(!t)return null;try{return JSON.parse(t.data)}catch{return null}}setServerFile(e){this.stmts.setServerFile.run(e.path,JSON.stringify(e))}deleteServerFile(e){this.stmts.deleteServerFile.run(e)}getAllServerFiles(){let e=this.stmts.getAllServerFiles.all(),t={};for(let i of e)try{t[i.path]=JSON.parse(i.data)}catch{}return t}addPendingFile(e){this.stmts.addPendingFile.run(e.uid,e.path,JSON.stringify(e))}deletePendingFile(e){this.stmts.deletePendingFile.run(e)}getPendingFiles(){let e=this.stmts.getPendingFiles.all(),t=[];for(let i of e)try{t.push(JSON.parse(i.data))}catch{}return t}close(){this.db.close()}};var te=()=>typeof activeWindow<"u"?activeWindow:global;function It(s,e=0,t=!1){let i=null,r=null,n=null,o=0,a=0,l=te(),u=function(){let d=r,F=n;return r=null,n=null,s.apply(d,F)},c=function(){if(o){let d=Date.now();if(d<o){l=te(),i=l.setTimeout(c,o-d),o=0;return}}a=0,i=null,u()},p=function(...d){r=this,n=d;let F=Date.now();return i?t?o=a=F+e:l!==te()&&a<=F&&(l.clearTimeout(i),l=te(),i=l.setTimeout(c,0)):(l=te(),a=F+e,i=l.setTimeout(c,e)),p};return p.cancel=function(){return i&&(l.clearTimeout(i),i=null),p},p.run=function(){if(i)return l.clearTimeout(i),i=null,u()},p}var Ti=/\u00A0|\u202F/g;function Ge(s){return s.replace(Ti," ")}function C(s){let e=s.lastIndexOf("/");return e===-1?s:s.slice(e+1)}function k(s){let e=s.lastIndexOf("/");return e===-1?"":s.slice(0,e)}function $e(s){for(;s;){if(C(s).startsWith("."))return!0;s=k(s)}return!1}function Lt(s){let e=C(s),t=e.lastIndexOf(".");return t===-1||t===e.length-1||t===0?e:e.substr(0,t)}function Ct(s){let e=s.lastIndexOf(".");return e===-1||e===s.length-1||e===0?s:s.substr(0,e)}function T(s){let e=s.lastIndexOf(".");return e===-1||e===s.length-1||e===0?"":s.substr(e+1).toLowerCase()}function H(s){return Ge(G(s)).normalize("NFC")}function G(s){return s=s.replace(/([\\/])+/g,"/").replace(/(^\/+|\/+$)/g,""),s===""&&(s="/"),s}function ie(s){return s.buffer.slice(s.byteOffset,s.byteOffset+s.byteLength)}function Qe(s){return Buffer.from(s)}var xi=5;function Ii(s,e){if(e.isFile())return{type:"file",realpath:s,ctime:Math.round(e.birthtimeMs),mtime:Math.round(e.mtimeMs),size:e.size};if(e.isDirectory())return{type:"folder",realpath:s}}function Xe(s){return{ctime:Math.round(s.birthtimeMs),mtime:Math.round(s.mtimeMs),size:s.size}}var Ot=typeof process<"u"?process:null,Rt=Ot?Ot.platform:"",Nt=Rt==="darwin",kt=Rt==="win32",de=Nt||kt,me=class{constructor(e,t,i,r,n,o,a){this.thingsHappening=It(this.kill.bind(this),60*1e3,!0);this.resourcePathPrefix=o,this.basePath=a,this.fs=e,this.fsPromises=e.promises,this.path=t,this.url=i,this.trash=r,this.files={},this.promise=Promise.resolve(),this.watchers={},this.handler=null,this.btime=n,this.insensitive=Nt||kt;try{this.testInsensitive()}catch(l){console.error(l)}}testInsensitive(){let{fs:e,path:t,basePath:i}=this,r=t.join(i,".OBSIDIANTEST"),n=t.join(i,".OBSIDIANTEST".toLowerCase());e.existsSync(r)&&e.unlinkSync(r),e.writeFileSync(r,"","utf8"),this.insensitive=e.existsSync(n),e.unlinkSync(r)}getName(){return this.path.basename(this.basePath)}getBasePath(){return this.basePath}async listAll(){this.files={},this.files["/"]={type:"folder",realpath:"/"},await this.listRecursive("")}async listRecursive(e){let t=this.getFullRealPath(e),i=await this.fsPromises.readdir(t);this.thingsHappening();let r=[];for(let n of i)r.push(this.listRecursiveChild(e,n));await Promise.all(r)}async listRecursiveChild(e,t){let i=G(e===""?t:e+"/"+t),r=H(i);if(this.trigger("raw",r),$e(r))return await this.reconcileDeletion(i,r);try{await this.reconcileFileInternal(i,r)}catch(n){if(n.code==="ENOENT")await this.reconcileDeletion(i,r,!0);else throw n}}mkdir(e){return this.queue(async()=>{let t=this.getFullPath(e);await this.fsPromises.mkdir(t,{recursive:!0}),await this.reconcileInternalFile(e)})}trashSystem(e){return this.queue(async()=>{let t=this.getFullPath(e);return this.trash(t)?(await this.reconcileInternalFile(e),!0):!1})}trashLocal(e){return this.queue(async()=>{let t=this.getFullPath(e),i=this.getFullPath(".trash");await this.fsPromises.mkdir(i,{recursive:!0});let r=this.path.extname(t),n=this.path.basename(t,r),o=this.path.join(i,n+r),a=1;for(;await this._exists(o);)a++,o=this.path.join(i,n+" "+a+r);await this.fsPromises.rename(t,o),await this.reconcileInternalFile(e)})}rmdir(e,t){return this.queue(async()=>{let i=this.getFullPath(e);await this.fsPromises.rm(i,{maxRetries:xi,recursive:t}),await this.reconcileInternalFile(e)})}read(e){return this.queue(async()=>{let t=this.getFullPath(e);try{return this.fsPromises.readFile(t,"utf8")}catch(i){throw this.queue(()=>this.reconcileInternalFile(e)),i}})}readBinary(e){return this.queue(async()=>{let t=this.getFullPath(e);try{let i=await this.fsPromises.readFile(t);return ie(i)}catch(i){throw this.queue(()=>this.reconcileInternalFile(e)),i}})}write(e,t,i){return this.queue(async()=>{let r=this.getFullPath(e);try{await this.fsPromises.writeFile(r,t,"utf8"),await this.applyWriteOptions(r,i)}finally{await this.reconcileInternalFile(e)}})}writeBinary(e,t,i){return this.queue(async()=>{let r=this.getFullPath(e),n=Qe(t);try{await this.fsPromises.writeFile(r,n),await this.applyWriteOptions(r,i)}finally{await this.reconcileInternalFile(e)}})}append(e,t,i){return this.queue(async()=>{let r=this.getFullPath(e);try{await this.fsPromises.appendFile(r,t,"utf8"),await this.applyWriteOptions(r,i)}finally{await this.reconcileInternalFile(e)}})}appendBinary(e,t,i){return this.queue(async()=>{let r=this.getFullPath(e),n=Qe(t);try{await this.fsPromises.appendFile(r,n),await this.applyWriteOptions(r,i)}finally{await this.reconcileInternalFile(e)}})}process(e,t,i){return this.queue(async()=>{let r=this.getFullPath(e),n=await this.fsPromises.readFile(r,"utf8"),o=t(n);if(o===n)return n;try{await this.fsPromises.writeFile(r,o,"utf8"),await this.applyWriteOptions(r,i)}finally{await this.reconcileInternalFile(e)}return o})}async applyWriteOptions(e,t){if(!t)return;let{ctime:i,mtime:r,immediate:n}=t;i&&this.btime(e,i),r&&await this.fsPromises.utimes(e,r/1e3,r/1e3),n&&n()}getResourcePath(e){let t=this.getFullPath(e),i=0,r=this.files[e];r&&r.type==="file"&&(i=r.mtime),i||(i=Date.now());let n=this.url.pathToFileURL(t).href;return n.startsWith("file:///")?n=n.substring(8):n.startsWith("file://")&&(n="%5C%5C"+n.substring(7)),this.resourcePathPrefix+n+"?"+i}getFilePath(e){let t=this.getFullPath(e);return this.url.pathToFileURL(t).toString()}remove(e){return this.queue(async()=>{let t=this.getFullPath(e);await this.fsPromises.unlink(t),await this.reconcileInternalFile(e)})}update(e){return this.queue(async()=>{await this.reconcileInternalFile(e)})}async rename(e,t){e!==t&&await this.queue(async()=>{let i=this.getFullPath(e),r=this.getFullPath(t);if(await this._exists(r,!1)&&!(this.insensitive&&e.toLowerCase()===t.toLowerCase()))throw new Error("Destination file already exists!");let n=this.files[e],o=n?n.realpath:null;if(await this.fsPromises.rename(i,r),!n)return;delete this.files[e];let a=this.getRealPath(t);if(n.realpath=a,this.files[t]=n,this.trigger("renamed",t,e),n.type==="folder"&&this.watchers.hasOwnProperty(e)&&(this.stopWatchPath(e),await this.startWatchPath(t)),n.type==="folder"){for(let u in this.files)if(this.files.hasOwnProperty(u)&&u.startsWith(e+"/")){let c=u.slice(e.length),p=t+c,d=this.files[u];delete this.files[u];let F=d.realpath.slice(o.length);d.realpath=a+F,this.files[p]=d,this.trigger("renamed",p,u)}}})}async copyRecursive(e,t){let i=await this.fsPromises.stat(e);if(i.isFile()&&await this.fsPromises.copyFile(e,t,this.fs.constants.COPYFILE_EXCL),i.isDirectory()){await this.fsPromises.mkdir(t,{recursive:!0});let r=await this.fsPromises.readdir(e);for(let n of r){let o=this.path.join(e,n),a=this.path.join(t,n);await this.copyRecursive(o,a)}}}async copy(e,t){await this.queue(async()=>{let i=this.getFullPath(e),r=this.getFullPath(t);await this.copyRecursive(i,r),await this.reconcileInternalFile(t)})}async exists(e,t){return this.queue(()=>{let i=this.getFullPath(e);return this._exists(i,t)})}async _exists(e,t){try{await this.fsPromises.access(e)}catch{return!1}if(t&&this.insensitive){let i=this.path.dirname(e),r=this.path.basename(e);if((await this.fsPromises.readdir(i)).indexOf(r)===-1)return!1}return!0}async stat(e){return this.queue(async()=>{let t=this.getFullPath(e);try{let i=await this.fsPromises.stat(t);if(i.isFile())return{type:"file",...Xe(i)};if(i.isDirectory())return{type:"folder",...Xe(i)}}catch(i){if(i.code!=="ENOENT")throw i}return null})}async list(e){return this.queue(async()=>{let t=this.getFullPath(e),i=await this.fsPromises.readdir(t),r={folders:[],files:[]};for(let n of i){let o=G(e===""?n:e+"/"+n),a=H(o),l=await this.fsPromises.stat(this.getFullRealPath(o));l.isFile()&&r.files.push(a),l.isDirectory()&&r.folders.push(a)}return r})}async watch(e){return this.stopWatch(),this.handler=e,await this.startWatchPath("/"),this.queue(()=>this.listAll())}async watchHiddenRecursive(e){if(!de)try{let t=this.getFullRealPath(e),i=await this.fsPromises.readdir(t);await this.startWatchPath(e);for(let r of i)try{let n=G(e===""?r:e+"/"+r),o=this.getFullRealPath(n);(await this.fsPromises.lstat(o)).isDirectory()&&await this.watchHiddenRecursive(n)}catch{}}catch{}}stopWatch(){for(let e in this.watchers)this.watchers.hasOwnProperty(e)&&this.stopWatchPath(e);this.handler=null}async startWatchPath(e){let t=this.getRealPath(e);if(this.watchers[e])return;let i=this.getFullPath(e),r=i;try{r=await this.fsPromises.realpath(i)}catch(o){o.code!=="ENOENT"&&console.error(o)}let n=this.fs.watch(i,{persistent:!1,encoding:"utf8",recursive:de});n.on("change",(o,a)=>{let l=t==="/"?a:t+"/"+a;this.onFileChange(l)}),n.on("error",()=>{this.onFileChange(t)}),this.watchers[e]={watcher:n,resolvedPath:r}}stopWatchPath(e){let t=this.watchers[e];t&&(t.watcher.close(),delete this.watchers[e])}onFileChange(e){e&&(e=G(e),setTimeout(()=>{let t=H(e);this.queue(()=>this.reconcileFile(e,t,!1))},0))}async reconcileInternalFile(e){return this.reconcileFile(this.getRealPath(e),e)}async reconcileFile(e,t,i=!0){if(this.trigger("raw",t),$e(t))return await this.reconcileDeletion(e,t,i);let r=k(t);r&&r!=="/"&&(this.files[t]||await this.reconcileFile(k(e),r,i));try{let n=this.getFullRealPath(e);if(this.insensitive){let o=this.path.dirname(n),a=this.path.basename(t),l=await this.fsPromises.readdir(o);if(l=l.map(u=>Ge(u).normalize("NFC")),l.indexOf(a)===-1)return await this.reconcileDeletion(e,t,i)}await this.reconcileFileInternal(e,t)}catch(n){n.code==="ENOENT"?await this.reconcileDeletion(e,t,i):console.error(n)}}async reconcileFileInternal(e,t){let i=this.getFullRealPath(e),r=await this.fsPromises.lstat(i);r.isFile()?await this.reconcileFileCreation(e,t,r):r.isDirectory()?await this.reconcileFolderCreation(e,t):r.isSymbolicLink()&&await this.reconcileSymbolicLinkCreation(e,t)}async reconcileFileCreation(e,t,i){let r=Xe(i),n=this.files[t];if(n)if(n.realpath=e,n.type==="file"){(n.mtime!==Math.round(i.mtimeMs)||n.size!==i.size)&&(n.mtime=Math.round(i.mtimeMs),n.size=i.size,this.trigger("raw",t,t,r),this.trigger("modified",t,t,r));return}else this.removeFile(t);this.files[t]=Ii(e,i),this.trigger("file-created",t,t,r)}async reconcileFolderCreation(e,t){this.files.hasOwnProperty(t)?this.files[t].realpath=e:(this.files[t]={type:"folder",realpath:e},this.trigger("folder-created",t),de||await this.startWatchPath(t),await this.listRecursive(e))}async reconcileSymbolicLinkCreation(e,t){let i=this.getFullRealPath(e),r;try{r=await this.fsPromises.realpath(i)}catch{return}let n=this.path.sep,o=this.watchers;if(o.hasOwnProperty(t))o[t].resolvedPath=r;else for(let l in o)if(o.hasOwnProperty(l)&&l!==t){let u=o[l].resolvedPath;if(r===u||u.startsWith(r+n)||r.startsWith(u+n))return}let a=await this.fsPromises.stat(i);a.isFile()?await this.reconcileFileCreation(e,t,a):a.isDirectory()&&(de&&await this.startWatchPath(t),await this.reconcileFolderCreation(e,t))}async reconcileDeletion(e,t,i=!0){if(t==="/"){this.trigger("closed",t);return}this.stopWatchPath(t);let r=this.files[t];if(r){if(!i){setTimeout(()=>{this.queue(()=>this.reconcileFile(e,t))},100);return}if(r.type==="folder")for(let n in this.files)this.files.hasOwnProperty(n)&&n.startsWith(t+"/")&&this.removeFile(n);this.removeFile(t)}}trigger(e,t,i,r){this.handler&&this.handler(e,t,i,r)}getRealPath(e){let t=e;for(;t;){if(this.files.hasOwnProperty(t)){let i=e.substr(t.length);return this.files[t].realpath+i}t=k(t)}return e}getFullPath(e){let t=this.getRealPath(e);return this.getFullRealPath(t)}getFullRealPath(e){return this.path.join(this.basePath,e)}kill(){this.killLastAction&&(this.killLastAction(new Error("File system operation timed out.")),this.killLastAction=null)}queue(e){let t=()=>{let r=new Promise((n,o)=>this.killLastAction=o);return this.thingsHappening(),Promise.race([r,e()])},i=this.promise.then(t,t);return this.promise=i,i}removeFile(e){let t=this.files[e];delete this.files[e],t&&(t.type==="file"?this.trigger("file-removed",e):t.type==="folder"&&this.trigger("folder-removed",e))}static async readLocalFile(e){let t=require;if(t){let i=t("fs");return ie(await i.promises.readFile(e))}return null}static async mkdir(e){let t=require;return t?await t("fs").promises.mkdir(e,{recursive:!0}):null}};var Mt=/[^a-zA-Z0-9]/,Bt=/\s/,Ut=/[\r\n]/,Li=/\n\r?\n$/,Ci=/^\r?\n\r?\n/;function M(s,e){return s<e?s:e}function B(s,e){return s>e?s:e}var Oi=/\W/;function Ri(s,e){let t=s.length;for(let i=e;i<t;i+=1)if(Oi.test(s[i]))return i;return-1}function Ni(s,e){let t=0,i=-1;for(;i<s.length-1;)if(i=Ri(s,t),i!==-1){if(t!==i){let n=s.substring(t,i);e(n)}let r=s[i];e(r),t=i+1}else{let r=s.substring(t,s.length);e(r),i=s.length;break}}var ye=class{constructor(){this.diffTimeout=1;this.diffEditCost=4;this.matchThreshold=.5;this.matchDistance=1e3;this.patchDeleteThreshold=.5;this.patchMargin=4;this.matchMaxBits=32}diff_main(e,t,i,r){typeof r>"u"&&(this.diffTimeout<=0?r=Number.MAX_VALUE:r=Date.now()+this.diffTimeout*1e3);let n=r;if(e==null||t==null)throw new Error("Null input. (diff_main)");if(e===t)return e?[[0,e]]:[];typeof i>"u"&&(i=!0);let o=i,a=this.diff_commonPrefix(e,t),l=e.substring(0,a);e=e.substring(a),t=t.substring(a),a=this.diff_commonSuffix(e,t);let u=e.substring(e.length-a);e=e.substring(0,e.length-a),t=t.substring(0,t.length-a);let c=this.diff_compute_(e,t,o,n);return l&&c.unshift([0,l]),u&&c.push([0,u]),this.diff_cleanupMerge(c),c}diff_lineMode(e,t){let{chars1:i,chars2:r,lineArray:n}=this.diff_linesToChars_(e,t),o=this.diff_main(i,r,!1);return this.diff_charsToLines_(o,n),o}diff_wordMode(e,t){let{chars1:i,chars2:r,lineArray:n}=this.diff_wordsToChars_(e,t),o=this.diff_main(i,r,!1);return this.diff_charsToLines_(o,n),o}diff_wordsToChars_(e,t){let i=[],r={};i[0]="";let n=l=>{let u="",c=i.length;return Ni(l,p=>{(r.hasOwnProperty?r.hasOwnProperty(p):r[p]!==void 0)?u+=String.fromCharCode(r[p]):(u+=String.fromCharCode(c),r[p]=c,i[c++]=p)}),u},o=n(e),a=n(t);return{chars1:o,chars2:a,lineArray:i}}diff_commonPrefix(e,t){if(!e||!t||e.charAt(0)!==t.charAt(0))return 0;let i=0,r=M(e.length,t.length),n=r,o=0;for(;i<n;)e.substring(o,n)===t.substring(o,n)?(i=n,o=i):r=n,n=Math.floor((r-i)/2+i);return n}diff_commonSuffix(e,t){if(!e||!t||e.charAt(e.length-1)!==t.charAt(t.length-1))return 0;let i=0,r=M(e.length,t.length),n=r,o=0;for(;i<n;)e.substring(e.length-n,e.length-o)===t.substring(t.length-n,t.length-o)?(i=n,o=i):r=n,n=Math.floor((r-i)/2+i);return n}diff_cleanupSemantic(e){let t=!1,i=[],r=0,n=null,o=0,a=0,l=0,u=0,c=0;for(;o<e.length;)e[o][0]===0?(i[r++]=o,a=u,l=c,u=0,c=0,n=e[o][1]):(e[o][0]===1?u+=e[o][1].length:c+=e[o][1].length,n&&n.length<=B(a,l)&&n.length<=B(u,c)&&(e.splice(i[r-1],0,[-1,n]),e[i[r-1]+1][0]=1,r--,r--,o=r>0?i[r-1]:-1,a=0,l=0,u=0,c=0,n=null,t=!0)),o++;for(t&&this.diff_cleanupMerge(e),this.diff_cleanupSemanticLossless(e),o=1;o<e.length;){if(e[o-1][0]===-1&&e[o][0]===1){let p=e[o-1][1],d=e[o][1],F=this.diff_commonOverlap_(p,d),b=this.diff_commonOverlap_(d,p);F>=b?(F>=p.length/2||F>=d.length/2)&&(e.splice(o,0,[0,d.substring(0,F)]),e[o-1][1]=p.substring(0,p.length-F),e[o+1][1]=d.substring(F),o++):(b>=p.length/2||b>=d.length/2)&&(e.splice(o,0,[0,p.substring(0,b)]),e[o-1][0]=1,e[o-1][1]=d.substring(0,d.length-b),e[o+1][0]=-1,e[o+1][1]=p.substring(b),o++),o++}o++}}diff_cleanupSemanticLossless(e){let t=1;for(;t<e.length-1;){if(e[t-1][0]===0&&e[t+1][0]===0){let i=e[t-1][1],r=e[t][1],n=e[t+1][1],o=this.diff_commonSuffix(i,r);if(o){let p=r.substring(r.length-o);i=i.substring(0,i.length-o),r=p+r.substring(0,r.length-o),n=p+n}let a=i,l=r,u=n,c=this.diff_cleanupSemanticScore_(i,r)+this.diff_cleanupSemanticScore_(r,n);for(;r.charAt(0)===n.charAt(0);){i+=r.charAt(0),r=r.substring(1)+n.charAt(0),n=n.substring(1);let p=this.diff_cleanupSemanticScore_(i,r)+this.diff_cleanupSemanticScore_(r,n);p>=c&&(c=p,a=i,l=r,u=n)}e[t-1][1]!==a&&(a?e[t-1][1]=a:(e.splice(t-1,1),t--),e[t][1]=l,u?e[t+1][1]=u:(e.splice(t+1,1),t--))}t++}}diff_cleanupEfficiency(e){let t=!1,i=[],r=0,n=null,o=0,a=!1,l=!1,u=!1,c=!1;for(;o<e.length;)e[o][0]===0?(e[o][1].length<this.diffEditCost&&(u||c)?(i[r++]=o,a=u,l=c,n=e[o][1]):(r=0,n=null),u=c=!1):(e[o][0]===-1?c=!0:u=!0,n&&(a&&l&&u&&c||n.length<this.diffEditCost/2&&Number(a)+Number(l)+Number(u)+Number(c)===3)&&(e.splice(i[r-1],0,[-1,n]),e[i[r-1]+1][0]=1,r--,n=null,a&&l?(u=c=!0,r=0):(r--,o=r>0?i[r-1]:-1,u=c=!1),t=!0)),o++;t&&this.diff_cleanupMerge(e)}diff_cleanupMerge(e){e.push([0,""]);let t=0,i=0,r=0,n="",o="",a;for(;t<e.length;)switch(e[t][0]){case 1:r++,o+=e[t][1],t++;break;case-1:i++,n+=e[t][1],t++;break;case 0:i+r>1?(i!==0&&r!==0&&(a=this.diff_commonPrefix(o,n),a!==0&&(t-i-r>0&&e[t-i-r-1][0]===0?e[t-i-r-1][1]+=o.substring(0,a):(e.splice(0,0,[0,o.substring(0,a)]),t++),o=o.substring(a),n=n.substring(a)),a=this.diff_commonSuffix(o,n),a!==0&&(e[t][1]=o.substring(o.length-a)+e[t][1],o=o.substring(0,o.length-a),n=n.substring(0,n.length-a))),t-=i+r,e.splice(t,i+r),n.length&&(e.splice(t,0,[-1,n]),t++),o.length&&(e.splice(t,0,[1,o]),t++),t++):t!==0&&e[t-1][0]===0?(e[t-1][1]+=e[t][1],e.splice(t,1)):t++,r=0,i=0,n="",o="";break}e[e.length-1][1]===""&&e.pop();let l=!1;for(t=1;t<e.length-1;)e[t-1][0]===0&&e[t+1][0]===0&&(e[t][1].substring(e[t][1].length-e[t-1][1].length)===e[t-1][1]?(e[t][1]=e[t-1][1]+e[t][1].substring(0,e[t][1].length-e[t-1][1].length),e[t+1][1]=e[t-1][1]+e[t+1][1],e.splice(t-1,1),l=!0):e[t][1].substring(0,e[t+1][1].length)===e[t+1][1]&&(e[t-1][1]+=e[t+1][1],e[t][1]=e[t][1].substring(e[t+1][1].length)+e[t+1][1],e.splice(t+1,1),l=!0)),t++;l&&this.diff_cleanupMerge(e)}diff_xIndex(e,t){let i=0,r=0,n=0,o=0,a;for(a=0;a<e.length&&(e[a][0]!==1&&(i+=e[a][1].length),e[a][0]!==-1&&(r+=e[a][1].length),!(i>t));a++)n=i,o=r;return e.length!==a&&e[a][0]===-1?o:o+(t-n)}diff_prettyHtml(e){let t=[],i=/&/g,r=/</g,n=/>/g,o=/\n/g;for(let a=0;a<e.length;a++){let l=e[a][0],c=e[a][1].replace(i,"&").replace(r,"<").replace(n,">").replace(o,"¶<br>");switch(l){case 1:t[a]='<ins style="background:#e6ffe6;">'+c+"</ins>";break;case-1:t[a]='<del style="background:#ffe6e6;">'+c+"</del>";break;case 0:t[a]="<span>"+c+"</span>";break}}return t.join("")}diff_text1(e){let t=[];for(let i=0;i<e.length;i++)e[i][0]!==1&&(t[i]=e[i][1]);return t.join("")}diff_text2(e){let t=[];for(let i=0;i<e.length;i++)e[i][0]!==-1&&(t[i]=e[i][1]);return t.join("")}diff_levenshtein(e){let t=0,i=0,r=0;for(let n=0;n<e.length;n++){let o=e[n][0],a=e[n][1];switch(o){case 1:i+=a.length;break;case-1:r+=a.length;break;case 0:t+=B(i,r),i=0,r=0;break}}return t+=B(i,r),t}diff_toDelta(e){let t=[];for(let i=0;i<e.length;i++)switch(e[i][0]){case 1:t[i]="+"+encodeURI(e[i][1]);break;case-1:t[i]="-"+e[i][1].length;break;case 0:t[i]="="+e[i][1].length;break}return t.join(" ").replace(/%20/g," ")}diff_fromDelta(e,t){let i=[],r=0,n=0,o=t.split(/\t/g);for(let a=0;a<o.length;a++){let l=o[a].substring(1);switch(o[a].charAt(0)){case"+":try{i[r++]=[1,decodeURI(l)]}catch{throw new Error("Illegal escape in diff_fromDelta: "+l)}break;case"-":case"=":let u=parseInt(l,10);if(isNaN(u)||u<0)throw new Error("Invalid number in diff_fromDelta: "+l);let c=e.substring(n,n+=u);o[a].charAt(0)==="="?i[r++]=[0,c]:i[r++]=[-1,c];break;default:if(o[a])throw new Error("Invalid diff operation in diff_fromDelta: "+o[a])}}if(n!==e.length)throw new Error("Delta length ("+n+") does not equal source text length ("+e.length+")");return i}match_main(e,t,i){if(e==null||t==null||i==null)throw new Error("Null input. (match_main)");return i=B(0,M(i,e.length)),e===t?0:e.length?e.substring(i,i+t.length)===t?i:this.match_bitap_(e,t,i):-1}patch_make(e,t,i){let r,n;if(typeof e=="string"&&typeof t=="string"&&typeof i>"u")r=e,n=this.diff_main(r,t,!0),n.length>2&&(this.diff_cleanupSemantic(n),this.diff_cleanupEfficiency(n));else if(e&&typeof e=="object"&&typeof t>"u"&&typeof i>"u")n=e,r=this.diff_text1(n);else if(typeof e=="string"&&t&&typeof t=="object"&&typeof i>"u")r=e,n=t;else if(typeof e=="string"&&typeof t=="string"&&i&&typeof i=="object")r=e,n=i;else throw new Error("Unknown call format to patch_make");if(n.length===0)return[];let o=[],a=new U,l=0,u=0,c=0,p=r,d=r;for(let F=0;F<n.length;F++){let b=n[F][0],y=n[F][1];switch(!l&&b!==0&&(a.start1=u,a.start2=c),b){case 1:a.diffs[l++]=n[F],a.length2+=y.length,d=d.substring(0,c)+y+d.substring(c);break;case-1:a.length1+=y.length,a.diffs[l++]=n[F],d=d.substring(0,c)+d.substring(c+y.length);break;case 0:y.length<=2*this.patchMargin&&l&&n.length!==F+1?(a.diffs[l++]=n[F],a.length1+=y.length,a.length2+=y.length):y.length>=2*this.patchMargin&&l&&(this.patch_addContext_(a,p),o.push(a),a=new U,l=0,p=d,u=c);break}b!==1&&(u+=y.length),b!==-1&&(c+=y.length)}return l&&(this.patch_addContext_(a,p),o.push(a)),o}patch_deepCopy(e){let t=[];for(let i=0;i<e.length;i++){let r=e[i],n=new U;for(let o=0;o<r.diffs.length;o++)n.diffs[o]=[r.diffs[o][0],r.diffs[o][1]];n.start1=r.start1,n.start2=r.start2,n.length1=r.length1,n.length2=r.length2,t[i]=n}return t}patch_apply(e,t){if(e.length===0)return[t,[]];e=this.patch_deepCopy(e);let i=this.patch_addPadding(e);t=i+t+i,this.patch_splitMax(e);let r=0,n=[];for(let o=0;o<e.length;o++){let a=e[o].start2+r,l=this.diff_text1(e[o].diffs),u,c=-1;if(l.length>this.matchMaxBits?(u=this.match_main(t,l.substring(0,this.matchMaxBits),a),u!==-1&&(c=this.match_main(t,l.substring(l.length-this.matchMaxBits),a+l.length-this.matchMaxBits),(c===-1||u>=c)&&(u=-1))):u=this.match_main(t,l,a),u===-1)n[o]=!1,r-=e[o].length2-e[o].length1;else{n[o]=!0,r=u-a;let p;if(c===-1?p=t.substring(u,u+l.length):p=t.substring(u,c+this.matchMaxBits),l===p)t=t.substring(0,u)+this.diff_text2(e[o].diffs)+t.substring(u+l.length);else{let d=this.diff_main(l,p,!1);if(l.length>this.matchMaxBits&&this.diff_levenshtein(d)/l.length>this.patchDeleteThreshold)n[o]=!1;else{this.diff_cleanupSemanticLossless(d);let F=0,b=0;for(let y=0;y<e[o].diffs.length;y++){let g=e[o].diffs[y];g[0]!==0&&(b=this.diff_xIndex(d,F)),g[0]===1?t=t.substring(0,u+b)+g[1]+t.substring(u+b):g[0]===-1&&(t=t.substring(0,u+b)+t.substring(u+this.diff_xIndex(d,F+g[1].length))),g[0]!==-1&&(F+=g[1].length)}}}}}return t=t.substring(i.length,t.length-i.length),[t,n]}patch_addPadding(e){let t=this.patchMargin,i="";for(let o=1;o<=t;o++)i+=String.fromCharCode(o);for(let o=0;o<e.length;o++)e[o].start1+=t,e[o].start2+=t;let r=e[0],n=r.diffs;if(n.length===0||n[0][0]!==0)n.unshift([0,i]),r.start1-=t,r.start2-=t,r.length1+=t,r.length2+=t;else if(t>n[0][1].length){let o=t-n[0][1].length;n[0][1]=i.substring(n[0][1].length)+n[0][1],r.start1-=o,r.start2-=o,r.length1+=o,r.length2+=o}if(r=e[e.length-1],n=r.diffs,n.length===0||n[n.length-1][0]!==0)n.push([0,i]),r.length1+=t,r.length2+=t;else if(t>n[n.length-1][1].length){let o=t-n[n.length-1][1].length;n[n.length-1][1]+=i.substring(0,o),r.length1+=o,r.length2+=o}return i}patch_splitMax(e){let t=this.matchMaxBits;for(let i=0;i<e.length;i++){if(e[i].length1<=t)continue;let r=e[i];e.splice(i--,1);let n=r.start1,o=r.start2,a="";for(;r.diffs.length!==0;){let l=new U,u=!0;for(l.start1=n-a.length,l.start2=o-a.length,a!==""&&(l.length1=l.length2=a.length,l.diffs.push([0,a]));r.diffs.length!==0&&l.length1<t-this.patchMargin;){let p=r.diffs[0][0],d=r.diffs[0][1];p===1?(l.length2+=d.length,o+=d.length,l.diffs.push(r.diffs.shift()),u=!1):p===-1&&l.diffs.length===1&&l.diffs[0][0]===0&&d.length>2*t?(l.length1+=d.length,n+=d.length,u=!1,l.diffs.push([p,d]),r.diffs.shift()):(d=d.substring(0,t-l.length1-this.patchMargin),l.length1+=d.length,n+=d.length,p===0?(l.length2+=d.length,o+=d.length):u=!1,l.diffs.push([p,d]),d===r.diffs[0][1]?r.diffs.shift():r.diffs[0][1]=r.diffs[0][1].substring(d.length))}a=this.diff_text2(l.diffs),a=a.substring(a.length-this.patchMargin);let c=this.diff_text1(r.diffs).substring(0,this.patchMargin);c!==""&&(l.length1+=c.length,l.length2+=c.length,l.diffs.length!==0&&l.diffs[l.diffs.length-1][0]===0?l.diffs[l.diffs.length-1][1]+=c:l.diffs.push([0,c])),u||e.splice(++i,0,l)}}}patch_toText(e){let t=[];for(let i=0;i<e.length;i++)t[i]=e[i];return t.join("")}patch_fromText(e){let t=[];if(!e)return t;let i=e.split(`
|
|
4
|
-
`),r=0,n=/^@@ -(\d+),?(\d*) \+(\d+),?(\d*) @@$/;for(;r<i.length;){let o=i[r].match(n);if(!o)throw new Error("Invalid patch string: "+i[r]);let a=new U;t.push(a),a.start1=parseInt(o[1],10),o[2]===""?(a.start1--,a.length1=1):o[2]==="0"?a.length1=0:(a.start1--,a.length1=parseInt(o[2],10)),a.start2=parseInt(o[3],10),o[4]===""?(a.start2--,a.length2=1):o[4]==="0"?a.length2=0:(a.start2--,a.length2=parseInt(o[4],10)),r++;let l,u
|
|
5
|
-
`,o),a===-1&&(a=e.length-1);let
|
|
2
|
+
var wi=Object.create;var gt=Object.defineProperty;var vi=Object.getOwnPropertyDescriptor;var Si=Object.getOwnPropertyNames;var Ei=Object.getPrototypeOf,Di=Object.prototype.hasOwnProperty;var Pi=(s,e,t,i)=>{if(e&&typeof e=="object"||typeof e=="function")for(let r of Si(e))!Di.call(s,r)&&r!==t&>(s,r,{get:()=>e[r],enumerable:!(i=vi(e,r))||i.enumerable});return s};var W=(s,e,t)=>(t=s!=null?wi(Ei(s)):{},Pi(e||!s||!s.__esModule?gt(t,"default",{value:s,enumerable:!0}):t,s));var gi=require("commander");var dt=W(require("node:crypto")),D=W(require("node:fs")),N=W(require("node:os")),P=W(require("node:path")),Ne=W(require("node:url"));global.nodeCrypto=dt.default;var pe=null;try{let s=P.default.join(__dirname,"btime",process.platform+"-"+process.arch);pe=require(P.default.join(s,"btime.node")).btime}catch{}function mt(){return pe!==null}function yt(s,e){if(!pe)return;let t=Buffer.alloc(Buffer.byteLength(s,"utf-8")+1);t.write(s,0,t.length-1,"utf-8"),t[t.length-1]=0,pe(t,e)}var ke=["image","audio","video","pdf","unsupported"],K=["image","audio","pdf","video"],Me=["app","appearance","appearance-data","hotkey","core-plugin","core-plugin-data","community-plugin","community-plugin-data"],Be=["app","appearance","appearance-data","hotkey","core-plugin","core-plugin-data"];var Ft="obsidian-headless",Y=N.default.platform()==="linux"?P.default.join(process.env.XDG_CONFIG_HOME||P.default.join(N.default.homedir(),".config"),Ft):P.default.join(N.default.homedir(),"."+Ft),bt="OBSIDIAN_AUTH_TOKEN",Ue=P.default.join(Y,"auth_token");function J(){if(process.env[bt])return process.env[bt];try{return D.default.readFileSync(Ue,"utf8")}catch{return null}}function wt(s){D.default.existsSync(Y)||D.default.mkdirSync(Y,{recursive:!0,mode:448}),D.default.writeFileSync(Ue,s,{mode:384})}function Ve(){D.default.rmSync(Ue,{force:!0})}function Z(s){return P.default.join(Y,"sync",s)}function vt(s){return P.default.join(Z(s),"state.db")}function St(s){return P.default.join(Z(s),"sync.log")}function Et(s){return P.default.join(Z(s),"config.json")}function je(s){let e=Z(s);return D.default.existsSync(e)||D.default.mkdirSync(e,{recursive:!0,mode:448}),e}function qe(s){let e=Et(s);if(!D.default.existsSync(e))return null;try{let t=D.default.readFileSync(e,"utf-8");return JSON.parse(t)}catch{return null}}function We(s,e){je(s);let t=Et(s);D.default.writeFileSync(t,JSON.stringify(e,null,2),{mode:384})}function Dt(s,e){return P.default.join(s,e,".sync.lock")}function Pt(s){let e=Z(s);D.default.existsSync(e)&&D.default.rmSync(e,{recursive:!0,force:!0})}function Ke(){let s=P.default.join(Y,"sync");if(!D.default.existsSync(s))return[];let e=D.default.readdirSync(s,{withFileTypes:!0}),t=[];for(let i of e)if(i.isDirectory()){let r=P.default.join(s,i.name,"config.json");D.default.existsSync(r)&&t.push(i.name)}return t}function z(s){let e=P.default.resolve(s),t=Ke();for(let i of t){let r=qe(i);if(r&&P.default.resolve(r.vaultPath)===e)return r}return null}function At(s){let e=s.split(",").map(t=>t.trim().toLowerCase());for(let t of e)if(!ke.includes(t))throw new Error(`Invalid file type: "${t}". Valid values: ${ke.join(", ")}`);return e}function _t(s){let e=s.split(",").map(t=>t.trim().toLowerCase());for(let t of e)if(!Me.includes(t))throw new Error(`Invalid config: "${t}". Valid values: ${Me.join(", ")}`);return e}function He(s){if(s){if(!s.startsWith(".")||s.includes("/")||s.includes("\\"))throw new Error(`Invalid config directory: "${s}". Must be a dotfolder name (e.g. .obsidian).`);return s}}function $e(){let s=N.default.hostname(),e=N.default.platform();return`${s} (${e==="darwin"?"macOS":e==="win32"?"Windows":e==="linux"?"Linux":e})`}function Tt(s){let e=P.default.dirname(s);D.default.existsSync(e)||D.default.mkdirSync(e,{recursive:!0});let t=D.default.createWriteStream(s,{flags:"a"}),i=console.log,r=console.warn,n=console.error,o=console.debug;function a(...l){let c=new Date().toISOString(),u=l.map(p=>typeof p=="object"?JSON.stringify(p):String(p)).join(" ");t.write(`[${c}] ${u}
|
|
3
|
+
`)}return console.log=(...l)=>{i(...l),a(...l)},console.warn=(...l)=>{r(...l),a(...l)},console.error=(...l)=>{n(...l),a(...l)},console.debug=(...l)=>{o(...l),a(...l)},()=>{console.log=i,console.warn=r,console.error=n,console.debug=o,t.end()}}var ee=()=>typeof activeWindow<"u"?activeWindow:global;function xt(s,e=0,t=!1){let i=null,r=null,n=null,o=0,a=0,l=ee(),c=function(){let d=r,w=n;return r=null,n=null,s.apply(d,w)},u=function(){if(o){let d=Date.now();if(d<o){l=ee(),i=l.setTimeout(u,o-d),o=0;return}}a=0,i=null,c()},p=function(...d){r=this,n=d;let w=Date.now();return i?t?o=a=w+e:l!==ee()&&a<=w&&(l.clearTimeout(i),l=ee(),i=l.setTimeout(u,0)):(l=ee(),a=w+e,i=l.setTimeout(u,e)),p};return p.cancel=function(){return i&&(l.clearTimeout(i),i=null),p},p.run=function(){if(i)return l.clearTimeout(i),i=null,c()},p}var Ai=/\u00A0|\u202F/g;function Ge(s){return s.replace(Ai," ")}function C(s){let e=s.lastIndexOf("/");return e===-1?s:s.slice(e+1)}function k(s){let e=s.lastIndexOf("/");return e===-1?"":s.slice(0,e)}function Qe(s){for(;s;){if(C(s).startsWith("."))return!0;s=k(s)}return!1}function It(s){let e=C(s),t=e.lastIndexOf(".");return t===-1||t===e.length-1||t===0?e:e.substr(0,t)}function Lt(s){let e=s.lastIndexOf(".");return e===-1||e===s.length-1||e===0?s:s.substr(0,e)}function T(s){let e=s.lastIndexOf(".");return e===-1||e===s.length-1||e===0?"":s.substr(e+1).toLowerCase()}function H(s){return Ge($(s)).normalize("NFC")}function $(s){return s=s.replace(/([\\/])+/g,"/").replace(/(^\/+|\/+$)/g,""),s===""&&(s="/"),s}function te(s){return s.buffer.slice(s.byteOffset,s.byteOffset+s.byteLength)}function Xe(s){return Buffer.from(s)}var _i=5;function Ti(s,e){if(e.isFile())return{type:"file",realpath:s,ctime:Math.round(e.birthtimeMs),mtime:Math.round(e.mtimeMs),size:e.size};if(e.isDirectory())return{type:"folder",realpath:s}}function Ye(s){return{ctime:Math.round(s.birthtimeMs),mtime:Math.round(s.mtimeMs),size:s.size}}var Ct=typeof process<"u"?process:null,Ot=Ct?Ct.platform:"",Rt=Ot==="darwin",Nt=Ot==="win32",ge=Rt||Nt,de=class{constructor(e,t,i,r,n,o,a){this.thingsHappening=xt(this.kill.bind(this),60*1e3,!0);this.resourcePathPrefix=o,this.basePath=a,this.fs=e,this.fsPromises=e.promises,this.path=t,this.url=i,this.trash=r,this.files={},this.promise=Promise.resolve(),this.watchers={},this.handler=null,this.btime=n,this.insensitive=Rt||Nt;try{this.testInsensitive()}catch(l){console.error(l)}}testInsensitive(){let{fs:e,path:t,basePath:i}=this,r=t.join(i,".OBSIDIANTEST"),n=t.join(i,".OBSIDIANTEST".toLowerCase());e.existsSync(r)&&e.unlinkSync(r),e.writeFileSync(r,"","utf8"),this.insensitive=e.existsSync(n),e.unlinkSync(r)}getName(){return this.path.basename(this.basePath)}getBasePath(){return this.basePath}async listAll(){this.files={},this.files["/"]={type:"folder",realpath:"/"},await this.listRecursive("")}async listRecursive(e){let t=this.getFullRealPath(e),i=await this.fsPromises.readdir(t);this.thingsHappening();let r=[];for(let n of i)r.push(this.listRecursiveChild(e,n));await Promise.all(r)}async listRecursiveChild(e,t){let i=$(e===""?t:e+"/"+t),r=H(i);if(this.trigger("raw",r),Qe(r))return await this.reconcileDeletion(i,r);try{await this.reconcileFileInternal(i,r)}catch(n){if(n.code==="ENOENT")await this.reconcileDeletion(i,r,!0);else throw n}}mkdir(e){return this.queue(async()=>{let t=this.getFullPath(e);await this.fsPromises.mkdir(t,{recursive:!0}),await this.reconcileInternalFile(e)})}trashSystem(e){return this.queue(async()=>{let t=this.getFullPath(e);return this.trash(t)?(await this.reconcileInternalFile(e),!0):!1})}trashLocal(e){return this.queue(async()=>{let t=this.getFullPath(e),i=this.getFullPath(".trash");await this.fsPromises.mkdir(i,{recursive:!0});let r=this.path.extname(t),n=this.path.basename(t,r),o=this.path.join(i,n+r),a=1;for(;await this._exists(o);)a++,o=this.path.join(i,n+" "+a+r);await this.fsPromises.rename(t,o),await this.reconcileInternalFile(e)})}rmdir(e,t){return this.queue(async()=>{let i=this.getFullPath(e);await this.fsPromises.rm(i,{maxRetries:_i,recursive:t}),await this.reconcileInternalFile(e)})}read(e){return this.queue(async()=>{let t=this.getFullPath(e);try{return this.fsPromises.readFile(t,"utf8")}catch(i){throw this.queue(()=>this.reconcileInternalFile(e)),i}})}readBinary(e){return this.queue(async()=>{let t=this.getFullPath(e);try{let i=await this.fsPromises.readFile(t);return te(i)}catch(i){throw this.queue(()=>this.reconcileInternalFile(e)),i}})}write(e,t,i){return this.queue(async()=>{let r=this.getFullPath(e);try{await this.fsPromises.writeFile(r,t,"utf8"),await this.applyWriteOptions(r,i)}finally{await this.reconcileInternalFile(e)}})}writeBinary(e,t,i){return this.queue(async()=>{let r=this.getFullPath(e),n=Xe(t);try{await this.fsPromises.writeFile(r,n),await this.applyWriteOptions(r,i)}finally{await this.reconcileInternalFile(e)}})}append(e,t,i){return this.queue(async()=>{let r=this.getFullPath(e);try{await this.fsPromises.appendFile(r,t,"utf8"),await this.applyWriteOptions(r,i)}finally{await this.reconcileInternalFile(e)}})}appendBinary(e,t,i){return this.queue(async()=>{let r=this.getFullPath(e),n=Xe(t);try{await this.fsPromises.appendFile(r,n),await this.applyWriteOptions(r,i)}finally{await this.reconcileInternalFile(e)}})}process(e,t,i){return this.queue(async()=>{let r=this.getFullPath(e),n=await this.fsPromises.readFile(r,"utf8"),o=t(n);if(o===n)return n;try{await this.fsPromises.writeFile(r,o,"utf8"),await this.applyWriteOptions(r,i)}finally{await this.reconcileInternalFile(e)}return o})}async applyWriteOptions(e,t){if(!t)return;let{ctime:i,mtime:r,immediate:n}=t;i&&this.btime(e,i),r&&await this.fsPromises.utimes(e,r/1e3,r/1e3),n&&n()}getResourcePath(e){let t=this.getFullPath(e),i=0,r=this.files[e];r&&r.type==="file"&&(i=r.mtime),i||(i=Date.now());let n=this.url.pathToFileURL(t).href;return n.startsWith("file:///")?n=n.substring(8):n.startsWith("file://")&&(n="%5C%5C"+n.substring(7)),this.resourcePathPrefix+n+"?"+i}getFilePath(e){let t=this.getFullPath(e);return this.url.pathToFileURL(t).toString()}remove(e){return this.queue(async()=>{let t=this.getFullPath(e);await this.fsPromises.unlink(t),await this.reconcileInternalFile(e)})}update(e){return this.queue(async()=>{await this.reconcileInternalFile(e)})}async rename(e,t){e!==t&&await this.queue(async()=>{let i=this.getFullPath(e),r=this.getFullPath(t);if(await this._exists(r,!1)&&!(this.insensitive&&e.toLowerCase()===t.toLowerCase()))throw new Error("Destination file already exists!");let n=this.files[e],o=n?n.realpath:null;if(await this.fsPromises.rename(i,r),!n)return;delete this.files[e];let a=this.getRealPath(t);if(n.realpath=a,this.files[t]=n,this.trigger("renamed",t,e),n.type==="folder"&&this.watchers.hasOwnProperty(e)&&(this.stopWatchPath(e),await this.startWatchPath(t)),n.type==="folder"){for(let c in this.files)if(this.files.hasOwnProperty(c)&&c.startsWith(e+"/")){let u=c.slice(e.length),p=t+u,d=this.files[c];delete this.files[c];let w=d.realpath.slice(o.length);d.realpath=a+w,this.files[p]=d,this.trigger("renamed",p,c)}}})}async copyRecursive(e,t){let i=await this.fsPromises.stat(e);if(i.isFile()&&await this.fsPromises.copyFile(e,t,this.fs.constants.COPYFILE_EXCL),i.isDirectory()){await this.fsPromises.mkdir(t,{recursive:!0});let r=await this.fsPromises.readdir(e);for(let n of r){let o=this.path.join(e,n),a=this.path.join(t,n);await this.copyRecursive(o,a)}}}async copy(e,t){await this.queue(async()=>{let i=this.getFullPath(e),r=this.getFullPath(t);await this.copyRecursive(i,r),await this.reconcileInternalFile(t)})}async exists(e,t){return this.queue(()=>{let i=this.getFullPath(e);return this._exists(i,t)})}async _exists(e,t){try{await this.fsPromises.access(e)}catch{return!1}if(t&&this.insensitive){let i=this.path.dirname(e),r=this.path.basename(e);if((await this.fsPromises.readdir(i)).indexOf(r)===-1)return!1}return!0}async stat(e){return this.queue(async()=>{let t=this.getFullPath(e);try{let i=await this.fsPromises.stat(t);if(i.isFile())return{type:"file",...Ye(i)};if(i.isDirectory())return{type:"folder",...Ye(i)}}catch(i){if(i.code!=="ENOENT")throw i}return null})}async list(e){return this.queue(async()=>{let t=this.getFullPath(e),i=await this.fsPromises.readdir(t),r={folders:[],files:[]};for(let n of i){let o=$(e===""?n:e+"/"+n),a=H(o),l=await this.fsPromises.stat(this.getFullRealPath(o));l.isFile()&&r.files.push(a),l.isDirectory()&&r.folders.push(a)}return r})}async watch(e){return this.stopWatch(),this.handler=e,await this.startWatchPath("/"),this.queue(()=>this.listAll())}async watchHiddenRecursive(e){if(!ge)try{let t=this.getFullRealPath(e),i=await this.fsPromises.readdir(t);await this.startWatchPath(e);for(let r of i)try{let n=$(e===""?r:e+"/"+r),o=this.getFullRealPath(n);(await this.fsPromises.lstat(o)).isDirectory()&&await this.watchHiddenRecursive(n)}catch{}}catch{}}stopWatch(){for(let e in this.watchers)this.watchers.hasOwnProperty(e)&&this.stopWatchPath(e);this.handler=null}async startWatchPath(e){let t=this.getRealPath(e);if(this.watchers[e])return;let i=this.getFullPath(e),r=i;try{r=await this.fsPromises.realpath(i)}catch(o){o.code!=="ENOENT"&&console.error(o)}let n=this.fs.watch(i,{persistent:!1,encoding:"utf8",recursive:ge});n.on("change",(o,a)=>{let l=t==="/"?a:t+"/"+a;this.onFileChange(l)}),n.on("error",()=>{this.onFileChange(t)}),this.watchers[e]={watcher:n,resolvedPath:r}}stopWatchPath(e){let t=this.watchers[e];t&&(t.watcher.close(),delete this.watchers[e])}onFileChange(e){e&&(e=$(e),setTimeout(()=>{let t=H(e);this.queue(()=>this.reconcileFile(e,t,!1))},0))}async reconcileInternalFile(e){return this.reconcileFile(this.getRealPath(e),e)}async reconcileFile(e,t,i=!0){if(this.trigger("raw",t),Qe(t))return await this.reconcileDeletion(e,t,i);let r=k(t);r&&r!=="/"&&(this.files[t]||await this.reconcileFile(k(e),r,i));try{let n=this.getFullRealPath(e);if(this.insensitive){let o=this.path.dirname(n),a=this.path.basename(t),l=await this.fsPromises.readdir(o);if(l=l.map(c=>Ge(c).normalize("NFC")),l.indexOf(a)===-1)return await this.reconcileDeletion(e,t,i)}await this.reconcileFileInternal(e,t)}catch(n){n.code==="ENOENT"?await this.reconcileDeletion(e,t,i):console.error(n)}}async reconcileFileInternal(e,t){let i=this.getFullRealPath(e),r=await this.fsPromises.lstat(i);r.isFile()?await this.reconcileFileCreation(e,t,r):r.isDirectory()?await this.reconcileFolderCreation(e,t):r.isSymbolicLink()&&await this.reconcileSymbolicLinkCreation(e,t)}async reconcileFileCreation(e,t,i){let r=Ye(i),n=this.files[t];if(n)if(n.realpath=e,n.type==="file"){(n.mtime!==Math.round(i.mtimeMs)||n.size!==i.size)&&(n.mtime=Math.round(i.mtimeMs),n.size=i.size,this.trigger("raw",t,t,r),this.trigger("modified",t,t,r));return}else this.removeFile(t);this.files[t]=Ti(e,i),this.trigger("file-created",t,t,r)}async reconcileFolderCreation(e,t){this.files.hasOwnProperty(t)?this.files[t].realpath=e:(this.files[t]={type:"folder",realpath:e},this.trigger("folder-created",t),ge||await this.startWatchPath(t),await this.listRecursive(e))}async reconcileSymbolicLinkCreation(e,t){let i=this.getFullRealPath(e),r;try{r=await this.fsPromises.realpath(i)}catch{return}let n=this.path.sep,o=this.watchers;if(o.hasOwnProperty(t))o[t].resolvedPath=r;else for(let l in o)if(o.hasOwnProperty(l)&&l!==t){let c=o[l].resolvedPath;if(r===c||c.startsWith(r+n)||r.startsWith(c+n))return}let a=await this.fsPromises.stat(i);a.isFile()?await this.reconcileFileCreation(e,t,a):a.isDirectory()&&(ge&&await this.startWatchPath(t),await this.reconcileFolderCreation(e,t))}async reconcileDeletion(e,t,i=!0){if(t==="/"){this.trigger("closed",t);return}this.stopWatchPath(t);let r=this.files[t];if(r){if(!i){setTimeout(()=>{this.queue(()=>this.reconcileFile(e,t))},100);return}if(r.type==="folder")for(let n in this.files)this.files.hasOwnProperty(n)&&n.startsWith(t+"/")&&this.removeFile(n);this.removeFile(t)}}trigger(e,t,i,r){this.handler&&this.handler(e,t,i,r)}getRealPath(e){let t=e;for(;t;){if(this.files.hasOwnProperty(t)){let i=e.substr(t.length);return this.files[t].realpath+i}t=k(t)}return e}getFullPath(e){let t=this.getRealPath(e);return this.getFullRealPath(t)}getFullRealPath(e){return this.path.join(this.basePath,e)}kill(){this.killLastAction&&(this.killLastAction(new Error("File system operation timed out.")),this.killLastAction=null)}queue(e){let t=()=>{let r=new Promise((n,o)=>this.killLastAction=o);return this.thingsHappening(),Promise.race([r,e()])},i=this.promise.then(t,t);return this.promise=i,i}removeFile(e){let t=this.files[e];delete this.files[e],t&&(t.type==="file"?this.trigger("file-removed",e):t.type==="folder"&&this.trigger("folder-removed",e))}static async readLocalFile(e){let t=require;if(t){let i=t("fs");return te(await i.promises.readFile(e))}return null}static async mkdir(e){let t=require;return t?await t("fs").promises.mkdir(e,{recursive:!0}):null}};var kt=W(require("better-sqlite3"));var xi=1,me=class{constructor(e){let t=P.default.dirname(e);D.default.existsSync(t)||D.default.mkdirSync(t,{recursive:!0}),this.db=new kt.default(e),this.db.pragma("journal_mode = WAL"),this.db.exec("CREATE TABLE IF NOT EXISTS meta (key TEXT PRIMARY KEY, value TEXT );"),this.db.exec("CREATE TABLE IF NOT EXISTS local_files (path TEXT PRIMARY KEY, data TEXT NOT NULL);"),this.db.exec("CREATE TABLE IF NOT EXISTS server_files (path TEXT PRIMARY KEY, data TEXT NOT NULL);"),this.db.exec("CREATE TABLE IF NOT EXISTS pending_files (uid INTEGER PRIMARY KEY, path TEXT, data TEXT NOT NULL)"),this.stmts={getMeta:this.db.prepare("SELECT value FROM meta WHERE key = ?"),setMeta:this.db.prepare("INSERT OR REPLACE INTO meta (key, value) VALUES (?, ?)"),getLocalFile:this.db.prepare("SELECT data FROM local_files WHERE path = ?"),setLocalFile:this.db.prepare("INSERT OR REPLACE INTO local_files (path, data) VALUES (?, ?)"),deleteLocalFile:this.db.prepare("DELETE FROM local_files WHERE path = ?"),getAllLocalFiles:this.db.prepare("SELECT path, data FROM local_files"),getServerFile:this.db.prepare("SELECT data FROM server_files WHERE path = ?"),setServerFile:this.db.prepare("INSERT OR REPLACE INTO server_files (path, data) VALUES (?, ?)"),deleteServerFile:this.db.prepare("DELETE FROM server_files WHERE path = ?"),getAllServerFiles:this.db.prepare("SELECT path, data FROM server_files"),addPendingFile:this.db.prepare("INSERT OR REPLACE INTO pending_files (uid, path, data) VALUES (?, ?, ?)"),deletePendingFile:this.db.prepare("DELETE FROM pending_files WHERE path = ?"),getPendingFiles:this.db.prepare("SELECT data FROM pending_files ORDER BY uid")},this.getMetaValue("schema_version")===null&&this.setMetaValue("schema_version",String(xi))}getMetaValue(e){let t=this.stmts.getMeta.get(e);return t?t.value:null}setMetaValue(e,t){this.stmts.setMeta.run(e,t)}getVersion(){let e=this.getMetaValue("version"),t=e?parseInt(e,10):0;return isNaN(t)&&(t=0),t}setVersion(e){this.setMetaValue("version",String(e))}isInitial(){return this.getMetaValue("initial")!=="false"}setInitial(e){this.setMetaValue("initial",e?"true":"false")}getLocalFile(e){let t=this.stmts.getLocalFile.get(e);if(!t)return null;try{return JSON.parse(t.data)}catch{return null}}setLocalFile(e){this.stmts.setLocalFile.run(e.path,JSON.stringify(e))}deleteLocalFile(e){this.stmts.deleteLocalFile.run(e)}getAllLocalFiles(){let e=this.stmts.getAllLocalFiles.all(),t={};for(let i of e)try{t[i.path]=JSON.parse(i.data)}catch{}return t}getServerFile(e){let t=this.stmts.getServerFile.get(e);if(!t)return null;try{return JSON.parse(t.data)}catch{return null}}setServerFile(e){this.stmts.setServerFile.run(e.path,JSON.stringify(e))}deleteServerFile(e){this.stmts.deleteServerFile.run(e)}getAllServerFiles(){let e=this.stmts.getAllServerFiles.all(),t={};for(let i of e)try{t[i.path]=JSON.parse(i.data)}catch{}return t}addPendingFile(e){this.stmts.addPendingFile.run(e.uid,e.path,JSON.stringify(e))}deletePendingFile(e){this.stmts.deletePendingFile.run(e)}getPendingFiles(){let e=this.stmts.getPendingFiles.all(),t=[];for(let i of e)try{t.push(JSON.parse(i.data))}catch{}return t}close(){this.db.open&&this.db.close()}};var Mt=/[^a-zA-Z0-9]/,Bt=/\s/,Ut=/[\r\n]/,Ii=/\n\r?\n$/,Li=/^\r?\n\r?\n/;function M(s,e){return s<e?s:e}function B(s,e){return s>e?s:e}var Ci=/\W/;function Oi(s,e){let t=s.length;for(let i=e;i<t;i+=1)if(Ci.test(s[i]))return i;return-1}function Ri(s,e){let t=0,i=-1;for(;i<s.length-1;)if(i=Oi(s,t),i!==-1){if(t!==i){let n=s.substring(t,i);e(n)}let r=s[i];e(r),t=i+1}else{let r=s.substring(t,s.length);e(r),i=s.length;break}}var ye=class{constructor(){this.diffTimeout=1;this.diffEditCost=4;this.matchThreshold=.5;this.matchDistance=1e3;this.patchDeleteThreshold=.5;this.patchMargin=4;this.matchMaxBits=32}diff_main(e,t,i,r){typeof r>"u"&&(this.diffTimeout<=0?r=Number.MAX_VALUE:r=Date.now()+this.diffTimeout*1e3);let n=r;if(e==null||t==null)throw new Error("Null input. (diff_main)");if(e===t)return e?[[0,e]]:[];typeof i>"u"&&(i=!0);let o=i,a=this.diff_commonPrefix(e,t),l=e.substring(0,a);e=e.substring(a),t=t.substring(a),a=this.diff_commonSuffix(e,t);let c=e.substring(e.length-a);e=e.substring(0,e.length-a),t=t.substring(0,t.length-a);let u=this.diff_compute_(e,t,o,n);return l&&u.unshift([0,l]),c&&u.push([0,c]),this.diff_cleanupMerge(u),u}diff_lineMode(e,t){let{chars1:i,chars2:r,lineArray:n}=this.diff_linesToChars_(e,t),o=this.diff_main(i,r,!1);return this.diff_charsToLines_(o,n),o}diff_wordMode(e,t){let{chars1:i,chars2:r,lineArray:n}=this.diff_wordsToChars_(e,t),o=this.diff_main(i,r,!1);return this.diff_charsToLines_(o,n),o}diff_wordsToChars_(e,t){let i=[],r={};i[0]="";let n=l=>{let c="",u=i.length;return Ri(l,p=>{(r.hasOwnProperty?r.hasOwnProperty(p):r[p]!==void 0)?c+=String.fromCharCode(r[p]):(c+=String.fromCharCode(u),r[p]=u,i[u++]=p)}),c},o=n(e),a=n(t);return{chars1:o,chars2:a,lineArray:i}}diff_commonPrefix(e,t){if(!e||!t||e.charAt(0)!==t.charAt(0))return 0;let i=0,r=M(e.length,t.length),n=r,o=0;for(;i<n;)e.substring(o,n)===t.substring(o,n)?(i=n,o=i):r=n,n=Math.floor((r-i)/2+i);return n}diff_commonSuffix(e,t){if(!e||!t||e.charAt(e.length-1)!==t.charAt(t.length-1))return 0;let i=0,r=M(e.length,t.length),n=r,o=0;for(;i<n;)e.substring(e.length-n,e.length-o)===t.substring(t.length-n,t.length-o)?(i=n,o=i):r=n,n=Math.floor((r-i)/2+i);return n}diff_cleanupSemantic(e){let t=!1,i=[],r=0,n=null,o=0,a=0,l=0,c=0,u=0;for(;o<e.length;)e[o][0]===0?(i[r++]=o,a=c,l=u,c=0,u=0,n=e[o][1]):(e[o][0]===1?c+=e[o][1].length:u+=e[o][1].length,n&&n.length<=B(a,l)&&n.length<=B(c,u)&&(e.splice(i[r-1],0,[-1,n]),e[i[r-1]+1][0]=1,r--,r--,o=r>0?i[r-1]:-1,a=0,l=0,c=0,u=0,n=null,t=!0)),o++;for(t&&this.diff_cleanupMerge(e),this.diff_cleanupSemanticLossless(e),o=1;o<e.length;){if(e[o-1][0]===-1&&e[o][0]===1){let p=e[o-1][1],d=e[o][1],w=this.diff_commonOverlap_(p,d),v=this.diff_commonOverlap_(d,p);w>=v?(w>=p.length/2||w>=d.length/2)&&(e.splice(o,0,[0,d.substring(0,w)]),e[o-1][1]=p.substring(0,p.length-w),e[o+1][1]=d.substring(w),o++):(v>=p.length/2||v>=d.length/2)&&(e.splice(o,0,[0,p.substring(0,v)]),e[o-1][0]=1,e[o-1][1]=d.substring(0,d.length-v),e[o+1][0]=-1,e[o+1][1]=p.substring(v),o++),o++}o++}}diff_cleanupSemanticLossless(e){let t=1;for(;t<e.length-1;){if(e[t-1][0]===0&&e[t+1][0]===0){let i=e[t-1][1],r=e[t][1],n=e[t+1][1],o=this.diff_commonSuffix(i,r);if(o){let p=r.substring(r.length-o);i=i.substring(0,i.length-o),r=p+r.substring(0,r.length-o),n=p+n}let a=i,l=r,c=n,u=this.diff_cleanupSemanticScore_(i,r)+this.diff_cleanupSemanticScore_(r,n);for(;r.charAt(0)===n.charAt(0);){i+=r.charAt(0),r=r.substring(1)+n.charAt(0),n=n.substring(1);let p=this.diff_cleanupSemanticScore_(i,r)+this.diff_cleanupSemanticScore_(r,n);p>=u&&(u=p,a=i,l=r,c=n)}e[t-1][1]!==a&&(a?e[t-1][1]=a:(e.splice(t-1,1),t--),e[t][1]=l,c?e[t+1][1]=c:(e.splice(t+1,1),t--))}t++}}diff_cleanupEfficiency(e){let t=!1,i=[],r=0,n=null,o=0,a=!1,l=!1,c=!1,u=!1;for(;o<e.length;)e[o][0]===0?(e[o][1].length<this.diffEditCost&&(c||u)?(i[r++]=o,a=c,l=u,n=e[o][1]):(r=0,n=null),c=u=!1):(e[o][0]===-1?u=!0:c=!0,n&&(a&&l&&c&&u||n.length<this.diffEditCost/2&&Number(a)+Number(l)+Number(c)+Number(u)===3)&&(e.splice(i[r-1],0,[-1,n]),e[i[r-1]+1][0]=1,r--,n=null,a&&l?(c=u=!0,r=0):(r--,o=r>0?i[r-1]:-1,c=u=!1),t=!0)),o++;t&&this.diff_cleanupMerge(e)}diff_cleanupMerge(e){e.push([0,""]);let t=0,i=0,r=0,n="",o="",a;for(;t<e.length;)switch(e[t][0]){case 1:r++,o+=e[t][1],t++;break;case-1:i++,n+=e[t][1],t++;break;case 0:i+r>1?(i!==0&&r!==0&&(a=this.diff_commonPrefix(o,n),a!==0&&(t-i-r>0&&e[t-i-r-1][0]===0?e[t-i-r-1][1]+=o.substring(0,a):(e.splice(0,0,[0,o.substring(0,a)]),t++),o=o.substring(a),n=n.substring(a)),a=this.diff_commonSuffix(o,n),a!==0&&(e[t][1]=o.substring(o.length-a)+e[t][1],o=o.substring(0,o.length-a),n=n.substring(0,n.length-a))),t-=i+r,e.splice(t,i+r),n.length&&(e.splice(t,0,[-1,n]),t++),o.length&&(e.splice(t,0,[1,o]),t++),t++):t!==0&&e[t-1][0]===0?(e[t-1][1]+=e[t][1],e.splice(t,1)):t++,r=0,i=0,n="",o="";break}e[e.length-1][1]===""&&e.pop();let l=!1;for(t=1;t<e.length-1;)e[t-1][0]===0&&e[t+1][0]===0&&(e[t][1].substring(e[t][1].length-e[t-1][1].length)===e[t-1][1]?(e[t][1]=e[t-1][1]+e[t][1].substring(0,e[t][1].length-e[t-1][1].length),e[t+1][1]=e[t-1][1]+e[t+1][1],e.splice(t-1,1),l=!0):e[t][1].substring(0,e[t+1][1].length)===e[t+1][1]&&(e[t-1][1]+=e[t+1][1],e[t][1]=e[t][1].substring(e[t+1][1].length)+e[t+1][1],e.splice(t+1,1),l=!0)),t++;l&&this.diff_cleanupMerge(e)}diff_xIndex(e,t){let i=0,r=0,n=0,o=0,a;for(a=0;a<e.length&&(e[a][0]!==1&&(i+=e[a][1].length),e[a][0]!==-1&&(r+=e[a][1].length),!(i>t));a++)n=i,o=r;return e.length!==a&&e[a][0]===-1?o:o+(t-n)}diff_prettyHtml(e){let t=[],i=/&/g,r=/</g,n=/>/g,o=/\n/g;for(let a=0;a<e.length;a++){let l=e[a][0],u=e[a][1].replace(i,"&").replace(r,"<").replace(n,">").replace(o,"¶<br>");switch(l){case 1:t[a]='<ins style="background:#e6ffe6;">'+u+"</ins>";break;case-1:t[a]='<del style="background:#ffe6e6;">'+u+"</del>";break;case 0:t[a]="<span>"+u+"</span>";break}}return t.join("")}diff_text1(e){let t=[];for(let i=0;i<e.length;i++)e[i][0]!==1&&(t[i]=e[i][1]);return t.join("")}diff_text2(e){let t=[];for(let i=0;i<e.length;i++)e[i][0]!==-1&&(t[i]=e[i][1]);return t.join("")}diff_levenshtein(e){let t=0,i=0,r=0;for(let n=0;n<e.length;n++){let o=e[n][0],a=e[n][1];switch(o){case 1:i+=a.length;break;case-1:r+=a.length;break;case 0:t+=B(i,r),i=0,r=0;break}}return t+=B(i,r),t}diff_toDelta(e){let t=[];for(let i=0;i<e.length;i++)switch(e[i][0]){case 1:t[i]="+"+encodeURI(e[i][1]);break;case-1:t[i]="-"+e[i][1].length;break;case 0:t[i]="="+e[i][1].length;break}return t.join(" ").replace(/%20/g," ")}diff_fromDelta(e,t){let i=[],r=0,n=0,o=t.split(/\t/g);for(let a=0;a<o.length;a++){let l=o[a].substring(1);switch(o[a].charAt(0)){case"+":try{i[r++]=[1,decodeURI(l)]}catch{throw new Error("Illegal escape in diff_fromDelta: "+l)}break;case"-":case"=":let c=parseInt(l,10);if(isNaN(c)||c<0)throw new Error("Invalid number in diff_fromDelta: "+l);let u=e.substring(n,n+=c);o[a].charAt(0)==="="?i[r++]=[0,u]:i[r++]=[-1,u];break;default:if(o[a])throw new Error("Invalid diff operation in diff_fromDelta: "+o[a])}}if(n!==e.length)throw new Error("Delta length ("+n+") does not equal source text length ("+e.length+")");return i}match_main(e,t,i){if(e==null||t==null||i==null)throw new Error("Null input. (match_main)");return i=B(0,M(i,e.length)),e===t?0:e.length?e.substring(i,i+t.length)===t?i:this.match_bitap_(e,t,i):-1}patch_make(e,t,i){let r,n;if(typeof e=="string"&&typeof t=="string"&&typeof i>"u")r=e,n=this.diff_main(r,t,!0),n.length>2&&(this.diff_cleanupSemantic(n),this.diff_cleanupEfficiency(n));else if(e&&typeof e=="object"&&typeof t>"u"&&typeof i>"u")n=e,r=this.diff_text1(n);else if(typeof e=="string"&&t&&typeof t=="object"&&typeof i>"u")r=e,n=t;else if(typeof e=="string"&&typeof t=="string"&&i&&typeof i=="object")r=e,n=i;else throw new Error("Unknown call format to patch_make");if(n.length===0)return[];let o=[],a=new U,l=0,c=0,u=0,p=r,d=r;for(let w=0;w<n.length;w++){let v=n[w][0],b=n[w][1];switch(!l&&v!==0&&(a.start1=c,a.start2=u),v){case 1:a.diffs[l++]=n[w],a.length2+=b.length,d=d.substring(0,u)+b+d.substring(u);break;case-1:a.length1+=b.length,a.diffs[l++]=n[w],d=d.substring(0,u)+d.substring(u+b.length);break;case 0:b.length<=2*this.patchMargin&&l&&n.length!==w+1?(a.diffs[l++]=n[w],a.length1+=b.length,a.length2+=b.length):b.length>=2*this.patchMargin&&l&&(this.patch_addContext_(a,p),o.push(a),a=new U,l=0,p=d,c=u);break}v!==1&&(c+=b.length),v!==-1&&(u+=b.length)}return l&&(this.patch_addContext_(a,p),o.push(a)),o}patch_deepCopy(e){let t=[];for(let i=0;i<e.length;i++){let r=e[i],n=new U;for(let o=0;o<r.diffs.length;o++)n.diffs[o]=[r.diffs[o][0],r.diffs[o][1]];n.start1=r.start1,n.start2=r.start2,n.length1=r.length1,n.length2=r.length2,t[i]=n}return t}patch_apply(e,t){if(e.length===0)return[t,[]];e=this.patch_deepCopy(e);let i=this.patch_addPadding(e);t=i+t+i,this.patch_splitMax(e);let r=0,n=[];for(let o=0;o<e.length;o++){let a=e[o].start2+r,l=this.diff_text1(e[o].diffs),c,u=-1;if(l.length>this.matchMaxBits?(c=this.match_main(t,l.substring(0,this.matchMaxBits),a),c!==-1&&(u=this.match_main(t,l.substring(l.length-this.matchMaxBits),a+l.length-this.matchMaxBits),(u===-1||c>=u)&&(c=-1))):c=this.match_main(t,l,a),c===-1)n[o]=!1,r-=e[o].length2-e[o].length1;else{n[o]=!0,r=c-a;let p;if(u===-1?p=t.substring(c,c+l.length):p=t.substring(c,u+this.matchMaxBits),l===p)t=t.substring(0,c)+this.diff_text2(e[o].diffs)+t.substring(c+l.length);else{let d=this.diff_main(l,p,!1);if(l.length>this.matchMaxBits&&this.diff_levenshtein(d)/l.length>this.patchDeleteThreshold)n[o]=!1;else{this.diff_cleanupSemanticLossless(d);let w=0,v=0;for(let b=0;b<e[o].diffs.length;b++){let g=e[o].diffs[b];g[0]!==0&&(v=this.diff_xIndex(d,w)),g[0]===1?t=t.substring(0,c+v)+g[1]+t.substring(c+v):g[0]===-1&&(t=t.substring(0,c+v)+t.substring(c+this.diff_xIndex(d,w+g[1].length))),g[0]!==-1&&(w+=g[1].length)}}}}}return t=t.substring(i.length,t.length-i.length),[t,n]}patch_addPadding(e){let t=this.patchMargin,i="";for(let o=1;o<=t;o++)i+=String.fromCharCode(o);for(let o=0;o<e.length;o++)e[o].start1+=t,e[o].start2+=t;let r=e[0],n=r.diffs;if(n.length===0||n[0][0]!==0)n.unshift([0,i]),r.start1-=t,r.start2-=t,r.length1+=t,r.length2+=t;else if(t>n[0][1].length){let o=t-n[0][1].length;n[0][1]=i.substring(n[0][1].length)+n[0][1],r.start1-=o,r.start2-=o,r.length1+=o,r.length2+=o}if(r=e[e.length-1],n=r.diffs,n.length===0||n[n.length-1][0]!==0)n.push([0,i]),r.length1+=t,r.length2+=t;else if(t>n[n.length-1][1].length){let o=t-n[n.length-1][1].length;n[n.length-1][1]+=i.substring(0,o),r.length1+=o,r.length2+=o}return i}patch_splitMax(e){let t=this.matchMaxBits;for(let i=0;i<e.length;i++){if(e[i].length1<=t)continue;let r=e[i];e.splice(i--,1);let n=r.start1,o=r.start2,a="";for(;r.diffs.length!==0;){let l=new U,c=!0;for(l.start1=n-a.length,l.start2=o-a.length,a!==""&&(l.length1=l.length2=a.length,l.diffs.push([0,a]));r.diffs.length!==0&&l.length1<t-this.patchMargin;){let p=r.diffs[0][0],d=r.diffs[0][1];p===1?(l.length2+=d.length,o+=d.length,l.diffs.push(r.diffs.shift()),c=!1):p===-1&&l.diffs.length===1&&l.diffs[0][0]===0&&d.length>2*t?(l.length1+=d.length,n+=d.length,c=!1,l.diffs.push([p,d]),r.diffs.shift()):(d=d.substring(0,t-l.length1-this.patchMargin),l.length1+=d.length,n+=d.length,p===0?(l.length2+=d.length,o+=d.length):c=!1,l.diffs.push([p,d]),d===r.diffs[0][1]?r.diffs.shift():r.diffs[0][1]=r.diffs[0][1].substring(d.length))}a=this.diff_text2(l.diffs),a=a.substring(a.length-this.patchMargin);let u=this.diff_text1(r.diffs).substring(0,this.patchMargin);u!==""&&(l.length1+=u.length,l.length2+=u.length,l.diffs.length!==0&&l.diffs[l.diffs.length-1][0]===0?l.diffs[l.diffs.length-1][1]+=u:l.diffs.push([0,u])),c||e.splice(++i,0,l)}}}patch_toText(e){let t=[];for(let i=0;i<e.length;i++)t[i]=e[i];return t.join("")}patch_fromText(e){let t=[];if(!e)return t;let i=e.split(`
|
|
4
|
+
`),r=0,n=/^@@ -(\d+),?(\d*) \+(\d+),?(\d*) @@$/;for(;r<i.length;){let o=i[r].match(n);if(!o)throw new Error("Invalid patch string: "+i[r]);let a=new U;t.push(a),a.start1=parseInt(o[1],10),o[2]===""?(a.start1--,a.length1=1):o[2]==="0"?a.length1=0:(a.start1--,a.length1=parseInt(o[2],10)),a.start2=parseInt(o[3],10),o[4]===""?(a.start2--,a.length2=1):o[4]==="0"?a.length2=0:(a.start2--,a.length2=parseInt(o[4],10)),r++;let l,c,u;for(;r<i.length;){l=i[r].charAt(0),u=i[r].substring(1);try{c=decodeURI(u)}catch{throw new Error("Illegal escape in patch_fromText: "+u)}if(l==="-")a.diffs.push([-1,c]);else if(l==="+")a.diffs.push([1,c]);else if(l===" ")a.diffs.push([0,c]);else{if(l==="@")break;if(l!=="")throw new Error('Invalid patch mode "'+l+'" in: '+c)}r++}}return t}diff_compute_(e,t,i,r){let n;if(!e)return[[1,t]];if(!t)return[[-1,e]];let o=e.length>t.length?e:t,a=e.length>t.length?t:e,l=o.indexOf(a);if(l!==-1)return n=[[1,o.substring(0,l)],[0,a],[1,o.substring(l+a.length)]],e.length>t.length&&(n[0][0]=-1,n[2][0]=-1),n;if(a.length===1)return[[-1,e],[1,t]];let c=this.diff_halfMatch_(e,t);if(c){let u=c[0],p=c[1],d=c[2],w=c[3],v=c[4],b=this.diff_main(u,d,i,r),g=this.diff_main(p,w,i,r);return b.concat([[0,v]],g)}return i&&e.length>100&&t.length>100?this.diff_lineMode_(e,t,r):this.diff_bisect_(e,t,r)}diff_lineMode_(e,t,i){let r=this.diff_linesToChars_(e,t);e=r.chars1,t=r.chars2;let n=r.lineArray,o=this.diff_main(e,t,!1,i);this.diff_charsToLines_(o,n),this.diff_cleanupSemantic(o),o.push([0,""]);let a=0,l=0,c=0,u="",p="";for(;a<o.length;){switch(o[a][0]){case 1:c++,p+=o[a][1];break;case-1:l++,u+=o[a][1];break;case 0:if(l>=1&&c>=1){o.splice(a-l-c,l+c),a=a-l-c;let d=this.diff_main(u,p,!1,i);for(let w=d.length-1;w>=0;w--)o.splice(a,0,d[w]);a=a+d.length}c=0,l=0,u="",p="";break}a++}return o.pop(),o}diff_bisect_(e,t,i){let r=e.length,n=t.length,o=Math.ceil((r+n)/2),a=o,l=2*o,c=new Array(l),u=new Array(l);for(let h=0;h<l;h++)c[h]=-1,u[h]=-1;c[a+1]=0,u[a+1]=0;let p=r-n,d=p%2!==0,w=0,v=0,b=0,g=0;for(let h=0;h<o&&!(Date.now()>i);h++){for(let f=-h+w;f<=h-v;f+=2){let S=a+f,m;f===-h||f!==h&&c[S-1]<c[S+1]?m=c[S+1]:m=c[S-1]+1;let y=m-f;for(;m<r&&y<n&&e.charAt(m)===t.charAt(y);)m++,y++;if(c[S]=m,m>r)v+=2;else if(y>n)w+=2;else if(d){let F=a+p-f;if(F>=0&&F<l&&u[F]!==-1){let E=r-u[F];if(m>=E)return this.diff_bisectSplit_(e,t,m,y,i)}}}for(let f=-h+b;f<=h-g;f+=2){let S=a+f,m;f===-h||f!==h&&u[S-1]<u[S+1]?m=u[S+1]:m=u[S-1]+1;let y=m-f;for(;m<r&&y<n&&e.charAt(r-m-1)===t.charAt(n-y-1);)m++,y++;if(u[S]=m,m>r)g+=2;else if(y>n)b+=2;else if(!d){let F=a+p-f;if(F>=0&&F<l&&c[F]!==-1){let E=c[F],_=a+E-F;if(m=r-m,E>=m)return this.diff_bisectSplit_(e,t,E,_,i)}}}}return[[-1,e],[1,t]]}diff_bisectSplit_(e,t,i,r,n){let o=e.substring(0,i),a=t.substring(0,r),l=e.substring(i),c=t.substring(r),u=this.diff_main(o,a,!1,n),p=this.diff_main(l,c,!1,n);return u.concat(p)}diff_linesToChars_(e,t){let i=[],r={};i[0]="";let n=this.diff_linesToCharsMunge_(e,i,r,4e4),o=this.diff_linesToCharsMunge_(t,i,r,65535);return{chars1:n,chars2:o,lineArray:i}}diff_linesToCharsMunge_(e,t,i,r){let n="",o=0,a=-1,l=t.length;for(;a<e.length-1;){a=e.indexOf(`
|
|
5
|
+
`,o),a===-1&&(a=e.length-1);let c=e.substring(o,a+1);(i.hasOwnProperty?i.hasOwnProperty(c):i[c]!==void 0)?n+=String.fromCharCode(i[c]):(l===r&&(c=e.substring(o),a=e.length),n+=String.fromCharCode(l),i[c]=l,t[l++]=c),o=a+1}return n}diff_charsToLines_(e,t){for(let i=0;i<e.length;i++){let r=e[i][1],n=[];for(let o=0;o<r.length;o++)n[o]=t[r.charCodeAt(o)];e[i][1]=n.join("")}}diff_commonOverlap_(e,t){let i=e.length,r=t.length;if(i===0||r===0)return 0;i>r?e=e.substring(i-r):i<r&&(t=t.substring(0,i));let n=M(i,r);if(e===t)return n;let o=0,a=1;for(;;){let l=e.substring(n-a),c=t.indexOf(l);if(c===-1)return o;a+=c,(c===0||e.substring(n-a)===t.substring(0,a))&&(o=a,a++)}}diff_halfMatch_(e,t){if(this.diffTimeout<=0)return null;let i=e.length>t.length?e:t,r=e.length>t.length?t:e;if(i.length<4||r.length*2<i.length)return null;let n=this.diff_halfMatchI_(i,r,Math.ceil(i.length/4)),o=this.diff_halfMatchI_(i,r,Math.ceil(i.length/2)),a;if(!n&&!o)return null;o?n?a=n[4].length>o[4].length?n:o:a=o:a=n;let l,c,u,p,d=a[4];return e.length>t.length?(l=a[0],c=a[1],u=a[2],p=a[3]):(u=a[0],p=a[1],l=a[2],c=a[3]),[l,c,u,p,d]}diff_halfMatchI_(e,t,i){let r=e.substring(i,i+Math.floor(e.length/4)),n="",o,a,l,c,u=t.indexOf(r,0);for(;u!==-1;){let p=this.diff_commonPrefix(e.substring(i),t.substring(u)),d=this.diff_commonSuffix(e.substring(0,i),t.substring(0,u));n.length<d+p&&(n=t.substring(u-d,u)+t.substring(u,u+p),o=e.substring(0,i-d),a=e.substring(i+p),l=t.substring(0,u-d),c=t.substring(u+p)),u=t.indexOf(r,u+1)}return n.length*2>=e.length?[o,a,l,c,n]:null}diff_cleanupSemanticScore_(e,t){if(!e||!t)return 6;let i=e.charAt(e.length-1),r=t.charAt(0),n=i.match(Mt),o=r.match(Mt),a=n&&i.match(Bt),l=o&&r.match(Bt),c=a&&i.match(Ut),u=l&&r.match(Ut),p=c&&e.match(Ii),d=u&&t.match(Li);return p||d?5:c||u?4:n&&!a&&l?3:a||l?2:n||o?1:0}match_bitap_(e,t,i){if(t.length>this.matchMaxBits)throw new Error("Pattern too long for this browser");let r=this.match_alphabet_(t),n=this.matchThreshold,o=e.indexOf(t,i);o!==-1&&(n=M(this.match_bitapScore_(0,o,t,i),n),o=e.lastIndexOf(t,i+t.length),o!==-1&&(n=M(this.match_bitapScore_(0,o,t,i),n)));let a=1<<t.length-1;o=-1;let l,c,u=t.length+e.length,p;for(let d=0;d<t.length;d++){for(l=0,c=u;l<c;)this.match_bitapScore_(d,i+c,t,i)<=n?l=c:u=c,c=Math.floor((u-l)/2+l);u=c;let w=B(1,i-c+1),v=M(i+c,e.length)+t.length,b=Array(v+2);b[v+1]=(1<<d)-1;for(let g=v;g>=w;g--){let h=r[e.charAt(g-1)];if(d===0?b[g]=(b[g+1]<<1|1)&h:b[g]=(b[g+1]<<1|1)&h|((p[g+1]|p[g])<<1|1)|p[g+1],b[g]&a){let f=this.match_bitapScore_(d,g-1,t,i);if(f<=n)if(n=f,o=g-1,o>i)w=B(1,2*i-o);else break}}if(this.match_bitapScore_(d+1,i,t,i)>n)break;p=b}return o}match_bitapScore_(e,t,i,r){let n=e/i.length,o=Math.abs(r-t);return this.matchDistance?n+o/this.matchDistance:o?1:n}match_alphabet_(e){let t={};for(let i=0;i<e.length;i++)t[e.charAt(i)]=0;for(let i=0;i<e.length;i++)t[e.charAt(i)]|=1<<e.length-i-1;return t}patch_addContext_(e,t){if(t.length===0)return;if(e.start2==null)throw Error("patch not initialized");let i=t.substring(e.start2,e.start2+e.length1),r=0;for(;t.indexOf(i)!==t.lastIndexOf(i)&&i.length<this.matchMaxBits-this.patchMargin-this.patchMargin;)r+=this.patchMargin,i=t.substring(e.start2-r,e.start2+e.length1+r);r+=this.patchMargin;let n=t.substring(e.start2-r,e.start2);n&&e.diffs.unshift([0,n]);let o=t.substring(e.start2+e.length1,e.start2+e.length1+r);o&&e.diffs.push([0,o]),e.start1-=n.length,e.start2-=n.length,e.length1+=n.length+o.length,e.length2+=n.length+o.length}},U=class{constructor(){this.diffs=[];this.start1=0;this.start2=0;this.length1=0;this.length2=0}toString(){let e,t;this.length1===0?e=this.start1+",0":this.length1===1?e=this.start1+1:e=this.start1+1+","+this.length1,this.length2===0?t=this.start2+",0":this.length2===1?t=this.start2+1:t=this.start2+1+","+this.length2;let i=["@@ -"+e+" +"+t+` @@
|
|
6
6
|
`],r;for(let n=0;n<this.diffs.length;n++){switch(this.diffs[n][0]){case 1:r="+";break;case-1:r="-";break;case 0:r=" ";break}i[n+1]=r+encodeURI(this.diffs[n][1])+`
|
|
7
|
-
`}return i.join("").replace(/%20/g," ")}};function Vt(s,e,t){let i=new ye,r=i.diff_main(s,e,!0,0);r.length>2&&(i.diff_cleanupSemantic(r),i.diff_cleanupEfficiency(r));let n=i.patch_make(s,r);return i.patch_apply(n,t)[0]}var Fe=["bmp","png","jpg","jpeg","gif","svg","webp","avif"],be=["mp3","wav","m4a","3gp","flac","ogg","oga","opus"],we=["mp4","webm","ogv","mov","mkv"],Se=["pdf"],jt=["md"],Ye=["canvas"],qt=["base"];var Pr=jt.concat(Ye,qt),Ar=[].concat(Fe,be,we,Se,jt,Ye);var _r=[...Fe,...be,...we,...Se,...qt,...Ye];var ve=class{constructor(e){this.allowTypes=new Set(K);this.allowSpecialFiles=new Set(Y);this.ignoreFolders=[];this.filterCache={};this.configDir=e}init(e,t,i){this.filterCache={},this.allowTypes=new Set(e||K),this.allowSpecialFiles=new Set(t||[]),this.ignoreFolders=i||[]}clear(){this.filterCache={},this.allowTypes=new Set(K),this.allowSpecialFiles=new Set(Y),this.ignoreFolders=[]}clearCache(){this.filterCache={}}allowSyncFile(e,t){let{filterCache:i}=this;return Object.hasOwn(i,e)?i[e]:i[e]=this._allowSyncFile(e,t)}_allowSyncFile(e,t){for(let n of this.ignoreFolders)if(t&&e===n||e.startsWith(n+"/"))return!1;if(!t&&e.startsWith(this.configDir+"/")){let n=e.substring((this.configDir+"/").length),o=n.split("/");if(o.some(c=>c==="node_modules"||c.startsWith(".")))return!1;let a=C(n),l=T(a),u=null;return n==="workspace.json"||n==="workspace-mobile.json"?!1:(n==="app.json"||n==="types.json"?u="app":n==="appearance.json"?u="appearance":n==="hotkeys.json"?u="hotkey":n==="core-plugins.json"||n==="core-plugins-migration.json"?u="core-plugin":n==="community-plugins.json"?u="community-plugin":o[0]==="themes"&&o.length===3&&(a==="theme.css"||a==="manifest.json")||o[0]==="snippets"&&o.length===2&&l==="css"?u="appearance-data":o.length===1&&l==="json"?u="core-plugin-data":o[0]==="plugins"&&o.length===3&&this.isPluginFile(a)&&(u="community-plugin-data"),u&&this.allowSpecialFiles.has(u))}if(e.startsWith("."))return!1;if(t)return!0;if(e.startsWith("."))return!1;let i=T(C(e));if(i==="md"||i==="canvas"||i==="base")return!0;let{allowTypes:r}=this;return Fe.includes(i)?r.has("image"):i==="webm"?r.has("audio")||r.has("video"):be.includes(i)?r.has("audio"):we.includes(i)?r.has("video"):Se.includes(i)?r.has("pdf"):!!r.has("unsupported")}isPluginFile(e){return e==="manifest.json"||e==="main.js"||e==="styles.css"||e==="data.json"}};var re=class{constructor(){this.promise=Promise.resolve()}queue(e){let t=this.promise.then(e,e);return this.promise=t,t}};function Ee(){let s={promise:null,resolve:null,reject:null};return s.promise=new Promise((e,t)=>{s.resolve=e,s.reject=t}),s}var Je=WebSocket,Kt=URL,ki=Object.getOwnPropertyDescriptor(Kt.prototype,"hostname").get,Mi=String.prototype.endsWith,Wt={1e3:"Disconnected",1001:"Going Away",1002:"Protocol Error",1003:"Unsupported Data",1004:"(For future)",1005:"No Status Received",1006:"Disconnected",1007:"Invalid frame payload data",1008:"Policy Violation",1009:"Message too big",1010:"Missing Extension",1011:"Internal Error",1012:"Service Restart",1013:"Try Again Later",1014:"Bad Gateway",1015:"TLS Handshake"};function Bi(s){if(s>=0&&s<=999)return"(Unused)";if(s>=1016){if(s<=1999)return"(For WebSocket standard)";if(s<=2999)return"(For WebSocket extensions)";if(s<=3999)return"(For libraries and frameworks)";if(s<=4999)return"(For applications)"}return Wt.hasOwnProperty(s)?Wt[s]:"(Unknown)"}var Ui=20*1e3,Vi=10*1e3,ji=2*60*1e3,De=class{constructor(e){this.socket=null;this.queue=new re;this.notifyQueue=new re;this.dataQueue=[];this.onDisconnect=null;this.perFileMax=199*1024*1024;this.userId=-1;this.justPushed=null;this.encryptionProvider=e}isConnecting(){let{socket:e}=this;return e&&e.readyState===Je.CONNECTING}isConnected(){let{socket:e}=this;return e&&e.readyState===Je.OPEN}hasConnection(){let{socket:e}=this;return!!e}async connect(e,t,i,r,n,o,a,l){if(this.hasConnection())return;this.onReady=a,this.onPush=l;let u=this.encryptionProvider.keyHash;return new Promise((c,p)=>{let d=new Kt(e),F=ki.call(d);if(!Mi.call(F,".obsidian.md")&&F!=="127.0.0.1")return p(new Error("Unable to connect to server."));let b=!1,y=h=>{b||(b=!0,this.disconnect(),p(h))},g=this.socket=new Je(d);g.binaryType="arraybuffer",g.onclose=h=>{h.code===1006?y(new Error("Unable to connect to server.")):y(new Error("Disconnected. Code: "+h.code+" "+Bi(h.code)))},g.onopen=()=>{this.lastMessageTs=Date.now(),this.heartbeat=setInterval(()=>{let h=Date.now()-this.lastMessageTs;if(h>ji){this.disconnect();return}h>Vi&&this.send({op:"ping"})},Ui),this.send({op:"init",token:t,id:i,keyhash:u,version:r,initial:n,device:o,encryption_version:this.encryptionProvider.encryptionVersion})},g.onmessage=h=>{let f=h.data;if(typeof f!="string")return y(new Error("Server returned binary"));let w;try{w=JSON.parse(f)}catch(m){return console.error(m),y(new Error("Server JSON failed to parse: "+f))}if(w.op!=="pong"){if(w.status==="err"||w.res==="err")return y(new Error("Failed to authenticate: "+w.msg));if(w.res!=="ok")return y(new Error("Did not respond to login request: "+f));if(w.hasOwnProperty("perFileMax")){let m=w.perFileMax;if(!Number.isInteger(m)||isNaN(m)||m<0)return y(new Error("Unexpected value from server for max file size"));this.perFileMax=m}w.userId&&(this.userId=w.userId),c(),b=!0,g.onmessage=this.onMessage.bind(this),g.onclose=this.disconnect.bind(this),g.onerror=this.disconnect.bind(this)}}})}disconnect(){let e=!1;this.socket&&(this.socket.close(),this.socket=null,e=!0),this.heartbeat&&(clearInterval(this.heartbeat),this.heartbeat=null),this.responsePromise&&(this.responsePromise.reject(new Error("Disconnected")),this.responsePromise=null),this.dataPromise&&(this.dataPromise.reject(new Error("Disconnected")),this.dataPromise=null),e&&this.onDisconnect&&this.onDisconnect()}async pull(e){return this.queue.queue(async()=>{this.lastNetworkRequestTs=Date.now(),this.dataQueue.length=0;let t=await this.request({op:"pull",uid:e});if(!t.deleted){let i=t.size,r=t.pieces,n=new ArrayBuffer(i),o=0;for(let a=0;a<r;a++){let l=await this.dataResponse();new Uint8Array(n,o,l.byteLength).set(new Uint8Array(l)),o+=l.byteLength}return n.byteLength>0&&(n=await this.encryptionProvider.decrypt(n)),n}return null})}async push(e,t,i,r,n,o,a,l){return this.queue.queue(async()=>{this.lastNetworkRequestTs=Date.now();let u=await this.encryptionProvider.deterministicEncodeStr(e),c=t?await this.encryptionProvider.deterministicEncodeStr(t):null,p=i?"":T(C(e));if(i||r){this.justPushed={path:u,folder:i,deleted:r,mtime:0,hash:""},await this.request({op:"push",path:u,relatedpath:c,extension:p,hash:"",ctime:0,mtime:0,folder:i,deleted:r});return}l.byteLength>0&&(l=await this.encryptionProvider.encrypt(l)),a&&(a=await this.encryptionProvider.deterministicEncodeStr(a));let d=l.byteLength,F=2*1024*1024,b=Math.ceil(d/F);if(this.justPushed={path:u,folder:i,deleted:r,mtime:o,hash:a},(await this.request({op:"push",path:u,relatedpath:c,extension:p,hash:a,ctime:n,mtime:o,folder:i,deleted:r,size:d,pieces:b})).res==="ok"){this.justPushed=null;return}for(let g=0;g<b;g++){let h=g*F,f=Math.min(F,d-h);this.sendBinary(new Uint8Array(l,h,f)),await this.response()}this.justPushed=null})}async listDeleted(){return this.queue.queue(async()=>{let t=(await this.request({op:"deleted",suppressrenames:!0})).items;for(let i of t)i.path=await this.encryptionProvider.deterministicDecodeStr(i.path);return t})}async listHistory(e,t){return this.queue.queue(async()=>{let i=await this.encryptionProvider.deterministicEncodeStr(e),r=await this.request({op:"history",path:i,last:t}),n=r.items;for(let o of n)o.path=await this.encryptionProvider.deterministicDecodeStr(o.path),o.relatedpath=o.relatedpath&&await this.encryptionProvider.deterministicDecodeStr(o.relatedpath);return r})}async restore(e){return this.queue.queue(async()=>this.request({op:"restore",uid:e}))}async getUsernames(){return this.queue.queue(()=>this.request({op:"usernames"}))}async purge(){return this.queue.queue(()=>this.request({op:"purge"}))}async size(){return this.queue.queue(()=>this.request({op:"size"}))}onServerPush(e){let{justPushed:t}=this;t&&t.path===e.path&&t.folder===e.folder&&t.deleted===e.deleted&&t.mtime===e.mtime&&t.hash===e.hash&&(this.justPushed=null,e.wasJustPushed=!0),this.notifyQueue.queue(async()=>{e.path=await this.encryptionProvider.deterministicDecodeStr(e.path),e.hash&&(e.hash=await this.encryptionProvider.deterministicDecodeStr(e.hash)),this.onPush(e)})}response(){return(this.responsePromise=Ee()).promise}dataResponse(){return this.dataQueue.length>0?Promise.resolve(this.dataQueue.shift()):(this.dataPromise=Ee()).promise}async request(e,t=6e4){let i=this.responsePromise=Ee();this.send(e);let r=new Error("Timeout"),n=setTimeout(()=>i.reject(r),t),o;try{o=await i.promise,clearTimeout(n)}catch(a){throw a===r&&this.disconnect(),a}if(o.err)throw new Error(o.err);return o}onMessage(e){if(this.lastMessageTs=Date.now(),typeof e.data=="string"){let t;try{t=JSON.parse(e.data)}catch{console.log(e.data),this.disconnect();return}let i=t.op;if(i==="pong")return;if(i==="ready"){this.notifyQueue.queue(async()=>{this.onReady(t.version)});return}if(i==="push"){this.onServerPush(t);return}let r=this.responsePromise;r&&(this.responsePromise=null,r.resolve(t))}else{let t=this.dataPromise;t?(this.dataPromise=null,t.resolve(e.data)):this.dataQueue.push(e.data)}}send(e){this.socket.send(JSON.stringify(e))}sendBinary(e){this.socket.send(e)}};var Pe=class{constructor(e,t,i,r){this.min=e||0,this.max=t||Number.MAX_VALUE,this.base=i||1e3,this.jitter=r||!0,this.count=0,this.nextTs=Date.now()}success(){this.count=0,this.nextTs=Date.now()+this.getTimeout()}fail(){this.count++,this.nextTs=Date.now()+this.getTimeout()}getTimeout(){if(this.count===0)return this.min;let e=this.count-1,t=this.base*Math.pow(2,e);if(this.jitter){let i=.5;t=t*(1-i+i*Math.random())}return t=Math.floor(Math.min(this.max,this.min+t)),t}getNextTs(){return this.nextTs}isReady(){return Date.now()>this.nextTs}};var Ht=crypto,x=Ht.subtle,Ze="AES-GCM";function Gt(s){return x.importKey("raw",s,Ze,!1,["encrypt","decrypt"])}async function Ae(s,e,t){t||(t=Ht.getRandomValues(new Uint8Array(12)));let i=await x.encrypt({name:Ze,iv:t},e,s),r=new ArrayBuffer(t.byteLength+i.byteLength),n=new Uint8Array(r);return n.set(new Uint8Array(t),0),n.set(new Uint8Array(i),t.byteLength),r}async function _e(s,e){if(s.byteLength<12)throw new Error("Encrypted data is bad");if(s.byteLength===12)return new ArrayBuffer(0);let t=new Uint8Array(s,0,12),i=new Uint8Array(s,12);return await x.decrypt({name:Ze,iv:t},e,i)}function ne(s){return s.buffer.slice(s.byteOffset,s.byteOffset+s.byteLength)}function I(s){return ne(new TextEncoder().encode(s))}function V(s){return new TextDecoder().decode(new Uint8Array(s))}function $t(s){let e=atob(s),t=e.length,i=new Uint8Array(t);for(let r=0;r<t;r++)i[r]=e.charCodeAt(r);return i.buffer}function Qt(s){return qi(new Uint8Array(s))}function qi(s){let e=[],t=s.byteLength;for(let i=0;i<t;i++)e.push(String.fromCharCode(s[i]));return btoa(e.join(""))}async function Te(s){return O(await se(s))}async function se(s){return x.digest("SHA-256",new Uint8Array(s))}function ze(s){let e=s.length/2,t=new ArrayBuffer(e),i=new Uint8Array(t);for(let r=0;r<e;r++)i[r]=parseInt(s.substr(r*2,2),16);return t}function O(s){let e=new Uint8Array(s),t=[];for(let i=0;i<e.length;i++){let r=e[i];t.push((r>>>4).toString(16)),t.push((r&15).toString(16))}return t.join("")}function et(s){if(s<=0)return"0 B";let e=["B","KB","MB","GB","TB","PB"],t=e.length-1,i=1024;for(let n=0;n<e.length;n++)if(s<Math.pow(i,n+1)){t=n;break}let r=s/Math.pow(i,t);return`${Wi(r,t===0?0:2)} ${e[t]}`}function Wi(s,e=2,t=".",i=","){let r=s<0?"-":"";s=Math.abs(s);let n=parseInt(s.toFixed(e),10)+"",o=n.length>3?n.length%3:0;return r+(o?n.substr(0,o)+i:"")+n.substr(o).replace(/(\d{3})(?=\d)/g,"$1"+i)+(e?t+Math.abs(s-Math.floor(s)).toFixed(e).slice(2):"")}var Ki=function(){let s=typeof process<"u"?process.platform:"";if(s==="win32")return"win";if(s==="darwin")return"mac";if(s==="linux")return"linux";if(s)return"unknown";let e=navigator.userAgent;return e.indexOf("Win")!==-1?"win":e.indexOf("Mac")!==-1?"mac":e.indexOf("X11")!==-1||e.indexOf("Linux")!==-1?"linux":"unknown"}(),Xt=navigator.userAgent.toLowerCase();var tt=Ki==="win";var $r=/^((?!chrome|android).)*safari/i.test(Xt),Yt=/android/i.test(Xt);var Hi=/[.?*+^$[\]\\(){}|-]/g;function xe(s){return s.replace(Hi,"\\$&")}var Gi="\\/:"+(Yt?'*?<>"':""),$i='*"\\/<>:|?',Jt="#^[]|",Zt=tt?$i:Gi,Qi=Zt.split("").join("\xA0"),zr=Jt.split("").join("\xA0"),zt=new RegExp("["+xe(Zt)+"]"),en=new RegExp("["+xe(Jt)+"]"),Xi=/^(CON|PRN|AUX|NUL|COM[1-9]|LPT[1-9])$/i;function ei(s){try{return Yi(s),!0}catch{return!1}}function Yi(s){if(tt){let e=s.charAt(s.length-1);if(e==="."||e===" ")throw new Error("File names cannot end with a dot or a space.");let t=Lt(s);if(Xi.test(t))throw new Error("File name is forbidden: "+t)}if(s.split("/").some(e=>zt.test(e)))throw new Error("File name cannot contain any of the following characters: "+Qi)}function ti(s,e="_"){let t=s.trim();if(t&&(t=s.replace(zt,e),e.length===1)){let i=xe(e),r=new RegExp(`${i}{2,}`,"g");t=t.replace(r,e)}return t}function Ji(s){return new Promise(e=>setTimeout(e,s))}var Ie=class{constructor(e){this.server=null;this.localFiles={};this.serverFiles={};this.newServerFiles=[];this.version=0;this.initial=!0;this.ready=!1;this.syncing=!1;this.loaded=!1;this.backoff=new Pe(0,5*60*1e3,5e3,!0);this.fileRetry={};this.skippedFiles={};this.syncingPath="";this.scanSpecialFiles=!1;this.scanSpecialFileQueue=[];this.resolveStop=null;let{config:t}=e;this.host=t.host,this.token=e.token,this.vaultId=t.vaultId,this.continuous=e.continuous||!1,this.encryption=e.encryption,this.stateStore=e.stateStore,this.conflictStrategy=t.conflictStrategy||"merge",this.deviceName=t.deviceName||"Sync Client",this.adapter=new me(D.default,P.default,Ne.default,()=>!1,_t,"file:///",t.vaultPath),this.filter=new ve(t.configDir),this.filter.init(t.allowTypes||[],t.allowSpecialFiles||[],t.ignoreFolders||[]),this.loadState()}loadState(){this.version=this.stateStore.getVersion(),this.initial=this.stateStore.isInitial(),this.localFiles=this.stateStore.getAllLocalFiles(),this.serverFiles=this.stateStore.getAllServerFiles(),this.newServerFiles=this.stateStore.getPendingFiles()}handlePush(e){if(this.version=e.uid,this.initial&&e.deleted){this.stateStore.setVersion(this.version);return}let t=e.path,i={path:t,size:e.size,hash:e.hash,ctime:e.ctime,mtime:e.mtime,folder:e.folder,deleted:e.deleted,uid:e.uid,device:e.device,user:e.user};this.initial&&(i.initial=!0);let{newServerFiles:r}=this;if(e.wasJustPushed){for(let n=0;n<r.length;n++)r[n].path===t&&(r.splice(n,1),n-=1);this.stateStore.deletePendingFile(t),this.serverFiles[t]=i,this.stateStore.setServerFile(i),this.stateStore.setVersion(this.version);return}r.push(i),this.stateStore.addPendingFile(i),this.stateStore.setVersion(this.version),this.initial||console.debug(`Push: ${i.path} (${i.deleted?"deleted":"updated"})`),this.requestSync()}async sync(){let e=new Promise(i=>this.resolveStop=i),t=setInterval(this.requestSync.bind(this),30*1e3);try{if(!this.loaded){await this.adapter.watch(this.onChange.bind(this));for(let i in this.localFiles)Object.hasOwn(this.adapter.files,i)||(delete this.localFiles[i],this.stateStore.deleteLocalFile(i));this.loaded=!0}await this.requestSync(),await e}finally{clearInterval(t)}}stop(){this.server&&(this.server.disconnect(),this.server=null),this.ready=!1,this.stateStore.close(),this.adapter.stopWatch(),this.adapter.thingsHappening.cancel(),this.resolveStop&&(this.resolveStop(),this.resolveStop=null)}async requestSync(){if(!this.syncing){this.syncing=!0;try{let e=!0;for(;e;){try{this.syncingPath="",e=await this._sync();let i=this.syncingPath;i&&delete this.fileRetry[i]}catch(i){if(console.error("Sync error:",i),this.failedSync(this.syncingPath),e=!1,!this.continuous)throw this.syncing=!1,i}if(!e)return;let t=0;if(this.server){let i=Date.now()-this.server.lastNetworkRequestTs;t=Math.max(0,50-i)}await Ji(t)}}finally{this.syncing=!1}}}canSyncPath(e,t){let{fileRetry:i}=this;for(let r in i)if(i.hasOwnProperty(r)&&i[r].ts>e&&t.startsWith(r))return!1;return!0}canSyncLocalFile(e,t){if(!t.synctime)return!0;let i=t.size,r=i>10*1024,n=i>100*1024,o=r?n?30:20:10;return e-t.synctime>o*1e3}failedSync(e){if(!e)return;let t=Date.now(),i=this.fileRetry[e];i||(i=this.fileRetry[e]={count:0,ts:0});let r=i.count=i.count+1,n=Math.pow(2,r)*5*1e3;n=Math.min(n,5*60*1e3),i.ts=t+n}async getServer(){let{server:e}=this;if(e&&!e.isConnected()&&!e.isConnecting()&&(e.disconnect(),e=this.server=null,this.backoff.fail()),!e){if(!this.backoff.isReady())return this.log("Waiting to connect to server"),null;e=this.server=new De(this.encryption)}if(!e.hasConnection()){this.log("Connecting..."),this.ready=!1;try{let t=this.host.startsWith("127.0.0.1")||this.host.startsWith("localhost")?"ws://":"wss://";e.onDisconnect=()=>{this.ready=!1,this.log("Disconnected from server"),this.continuous&&this.requestSync()},await e.connect(t+this.host,this.token,this.vaultId,this.version,this.initial,this.deviceName,i=>{this.ready=!0,this.initial=!1,this.stateStore.setInitial(!1),this.version<i&&(this.version=i,this.stateStore.setVersion(this.version)),this.requestSync()},i=>this.handlePush(i)),this.log("Connection successful. Detecting changes..."),this.backoff.success()}catch(t){if(t.message&&t.message.includes("Your subscription to Obsidian Sync has expired"))throw console.error(t.message),this.stop(),t;if(t.message&&t.message.includes("Vault not found"))throw console.error("The connected remote vault no longer exists."),this.stop(),t;return console.error(t),e.disconnect(),e=this.server=null,this.backoff.fail(),null}}return e}async _sync(){let e=await this.getServer();if(!e)return!1;let t=Date.now(),i=0,r=this.filter.configDir,n=r+"/",{localFiles:o,serverFiles:a,newServerFiles:l,stateStore:u,filter:c,adapter:p}=this;try{let g={},h=this.scanSpecialFileQueue;if(this.scanSpecialFiles){this.scanSpecialFiles=!1,h=this.scanSpecialFileQueue=[];for(let f in o)Object.hasOwn(o,f)&&f.startsWith(".")&&(g[f]=o[f],delete o[f],u.deleteLocalFile(f));if(c.allowSpecialFiles.size>0&&await p.exists(r)){h.push(n+"config");let f=await p.list(r);for(let w of f.files)T(w)==="json"&&h.push(w);if(await p.exists(n+"themes")){let w=await p.list(n+"themes");for(let m of w.folders){let S=await p.list(m);for(let v of S.files){let E=C(v);(E==="manifest.json"||E==="theme.css")&&h.push(v)}}}if(await p.exists(n+"snippets")){let w=await p.list(n+"snippets");for(let m of w.files)T(m)==="css"&&h.push(m)}if(await p.exists(n+"plugins")){let w=await p.list(n+"plugins");for(let m of w.folders){let S=await p.list(m);for(let v of S.files){let E=C(v);c.isPluginFile(E)&&h.push(v)}}}}}for(;h.length>0;){let f=h.pop();if(!await p.exists(f)){delete o[f],u.deleteLocalFile(f);continue}let w=await p.stat(f);if(!w||w.type!=="file"){delete o[f],u.deleteLocalFile(f);continue}let m=o[f];m||(Object.hasOwn(g,f)?m=o[f]=g[f]:m=o[f]={path:f,previouspath:"",ctime:0,mtime:0,size:0,folder:!1,hash:"",synchash:"",synctime:0});let S=Math.ceil(w.mtime),v=Math.ceil(w.ctime),E=w.size;(!m.mtime||m.mtime!==S||m.size!==w.size)&&(m.hash=""),m.mtime=S,m.ctime=v,m.size=E,u.setLocalFile(m)}}catch(g){console.error("Failed to scan config files",g)}if(l.length>0)for(let g=0;g<l.length;g++){let h=l[g],f=h.path,w=a[f],m=o[f],S=(v,E)=>(v||this.log("Accepted",f),m&&(m.synctime=Date.now(),u.setLocalFile(m)),E||(a[f]=h,u.setServerFile(h)),l.splice(g,1),u.deletePendingFile(f),!0);if(!c.allowSyncFile(f,h.folder))return S(!0);if(!ei(f))return this.log("Ignoring remote file name with illegal characters",f,!0),S(!0,!0);if(H(f).split("/").includes(".."))return S(!0);if(!this.canSyncPath(t,f)){i++;continue}if(this.syncingPath=f,m&&!m.folder&&!m.hash){this.log("Checking",f);let v=await p.readBinary(f);m.hash=await Te(v),u.setLocalFile(m)}if(m&&!m.folder&&!h.folder&&m.hash===h.hash)return S(!0);for(let v=g+1;v<l.length;v++)if(l[v].path===f)return this.log("Skipped",f),S(!0,!0);if(!m)return h.deleted?S(!0):(await this.syncFileDown(e,h),S());if(m.folder&&h.folder){if(h.deleted){try{let v=await p.list(f);if(v.files.length>0||v.folders.length>0)return S(!0)}catch{}this.log("Deleting",f);try{await p.rmdir(f,!0)}catch(v){let E=(v?v.message:"")||"Failed to delete folder";this.log(E,f,!0)}}return S(!0)}if(w&&(m.folder&&w.folder||m.hash===w.hash))return h.deleted?(this.log("Deleting",f),m.folder?await this.adapter.rmdir(f,!0):await this.adapter.remove(f),delete o[f],this.stateStore.deleteLocalFile(f),S()):(await this.syncFileDown(e,h),S());if(!m.folder&&h.folder)try{if((await p.stat(f)).type==="file"){let E=T(C(f)),_=E?f.substr(f.length-E.length-1):"",R=f.substr(0,f.length-_.length)+" (Conflicted copy)"+_;return this.log("Renaming conflicted file",f),await p.rename(f,R),!0}}catch{}if(h.initial&&h.mtime>m.mtime)return await this.syncFileDown(e,h),S();if(!h.initial&&!m.folder&&!h.folder&&!h.deleted&&T(f)==="md"&&h.hash!==m.synchash){this.logMerge("Merging conflicted file",f);let v=await this.adapter.read(f);if(!v)return await this.syncFileDown(e,h),S();let E="";if(w&&!w.deleted)try{E=V(await e.pull(w.uid))}catch(R){return this.logMerge("Merge failed. "+R.toString(),f,!0),S(!0)}let _;try{_=V(await e.pull(h.uid))}catch(R){return this.logMerge("Merge failed. "+R.toString(),f,!0),S(!0)}if(E===_||v===_||!_)return S();if(this.conflictStrategy==="conflict"){let R=new Date().toLocaleString("sv").replace(/[:\- ]/g,"").substring(0,12),yi=T(f),Fi=Ct(f),bi=ti(this.deviceName),wi=`${Fi} (Conflicted copy ${bi} ${R}).${yi}`;try{await p.write(wi,v,{ctime:m.ctime,mtime:m.mtime}),await p.write(f,_,{ctime:h.ctime,mtime:h.mtime}),this.logMerge("Conflicted copy stored",f)}catch{return S()}return S()}if(!E)return Math.abs(Date.now()-m.ctime)<3*60*1e3?(this.log("Downloading "+f),await p.write(f,_,{ctime:h.ctime,mtime:h.mtime}),S()):(h.mtime>m.mtime&&(this.log("Downloading "+f),await p.write(f,_,{ctime:h.ctime,mtime:h.mtime})),S());let q=Vt(E,v,_);return await p.write(f,q),this.logMerge("Merge successful",f),S()}if(!h.folder&&!h.deleted&&h.size>0&&f.startsWith(n)){if(T(f)==="json")try{this.log("Merging conflicted file",f);let v=JSON.parse(await p.read(f));if(v&&!Array.isArray(v)&&typeof v=="object"){let E=JSON.parse(V(await e.pull(h.uid)));if(E&&!Array.isArray(E)&&typeof E=="object"){for(let q in E)Object.hasOwn(E,q)&&(v[q]=E[q]);let _=I(JSON.stringify(v,void 0,2));return await p.writeBinary(f,_),this.log("Merge successful",f),S(!0)}}}catch(v){this.log("Merge failed. "+v.toString(),f,!0)}return await this.syncFileDown(e,h),S()}return this.log("Rejected server change",f),S(!0)}if(!this.ready)return!1;let d=null,F=null;for(let g in a){if(!Object.hasOwn(a,g))continue;let h=a[g];if(!Object.hasOwn(o,g)){if(h.deleted){delete a[g],u.deleteServerFile(g);continue}if(!c.allowSyncFile(g,h.folder))continue;h.folder?(!F||h.path.length>F.path.length)&&(F=h):(!d||h.path.length>d.path.length)&&(d=h)}}if(d){let g=d.path;return this.log("Deleting remote file",g),this.syncingPath=g,await e.push(g,null,!1,!0,0,0,"",null),d.deleted=!0,u.setServerFile(d),!0}if(F){let g=F.path;return this.log("Deleting remote folder",g),this.syncingPath=g,await e.push(g,null,!0,!0,0,0,"",null),F.deleted=!0,u.setServerFile(F),!0}let b=null,y=null;for(let g in o){if(!Object.hasOwn(o,g))continue;let h=o[g],f=a[g];if(!(f&&!f.deleted&&h.folder===f.folder&&h.ctime===f.ctime&&h.mtime===f.mtime&&h.size===f.size&&h.hash&&h.hash===f.hash)&&c.allowSyncFile(g,h.folder)){if(!this.canSyncPath(t,g)){i++;continue}if(process.platform==="linux"&&!h.folder&&f&&f.ctime&&(h.ctime===0||h.ctime>f.ctime)&&!f.folder&&!f.deleted&&(h.ctime=f.ctime),!h.folder&&h.size>e.perFileMax){this.logSkip(`File too large to sync (${et(h.size)}, max ${et(e.perFileMax)})`,g);continue}if(!f||f.deleted){if(!this.canSyncLocalFile(t,h)){i++;continue}h.folder?(!b||h.path.length<b.path.length)&&(b=h):(!y||h.size<y.size)&&(y=h);continue}if(!b){if(h.folder){if(!this.canSyncLocalFile(t,h)){i++;continue}f.folder||(!b||h.path.length<b.path.length)&&(b=h);continue}if(f.folder){if(!this.canSyncLocalFile(t,h)){i++;continue}F=f;continue}if(!h.hash||h.hash!==f.hash){if(!this.canSyncLocalFile(t,h)){i++;continue}(!y||h.size<y.size)&&(y=h)}}}}if(b){let g=b.path;return this.syncingPath=g,this.log("Uploading",g),await e.push(g,b.previouspath,!0,!1,0,0,"",null),Object.hasOwn(a,g)?a[g].deleted&&(a[g].deleted=!1):a[g]={uid:0,path:g,size:0,hash:"",ctime:0,mtime:0,folder:!0,deleted:!1,device:this.deviceName},u.setServerFile(a[g]),b.previouspath="",b.synctime=Date.now(),u.setLocalFile(b),!0}if(y){let g=y.path;this.log("New file",g),this.syncingPath=g;let h=a[g],{ctime:f,mtime:w}=y,m=await p.readBinary(g),S=y.hash=await Te(m);return u.setLocalFile(y),h&&!h.deleted&&h.hash===y.hash||(this.log("Uploading file",g),await e.push(g,y.previouspath,!1,!1,f,w,S,m),y.synchash=S,this.log("Upload complete",g),y.previouspath="",y.synctime=Date.now(),u.setLocalFile(y)),!0}return i===0?(this.log("Fully synced"),this.fileRetry={},this.continuous||this.stop(),!1):!0}onChange(e,t,i,r){if(e==="file-created"){let n=this.localFiles[t];n||(n=this.localFiles[t]={path:t,previouspath:"",folder:!1,ctime:0,mtime:0,size:0,hash:"",synctime:0,synchash:""}),r&&((n.mtime!==r.mtime||n.size!==r.size)&&(n.hash=""),n.ctime=r.ctime,n.mtime=r.mtime,n.size=r.size),this.stateStore.setLocalFile(n)}else if(e==="folder-created")this.localFiles[t]||(this.localFiles[t]={path:t,previouspath:"",folder:!0,ctime:0,mtime:0,size:0,hash:"",synctime:0,synchash:""},this.stateStore.setLocalFile(this.localFiles[t]));else if(e==="modified"){let n=this.localFiles[t];n&&r&&((n.mtime!==r.mtime||n.size!==r.size)&&(n.hash=""),n.ctime=r.ctime,n.mtime=r.mtime,n.size=r.size,this.stateStore.setLocalFile(n))}else if(e==="file-removed"||e==="folder-removed")delete this.localFiles[t],this.stateStore.deleteLocalFile(t);else if(e==="renamed"){let n=this.localFiles[i];n&&(delete this.localFiles[i],this.stateStore.deleteLocalFile(i),n.path=t,n.previouspath=i,this.localFiles[t]=n,this.stateStore.setLocalFile(n))}this.loaded&&e!=="raw"&&this.requestSync()}async syncFileDown(e,t){let i=t.path;if(this.log("Downloading",i),t.folder){await this.adapter.mkdir(i),this.log("Downloaded",i);return}let r=await e.pull(t.uid);if(!r)throw new Error("Failed to download file, no data.");let n=k(i);n&&await this.adapter.mkdir(n),await this.adapter.writeBinary(i,r,{ctime:t.ctime,mtime:t.mtime});let o=await Te(r);this.localFiles[i]&&(this.localFiles[i].hash=o,this.localFiles[i].synchash=o,this.stateStore.setLocalFile(this.localFiles[i])),this.log("Downloaded",i)}log(e,t,i=!1){i?t?console.error(e,t):console.error(e):t?console.log(e,t):console.log(e)}logMerge(e,t,i=!1){this.log(e,t,i)}logSkip(e,t){let{skippedFiles:i}=this;(!Object.hasOwn(i,t)||i[t]!==e)&&(i[t]=e,this.log(e,t,!0))}};var di=require("commander");var ii=fetch,ri="https://"+["api","obsidian","md"].join("."),oe=class s extends Error{constructor(e){super(e.error),this.response=e,this.error=e.error,Object.setPrototypeOf(this,s.prototype)}};async function j(s,e,t){let{preflight:i,headers:r}=t||{};i&&await ii(ri+s,{method:"OPTIONS"}),r||(r={}),r["Content-Type"]="application/json";let n=await(await ii(ri+s,{method:"POST",body:JSON.stringify(e),headers:r})).json();if("error"in n)throw new oe(n);return n}async function it(s,e,t){return j("/user/signin",{email:s,password:e,mfa:t},{preflight:!0,headers:{Origin:"https://obsidian.md"}})}function rt(s){return j("/user/signout",{token:s})}function ni(s){return j("/user/info",{token:s})}function si(s,e){return j("/vault/regions",{token:s,host:e})}function nt(s,e){return j("/vault/list",{token:s,supported_encryption_version:e})}function oi(s,e,t,i,r,n){return j("/vault/create",{token:s,name:e,keyhash:t,salt:i,region:r,encryption_version:n})}function ai(s,e,t,i,r){return j("/vault/access",{token:s,vault_uid:e,keyhash:t,host:i,encryption_version:r})}var ae=class s extends Error{constructor(e){super(e),Object.setPrototypeOf(this,s.prototype)}};function li(s,e,t){return~(s-1)&e|s-1&t}function Zi(s,e){if(s.length!==e.length)return 0;let t=0;for(let i=0;i<s.length;i++)t|=s[i]^e[i];return 1&t-1>>>8}function ui(s,e){return s.length===0||e.length===0?!1:Zi(s,e)!==0}function Le(s){for(let e=0;e<s.length;e++)s[e]=0;return s}function Ce(s,e){for(let t=0;t<e.length;t++)s[t]^=e[t]}var A=class s{static{this.SIZE=16}static{this.R=135}constructor(){this.data=new Uint8Array(s.SIZE)}clear(){Le(this.data)}clone(){let e=new s;return e.copy(this),e}copy(e){this.data.set(e.data)}dbl(){let e=0;for(let t=s.SIZE-1;t>=0;t--){let i=this.data[t]>>>7&255;this.data[t]=this.data[t]<<1|e,e=i}this.data[s.SIZE-1]^=li(e,s.R,0),e=0}};var $=crypto.subtle;var le=class s{constructor(e){this.key=e}static async importKey(e,t){let i=await $.deriveKey({name:"HKDF",salt:t,info:new TextEncoder().encode("ObsidianAesSivEnc"),hash:"SHA-256"},e,{name:"AES-CTR",length:256},!1,["encrypt"]);return new s(i)}async encryptCtr(e,t){let i=await $.encrypt({name:"AES-CTR",counter:e,length:16},this.key,t);return new Uint8Array(i)}};var ue=class s{constructor(e){this._key=e;this._iv=new A;this._emptyPromise=Promise.resolve(this)}static async importKey(e,t){let i=await $.deriveKey({name:"HKDF",salt:t,info:new TextEncoder().encode("ObsidianAesSivMac"),hash:"SHA-256"},e,{name:"AES-CBC",length:256},!1,["encrypt"]);return new s(i)}clear(){return this}async encryptBlock(e){let t={name:"AES-CBC",iv:this._iv.data},i=await $.encrypt(t,this._key,e.data);return e.data.set(new Uint8Array(i,0,A.SIZE)),this._emptyPromise}};var ce=class s{constructor(e,t,i){this._cipher=e;this._subkey1=t;this._subkey2=i;this._bufferPos=0;this._finished=!1;this._buffer=new A}static async importKey(e,t){let i=await ue.importKey(e,t),r=new A;await i.encryptBlock(r),r.dbl();let n=r.clone();return n.dbl(),()=>new s(i,r,n)}async update(e){if(this._finished)throw new Error("Cannot update finished CMAC");let t=A.SIZE-this._bufferPos,i=0,r=e.length;if(r>t){for(let n=0;n<t;n++)this._buffer.data[this._bufferPos+n]^=e[n];r-=t,i+=t,await this._cipher.encryptBlock(this._buffer),this._bufferPos=0}for(;r>A.SIZE;){for(let n=0;n<A.SIZE;n++)this._buffer.data[n]^=e[i+n];r-=A.SIZE,i+=A.SIZE,await this._cipher.encryptBlock(this._buffer)}for(let n=0;n<r;n++)this._buffer.data[this._bufferPos++]^=e[i+n];return this}async finish(){if(!this._finished){let e=this._bufferPos<A.SIZE?this._subkey2:this._subkey1;Ce(this._buffer.data,e.data),this._bufferPos<A.SIZE&&(this._buffer.data[this._bufferPos]^=128),await this._cipher.encryptBlock(this._buffer),this._finished=!0}return this._buffer.data}};var fe=class s{static async importKey(e,t){let i=await ce.importKey(e,t),r=await le.importKey(e,t);return new s(i,r)}constructor(e,t){this.cmacFactory=e,this._ctr=t}async seal(e){let t=A.SIZE+e.length,i=new Uint8Array(t),r=await this._s2v(e);return i.set(r),ci(r),i.set(await this._ctr.encryptCtr(r,e),r.length),i}async open(e){if(e.length<A.SIZE)throw new ae("AES-SIV: ciphertext is truncated");let t=e.subarray(0,A.SIZE),i=new Uint8Array(A.SIZE);i.set(t),ci(i);let r=await this._ctr.encryptCtr(i,e.subarray(A.SIZE)),n=await this._s2v(r);if(!ui(n,t))throw Le(r),new ae("AES-SIV: ciphertext verification failure!");return r}async _s2v(e){let t=this.cmacFactory(),i=new A,r=new A;if(await t.update(i.data),r.data.set(await t.finish()),t=this.cmacFactory(),i.clear(),e.length>=A.SIZE){let n=e.length-A.SIZE;i.data.set(e.subarray(n)),await t.update(e.subarray(0,n))}else i.data.set(e),i.data[e.length]=128,r.dbl();return Ce(i.data,r.data),await t.update(i.data),t.finish()}};function ci(s){s[s.length-8]&=127,s[s.length-4]&=127}var ut=3,ct=3,fi=32,st=32768,ot=8,hi=1,zi={N:st,r:ot,p:hi,maxmem:128*st*ot*2};async function ft(s,e){s=s.normalize("NFKC"),e=e.normalize("NFKC");let t=require&&require("crypto");if(t){let r=await new Promise((n,o)=>{t.scrypt(Buffer.from(s,"utf8"),Buffer.from(e,"utf8"),fi,zi,(a,l)=>{a?o(a):n(l)})});return ie(r)}let i=await window.scrypt.scrypt(new Uint8Array(I(s)),new Uint8Array(I(e)),st,ot,hi,fi);return ne(i)}async function pi(s,e,t){switch(s){case 0:return at.init(e);case 2:case 3:return lt.init(e,t,s);default:throw new Error("Encryption version not supported")}}async function ht(s,e,t){switch(t){case 0:return O(await se(s));case 2:case 3:let i=await x.importKey("raw",s,"HKDF",!1,["deriveKey"]),r=await x.deriveKey({name:"HKDF",salt:I(e),info:I("ObsidianKeyHash"),hash:"SHA-256"},i,{name:"AES-CBC",length:256},!0,["encrypt"]);return O(await x.exportKey("raw",r));default:throw new Error("Encryption version not supported")}}var at=class s{constructor(e,t){this.encryptionVersion=0;this.keyHash=e,this.cryptoKey=t}static async init(e){if(e.byteLength!==32)throw new Error("Invalid encryption key");let t=O(await se(e)),i=await Gt(e);return new s(t,i)}async deterministicEncodeStr(e){let t=I(e),i=await se(t),r=new Uint8Array(i,0,12);return O(await Ae(t,this.cryptoKey,r))}async deterministicDecodeStr(e){let t=ze(e);return V(await _e(t,this.cryptoKey))}async encrypt(e){return Ae(e,this.cryptoKey)}async decrypt(e){return _e(e,this.cryptoKey)}},lt=class s{constructor(e,t,i,r){if(this.keyHash=e,this.cryptoKey=t,this.siv=i,r!==2&&r!==3)throw new Error("Invalid encryption version");this.encryptionVersion=r}static async init(e,t,i){if(e.byteLength!==32)throw new Error("Invalid encryption key");let r=await x.importKey("raw",e,"HKDF",!1,["deriveKey"]),n=I(t),o=await x.deriveKey({name:"HKDF",salt:n,info:I("ObsidianKeyHash"),hash:"SHA-256"},r,{name:"AES-CBC",length:256},!0,["encrypt"]),a=O(await x.exportKey("raw",o)),l=await fe.importKey(r,n),u=await x.deriveKey({name:"HKDF",salt:new Uint8Array,info:I("ObsidianAesGcm"),hash:"SHA-256"},r,{name:"AES-GCM",length:256},!1,["encrypt","decrypt"]);return new s(a,u,l,i)}async deterministicEncodeStr(e){let t=I(e),i=await this.siv.seal(new Uint8Array(t));return O(ne(i))}async deterministicDecodeStr(e){let t=ze(e),i=await this.siv.open(new Uint8Array(t));return V(ne(i))}async encrypt(e){return Ae(e,this.cryptoKey)}async decrypt(e){return _e(e,this.cryptoKey)}};var Oe=class{constructor(e,t,i){this.refreshTimer=null;this.lockTime=0;this.fs=e,this.path=t,this.lockPath=i}acquire(){let{fs:e,lockPath:t}=this,i=this.path.dirname(t);e.mkdirSync(i,{recursive:!0});try{e.mkdirSync(t)}catch(r){if(r.code!=="EEXIST")throw r;let n;try{n=e.statSync(t).mtimeMs}catch(o){if(o.code==="ENOENT")return this.acquire();throw o}if(Date.now()-n<5e3)throw new Q}if(this.lockTime=gi(),this.touch(),!this.verify())throw new Q;this.refreshTimer=setInterval(()=>{this.lockTime=gi(),this.touch()},1e3)}release(){this.refreshTimer&&(clearInterval(this.refreshTimer),this.refreshTimer=null);try{this.verify()&&this.fs.rmdirSync(this.lockPath)}catch{}}touch(){try{let e=this.lockTime/1e3;this.fs.utimesSync(this.lockPath,e,e)}catch{}}verify(){try{let e=this.fs.statSync(this.lockPath).mtimeMs;return e===this.lockTime||Math.floor(e/1e3)===Math.floor(this.lockTime/1e3)}catch{return!1}}},Q=class extends Error{constructor(){super("Failed to acquire lock.")}};function gi(){let s=Date.now();return s%1e3===0&&(s+=1),s}var L=new di.Command,X="ob";L.name(X).description("Headless client for Obsidian services").version("1.0.0");L.command("login").description("Login to Obsidian account or display login status").option("--email <email>","Email address (prompted if omitted)").option("--password <password>","Password (prompted if omitted)").option("--mfa <code>","MFA code (prompted if omitted)").action(async s=>{try{let e=Z();if(e&&!s.email&&!s.password){let n=await ni(e);if(n){console.log(`Logged in as ${n.name} (${n.email})`);return}}if(e){try{await rt(e)}catch{}Ue()}let t=s.email||await he("Email: ",!0),i=s.password||await he("Password: "),r;try{r=await it(t,i,s.mfa||"")}catch(n){if(n instanceof oe&&n.error.includes("2FA code")){if(n.error.includes("2FA code is incorrect"))throw n;let o=await he("2FA code: ");r=await it(t,i,o)}else throw n}Ft(r.token),console.log(`Logged in as ${r.name} (${r.email})`)}catch(e){console.error("Login failed:",e.message||e),process.exit(2)}});L.command("logout").description("Logout from Obsidian account").action(async()=>{try{let s=Z();if(!s){console.log("No account logged in.");return}try{await rt(s)}catch{}Ue(),console.log("Logged out.")}catch(s){console.error("Logout failed:",s.message||s),process.exit(1)}});L.command("sync-list-remote").description("List available remote vaults").action(async()=>{try{let s=Re();console.log("Fetching vaults...");let e=await nt(s,ct);if(e.vaults.length===0&&e.shared.length===0){console.log("No vaults found.");return}console.log(`
|
|
7
|
+
`}return i.join("").replace(/%20/g," ")}};function Vt(s,e,t){let i=new ye,r=i.diff_main(s,e,!0,0);r.length>2&&(i.diff_cleanupSemantic(r),i.diff_cleanupEfficiency(r));let n=i.patch_make(s,r);return i.patch_apply(n,t)[0]}var Fe=["bmp","png","jpg","jpeg","gif","svg","webp","avif"],be=["mp3","wav","m4a","3gp","flac","ogg","oga","opus"],we=["mp4","webm","ogv","mov","mkv"],ve=["pdf"],jt=["md"],Je=["canvas"],qt=["base"];var Pr=jt.concat(Je,qt),Ar=[].concat(Fe,be,we,ve,jt,Je);var _r=[...Fe,...be,...we,...ve,...qt,...Je];var Se=class{constructor(e){this.allowTypes=new Set(K);this.allowSpecialFiles=new Set(Be);this.ignoreFolders=[];this.filterCache={};this.configDir=e}init(e,t,i){this.filterCache={},this.allowTypes=new Set(e||K),this.allowSpecialFiles=new Set(t||[]),this.ignoreFolders=i||[]}clear(){this.filterCache={},this.allowTypes=new Set(K),this.allowSpecialFiles=new Set(Be),this.ignoreFolders=[]}clearCache(){this.filterCache={}}allowSyncFile(e,t){let{filterCache:i}=this;return Object.hasOwn(i,e)?i[e]:i[e]=this._allowSyncFile(e,t)}_allowSyncFile(e,t){for(let n of this.ignoreFolders)if(t&&e===n||e.startsWith(n+"/"))return!1;if(!t&&e.startsWith(this.configDir+"/")){let n=e.substring((this.configDir+"/").length),o=n.split("/");if(o.some(u=>u==="node_modules"||u.startsWith(".")))return!1;let a=C(n),l=T(a),c=null;return n==="workspace.json"||n==="workspace-mobile.json"?!1:(n==="app.json"||n==="types.json"?c="app":n==="appearance.json"?c="appearance":n==="hotkeys.json"?c="hotkey":n==="core-plugins.json"||n==="core-plugins-migration.json"?c="core-plugin":n==="community-plugins.json"?c="community-plugin":o[0]==="themes"&&o.length===3&&(a==="theme.css"||a==="manifest.json")||o[0]==="snippets"&&o.length===2&&l==="css"?c="appearance-data":o.length===1&&l==="json"?c="core-plugin-data":o[0]==="plugins"&&o.length===3&&this.isPluginFile(a)&&(c="community-plugin-data"),c&&this.allowSpecialFiles.has(c))}if(e.startsWith("."))return!1;if(t)return!0;if(e.startsWith("."))return!1;let i=T(C(e));if(i==="md"||i==="canvas"||i==="base")return!0;let{allowTypes:r}=this;return Fe.includes(i)?r.has("image"):i==="webm"?r.has("audio")||r.has("video"):be.includes(i)?r.has("audio"):we.includes(i)?r.has("video"):ve.includes(i)?r.has("pdf"):!!r.has("unsupported")}isPluginFile(e){return e==="manifest.json"||e==="main.js"||e==="styles.css"||e==="data.json"}};var ie=class{constructor(){this.promise=Promise.resolve()}queue(e){let t=this.promise.then(e,e);return this.promise=t,t}};function Ee(){let s={promise:null,resolve:null,reject:null};return s.promise=new Promise((e,t)=>{s.resolve=e,s.reject=t}),s}var Ze=WebSocket,Kt=URL,Ni=Object.getOwnPropertyDescriptor(Kt.prototype,"hostname").get,ki=String.prototype.endsWith,Wt={1e3:"Disconnected",1001:"Going Away",1002:"Protocol Error",1003:"Unsupported Data",1004:"(For future)",1005:"No Status Received",1006:"Disconnected",1007:"Invalid frame payload data",1008:"Policy Violation",1009:"Message too big",1010:"Missing Extension",1011:"Internal Error",1012:"Service Restart",1013:"Try Again Later",1014:"Bad Gateway",1015:"TLS Handshake"};function Mi(s){if(s>=0&&s<=999)return"(Unused)";if(s>=1016){if(s<=1999)return"(For WebSocket standard)";if(s<=2999)return"(For WebSocket extensions)";if(s<=3999)return"(For libraries and frameworks)";if(s<=4999)return"(For applications)"}return Wt.hasOwnProperty(s)?Wt[s]:"(Unknown)"}var Bi=20*1e3,Ui=10*1e3,Vi=2*60*1e3,De=class{constructor(e){this.socket=null;this.queue=new ie;this.notifyQueue=new ie;this.dataQueue=[];this.onDisconnect=null;this.perFileMax=199*1024*1024;this.userId=-1;this.justPushed=null;this.encryptionProvider=e}isConnecting(){let{socket:e}=this;return e&&e.readyState===Ze.CONNECTING}isConnected(){let{socket:e}=this;return e&&e.readyState===Ze.OPEN}hasConnection(){let{socket:e}=this;return!!e}async connect(e,t,i,r,n,o,a,l){if(this.hasConnection())return;this.onReady=a,this.onPush=l;let c=this.encryptionProvider.keyHash;return new Promise((u,p)=>{let d=new Kt(e),w=Ni.call(d);if(!ki.call(w,".obsidian.md")&&w!=="127.0.0.1")return p(new Error("Unable to connect to server."));let v=!1,b=h=>{v||(v=!0,this.disconnect(),p(h))},g=this.socket=new Ze(d);g.binaryType="arraybuffer",g.onclose=h=>{h.code===1006?b(new Error("Unable to connect to server.")):b(new Error("Disconnected. Code: "+h.code+" "+Mi(h.code)))},g.onopen=()=>{this.lastMessageTs=Date.now(),this.heartbeat=setInterval(()=>{let h=Date.now()-this.lastMessageTs;if(h>Vi){this.disconnect();return}h>Ui&&this.send({op:"ping"})},Bi),this.send({op:"init",token:t,id:i,keyhash:c,version:r,initial:n,device:o,encryption_version:this.encryptionProvider.encryptionVersion})},g.onmessage=h=>{let f=h.data;if(typeof f!="string")return b(new Error("Server returned binary"));let S;try{S=JSON.parse(f)}catch(m){return console.error(m),b(new Error("Server JSON failed to parse: "+f))}if(S.op!=="pong"){if(S.status==="err"||S.res==="err")return b(new Error("Failed to authenticate: "+S.msg));if(S.res!=="ok")return b(new Error("Did not respond to login request: "+f));if(S.hasOwnProperty("perFileMax")){let m=S.perFileMax;if(!Number.isInteger(m)||isNaN(m)||m<0)return b(new Error("Unexpected value from server for max file size"));this.perFileMax=m}S.userId&&(this.userId=S.userId),u(),v=!0,g.onmessage=this.onMessage.bind(this),g.onclose=this.disconnect.bind(this),g.onerror=this.disconnect.bind(this)}}})}disconnect(){let e=!1;this.socket&&(this.socket.close(),this.socket=null,e=!0),this.heartbeat&&(clearInterval(this.heartbeat),this.heartbeat=null),this.responsePromise&&(this.responsePromise.reject(new Error("Disconnected")),this.responsePromise=null),this.dataPromise&&(this.dataPromise.reject(new Error("Disconnected")),this.dataPromise=null),e&&this.onDisconnect&&this.onDisconnect()}async pull(e){return this.queue.queue(async()=>{this.lastNetworkRequestTs=Date.now(),this.dataQueue.length=0;let t=await this.request({op:"pull",uid:e});if(!t.deleted){let i=t.size,r=t.pieces,n=new ArrayBuffer(i),o=0;for(let a=0;a<r;a++){let l=await this.dataResponse();new Uint8Array(n,o,l.byteLength).set(new Uint8Array(l)),o+=l.byteLength}return n.byteLength>0&&(n=await this.encryptionProvider.decrypt(n)),n}return null})}async push(e,t,i,r,n,o,a,l){return this.queue.queue(async()=>{this.lastNetworkRequestTs=Date.now();let c=await this.encryptionProvider.deterministicEncodeStr(e),u=t?await this.encryptionProvider.deterministicEncodeStr(t):null,p=i?"":T(C(e));if(i||r){this.justPushed={path:c,folder:i,deleted:r,mtime:0,hash:""},await this.request({op:"push",path:c,relatedpath:u,extension:p,hash:"",ctime:0,mtime:0,folder:i,deleted:r});return}l.byteLength>0&&(l=await this.encryptionProvider.encrypt(l)),a&&(a=await this.encryptionProvider.deterministicEncodeStr(a));let d=l.byteLength,w=2*1024*1024,v=Math.ceil(d/w);if(this.justPushed={path:c,folder:i,deleted:r,mtime:o,hash:a},(await this.request({op:"push",path:c,relatedpath:u,extension:p,hash:a,ctime:n,mtime:o,folder:i,deleted:r,size:d,pieces:v})).res==="ok"){this.justPushed=null;return}for(let g=0;g<v;g++){let h=g*w,f=Math.min(w,d-h);this.sendBinary(new Uint8Array(l,h,f)),await this.response()}this.justPushed=null})}async listDeleted(){return this.queue.queue(async()=>{let t=(await this.request({op:"deleted",suppressrenames:!0})).items;for(let i of t)i.path=await this.encryptionProvider.deterministicDecodeStr(i.path);return t})}async listHistory(e,t){return this.queue.queue(async()=>{let i=await this.encryptionProvider.deterministicEncodeStr(e),r=await this.request({op:"history",path:i,last:t}),n=r.items;for(let o of n)o.path=await this.encryptionProvider.deterministicDecodeStr(o.path),o.relatedpath=o.relatedpath&&await this.encryptionProvider.deterministicDecodeStr(o.relatedpath);return r})}async restore(e){return this.queue.queue(async()=>this.request({op:"restore",uid:e}))}async getUsernames(){return this.queue.queue(()=>this.request({op:"usernames"}))}async purge(){return this.queue.queue(()=>this.request({op:"purge"}))}async size(){return this.queue.queue(()=>this.request({op:"size"}))}onServerPush(e){let{justPushed:t}=this;t&&t.path===e.path&&t.folder===e.folder&&t.deleted===e.deleted&&t.mtime===e.mtime&&t.hash===e.hash&&(this.justPushed=null,e.wasJustPushed=!0),this.notifyQueue.queue(async()=>{e.path=await this.encryptionProvider.deterministicDecodeStr(e.path),e.hash&&(e.hash=await this.encryptionProvider.deterministicDecodeStr(e.hash)),this.onPush(e)})}response(){return(this.responsePromise=Ee()).promise}dataResponse(){return this.dataQueue.length>0?Promise.resolve(this.dataQueue.shift()):(this.dataPromise=Ee()).promise}async request(e,t=6e4){let i=this.responsePromise=Ee();this.send(e);let r=new Error("Timeout"),n=setTimeout(()=>i.reject(r),t),o;try{o=await i.promise,clearTimeout(n)}catch(a){throw a===r&&this.disconnect(),a}if(o.err)throw new Error(o.err);return o}onMessage(e){if(this.lastMessageTs=Date.now(),typeof e.data=="string"){let t;try{t=JSON.parse(e.data)}catch{console.log(e.data),this.disconnect();return}let i=t.op;if(i==="pong")return;if(i==="ready"){this.notifyQueue.queue(async()=>{this.onReady(t.version)});return}if(i==="push"){this.onServerPush(t);return}let r=this.responsePromise;r&&(this.responsePromise=null,r.resolve(t))}else{let t=this.dataPromise;t?(this.dataPromise=null,t.resolve(e.data)):this.dataQueue.push(e.data)}}send(e){this.socket.send(JSON.stringify(e))}sendBinary(e){this.socket.send(e)}};var Pe=class{constructor(e,t,i,r){this.min=e||0,this.max=t||Number.MAX_VALUE,this.base=i||1e3,this.jitter=r||!0,this.count=0,this.nextTs=Date.now()}success(){this.count=0,this.nextTs=Date.now()+this.getTimeout()}fail(){this.count++,this.nextTs=Date.now()+this.getTimeout()}getTimeout(){if(this.count===0)return this.min;let e=this.count-1,t=this.base*Math.pow(2,e);if(this.jitter){let i=.5;t=t*(1-i+i*Math.random())}return t=Math.floor(Math.min(this.max,this.min+t)),t}getNextTs(){return this.nextTs}isReady(){return Date.now()>this.nextTs}};var Ht=crypto,x=Ht.subtle,ze="AES-GCM";function $t(s){return x.importKey("raw",s,ze,!1,["encrypt","decrypt"])}async function Ae(s,e,t){t||(t=Ht.getRandomValues(new Uint8Array(12)));let i=await x.encrypt({name:ze,iv:t},e,s),r=new ArrayBuffer(t.byteLength+i.byteLength),n=new Uint8Array(r);return n.set(new Uint8Array(t),0),n.set(new Uint8Array(i),t.byteLength),r}async function _e(s,e){if(s.byteLength<12)throw new Error("Encrypted data is bad");if(s.byteLength===12)return new ArrayBuffer(0);let t=new Uint8Array(s,0,12),i=new Uint8Array(s,12);return await x.decrypt({name:ze,iv:t},e,i)}function re(s){return s.buffer.slice(s.byteOffset,s.byteOffset+s.byteLength)}function I(s){return re(new TextEncoder().encode(s))}function V(s){return new TextDecoder().decode(new Uint8Array(s))}function Gt(s){let e=atob(s),t=e.length,i=new Uint8Array(t);for(let r=0;r<t;r++)i[r]=e.charCodeAt(r);return i.buffer}function Qt(s){return ji(new Uint8Array(s))}function ji(s){let e=[],t=s.byteLength;for(let i=0;i<t;i++)e.push(String.fromCharCode(s[i]));return btoa(e.join(""))}async function ne(s){return O(await se(s))}async function se(s){return x.digest("SHA-256",new Uint8Array(s))}function et(s){let e=s.length/2,t=new ArrayBuffer(e),i=new Uint8Array(t);for(let r=0;r<e;r++)i[r]=parseInt(s.substr(r*2,2),16);return t}function O(s){let e=new Uint8Array(s),t=[];for(let i=0;i<e.length;i++){let r=e[i];t.push((r>>>4).toString(16)),t.push((r&15).toString(16))}return t.join("")}function tt(s){if(s<=0)return"0 B";let e=["B","KB","MB","GB","TB","PB"],t=e.length-1,i=1024;for(let n=0;n<e.length;n++)if(s<Math.pow(i,n+1)){t=n;break}let r=s/Math.pow(i,t);return`${qi(r,t===0?0:2)} ${e[t]}`}function qi(s,e=2,t=".",i=","){let r=s<0?"-":"";s=Math.abs(s);let n=parseInt(s.toFixed(e),10)+"",o=n.length>3?n.length%3:0;return r+(o?n.substr(0,o)+i:"")+n.substr(o).replace(/(\d{3})(?=\d)/g,"$1"+i)+(e?t+Math.abs(s-Math.floor(s)).toFixed(e).slice(2):"")}var Wi=function(){let s=typeof process<"u"?process.platform:"";if(s==="win32")return"win";if(s==="darwin")return"mac";if(s==="linux")return"linux";if(s)return"unknown";let e=navigator.userAgent;return e.indexOf("Win")!==-1?"win":e.indexOf("Mac")!==-1?"mac":e.indexOf("X11")!==-1||e.indexOf("Linux")!==-1?"linux":"unknown"}(),Xt=navigator.userAgent.toLowerCase();var it=Wi==="win";var Gr=/^((?!chrome|android).)*safari/i.test(Xt),Yt=/android/i.test(Xt);var Ki=/[.?*+^$[\]\\(){}|-]/g;function Te(s){return s.replace(Ki,"\\$&")}var Hi="\\/:"+(Yt?'*?<>"':""),$i='*"\\/<>:|?',Jt="#^[]|",Zt=it?$i:Hi,Gi=Zt.split("").join("\xA0"),zr=Jt.split("").join("\xA0"),zt=new RegExp("["+Te(Zt)+"]"),en=new RegExp("["+Te(Jt)+"]"),Qi=/^(CON|PRN|AUX|NUL|COM[1-9]|LPT[1-9])$/i;function ei(s){try{return Xi(s),!0}catch{return!1}}function Xi(s){if(it){let e=s.charAt(s.length-1);if(e==="."||e===" ")throw new Error("File names cannot end with a dot or a space.");let t=It(s);if(Qi.test(t))throw new Error("File name is forbidden: "+t)}if(s.split("/").some(e=>zt.test(e)))throw new Error("File name cannot contain any of the following characters: "+Gi)}function ti(s,e="_"){let t=s.trim();if(t&&(t=s.replace(zt,e),e.length===1)){let i=Te(e),r=new RegExp(`${i}{2,}`,"g");t=t.replace(r,e)}return t}function Yi(s){return new Promise(e=>setTimeout(e,s))}var xe=class{constructor(e){this.server=null;this.localFiles={};this.serverFiles={};this.newServerFiles=[];this.version=0;this.initial=!0;this.ready=!1;this.syncing=!1;this.loaded=!1;this.backoff=new Pe(0,5*60*1e3,5e3,!0);this.fileRetry={};this.skippedFiles={};this.syncingPath="";this.scanSpecialFiles=!1;this.scanSpecialFileQueue=[];this.resolveStop=null;let{config:t}=e;this.host=t.host,this.token=e.token,this.vaultId=t.vaultId,this.continuous=e.continuous||!1,this.encryption=e.encryption;let i=vt(t.vaultId);this.stateStore=new me(i),this.conflictStrategy=t.conflictStrategy||"merge",this.syncMode=t.syncMode||"",this.deviceName=t.deviceName||"Sync Client",this.adapter=new de(D.default,P.default,Ne.default,()=>!1,yt,"file:///",t.vaultPath),this.filter=new Se(t.configDir),this.filter.init(t.allowTypes||[],t.allowSpecialFiles||[],t.ignoreFolders||[]),this.loadState()}loadState(){this.version=this.stateStore.getVersion(),this.initial=this.stateStore.isInitial(),this.localFiles=this.stateStore.getAllLocalFiles(),this.serverFiles=this.stateStore.getAllServerFiles(),this.newServerFiles=this.stateStore.getPendingFiles()}handlePush(e){if(this.version=e.uid,this.initial&&e.deleted){this.stateStore.setVersion(this.version);return}let t=e.path,i={path:t,size:e.size,hash:e.hash,ctime:e.ctime,mtime:e.mtime,folder:e.folder,deleted:e.deleted,uid:e.uid,device:e.device,user:e.user};this.initial&&(i.initial=!0);let{newServerFiles:r}=this;if(e.wasJustPushed){for(let n=0;n<r.length;n++)r[n].path===t&&(r.splice(n,1),n-=1);this.stateStore.deletePendingFile(t),this.serverFiles[t]=i,this.stateStore.setServerFile(i),this.stateStore.setVersion(this.version);return}r.push(i),this.stateStore.addPendingFile(i),this.stateStore.setVersion(this.version),this.initial||console.debug(`Push: ${i.path} (${i.deleted?"deleted":"updated"})`),this.requestSync()}async sync(){let e=new Promise(i=>this.resolveStop=i),t;try{if(!this.loaded){await this.adapter.watch(this.onChange.bind(this));for(let i in this.localFiles)Object.hasOwn(this.adapter.files,i)||(delete this.localFiles[i],this.stateStore.deleteLocalFile(i));this.scanSpecialFiles=!0,this.loaded=!0}t=setInterval(this.requestSync.bind(this),30*1e3),await this.requestSync(),await e}finally{clearInterval(t)}}stop(){this.server&&(this.server.disconnect(),this.server=null),this.ready=!1,this.continuous=!1,this.stateStore.close(),this.adapter.stopWatch(),this.adapter.thingsHappening.cancel(),this.resolveStop&&(this.resolveStop(),this.resolveStop=null)}async requestSync(){if(!this.syncing){this.syncing=!0;try{let e=!0;for(;e;){try{this.syncingPath="",e=await this._sync();let i=this.syncingPath;i&&delete this.fileRetry[i]}catch(i){if(console.error("Sync error:",i),this.failedSync(this.syncingPath),e=!1,!this.continuous)throw this.syncing=!1,i}if(!e)return;let t=0;if(this.server){let i=Date.now()-this.server.lastNetworkRequestTs;t=Math.max(0,50-i)}await Yi(t)}}finally{this.syncing=!1}}}canSyncPath(e,t){let{fileRetry:i}=this;for(let r in i)if(i.hasOwnProperty(r)&&i[r].ts>e&&t.startsWith(r))return!1;return!0}canSyncLocalFile(e,t){if(!t.synctime)return!0;let i=t.size,r=i>10*1024,n=i>100*1024,o=r?n?30:20:10;return e-t.synctime>o*1e3}failedSync(e){if(!e)return;let t=Date.now(),i=this.fileRetry[e];i||(i=this.fileRetry[e]={count:0,ts:0});let r=i.count=i.count+1,n=Math.pow(2,r)*5*1e3;n=Math.min(n,5*60*1e3),i.ts=t+n}async getServer(){let{server:e}=this;if(e&&!e.isConnected()&&!e.isConnecting()&&(e.disconnect(),e=this.server=null,this.backoff.fail()),!e){if(!this.backoff.isReady())return this.log("Waiting to connect to server"),null;e=this.server=new De(this.encryption)}if(!e.hasConnection()){this.log("Connecting..."),this.ready=!1;try{let t=this.host.startsWith("127.0.0.1")||this.host.startsWith("localhost")?"ws://":"wss://";e.onDisconnect=()=>{this.ready=!1,this.log("Disconnected from server"),this.continuous&&this.requestSync()},await e.connect(t+this.host,this.token,this.vaultId,this.version,this.initial,this.deviceName,i=>{this.ready=!0,this.initial=!1,this.stateStore.setInitial(!1),this.version<i&&(this.version=i,this.stateStore.setVersion(this.version)),this.requestSync()},i=>this.handlePush(i)),this.log("Connection successful. Detecting changes..."),this.backoff.success()}catch(t){if(t.message&&t.message.includes("Your subscription to Obsidian Sync has expired"))throw console.error(t.message),this.stop(),t;if(t.message&&t.message.includes("Vault not found"))throw console.error("The connected remote vault no longer exists."),this.stop(),t;return console.error(t),e.disconnect(),e=this.server=null,this.backoff.fail(),null}}return e}async _sync(){let e=await this.getServer();if(!e)return!1;let t=Date.now(),i=0,r=this.filter.configDir,n=r+"/",{localFiles:o,serverFiles:a,newServerFiles:l,stateStore:c,filter:u,adapter:p}=this;try{let g={},h=this.scanSpecialFileQueue;if(this.scanSpecialFiles){this.scanSpecialFiles=!1,h=this.scanSpecialFileQueue=[];for(let f in o)Object.hasOwn(o,f)&&f.startsWith(".")&&(g[f]=o[f],delete o[f],c.deleteLocalFile(f));if(u.allowSpecialFiles.size>0&&await p.exists(r)){h.push(n+"config");let f=await p.list(r);for(let S of f.files)T(S)==="json"&&h.push(S);if(await p.exists(n+"themes")){let S=await p.list(n+"themes");for(let m of S.folders){let y=await p.list(m);for(let F of y.files){let E=C(F);(E==="manifest.json"||E==="theme.css")&&h.push(F)}}}if(await p.exists(n+"snippets")){let S=await p.list(n+"snippets");for(let m of S.files)T(m)==="css"&&h.push(m)}if(await p.exists(n+"plugins")){let S=await p.list(n+"plugins");for(let m of S.folders){let y=await p.list(m);for(let F of y.files){let E=C(F);u.isPluginFile(E)&&h.push(F)}}}}}for(;h.length>0;){let f=h.pop();if(!await p.exists(f)){delete o[f],c.deleteLocalFile(f);continue}let S=await p.stat(f);if(!S||S.type!=="file"){delete o[f],c.deleteLocalFile(f);continue}let m=o[f];m||(Object.hasOwn(g,f)?m=o[f]=g[f]:m=o[f]={path:f,previouspath:"",ctime:0,mtime:0,size:0,folder:!1,hash:"",synchash:"",synctime:0});let y=Math.ceil(S.mtime),F=Math.ceil(S.ctime),E=S.size;(!m.mtime||m.mtime!==y||m.size!==S.size)&&(m.hash=""),m.mtime=y,m.ctime=F,m.size=E,c.setLocalFile(m)}}catch(g){console.error("Failed to scan config files",g)}if(l.length>0)for(let g=0;g<l.length;g++){let h=l[g],f=h.path,S=a[f],m=o[f],y=(F,E)=>(F||this.log("Accepted",f),m&&(m.synctime=Date.now(),c.setLocalFile(m)),E||(a[f]=h,c.setServerFile(h)),l.splice(g,1),c.deletePendingFile(f),!0);if(!u.allowSyncFile(f,h.folder))return y(!0);if(!ei(f))return this.log("Ignoring remote file name with illegal characters",f,!0),y(!0,!0);if(H(f).split("/").includes(".."))return y(!0);if(!this.canSyncPath(t,f)){i++;continue}if(this.syncingPath=f,m&&!m.folder&&!m.hash){this.log("Checking",f);let F=await p.readBinary(f);m.hash=await ne(F),c.setLocalFile(m)}if(m&&!m.folder&&!h.folder&&m.hash===h.hash)return y(!0);for(let F=g+1;F<l.length;F++)if(l[F].path===f)return this.log("Skipped",f),y(!0,!0);if(!m)return h.deleted?y(!0):(await this.syncFileDown(e,h),y());if(m.folder&&h.folder){if(h.deleted){try{let F=await p.list(f);if(F.files.length>0||F.folders.length>0)return y(!0)}catch{}this.log("Deleting",f);try{await p.rmdir(f,!0)}catch(F){let E=(F?F.message:"")||"Failed to delete folder";this.log(E,f,!0)}}return y(!0)}if(this.syncMode==="pull-only"||this.syncMode==="mirror-remote"||S&&(m.folder&&S.folder||m.hash===S.hash))return h.deleted?(this.log("Deleting",f),m.folder?await this.adapter.rmdir(f,!0):await this.adapter.remove(f),delete o[f],this.stateStore.deleteLocalFile(f),y()):(await this.syncFileDown(e,h),y());if(!m.folder&&h.folder)try{let F=await p.stat(f);if(F&&F.type==="file"){let E=T(C(f)),_=E?f.substr(f.length-E.length-1):"",R=f.substr(0,f.length-_.length)+" (Conflicted copy)"+_;return this.log("Renaming conflicted file",f),await p.rename(f,R),!0}}catch{}if(h.initial&&h.mtime>m.mtime)return await this.syncFileDown(e,h),y();if(!h.initial&&!m.folder&&!h.folder&&!h.deleted&&T(f)==="md"&&h.hash!==m.synchash){this.logMerge("Merging conflicted file",f);let F=await this.adapter.read(f);if(!F)return await this.syncFileDown(e,h),y();let E="";if(S&&!S.deleted)try{E=V(await e.pull(S.uid))}catch(R){return this.logMerge("Merge failed. "+R.toString(),f,!0),y(!0)}let _;try{_=V(await e.pull(h.uid))}catch(R){return this.logMerge("Merge failed. "+R.toString(),f,!0),y(!0)}if(E===_||F===_||!_)return y();if(this.conflictStrategy==="conflict"){let R=new Date().toLocaleString("sv").replace(/[:\- ]/g,"").substring(0,12),mi=T(f),yi=Lt(f),Fi=ti(this.deviceName),bi=`${yi} (Conflicted copy ${Fi} ${R}).${mi}`;try{await p.write(bi,F,{ctime:m.ctime,mtime:m.mtime}),await p.write(f,_,{ctime:h.ctime,mtime:h.mtime}),this.logMerge("Conflicted copy stored",f)}catch{return y()}return y()}if(!E)return Math.abs(Date.now()-m.ctime)<3*60*1e3?(this.log("Downloading "+f),await p.write(f,_,{ctime:h.ctime,mtime:h.mtime}),y()):(h.mtime>m.mtime&&(this.log("Downloading "+f),await p.write(f,_,{ctime:h.ctime,mtime:h.mtime})),y());let q=Vt(E,F,_);return await p.write(f,q),this.logMerge("Merge successful",f),y()}if(!h.folder&&!h.deleted&&h.size>0&&f.startsWith(n)){if(T(f)==="json")try{this.log("Merging conflicted file",f);let F=JSON.parse(await p.read(f));if(F&&!Array.isArray(F)&&typeof F=="object"){let E=JSON.parse(V(await e.pull(h.uid)));if(E&&!Array.isArray(E)&&typeof E=="object"){for(let q in E)Object.hasOwn(E,q)&&(F[q]=E[q]);let _=I(JSON.stringify(F,void 0,2));return await p.writeBinary(f,_),this.log("Merge successful",f),y(!0)}}}catch(F){this.log("Merge failed. "+F.toString(),f,!0)}return await this.syncFileDown(e,h),y()}return this.log("Rejected server change",f),y(!0)}if(!this.ready)return!1;if(this.syncMode==="mirror-remote"){let g=null,h=null;for(let y in a){if(!Object.hasOwn(a,y))continue;let F=a[y];if(!F.deleted&&!Object.hasOwn(o,y)&&u.allowSyncFile(y,F.folder)){if(!this.canSyncPath(t,y)){i++;continue}F.folder?(!g||y.length<g.path.length)&&(g=F):(!h||F.size<h.size)&&(h=F)}}if(g)return this.syncingPath=g.path,this.log("Restoring",g.path),await this.syncFileDown(e,g),!0;if(h)return this.syncingPath=h.path,this.log("Restoring",h.path),await this.syncFileDown(e,h),!0;let f=null,S=null,m=null;for(let y in o){if(!Object.hasOwn(o,y))continue;let F=o[y],E=a[y];if(u.allowSyncFile(y,F.folder)){if(!this.canSyncPath(t,y)){i++;continue}if(!E||E.deleted){F.folder?(!S||y.length>S.path.length)&&(S=F):(!f||y.length>f.path.length)&&(f=F);continue}if(!F.folder&&!E.folder){if(F.hash&&F.hash===E.hash)continue;(!m||F.size<m.size)&&(m=F)}}}if(f){let y=f.path;return this.syncingPath=y,this.log("Removing local-only file",y),await p.remove(y),delete o[y],c.deleteLocalFile(y),!0}if(S){let y=S.path;return this.syncingPath=y,this.log("Removing local-only folder",y),await p.rmdir(y,!0),delete o[y],c.deleteLocalFile(y),!0}if(m){let y=m.path,F=a[y];if(this.syncingPath=y,!m.hash){let E=await p.readBinary(y);if(m.hash=await ne(E),c.setLocalFile(m),m.hash===F.hash)return!0}return this.log("Reverting",y),await this.syncFileDown(e,F),!0}}if(this.syncMode==="mirror-remote"||this.syncMode==="pull-only")return i===0?(this.log("Fully synced"),this.fileRetry={},this.continuous||this.stop(),!1):!0;let d=null,w=null;for(let g in a){if(!Object.hasOwn(a,g))continue;let h=a[g];if(!Object.hasOwn(o,g)){if(h.deleted){delete a[g],c.deleteServerFile(g);continue}if(!u.allowSyncFile(g,h.folder))continue;h.folder?(!w||h.path.length>w.path.length)&&(w=h):(!d||h.path.length>d.path.length)&&(d=h)}}if(d){let g=d.path;return this.log("Deleting remote file",g),this.syncingPath=g,await e.push(g,null,!1,!0,0,0,"",null),d.deleted=!0,c.setServerFile(d),!0}if(w){let g=w.path;return this.log("Deleting remote folder",g),this.syncingPath=g,await e.push(g,null,!0,!0,0,0,"",null),w.deleted=!0,c.setServerFile(w),!0}let v=null,b=null;for(let g in o){if(!Object.hasOwn(o,g))continue;let h=o[g],f=a[g];if(!(f&&!f.deleted&&h.folder===f.folder&&h.ctime===f.ctime&&h.mtime===f.mtime&&h.size===f.size&&h.hash&&h.hash===f.hash)&&u.allowSyncFile(g,h.folder)){if(!this.canSyncPath(t,g)){i++;continue}if(process.platform==="linux"&&!h.folder&&f&&f.ctime&&(h.ctime===0||h.ctime>f.ctime)&&!f.folder&&!f.deleted&&(h.ctime=f.ctime),!h.folder&&h.size>e.perFileMax){this.logSkip(`File too large to sync (${tt(h.size)}, max ${tt(e.perFileMax)})`,g);continue}if(!f||f.deleted){if(!this.canSyncLocalFile(t,h)){i++;continue}h.folder?(!v||h.path.length<v.path.length)&&(v=h):(!b||h.size<b.size)&&(b=h);continue}if(!v){if(h.folder){if(!this.canSyncLocalFile(t,h)){i++;continue}f.folder||(!v||h.path.length<v.path.length)&&(v=h);continue}if(f.folder){if(!this.canSyncLocalFile(t,h)){i++;continue}w=f;continue}if(!h.hash||h.hash!==f.hash){if(!this.canSyncLocalFile(t,h)){i++;continue}(!b||h.size<b.size)&&(b=h)}}}}if(v){let g=v.path;return this.syncingPath=g,this.log("Uploading",g),await e.push(g,v.previouspath,!0,!1,0,0,"",null),Object.hasOwn(a,g)?a[g].deleted&&(a[g].deleted=!1):a[g]={uid:0,path:g,size:0,hash:"",ctime:0,mtime:0,folder:!0,deleted:!1,device:this.deviceName},c.setServerFile(a[g]),v.previouspath="",v.synctime=Date.now(),c.setLocalFile(v),!0}if(b){let g=b.path;this.log("New file",g),this.syncingPath=g;let h=a[g],{ctime:f,mtime:S}=b,m=await p.readBinary(g),y=b.hash=await ne(m);return c.setLocalFile(b),h&&!h.deleted&&h.hash===b.hash||(this.log("Uploading file",g),await e.push(g,b.previouspath,!1,!1,f,S,y,m),b.synchash=y,this.log("Upload complete",g),b.previouspath="",b.synctime=Date.now(),c.setLocalFile(b)),!0}return i===0?(this.log("Fully synced"),this.fileRetry={},this.continuous||this.stop(),!1):!0}onChange(e,t,i,r){if(e==="file-created"){let n=this.localFiles[t];n||(n=this.localFiles[t]={path:t,previouspath:"",folder:!1,ctime:0,mtime:0,size:0,hash:"",synctime:0,synchash:""}),r&&((n.mtime!==r.mtime||n.size!==r.size)&&(n.hash=""),n.ctime=r.ctime,n.mtime=r.mtime,n.size=r.size),this.stateStore.setLocalFile(n)}else if(e==="folder-created")this.localFiles[t]||(this.localFiles[t]={path:t,previouspath:"",folder:!0,ctime:0,mtime:0,size:0,hash:"",synctime:0,synchash:""},this.stateStore.setLocalFile(this.localFiles[t]));else if(e==="modified"){let n=this.localFiles[t];n&&r&&((n.mtime!==r.mtime||n.size!==r.size)&&(n.hash=""),n.ctime=r.ctime,n.mtime=r.mtime,n.size=r.size,this.stateStore.setLocalFile(n))}else if(e==="file-removed"||e==="folder-removed")delete this.localFiles[t],this.stateStore.deleteLocalFile(t);else if(e==="renamed"){let n=this.localFiles[i];n&&(delete this.localFiles[i],this.stateStore.deleteLocalFile(i),n.path=t,n.previouspath=i,this.localFiles[t]=n,this.stateStore.setLocalFile(n))}if(e==="raw"&&t.startsWith(this.filter.configDir+"/")&&!t.endsWith(".sync.lock")){let n=this.scanSpecialFileQueue;if(n.includes(t))return;n.push(t),this.requestSync()}this.loaded&&e!=="raw"&&this.requestSync()}async syncFileDown(e,t){let i=t.path;if(this.log("Downloading",i),t.folder){await this.adapter.mkdir(i),this.log("Downloaded",i);return}let r=await e.pull(t.uid);if(!r)throw new Error("Failed to download file, no data.");let n=k(i);n&&await this.adapter.mkdir(n);let o=await ne(r);await this.adapter.writeBinary(i,r,{ctime:t.ctime,mtime:t.mtime});let a=this.localFiles[i];a&&(a.hash=o,a.synchash=o,this.stateStore.setLocalFile(a)),this.log("Downloaded",i)}log(e,t,i=!1){i?t?console.error(e,t):console.error(e):t?console.log(e,t):console.log(e)}logMerge(e,t,i=!1){this.log(e,t,i)}logSkip(e,t){let{skippedFiles:i}=this;(!Object.hasOwn(i,t)||i[t]!==e)&&(i[t]=e,this.log(e,t,!0))}};var ii=fetch,ri="https://"+["api","obsidian","md"].join("."),oe=class s extends Error{constructor(e){super(e.error),this.response=e,this.error=e.error,Object.setPrototypeOf(this,s.prototype)}};async function j(s,e,t){let{preflight:i,headers:r}=t||{};i&&await ii(ri+s,{method:"OPTIONS"}),r||(r={}),r["Content-Type"]="application/json";let n=await(await ii(ri+s,{method:"POST",body:JSON.stringify(e),headers:r})).json();if("error"in n)throw new oe(n);return n}async function rt(s,e,t){return j("/user/signin",{email:s,password:e,mfa:t},{preflight:!0,headers:{Origin:"https://obsidian.md"}})}function nt(s){return j("/user/signout",{token:s})}function ni(s){return j("/user/info",{token:s})}function si(s,e){return j("/vault/regions",{token:s,host:e})}function st(s,e){return j("/vault/list",{token:s,supported_encryption_version:e})}function oi(s,e,t,i,r,n){return j("/vault/create",{token:s,name:e,keyhash:t,salt:i,region:r,encryption_version:n})}function ai(s,e,t,i,r){return j("/vault/access",{token:s,vault_uid:e,keyhash:t,host:i,encryption_version:r})}var ae=class s extends Error{constructor(e){super(e),Object.setPrototypeOf(this,s.prototype)}};function li(s,e,t){return~(s-1)&e|s-1&t}function Ji(s,e){if(s.length!==e.length)return 0;let t=0;for(let i=0;i<s.length;i++)t|=s[i]^e[i];return 1&t-1>>>8}function ci(s,e){return s.length===0||e.length===0?!1:Ji(s,e)!==0}function Ie(s){for(let e=0;e<s.length;e++)s[e]=0;return s}function Le(s,e){for(let t=0;t<e.length;t++)s[t]^=e[t]}var A=class s{static{this.SIZE=16}static{this.R=135}constructor(){this.data=new Uint8Array(s.SIZE)}clear(){Ie(this.data)}clone(){let e=new s;return e.copy(this),e}copy(e){this.data.set(e.data)}dbl(){let e=0;for(let t=s.SIZE-1;t>=0;t--){let i=this.data[t]>>>7&255;this.data[t]=this.data[t]<<1|e,e=i}this.data[s.SIZE-1]^=li(e,s.R,0),e=0}};var G=crypto.subtle;var le=class s{constructor(e){this.key=e}static async importKey(e,t){let i=await G.deriveKey({name:"HKDF",salt:t,info:new TextEncoder().encode("ObsidianAesSivEnc"),hash:"SHA-256"},e,{name:"AES-CTR",length:256},!1,["encrypt"]);return new s(i)}async encryptCtr(e,t){let i=await G.encrypt({name:"AES-CTR",counter:e,length:16},this.key,t);return new Uint8Array(i)}};var ce=class s{constructor(e){this._key=e;this._iv=new A;this._emptyPromise=Promise.resolve(this)}static async importKey(e,t){let i=await G.deriveKey({name:"HKDF",salt:t,info:new TextEncoder().encode("ObsidianAesSivMac"),hash:"SHA-256"},e,{name:"AES-CBC",length:256},!1,["encrypt"]);return new s(i)}clear(){return this}async encryptBlock(e){let t={name:"AES-CBC",iv:this._iv.data},i=await G.encrypt(t,this._key,e.data);return e.data.set(new Uint8Array(i,0,A.SIZE)),this._emptyPromise}};var ue=class s{constructor(e,t,i){this._cipher=e;this._subkey1=t;this._subkey2=i;this._bufferPos=0;this._finished=!1;this._buffer=new A}static async importKey(e,t){let i=await ce.importKey(e,t),r=new A;await i.encryptBlock(r),r.dbl();let n=r.clone();return n.dbl(),()=>new s(i,r,n)}async update(e){if(this._finished)throw new Error("Cannot update finished CMAC");let t=A.SIZE-this._bufferPos,i=0,r=e.length;if(r>t){for(let n=0;n<t;n++)this._buffer.data[this._bufferPos+n]^=e[n];r-=t,i+=t,await this._cipher.encryptBlock(this._buffer),this._bufferPos=0}for(;r>A.SIZE;){for(let n=0;n<A.SIZE;n++)this._buffer.data[n]^=e[i+n];r-=A.SIZE,i+=A.SIZE,await this._cipher.encryptBlock(this._buffer)}for(let n=0;n<r;n++)this._buffer.data[this._bufferPos++]^=e[i+n];return this}async finish(){if(!this._finished){let e=this._bufferPos<A.SIZE?this._subkey2:this._subkey1;Le(this._buffer.data,e.data),this._bufferPos<A.SIZE&&(this._buffer.data[this._bufferPos]^=128),await this._cipher.encryptBlock(this._buffer),this._finished=!0}return this._buffer.data}};var fe=class s{static async importKey(e,t){let i=await ue.importKey(e,t),r=await le.importKey(e,t);return new s(i,r)}constructor(e,t){this.cmacFactory=e,this._ctr=t}async seal(e){let t=A.SIZE+e.length,i=new Uint8Array(t),r=await this._s2v(e);return i.set(r),ui(r),i.set(await this._ctr.encryptCtr(r,e),r.length),i}async open(e){if(e.length<A.SIZE)throw new ae("AES-SIV: ciphertext is truncated");let t=e.subarray(0,A.SIZE),i=new Uint8Array(A.SIZE);i.set(t),ui(i);let r=await this._ctr.encryptCtr(i,e.subarray(A.SIZE)),n=await this._s2v(r);if(!ci(n,t))throw Ie(r),new ae("AES-SIV: ciphertext verification failure!");return r}async _s2v(e){let t=this.cmacFactory(),i=new A,r=new A;if(await t.update(i.data),r.data.set(await t.finish()),t=this.cmacFactory(),i.clear(),e.length>=A.SIZE){let n=e.length-A.SIZE;i.data.set(e.subarray(n)),await t.update(e.subarray(0,n))}else i.data.set(e),i.data[e.length]=128,r.dbl();return Le(i.data,r.data),await t.update(i.data),t.finish()}};function ui(s){s[s.length-8]&=127,s[s.length-4]&=127}var ut=3,ft=3,fi=32,ot=32768,at=8,hi=1,Zi={N:ot,r:at,p:hi,maxmem:128*ot*at*2};async function ht(s,e){s=s.normalize("NFKC"),e=e.normalize("NFKC");let t=require&&require("crypto");if(t){let r=await new Promise((n,o)=>{t.scrypt(Buffer.from(s,"utf8"),Buffer.from(e,"utf8"),fi,Zi,(a,l)=>{a?o(a):n(l)})});return te(r)}let i=await window.scrypt.scrypt(new Uint8Array(I(s)),new Uint8Array(I(e)),ot,at,hi,fi);return re(i)}async function pi(s,e,t){switch(s){case 0:return lt.init(e);case 2:case 3:return ct.init(e,t,s);default:throw new Error("Encryption version not supported")}}async function pt(s,e,t){switch(t){case 0:return O(await se(s));case 2:case 3:let i=await x.importKey("raw",s,"HKDF",!1,["deriveKey"]),r=await x.deriveKey({name:"HKDF",salt:I(e),info:I("ObsidianKeyHash"),hash:"SHA-256"},i,{name:"AES-CBC",length:256},!0,["encrypt"]);return O(await x.exportKey("raw",r));default:throw new Error("Encryption version not supported")}}var lt=class s{constructor(e,t){this.encryptionVersion=0;this.keyHash=e,this.cryptoKey=t}static async init(e){if(e.byteLength!==32)throw new Error("Invalid encryption key");let t=O(await se(e)),i=await $t(e);return new s(t,i)}async deterministicEncodeStr(e){let t=I(e),i=await se(t),r=new Uint8Array(i,0,12);return O(await Ae(t,this.cryptoKey,r))}async deterministicDecodeStr(e){let t=et(e);return V(await _e(t,this.cryptoKey))}async encrypt(e){return Ae(e,this.cryptoKey)}async decrypt(e){return _e(e,this.cryptoKey)}},ct=class s{constructor(e,t,i,r){if(this.keyHash=e,this.cryptoKey=t,this.siv=i,r!==2&&r!==3)throw new Error("Invalid encryption version");this.encryptionVersion=r}static async init(e,t,i){if(e.byteLength!==32)throw new Error("Invalid encryption key");let r=await x.importKey("raw",e,"HKDF",!1,["deriveKey"]),n=I(t),o=await x.deriveKey({name:"HKDF",salt:n,info:I("ObsidianKeyHash"),hash:"SHA-256"},r,{name:"AES-CBC",length:256},!0,["encrypt"]),a=O(await x.exportKey("raw",o)),l=await fe.importKey(r,n),c=await x.deriveKey({name:"HKDF",salt:new Uint8Array,info:I("ObsidianAesGcm"),hash:"SHA-256"},r,{name:"AES-GCM",length:256},!1,["encrypt","decrypt"]);return new s(a,c,l,i)}async deterministicEncodeStr(e){let t=I(e),i=await this.siv.seal(new Uint8Array(t));return O(re(i))}async deterministicDecodeStr(e){let t=et(e),i=await this.siv.open(new Uint8Array(t));return V(re(i))}async encrypt(e){return Ae(e,this.cryptoKey)}async decrypt(e){return _e(e,this.cryptoKey)}};var Ce=class{constructor(e,t,i){this.refreshTimer=null;this.lockTime=0;this.isMs=!0;this.fs=e,this.path=t,this.lockPath=i}acquire(){let{fs:e,lockPath:t}=this,i=this.path.dirname(t);e.mkdirSync(i,{recursive:!0});try{e.mkdirSync(t)}catch(o){if(o.code!=="EEXIST")throw o;let a;try{a=e.statSync(t).mtimeMs}catch(l){if(l.code==="ENOENT")return this.acquire();throw l}if(Date.now()-a<5e3)throw new Q}let r=Date.now();if(r%1e3===0&&(r+=1),this.lockTime=r,this.touch(),this.get()%1e3===0&&(this.isMs=!1),this.set(),!this.verify())throw new Q;this.refreshTimer=setInterval(()=>this.set(),1e3)}release(){this.refreshTimer&&(clearInterval(this.refreshTimer),this.refreshTimer=null);try{this.verify()&&this.fs.rmdirSync(this.lockPath)}catch{}}set(){let e=Date.now();this.isMs||(e=Math.ceil(e/1e3)*1e3),this.lockTime=e,this.touch()}touch(){try{let e=this.lockTime/1e3;this.fs.utimesSync(this.lockPath,e,e)}catch{}}get(){try{return this.fs.statSync(this.lockPath).mtimeMs}catch{return 0}}verify(){return this.lockTime===this.get()}},Q=class extends Error{constructor(){super("Failed to acquire lock.")}};var L=new gi.Command,X="ob",{version:zi}=JSON.parse(D.default.readFileSync(P.default.join(__dirname,"package.json"),"utf-8"));L.name(X).description("Headless client for Obsidian services").version(zi);L.command("login").description("Login to Obsidian account or display login status").option("--email <email>","Email address (prompted if omitted)").option("--password <password>","Password (prompted if omitted)").option("--mfa <code>","MFA code (prompted if omitted)").action(async s=>{try{let e=J();if(e&&!s.email&&!s.password){let n=await ni(e);if(n){console.log(`Logged in as ${n.name} (${n.email})`);return}}if(e){try{await nt(e)}catch{}Ve()}let t=s.email||await he("Email: ",!0),i=s.password||await he("Password: "),r;try{r=await rt(t,i,s.mfa||"")}catch(n){if(n instanceof oe&&n.error.includes("2FA code")){if(n.error.includes("2FA code is incorrect"))throw n;let o=await he("2FA code: ");r=await rt(t,i,o)}else throw n}wt(r.token),console.log(`Logged in as ${r.name} (${r.email})`)}catch(e){console.error("Login failed:",e.message||e),process.exit(2)}});L.command("logout").description("Logout from Obsidian account").action(async()=>{try{let s=J();if(!s){console.log("No account logged in.");return}try{await nt(s)}catch{}Ve(),console.log("Logged out.")}catch(s){console.error("Logout failed:",s.message||s),process.exit(1)}});L.command("sync-list-remote").description("List available remote vaults").action(async()=>{try{let s=Re();console.log("Fetching vaults...");let e=await st(s,ft);if(e.vaults.length===0&&e.shared.length===0){console.log("No vaults found.");return}console.log(`
|
|
8
8
|
Vaults:`);let t=i=>console.log(` ${i.id} "${i.name}" (${i.region})`);for(let i of e.vaults)t(i);if(e.shared.length>0){console.log(`
|
|
9
|
-
Shared vaults:`);for(let i of e.shared)t(i)}}catch(s){console.error("Failed to list vaults:",s.message||s),process.exit(1)}});L.command("sync-list-local").description("List locally configured vaults").action(()=>{try{let s=
|
|
9
|
+
Shared vaults:`);for(let i of e.shared)t(i)}}catch(s){console.error("Failed to list vaults:",s.message||s),process.exit(1)}});L.command("sync-list-local").description("List locally configured vaults").action(()=>{try{let s=Ke();if(s.length===0){console.log("No vaults configured.");return}console.log("Configured vaults:");for(let e of s){let t=qe(e);t&&(console.log(` ${e}`),console.log(` Path: ${t.vaultPath}`),console.log(` Host: ${t.host}`))}}catch(s){console.error("Failed to list vaults:",s.message||s),process.exit(1)}});L.command("sync-create-remote").description("Create a new remote vault").requiredOption("--name <name>","Vault name").option("--encryption <standard|e2ee>","Encryption").option("--password <encryption-password>","End-to-end encryption password (prompt if omitted)").option("--region <region>","Vault region (leave empty for automatic)").action(async s=>{try{let e=Re(),t=s.name,i=s.password;!i&&s.encryption!=="standard"&&(i=await he("End-to-end encryption password (leave empty for standard encryption): "));let r=s.region||"";if(r){let c=(await si(e)).regions;if(!c.some(u=>u.value===r)){console.error(`Invalid region: "${r}". Available regions:`);for(let u of c)console.error(` ${u.value} (${u.name})`);process.exit(1)}}console.log("Creating vault...");let n,o=null;if(i){n=O(crypto.getRandomValues(new Uint8Array(16)));let l=await ht(i,n);o=await pt(l,n,ut)}let a=await oi(e,t,o,n,r,ut);console.log(`
|
|
10
10
|
Vault created successfully!`),console.log(` Vault ID: ${a.id}`),console.log(` Vault name: ${a.name}`),console.log(` Region: ${a.region}`),console.log(` Encryption: ${i?"end-to-end":"managed"}`),console.log(`
|
|
11
|
-
Run '${X} sync-setup --vault "${a.id}"' to configure sync.`)}catch(e){console.error("Failed to create vault:",e.message||e),process.exit(1)}});L.command("sync-setup").description("Setup sync from a local path to a remote vault").requiredOption("--vault <vault>","Remote vault ID or name").option("--path <local-path>","Local vault path (use current directory if omitted)").option("--password <encryption-password>","End-to-end encryption password (prompted if omitted)").option("--device-name <name>","Device name to identify this client in the sync version history").option("--config-dir <name>","Config directory name (default: .obsidian)").action(async s=>{try{let e=Re(),t=s.vault,i=P.default.resolve(s.path||"."),r=s.password,n=s.deviceName||"",o=
|
|
12
|
-
Vault configured successfully!`),
|
|
13
|
-
Warning: Your local vault already contains some notes.`),console.log("If you start syncing, notes in your local vault will be merged with notes from your remote vault."),console.log("In case of conflicts, the most recent version of the note will be preserved.")):D.default.mkdirSync(i,{recursive:!0}),
|
|
14
|
-
Run '${X} sync' to start syncing.`)}catch(e){console.error("Setup failed:",e.message||e),process.exit(1)}});L.command("sync-config").description("Change sync configuration for a vault").option("--path <local-path>","Local vault path (use current directory if omitted)").option("--conflict-strategy <strategy>","Conflict resolution strategy (merge or conflict)").option("--excluded-folders <folders>","Folders to exclude, comma-separated (empty string to clear)").option("--file-types <types>","Attachment types to sync, comma-separated: image, audio, video, pdf, unsupported (empty to clear)").option("--configs <settings>","Config categories to sync, comma-separated: app, appearance, appearance-data, hotkey, core-plugin, core-plugin-data, community-plugin, community-plugin-data (empty to clear)").option("--device-name <name>","Device name to identify this client in the sync version history").option("--config-dir <name>","Config directory name (default: .obsidian)").action(s=>{try{let e=P.default.resolve(s.path||"."),t=
|
|
15
|
-
|
|
11
|
+
Run '${X} sync-setup --vault "${a.id}"' to configure sync.`)}catch(e){console.error("Failed to create vault:",e.message||e),process.exit(1)}});L.command("sync-setup").description("Setup sync from a local path to a remote vault").requiredOption("--vault <vault>","Remote vault ID or name").option("--path <local-path>","Local vault path (use current directory if omitted)").option("--password <encryption-password>","End-to-end encryption password (prompted if omitted)").option("--device-name <name>","Device name to identify this client in the sync version history").option("--config-dir <name>","Config directory name (default: .obsidian)").action(async s=>{try{let e=Re(),t=s.vault,i=P.default.resolve(s.path||"."),r=s.password,n=s.deviceName||"",o=He(s.configDir);console.log("Fetching vault info...");let a=await st(e,ft),l=[...a.vaults,...a.shared],c=l.find(v=>v.id===t);if(!c){let v=l.filter(b=>b.name===t);if(v.length===1)c=v[0];else if(v.length>1){console.error(`Multiple vaults named "${t}". Use the vault ID instead:`);for(let b of v)console.error(` ${b.id} "${b.name}"`);process.exit(1)}}c||(console.error(`Vault "${t}" not found.`),process.exit(3));let u=c.id;c.password?r=c.password:r||(r=await he("End-to-end encryption password: ")),r||(console.error("Failed to validate password."),process.exit(2)),console.log("Setting up...");let p=await ht(r,c.salt),d=await pt(p,c.salt,c.encryption_version);try{await ai(e,u,d,c.host,c.encryption_version)}catch{console.error("Failed to validate password."),process.exit(2)}let w={vaultId:u,vaultName:c.name,vaultPath:i,host:c.host,encryptionVersion:c.encryption_version,encryptionKey:Qt(p),encryptionSalt:c.salt,conflictStrategy:"merge",deviceName:n,configDir:o};je(u),We(u,w),console.log(`
|
|
12
|
+
Vault configured successfully!`),Oe(w),D.default.existsSync(i)?D.default.readdirSync(i).filter(g=>!g.startsWith(".")).length>0&&(console.log(`
|
|
13
|
+
Warning: Your local vault already contains some notes.`),console.log("If you start syncing, notes in your local vault will be merged with notes from your remote vault."),console.log("In case of conflicts, the most recent version of the note will be preserved.")):D.default.mkdirSync(i,{recursive:!0}),di(),console.log(`
|
|
14
|
+
Run '${X} sync' to start syncing.`)}catch(e){console.error("Setup failed:",e.message||e),process.exit(1)}});L.command("sync-config").description("Change sync configuration for a vault").option("--path <local-path>","Local vault path (use current directory if omitted)").option("--conflict-strategy <strategy>","Conflict resolution strategy (merge or conflict)").option("--excluded-folders <folders>","Folders to exclude, comma-separated (empty string to clear)").option("--file-types <types>","Attachment types to sync, comma-separated: image, audio, video, pdf, unsupported (empty to clear)").option("--configs <settings>","Config categories to sync, comma-separated: app, appearance, appearance-data, hotkey, core-plugin, core-plugin-data, community-plugin, community-plugin-data (empty to clear)").option("--device-name <name>","Device name to identify this client in the sync version history").option("--mode <mode>","Sync mode: bidirectional (default), pull-only (only download, ignore local changes), or mirror-remote (only download, revert local changes)").option("--config-dir <name>","Config directory name (default: .obsidian)").action(s=>{try{let e=P.default.resolve(s.path||"."),t=z(e);t||(console.error(`No sync configuration found for ${e}`),console.error(`Run '${X} sync-setup' first.`),process.exit(3));let i=!1;s.mode!==void 0&&(s.mode!=="bidirectional"&&s.mode!=="pull-only"&&s.mode!=="mirror-remote"&&(console.error(`Invalid sync mode: "${s.mode}". Must be "bidirectional", "pull-only", or "mirror-remote".`),process.exit(1)),s.mode==="bidirectional"?delete t.syncMode:t.syncMode=s.mode,i=!0),s.conflictStrategy!==void 0&&(s.conflictStrategy!=="merge"&&s.conflictStrategy!=="conflict"&&(console.error(`Invalid conflict strategy: "${s.conflictStrategy}". Must be "merge" or "conflict".`),process.exit(1)),t.conflictStrategy=s.conflictStrategy,i=!0),s.excludedFolders!==void 0&&(s.excludedFolders===""?delete t.ignoreFolders:t.ignoreFolders=s.excludedFolders.split(",").map(r=>r.trim()),i=!0),s.fileTypes!==void 0&&(s.fileTypes===""?delete t.allowTypes:t.allowTypes=At(s.fileTypes),i=!0),s.configs!==void 0&&(s.configs===""?delete t.allowSpecialFiles:t.allowSpecialFiles=_t(s.configs),i=!0),s.deviceName!==void 0&&(t.deviceName=s.deviceName,i=!0),s.configDir!==void 0&&(t.configDir=He(s.configDir),i=!0),i?(We(t.vaultId,t),console.log("Configuration updated:")):console.log("No options provided. Current configuration:"),Oe(t)}catch(e){console.error("Config update failed:",e.message||e),process.exit(1)}});L.command("sync-status").description("Show sync status for a vault").option("--path <local-path>","Local vault path (use current directory if omitted)").action(async s=>{try{let e=P.default.resolve(s.path||"."),t=z(e);t||(console.error(`No sync configuration found for ${e}`),process.exit(3)),J()||console.log("Not logged in."),t.encryptionKey||console.log("End-to-end encryption key missing. Run setup again."),console.log("Sync Configuration:"),Oe(t)}catch(e){console.error("Status check failed:",e.message||e),process.exit(1)}});L.command("sync-unlink").description("Disconnect a vault from sync and remove stored credentials").option("--path <local-path>","Local vault path (use current directory if omitted)").action(async s=>{try{let e=P.default.resolve(s.path||"."),t=z(e);t||(console.error(`No sync configuration found for ${e}`),process.exit(3)),Pt(t.vaultId),console.log(`Sync configuration removed for ${e}`)}catch(e){console.error("Unlink failed:",e.message||e),process.exit(1)}});L.command("sync").description("Sync a vault").option("--path <local-path>","Local vault path (use current directory if omitted)").option("--continuous","Run in continuous sync mode").action(async s=>{try{let e=P.default.resolve(s.path||"."),t=z(e);t||(console.error(`No sync configuration found for ${e}`),console.error(`Run '${X} sync-setup' first.`),process.exit(3));let i=Re();(!t.encryptionKey||!t.encryptionSalt||t.encryptionVersion==null)&&(console.error("Encryption key not found. Run setup again."),process.exit(2));let r=await pi(t.encryptionVersion,Gt(t.encryptionKey),t.encryptionSalt),n=Tt(St(t.vaultId));t.deviceName||(t.deviceName=$e()),(!t.configDir||!t.configDir.startsWith("."))&&(t.configDir=".obsidian"),di();let o=new Ce(D.default,P.default,Dt(t.vaultPath,t.configDir));o.acquire();let a;try{a=new xe({config:t,token:i,encryption:r,continuous:s.continuous});let l=()=>{console.log(`
|
|
15
|
+
Received signal to shut down...`),a.stop()};process.on("SIGINT",l),process.on("SIGTERM",l),console.log("Starting sync:"),Oe(t),await a.sync()}catch{a?.stop()}finally{o.release(),n()}process.exit(0)}catch(e){e instanceof Q&&(console.error("Another sync instance is already running for this vault."),process.exit(1)),console.error("Sync failed:",e),process.exit(1)}});function Oe(s){console.log(` Vault: ${s.vaultName} (${s.vaultId})`),console.log(` Location: ${s.vaultPath}`),console.log(` Sync mode: ${s.syncMode||"bidirectional"}`),console.log(` Conflict strategy: ${s.conflictStrategy}`),console.log(` Device name: ${s.deviceName||$e()}`),s.configDir&&console.log(` Config directory: ${s.configDir}`);let{allowTypes:e,allowSpecialFiles:t,ignoreFolders:i}=s;console.log(` File types: ${(e||K).join(", ")}`),console.log(` Configs: ${t?.length?(t||[]).join(", "):"none (config syncing disabled)"}`),i&&i.length>0&&console.log(` Excluded folders: ${i.join(", ")}`)}function he(s,e){return new Promise(t=>{if(process.stdin.isTTY){process.stdout.write(s),process.stdin.setRawMode(!0),process.stdin.resume();let i="",r=()=>{process.stdout.clearLine(0),process.stdout.cursorTo(0),process.stdout.write(s+(e?i:"*".repeat(i.length)))},n=o=>{let a=o.toString();a===`
|
|
16
16
|
`||a==="\r"?(process.stdin.setRawMode(!1),process.stdin.pause(),process.stdin.removeListener("data",n),process.stdout.write(`
|
|
17
|
-
`),t(i)):a===""?(process.stdin.setRawMode(!1),process.exit(1)):a==="\x7F"||a==="\b"?(i=i.slice(0,-1),r()):(i+=a,process.stdout.write(e?a:"*".repeat(a.length)))};process.stdin.on("data",n)}else{let i="";process.stdin.setEncoding("utf-8"),process.stdin.on("data",r=>{i+=r}),process.stdin.on("end",()=>{t(i.trimEnd())}),process.stdin.resume()}})}function
|
|
17
|
+
`),t(i)):a===""?(process.stdin.setRawMode(!1),process.exit(1)):a==="\x7F"||a==="\b"?(i=i.slice(0,-1),r()):(i+=a,process.stdout.write(e?a:"*".repeat(a.length)))};process.stdin.on("data",n)}else{let i="";process.stdin.setEncoding("utf-8"),process.stdin.on("data",r=>{i+=r}),process.stdin.on("end",()=>{t(i.trimEnd())}),process.stdin.resume()}})}function di(){(process.platform==="win32"||process.platform==="darwin")&&!mt()&&console.warn("Warning: btime native module failed to load. File creation times will not be preserved.")}function Re(){let s=J();return s||(console.error(`No account logged in. Run "${X} login" first.`),process.exit(2)),s}L.parse();
|