npm package discovery and stats viewer.

Discover Tips

  • General search

    [free text search, go nuts!]

  • Package details

    pkg:[package-name]

  • User packages

    @[username]

Sponsor

Optimize Toolset

I’ve always been into building performant and accessible sites, but lately I’ve been taking it extremely seriously. So much so that I’ve been building a tool to help me optimize and monitor the sites that I build to make sure that I’m making an attempt to offer the best experience to those who visit them. If you’re into performant, accessible and SEO friendly sites, you might like it too! You can check it out at Optimize Toolset.

About

Hi, 👋, I’m Ryan Hefner  and I built this site for me, and you! The goal of this site was to provide an easy way for me to check the stats on my npm packages, both for prioritizing issues and updates, and to give me a little kick in the pants to keep up on stuff.

As I was building it, I realized that I was actually using the tool to build the tool, and figured I might as well put this out there and hopefully others will find it to be a fast and useful way to search and browse npm packages as I have.

If you’re interested in other things I’m working on, follow me on Twitter or check out the open source projects I’ve been publishing on GitHub.

I am also working on a Twitter bot for this site to tweet the most popular, newest, random packages from npm. Please follow that account now and it will start sending out packages soon–ish.

Open Software & Tools

This site wouldn’t be possible without the immense generosity and tireless efforts from the people who make contributions to the world and share their work via open source initiatives. Thank you 🙏

© 2026 – Pkg Stats / Ryan Hefner

@enclosurejs/platform-tauri

v1.1.0

Published

> [!IMPORTANT] > This package bridges `@enclosurejs/core` to Tauri v2. It provides `TauriBackend` (the `BackendAdapter`), and concrete implementations for all 26 capability contracts using `@tauri-apps/api` and `@tauri-apps/plugin-*`. Your application cod

Readme

@enclosurejs/platform-tauri — Tauri v2 Backend + 26 Capability Implementations

[!IMPORTANT] This package bridges @enclosurejs/core to Tauri v2. It provides TauriBackend (the BackendAdapter), and concrete implementations for all 26 capability contracts using @tauri-apps/api and @tauri-apps/plugin-*. Your application code never imports this package directly — it consumes capability tokens from @enclosurejs/core.

The Problem

Tauri v2 exposes native functionality through a combination of @tauri-apps/api/core.invoke() for Rust commands and ~15 official plugins (plugin-fs, plugin-shell, plugin-dialog, etc.), each with its own API surface. Wiring 26 capabilities to these plugins by hand means scattered imports, inconsistent error handling, and callsites tightly coupled to Tauri's API. If you later want to switch to Electron, every invoke() and plugin import must be rewritten.

@enclosurejs/platform-tauri solves this by mapping every @enclosurejs/core capability token to a Tauri implementation behind a single registration call. Application code talks to abstract interfaces via DI; switching to Electron means swapping the import — zero changes to business logic.

Architecture

┌──────────────── Webview (JS) ─────────────────────────┐
│                                                        │
│  App code → context.use(FileSystemToken)               │
│               │                                        │
│  TauriFileSystem.readTextFile(path)                    │
│               │                                        │
│  @tauri-apps/plugin-fs → readTextFile(path)            │
│               │ (JS → Rust IPC)                        │
└───────────────┼────────────────────────────────────────┘
                │ invoke / plugin bridge
┌───────────────┼──── Rust Core ─────────────────────────┐
│               │                                        │
│  Tauri command handler / plugin implementation         │
│    → std::fs::read_to_string(path)                    │
│                                                        │
└────────────────────────────────────────────────────────┘

Two layers, each with a single responsibility:

| Layer | Package | Runs in | Responsibility | | --------------- | --------------------------- | -------------- | ------------------------------------------------------------------ | | Rust Core | Tauri + official plugins | Native process | Command handlers, OS-level APIs, security permissions | | JS Services | @enclosurejs/platform-tauri | Webview (JS) | TauriBackend + 26 service classes that call plugin APIs / invoke |

