@tensorix/metahub 0.5.6 → 0.5.7
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/dist/cli.js +13 -5
- package/dist/cli.js.map +2 -2
- package/dist/db-worker.js +1 -1
- package/dist/index.js +13 -5
- package/dist/index.js.map +2 -2
- package/dist/webui.js +108 -108
- package/package.json +1 -1
package/dist/db-worker.js
CHANGED
|
@@ -472,7 +472,7 @@ Set the \`cycles\` parameter to \`"ref"\` to resolve cyclical schemas with defs.
|
|
|
472
472
|
SELECT 1 FROM crdt_changes k
|
|
473
473
|
WHERE k.dataset = c.dataset AND k.row_id = c.row_id AND k.col = c.col AND k.hlc > c.hlc
|
|
474
474
|
)`).all();return gs(r,t)}function iE(e){let t={};for(let r of e)if(!t[r.node_id]||r.hlc>t[r.node_id])t[r.node_id]=r.hlc;return t}function sE(e){let t=e.query("SELECT node_id, MAX(hlc) AS h FROM crdt_changes GROUP BY node_id").all(),r={};for(let n of t)r[n.node_id]=n.h;return r}function aE(e,t){for(let r in t)if(!e[r]||e[r]<t[r])return!1;return!0}async function cE(e,t){let r=await ng(new TextEncoder().encode(JSON.stringify(e)));return t?nr(t,r):r}async function lE(e,t){try{let r=t?await yr(t,e):e;return JSON.parse(new TextDecoder().decode(await og(r)))}catch{return null}}function uE(e,t){let r=new Set;for(let n of e){let o=n.key.slice(t.length),s=o.indexOf("/");if(s>0)r.add(o.slice(0,s))}return[...r]}async function dE(e,t){let r=Jv(t);return uE(await e.list(r,void 0,"/"),r)}async function za(e,t,r){if(!t.encrypt)return null;let n=go(t.prefix),o=Qv(n),s=async(m)=>rr(await Ia(JSON.parse(new TextDecoder().decode(m)),r)),a=await e.get(o);if(a)return s(a);let c=po(),p=await Vh(c,r);try{return await e.put(o,new TextEncoder().encode(JSON.stringify(p)),{contentType:"application/json",ifNoneMatch:!0}),rr(c)}catch(m){if(fn(m)==="conflict"){let x=await e.get(o);if(x)return s(x)}throw m}}async function Yh(e,t,r,n=Zv){let o=Date.now();gn(e,o);let s=Ri(r),a=go(r.prefix),c=We(e),p=(await t.list(Na(a,c))).map((_e)=>_e.key).filter((_e)=>_e.endsWith(".seg")).sort(),m=p.length?p[p.length-1]:null,x=oE(e,o);if(x.length===0)return null;let A=x.reduce((_e,le)=>le.hlc>_e?le.hlc:_e,""),F=await eE(x.map((_e)=>JSON.stringify(_e)).sort().join(`
|
|
475
|
-
`)),X=`${ho(a)}${A}${Pa}${F}.snap`;await t.put(X,await ig(x,s),{contentType:"application/octet-stream"}),await t.put(qa(X),await cE({frontier:iE(x),ownNode:c,ownSegHigh:m},s),{contentType:"application/octet-stream"});for(let _e of await t.list(ho(a))){if(!_e.key.endsWith(".snap"))continue;if(_e.key.slice(ho(a).length).split(Pa)[0]<A)await t.del(_e.key),await t.del(qa(_e.key))}let he=p.slice(0,Math.max(0,p.length-n));for(let _e of he)await t.del(_e);return{key:X,changes:x.length}}function lg(e){return parseInt(e.slice(0,15),10)}function fE(e){return Date.now()-lg(e.hlc)}function pE(e,t){let r=ho(t),n=null;for(let o of e){let s=o.slice(r.length).split(Pa)[0];if(n===null||s>n)n=s}return n}async function ug(e,t,r,n,o={}){gn(e);let s=We(e),a=Ri(n),c=go(n.prefix),p=tE(e,t),m=Er(e,p,{onlyNode:s}),x=0,A=!1;if(m.changes.length===0)Qh(e,t,m.cursor);else{let Oe=o.minPushChanges??1,Be=o.maxPushAgeMs??0;if(o.forcePush||m.changes.length>=Oe||fE(m.changes[0])>=Be){let He=Xv(c,s,m.cursor);await r.put(Xh(c,s),new TextEncoder().encode(He),{contentType:"text/plain"}),await r.put(He,await ig(m.changes,a),{contentType:"application/octet-stream"}),Qh(e,t,m.cursor),x=m.changes.length}else A=!0}let F=[],X=0,he={};if(o.pull??!0){F=(await r.list(ho(c))).map((Oe)=>Oe.key).filter((Oe)=>Oe.endsWith(".snap")),X+=await hE(e,t,F,r,a,he);for(let Oe of await dE(r,c)){if(Oe===s)continue;let Be=Ma(e,t,Oe),Me=await r.get(Xh(c,Oe));if(Me){let Ze=new TextDecoder().decode(Me);if(Be&&Ze<=Be)continue}let He=(await r.list(Na(c,Oe),Be??void 0)).filter((Ze)=>Ze.key.endsWith(".seg"));for(let Ze of He){let zt=await r.get(Ze.key);if(!zt)continue;let Rt=await sg(zt,a);X+=dg(he,mn(e,Rt)),Fa(e,t,Oe,Ze.key)}}}let _e=!1;if(o.publish){let Oe=e.query("SELECT COUNT(*) AS n FROM crdt_changes").get().n;if(Oe>0){let Be=pE(F,c),Me=o.snapshotMinDelta??Kv,He=o.snapshotDeltaRatio??Gv,Ze=o.snapshotMaxIntervalMs??Vv,zt=Be===null?Oe:e.query("SELECT COUNT(*) AS n FROM crdt_changes WHERE hlc > ?").get(Be).n;if((Be===null||zt>=Math.max(Me,Oe*He)||zt>0&&Date.now()-lg(Be)>=Ze)&&await Wh(r,c,s,o.priority??0))await Yh(e,r,n,o.snapshotRetainSegments),_e=!0}}if(o.publish&&!_e&&x>0){let Oe=o.snapshotEverySegments??200;if((await r.list(Na(c,s))).filter((Me)=>Me.key.endsWith(".seg")).length>=Oe)await Yh(e,r,n,o.snapshotRetainSegments)}let le=Oa(t,he);return{pushed:x,pulled:X,pendingPush:A,...le.length?{warnings:le}:{}}}function dg(e,t){for(let[r,n]of Object.entries(t.skewed))e[r]=(e[r]??0)+n;return t.received}async function hE(e,t,r,n,o,s={}){if(r.length===0)return 0;let a=rE(e,t),c=sE(e),p=0;for(let x of[...r].sort().reverse()){if(a.has(x))continue;let A=await n.get(qa(x)),F=A?await lE(A,o):null;if(F&&aE(c,F.frontier)){a.add(x);continue}let X=await n.get(x);if(!X)continue;let he=await sg(X,o);p+=dg(s,mn(e,he)),a.add(x);for(let _e of he)if(!c[_e.node_id]||_e.hlc>c[_e.node_id])c[_e.node_id]=_e.hlc;if(F?.ownSegHigh){let _e=Ma(e,t,F.ownNode);if(!_e||_e<F.ownSegHigh)Fa(e,t,F.ownNode,F.ownSegHigh)}}let m=new Set(r);return nE(e,t,[...a].filter((x)=>m.has(x))),p}var Ca=null,rg="__snapshot__",Wv=16,Pa="~",Zv=40,Kv=200,Gv=0.5,Vv=1800000,Jv=(e)=>`${e}/oplog/`,Na=(e,t)=>`${e}/oplog/${t}/`,Xh=(e,t)=>`${e}/oplog/${t}/HEAD`,Xv=(e,t,r)=>`${e}/oplog/${t}/${String(r).padStart(Wv,"0")}.seg`,ho=(e)=>`${e}/snapshot/`,Qv=(e)=>`${e}/keys/main.json`,ag=(e,t)=>`${e}/blobs/${t}`,qa=(e)=>`${e}.vc`;var Xr=Ae(()=>{Kt();lt();Zh();Xe();Ti();Jr()});var gE=32,mE=3,gD;var fg=Ae(()=>{Xe();gD=(gE+mE)*8/5});var pg=Ae(()=>{Xe()});function _E(e){let t=e.query("SELECT value FROM meta WHERE key = ?").get("site_publish_rollbacks");if(!t?.value)return[];try{let r=JSON.parse(t.value);if(!Array.isArray(r))return[];return r.filter((n)=>!!n&&typeof n.siteId==="string"&&typeof n.peerUrl==="string"&&typeof n.targetUrl==="string"&&Number.isFinite(n.requiredSeq)&&Number.isFinite(n.createdAt)&&typeof n.lastError==="string")}catch{return[]}}function yE(e,t){if(t.length===0){e.query("DELETE FROM meta WHERE key = ?").run("site_publish_rollbacks");return}e.query("INSERT INTO meta (key,value) VALUES (?,?) ON CONFLICT(key) DO UPDATE SET value=excluded.value").run("site_publish_rollbacks",JSON.stringify(t))}function hg(e,t){let r=e.query("SELECT push_cursor,last_status FROM peers WHERE url = ?").get(t);if(!r||r.last_status!=="ok")return 0;let n=_E(e),o=n.filter((s)=>s.peerUrl!==t||s.requiredSeq>r.push_cursor);return yE(e,o),n.length-o.length}var mg;var gg=Ae(()=>{mg={name:"@tensorix/metahub",version:"0.5.6",description:"Metahub core library and CLI",license:"AGPL-3.0-only",type:"module",main:"./dist/index.js",module:"./dist/index.js",types:"./dist/index.d.ts",exports:{".":{types:"./dist/index.d.ts",import:"./dist/index.js"},"./package.json":"./package.json"},bin:{metahub:"./dist/cli.js",mh:"./dist/cli.js"},files:["dist","README.md","README.zh-CN.md","LICENSE"],scripts:{dev:"bun --hot src/cli/index.ts",build:"bun run scripts/build.ts","build:shell":"bun run scripts/build-shell.ts","build:share-viewer":"bun run scripts/build-share-viewer.ts","build:binaries":"bun run scripts/compile-binaries.ts","build:binaries:host":"HOST_ONLY=1 bun run scripts/compile-binaries.ts",prepublishOnly:"bun run build",test:"bun test",release:"bun run scripts/tag-release.ts"},dependencies:{"@clack/prompts":"^1.5.0","@codemirror/commands":"6.10.4","@codemirror/state":"6.7.0","@codemirror/view":"6.43.4","@joplin/turndown-plugin-gfm":"^1.0.67","@sqlite.org/sqlite-wasm":"^3.53.0-build1",aws4fetch:"^1.0.20",citty:"^0.1.6","highlight.js":"^11.11.1",jsqr:"^1.4.0",preact:"^10.29.2","qrcode-generator":"^2.0.4",turndown:"^7.2.4",zod:"^4.4.3"},devDependencies:{"@happy-dom/global-registrator":"^20.10.2","@prettier/plugin-php":"^0.25.0","@types/bun":"latest","@types/turndown":"^5.0.6","@wasm-fmt/clang-format":"^22.1.8","@wasm-fmt/gofmt":"^0.7.3","@wasm-fmt/lua_fmt":"^0.3.3","@wasm-fmt/ruff_fmt":"^0.15.20","@wasm-fmt/taplo_fmt":"^0.2.5","mvdan-sh":"^0.10.1",prettier:"^3.6","sql-formatter":"^15",typescript:"^5"}}});function Ua(){return{v:1,tables:[]}}function vE(e){return typeof e==="string"&&Ba.includes(e)}function _g(e){let t=new Map;for(let n of e){let o=t.get(n.db)??new Set;for(let s of n.ops)o.add(s);t.set(n.db,o)}let r=[];for(let[n,o]of t){let s=Ba.filter((a)=>o.has(a));if(s.length)r.push({db:n,ops:s})}return r.sort((n,o)=>n.db<o.db?-1:n.db>o.db?1:0),{v:1,tables:r}}function br(e){if(!e)return Ua();let t;try{t=JSON.parse(e)}catch{return Ua()}try{return mo(t)}catch{return Ua()}}function mo(e){if(typeof e!=="object"||e===null||Array.isArray(e))throw new H("invalid_input","grants must be an object {v:1, tables:[...]}");let t=e;if(t.v!==1)throw new H("invalid_input","grants version must be 1");if(!Array.isArray(t.tables))throw new H("invalid_input","grants.tables must be an array");let r=[];for(let n of t.tables){if(typeof n!=="object"||n===null)throw new H("invalid_input","each grant table must be an object {db, ops}");let{db:o,ops:s}=n;if(typeof o!=="string"||!o)throw new H("invalid_input","grant table `db` must be a database id");if(!Array.isArray(s)||!s.every(vE))throw new H("invalid_input",`grant ops must be a subset of ${Ba.join("|")} (delete is never grantable)`);r.push({db:o,ops:s})}return _g(r)}function Ai(e){return JSON.stringify(_g(e.tables))}function yg(e){return e.tables.some((t)=>t.ops.some((r)=>r!=="read"))}var Ba;var Qr=Ae(()=>{Xe();zr();kr();Ur();lt();Ba=["read","create","update"]});function ja(e,t){let r=t.permission??"view";if(!EE.has(t.kind))throw new H("invalid_input",`unknown share kind: ${t.kind}`);if(r!=="view"&&r!=="edit")throw new H("invalid_input",`unknown share permission: ${r}`);let n=t.requestId?.trim()||null;if(n&&!/^[A-Za-z0-9_-]{16,80}$/.test(n))throw new H("invalid_input","share request id is invalid");if(n){let p=wg(e,n);if(p){if(p.kind!==t.kind||p.target_id!==t.target_id)throw new H("conflict","share request id was already used for another target");return p}}let o=null;if(t.grants!=null){let p;try{p=JSON.parse(t.grants)}catch{throw new H("invalid_input","grants must be a JSON GrantSet")}o=Ai(mo(p))}let s=Et(12);while(lr(e,s))s=Et(12);let c=r==="edit"||yg(br(o))?"g"+Et(8):null;return e.query(`INSERT INTO shares (${_o}) VALUES (?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?)`).run(s,t.kind,t.target_id,r,"server",t.pwSalt??null,t.pwHash??null,t.expiresAt??null,c,t.servedBase??null,null,null,null,null,Date.now(),n,o),lr(e,s)}function wg(e,t){return e.query(`SELECT ${_o} FROM shares WHERE request_id = ?`).get(t)??null}function lr(e,t){return e.query(`SELECT ${_o} FROM shares WHERE slug = ?`).get(t)??null}function Ha(e){return e.query(`SELECT ${_o} FROM shares ORDER BY created_at DESC`).all()}function Wa(e,t){return e.query(`SELECT ${_o} FROM shares WHERE target_id = ? ORDER BY created_at DESC`).all(t)}function or(e,t){return e.query("DELETE FROM shares WHERE slug = ?").run(t).changes>0}function bg(e){let t=new Uint8Array(e.byteLength);return t.set(e),t.buffer}async function TE(e,t){let r=await crypto.subtle.importKey("raw",bg(new TextEncoder().encode(e)),"PBKDF2",!1,["deriveBits"]),n=await crypto.subtle.deriveBits({name:"PBKDF2",salt:bg(t),iterations:SE,hash:"SHA-256"},r,xE);return new Uint8Array(n)}async function Za(e){let t=crypto.getRandomValues(new Uint8Array(kE)),r=await TE(e,t);return{salt:rr(t),hash:rr(r)}}var EE,_o="slug, kind, target_id, permission, transport, pw_salt, pw_hash, expires_at, guest_node_id, served_base, s3_peer_url, s3_object_prefix, s3_presign_exp, s3_key_b64, created_at, request_id, grants",SE=600000,kE=16,xE=256;var Rn=Ae(()=>{Xe();St();Jr();Qr();EE=new Set(["doc","database","site"])});function Ka(e){let t=RE;for(let r=0;r<e.length;r++)t^=BigInt(e.charCodeAt(r)),t=t*AE&DE;return t.toString(16).padStart(16,"0")}var RE=0xcbf29ce484222325n,AE=0x100000001b3n,DE=0xffffffffffffffffn;function Ga(e){let t=[],r=[];if(e.grantedDbIds.length>0){let n=e.grantedDbIds.map(()=>"?").join(", ");t.push(`SELECT 'databases' AS dataset, id AS row_id FROM databases WHERE id IN (${n})`),r.push(...e.grantedDbIds),t.push(`SELECT 'properties', id FROM properties WHERE database_id IN (${n})`),r.push(...e.grantedDbIds),t.push(`SELECT 'records', id FROM records WHERE database_id IN (${n})`),r.push(...e.grantedDbIds)}if(e.siteId)t.push("SELECT 'sites', id FROM sites WHERE id = ?"),r.push(e.siteId),t.push("SELECT 'site_files', id FROM site_files WHERE site_id = ?"),r.push(e.siteId);if(t.length===0)t.push("SELECT '' AS dataset, '' AS row_id WHERE 0");return{sql:t.join(" UNION ALL "),params:r}}function Sg(e,t){let r=Ga(t);return e.query(`SELECT dataset, row_id FROM (${r.sql}) ORDER BY dataset, row_id`).all(...r.params)}function Va(e,t,r){switch(r.dataset){case"databases":return t.grantedDbIds.includes(r.row_id)&&e.query("SELECT 1 FROM databases WHERE id = ?").get(r.row_id)!=null;case"properties":case"records":{let n=e.query(`SELECT database_id FROM ${r.dataset} WHERE id = ?`).get(r.row_id);return n?.database_id!=null&&t.grantedDbIds.includes(n.database_id)}case"sites":return t.siteId===r.row_id&&e.query("SELECT 1 FROM sites WHERE id = ?").get(r.row_id)!=null;case"site_files":{if(!t.siteId)return!1;return e.query("SELECT site_id FROM site_files WHERE id = ?").get(r.row_id)?.site_id===t.siteId}default:return!1}}function kg(e,t,r){let n=Ga(r),o=e.query(`WITH m(dataset, row_id) AS (${n.sql})
|
|
475
|
+
`)),X=`${ho(a)}${A}${Pa}${F}.snap`;await t.put(X,await ig(x,s),{contentType:"application/octet-stream"}),await t.put(qa(X),await cE({frontier:iE(x),ownNode:c,ownSegHigh:m},s),{contentType:"application/octet-stream"});for(let _e of await t.list(ho(a))){if(!_e.key.endsWith(".snap"))continue;if(_e.key.slice(ho(a).length).split(Pa)[0]<A)await t.del(_e.key),await t.del(qa(_e.key))}let he=p.slice(0,Math.max(0,p.length-n));for(let _e of he)await t.del(_e);return{key:X,changes:x.length}}function lg(e){return parseInt(e.slice(0,15),10)}function fE(e){return Date.now()-lg(e.hlc)}function pE(e,t){let r=ho(t),n=null;for(let o of e){let s=o.slice(r.length).split(Pa)[0];if(n===null||s>n)n=s}return n}async function ug(e,t,r,n,o={}){gn(e);let s=We(e),a=Ri(n),c=go(n.prefix),p=tE(e,t),m=Er(e,p,{onlyNode:s}),x=0,A=!1;if(m.changes.length===0)Qh(e,t,m.cursor);else{let Oe=o.minPushChanges??1,Be=o.maxPushAgeMs??0;if(o.forcePush||m.changes.length>=Oe||fE(m.changes[0])>=Be){let He=Xv(c,s,m.cursor);await r.put(Xh(c,s),new TextEncoder().encode(He),{contentType:"text/plain"}),await r.put(He,await ig(m.changes,a),{contentType:"application/octet-stream"}),Qh(e,t,m.cursor),x=m.changes.length}else A=!0}let F=[],X=0,he={};if(o.pull??!0){F=(await r.list(ho(c))).map((Oe)=>Oe.key).filter((Oe)=>Oe.endsWith(".snap")),X+=await hE(e,t,F,r,a,he);for(let Oe of await dE(r,c)){if(Oe===s)continue;let Be=Ma(e,t,Oe),Me=await r.get(Xh(c,Oe));if(Me){let Ze=new TextDecoder().decode(Me);if(Be&&Ze<=Be)continue}let He=(await r.list(Na(c,Oe),Be??void 0)).filter((Ze)=>Ze.key.endsWith(".seg"));for(let Ze of He){let zt=await r.get(Ze.key);if(!zt)continue;let Rt=await sg(zt,a);X+=dg(he,mn(e,Rt)),Fa(e,t,Oe,Ze.key)}}}let _e=!1;if(o.publish){let Oe=e.query("SELECT COUNT(*) AS n FROM crdt_changes").get().n;if(Oe>0){let Be=pE(F,c),Me=o.snapshotMinDelta??Kv,He=o.snapshotDeltaRatio??Gv,Ze=o.snapshotMaxIntervalMs??Vv,zt=Be===null?Oe:e.query("SELECT COUNT(*) AS n FROM crdt_changes WHERE hlc > ?").get(Be).n;if((Be===null||zt>=Math.max(Me,Oe*He)||zt>0&&Date.now()-lg(Be)>=Ze)&&await Wh(r,c,s,o.priority??0))await Yh(e,r,n,o.snapshotRetainSegments),_e=!0}}if(o.publish&&!_e&&x>0){let Oe=o.snapshotEverySegments??200;if((await r.list(Na(c,s))).filter((Me)=>Me.key.endsWith(".seg")).length>=Oe)await Yh(e,r,n,o.snapshotRetainSegments)}let le=Oa(t,he);return{pushed:x,pulled:X,pendingPush:A,...le.length?{warnings:le}:{}}}function dg(e,t){for(let[r,n]of Object.entries(t.skewed))e[r]=(e[r]??0)+n;return t.received}async function hE(e,t,r,n,o,s={}){if(r.length===0)return 0;let a=rE(e,t),c=sE(e),p=0;for(let x of[...r].sort().reverse()){if(a.has(x))continue;let A=await n.get(qa(x)),F=A?await lE(A,o):null;if(F&&aE(c,F.frontier)){a.add(x);continue}let X=await n.get(x);if(!X)continue;let he=await sg(X,o);p+=dg(s,mn(e,he)),a.add(x);for(let _e of he)if(!c[_e.node_id]||_e.hlc>c[_e.node_id])c[_e.node_id]=_e.hlc;if(F?.ownSegHigh){let _e=Ma(e,t,F.ownNode);if(!_e||_e<F.ownSegHigh)Fa(e,t,F.ownNode,F.ownSegHigh)}}let m=new Set(r);return nE(e,t,[...a].filter((x)=>m.has(x))),p}var Ca=null,rg="__snapshot__",Wv=16,Pa="~",Zv=40,Kv=200,Gv=0.5,Vv=1800000,Jv=(e)=>`${e}/oplog/`,Na=(e,t)=>`${e}/oplog/${t}/`,Xh=(e,t)=>`${e}/oplog/${t}/HEAD`,Xv=(e,t,r)=>`${e}/oplog/${t}/${String(r).padStart(Wv,"0")}.seg`,ho=(e)=>`${e}/snapshot/`,Qv=(e)=>`${e}/keys/main.json`,ag=(e,t)=>`${e}/blobs/${t}`,qa=(e)=>`${e}.vc`;var Xr=Ae(()=>{Kt();lt();Zh();Xe();Ti();Jr()});var gE=32,mE=3,gD;var fg=Ae(()=>{Xe();gD=(gE+mE)*8/5});var pg=Ae(()=>{Xe()});function _E(e){let t=e.query("SELECT value FROM meta WHERE key = ?").get("site_publish_rollbacks");if(!t?.value)return[];try{let r=JSON.parse(t.value);if(!Array.isArray(r))return[];return r.filter((n)=>!!n&&typeof n.siteId==="string"&&typeof n.peerUrl==="string"&&typeof n.targetUrl==="string"&&Number.isFinite(n.requiredSeq)&&Number.isFinite(n.createdAt)&&typeof n.lastError==="string")}catch{return[]}}function yE(e,t){if(t.length===0){e.query("DELETE FROM meta WHERE key = ?").run("site_publish_rollbacks");return}e.query("INSERT INTO meta (key,value) VALUES (?,?) ON CONFLICT(key) DO UPDATE SET value=excluded.value").run("site_publish_rollbacks",JSON.stringify(t))}function hg(e,t){let r=e.query("SELECT push_cursor,last_status FROM peers WHERE url = ?").get(t);if(!r||r.last_status!=="ok")return 0;let n=_E(e),o=n.filter((s)=>s.peerUrl!==t||s.requiredSeq>r.push_cursor);return yE(e,o),n.length-o.length}var mg;var gg=Ae(()=>{mg={name:"@tensorix/metahub",version:"0.5.7",description:"Metahub core library and CLI",license:"AGPL-3.0-only",type:"module",main:"./dist/index.js",module:"./dist/index.js",types:"./dist/index.d.ts",exports:{".":{types:"./dist/index.d.ts",import:"./dist/index.js"},"./package.json":"./package.json"},bin:{metahub:"./dist/cli.js",mh:"./dist/cli.js"},files:["dist","README.md","README.zh-CN.md","LICENSE"],scripts:{dev:"bun --hot src/cli/index.ts",build:"bun run scripts/build.ts","build:shell":"bun run scripts/build-shell.ts","build:share-viewer":"bun run scripts/build-share-viewer.ts","build:binaries":"bun run scripts/compile-binaries.ts","build:binaries:host":"HOST_ONLY=1 bun run scripts/compile-binaries.ts",prepublishOnly:"bun run build",test:"bun test",release:"bun run scripts/tag-release.ts"},dependencies:{"@clack/prompts":"^1.5.0","@codemirror/commands":"6.10.4","@codemirror/state":"6.7.0","@codemirror/view":"6.43.4","@joplin/turndown-plugin-gfm":"^1.0.67","@sqlite.org/sqlite-wasm":"^3.53.0-build1",aws4fetch:"^1.0.20",citty:"^0.1.6","highlight.js":"^11.11.1",jsqr:"^1.4.0",preact:"^10.29.2","qrcode-generator":"^2.0.4",turndown:"^7.2.4",zod:"^4.4.3"},devDependencies:{"@happy-dom/global-registrator":"^20.10.2","@prettier/plugin-php":"^0.25.0","@types/bun":"latest","@types/turndown":"^5.0.6","@wasm-fmt/clang-format":"^22.1.8","@wasm-fmt/gofmt":"^0.7.3","@wasm-fmt/lua_fmt":"^0.3.3","@wasm-fmt/ruff_fmt":"^0.15.20","@wasm-fmt/taplo_fmt":"^0.2.5","mvdan-sh":"^0.10.1",prettier:"^3.6","sql-formatter":"^15",typescript:"^5"}}});function Ua(){return{v:1,tables:[]}}function vE(e){return typeof e==="string"&&Ba.includes(e)}function _g(e){let t=new Map;for(let n of e){let o=t.get(n.db)??new Set;for(let s of n.ops)o.add(s);t.set(n.db,o)}let r=[];for(let[n,o]of t){let s=Ba.filter((a)=>o.has(a));if(s.length)r.push({db:n,ops:s})}return r.sort((n,o)=>n.db<o.db?-1:n.db>o.db?1:0),{v:1,tables:r}}function br(e){if(!e)return Ua();let t;try{t=JSON.parse(e)}catch{return Ua()}try{return mo(t)}catch{return Ua()}}function mo(e){if(typeof e!=="object"||e===null||Array.isArray(e))throw new H("invalid_input","grants must be an object {v:1, tables:[...]}");let t=e;if(t.v!==1)throw new H("invalid_input","grants version must be 1");if(!Array.isArray(t.tables))throw new H("invalid_input","grants.tables must be an array");let r=[];for(let n of t.tables){if(typeof n!=="object"||n===null)throw new H("invalid_input","each grant table must be an object {db, ops}");let{db:o,ops:s}=n;if(typeof o!=="string"||!o)throw new H("invalid_input","grant table `db` must be a database id");if(!Array.isArray(s)||!s.every(vE))throw new H("invalid_input",`grant ops must be a subset of ${Ba.join("|")} (delete is never grantable)`);r.push({db:o,ops:s})}return _g(r)}function Ai(e){return JSON.stringify(_g(e.tables))}function yg(e){return e.tables.some((t)=>t.ops.some((r)=>r!=="read"))}var Ba;var Qr=Ae(()=>{Xe();zr();kr();Ur();lt();Ba=["read","create","update"]});function ja(e,t){let r=t.permission??"view";if(!EE.has(t.kind))throw new H("invalid_input",`unknown share kind: ${t.kind}`);if(r!=="view"&&r!=="edit")throw new H("invalid_input",`unknown share permission: ${r}`);let n=t.requestId?.trim()||null;if(n&&!/^[A-Za-z0-9_-]{16,80}$/.test(n))throw new H("invalid_input","share request id is invalid");if(n){let p=wg(e,n);if(p){if(p.kind!==t.kind||p.target_id!==t.target_id)throw new H("conflict","share request id was already used for another target");return p}}let o=null;if(t.grants!=null){let p;try{p=JSON.parse(t.grants)}catch{throw new H("invalid_input","grants must be a JSON GrantSet")}o=Ai(mo(p))}let s=Et(12);while(lr(e,s))s=Et(12);let c=r==="edit"||yg(br(o))?"g"+Et(8):null;return e.query(`INSERT INTO shares (${_o}) VALUES (?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?)`).run(s,t.kind,t.target_id,r,"server",t.pwSalt??null,t.pwHash??null,t.expiresAt??null,c,t.servedBase??null,null,null,null,null,Date.now(),n,o),lr(e,s)}function wg(e,t){return e.query(`SELECT ${_o} FROM shares WHERE request_id = ?`).get(t)??null}function lr(e,t){return e.query(`SELECT ${_o} FROM shares WHERE slug = ?`).get(t)??null}function Ha(e){return e.query(`SELECT ${_o} FROM shares ORDER BY created_at DESC`).all()}function Wa(e,t){return e.query(`SELECT ${_o} FROM shares WHERE target_id = ? ORDER BY created_at DESC`).all(t)}function or(e,t){return e.query("DELETE FROM shares WHERE slug = ?").run(t).changes>0}function bg(e){let t=new Uint8Array(e.byteLength);return t.set(e),t.buffer}async function TE(e,t){let r=await crypto.subtle.importKey("raw",bg(new TextEncoder().encode(e)),"PBKDF2",!1,["deriveBits"]),n=await crypto.subtle.deriveBits({name:"PBKDF2",salt:bg(t),iterations:SE,hash:"SHA-256"},r,xE);return new Uint8Array(n)}async function Za(e){let t=crypto.getRandomValues(new Uint8Array(kE)),r=await TE(e,t);return{salt:rr(t),hash:rr(r)}}var EE,_o="slug, kind, target_id, permission, transport, pw_salt, pw_hash, expires_at, guest_node_id, served_base, s3_peer_url, s3_object_prefix, s3_presign_exp, s3_key_b64, created_at, request_id, grants",SE=600000,kE=16,xE=256;var Rn=Ae(()=>{Xe();St();Jr();Qr();EE=new Set(["doc","database","site"])});function Ka(e){let t=RE;for(let r=0;r<e.length;r++)t^=BigInt(e.charCodeAt(r)),t=t*AE&DE;return t.toString(16).padStart(16,"0")}var RE=0xcbf29ce484222325n,AE=0x100000001b3n,DE=0xffffffffffffffffn;function Ga(e){let t=[],r=[];if(e.grantedDbIds.length>0){let n=e.grantedDbIds.map(()=>"?").join(", ");t.push(`SELECT 'databases' AS dataset, id AS row_id FROM databases WHERE id IN (${n})`),r.push(...e.grantedDbIds),t.push(`SELECT 'properties', id FROM properties WHERE database_id IN (${n})`),r.push(...e.grantedDbIds),t.push(`SELECT 'records', id FROM records WHERE database_id IN (${n})`),r.push(...e.grantedDbIds)}if(e.siteId)t.push("SELECT 'sites', id FROM sites WHERE id = ?"),r.push(e.siteId),t.push("SELECT 'site_files', id FROM site_files WHERE site_id = ?"),r.push(e.siteId);if(t.length===0)t.push("SELECT '' AS dataset, '' AS row_id WHERE 0");return{sql:t.join(" UNION ALL "),params:r}}function Sg(e,t){let r=Ga(t);return e.query(`SELECT dataset, row_id FROM (${r.sql}) ORDER BY dataset, row_id`).all(...r.params)}function Va(e,t,r){switch(r.dataset){case"databases":return t.grantedDbIds.includes(r.row_id)&&e.query("SELECT 1 FROM databases WHERE id = ?").get(r.row_id)!=null;case"properties":case"records":{let n=e.query(`SELECT database_id FROM ${r.dataset} WHERE id = ?`).get(r.row_id);return n?.database_id!=null&&t.grantedDbIds.includes(n.database_id)}case"sites":return t.siteId===r.row_id&&e.query("SELECT 1 FROM sites WHERE id = ?").get(r.row_id)!=null;case"site_files":{if(!t.siteId)return!1;return e.query("SELECT site_id FROM site_files WHERE id = ?").get(r.row_id)?.site_id===t.siteId}default:return!1}}function kg(e,t,r){let n=Ga(r),o=e.query(`WITH m(dataset, row_id) AS (${n.sql})
|
|
476
476
|
SELECT dataset, row_id FROM m
|
|
477
477
|
EXCEPT SELECT dataset, row_id FROM room_rows WHERE peer_key = ?`).all(...n.params,t),s=e.query(`WITH m(dataset, row_id) AS (${n.sql})
|
|
478
478
|
SELECT dataset, row_id FROM room_rows WHERE peer_key = ?
|
package/dist/index.js
CHANGED
|
@@ -9389,7 +9389,7 @@ var package_default;
|
|
|
9389
9389
|
var init_package = __esm(() => {
|
|
9390
9390
|
package_default = {
|
|
9391
9391
|
name: "@tensorix/metahub",
|
|
9392
|
-
version: "0.5.
|
|
9392
|
+
version: "0.5.7",
|
|
9393
9393
|
description: "Metahub core library and CLI",
|
|
9394
9394
|
license: "AGPL-3.0-only",
|
|
9395
9395
|
type: "module",
|
|
@@ -18702,14 +18702,22 @@ var styles_default = ` :root {
|
|
|
18702
18702
|
.tmpl .tt { font-weight:600; font-size:var(--fs-ui); } .tmpl .td { font-size:var(--fs-xs); color:var(--muted); margin-top:2px; }
|
|
18703
18703
|
|
|
18704
18704
|
/* toast */
|
|
18705
|
-
.toasts { position:fixed; bottom:20px; left:20px; z-index:110; display:flex; flex-direction:column; gap:8px; }
|
|
18706
|
-
.toast { background:var(--fg); color:var(--bg); padding:10px 14px; border-radius:9px; font-size:13px; box-shadow:var(--shadow-lg);
|
|
18705
|
+
.toasts { position:fixed; bottom:20px; left:20px; max-width:calc(100vw - 40px); z-index:110; display:flex; flex-direction:column; gap:8px; }
|
|
18706
|
+
.toast { position:relative; box-sizing:border-box; touch-action:pan-y; user-select:none; transform:translateX(var(--toast-offset, 0px)); transition:transform .18s ease-out, opacity .16s ease; background:var(--fg); color:var(--bg); padding:10px 14px; border-radius:9px; font-size:13px; box-shadow:var(--shadow-lg);
|
|
18707
18707
|
display:flex; align-items:center; gap:8px; animation:slidein .2s ease; }
|
|
18708
18708
|
@keyframes slidein { from { opacity:0; transform:translateX(-12px); } }
|
|
18709
18709
|
.toast.error { background:var(--danger); color:var(--danger-fg); }
|
|
18710
18710
|
.toast.leaving { animation:toast-out .16s ease-in forwards; pointer-events:none; }
|
|
18711
18711
|
@keyframes toast-out { to { opacity:0; transform:translateX(-8px); } }
|
|
18712
|
-
.toast-msg { min-width:0; }
|
|
18712
|
+
.toast-msg { min-width:0; overflow-wrap:anywhere; }
|
|
18713
|
+
.toast > .ico, .toast-act { flex-shrink:0; }
|
|
18714
|
+
.toast.dragging { animation:none; transition:none; cursor:grabbing; }
|
|
18715
|
+
.toast.leaving.swipe-out { animation:none; transition:transform .16s ease-in, opacity .16s ease-in; }
|
|
18716
|
+
.toast-act:focus-visible { outline:2px solid currentColor; outline-offset:2px; }
|
|
18717
|
+
@media (prefers-reduced-motion:reduce) {
|
|
18718
|
+
.toast, .toast.dragging, .toast.leaving, .toast.leaving.swipe-out { animation:none; transition:none; transform:none; }
|
|
18719
|
+
.toast.leaving { opacity:0; }
|
|
18720
|
+
}
|
|
18713
18721
|
.toast-act { margin-left:4px; padding:3px 9px; border-radius:6px; font-weight:600; color:inherit; background:color-mix(in srgb, var(--bg) 16%, transparent); white-space:nowrap; }
|
|
18714
18722
|
.toast-act:hover { background:color-mix(in srgb, var(--bg) 28%, transparent); }
|
|
18715
18723
|
|
|
@@ -25344,4 +25352,4 @@ export {
|
|
|
25344
25352
|
writeTx
|
|
25345
25353
|
};
|
|
25346
25354
|
|
|
25347
|
-
//# debugId=
|
|
25355
|
+
//# debugId=ACE65D6746A1B19864756E2164756E21
|