kiwime 0.1.0__tar.gz

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.
@@ -0,0 +1,78 @@
1
+ # OS
2
+ .DS_Store
3
+ Thumbs.db
4
+
5
+ # Editors
6
+ .vscode/*
7
+ !.vscode/settings.json
8
+ .idea/
9
+ *.swp
10
+ *.swo
11
+
12
+ # Rust
13
+ target/
14
+ Cargo.lock.bak
15
+
16
+ # Node
17
+ node_modules/
18
+ dist/
19
+ .pnpm-store/
20
+ *.log
21
+
22
+ # Python
23
+ __pycache__/
24
+ *.py[cod]
25
+ *.egg-info/
26
+ .venv/
27
+ .pytest_cache/
28
+ .mypy_cache/
29
+ .ruff_cache/
30
+ .coverage
31
+ htmlcov/
32
+
33
+ # Tauri
34
+ apps/desktop/src-tauri/target/
35
+
36
+ # Frozen Python sidecars (build artifacts, see ADR 0006)
37
+ apps/desktop/src-tauri/binaries/
38
+ target/pyinstaller/
39
+
40
+ # uv
41
+ .python-version
42
+
43
+ # Frontend build copied into the host package by the publish workflow
44
+ apps/host/src/kiwime_host/_ui/
45
+
46
+ # Local data
47
+ *.sqlite
48
+ *.sqlite-journal
49
+ *.db
50
+ data/
51
+ blobs/
52
+
53
+ # Secrets
54
+ .env
55
+ .env.local
56
+ *.pem
57
+
58
+ # Per-user Claude Code settings (personal permission allowlists, local paths)
59
+ .claude/settings.local.json
60
+
61
+ # TypeScript incremental build state
62
+ *.tsbuildinfo
63
+ apps/desktop/dist-types-node/
64
+
65
+ # Internal planning notes (kept out of the public tree; see docs/ for the
66
+ # published roadmap, ADRs, and release docs)
67
+ .internal-notes/
68
+ docs/release/C_NOTES.md
69
+ docs/release/D_NOTES.md
70
+ docs/release/oss-readiness-review.md
71
+ docs/release/implementation-plan-*.md
72
+ docs/release/webification-plan.md
73
+
74
+ # Tool caches / scratch
75
+ .mypy_cache/
76
+ .pytest_cache/
77
+ .ruff_cache/
78
+ .a1/
kiwime-0.1.0/PKG-INFO ADDED
@@ -0,0 +1,117 @@
1
+ Metadata-Version: 2.4
2
+ Name: kiwime
3
+ Version: 0.1.0
4
+ Summary: Compile a person into AI-readable expert context. Local-first web runtime + MCP server.
5
+ Project-URL: Homepage, https://github.com/kiwiberry-ai/kiwime
6
+ Project-URL: Documentation, https://github.com/kiwiberry-ai/kiwime/tree/main/docs
7
+ Project-URL: Changelog, https://github.com/kiwiberry-ai/kiwime/blob/main/CHANGELOG.md
8
+ License-Expression: Apache-2.0
9
+ Keywords: ai,context,knowledge-graph,local-first,mcp,memory
10
+ Classifier: Development Status :: 2 - Pre-Alpha
11
+ Classifier: Environment :: Web Environment
12
+ Classifier: Intended Audience :: Developers
13
+ Classifier: Operating System :: OS Independent
14
+ Classifier: Programming Language :: Python :: 3.11
15
+ Classifier: Programming Language :: Python :: 3.12
16
+ Classifier: Topic :: Scientific/Engineering :: Artificial Intelligence
17
+ Requires-Python: >=3.11
18
+ Requires-Dist: fastapi>=0.115
19
+ Requires-Dist: kiwime-compiler==0.1.0
20
+ Requires-Dist: kiwime-connector-gdrive==0.1.0
21
+ Requires-Dist: kiwime-connector-github==0.1.0
22
+ Requires-Dist: kiwime-connector-gmail==0.1.0
23
+ Requires-Dist: kiwime-connector-local-files==0.1.0
24
+ Requires-Dist: kiwime-connector-mcp-client==0.1.0
25
+ Requires-Dist: kiwime-connector-notion==0.1.0
26
+ Requires-Dist: kiwime-connector-slack==0.1.0
27
+ Requires-Dist: kiwime-export==0.1.0
28
+ Requires-Dist: kiwime-sdk==0.1.0
29
+ Requires-Dist: kiwime-secret==0.1.0
30
+ Requires-Dist: kiwime-store==0.1.0
31
+ Requires-Dist: uvicorn>=0.34
32
+ Description-Content-Type: text/markdown
33
+
34
+ # kiwiMe web host
35
+
36
+ Run kiwiMe as a local web app — a background service on `127.0.0.1` plus a
37
+ browser UI — instead of the Tauri desktop shell. This is the primary
38
+ distribution for developers and technical users (no code signing, no native
39
+ installer): you start a service and open a browser.
40
+
41
+ It is **local-first**: the service binds to loopback only, and all data
42
+ (credentials, content, indexes) stays on your machine, exactly as in the
43
+ desktop app. The host runs every sidecar *in-process* — there are no child
44
+ processes and no stdio plumbing; see `docs/release/webification-plan.md`.
45
+
46
+ ## Run from a checkout (current)
47
+
48
+ Prerequisites:
49
+
50
+ - [uv](https://docs.astral.sh/uv/) (Python package manager)
51
+ - Node ≥ 20 **and [pnpm](https://pnpm.io/installation)** — the easiest way to
52
+ get pnpm is `corepack enable` (ships with Node), or
53
+ `npm install -g pnpm`.
54
+ - Python ≥ 3.11 with SQLite loadable-extension support (standard CPython
55
+ builds have it).
56
+
57
+ ```bash
58
+ # 1. install the Python workspace (all sidecars + the host)
59
+ uv sync --all-packages -p 3.12
60
+
61
+ # 2. build the frontend once (served as static files by the host)
62
+ cd apps/desktop && pnpm install && pnpm build && cd -
63
+
64
+ # 3. start the host — opens http://127.0.0.1:8765 in your browser
65
+ uv run kiwime
66
+ ```
67
+
68
+ If you skip step 2, the host still starts and serves the API, and shows a
69
+ "UI not built" page with these instructions instead of the app.
70
+
71
+ Options:
72
+
73
+ ```
74
+ kiwime [--host 127.0.0.1] [--port 8765] [--db PATH] [--no-browser]
75
+ ```
76
+
77
+ - `--db PATH` — use a specific store SQLite file (default: the platform app
78
+ data dir, the same one the desktop app uses).
79
+ - `--no-browser` — don't auto-open a browser. The startup log prints an
80
+ authenticated `…/auth?token=…` link — open that (or use the token as an
81
+ `Authorization: Bearer` header for scripting).
82
+ - `KIWIME_DIST=/path/to/dist` — override where the built UI is served from.
83
+
84
+ ### Security
85
+
86
+ The API requires a per-session token even on loopback: the browser gets it
87
+ via the `/auth?token=…` link (exchanged for an HttpOnly cookie), other
88
+ clients pass `Authorization: Bearer <token>`. Requests with a non-localhost
89
+ `Host` header or a non-JSON body are rejected. A fresh token is minted on
90
+ every start.
91
+
92
+ ### Linux note
93
+
94
+ Connector credentials go to the OS keyring. On Linux this needs a Secret
95
+ Service provider (GNOME Keyring / KWallet via `libsecret`); on a headless
96
+ box or minimal WSL distro, install `gnome-keyring` (or configure another
97
+ [keyring backend](https://pypi.org/project/keyring/)) before adding sources.
98
+
99
+ ## Local models
100
+
101
+ The host exposes the same one-click Ollama flow as the desktop app
102
+ (detect / download with progress). Install [Ollama](https://ollama.com/download)
103
+ and use the in-app model manager to pull Qwen3 / Gemma 3. The curated model
104
+ list lives in `shared/model-catalog.json`, shared with the desktop runtime.
105
+
106
+ ## Installing as a tool (future)
107
+
108
+ `pipx install kiwime` / `uv tool install kiwime` will be the one-line
109
+ install once the packages are published to PyPI and the built UI is bundled
110
+ into the wheel. Until then, use the checkout flow above.
111
+
112
+ ## How it relates to the desktop app
113
+
114
+ The React frontend and all Python sidecars are shared. Only the *host* differs:
115
+ the desktop app uses a Rust (Tauri) shell that spawns sidecars as processes;
116
+ this web host holds them in one Python process and serves the same UI over
117
+ HTTP + SSE. `apps/desktop/src/api/tauri.ts` picks the transport at runtime.
kiwime-0.1.0/README.md ADDED
@@ -0,0 +1,84 @@
1
+ # kiwiMe web host
2
+
3
+ Run kiwiMe as a local web app — a background service on `127.0.0.1` plus a
4
+ browser UI — instead of the Tauri desktop shell. This is the primary
5
+ distribution for developers and technical users (no code signing, no native
6
+ installer): you start a service and open a browser.
7
+
8
+ It is **local-first**: the service binds to loopback only, and all data
9
+ (credentials, content, indexes) stays on your machine, exactly as in the
10
+ desktop app. The host runs every sidecar *in-process* — there are no child
11
+ processes and no stdio plumbing; see `docs/release/webification-plan.md`.
12
+
13
+ ## Run from a checkout (current)
14
+
15
+ Prerequisites:
16
+
17
+ - [uv](https://docs.astral.sh/uv/) (Python package manager)
18
+ - Node ≥ 20 **and [pnpm](https://pnpm.io/installation)** — the easiest way to
19
+ get pnpm is `corepack enable` (ships with Node), or
20
+ `npm install -g pnpm`.
21
+ - Python ≥ 3.11 with SQLite loadable-extension support (standard CPython
22
+ builds have it).
23
+
24
+ ```bash
25
+ # 1. install the Python workspace (all sidecars + the host)
26
+ uv sync --all-packages -p 3.12
27
+
28
+ # 2. build the frontend once (served as static files by the host)
29
+ cd apps/desktop && pnpm install && pnpm build && cd -
30
+
31
+ # 3. start the host — opens http://127.0.0.1:8765 in your browser
32
+ uv run kiwime
33
+ ```
34
+
35
+ If you skip step 2, the host still starts and serves the API, and shows a
36
+ "UI not built" page with these instructions instead of the app.
37
+
38
+ Options:
39
+
40
+ ```
41
+ kiwime [--host 127.0.0.1] [--port 8765] [--db PATH] [--no-browser]
42
+ ```
43
+
44
+ - `--db PATH` — use a specific store SQLite file (default: the platform app
45
+ data dir, the same one the desktop app uses).
46
+ - `--no-browser` — don't auto-open a browser. The startup log prints an
47
+ authenticated `…/auth?token=…` link — open that (or use the token as an
48
+ `Authorization: Bearer` header for scripting).
49
+ - `KIWIME_DIST=/path/to/dist` — override where the built UI is served from.
50
+
51
+ ### Security
52
+
53
+ The API requires a per-session token even on loopback: the browser gets it
54
+ via the `/auth?token=…` link (exchanged for an HttpOnly cookie), other
55
+ clients pass `Authorization: Bearer <token>`. Requests with a non-localhost
56
+ `Host` header or a non-JSON body are rejected. A fresh token is minted on
57
+ every start.
58
+
59
+ ### Linux note
60
+
61
+ Connector credentials go to the OS keyring. On Linux this needs a Secret
62
+ Service provider (GNOME Keyring / KWallet via `libsecret`); on a headless
63
+ box or minimal WSL distro, install `gnome-keyring` (or configure another
64
+ [keyring backend](https://pypi.org/project/keyring/)) before adding sources.
65
+
66
+ ## Local models
67
+
68
+ The host exposes the same one-click Ollama flow as the desktop app
69
+ (detect / download with progress). Install [Ollama](https://ollama.com/download)
70
+ and use the in-app model manager to pull Qwen3 / Gemma 3. The curated model
71
+ list lives in `shared/model-catalog.json`, shared with the desktop runtime.
72
+
73
+ ## Installing as a tool (future)
74
+
75
+ `pipx install kiwime` / `uv tool install kiwime` will be the one-line
76
+ install once the packages are published to PyPI and the built UI is bundled
77
+ into the wheel. Until then, use the checkout flow above.
78
+
79
+ ## How it relates to the desktop app
80
+
81
+ The React frontend and all Python sidecars are shared. Only the *host* differs:
82
+ the desktop app uses a Rust (Tauri) shell that spawns sidecars as processes;
83
+ this web host holds them in one Python process and serves the same UI over
84
+ HTTP + SSE. `apps/desktop/src/api/tauri.ts` picks the transport at runtime.
@@ -0,0 +1,83 @@
1
+ [project]
2
+ # Published as "kiwime" so `uvx kiwime` / `pipx install kiwime` just work —
3
+ # this is the package users install; everything else is a dependency of it.
4
+ name = "kiwime"
5
+ version = "0.1.0"
6
+ description = "Compile a person into AI-readable expert context. Local-first web runtime + MCP server."
7
+ readme = "README.md"
8
+ requires-python = ">=3.11"
9
+ license = "Apache-2.0"
10
+ keywords = ["mcp", "ai", "context", "local-first", "knowledge-graph", "memory"]
11
+ classifiers = [
12
+ "Development Status :: 2 - Pre-Alpha",
13
+ "Environment :: Web Environment",
14
+ "Intended Audience :: Developers",
15
+ "Operating System :: OS Independent",
16
+ "Programming Language :: Python :: 3.11",
17
+ "Programming Language :: Python :: 3.12",
18
+ "Topic :: Scientific/Engineering :: Artificial Intelligence",
19
+ ]
20
+ dependencies = [
21
+ "kiwime-sdk==0.1.0",
22
+ "kiwime-store==0.1.0",
23
+ "kiwime-compiler==0.1.0",
24
+ "kiwime-export==0.1.0",
25
+ "kiwime-secret==0.1.0",
26
+ # P0 connectors, imported in-process.
27
+ "kiwime-connector-local-files==0.1.0",
28
+ "kiwime-connector-github==0.1.0",
29
+ "kiwime-connector-notion==0.1.0",
30
+ "kiwime-connector-gdrive==0.1.0",
31
+ "kiwime-connector-gmail==0.1.0",
32
+ "kiwime-connector-slack==0.1.0",
33
+ "kiwime-connector-mcp-client==0.1.0",
34
+ "fastapi>=0.115",
35
+ "uvicorn>=0.34",
36
+ ]
37
+
38
+ [project.urls]
39
+ Homepage = "https://github.com/kiwiberry-ai/kiwime"
40
+ Documentation = "https://github.com/kiwiberry-ai/kiwime/tree/main/docs"
41
+ Changelog = "https://github.com/kiwiberry-ai/kiwime/blob/main/CHANGELOG.md"
42
+
43
+ [project.scripts]
44
+ kiwime = "kiwime_host.__main__:main"
45
+
46
+ [build-system]
47
+ requires = ["hatchling"]
48
+ build-backend = "hatchling.build"
49
+
50
+ # The publish workflow copies the built frontend (apps/desktop/dist) into
51
+ # src/kiwime_host/_ui before `uv build`, so `uvx kiwime` serves the UI with
52
+ # no Node/pnpm on the user's machine. _ui is gitignored; `artifacts` tells
53
+ # hatchling to package it anyway. When absent (dev checkouts) the build
54
+ # still succeeds and _find_dist() falls back to apps/desktop/dist.
55
+ [tool.hatch.build]
56
+ artifacts = ["src/kiwime_host/_ui"]
57
+
58
+ [tool.hatch.build.targets.wheel]
59
+ packages = ["src/kiwime_host"]
60
+
61
+ [tool.uv.sources]
62
+ kiwime-sdk = { workspace = true }
63
+ kiwime-store = { workspace = true }
64
+ kiwime-compiler = { workspace = true }
65
+ kiwime-export = { workspace = true }
66
+ kiwime-secret = { workspace = true }
67
+ kiwime-connector-local-files = { workspace = true }
68
+ kiwime-connector-github = { workspace = true }
69
+ kiwime-connector-notion = { workspace = true }
70
+ kiwime-connector-gdrive = { workspace = true }
71
+ kiwime-connector-gmail = { workspace = true }
72
+ kiwime-connector-slack = { workspace = true }
73
+ kiwime-connector-mcp-client = { workspace = true }
74
+
75
+ [dependency-groups]
76
+ dev = [
77
+ "pytest>=8.0",
78
+ "pytest-asyncio>=0.24",
79
+ "httpx>=0.27",
80
+ ]
81
+
82
+ [tool.pytest.ini_options]
83
+ asyncio_mode = "auto"
@@ -0,0 +1,13 @@
1
+ """kiwiMe web host (distribution route B).
2
+
3
+ In-process FastAPI runtime: holds every sidecar's Server instance in one
4
+ process and routes UI requests to ``Server.dispatch(method, params)`` directly
5
+ — no child processes, no stdio JSON-RPC. Replaces the Rust supervisor's
6
+ process orchestration with an in-process method table.
7
+
8
+ See docs/release/webification-plan.md.
9
+ """
10
+
11
+ from kiwime_host.host import InProcessHost
12
+
13
+ __all__ = ["InProcessHost"]
@@ -0,0 +1,102 @@
1
+ """``kiwime`` entry point — start the local web host.
2
+
3
+ kiwime [--host 127.0.0.1] [--port 8765] [--db PATH] [--no-browser]
4
+
5
+ Binds to loopback by default (local-first; no remote access in v1), serves the
6
+ built UI + the /api surface, and opens the browser. This is the pipx-installed
7
+ command users run (route B).
8
+ """
9
+
10
+ from __future__ import annotations
11
+
12
+ import argparse
13
+ import sys
14
+ import threading
15
+ import webbrowser
16
+ from pathlib import Path
17
+
18
+
19
+ def _find_dist() -> Path | None:
20
+ """Locate the built frontend.
21
+
22
+ Resolution order:
23
+ 1. $KIWIME_DIST — explicit override (packaging / unusual layouts).
24
+ 2. kiwime_host/_ui — bundled into the wheel by the publish workflow;
25
+ this is what `uvx kiwime` / `pipx install kiwime` hits.
26
+ 3. apps/desktop/dist relative to the repo root (source checkout).
27
+ 4. cwd/apps/desktop/dist — running from a clone without installing.
28
+
29
+ Returns None if no build is found; the host still serves /api so the UI
30
+ can be run separately (e.g. `vite dev`) against it during development.
31
+ """
32
+ import os
33
+
34
+ env = os.environ.get("KIWIME_DIST")
35
+ if env:
36
+ p = Path(env)
37
+ return p if p.is_dir() else None
38
+
39
+ here = Path(__file__).resolve()
40
+ candidates = [
41
+ here.parent / "_ui", # bundled in the wheel
42
+ here.parents[4] / "apps" / "desktop" / "dist", # source checkout
43
+ Path.cwd() / "apps" / "desktop" / "dist", # run from repo root
44
+ ]
45
+ for c in candidates:
46
+ # index.html (not just the dir) so a stray empty _ui doesn't win.
47
+ if (c / "index.html").is_file():
48
+ return c
49
+ return None
50
+
51
+
52
+ def main(argv: list[str] | None = None) -> int:
53
+ parser = argparse.ArgumentParser(prog="kiwime")
54
+ parser.add_argument("--host", default="127.0.0.1", help="Bind address (loopback only by default).")
55
+ parser.add_argument("--port", type=int, default=8765)
56
+ parser.add_argument("--db", default=None, help="Store SQLite path (default: platform app dir).")
57
+ parser.add_argument("--no-browser", action="store_true", help="Do not open a browser on start.")
58
+ parser.add_argument(
59
+ "--sync-interval",
60
+ type=int,
61
+ default=15,
62
+ metavar="MINUTES",
63
+ help="Incremental-sync + auto-compile cadence in minutes (0 disables).",
64
+ )
65
+ args = parser.parse_args(argv)
66
+
67
+ import uvicorn
68
+
69
+ from kiwime_host.host import InProcessHost
70
+ from kiwime_host.web import create_app, mint_token
71
+
72
+ host = InProcessHost(db_path=args.db)
73
+ # Ensure the schema exists before serving (idempotent).
74
+ import asyncio
75
+
76
+ asyncio.run(host.call("store", "store.migrate", {}))
77
+
78
+ token = mint_token()
79
+ app = create_app(
80
+ host,
81
+ dist_dir=_find_dist(),
82
+ token=token,
83
+ sync_interval=args.sync_interval * 60 if args.sync_interval > 0 else None,
84
+ )
85
+
86
+ url = f"http://{args.host}:{args.port}"
87
+ auth_url = f"{url}/auth?token={token}"
88
+ print(f"kiwiMe web host running at {url}", file=sys.stderr)
89
+ if args.no_browser:
90
+ # No browser will pick up the session cookie, so hand the user the
91
+ # authenticated entry link (and the token for curl/scripts).
92
+ print(f"open {auth_url} to start a session", file=sys.stderr)
93
+ else:
94
+ threading.Timer(1.0, lambda: webbrowser.open(auth_url)).start()
95
+
96
+ uvicorn.run(app, host=args.host, port=args.port, log_level="warning")
97
+ host.close()
98
+ return 0
99
+
100
+
101
+ if __name__ == "__main__":
102
+ sys.exit(main())
@@ -0,0 +1,2 @@
1
+ function t(n,e,i,s){if(typeof e=="function"?n!==e||!s:!e.has(n))throw new TypeError("Cannot read private member from an object whose class did not declare it");return i==="m"?s:i==="a"?s.call(n):s?s.value:e.get(n)}function c(n,e,i,s,_){if(typeof e=="function"?n!==e||!0:!e.has(n))throw new TypeError("Cannot write private member to an object whose class did not declare it");return e.set(n,i),i}var a,r,o,l,u;const d="__TAURI_TO_IPC_KEY__";function w(n,e=!1){return window.__TAURI_INTERNALS__.transformCallback(n,e)}class g{constructor(e){a.set(this,void 0),r.set(this,0),o.set(this,[]),l.set(this,void 0),c(this,a,e||(()=>{})),this.id=w(i=>{const s=i.index;if("end"in i){s==t(this,r,"f")?this.cleanupCallback():c(this,l,s);return}const _=i.message;if(s==t(this,r,"f")){for(t(this,a,"f").call(this,_),c(this,r,t(this,r,"f")+1);t(this,r,"f")in t(this,o,"f");){const p=t(this,o,"f")[t(this,r,"f")];t(this,a,"f").call(this,p),delete t(this,o,"f")[t(this,r,"f")],c(this,r,t(this,r,"f")+1)}t(this,r,"f")===t(this,l,"f")&&this.cleanupCallback()}else t(this,o,"f")[s]=_})}cleanupCallback(){window.__TAURI_INTERNALS__.unregisterCallback(this.id)}set onmessage(e){c(this,a,e)}get onmessage(){return t(this,a,"f")}[(a=new WeakMap,r=new WeakMap,o=new WeakMap,l=new WeakMap,d)](){return`__CHANNEL__:${this.id}`}toJSON(){return this[d]()}}class f{constructor(e,i,s){this.plugin=e,this.event=i,this.channelId=s}async unregister(){return h(`plugin:${this.plugin}|remove_listener`,{event:this.event,channelId:this.channelId})}}async function m(n,e,i){const s=new g(i);try{return await h(`plugin:${n}|register_listener`,{event:e,handler:s}),new f(n,e,s.id)}catch{return await h(`plugin:${n}|registerListener`,{event:e,handler:s}),new f(n,e,s.id)}}async function I(n){return h(`plugin:${n}|check_permissions`)}async function C(n){return h(`plugin:${n}|request_permissions`)}async function h(n,e={},i){return window.__TAURI_INTERNALS__.invoke(n,e,i)}function T(n,e="asset"){return window.__TAURI_INTERNALS__.convertFileSrc(n,e)}class k{get rid(){return t(this,u,"f")}constructor(e){u.set(this,void 0),c(this,u,e)}async close(){return h("plugin:resources|close",{rid:this.rid})}}u=new WeakMap;function E(){return!!(globalThis||window).isTauri}export{g as Channel,f as PluginListener,k as Resource,d as SERIALIZE_TO_IPC_FN,m as addPluginListener,I as checkPermissions,T as convertFileSrc,h as invoke,E as isTauri,C as requestPermissions,w as transformCallback};
2
+ //# sourceMappingURL=core-DhEqZVGG.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"core-DhEqZVGG.js","sources":["../../../../node_modules/@tauri-apps/api/external/tslib/tslib.es6.js","../../../../node_modules/@tauri-apps/api/core.js"],"sourcesContent":["/******************************************************************************\r\nCopyright (c) Microsoft Corporation.\r\n\r\nPermission to use, copy, modify, and/or distribute this software for any\r\npurpose with or without fee is hereby granted.\r\n\r\nTHE SOFTWARE IS PROVIDED \"AS IS\" AND THE AUTHOR DISCLAIMS ALL WARRANTIES WITH\r\nREGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY\r\nAND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY SPECIAL, DIRECT,\r\nINDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES WHATSOEVER RESULTING FROM\r\nLOSS OF USE, DATA OR PROFITS, WHETHER IN AN ACTION OF CONTRACT, NEGLIGENCE OR\r\nOTHER TORTIOUS ACTION, ARISING OUT OF OR IN CONNECTION WITH THE USE OR\r\nPERFORMANCE OF THIS SOFTWARE.\r\n***************************************************************************** */\r\n/* global Reflect, Promise, SuppressedError, Symbol, Iterator */\r\n\r\n\r\nfunction __classPrivateFieldGet(receiver, state, kind, f) {\r\n if (kind === \"a\" && !f) throw new TypeError(\"Private accessor was defined without a getter\");\r\n if (typeof state === \"function\" ? receiver !== state || !f : !state.has(receiver)) throw new TypeError(\"Cannot read private member from an object whose class did not declare it\");\r\n return kind === \"m\" ? f : kind === \"a\" ? f.call(receiver) : f ? f.value : state.get(receiver);\r\n}\r\n\r\nfunction __classPrivateFieldSet(receiver, state, value, kind, f) {\r\n if (kind === \"m\") throw new TypeError(\"Private method is not writable\");\r\n if (kind === \"a\" && !f) throw new TypeError(\"Private accessor was defined without a setter\");\r\n if (typeof state === \"function\" ? receiver !== state || !f : !state.has(receiver)) throw new TypeError(\"Cannot write private member to an object whose class did not declare it\");\r\n return (kind === \"a\" ? f.call(receiver, value) : f ? f.value = value : state.set(receiver, value)), value;\r\n}\r\n\r\ntypeof SuppressedError === \"function\" ? SuppressedError : function (error, suppressed, message) {\r\n var e = new Error(message);\r\n return e.name = \"SuppressedError\", e.error = error, e.suppressed = suppressed, e;\r\n};\n\nexport { __classPrivateFieldGet, __classPrivateFieldSet };\n","import { __classPrivateFieldSet, __classPrivateFieldGet } from './external/tslib/tslib.es6.js';\n\n// Copyright 2019-2024 Tauri Programme within The Commons Conservancy\n// SPDX-License-Identifier: Apache-2.0\n// SPDX-License-Identifier: MIT\nvar _Channel_onmessage, _Channel_nextMessageIndex, _Channel_pendingMessages, _Channel_messageEndIndex, _Resource_rid;\n/**\n * Invoke your custom commands.\n *\n * This package is also accessible with `window.__TAURI__.core` when [`app.withGlobalTauri`](https://v2.tauri.app/reference/config/#withglobaltauri) in `tauri.conf.json` is set to `true`.\n * @module\n */\n/**\n * A key to be used to implement a special function\n * on your types that define how your type should be serialized\n * when passing across the IPC.\n * @example\n * Given a type in Rust that looks like this\n * ```rs\n * #[derive(serde::Serialize, serde::Deserialize)\n * enum UserId {\n * String(String),\n * Number(u32),\n * }\n * ```\n * `UserId::String(\"id\")` would be serialized into `{ String: \"id\" }`\n * and so we need to pass the same structure back to Rust\n * ```ts\n * import { SERIALIZE_TO_IPC_FN } from \"@tauri-apps/api/core\"\n *\n * class UserIdString {\n * id\n * constructor(id) {\n * this.id = id\n * }\n *\n * [SERIALIZE_TO_IPC_FN]() {\n * return { String: this.id }\n * }\n * }\n *\n * class UserIdNumber {\n * id\n * constructor(id) {\n * this.id = id\n * }\n *\n * [SERIALIZE_TO_IPC_FN]() {\n * return { Number: this.id }\n * }\n * }\n *\n * type UserId = UserIdString | UserIdNumber\n * ```\n *\n */\n// if this value changes, make sure to update it in:\n// 1. ipc.js\n// 2. process-ipc-message-fn.js\nconst SERIALIZE_TO_IPC_FN = '__TAURI_TO_IPC_KEY__';\n/**\n * Stores the callback in a known location, and returns an identifier that can be passed to the backend.\n * The backend uses the identifier to `eval()` the callback.\n *\n * @return An unique identifier associated with the callback function.\n *\n * @since 1.0.0\n */\nfunction transformCallback(\n// TODO: Make this not optional in v3\ncallback, once = false) {\n return window.__TAURI_INTERNALS__.transformCallback(callback, once);\n}\nclass Channel {\n constructor(onmessage) {\n _Channel_onmessage.set(this, void 0);\n // the index is used as a mechanism to preserve message order\n _Channel_nextMessageIndex.set(this, 0);\n _Channel_pendingMessages.set(this, []);\n _Channel_messageEndIndex.set(this, void 0);\n __classPrivateFieldSet(this, _Channel_onmessage, onmessage || (() => { }), \"f\");\n this.id = transformCallback((rawMessage) => {\n const index = rawMessage.index;\n if ('end' in rawMessage) {\n if (index == __classPrivateFieldGet(this, _Channel_nextMessageIndex, \"f\")) {\n this.cleanupCallback();\n }\n else {\n __classPrivateFieldSet(this, _Channel_messageEndIndex, index, \"f\");\n }\n return;\n }\n const message = rawMessage.message;\n // Process the message if we're at the right order\n if (index == __classPrivateFieldGet(this, _Channel_nextMessageIndex, \"f\")) {\n __classPrivateFieldGet(this, _Channel_onmessage, \"f\").call(this, message);\n __classPrivateFieldSet(this, _Channel_nextMessageIndex, __classPrivateFieldGet(this, _Channel_nextMessageIndex, \"f\") + 1, \"f\");\n // process pending messages\n while (__classPrivateFieldGet(this, _Channel_nextMessageIndex, \"f\") in __classPrivateFieldGet(this, _Channel_pendingMessages, \"f\")) {\n const message = __classPrivateFieldGet(this, _Channel_pendingMessages, \"f\")[__classPrivateFieldGet(this, _Channel_nextMessageIndex, \"f\")];\n __classPrivateFieldGet(this, _Channel_onmessage, \"f\").call(this, message);\n // eslint-disable-next-line @typescript-eslint/no-array-delete\n delete __classPrivateFieldGet(this, _Channel_pendingMessages, \"f\")[__classPrivateFieldGet(this, _Channel_nextMessageIndex, \"f\")];\n __classPrivateFieldSet(this, _Channel_nextMessageIndex, __classPrivateFieldGet(this, _Channel_nextMessageIndex, \"f\") + 1, \"f\");\n }\n if (__classPrivateFieldGet(this, _Channel_nextMessageIndex, \"f\") === __classPrivateFieldGet(this, _Channel_messageEndIndex, \"f\")) {\n this.cleanupCallback();\n }\n }\n // Queue the message if we're not\n else {\n // eslint-disable-next-line security/detect-object-injection\n __classPrivateFieldGet(this, _Channel_pendingMessages, \"f\")[index] = message;\n }\n });\n }\n cleanupCallback() {\n window.__TAURI_INTERNALS__.unregisterCallback(this.id);\n }\n set onmessage(handler) {\n __classPrivateFieldSet(this, _Channel_onmessage, handler, \"f\");\n }\n get onmessage() {\n return __classPrivateFieldGet(this, _Channel_onmessage, \"f\");\n }\n [(_Channel_onmessage = new WeakMap(), _Channel_nextMessageIndex = new WeakMap(), _Channel_pendingMessages = new WeakMap(), _Channel_messageEndIndex = new WeakMap(), SERIALIZE_TO_IPC_FN)]() {\n return `__CHANNEL__:${this.id}`;\n }\n toJSON() {\n // eslint-disable-next-line security/detect-object-injection\n return this[SERIALIZE_TO_IPC_FN]();\n }\n}\nclass PluginListener {\n constructor(plugin, event, channelId) {\n this.plugin = plugin;\n this.event = event;\n this.channelId = channelId;\n }\n async unregister() {\n return invoke(`plugin:${this.plugin}|remove_listener`, {\n event: this.event,\n channelId: this.channelId\n });\n }\n}\n/**\n * Adds a listener to a plugin event.\n *\n * @returns The listener object to stop listening to the events.\n *\n * @since 2.0.0\n */\nasync function addPluginListener(plugin, event, cb) {\n const handler = new Channel(cb);\n try {\n await invoke(`plugin:${plugin}|register_listener`, {\n event,\n handler\n });\n return new PluginListener(plugin, event, handler.id);\n }\n catch {\n // TODO(v3): remove this fallback\n // note: we must try with camelCase here for backwards compatibility\n await invoke(`plugin:${plugin}|registerListener`, { event, handler });\n return new PluginListener(plugin, event, handler.id);\n }\n}\n/**\n * Get permission state for a plugin.\n *\n * This should be used by plugin authors to wrap their actual implementation.\n */\nasync function checkPermissions(plugin) {\n return invoke(`plugin:${plugin}|check_permissions`);\n}\n/**\n * Request permissions.\n *\n * This should be used by plugin authors to wrap their actual implementation.\n */\nasync function requestPermissions(plugin) {\n return invoke(`plugin:${plugin}|request_permissions`);\n}\n/**\n * Sends a message to the backend.\n * @example\n * ```typescript\n * import { invoke } from '@tauri-apps/api/core';\n * await invoke('login', { user: 'tauri', password: 'poiwe3h4r5ip3yrhtew9ty' });\n * ```\n *\n * @param cmd The command name.\n * @param args The optional arguments to pass to the command.\n * @param options The request options.\n * @return A promise resolving or rejecting to the backend response.\n *\n * @since 1.0.0\n */\nasync function invoke(cmd, args = {}, options) {\n return window.__TAURI_INTERNALS__.invoke(cmd, args, options);\n}\n/**\n * Convert a device file path to an URL that can be loaded by the webview.\n * Note that `asset:` and `http://asset.localhost` must be added to [`app.security.csp`](https://v2.tauri.app/reference/config/#csp-1) in `tauri.conf.json`.\n * Example CSP value: `\"csp\": \"default-src 'self' ipc: http://ipc.localhost; img-src 'self' asset: http://asset.localhost\"` to use the asset protocol on image sources.\n *\n * Additionally, `\"enable\" : \"true\"` must be added to [`app.security.assetProtocol`](https://v2.tauri.app/reference/config/#assetprotocolconfig)\n * in `tauri.conf.json` and its access scope must be defined on the `scope` array on the same `assetProtocol` object.\n *\n * @param filePath The file path.\n * @param protocol The protocol to use. Defaults to `asset`. You only need to set this when using a custom protocol.\n * @example\n * ```typescript\n * import { appDataDir, join } from '@tauri-apps/api/path';\n * import { convertFileSrc } from '@tauri-apps/api/core';\n * const appDataDirPath = await appDataDir();\n * const filePath = await join(appDataDirPath, 'assets/video.mp4');\n * const assetUrl = convertFileSrc(filePath);\n *\n * const video = document.getElementById('my-video');\n * const source = document.createElement('source');\n * source.type = 'video/mp4';\n * source.src = assetUrl;\n * video.appendChild(source);\n * video.load();\n * ```\n *\n * @return the URL that can be used as source on the webview.\n *\n * @since 1.0.0\n */\nfunction convertFileSrc(filePath, protocol = 'asset') {\n return window.__TAURI_INTERNALS__.convertFileSrc(filePath, protocol);\n}\n/**\n * A rust-backed resource stored through `tauri::Manager::resources_table` API.\n *\n * The resource lives in the main process and does not exist\n * in the Javascript world, and thus will not be cleaned up automatically\n * except on application exit. If you want to clean it up early, call {@linkcode Resource.close}\n *\n * @example\n * ```typescript\n * import { Resource, invoke } from '@tauri-apps/api/core';\n * export class DatabaseHandle extends Resource {\n * static async open(path: string): Promise<DatabaseHandle> {\n * const rid: number = await invoke('open_db', { path });\n * return new DatabaseHandle(rid);\n * }\n *\n * async execute(sql: string): Promise<void> {\n * await invoke('execute_sql', { rid: this.rid, sql });\n * }\n * }\n * ```\n */\nclass Resource {\n get rid() {\n return __classPrivateFieldGet(this, _Resource_rid, \"f\");\n }\n constructor(rid) {\n _Resource_rid.set(this, void 0);\n __classPrivateFieldSet(this, _Resource_rid, rid, \"f\");\n }\n /**\n * Destroys and cleans up this resource from memory.\n * **You should not call any method on this object anymore and should drop any reference to it.**\n */\n async close() {\n return invoke('plugin:resources|close', {\n rid: this.rid\n });\n }\n}\n_Resource_rid = new WeakMap();\nfunction isTauri() {\n // eslint-disable-next-line @typescript-eslint/no-explicit-any, @typescript-eslint/no-unsafe-member-access\n return !!(globalThis || window).isTauri;\n}\n\nexport { Channel, PluginListener, Resource, SERIALIZE_TO_IPC_FN, addPluginListener, checkPermissions, convertFileSrc, invoke, isTauri, requestPermissions, transformCallback };\n"],"names":["__classPrivateFieldGet","receiver","state","kind","f","__classPrivateFieldSet","value","_Channel_onmessage","_Channel_nextMessageIndex","_Channel_pendingMessages","_Channel_messageEndIndex","_Resource_rid","SERIALIZE_TO_IPC_FN","transformCallback","callback","once","Channel","onmessage","rawMessage","index","message","handler","PluginListener","plugin","event","channelId","invoke","addPluginListener","cb","checkPermissions","requestPermissions","cmd","args","options","convertFileSrc","filePath","protocol","Resource","rid","isTauri"],"mappings":"AAiBA,SAASA,EAAuBC,EAAUC,EAAOC,EAAMC,EAAG,CAEtD,GAAI,OAAOF,GAAU,WAAaD,IAAaC,GAAS,CAACE,EAAI,CAACF,EAAM,IAAID,CAAQ,EAAG,MAAM,IAAI,UAAU,0EAA0E,EACjL,OAAOE,IAAS,IAAMC,EAAID,IAAS,IAAMC,EAAE,KAAKH,CAAQ,EAAIG,EAAIA,EAAE,MAAQF,EAAM,IAAID,CAAQ,CAChG,CAEA,SAASI,EAAuBJ,EAAUC,EAAOI,EAAOH,EAAMC,EAAG,CAG7D,GAAI,OAAOF,GAAU,WAAaD,IAAaC,GAAS,GAAK,CAACA,EAAM,IAAID,CAAQ,EAAG,MAAM,IAAI,UAAU,yEAAyE,EAChL,OAAuEC,EAAM,IAAID,EAAUK,CAAK,EAAIA,CACxG,CCvBA,IAAIC,EAAoBC,EAA2BC,EAA0BC,EAA0BC,EAsDlG,MAACC,EAAsB,uBAS5B,SAASC,EAETC,EAAUC,EAAO,GAAO,CACpB,OAAO,OAAO,oBAAoB,kBAAkBD,EAAUC,CAAI,CACtE,CACA,MAAMC,CAAQ,CACV,YAAYC,EAAW,CACnBV,EAAmB,IAAI,KAAM,MAAM,EAEnCC,EAA0B,IAAI,KAAM,CAAC,EACrCC,EAAyB,IAAI,KAAM,EAAE,EACrCC,EAAyB,IAAI,KAAM,MAAM,EACzCL,EAAuB,KAAME,EAAoBU,IAAc,IAAM,CAAE,EAAO,EAC9E,KAAK,GAAKJ,EAAmBK,GAAe,CACxC,MAAMC,EAAQD,EAAW,MACzB,GAAI,QAASA,EAAY,CACjBC,GAASnB,EAAuB,KAAMQ,EAA2B,GAAG,EACpE,KAAK,gBAAe,EAGpBH,EAAuB,KAAMK,EAA0BS,CAAU,EAErE,MACJ,CACA,MAAMC,EAAUF,EAAW,QAE3B,GAAIC,GAASnB,EAAuB,KAAMQ,EAA2B,GAAG,EAAG,CAIvE,IAHAR,EAAuB,KAAMO,EAAoB,GAAG,EAAE,KAAK,KAAMa,CAAO,EACxEf,EAAuB,KAAMG,EAA2BR,EAAuB,KAAMQ,EAA2B,GAAG,EAAI,CAAM,EAEtHR,EAAuB,KAAMQ,EAA2B,GAAG,IAAKR,EAAuB,KAAMS,EAA0B,GAAG,GAAG,CAChI,MAAMW,EAAUpB,EAAuB,KAAMS,EAA0B,GAAG,EAAET,EAAuB,KAAMQ,EAA2B,GAAG,CAAC,EACxIR,EAAuB,KAAMO,EAAoB,GAAG,EAAE,KAAK,KAAMa,CAAO,EAExE,OAAOpB,EAAuB,KAAMS,EAA0B,GAAG,EAAET,EAAuB,KAAMQ,EAA2B,GAAG,CAAC,EAC/HH,EAAuB,KAAMG,EAA2BR,EAAuB,KAAMQ,EAA2B,GAAG,EAAI,CAAM,CACjI,CACIR,EAAuB,KAAMQ,EAA2B,GAAG,IAAMR,EAAuB,KAAMU,EAA0B,GAAG,GAC3H,KAAK,gBAAe,CAE5B,MAIIV,EAAuB,KAAMS,EAA0B,GAAG,EAAEU,CAAK,EAAIC,CAE7E,CAAC,CACL,CACA,iBAAkB,CACd,OAAO,oBAAoB,mBAAmB,KAAK,EAAE,CACzD,CACA,IAAI,UAAUC,EAAS,CACnBhB,EAAuB,KAAME,EAAoBc,CAAY,CACjE,CACA,IAAI,WAAY,CACZ,OAAOrB,EAAuB,KAAMO,EAAoB,GAAG,CAC/D,CACA,EAAEA,EAAqB,IAAI,QAAWC,EAA4B,IAAI,QAAWC,EAA2B,IAAI,QAAWC,EAA2B,IAAI,QAAWE,EAAmB,GAAK,CACzL,MAAO,eAAe,KAAK,EAAE,EACjC,CACA,QAAS,CAEL,OAAO,KAAKA,CAAmB,EAAC,CACpC,CACJ,CACA,MAAMU,CAAe,CACjB,YAAYC,EAAQC,EAAOC,EAAW,CAClC,KAAK,OAASF,EACd,KAAK,MAAQC,EACb,KAAK,UAAYC,CACrB,CACA,MAAM,YAAa,CACf,OAAOC,EAAO,UAAU,KAAK,MAAM,mBAAoB,CACnD,MAAO,KAAK,MACZ,UAAW,KAAK,SAC5B,CAAS,CACL,CACJ,CAQA,eAAeC,EAAkBJ,EAAQC,EAAOI,EAAI,CAChD,MAAMP,EAAU,IAAIL,EAAQY,CAAE,EAC9B,GAAI,CACA,aAAMF,EAAO,UAAUH,CAAM,qBAAsB,CAC/C,MAAAC,EACA,QAAAH,CACZ,CAAS,EACM,IAAIC,EAAeC,EAAQC,EAAOH,EAAQ,EAAE,CACvD,MACM,CAGF,aAAMK,EAAO,UAAUH,CAAM,oBAAqB,CAAE,MAAAC,EAAO,QAAAH,EAAS,EAC7D,IAAIC,EAAeC,EAAQC,EAAOH,EAAQ,EAAE,CACvD,CACJ,CAMA,eAAeQ,EAAiBN,EAAQ,CACpC,OAAOG,EAAO,UAAUH,CAAM,oBAAoB,CACtD,CAMA,eAAeO,EAAmBP,EAAQ,CACtC,OAAOG,EAAO,UAAUH,CAAM,sBAAsB,CACxD,CAgBA,eAAeG,EAAOK,EAAKC,EAAO,CAAA,EAAIC,EAAS,CAC3C,OAAO,OAAO,oBAAoB,OAAOF,EAAKC,EAAMC,CAAO,CAC/D,CA+BA,SAASC,EAAeC,EAAUC,EAAW,QAAS,CAClD,OAAO,OAAO,oBAAoB,eAAeD,EAAUC,CAAQ,CACvE,CAuBA,MAAMC,CAAS,CACX,IAAI,KAAM,CACN,OAAOrC,EAAuB,KAAMW,EAAe,GAAG,CAC1D,CACA,YAAY2B,EAAK,CACb3B,EAAc,IAAI,KAAM,MAAM,EAC9BN,EAAuB,KAAMM,EAAe2B,CAAQ,CACxD,CAKA,MAAM,OAAQ,CACV,OAAOZ,EAAO,yBAA0B,CACpC,IAAK,KAAK,GACtB,CAAS,CACL,CACJ,CACAf,EAAgB,IAAI,QACpB,SAAS4B,GAAU,CAEf,MAAO,CAAC,EAAE,YAAc,QAAQ,OACpC","x_google_ignoreList":[0,1]}
@@ -0,0 +1,2 @@
1
+ import{invoke as n,transformCallback as d}from"./core-DhEqZVGG.js";var i;(function(e){e.WINDOW_RESIZED="tauri://resize",e.WINDOW_MOVED="tauri://move",e.WINDOW_CLOSE_REQUESTED="tauri://close-requested",e.WINDOW_DESTROYED="tauri://destroyed",e.WINDOW_FOCUS="tauri://focus",e.WINDOW_BLUR="tauri://blur",e.WINDOW_SCALE_FACTOR_CHANGED="tauri://scale-change",e.WINDOW_THEME_CHANGED="tauri://theme-changed",e.WINDOW_CREATED="tauri://window-created",e.WINDOW_SUSPENDED="tauri://suspended",e.WINDOW_RESUMED="tauri://resumed",e.WEBVIEW_CREATED="tauri://webview-created",e.DRAG_ENTER="tauri://drag-enter",e.DRAG_OVER="tauri://drag-over",e.DRAG_DROP="tauri://drag-drop",e.DRAG_LEAVE="tauri://drag-leave"})(i||(i={}));async function _(e,r){window.__TAURI_EVENT_PLUGIN_INTERNALS__.unregisterListener(e,r),await n("plugin:event|unlisten",{event:e,eventId:r})}async function u(e,r,t){var a;const l=typeof t?.target=="string"?{kind:"AnyLabel",label:t.target}:(a=t?.target)!==null&&a!==void 0?a:{kind:"Any"};return n("plugin:event|listen",{event:e,target:l,handler:d(r)}).then(D=>async()=>_(e,D))}async function c(e,r,t){return u(e,a=>{_(e,a.id),r(a)},t)}async function o(e,r){await n("plugin:event|emit",{event:e,payload:r})}async function s(e,r,t){await n("plugin:event|emit_to",{target:typeof e=="string"?{kind:"AnyLabel",label:e}:e,event:r,payload:t})}export{i as TauriEvent,o as emit,s as emitTo,u as listen,c as once};
2
+ //# sourceMappingURL=event-BK_86lmQ.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"event-BK_86lmQ.js","sources":["../../../../node_modules/@tauri-apps/api/event.js"],"sourcesContent":["import { invoke, transformCallback } from './core.js';\n\n// Copyright 2019-2024 Tauri Programme within The Commons Conservancy\n// SPDX-License-Identifier: Apache-2.0\n// SPDX-License-Identifier: MIT\n/**\n * The event system allows you to emit events to the backend and listen to events from it.\n *\n * This package is also accessible with `window.__TAURI__.event` when [`app.withGlobalTauri`](https://v2.tauri.app/reference/config/#withglobaltauri) in `tauri.conf.json` is set to `true`.\n * @module\n */\n/**\n * @since 1.1.0\n */\nvar TauriEvent;\n(function (TauriEvent) {\n TauriEvent[\"WINDOW_RESIZED\"] = \"tauri://resize\";\n TauriEvent[\"WINDOW_MOVED\"] = \"tauri://move\";\n TauriEvent[\"WINDOW_CLOSE_REQUESTED\"] = \"tauri://close-requested\";\n TauriEvent[\"WINDOW_DESTROYED\"] = \"tauri://destroyed\";\n TauriEvent[\"WINDOW_FOCUS\"] = \"tauri://focus\";\n TauriEvent[\"WINDOW_BLUR\"] = \"tauri://blur\";\n TauriEvent[\"WINDOW_SCALE_FACTOR_CHANGED\"] = \"tauri://scale-change\";\n TauriEvent[\"WINDOW_THEME_CHANGED\"] = \"tauri://theme-changed\";\n TauriEvent[\"WINDOW_CREATED\"] = \"tauri://window-created\";\n TauriEvent[\"WINDOW_SUSPENDED\"] = \"tauri://suspended\";\n TauriEvent[\"WINDOW_RESUMED\"] = \"tauri://resumed\";\n TauriEvent[\"WEBVIEW_CREATED\"] = \"tauri://webview-created\";\n TauriEvent[\"DRAG_ENTER\"] = \"tauri://drag-enter\";\n TauriEvent[\"DRAG_OVER\"] = \"tauri://drag-over\";\n TauriEvent[\"DRAG_DROP\"] = \"tauri://drag-drop\";\n TauriEvent[\"DRAG_LEAVE\"] = \"tauri://drag-leave\";\n})(TauriEvent || (TauriEvent = {}));\n/**\n * Unregister the event listener associated with the given name and id.\n *\n * @ignore\n * @param event The event name\n * @param eventId Event identifier\n * @returns\n */\nasync function _unlisten(event, eventId) {\n window.__TAURI_EVENT_PLUGIN_INTERNALS__.unregisterListener(event, eventId);\n await invoke('plugin:event|unlisten', {\n event,\n eventId\n });\n}\n/**\n * Listen to an emitted event to any {@link EventTarget|target}.\n *\n * @example\n * ```typescript\n * import { listen } from '@tauri-apps/api/event';\n * const unlisten = await listen<string>('error', (event) => {\n * console.log(`Got error, payload: ${event.payload}`);\n * });\n *\n * // you need to call unlisten if your handler goes out of scope e.g. the component is unmounted\n * unlisten();\n * ```\n *\n * @param event Event name. Must include only alphanumeric characters, `-`, `/`, `:` and `_`.\n * @param handler Event handler callback.\n * @param options Event listening options.\n * @returns A promise resolving to a function to unlisten to the event.\n * Note that removing the listener is required if your listener goes out of scope e.g. the component is unmounted.\n *\n * @since 1.0.0\n */\nasync function listen(event, handler, options) {\n var _a;\n const target = typeof (options === null || options === void 0 ? void 0 : options.target) === 'string'\n ? { kind: 'AnyLabel', label: options.target }\n : ((_a = options === null || options === void 0 ? void 0 : options.target) !== null && _a !== void 0 ? _a : { kind: 'Any' });\n return invoke('plugin:event|listen', {\n event,\n target,\n handler: transformCallback(handler)\n }).then((eventId) => {\n return async () => _unlisten(event, eventId);\n });\n}\n/**\n * Listens once to an emitted event to any {@link EventTarget|target}.\n *\n * @example\n * ```typescript\n * import { once } from '@tauri-apps/api/event';\n * interface LoadedPayload {\n * loggedIn: boolean,\n * token: string\n * }\n * const unlisten = await once<LoadedPayload>('loaded', (event) => {\n * console.log(`App is loaded, loggedIn: ${event.payload.loggedIn}, token: ${event.payload.token}`);\n * });\n *\n * // you need to call unlisten if your handler goes out of scope e.g. the component is unmounted\n * unlisten();\n * ```\n *\n * @param event Event name. Must include only alphanumeric characters, `-`, `/`, `:` and `_`.\n * @param handler Event handler callback.\n * @param options Event listening options.\n * @returns A promise resolving to a function to unlisten to the event.\n * Note that removing the listener is required if your listener goes out of scope e.g. the component is unmounted.\n *\n * @since 1.0.0\n */\nasync function once(event, handler, options) {\n return listen(event, (eventData) => {\n void _unlisten(event, eventData.id);\n handler(eventData);\n }, options);\n}\n/**\n * Emits an event to all {@link EventTarget|targets}.\n *\n * @example\n * ```typescript\n * import { emit } from '@tauri-apps/api/event';\n * await emit('frontend-loaded', { loggedIn: true, token: 'authToken' });\n * ```\n *\n * @param event Event name. Must include only alphanumeric characters, `-`, `/`, `:` and `_`.\n * @param payload Event payload.\n *\n * @since 1.0.0\n */\nasync function emit(event, payload) {\n await invoke('plugin:event|emit', {\n event,\n payload\n });\n}\n/**\n * Emits an event to all {@link EventTarget|targets} matching the given target.\n *\n * @example\n * ```typescript\n * import { emitTo } from '@tauri-apps/api/event';\n * await emitTo('main', 'frontend-loaded', { loggedIn: true, token: 'authToken' });\n * ```\n *\n * @param target Label of the target Window/Webview/WebviewWindow or raw {@link EventTarget} object.\n * @param event Event name. Must include only alphanumeric characters, `-`, `/`, `:` and `_`.\n * @param payload Event payload.\n *\n * @since 2.0.0\n */\nasync function emitTo(target, event, payload) {\n const eventTarget = typeof target === 'string' ? { kind: 'AnyLabel', label: target } : target;\n await invoke('plugin:event|emit_to', {\n target: eventTarget,\n event,\n payload\n });\n}\n\nexport { TauriEvent, emit, emitTo, listen, once };\n"],"names":["TauriEvent","_unlisten","event","eventId","invoke","listen","handler","options","_a","target","transformCallback","once","eventData","emit","payload","emitTo"],"mappings":"mEAcG,IAACA,GACH,SAAUA,EAAY,CACnBA,EAAW,eAAoB,iBAC/BA,EAAW,aAAkB,eAC7BA,EAAW,uBAA4B,0BACvCA,EAAW,iBAAsB,oBACjCA,EAAW,aAAkB,gBAC7BA,EAAW,YAAiB,eAC5BA,EAAW,4BAAiC,uBAC5CA,EAAW,qBAA0B,wBACrCA,EAAW,eAAoB,yBAC/BA,EAAW,iBAAsB,oBACjCA,EAAW,eAAoB,kBAC/BA,EAAW,gBAAqB,0BAChCA,EAAW,WAAgB,qBAC3BA,EAAW,UAAe,oBAC1BA,EAAW,UAAe,oBAC1BA,EAAW,WAAgB,oBAC/B,GAAGA,IAAeA,EAAa,CAAA,EAAG,EASlC,eAAeC,EAAUC,EAAOC,EAAS,CACrC,OAAO,iCAAiC,mBAAmBD,EAAOC,CAAO,EACzE,MAAMC,EAAO,wBAAyB,CAClC,MAAAF,EACA,QAAAC,CACR,CAAK,CACL,CAuBA,eAAeE,EAAOH,EAAOI,EAASC,EAAS,CAC3C,IAAIC,EACJ,MAAMC,EAAS,OAA0DF,GAAQ,QAAY,SACvF,CAAE,KAAM,WAAY,MAAOA,EAAQ,MAAM,GACvCC,EAAuDD,GAAQ,UAAY,MAAQC,IAAO,OAASA,EAAK,CAAE,KAAM,OACxH,OAAOJ,EAAO,sBAAuB,CACjC,MAAAF,EACA,OAAAO,EACA,QAASC,EAAkBJ,CAAO,CAC1C,CAAK,EAAE,KAAMH,GACE,SAAYF,EAAUC,EAAOC,CAAO,CAC9C,CACL,CA2BA,eAAeQ,EAAKT,EAAOI,EAASC,EAAS,CACzC,OAAOF,EAAOH,EAAQU,GAAc,CAC3BX,EAAUC,EAAOU,EAAU,EAAE,EAClCN,EAAQM,CAAS,CACrB,EAAGL,CAAO,CACd,CAeA,eAAeM,EAAKX,EAAOY,EAAS,CAChC,MAAMV,EAAO,oBAAqB,CAC9B,MAAAF,EACA,QAAAY,CACR,CAAK,CACL,CAgBA,eAAeC,EAAON,EAAQP,EAAOY,EAAS,CAE1C,MAAMV,EAAO,uBAAwB,CACjC,OAFgB,OAAOK,GAAW,SAAW,CAAE,KAAM,WAAY,MAAOA,CAAM,EAAKA,EAGnF,MAAAP,EACA,QAAAY,CACR,CAAK,CACL","x_google_ignoreList":[0]}
@@ -0,0 +1,2 @@
1
+ import{invoke as n}from"./core-DhEqZVGG.js";async function r(e={}){return typeof e=="object"&&Object.freeze(e),await n("plugin:dialog|open",{options:e})}export{r as open};
2
+ //# sourceMappingURL=index-C4lDuuOm.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"index-C4lDuuOm.js","sources":["../../../../node_modules/@tauri-apps/plugin-dialog/dist-js/index.js"],"sourcesContent":["import { invoke } from '@tauri-apps/api/core';\n\n// Copyright 2019-2023 Tauri Programme within The Commons Conservancy\n// SPDX-License-Identifier: Apache-2.0\n// SPDX-License-Identifier: MIT\n/**\n * Internal function to convert the buttons to the Rust type.\n */\nfunction buttonsToRust(buttons) {\n if (buttons === undefined) {\n return undefined;\n }\n if (typeof buttons === 'string') {\n return buttons;\n }\n else if ('ok' in buttons && 'cancel' in buttons) {\n return { OkCancelCustom: [buttons.ok, buttons.cancel] };\n }\n else if ('yes' in buttons && 'no' in buttons && 'cancel' in buttons) {\n return {\n YesNoCancelCustom: [buttons.yes, buttons.no, buttons.cancel]\n };\n }\n else if ('ok' in buttons) {\n return { OkCustom: buttons.ok };\n }\n return undefined;\n}\n/**\n * Open a file/directory selection dialog.\n *\n * The selected paths are added to the filesystem and asset protocol scopes.\n * When security is more important than the easy of use of this API,\n * prefer writing a dedicated command instead.\n *\n * Note that the scope change is not persisted, so the values are cleared when the application is restarted.\n * You can save it to the filesystem using [tauri-plugin-persisted-scope](https://github.com/tauri-apps/tauri-plugin-persisted-scope).\n * @example\n * ```typescript\n * import { open } from '@tauri-apps/plugin-dialog';\n * // Open a selection dialog for image files\n * const selected = await open({\n * multiple: true,\n * filters: [{\n * name: 'Image',\n * extensions: ['png', 'jpeg']\n * }]\n * });\n * if (Array.isArray(selected)) {\n * // user selected multiple files\n * } else if (selected === null) {\n * // user cancelled the selection\n * } else {\n * // user selected a single file\n * }\n * ```\n *\n * @example\n * ```typescript\n * import { open } from '@tauri-apps/plugin-dialog';\n * import { appDir } from '@tauri-apps/api/path';\n * // Open a selection dialog for directories\n * const selected = await open({\n * directory: true,\n * multiple: true,\n * defaultPath: await appDir(),\n * });\n * if (Array.isArray(selected)) {\n * // user selected multiple directories\n * } else if (selected === null) {\n * // user cancelled the selection\n * } else {\n * // user selected a single directory\n * }\n * ```\n *\n * @returns A promise resolving to the selected path(s)\n *\n * @since 2.0.0\n */\nasync function open(options = {}) {\n if (typeof options === 'object') {\n Object.freeze(options);\n }\n return await invoke('plugin:dialog|open', { options });\n}\n/**\n * Open a file/directory save dialog.\n *\n * The selected path is added to the filesystem and asset protocol scopes.\n * When security is more important than the easy of use of this API,\n * prefer writing a dedicated command instead.\n *\n * Note that the scope change is not persisted, so the values are cleared when the application is restarted.\n * You can save it to the filesystem using [tauri-plugin-persisted-scope](https://github.com/tauri-apps/tauri-plugin-persisted-scope).\n * @example\n * ```typescript\n * import { save } from '@tauri-apps/plugin-dialog';\n * const filePath = await save({\n * filters: [{\n * name: 'Image',\n * extensions: ['png', 'jpeg']\n * }]\n * });\n * ```\n *\n * @returns A promise resolving to the selected path.\n *\n * @since 2.0.0\n */\nasync function save(options = {}) {\n if (typeof options === 'object') {\n Object.freeze(options);\n }\n return await invoke('plugin:dialog|save', { options });\n}\nasync function messageCommand(message, options) {\n return await invoke('plugin:dialog|message', {\n message,\n title: options?.title,\n kind: options?.kind,\n buttons: buttonsToRust(options?.buttons)\n });\n}\n/**\n * Shows a message dialog with an `Ok` button.\n * @example\n * ```typescript\n * import { message } from '@tauri-apps/plugin-dialog';\n * await message('Tauri is awesome', 'Tauri');\n * await message('File not found', { title: 'Tauri', kind: 'error' });\n * ```\n *\n * @param message The message to show.\n * @param options The dialog's options. If a string, it represents the dialog title.\n *\n * @returns A promise indicating the success or failure of the operation.\n *\n * @since 2.0.0\n *\n */\nasync function message(message, options) {\n const opts = typeof options === 'string' ? { title: options } : options;\n if (opts && !opts.buttons && opts.okLabel) {\n opts.buttons = { ok: opts.okLabel };\n }\n return messageCommand(message, opts);\n}\n/**\n * Shows a question dialog with `Yes` and `No` buttons.\n *\n * Convenient wrapper for `await message('msg', { buttons: 'YesNo' }) === 'Yes'`\n *\n * @example\n * ```typescript\n * import { ask } from '@tauri-apps/plugin-dialog';\n * const yes = await ask('Are you sure?', 'Tauri');\n * const yes2 = await ask('This action cannot be reverted. Are you sure?', { title: 'Tauri', kind: 'warning' });\n * ```\n *\n * @param message The message to show.\n * @param options The dialog's options. If a string, it represents the dialog title.\n *\n * @returns A promise resolving to a boolean indicating whether `Yes` was clicked or not.\n *\n * @since 2.0.0\n */\nasync function ask(message, options) {\n const opts = typeof options === 'string' ? { title: options } : options;\n const customButtons = opts?.okLabel || opts?.cancelLabel;\n const okLabel = opts?.okLabel ?? 'Yes';\n return ((await messageCommand(message, {\n title: opts?.title,\n kind: opts?.kind,\n buttons: customButtons\n ? { ok: okLabel, cancel: opts.cancelLabel ?? 'No' }\n : 'YesNo'\n })) === okLabel);\n}\n/**\n * Shows a question dialog with `Ok` and `Cancel` buttons.\n *\n * Convenient wrapper for `await message('msg', { buttons: 'OkCancel' }) === 'Ok'`\n *\n * @example\n * ```typescript\n * import { confirm } from '@tauri-apps/plugin-dialog';\n * const confirmed = await confirm('Are you sure?', 'Tauri');\n * const confirmed2 = await confirm('This action cannot be reverted. Are you sure?', { title: 'Tauri', kind: 'warning' });\n * ```\n *\n * @param message The message to show.\n * @param options The dialog's options. If a string, it represents the dialog title.\n *\n * @returns A promise resolving to a boolean indicating whether `Ok` was clicked or not.\n *\n * @since 2.0.0\n */\nasync function confirm(message, options) {\n const opts = typeof options === 'string' ? { title: options } : options;\n const customButtons = opts?.okLabel || opts?.cancelLabel;\n const okLabel = opts?.okLabel ?? 'Ok';\n return ((await messageCommand(message, {\n title: opts?.title,\n kind: opts?.kind,\n buttons: customButtons\n ? { ok: okLabel, cancel: opts.cancelLabel ?? 'Cancel' }\n : 'OkCancel'\n })) === okLabel);\n}\n\nexport { ask, confirm, message, open, save };\n"],"names":["open","options","invoke"],"mappings":"4CAgFA,eAAeA,EAAKC,EAAU,GAAI,CAC9B,OAAI,OAAOA,GAAY,UACnB,OAAO,OAAOA,CAAO,EAElB,MAAMC,EAAO,qBAAsB,CAAE,QAAAD,CAAO,CAAE,CACzD","x_google_ignoreList":[0]}
@@ -0,0 +1 @@
1
+ *,:before,:after{--tw-border-spacing-x: 0;--tw-border-spacing-y: 0;--tw-translate-x: 0;--tw-translate-y: 0;--tw-rotate: 0;--tw-skew-x: 0;--tw-skew-y: 0;--tw-scale-x: 1;--tw-scale-y: 1;--tw-pan-x: ;--tw-pan-y: ;--tw-pinch-zoom: ;--tw-scroll-snap-strictness: proximity;--tw-gradient-from-position: ;--tw-gradient-via-position: ;--tw-gradient-to-position: ;--tw-ordinal: ;--tw-slashed-zero: ;--tw-numeric-figure: ;--tw-numeric-spacing: ;--tw-numeric-fraction: ;--tw-ring-inset: ;--tw-ring-offset-width: 0px;--tw-ring-offset-color: #fff;--tw-ring-color: rgb(59 130 246 / .5);--tw-ring-offset-shadow: 0 0 #0000;--tw-ring-shadow: 0 0 #0000;--tw-shadow: 0 0 #0000;--tw-shadow-colored: 0 0 #0000;--tw-blur: ;--tw-brightness: ;--tw-contrast: ;--tw-grayscale: ;--tw-hue-rotate: ;--tw-invert: ;--tw-saturate: ;--tw-sepia: ;--tw-drop-shadow: ;--tw-backdrop-blur: ;--tw-backdrop-brightness: ;--tw-backdrop-contrast: ;--tw-backdrop-grayscale: ;--tw-backdrop-hue-rotate: ;--tw-backdrop-invert: ;--tw-backdrop-opacity: ;--tw-backdrop-saturate: ;--tw-backdrop-sepia: ;--tw-contain-size: ;--tw-contain-layout: ;--tw-contain-paint: ;--tw-contain-style: }::backdrop{--tw-border-spacing-x: 0;--tw-border-spacing-y: 0;--tw-translate-x: 0;--tw-translate-y: 0;--tw-rotate: 0;--tw-skew-x: 0;--tw-skew-y: 0;--tw-scale-x: 1;--tw-scale-y: 1;--tw-pan-x: ;--tw-pan-y: ;--tw-pinch-zoom: ;--tw-scroll-snap-strictness: proximity;--tw-gradient-from-position: ;--tw-gradient-via-position: ;--tw-gradient-to-position: ;--tw-ordinal: ;--tw-slashed-zero: ;--tw-numeric-figure: ;--tw-numeric-spacing: ;--tw-numeric-fraction: ;--tw-ring-inset: ;--tw-ring-offset-width: 0px;--tw-ring-offset-color: #fff;--tw-ring-color: rgb(59 130 246 / .5);--tw-ring-offset-shadow: 0 0 #0000;--tw-ring-shadow: 0 0 #0000;--tw-shadow: 0 0 #0000;--tw-shadow-colored: 0 0 #0000;--tw-blur: ;--tw-brightness: ;--tw-contrast: ;--tw-grayscale: ;--tw-hue-rotate: ;--tw-invert: ;--tw-saturate: ;--tw-sepia: ;--tw-drop-shadow: ;--tw-backdrop-blur: ;--tw-backdrop-brightness: ;--tw-backdrop-contrast: ;--tw-backdrop-grayscale: ;--tw-backdrop-hue-rotate: ;--tw-backdrop-invert: ;--tw-backdrop-opacity: ;--tw-backdrop-saturate: ;--tw-backdrop-sepia: ;--tw-contain-size: ;--tw-contain-layout: ;--tw-contain-paint: ;--tw-contain-style: }*,:before,:after{box-sizing:border-box;border-width:0;border-style:solid;border-color:#e5e7eb}:before,:after{--tw-content: ""}html,:host{line-height:1.5;-webkit-text-size-adjust:100%;-moz-tab-size:4;-o-tab-size:4;tab-size:4;font-family:Inter,system-ui,-apple-system,BlinkMacSystemFont,Segoe UI,sans-serif;font-feature-settings:normal;font-variation-settings:normal;-webkit-tap-highlight-color:transparent}body{margin:0;line-height:inherit}hr{height:0;color:inherit;border-top-width:1px}abbr:where([title]){-webkit-text-decoration:underline dotted;text-decoration:underline dotted}h1,h2,h3,h4,h5,h6{font-size:inherit;font-weight:inherit}a{color:inherit;text-decoration:inherit}b,strong{font-weight:bolder}code,kbd,samp,pre{font-family:JetBrains Mono,ui-monospace,monospace;font-feature-settings:normal;font-variation-settings:normal;font-size:1em}small{font-size:80%}sub,sup{font-size:75%;line-height:0;position:relative;vertical-align:baseline}sub{bottom:-.25em}sup{top:-.5em}table{text-indent:0;border-color:inherit;border-collapse:collapse}button,input,optgroup,select,textarea{font-family:inherit;font-feature-settings:inherit;font-variation-settings:inherit;font-size:100%;font-weight:inherit;line-height:inherit;letter-spacing:inherit;color:inherit;margin:0;padding:0}button,select{text-transform:none}button,input:where([type=button]),input:where([type=reset]),input:where([type=submit]){-webkit-appearance:button;background-color:transparent;background-image:none}:-moz-focusring{outline:auto}:-moz-ui-invalid{box-shadow:none}progress{vertical-align:baseline}::-webkit-inner-spin-button,::-webkit-outer-spin-button{height:auto}[type=search]{-webkit-appearance:textfield;outline-offset:-2px}::-webkit-search-decoration{-webkit-appearance:none}::-webkit-file-upload-button{-webkit-appearance:button;font:inherit}summary{display:list-item}blockquote,dl,dd,h1,h2,h3,h4,h5,h6,hr,figure,p,pre{margin:0}fieldset{margin:0;padding:0}legend{padding:0}ol,ul,menu{list-style:none;margin:0;padding:0}dialog{padding:0}textarea{resize:vertical}input::-moz-placeholder,textarea::-moz-placeholder{opacity:1;color:#9ca3af}input::placeholder,textarea::placeholder{opacity:1;color:#9ca3af}button,[role=button]{cursor:pointer}:disabled{cursor:default}img,svg,video,canvas,audio,iframe,embed,object{display:block;vertical-align:middle}img,video{max-width:100%;height:auto}[hidden]:where(:not([hidden=until-found])){display:none}:root{font-family:Inter,system-ui,sans-serif;color-scheme:dark}html,body,#root{height:100%}body{background:radial-gradient(1200px 800px at 0% 0%,rgba(34,211,238,.06),transparent 60%),radial-gradient(1000px 700px at 100% 100%,rgba(167,139,250,.05),transparent 60%),#0b0e14}.container{width:100%}@media (min-width: 640px){.container{max-width:640px}}@media (min-width: 768px){.container{max-width:768px}}@media (min-width: 1024px){.container{max-width:1024px}}@media (min-width: 1280px){.container{max-width:1280px}}@media (min-width: 1536px){.container{max-width:1536px}}.pointer-events-none{pointer-events:none}.visible{visibility:visible}.invisible{visibility:hidden}.fixed{position:fixed}.absolute{position:absolute}.relative{position:relative}.inset-0{inset:0}.bottom-4{bottom:1rem}.left-6{left:1.5rem}.right-0{right:0}.top-0{top:0}.top-4{top:1rem}.isolate{isolation:isolate}.z-10{z-index:10}.z-20{z-index:20}.z-30{z-index:30}.z-40{z-index:40}.z-50{z-index:50}.col-span-2{grid-column:span 2 / span 2}.row-start-1{grid-row-start:1}.row-start-2{grid-row-start:2}.m-3{margin:.75rem}.m-5{margin:1.25rem}.m-6{margin:1.5rem}.mb-1{margin-bottom:.25rem}.mb-1\.5{margin-bottom:.375rem}.mb-2{margin-bottom:.5rem}.mb-3{margin-bottom:.75rem}.mb-4{margin-bottom:1rem}.mb-5{margin-bottom:1.25rem}.mb-6{margin-bottom:1.5rem}.ml-2{margin-left:.5rem}.ml-auto{margin-left:auto}.mt-0\.5{margin-top:.125rem}.mt-1{margin-top:.25rem}.mt-1\.5{margin-top:.375rem}.mt-2{margin-top:.5rem}.mt-3{margin-top:.75rem}.mt-4{margin-top:1rem}.mt-5{margin-top:1.25rem}.mt-auto{margin-top:auto}.line-clamp-2{overflow:hidden;display:-webkit-box;-webkit-box-orient:vertical;-webkit-line-clamp:2}.block{display:block}.inline-block{display:inline-block}.inline{display:inline}.flex{display:flex}.inline-flex{display:inline-flex}.table{display:table}.grid{display:grid}.contents{display:contents}.hidden{display:none}.h-1{height:.25rem}.h-1\.5{height:.375rem}.h-2{height:.5rem}.h-2\.5{height:.625rem}.h-4{height:1rem}.h-6{height:1.5rem}.h-7{height:1.75rem}.h-\[70vh\]{height:70vh}.h-\[calc\(100vh-44px-3rem\)\]{height:calc(100vh - 44px - 3rem)}.h-full{height:100%}.max-h-\[85vh\]{max-height:85vh}.max-h-\[90vh\]{max-height:90vh}.min-h-screen{min-height:100vh}.w-2{width:.5rem}.w-2\.5{width:.625rem}.w-4{width:1rem}.w-6{width:1.5rem}.w-7{width:1.75rem}.w-72{width:18rem}.w-\[360px\]{width:360px}.w-\[420px\]{width:420px}.w-\[min\(720px\,92vw\)\]{width:min(720px,92vw)}.w-\[min\(900px\,90vw\)\]{width:min(900px,90vw)}.w-full{width:100%}.min-w-0{min-width:0px}.max-w-2xl{max-width:42rem}.max-w-3xl{max-width:48rem}.max-w-5xl{max-width:64rem}.max-w-\[200px\]{max-width:200px}.max-w-\[260px\]{max-width:260px}.max-w-md{max-width:28rem}.max-w-sm{max-width:24rem}.flex-1{flex:1 1 0%}.shrink-0{flex-shrink:0}@keyframes pulseSoft{0%,to{opacity:.85}50%{opacity:1}}.animate-pulse-soft{animation:pulseSoft 2.4s ease-in-out infinite}@keyframes riverIn{0%{opacity:0;transform:translateY(8px)}to{opacity:1;transform:translateY(0)}}.animate-river-in{animation:riverIn .32s ease-out both}@keyframes viewIn{0%{opacity:0;transform:translateY(4px)}to{opacity:1;transform:translateY(0)}}.animate-view-in{animation:viewIn .24s ease-out both}.cursor-default{cursor:default}.resize-none{resize:none}.resize-y{resize:vertical}.resize{resize:both}.list-decimal{list-style-type:decimal}.grid-cols-2{grid-template-columns:repeat(2,minmax(0,1fr))}.grid-cols-\[100px_1fr\]{grid-template-columns:100px 1fr}.grid-cols-\[110px_1fr\]{grid-template-columns:110px 1fr}.grid-cols-\[140px_1fr\]{grid-template-columns:140px 1fr}.grid-cols-\[160px_1fr\]{grid-template-columns:160px 1fr}.grid-cols-\[200px_1fr\]{grid-template-columns:200px 1fr}.grid-cols-\[260px_1fr\]{grid-template-columns:260px 1fr}.grid-cols-\[320px_1fr\]{grid-template-columns:320px 1fr}.grid-cols-\[360px_1fr\]{grid-template-columns:360px 1fr}.grid-rows-\[44px_1fr\]{grid-template-rows:44px 1fr}.flex-col{flex-direction:column}.flex-wrap{flex-wrap:wrap}.items-start{align-items:flex-start}.items-center{align-items:center}.items-baseline{align-items:baseline}.justify-end{justify-content:flex-end}.justify-center{justify-content:center}.justify-between{justify-content:space-between}.gap-0\.5{gap:.125rem}.gap-1{gap:.25rem}.gap-1\.5{gap:.375rem}.gap-2{gap:.5rem}.gap-3{gap:.75rem}.gap-4{gap:1rem}.gap-x-3{-moz-column-gap:.75rem;column-gap:.75rem}.gap-y-0\.5{row-gap:.125rem}.gap-y-1{row-gap:.25rem}.gap-y-1\.5{row-gap:.375rem}.gap-y-2{row-gap:.5rem}.space-y-1>:not([hidden])~:not([hidden]){--tw-space-y-reverse: 0;margin-top:calc(.25rem * calc(1 - var(--tw-space-y-reverse)));margin-bottom:calc(.25rem * var(--tw-space-y-reverse))}.space-y-2>:not([hidden])~:not([hidden]){--tw-space-y-reverse: 0;margin-top:calc(.5rem * calc(1 - var(--tw-space-y-reverse)));margin-bottom:calc(.5rem * var(--tw-space-y-reverse))}.space-y-5>:not([hidden])~:not([hidden]){--tw-space-y-reverse: 0;margin-top:calc(1.25rem * calc(1 - var(--tw-space-y-reverse)));margin-bottom:calc(1.25rem * var(--tw-space-y-reverse))}.divide-y>:not([hidden])~:not([hidden]){--tw-divide-y-reverse: 0;border-top-width:calc(1px * calc(1 - var(--tw-divide-y-reverse)));border-bottom-width:calc(1px * var(--tw-divide-y-reverse))}.divide-line>:not([hidden])~:not([hidden]){--tw-divide-opacity: 1;border-color:rgb(31 38 51 / var(--tw-divide-opacity, 1))}.overflow-auto{overflow:auto}.overflow-hidden{overflow:hidden}.overflow-x-auto{overflow-x:auto}.overflow-y-auto{overflow-y:auto}.truncate{overflow:hidden;text-overflow:ellipsis;white-space:nowrap}.whitespace-pre-wrap{white-space:pre-wrap}.break-words{overflow-wrap:break-word}.break-all{word-break:break-all}.rounded{border-radius:.25rem}.rounded-full{border-radius:9999px}.rounded-lg{border-radius:.5rem}.rounded-md{border-radius:.375rem}.rounded-xl{border-radius:.75rem}.border{border-width:1px}.border-b{border-bottom-width:1px}.border-l{border-left-width:1px}.border-r{border-right-width:1px}.border-t{border-top-width:1px}.border-dashed{border-style:dashed}.border-amber-400\/30{border-color:#fbbf244d}.border-amber-500\/30{border-color:#f59e0b4d}.border-cyan-400\/20{border-color:#22d3ee33}.border-cyan-400\/30{border-color:#22d3ee4d}.border-cyan-400\/40{border-color:#22d3ee66}.border-cyan-400\/50{border-color:#22d3ee80}.border-emerald-400\/30{border-color:#34d3994d}.border-emerald-500\/30{border-color:#10b9814d}.border-line{--tw-border-opacity: 1;border-color:rgb(31 38 51 / var(--tw-border-opacity, 1))}.border-line\/50{border-color:#1f263380}.border-line\/60{border-color:#1f263399}.border-red-400\/30{border-color:#f871714d}.border-red-500\/30{border-color:#ef44444d}.border-rose-400\/30{border-color:#fb71854d}.border-rose-500\/30{border-color:#f43f5e4d}.border-violet-400\/30{border-color:#a78bfa4d}.bg-amber-400\/10{background-color:#fbbf241a}.bg-amber-500\/10{background-color:#f59e0b1a}.bg-black\/60{background-color:#0009}.bg-canvas{--tw-bg-opacity: 1;background-color:rgb(11 14 20 / var(--tw-bg-opacity, 1))}.bg-canvas\/40{background-color:#0b0e1466}.bg-canvas\/60{background-color:#0b0e1499}.bg-cyan-400{--tw-bg-opacity: 1;background-color:rgb(34 211 238 / var(--tw-bg-opacity, 1))}.bg-cyan-400\/10{background-color:#22d3ee1a}.bg-cyan-400\/15{background-color:#22d3ee26}.bg-cyan-400\/20{background-color:#22d3ee33}.bg-cyan-400\/5{background-color:#22d3ee0d}.bg-cyan-500\/15{background-color:#06b6d426}.bg-cyan-500\/20{background-color:#06b6d433}.bg-emerald-400{--tw-bg-opacity: 1;background-color:rgb(52 211 153 / var(--tw-bg-opacity, 1))}.bg-emerald-500\/10{background-color:#10b9811a}.bg-line{--tw-bg-opacity: 1;background-color:rgb(31 38 51 / var(--tw-bg-opacity, 1))}.bg-panel{--tw-bg-opacity: 1;background-color:rgb(16 20 28 / var(--tw-bg-opacity, 1))}.bg-panel\/30{background-color:#10141c4d}.bg-panel\/40{background-color:#10141c66}.bg-panel\/60{background-color:#10141c99}.bg-panel\/80{background-color:#10141ccc}.bg-panel\/95{background-color:#10141cf2}.bg-panelHi{--tw-bg-opacity: 1;background-color:rgb(22 27 38 / var(--tw-bg-opacity, 1))}.bg-panelHi\/40{background-color:#161b2666}.bg-red-400\/10{background-color:#f871711a}.bg-red-500\/10{background-color:#ef44441a}.bg-rose-400\/10{background-color:#fb71851a}.bg-rose-500\/10{background-color:#f43f5e1a}.bg-sky-400\/10{background-color:#38bdf81a}.bg-slate-400\/10{background-color:#94a3b81a}.bg-slate-700\/40{background-color:#33415566}.bg-slate-800{--tw-bg-opacity: 1;background-color:rgb(30 41 59 / var(--tw-bg-opacity, 1))}.bg-slate-900\/60{background-color:#0f172a99}.bg-slate-950{--tw-bg-opacity: 1;background-color:rgb(2 6 23 / var(--tw-bg-opacity, 1))}.bg-violet-400{--tw-bg-opacity: 1;background-color:rgb(167 139 250 / var(--tw-bg-opacity, 1))}.bg-violet-400\/10{background-color:#a78bfa1a}.bg-violet-500\/20{background-color:#8b5cf633}.bg-gradient-to-r{background-image:linear-gradient(to right,var(--tw-gradient-stops))}.from-cyan-400{--tw-gradient-from: #22d3ee var(--tw-gradient-from-position);--tw-gradient-to: rgb(34 211 238 / 0) var(--tw-gradient-to-position);--tw-gradient-stops: var(--tw-gradient-from), var(--tw-gradient-to)}.to-violet-400{--tw-gradient-to: #a78bfa var(--tw-gradient-to-position)}.p-1{padding:.25rem}.p-2\.5{padding:.625rem}.p-3{padding:.75rem}.p-4{padding:1rem}.px-1{padding-left:.25rem;padding-right:.25rem}.px-1\.5{padding-left:.375rem;padding-right:.375rem}.px-2{padding-left:.5rem;padding-right:.5rem}.px-2\.5{padding-left:.625rem;padding-right:.625rem}.px-3{padding-left:.75rem;padding-right:.75rem}.px-4{padding-left:1rem;padding-right:1rem}.px-5{padding-left:1.25rem;padding-right:1.25rem}.px-6{padding-left:1.5rem;padding-right:1.5rem}.px-8{padding-left:2rem;padding-right:2rem}.py-0\.5{padding-top:.125rem;padding-bottom:.125rem}.py-1{padding-top:.25rem;padding-bottom:.25rem}.py-1\.5{padding-top:.375rem;padding-bottom:.375rem}.py-2{padding-top:.5rem;padding-bottom:.5rem}.py-2\.5{padding-top:.625rem;padding-bottom:.625rem}.py-3{padding-top:.75rem;padding-bottom:.75rem}.py-4{padding-top:1rem;padding-bottom:1rem}.py-6{padding-top:1.5rem;padding-bottom:1.5rem}.pl-5{padding-left:1.25rem}.pl-9{padding-left:2.25rem}.pt-2{padding-top:.5rem}.pt-3{padding-top:.75rem}.text-left{text-align:left}.text-center{text-align:center}.font-mono{font-family:JetBrains Mono,ui-monospace,monospace}.font-sans{font-family:Inter,system-ui,-apple-system,BlinkMacSystemFont,Segoe UI,sans-serif}.text-2xl{font-size:1.5rem;line-height:2rem}.text-\[10px\]{font-size:10px}.text-\[11px\]{font-size:11px}.text-\[12px\]{font-size:12px}.text-\[9px\]{font-size:9px}.text-base{font-size:1rem;line-height:1.5rem}.text-lg{font-size:1.125rem;line-height:1.75rem}.text-sm{font-size:.875rem;line-height:1.25rem}.text-xl{font-size:1.25rem;line-height:1.75rem}.text-xs{font-size:.75rem;line-height:1rem}.font-medium{font-weight:500}.font-semibold{font-weight:600}.uppercase{text-transform:uppercase}.capitalize{text-transform:capitalize}.normal-case{text-transform:none}.not-italic{font-style:normal}.leading-relaxed{line-height:1.625}.leading-snug{line-height:1.375}.tracking-normal{letter-spacing:0em}.tracking-wide{letter-spacing:.025em}.tracking-wider{letter-spacing:.05em}.tracking-widest{letter-spacing:.1em}.text-amber-200{--tw-text-opacity: 1;color:rgb(253 230 138 / var(--tw-text-opacity, 1))}.text-amber-300{--tw-text-opacity: 1;color:rgb(252 211 77 / var(--tw-text-opacity, 1))}.text-amber-400\/90{color:#fbbf24e6}.text-cyan-100{--tw-text-opacity: 1;color:rgb(207 250 254 / var(--tw-text-opacity, 1))}.text-cyan-200{--tw-text-opacity: 1;color:rgb(165 243 252 / var(--tw-text-opacity, 1))}.text-cyan-200\/70{color:#a5f3fcb3}.text-cyan-300{--tw-text-opacity: 1;color:rgb(103 232 249 / var(--tw-text-opacity, 1))}.text-cyan-300\/80{color:#67e8f9cc}.text-emerald-200{--tw-text-opacity: 1;color:rgb(167 243 208 / var(--tw-text-opacity, 1))}.text-emerald-300{--tw-text-opacity: 1;color:rgb(110 231 183 / var(--tw-text-opacity, 1))}.text-red-200{--tw-text-opacity: 1;color:rgb(254 202 202 / var(--tw-text-opacity, 1))}.text-red-300{--tw-text-opacity: 1;color:rgb(252 165 165 / var(--tw-text-opacity, 1))}.text-rose-200{--tw-text-opacity: 1;color:rgb(254 205 211 / var(--tw-text-opacity, 1))}.text-rose-300{--tw-text-opacity: 1;color:rgb(253 164 175 / var(--tw-text-opacity, 1))}.text-sky-300{--tw-text-opacity: 1;color:rgb(125 211 252 / var(--tw-text-opacity, 1))}.text-slate-100{--tw-text-opacity: 1;color:rgb(241 245 249 / var(--tw-text-opacity, 1))}.text-slate-200{--tw-text-opacity: 1;color:rgb(226 232 240 / var(--tw-text-opacity, 1))}.text-slate-300{--tw-text-opacity: 1;color:rgb(203 213 225 / var(--tw-text-opacity, 1))}.text-slate-400{--tw-text-opacity: 1;color:rgb(148 163 184 / var(--tw-text-opacity, 1))}.text-slate-500{--tw-text-opacity: 1;color:rgb(100 116 139 / var(--tw-text-opacity, 1))}.text-slate-600{--tw-text-opacity: 1;color:rgb(71 85 105 / var(--tw-text-opacity, 1))}.text-violet-200{--tw-text-opacity: 1;color:rgb(221 214 254 / var(--tw-text-opacity, 1))}.text-violet-300{--tw-text-opacity: 1;color:rgb(196 181 253 / var(--tw-text-opacity, 1))}.underline{text-decoration-line:underline}.line-through{text-decoration-line:line-through}.decoration-slate-600\/50{text-decoration-color:#47556980}.antialiased{-webkit-font-smoothing:antialiased;-moz-osx-font-smoothing:grayscale}.opacity-50{opacity:.5}.opacity-70{opacity:.7}.opacity-90{opacity:.9}.shadow-2xl{--tw-shadow: 0 25px 50px -12px rgb(0 0 0 / .25);--tw-shadow-colored: 0 25px 50px -12px var(--tw-shadow-color);box-shadow:var(--tw-ring-offset-shadow, 0 0 #0000),var(--tw-ring-shadow, 0 0 #0000),var(--tw-shadow)}.shadow-xl{--tw-shadow: 0 20px 25px -5px rgb(0 0 0 / .1), 0 8px 10px -6px rgb(0 0 0 / .1);--tw-shadow-colored: 0 20px 25px -5px var(--tw-shadow-color), 0 8px 10px -6px var(--tw-shadow-color);box-shadow:var(--tw-ring-offset-shadow, 0 0 #0000),var(--tw-ring-shadow, 0 0 #0000),var(--tw-shadow)}.outline-none{outline:2px solid transparent;outline-offset:2px}.ring{--tw-ring-offset-shadow: var(--tw-ring-inset) 0 0 0 var(--tw-ring-offset-width) var(--tw-ring-offset-color);--tw-ring-shadow: var(--tw-ring-inset) 0 0 0 calc(3px + var(--tw-ring-offset-width)) var(--tw-ring-color);box-shadow:var(--tw-ring-offset-shadow),var(--tw-ring-shadow),var(--tw-shadow, 0 0 #0000)}.ring-1{--tw-ring-offset-shadow: var(--tw-ring-inset) 0 0 0 var(--tw-ring-offset-width) var(--tw-ring-offset-color);--tw-ring-shadow: var(--tw-ring-inset) 0 0 0 calc(1px + var(--tw-ring-offset-width)) var(--tw-ring-color);box-shadow:var(--tw-ring-offset-shadow),var(--tw-ring-shadow),var(--tw-shadow, 0 0 #0000)}.ring-amber-400\/30{--tw-ring-color: rgb(251 191 36 / .3)}.ring-amber-400\/40{--tw-ring-color: rgb(251 191 36 / .4)}.ring-cyan-400\/20{--tw-ring-color: rgb(34 211 238 / .2)}.ring-cyan-400\/30{--tw-ring-color: rgb(34 211 238 / .3)}.ring-emerald-400\/30{--tw-ring-color: rgb(52 211 153 / .3)}.ring-emerald-400\/40{--tw-ring-color: rgb(52 211 153 / .4)}.ring-line{--tw-ring-opacity: 1;--tw-ring-color: rgb(31 38 51 / var(--tw-ring-opacity, 1))}.ring-rose-400\/30{--tw-ring-color: rgb(251 113 133 / .3)}.ring-rose-400\/40{--tw-ring-color: rgb(251 113 133 / .4)}.ring-sky-400\/30{--tw-ring-color: rgb(56 189 248 / .3)}.ring-slate-400\/30{--tw-ring-color: rgb(148 163 184 / .3)}.ring-slate-500\/30{--tw-ring-color: rgb(100 116 139 / .3)}.ring-violet-400\/20{--tw-ring-color: rgb(167 139 250 / .2)}.ring-violet-400\/30{--tw-ring-color: rgb(167 139 250 / .3)}.ring-violet-400\/40{--tw-ring-color: rgb(167 139 250 / .4)}.\!filter{filter:var(--tw-blur) var(--tw-brightness) var(--tw-contrast) var(--tw-grayscale) var(--tw-hue-rotate) var(--tw-invert) var(--tw-saturate) var(--tw-sepia) var(--tw-drop-shadow)!important}.filter{filter:var(--tw-blur) var(--tw-brightness) var(--tw-contrast) var(--tw-grayscale) var(--tw-hue-rotate) var(--tw-invert) var(--tw-saturate) var(--tw-sepia) var(--tw-drop-shadow)}.backdrop-blur{--tw-backdrop-blur: blur(8px);backdrop-filter:var(--tw-backdrop-blur) var(--tw-backdrop-brightness) var(--tw-backdrop-contrast) var(--tw-backdrop-grayscale) var(--tw-backdrop-hue-rotate) var(--tw-backdrop-invert) var(--tw-backdrop-opacity) var(--tw-backdrop-saturate) var(--tw-backdrop-sepia)}.backdrop-blur-sm{--tw-backdrop-blur: blur(4px);backdrop-filter:var(--tw-backdrop-blur) var(--tw-backdrop-brightness) var(--tw-backdrop-contrast) var(--tw-backdrop-grayscale) var(--tw-backdrop-hue-rotate) var(--tw-backdrop-invert) var(--tw-backdrop-opacity) var(--tw-backdrop-saturate) var(--tw-backdrop-sepia)}.transition{transition-property:color,background-color,border-color,text-decoration-color,fill,stroke,opacity,box-shadow,transform,filter,backdrop-filter;transition-timing-function:cubic-bezier(.4,0,.2,1);transition-duration:.15s}.transition-all{transition-property:all;transition-timing-function:cubic-bezier(.4,0,.2,1);transition-duration:.15s}.duration-300{transition-duration:.3s}.glass{background:linear-gradient(180deg,#161b26b3,#10141cb3);backdrop-filter:blur(8px);border:1px solid rgba(31,38,51,.8)}.scrollbar-thin{scrollbar-width:thin}.scrollbar-thin::-webkit-scrollbar{width:8px}.scrollbar-thin::-webkit-scrollbar-thumb{background:#94a3b82e;border-radius:4px}.placeholder\:text-slate-600::-moz-placeholder{--tw-text-opacity: 1;color:rgb(71 85 105 / var(--tw-text-opacity, 1))}.placeholder\:text-slate-600::placeholder{--tw-text-opacity: 1;color:rgb(71 85 105 / var(--tw-text-opacity, 1))}.last\:border-b-0:last-child{border-bottom-width:0px}.hover\:bg-amber-400\/10:hover{background-color:#fbbf241a}.hover\:bg-cyan-400\/20:hover{background-color:#22d3ee33}.hover\:bg-cyan-400\/25:hover{background-color:#22d3ee40}.hover\:bg-cyan-500\/25:hover{background-color:#06b6d440}.hover\:bg-cyan-500\/30:hover{background-color:#06b6d44d}.hover\:bg-emerald-400\/10:hover{background-color:#34d3991a}.hover\:bg-panel:hover{--tw-bg-opacity: 1;background-color:rgb(16 20 28 / var(--tw-bg-opacity, 1))}.hover\:bg-panelHi:hover{--tw-bg-opacity: 1;background-color:rgb(22 27 38 / var(--tw-bg-opacity, 1))}.hover\:bg-panelHi\/40:hover{background-color:#161b2666}.hover\:bg-panelHi\/50:hover{background-color:#161b2680}.hover\:bg-panelHi\/60:hover{background-color:#161b2699}.hover\:bg-red-400\/20:hover{background-color:#f8717133}.hover\:bg-rose-400\/10:hover{background-color:#fb71851a}.hover\:bg-rose-400\/20:hover{background-color:#fb718533}.hover\:bg-violet-400\/20:hover{background-color:#a78bfa33}.hover\:bg-violet-500\/30:hover{background-color:#8b5cf64d}.hover\:text-amber-100:hover{--tw-text-opacity: 1;color:rgb(254 243 199 / var(--tw-text-opacity, 1))}.hover\:text-cyan-200:hover{--tw-text-opacity: 1;color:rgb(165 243 252 / var(--tw-text-opacity, 1))}.hover\:text-rose-300:hover{--tw-text-opacity: 1;color:rgb(253 164 175 / var(--tw-text-opacity, 1))}.hover\:text-slate-100:hover{--tw-text-opacity: 1;color:rgb(241 245 249 / var(--tw-text-opacity, 1))}.hover\:text-slate-200:hover{--tw-text-opacity: 1;color:rgb(226 232 240 / var(--tw-text-opacity, 1))}.hover\:underline:hover{text-decoration-line:underline}.hover\:ring-rose-400\/30:hover{--tw-ring-color: rgb(251 113 133 / .3)}.hover\:ring-rose-400\/40:hover{--tw-ring-color: rgb(251 113 133 / .4)}.hover\:brightness-125:hover{--tw-brightness: brightness(1.25);filter:var(--tw-blur) var(--tw-brightness) var(--tw-contrast) var(--tw-grayscale) var(--tw-hue-rotate) var(--tw-invert) var(--tw-saturate) var(--tw-sepia) var(--tw-drop-shadow)}.focus\:border-cyan-400\/40:focus{border-color:#22d3ee66}.focus\:border-cyan-400\/50:focus{border-color:#22d3ee80}.focus\:outline-none:focus{outline:2px solid transparent;outline-offset:2px}.enabled\:hover\:bg-cyan-400\/20:hover:enabled{background-color:#22d3ee33}.disabled\:cursor-not-allowed:disabled{cursor:not-allowed}.disabled\:opacity-40:disabled{opacity:.4}.disabled\:opacity-50:disabled{opacity:.5}@media (min-width: 640px){.sm\:grid-cols-2{grid-template-columns:repeat(2,minmax(0,1fr))}}