How It Works

  1. Rust side — the Tauri app registers plugins in Cargo.toml and main.rs (e.g., tauri_plugin_fs, tauri_plugin_shell). Each plugin exposes Rust commands that the JS layer can call via IPC.

  2. JS sideTauriBackend wraps @tauri-apps/api/core.invoke() and @tauri-apps/api/event.listen() to implement BackendAdapter. Each Tauri* service class wraps the corresponding @tauri-apps/plugin-* package.

  3. RegistrationregisterTauriCapabilities(ctx) binds all 26 service classes to DI tokens in a single call.

  4. Application code calls context.use(ShellToken) and gets a ShellService interface. Replace TauriBackend with ElectronBackend and every service swaps automatically.

Quick Start

1. Rust setup (src-tauri/)

Enable the plugins you need in Cargo.toml and register them in main.rs:

fn main() {
    tauri::Builder::default()
        .plugin(tauri_plugin_fs::init())
        .plugin(tauri_plugin_shell::init())
        .plugin(tauri_plugin_dialog::init())
        // ... other plugins
        .run(tauri::generate_context!())
        .expect("error running tauri app");
}

2. Frontend (app.ts)

import { createApp, FileSystemToken } from '@enclosurejs/core';
import { TauriBackend, registerTauriCapabilities } from '@enclosurejs/platform-tauri';

const app = createApp({
    backend: new TauriBackend(),
    frontend: {
        mount({ container, context }) {
            const fs = context.use(FileSystemToken);
            fs.readTextFile('/etc/hostname').then((text) => {
                container.textContent = text;
            });
        },
    },
    container: document.getElementById('app')!,
    modules: [
        {
            id: 'tauri-caps',
            install(ctx) {
                registerTauriCapabilities(ctx.context);
            },
        },
    ],
});

await app.start();

API

Entrypoints

| Import path | Export | Purpose | | ------------------------------------ | -------------------------------- | ---------------------------------------------- | | @enclosurejs/platform-tauri | TauriBackend | BackendAdapter for webview | | | registerTauriCapabilities(ctx) | Registers all 26 capability tokens in one call | | | TauriCapabilitiesOptions | Options type (e.g., autoLaunch config) | | | Tauri* (26 classes) | Individual service implementations | | @enclosurejs/platform-tauri/register | registerTauriCapabilities(ctx) | Same as main export (direct import) | | | TauriCapabilitiesOptions | Options type (same as main export) |

TauriBackend

Implements BackendAdapter from @enclosurejs/core:

| Member | Type | Description | | ---------- | ------------------------------------------------------------ | ------------------------------------------------ | | platform | 'tauri' | Platform identifier | | invoke | <R>(cmd, args?) => Promise<R> | Delegates to @tauri-apps/api/core.invoke() | | on | (event, handler: (payload: unknown) => void) => Disposable | Wraps listen() — async setup, sync dispose() | | once | <T>(event) => Promise<T> | Wraps once() — resolves on first event payload |

The on() method handles the async nature of Tauri's listen(): if dispose() is called before the listener is ready, the unlisten function is called immediately upon resolution — no leaked listeners.

registerTauriCapabilities(ctx, options?)

Binds all 26 service classes to their corresponding @enclosurejs/core tokens in a single call. Throws CoreError if called twice on the same context (token-already-provided).

Options:

| Field | Type | Purpose | | ------------ | ----------------------- | ------------------------------------------------------------- | | autoLaunch | TauriAutoLaunchConfig | { openAsHidden?: boolean } — reflects Rust-side plugin args |

Capability Implementations (26)

