Skip to content

feat: add dory desktop app#435

Open
dory-finn wants to merge 4 commits intojackwener:mainfrom
dorylab:main
Open

feat: add dory desktop app#435
dory-finn wants to merge 4 commits intojackwener:mainfrom
dorylab:main

Conversation

@dory-finn
Copy link

Description

Related issue:

Type of Change

  • 🐛 Bug fix
  • ✨ New feature
  • 🌐 New site adapter
  • 📝 Documentation
  • ♻️ Refactor
  • 🔧 CI / build / tooling

Checklist

  • I ran the checks relevant to this PR
  • I updated tests or docs if needed
  • I included output or screenshots when useful

Documentation (if adding/modifying an adapter)

  • Added doc page under docs/adapters/ (if new adapter)
  • Updated docs/adapters/index.md table (if new adapter)
  • Updated sidebar in docs/.vitepress/config.mts (if new adapter)
  • Updated README.md / README.zh-CN.md when command discoverability changed
  • Used positional args for the command's primary subject unless a named flag is clearly better
  • Normalized expected adapter failures to CliError subclasses instead of raw Error

Screenshots / Output

image image image image image

@Astro-Han
Copy link
Contributor

Thanks for the contribution! Dory's AI + database combo is an interesting use case. A few thoughts:

Should this be a plugin instead?

Dory is a niche database client with a small user base compared to built-in adapters like Twitter, Bilibili, or WeChat. Putting 18 commands (1,165 lines) into the core repo means the maintainers take on the maintenance burden — every time Dory updates its UI or API, someone here needs to fix it.

This is a great fit for the plugin system: opencli-plugin-dory. You get the same YAML/TS format, automatic discovery, and full ecosystem visibility — but you own the maintenance. See the plugin guide.

Existing community adapters like opencli-plugin-github-trending follow this model successfully.

Architecture concern

The 18 commands mix two fundamentally different patterns:

  • Database commands (connections, databases, tables, columns, query, etc.) wrap Dory's internal REST API — this isn't browser automation at all
  • Chat commands (ask, send, read, etc.) do actual CDP UI automation

Existing desktop adapters (ChatGPT 6 commands, Cursor 12, Notion 8) stay within a single interaction surface. This PR introduces a new "database client" category without shared abstractions. The schema browsing commands (connectionsdatabasestablescolumns) could be consolidated, and query / query-export differ only in output format.

Code issues

localhost:3000 hardcodedensureChatbotPage and connect hardcode http://localhost:3000. If Dory runs on another port, all navigation commands fail. Other commands in the same PR use relative URLs, which is inconsistent.

ask completion detection — The "two consecutive identical polls at 2s interval = done" pattern will truncate streaming responses on normal generation pauses.

page.evaluate error propagationthrow new Error() inside page.evaluate may not propagate as a Node.js exception depending on the IPage implementation. Consider returning { error: message } instead.

Zero tests — 18 commands with no test coverage doesn't meet the project's TESTING.md requirements.

Minor: connections.ts empty-result row uses Driver but columns declare Engine; query-export.ts discards SQL error messages on failure.

@dory-finn
Copy link
Author

@Astro-Han Thanks for the feedback, is plugins works on electron app?

@Astro-Han
Copy link
Contributor

@dory-finn Yes, plugins fully support Electron/desktop apps. The plugin system shares the exact same execution path as built-in adapters — there's no distinction at runtime.

How it works:

  • Your TS plugin commands declare browser: true + Strategy.UI (same as built-in ChatGPT/Cursor/Notion adapters)
  • At runtime, OPENCLI_CDP_ENDPOINT env var controls whether opencli connects via CDP or browser extension — this is transparent to your adapter code
  • Your func receives an IPage object that abstracts over both CDP and browser modes
  • During plugin install, the host @jackwener/opencli package is symlinked into your plugin's node_modules/, so imports like @jackwener/opencli/registry and @jackwener/opencli/browser/cdp.js resolve correctly

You can also use requiredEnv to validate OPENCLI_CDP_ENDPOINT before execution:

import { cli, Strategy } from '@jackwener/opencli/registry';

cli({
  site: 'dory',
  name: 'connections',
  description: 'List database connections',
  strategy: Strategy.UI,
  browser: true,
  requiredEnv: [{ name: 'OPENCLI_CDP_ENDPOINT', help: 'Dory CDP endpoint (e.g. http://localhost:9222)' }],
  func: async (page, kwargs) => {
    // page is an IPage — same API as built-in desktop adapters
  },
});

The shared desktop utilities in src/clis/_shared/desktop-commands.ts are also accessible if you want to reuse the 5-Command Pattern (status/dump/read/send/new). See docs/advanced/electron.md for the full CDP adapter guide.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

3 participants