| Service class | Token | Tauri Plugin / API | | -------------------- | ------------------- | --------------------------------------------------------- | | TauriDialogs | DialogToken | @tauri-apps/plugin-dialog | | TauriWindows | WindowToken | @tauri-apps/api/window (WebviewWindow) | | TauriIpc | IpcToken | @tauri-apps/api/event (emit/listen between windows) | | TauriFileSystem | FileSystemToken | @tauri-apps/plugin-fs | | TauriShell | ShellToken | @tauri-apps/plugin-shell (Command + spawn) | | TauriClipboard | ClipboardToken | @tauri-apps/plugin-clipboard-manager | | TauriNotifications | NotificationToken | @tauri-apps/plugin-notification | | TauriStorage | StorageToken | @tauri-apps/plugin-store (LazyStore, JSON file) | | TauriHttp | HttpClientToken | @tauri-apps/plugin-http (fetch with Rust backend) | | TauriUpdater | UpdaterToken | @tauri-apps/plugin-updater | | TauriPath | PathToken | @tauri-apps/api/path | | TauriSystemInfo | SystemInfoToken | @tauri-apps/plugin-os + @tauri-apps/api/path + invoke | | TauriTray | TrayToken | @tauri-apps/api/tray (TrayIcon) | | TauriShortcuts | ShortcutToken | @tauri-apps/plugin-global-shortcut | | TauriDisplay | DisplayToken | @tauri-apps/api/window (monitor info) | | TauriPrint | PrintToken | @tauri-apps/api/core.invoke (custom commands) | | TauriSerial | SerialToken | @tauri-apps/api/core.invoke (custom Rust plugin) | | TauriFileWatcher | FileWatcherToken | @tauri-apps/plugin-fs (watch / watchImmediate) | | TauriUsb | UsbToken | @tauri-apps/api/core.invoke (custom Rust plugin) | | TauriDatabase | DatabaseToken | @tauri-apps/plugin-sql (SQLite via Rust) | | TauriDeepLink | DeepLinkToken | @tauri-apps/plugin-deep-link | | TauriAppLifecycle | AppLifecycleToken | @tauri-apps/plugin-process + @tauri-apps/api/window | | TauriTheme | ThemeToken | @tauri-apps/api/window (theme getter/setter) | | TauriAutoLaunch | AutoLaunchToken | @tauri-apps/plugin-autostart | | TauriPowerMonitor | PowerMonitorToken | @tauri-apps/api/core.invoke + @tauri-apps/api/event | | TauriKeychain | KeychainToken | @tauri-apps/api/core.invoke (custom Rust plugin) |

Configuration

Zero configuration files on the JS side. The package consumes Tauri's plugin APIs directly:

  • Registration: registerTauriCapabilities(ctx) — one call, no mandatory options.
  • AutoLaunch config: registerTauriCapabilities(ctx, { autoLaunch: { openAsHidden: true } }) — reports openAsHidden accurately when the Rust plugin was initialized with --hidden args.
  • Services: each service wraps a @tauri-apps/plugin-* import. No env vars, no config objects.

Rust-side prerequisites

Capabilities must be enabled in the Tauri app's Rust configuration:

  1. Cargo.toml — add tauri-plugin-fs, tauri-plugin-shell, etc. as dependencies
  2. main.rs — register each plugin with .plugin(tauri_plugin_*::init())
  3. capabilities JSON — grant permissions (e.g., fs:read, shell:open) in src-tauri/capabilities/
  4. Custom pluginsTauriSerial, TauriUsb, TauriKeychain, TauriPrint, TauriPowerMonitor, TauriSystemInfo (for cpus/memory/uptime) use custom invoke() commands that require matching Rust handlers

Plugin dependency matrix

| Dependency | Required by | Official plugin? | | -------------------------------------- | ------------- | ---------------- | | @tauri-apps/api | All services | Core API | | @tauri-apps/plugin-fs | FileSystem | Yes | | @tauri-apps/plugin-shell | Shell | Yes | | @tauri-apps/plugin-dialog | Dialogs | Yes | | @tauri-apps/plugin-clipboard-manager | Clipboard | Yes | | @tauri-apps/plugin-notification | Notifications | Yes | | @tauri-apps/plugin-store | Storage | Yes | | @tauri-apps/plugin-http | Http | Yes | | @tauri-apps/plugin-updater | Updater | Yes | | @tauri-apps/plugin-os | SystemInfo | Yes | | @tauri-apps/plugin-global-shortcut | Shortcuts | Yes | | @tauri-apps/plugin-sql | Database | Yes | | @tauri-apps/plugin-deep-link | DeepLink | Yes | | @tauri-apps/plugin-process | AppLifecycle | Yes | | @tauri-apps/plugin-autostart | AutoLaunch | Yes |

Types Exported

Types other packages and application code depend on:

| Type | Used by | | --------------------------- | ---------------------------------------------- | | TauriBackend | App entry point (renderer/webview) | | TauriCapabilitiesOptions | Module install() for DI registration | | TauriAutoLaunchConfig | Configuration of auto-launch behavior | | All 26 Tauri* classes | Direct use when bypassing DI (not recommended) | | registerTauriCapabilities | Module install() for DI registration |

Entrypoint separation:

| Import path | Contains | | ------------------------------------ | -------------------------------------------------------- | | @enclosurejs/platform-tauri | Backend + all 26 services + register | | @enclosurejs/platform-tauri/register | registerTauriCapabilities + TauriCapabilitiesOptions |

Both entrypoints import from @tauri-apps/* — this package is only usable inside a Tauri webview context.

Safety

Lifecycle Safety

  • TauriBackend.on() handles the async gap between listen() (returns a Promise) and dispose() (synchronous). If dispose() is called before the listener resolves, the unlisten function is invoked immediately upon resolution — no leaked listeners.
  • TauriBackend.on() returns Disposable with idempotent dispose() — double-dispose is safe.
  • registerTauriCapabilities() throws CoreError on double-call — prevents silent token shadowing.
  • All event-based services (IPC, shortcuts, theme, file watcher, power monitor) properly unsubscribe on dispose.

Error Safety

  • TauriHttp wraps failures in CoreError with HTTP_REQUEST_FAILED code — including non-Error thrown values.
  • TauriClipboard.writeImage() wraps failures in CoreError with CLIPBOARD_WRITE_IMAGE code.
  • TauriStorage delegates directly to LazyStore — errors propagate to the caller. Data integrity depends on the plugin's internal flushing.
  • TauriUpdater.checkAndInstall() delegates to update.downloadAndInstall() — errors propagate to the caller.

Data Safety

  • TauriStorage uses @tauri-apps/plugin-store (LazyStore) — data persisted to enclosure-storage.json on disk, automatically synced.
  • TauriDatabase uses @tauri-apps/plugin-sql with SQLite backend — transactions use raw BEGIN/COMMIT/ROLLBACK SQL statements on the same connection handle.
  • TauriKeychain delegates to a custom Rust plugin (plugin:enclosure-keychain) — secrets are stored via the OS keyring (platform-native encryption).

Shell Safety

  • TauriShell.spawn() shallow-copies args to prevent mutation after call.
  • TauriShell.exec() returns { code, stdout, stderr } — no throws on non-zero exit codes.
  • Spawned processes expose typed ReadableStream<Uint8Array> for stdout/stderr — no manual buffer management.

Deep Link Safety

  • URL parsing extracts scheme, host, path, and query from deep link URLs — handles both well-formed and malformed URLs gracefully.

Platform Specifics

Single-Process Architecture

Unlike Electron (main + renderer + preload), Tauri runs JS in a single webview process. All service classes call Tauri plugin APIs directly — no IPC bridge layer to manage. The TauriBackend wraps Tauri's invoke() and listen() to satisfy the BackendAdapter interface, but individual services bypass the backend and call their plugin APIs directly.

Custom Rust Plugins

Six services require custom Rust plugins (not official Tauri plugins). These must be implemented in the Tauri app's src-tauri/ directory:

| Service | Invoke prefix | Methods via invoke | | ------------------- | ----------------------------------- | ------------------------------------------------------------------------------- | | TauriSerial | plugin:enclosure-serial\|* | list, open, read, write, close + events | | TauriUsb | plugin:enclosure-usb\|* | list, open, transfer_in, transfer_out, close + events | | TauriKeychain | plugin:enclosure-keychain\|* | get, set, delete, has, get_accounts | | TauriPrint | plugin:enclosure-print\|* | print_url, print_html (but print() uses window.print()) | | TauriPowerMonitor | plugin:enclosure-power-monitor\|* | get_battery_info, is_on_battery_power, get_system_idle_time + events | | TauriSystemInfo | plugin:enclosure-system-info\|* | get_cpus, get_memory, get_uptime (other methods use official plugin-os) |

Storage — LazyStore JSON File

| Detail | Value | | ---------------- | ---------------------------------------------------------------------------------------- | | Backend | @tauri-apps/plugin-store (LazyStore) | | File path | enclosure-storage.json in Tauri's app data directory | | Persistence | Automatic async flush by the plugin — no explicit save() in JS | | size() | Estimates bytes via JSON.stringify(entries) — approximate, not actual file size | | onChange() | Uses LazyStore.onKeyChange() — subscription failure is silent (.catch(() => {})) |

Database — @tauri-apps/plugin-sql

| Detail | Value | | ---------------- | --------------------------------------------------------------------------------------------------------------------------- | | Path format | sqlite:{options.path ?? name}.db or sqlite::memory: | | Location | Plugin-managed (typically in app data directory) | | Migrations | BEGIN → all pending up queries → PRAGMA user_versionCOMMIT; catch → ROLLBACK | | Transactions | Same database handle reused — not savepoint-isolated; nested transaction() calls = multiple BEGIN on one connection |

Keychain — OS Native via Custom Plugin

TauriKeychain delegates to plugin:enclosure-keychain — all methods are Rust invoke() calls. Secrets are stored via the OS keyring (platform-native), not in a local file. This differs from Electron which uses an encrypted JSON file.

Path — Custom JS Implementation

TauriPath imports only sep() and delimiter() from @tauri-apps/api/path. All other operations (join, resolve, normalize, relative, parse, dirname, basename, extname, isAbsolute) are custom JS implementations — they may diverge from OS path rules for edge cases like UNC paths, extended-length Windows paths, or symlink resolution.

Shell — Line-Buffered Streams

| Detail | Value | | --------------------------- | ---------------------------------------------------------------------------------------------------------------- | | exec() timeout | CoreError with code SHELL_EXEC_TIMEOUT | | spawn() stdout/stderr | ReadableStream built from line events — each chunk is TextEncoder.encode(line + '\n'), not raw bytes | | stdin = 'ignore' | write() throws CoreError with code SHELL_STDIN_IGNORED | | kill() | void child.kill() — promise not awaited, errors not surfaced | | vs Electron | Electron sends raw Buffer chunks; Tauri sends line-buffered text |

Updater — No Custom Feed URL

| Detail | Value | | ------------------------------ | --------------------------------------------------------------------------------------------------- | | setFeedUrl() | Always throws CoreError NOT_SUPPORTED — feed URL is defined in tauri.conf.json only | | download() / install() | Re-calls check() internally — can race with concurrent checks or miss the originally found update |

Theme — Cached Initial Value

TauriTheme.get() calls getCurrentWindow().theme() which may return a Promise in some Tauri versions. If it returns a Promise, the method returns the cached this.currentTheme (initially 'light') — may be wrong until onChanged or set() updates it. getSource() reflects only the last set() call, not a real OS query.

AutoLaunch — Rust-Side Configuration Only

Tauri's autostart plugin configures launch arguments at Rust init time — the JS enable() call cannot pass openAsHidden or custom args. If openAsHidden is requested via enable({ openAsHidden: true }), the service logs console.warn but does not enable hidden mode unless the Rust plugin was initialized with --hidden in .args(). The TauriAutoLaunchConfig.openAsHidden constructor flag lets the service report openAsHidden accurately.

Print — Mixed Implementation

| Method | Implementation | | ------------- | ------------------------------------------------------------------- | | print() | window.print() — browser print dialog, ignores options | | printUrl() | invoke('plugin:enclosure-print\|print_url') — custom Rust plugin | | printHtml() | invoke('plugin:enclosure-print\|print_html') — custom Rust plugin |

Display — Name-Based Primary Detection

TauriDisplay identifies the primary monitor by comparing m.name with primaryMonitor().name. Monitor id and label both use m.name ?? 'unknown'. workArea falls back to full bounds if the Tauri API returns null.

Windows — Kiosk State Tracking

TauriWindows.setKiosk() sets a JS-side kioskActive flagisKiosk() returns this flag, not the actual OS state. If kiosk mode is changed outside this service (e.g., by the user or another API), the flag can desync. openModal() resolves undefined as T on close without closeWithResult — a type-level inaccuracy.

Shortcuts — Client-Side Registration Map

TauriShortcuts.isRegistered() checks a local Map, not the native OS state. register() chains .then().catch() — registration failure silently removes the entry from the map. unregister() waits for the registration promise to resolve before calling unregister(accelerator). Handler triggers only on event.state === 'Pressed'.

File Watcher — Plugin-Based with Custom Rename Detection

| Detail | Value | | ---------------------- | ---------------------------------------------------------------------- | | Backend | @tauri-apps/plugin-fs (watch / watchImmediate) | | Rename detection | Delete + create with 2 events = rename; isDirectory: false hardcoded | | Glob filtering | Regex approximation of glob patterns — not full glob semantics | | getWatched() | Returns { [path]: [path] }synthetic, not OS-backed watch list | | Unknown event kind | Mapped to 'modify' |

Silent .catch(() => {}) Patterns

Multiple services silently swallow listen() / onKeyChange() failures. If the Tauri runtime fails to set up an event listener, the service continues without the subscription — no error is thrown, no warning is logged:

| Service | Silent catch location | | ------------------- | ---------------------------------------- | | TauriIpc | @tauri-apps/api/event.listen() | | TauriAppLifecycle | onCloseRequested(), onFocusChanged() | | TauriDeepLink | onOpenUrl() | | TauriTheme | onThemeChanged() | | TauriStorage | LazyStore.onKeyChange() | | TauriWindows | Multiple subscribe/unlisten paths | | TauriPowerMonitor | All listenForEvent() calls | | TauriSerial | listen() for data events | | TauriUsb | onConnect(), onDisconnect() |

Error Wrapping

All services throw CoreError exclusively — no plain Error in any code path:

| Service | Method | Error code | | ------------------ | ------------------------- | ------------------------- | | TauriShell | exec (timeout) | SHELL_EXEC_TIMEOUT | | TauriShell | write (stdin=ignore) | SHELL_STDIN_IGNORED | | TauriFileSystem | copy (dest exists) | FS_DEST_EXISTS | | TauriFileWatcher | waitFor (timeout) | FILE_WATCHER_TIMEOUT | | TauriFileWatcher | waitFor (disposed) | FILE_WATCHER_DISPOSED | | TauriHttp | request | HTTP_REQUEST_FAILED | | TauriUpdater | setFeedUrl | NOT_SUPPORTED | | TauriUpdater | resolveUpdate | UPDATE_NOT_FOUND | | TauriTray | any (no tray) | TRAY_NOT_CREATED | | TauriDisplay | getPrimary/getCurrent | NO_PRIMARY_DISPLAY etc. | | TauriClipboard | writeImage | CLIPBOARD_WRITE_IMAGE | | TauriDatabase | open (migration fail) | DB_MIGRATION_FAILED | | TauriDatabase | batch / transaction | DB_BATCH_FAILED etc. |

Comparison with platform-electron

Key implementation differences between the two platform packages:

| Aspect | Tauri | Electron | | -------------------- | ------------------------------------------------ | --------------------------------------- | | Architecture | 1 JS process (webview) + Rust core | 3 processes (main, preload, renderer) | | Storage backend | LazyStore (file-based, auto-flushed) | localStorage (renderer, prefix-based) | | Keychain | OS native keyring (custom Rust plugin) | Encrypted JSON file (safeStorage) | | Database path | sqlite:{name}.db (plugin-managed) | {userData}/databases/{name}.sqlite | | Shell streams | Line-buffered text (line + '\n') | Raw byte Buffer chunks | | Path impl | Pure JS, @tauri-apps/api/path for sep/delim | Pure JS, userAgent for OS detection | | Print | print() = window.print(); others via Rust | All methods via IPC to main | | Updater feed URL | Fixed in tauri.conf.json (setFeedUrl throws) | Configurable at runtime | | Deep link | Plugin-based (@tauri-apps/plugin-deep-link) | requestSingleInstanceLock() + argv | | HTTP | @tauri-apps/plugin-http (Rust-backed fetch) | Renderer fetch() | | Notifications | @tauri-apps/plugin-notification (native) | Web Notification API (renderer) |

Benchmarks

Not applicable. @enclosurejs/platform-tauri is a platform bridge — its performance is dominated by Tauri's IPC round-trip latency (JS ↔ Rust via invoke()), which is ~0.05–0.2ms per call. Plugin APIs add negligible JS overhead. Real-world performance depends on:

  • Tauri's WebView-to-Rust serialization overhead (JSON via serde)
  • Rust command execution time (native API calls)
  • Plugin-specific overhead (e.g., SQLite query time, file I/O)

For production profiling, use Tauri's built-in performance tracing and browser DevTools.

Bundle Size

| Output | File | Size | | ------------ | ------------------------- | --------- | | Runtime (JS) | index.js | 62.85 KB | | | register.js | 61.75 KB | | Types (DTS) | index.d.ts | 11.02 KB | | | register.d.ts | 0.13 KB | | | register-*.d.ts (chunk) | 1.19 KB | | Total JS | | 124.60 KB | | Total | | 136.94 KB |

index.js and register.js share most code (26 service classes). All @tauri-apps/* dependencies are externalized in the build — they ship with the Tauri runtime, not in the JS bundle. The DTS output includes all 26 service classes and the TauriBackend type.

Quality

| Metric | Value | | --------------------- | ------------------------------------------------------------------ | | Unit tests | 648 (all pass) | | Test files | 28 (one per service + backend + register) | | Source files | 26 services + backend + register + barrel = 29 | | Dependencies | @enclosurejs/core + 15 @tauri-apps/* packages | | External dependencies | 0 at bundle time (all @tauri-apps/* externalized) | | Dev dependencies | tsup | | Coverage thresholds | statements >= 90%, branches >= 85%, functions >= 95%, lines >= 90% |

Quality Layers

Layer 1: STATIC ANALYSIS (every commit)
  tsc --noEmit        strict mode, zero errors
  eslint              ESLint 9 flat config, zero warnings
  prettier --check    formatting

Layer 2: UNIT TESTS (every commit)
  648 tests           backend, register, 26 services (one file each)
                      covers lifecycle, dispose, errors, edge cases
                      all Tauri APIs mocked via vi.mock
  v8 coverage         statements >= 90%, branches >= 85%, functions >= 95%, lines >= 90%

Layer 3: BENCHMARKS
  N/A                 platform bridge — performance dominated by Tauri IPC

Layer 4: PACKAGE HEALTH
  0 bundle deps       all @tauri-apps/* externalized
  tsup build          ESM + DTS output, 2 entrypoints

File Structure

packages/platform-tauri/
├── src/
│   ├── index.ts                    TauriBackend, re-exports services + register
│   ├── register.ts                 registerTauriCapabilities (26 tokens → DI)
│   ├── services/
│   │   ├── index.ts                Barrel — re-exports all 26 Tauri* service classes
│   │   ├── app-lifecycle.ts        TauriAppLifecycle
│   │   ├── auto-launch.ts          TauriAutoLaunch + TauriAutoLaunchConfig
│   │   ├── clipboard.ts            TauriClipboard
│   │   ├── database.ts             TauriDatabase
│   │   ├── deep-link.ts            TauriDeepLink
│   │   ├── dialogs.ts              TauriDialogs
│   │   ├── display.ts              TauriDisplay
│   │   ├── file-watcher.ts         TauriFileWatcher
│   │   ├── fs.ts                   TauriFileSystem
│   │   ├── http.ts                 TauriHttp
│   │   ├── ipc.ts                  TauriIpc
│   │   ├── keychain.ts             TauriKeychain
│   │   ├── notifications.ts        TauriNotifications
│   │   ├── path.ts                 TauriPath
│   │   ├── power-monitor.ts        TauriPowerMonitor
│   │   ├── print.ts                TauriPrint
│   │   ├── serial.ts               TauriSerial
│   │   ├── shell.ts                TauriShell
│   │   ├── shortcuts.ts            TauriShortcuts
│   │   ├── storage.ts              TauriStorage
│   │   ├── system-info.ts          TauriSystemInfo
│   │   ├── theme.ts                TauriTheme
│   │   ├── tray.ts                 TauriTray
│   │   ├── updater.ts              TauriUpdater
│   │   ├── usb.ts                  TauriUsb
│   │   └── windows.ts              TauriWindows
│   └── __tests__/
│       ├── app-lifecycle.test.ts    27 tests — AppLifecycle (state, quit, relaunch)
│       ├── auto-launch.test.ts     12 tests — AutoLaunch (enable, disable, config)
│       ├── backend.test.ts          9 tests — TauriBackend adapter
│       ├── clipboard.test.ts        8 tests — ClipboardService
│       ├── database.test.ts        22 tests — DatabaseService (SQLite, migrations)
│       ├── deep-link.test.ts       19 tests — DeepLink (register, events, URLs)
│       ├── dialogs.test.ts         21 tests — DialogService (alert, confirm, files)
│       ├── display.test.ts         11 tests — DisplayService (monitors, primary)
│       ├── file-watcher.test.ts    33 tests — FileWatcher (watch, glob, debounce)
│       ├── fs.test.ts              29 tests — FileSystem (read, write, stat, copy)
│       ├── http.test.ts            29 tests — HttpClient (fetch, progress, errors)
│       ├── ipc.test.ts             21 tests — IpcService (send, broadcast, listen)
│       ├── keychain.test.ts        10 tests — Keychain (get, set, delete, accounts)
│       ├── notifications.test.ts    9 tests — Notifications (send, permission)
│       ├── path.test.ts            39 tests — PathService (join, parse, resolve)
│       ├── power-monitor.test.ts   23 tests — PowerMonitor (battery, events)
│       ├── print.test.ts            8 tests — PrintService (print, PDF)
│       ├── register.test.ts         4 tests — registerTauriCapabilities (26 tokens)
│       ├── serial.test.ts          32 tests — SerialService (list, open, read, write)
│       ├── shell.test.ts           54 tests — ShellService (exec, spawn, streams)
│       ├── shortcuts.test.ts       23 tests — ShortcutService (register, unregister)
│       ├── storage.test.ts         33 tests — StorageService (get, set, onChange)
│       ├── system-info.test.ts     24 tests — SystemInfo (arch, memory, CPU)
│       ├── theme.test.ts           24 tests — ThemeService (get, set, onChange)
│       ├── tray.test.ts            29 tests — TrayService (create, menu, events)
│       ├── updater.test.ts         20 tests — UpdaterService (check, download)
│       ├── usb.test.ts             20 tests — UsbService (list, open, transfer)
│       └── windows.test.ts         55 tests — WindowService (open, resize, events)
├── package.json
├── tsconfig.json
├── tsup.config.ts
└── README.md

License

MIT