expandai 0.0.0 → 0.0.2
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/README.md +241 -6
- package/build/dts/ApiClient.d.ts +231 -0
- package/build/dts/ApiClient.d.ts.map +1 -0
- package/build/dts/Authentication.d.ts +23 -0
- package/build/dts/Authentication.d.ts.map +1 -0
- package/build/dts/BrowserOAuth.d.ts +99 -0
- package/build/dts/BrowserOAuth.d.ts.map +1 -0
- package/build/dts/Commands/Fetch.d.ts +30 -0
- package/build/dts/Commands/Fetch.d.ts.map +1 -0
- package/build/dts/Commands/Hook.d.ts +17 -0
- package/build/dts/Commands/Hook.d.ts.map +1 -0
- package/build/dts/Commands/Mcp.d.ts +11 -0
- package/build/dts/Commands/Mcp.d.ts.map +1 -0
- package/build/dts/Commands/McpRun.d.ts +5 -0
- package/build/dts/Commands/McpRun.d.ts.map +1 -0
- package/build/dts/Commands/Search.d.ts +21 -0
- package/build/dts/Commands/Search.d.ts.map +1 -0
- package/build/dts/Commands/Skill.d.ts +12 -0
- package/build/dts/Commands/Skill.d.ts.map +1 -0
- package/build/dts/Commands/Uninstall.d.ts +9 -0
- package/build/dts/Commands/Uninstall.d.ts.map +1 -0
- package/build/dts/Config.d.ts +105 -0
- package/build/dts/Config.d.ts.map +1 -0
- package/build/dts/DeviceAuth.d.ts +87 -0
- package/build/dts/DeviceAuth.d.ts.map +1 -0
- package/build/dts/Hook/Claude.d.ts +13 -0
- package/build/dts/Hook/Claude.d.ts.map +1 -0
- package/build/dts/Hook/Errors.d.ts +20 -0
- package/build/dts/Hook/Errors.d.ts.map +1 -0
- package/build/dts/Hook/Opencode.d.ts +13 -0
- package/build/dts/Hook/Opencode.d.ts.map +1 -0
- package/build/dts/Hook/SnapshotNote.d.ts +8 -0
- package/build/dts/Hook/SnapshotNote.d.ts.map +1 -0
- package/build/dts/Install/Claude/Hook.d.ts +60 -0
- package/build/dts/Install/Claude/Hook.d.ts.map +1 -0
- package/build/dts/Install/Claude/Mcp.d.ts +45 -0
- package/build/dts/Install/Claude/Mcp.d.ts.map +1 -0
- package/build/dts/Install/Claude/Skill.d.ts +24 -0
- package/build/dts/Install/Claude/Skill.d.ts.map +1 -0
- package/build/dts/Install/Codex/Mcp.d.ts +39 -0
- package/build/dts/Install/Codex/Mcp.d.ts.map +1 -0
- package/build/dts/Install/Codex/Skill.d.ts +20 -0
- package/build/dts/Install/Codex/Skill.d.ts.map +1 -0
- package/build/dts/Install/Cursor/Mcp.d.ts +45 -0
- package/build/dts/Install/Cursor/Mcp.d.ts.map +1 -0
- package/build/dts/Install/Cursor/Skill.d.ts +27 -0
- package/build/dts/Install/Cursor/Skill.d.ts.map +1 -0
- package/build/dts/Install/Domain.d.ts +73 -0
- package/build/dts/Install/Domain.d.ts.map +1 -0
- package/build/dts/Install/Hook.d.ts +30 -0
- package/build/dts/Install/Hook.d.ts.map +1 -0
- package/build/dts/Install/Mcp.d.ts +28 -0
- package/build/dts/Install/Mcp.d.ts.map +1 -0
- package/build/dts/Install/Opencode/Hook.d.ts +23 -0
- package/build/dts/Install/Opencode/Hook.d.ts.map +1 -0
- package/build/dts/Install/Opencode/Mcp.d.ts +47 -0
- package/build/dts/Install/Opencode/Mcp.d.ts.map +1 -0
- package/build/dts/Install/Opencode/Skill.d.ts +24 -0
- package/build/dts/Install/Opencode/Skill.d.ts.map +1 -0
- package/build/dts/Install/Skill.d.ts +32 -0
- package/build/dts/Install/Skill.d.ts.map +1 -0
- package/build/dts/Install/Uninstall.d.ts +32 -0
- package/build/dts/Install/Uninstall.d.ts.map +1 -0
- package/build/dts/Mcp/ExpandDocs.d.ts +7 -0
- package/build/dts/Mcp/ExpandDocs.d.ts.map +1 -0
- package/build/dts/Mcp/RequestHeaders.d.ts +15 -0
- package/build/dts/Mcp/RequestHeaders.d.ts.map +1 -0
- package/build/dts/Mcp/Server.d.ts +10 -0
- package/build/dts/Mcp/Server.d.ts.map +1 -0
- package/build/dts/Mcp/Toolkit.d.ts +3 -0
- package/build/dts/Mcp/Toolkit.d.ts.map +1 -0
- package/build/dts/Mcp/tools/Citations.d.ts +237 -0
- package/build/dts/Mcp/tools/Citations.d.ts.map +1 -0
- package/build/dts/Mcp/tools/Fetch.d.ts +167 -0
- package/build/dts/Mcp/tools/Fetch.d.ts.map +1 -0
- package/build/dts/Snippets.d.ts +19 -0
- package/build/dts/Snippets.d.ts.map +1 -0
- package/build/dts/index.d.ts +2 -0
- package/build/dts/index.d.ts.map +1 -0
- package/build/dts/main.d.ts +3 -0
- package/build/dts/main.d.ts.map +1 -0
- package/build/esm/ApiClient.js +182 -0
- package/build/esm/ApiClient.js.map +1 -0
- package/build/esm/Authentication.js +112 -0
- package/build/esm/Authentication.js.map +1 -0
- package/build/esm/BrowserOAuth.js +254 -0
- package/build/esm/BrowserOAuth.js.map +1 -0
- package/build/esm/Commands/Fetch.js +95 -0
- package/build/esm/Commands/Fetch.js.map +1 -0
- package/build/esm/Commands/Hook.js +20 -0
- package/build/esm/Commands/Hook.js.map +1 -0
- package/build/esm/Commands/Mcp.js +19 -0
- package/build/esm/Commands/Mcp.js.map +1 -0
- package/build/esm/Commands/McpRun.js +15 -0
- package/build/esm/Commands/McpRun.js.map +1 -0
- package/build/esm/Commands/Search.js +43 -0
- package/build/esm/Commands/Search.js.map +1 -0
- package/build/esm/Commands/Skill.js +17 -0
- package/build/esm/Commands/Skill.js.map +1 -0
- package/build/esm/Commands/Uninstall.js +28 -0
- package/build/esm/Commands/Uninstall.js.map +1 -0
- package/build/esm/Config.js +145 -0
- package/build/esm/Config.js.map +1 -0
- package/build/esm/DeviceAuth.js +127 -0
- package/build/esm/DeviceAuth.js.map +1 -0
- package/build/esm/Hook/Claude.js +74 -0
- package/build/esm/Hook/Claude.js.map +1 -0
- package/build/esm/Hook/Errors.js +18 -0
- package/build/esm/Hook/Errors.js.map +1 -0
- package/build/esm/Hook/Opencode.js +50 -0
- package/build/esm/Hook/Opencode.js.map +1 -0
- package/build/esm/Hook/SnapshotNote.js +18 -0
- package/build/esm/Hook/SnapshotNote.js.map +1 -0
- package/build/esm/Install/Claude/Hook.js +89 -0
- package/build/esm/Install/Claude/Hook.js.map +1 -0
- package/build/esm/Install/Claude/Mcp.js +71 -0
- package/build/esm/Install/Claude/Mcp.js.map +1 -0
- package/build/esm/Install/Claude/Skill.js +34 -0
- package/build/esm/Install/Claude/Skill.js.map +1 -0
- package/build/esm/Install/Codex/Mcp.js +92 -0
- package/build/esm/Install/Codex/Mcp.js.map +1 -0
- package/build/esm/Install/Codex/Skill.js +30 -0
- package/build/esm/Install/Codex/Skill.js.map +1 -0
- package/build/esm/Install/Cursor/Mcp.js +71 -0
- package/build/esm/Install/Cursor/Mcp.js.map +1 -0
- package/build/esm/Install/Cursor/Skill.js +37 -0
- package/build/esm/Install/Cursor/Skill.js.map +1 -0
- package/build/esm/Install/Domain.js +105 -0
- package/build/esm/Install/Domain.js.map +1 -0
- package/build/esm/Install/Hook.js +38 -0
- package/build/esm/Install/Hook.js.map +1 -0
- package/build/esm/Install/Mcp.js +40 -0
- package/build/esm/Install/Mcp.js.map +1 -0
- package/build/esm/Install/Opencode/Hook.js +44 -0
- package/build/esm/Install/Opencode/Hook.js.map +1 -0
- package/build/esm/Install/Opencode/Mcp.js +73 -0
- package/build/esm/Install/Opencode/Mcp.js.map +1 -0
- package/build/esm/Install/Opencode/Skill.js +34 -0
- package/build/esm/Install/Opencode/Skill.js.map +1 -0
- package/build/esm/Install/Opencode/expandai-webfetch.js +38 -0
- package/build/esm/Install/Skill.js +41 -0
- package/build/esm/Install/Skill.js.map +1 -0
- package/build/esm/Install/Uninstall.js +49 -0
- package/build/esm/Install/Uninstall.js.map +1 -0
- package/build/esm/Mcp/ExpandDocs.js +64 -0
- package/build/esm/Mcp/ExpandDocs.js.map +1 -0
- package/build/esm/Mcp/RequestHeaders.js +13 -0
- package/build/esm/Mcp/RequestHeaders.js.map +1 -0
- package/build/esm/Mcp/Server.js +11 -0
- package/build/esm/Mcp/Server.js.map +1 -0
- package/build/esm/Mcp/Toolkit.js +16 -0
- package/build/esm/Mcp/Toolkit.js.map +1 -0
- package/build/esm/Mcp/tools/Citations.js +92 -0
- package/build/esm/Mcp/tools/Citations.js.map +1 -0
- package/build/esm/Mcp/tools/Fetch.js +141 -0
- package/build/esm/Mcp/tools/Fetch.js.map +1 -0
- package/build/esm/Snippets.js +18 -0
- package/build/esm/Snippets.js.map +1 -0
- package/build/esm/index.js +2 -0
- package/build/esm/index.js.map +1 -0
- package/build/esm/main.js +97 -0
- package/build/esm/main.js.map +1 -0
- package/build/skills/expandai/SKILL.md +72 -0
- package/package.json +72 -10
- package/src/ApiClient.ts +257 -0
- package/src/Authentication.ts +164 -0
- package/src/BrowserOAuth.ts +361 -0
- package/src/Commands/Fetch.ts +157 -0
- package/src/Commands/Hook.ts +48 -0
- package/src/Commands/Mcp.ts +30 -0
- package/src/Commands/McpRun.ts +25 -0
- package/src/Commands/Search.ts +92 -0
- package/src/Commands/Skill.ts +30 -0
- package/src/Commands/Uninstall.ts +38 -0
- package/src/Config.ts +195 -0
- package/src/DeviceAuth.ts +193 -0
- package/src/Hook/Claude.ts +81 -0
- package/src/Hook/Errors.ts +19 -0
- package/src/Hook/Opencode.ts +58 -0
- package/src/Hook/SnapshotNote.ts +18 -0
- package/src/Install/Claude/Hook.ts +133 -0
- package/src/Install/Claude/Mcp.ts +82 -0
- package/src/Install/Claude/Skill.ts +44 -0
- package/src/Install/Codex/Mcp.ts +109 -0
- package/src/Install/Codex/Skill.ts +40 -0
- package/src/Install/Cursor/Mcp.ts +82 -0
- package/src/Install/Cursor/Skill.ts +47 -0
- package/src/Install/Domain.ts +148 -0
- package/src/Install/Hook.ts +50 -0
- package/src/Install/Mcp.ts +71 -0
- package/src/Install/Opencode/Hook.ts +55 -0
- package/src/Install/Opencode/Mcp.ts +84 -0
- package/src/Install/Opencode/Skill.ts +44 -0
- package/src/Install/Opencode/expandai-webfetch.d.ts +23 -0
- package/src/Install/Opencode/expandai-webfetch.js +38 -0
- package/src/Install/Skill.ts +57 -0
- package/src/Install/Uninstall.ts +82 -0
- package/src/Mcp/ExpandDocs.ts +71 -0
- package/src/Mcp/RequestHeaders.ts +16 -0
- package/src/Mcp/Server.ts +14 -0
- package/src/Mcp/Toolkit.ts +21 -0
- package/src/Mcp/tools/Citations.ts +110 -0
- package/src/Mcp/tools/Fetch.ts +177 -0
- package/src/Snippets.ts +32 -0
- package/src/index.ts +1 -0
- package/src/main.ts +146 -0
- package/bun.lockb +0 -0
- package/index.ts +0 -1
- package/tsconfig.json +0 -27
package/README.md
CHANGED
|
@@ -1,15 +1,250 @@
|
|
|
1
|
-
#
|
|
1
|
+
# expandai
|
|
2
2
|
|
|
3
|
-
|
|
3
|
+
Unified CLI and MCP server for [ExpandAI](https://expand.ai). Fetch any URL as
|
|
4
|
+
clean markdown, and wire ExpandAI into Claude Code, Cursor, OpenCode, or Codex
|
|
5
|
+
as an MCP server, a runtime webfetch hook, or a skill.
|
|
6
|
+
|
|
7
|
+
## Install
|
|
8
|
+
|
|
9
|
+
```bash
|
|
10
|
+
bun install -g expandai
|
|
11
|
+
# or
|
|
12
|
+
npm install -g expandai
|
|
13
|
+
```
|
|
14
|
+
|
|
15
|
+
The binary is published as `expandai`. One-off use without install:
|
|
16
|
+
|
|
17
|
+
```bash
|
|
18
|
+
bunx expandai fetch https://example.com
|
|
19
|
+
```
|
|
20
|
+
|
|
21
|
+
## Standalone binary
|
|
22
|
+
|
|
23
|
+
A self-contained `expandai` executable is published with each release — no
|
|
24
|
+
Node, Bun, or npm required at runtime. One command detects your platform,
|
|
25
|
+
downloads the right binary from GitHub Releases, and drops it on your
|
|
26
|
+
`PATH`:
|
|
27
|
+
|
|
28
|
+
```bash
|
|
29
|
+
curl -fsSL https://raw.githubusercontent.com/expandai/expandai-cli/main/install.sh | bash
|
|
30
|
+
```
|
|
31
|
+
|
|
32
|
+
Then:
|
|
33
|
+
|
|
34
|
+
```bash
|
|
35
|
+
expandai whoami
|
|
36
|
+
```
|
|
37
|
+
|
|
38
|
+
The binary bundles everything `expandai mcp run`, `expandai hook claude-code`,
|
|
39
|
+
and `expandai hook opencode` need at runtime, so the MCP server and webfetch
|
|
40
|
+
hooks work straight from `PATH` — no `node`/`bun` needed in your agent's
|
|
41
|
+
environment.
|
|
42
|
+
|
|
43
|
+
## Quick start
|
|
44
|
+
|
|
45
|
+
```bash
|
|
46
|
+
expandai login # interactive auth
|
|
47
|
+
expandai fetch https://docs.example.com/api # full markdown
|
|
48
|
+
expandai fetch https://docs.example.com/api --search auth # semantic snippets
|
|
49
|
+
```
|
|
50
|
+
|
|
51
|
+
## Supported harnesses
|
|
52
|
+
|
|
53
|
+
| Harness | MCP server | Webfetch hook | Skill |
|
|
54
|
+
|-------------|:----------:|:-------------:|:-----:|
|
|
55
|
+
| Claude Code | ✓ | ✓ | ✓ |
|
|
56
|
+
| OpenCode | ✓ | ✓ | ✓ |
|
|
57
|
+
| Cursor | ✓ | — | ✓ |
|
|
58
|
+
| Codex | ✓ | — | ✓ |
|
|
59
|
+
|
|
60
|
+
**Pick one — each integration works standalone.** In rough preference order:
|
|
61
|
+
|
|
62
|
+
1. **Hook** (Claude Code, OpenCode). `expandai hook install <host> <scope>`
|
|
63
|
+
— best invisible upgrade: every native web fetch the agent issues comes
|
|
64
|
+
back as ExpandAI markdown, no prompt changes required. Also wires the MCP
|
|
65
|
+
server in the same step. See [Recommended: `hook install`](#recommended-hook-install).
|
|
66
|
+
2. **Skill** (all four harnesses). `expandai skill install <host> <scope>`
|
|
67
|
+
— lightest-weight: drops a `SKILL.md` that teaches the agent when to
|
|
68
|
+
reach for `expandai fetch`.
|
|
69
|
+
3. **MCP server** (all four harnesses). `expandai mcp install <host> <scope>`
|
|
70
|
+
— exposes the full `fetch` API (snippets, screenshots, structured
|
|
71
|
+
extraction) as an MCP-callable tool.
|
|
72
|
+
|
|
73
|
+
Combinations are fine — installing skill on top of hook, for example, nudges
|
|
74
|
+
the agent to use `mcp__expandai__fetch` for refinement on top of the
|
|
75
|
+
automatic substitution — but any single one is a complete setup.
|
|
76
|
+
|
|
77
|
+
### Scopes
|
|
78
|
+
|
|
79
|
+
Every `install` / `uninstall` command takes a `<scope>` argument: `global`
|
|
80
|
+
or `project`.
|
|
81
|
+
|
|
82
|
+
- `global` — written under your `$HOME`. Applies to every session of the
|
|
83
|
+
harness, regardless of where the agent is launched. Pick this if you want
|
|
84
|
+
ExpandAI on by default everywhere.
|
|
85
|
+
- `project` — written under the current working directory. Applies only
|
|
86
|
+
when the harness is launched from inside that directory (or a
|
|
87
|
+
subdirectory). Pick this when you want different projects to opt in
|
|
88
|
+
independently, or when the integration should live in version control
|
|
89
|
+
alongside the project.
|
|
90
|
+
|
|
91
|
+
The exact files each scope touches differ per harness and per integration —
|
|
92
|
+
see the path comment next to each `install` line in the sections below.
|
|
93
|
+
|
|
94
|
+
## Authentication
|
|
95
|
+
|
|
96
|
+
```bash
|
|
97
|
+
expandai login # OAuth (browser device flow) or API key
|
|
98
|
+
expandai whoami # show current auth state
|
|
99
|
+
expandai logout # clear credentials and optionally remove installed integrations
|
|
100
|
+
```
|
|
101
|
+
|
|
102
|
+
Credentials are stored at `$XDG_CONFIG_HOME/expandai/config.json` (default
|
|
103
|
+
`~/.config/expandai/config.json`, mode `0600`).
|
|
104
|
+
|
|
105
|
+
Environment overrides:
|
|
106
|
+
|
|
107
|
+
- `EXPAND_API_KEY` — overrides the stored auth method.
|
|
108
|
+
- `EXPAND_API_URL` — overrides the API endpoint (defaults to `https://api.expand.ai`).
|
|
109
|
+
|
|
110
|
+
## fetch
|
|
111
|
+
|
|
112
|
+
`expandai fetch <url>` returns the rendered page as markdown. Handles
|
|
113
|
+
JavaScript-heavy SPAs and bot-protected sites that plain `curl` can't read.
|
|
4
114
|
|
|
5
115
|
```bash
|
|
6
|
-
|
|
116
|
+
expandai fetch https://example.com # markdown (default)
|
|
117
|
+
expandai fetch example.com # https:// is added automatically
|
|
118
|
+
expandai fetch https://example.com --format json # full response with metadata
|
|
119
|
+
expandai fetch https://docs.example.com/api --search "authentication"
|
|
7
120
|
```
|
|
8
121
|
|
|
9
|
-
|
|
122
|
+
Flags:
|
|
123
|
+
|
|
124
|
+
- `--format text|json` — output mode (default `text`).
|
|
125
|
+
- `--search <query>` — semantic search. Returns relevant snippets instead of the full page.
|
|
126
|
+
- `--max-results <n>` — snippet count when `--search` is set. Default `5`, max `50`.
|
|
127
|
+
- `--min-score <n>` — minimum relevance score, `0`–`1`. Default `0.6`.
|
|
128
|
+
|
|
129
|
+
## Recommended: `hook install`
|
|
130
|
+
|
|
131
|
+
`expandai hook install <host> <scope>` is the ideal setup on harnesses that
|
|
132
|
+
support it. One command, two effects:
|
|
133
|
+
|
|
134
|
+
1. **Installs a runtime webfetch hook** that intercepts the agent's *native*
|
|
135
|
+
web-fetch tool and silently substitutes ExpandAI's markdown for whatever
|
|
136
|
+
the agent would have fetched on its own.
|
|
137
|
+
2. **Registers the MCP server** at `<scope>` so the agent can also explicitly
|
|
138
|
+
call `mcp__expandai__fetch` for the full `select` API (markdown, snippets,
|
|
139
|
+
screenshot, links, JSON extraction, etc.).
|
|
10
140
|
|
|
11
141
|
```bash
|
|
12
|
-
|
|
142
|
+
expandai hook install claude-code global
|
|
143
|
+
expandai hook install opencode project
|
|
13
144
|
```
|
|
14
145
|
|
|
15
|
-
|
|
146
|
+
**Scope behavior:** `global` writes to the harness's user settings
|
|
147
|
+
(`~/.claude/settings.json` for Claude Code, `~/.config/opencode/plugins/` for
|
|
148
|
+
OpenCode) — the substitution fires for every session of that harness on the
|
|
149
|
+
machine. `project` writes to per-directory equivalents
|
|
150
|
+
(`<cwd>/.claude/settings.json`, `<cwd>/.opencode/plugins/`) — the
|
|
151
|
+
substitution only fires when the harness is launched from that directory.
|
|
152
|
+
|
|
153
|
+
### Why both, not just one
|
|
154
|
+
|
|
155
|
+
- The **runtime hook** makes the agent's native fetch path return ExpandAI
|
|
156
|
+
markdown automatically, so even agents that haven't been told about
|
|
157
|
+
expand.ai get clean rendered output for SPAs and bot-protected pages.
|
|
158
|
+
No prompt changes required.
|
|
159
|
+
- The **MCP server alone** requires the agent to consciously choose
|
|
160
|
+
`mcp__expandai__fetch` over its built-in tool, which it usually won't
|
|
161
|
+
unless something nudges it (a skill, a prompt).
|
|
162
|
+
- Together, default web access is upgraded transparently, and explicit
|
|
163
|
+
refinement (snippets, screenshots, structured extraction) is still one
|
|
164
|
+
MCP tool call away.
|
|
165
|
+
|
|
166
|
+
### How the substitution actually works
|
|
167
|
+
|
|
168
|
+
- **Claude Code** — `expandai hook install claude-code <scope>` writes a
|
|
169
|
+
`PreToolUse` matcher into `settings.json` that scopes to `WebFetch`. When
|
|
170
|
+
the agent invokes `WebFetch`, the runner reads the SDK's hook payload from
|
|
171
|
+
stdin, fetches the URL via expand.ai, and emits
|
|
172
|
+
`{ permissionDecision: "deny", additionalContext: <markdown> }`. The denial
|
|
173
|
+
blocks the native fetch; `additionalContext` is the documented channel for
|
|
174
|
+
injecting content into the model's next turn, so the markdown still reaches
|
|
175
|
+
the model in place of WebFetch's raw output.
|
|
176
|
+
- **OpenCode** — `expandai hook install opencode <scope>` copies an
|
|
177
|
+
`expandai-webfetch.js` plugin into `.opencode/plugins/`. The plugin hooks
|
|
178
|
+
`tool.execute.after` on `webfetch`, shells out to `expandai hook opencode`
|
|
179
|
+
with the URL, and overwrites `output.output` with the returned markdown.
|
|
180
|
+
(`tool.execute.before` can only mutate args, not replace results, which is
|
|
181
|
+
why we run in `after`.)
|
|
182
|
+
|
|
183
|
+
Cursor and Codex don't expose a hook system, so `hook install` only accepts
|
|
184
|
+
`claude-code` and `opencode`. For those harnesses, use `skill install` +
|
|
185
|
+
`mcp install` instead.
|
|
186
|
+
|
|
187
|
+
## Skill
|
|
188
|
+
|
|
189
|
+
The CLI ships a `SKILL.md` that teaches an agent when to reach for
|
|
190
|
+
`expandai fetch`. `SKILL.md` is the open-standard format that Claude Code,
|
|
191
|
+
Cursor, OpenCode, and Codex auto-discover for tool guidance.
|
|
192
|
+
|
|
193
|
+
```bash
|
|
194
|
+
expandai skill install claude-code global # ~/.claude/skills/expandai/
|
|
195
|
+
expandai skill install cursor project # <cwd>/.cursor/skills/expandai/
|
|
196
|
+
expandai skill install opencode global # ~/.config/opencode/skills/expandai/
|
|
197
|
+
expandai skill install codex project # <cwd>/.agents/skills/expandai/
|
|
198
|
+
```
|
|
199
|
+
|
|
200
|
+
**Scope behavior:** `global` drops `SKILL.md` into the harness's user-level
|
|
201
|
+
skills directory, so the agent auto-discovers it in every session. `project`
|
|
202
|
+
drops it into the cwd-level skills directory, so it's only discovered when
|
|
203
|
+
the harness is launched from that directory — useful for committing the
|
|
204
|
+
skill alongside a project so collaborators pick it up automatically.
|
|
205
|
+
|
|
206
|
+
## MCP server
|
|
207
|
+
|
|
208
|
+
`expandai mcp run` speaks MCP over stdio. Any MCP-aware client can call the
|
|
209
|
+
`fetch` tool, which exposes the full `select` API (markdown, snippets,
|
|
210
|
+
screenshot, links, JSON extraction, etc.).
|
|
211
|
+
|
|
212
|
+
`hook install` already registers the MCP server on Claude Code and OpenCode,
|
|
213
|
+
so this command is mostly for Cursor and Codex, or for installing the MCP
|
|
214
|
+
server without the runtime hook:
|
|
215
|
+
|
|
216
|
+
```bash
|
|
217
|
+
expandai mcp install claude-code global # ~/.claude.json
|
|
218
|
+
expandai mcp install claude-code project # <cwd>/.mcp.json
|
|
219
|
+
expandai mcp install cursor global # ~/.cursor/mcp.json
|
|
220
|
+
expandai mcp install cursor project # <cwd>/.cursor/mcp.json
|
|
221
|
+
expandai mcp install opencode global # ~/.config/opencode/opencode.json
|
|
222
|
+
expandai mcp install opencode project # <cwd>/opencode.json
|
|
223
|
+
expandai mcp install codex global # ~/.codex/config.toml
|
|
224
|
+
expandai mcp install codex project # <cwd>/.codex/config.toml
|
|
225
|
+
```
|
|
226
|
+
|
|
227
|
+
**Scope behavior:** `global` writes the `expandai` entry to the harness's
|
|
228
|
+
user-level MCP config — the server is discoverable in every session.
|
|
229
|
+
`project` writes to the per-directory MCP config — the server is only
|
|
230
|
+
discoverable when the harness is launched from that directory, and the
|
|
231
|
+
config file is well-suited for checking into version control.
|
|
232
|
+
|
|
233
|
+
`expandai mcp uninstall <host> <scope>` removes the entry without touching
|
|
234
|
+
other servers in the same config file.
|
|
235
|
+
|
|
236
|
+
## Uninstall
|
|
237
|
+
|
|
238
|
+
```bash
|
|
239
|
+
expandai uninstall # everything across every host and scope
|
|
240
|
+
expandai uninstall hook # all hooks (claude-code + opencode)
|
|
241
|
+
expandai uninstall mcp cursor global # just the Cursor global MCP entry
|
|
242
|
+
expandai uninstall skill # all skills across all hosts and scopes
|
|
243
|
+
```
|
|
244
|
+
|
|
245
|
+
`expandai logout` also offers an interactive multi-select cleanup when run in
|
|
246
|
+
a TTY.
|
|
247
|
+
|
|
248
|
+
## License
|
|
249
|
+
|
|
250
|
+
Apache-2.0. See `LICENSE`.
|
|
@@ -0,0 +1,231 @@
|
|
|
1
|
+
import { HttpClient } from '@effect/platform';
|
|
2
|
+
import * as Generated from '@expandai/sdk/Generated';
|
|
3
|
+
import { Effect, Schema } from 'effect';
|
|
4
|
+
import { BrowserOAuthService } from './BrowserOAuth.js';
|
|
5
|
+
import { ConfigManager, OAuthTokenExpired } from './Config.js';
|
|
6
|
+
declare const ApiRequestFailed_base: Schema.TaggedErrorClass<ApiRequestFailed, "ApiRequestFailed", {
|
|
7
|
+
readonly _tag: Schema.tag<"ApiRequestFailed">;
|
|
8
|
+
} & {
|
|
9
|
+
detail: typeof Schema.String;
|
|
10
|
+
}>;
|
|
11
|
+
/**
|
|
12
|
+
* Single user-facing error for any failure crossing the API boundary. The
|
|
13
|
+
* generated client raises a half-dozen status-specific tagged classes plus
|
|
14
|
+
* transport/decode errors; we collapse them here so the rest of the app sees
|
|
15
|
+
* one tag with a ready-made `.message` and never has to know about
|
|
16
|
+
* `Generated.ts` types.
|
|
17
|
+
*/
|
|
18
|
+
export declare class ApiRequestFailed extends ApiRequestFailed_base {
|
|
19
|
+
get message(): string;
|
|
20
|
+
}
|
|
21
|
+
declare const OAuthAuthMethodChanged_base: new <A extends Record<string, any> = {}>(args: import("effect/Types").VoidIfEmpty<{ readonly [P in keyof A as P extends "_tag" ? never : P]: A[P]; }>) => import("effect/Cause").YieldableError & {
|
|
22
|
+
readonly _tag: "OAuthAuthMethodChanged";
|
|
23
|
+
} & Readonly<A>;
|
|
24
|
+
declare class OAuthAuthMethodChanged extends OAuthAuthMethodChanged_base<Record<string, never>> {
|
|
25
|
+
}
|
|
26
|
+
declare const ApiClient_base: Effect.Service.Class<ApiClient, "@expandai/cli/ApiClient", {
|
|
27
|
+
readonly dependencies: readonly [import("effect/Layer").Layer<HttpClient.HttpClient, never, never>, import("effect/Layer").Layer<ConfigManager, import("effect/ConfigError").ConfigError, never>, import("effect/Layer").Layer<BrowserOAuthService, import("effect/ConfigError").ConfigError, never>];
|
|
28
|
+
readonly scoped: Effect.Effect<{
|
|
29
|
+
readonly fetchFetch: (options: {
|
|
30
|
+
readonly params: {
|
|
31
|
+
readonly include?: string | null | undefined;
|
|
32
|
+
};
|
|
33
|
+
readonly payload: {
|
|
34
|
+
readonly url: string;
|
|
35
|
+
readonly search?: {
|
|
36
|
+
readonly query: string;
|
|
37
|
+
readonly maxResults?: number | null | undefined;
|
|
38
|
+
readonly minScore?: number | null | undefined;
|
|
39
|
+
} | null | undefined;
|
|
40
|
+
readonly include?: {
|
|
41
|
+
readonly response?: {
|
|
42
|
+
readonly includeHeaders?: boolean | null | undefined;
|
|
43
|
+
} | null | undefined;
|
|
44
|
+
readonly meta?: boolean | null | undefined;
|
|
45
|
+
readonly markdown?: boolean | {
|
|
46
|
+
readonly [x: string]: unknown;
|
|
47
|
+
} | null | undefined;
|
|
48
|
+
readonly json?: boolean | null | undefined;
|
|
49
|
+
readonly appendix?: boolean | null | undefined;
|
|
50
|
+
readonly links?: boolean | {
|
|
51
|
+
readonly sameDomainOnly?: boolean | null | undefined;
|
|
52
|
+
readonly includePatterns?: readonly string[] | null | undefined;
|
|
53
|
+
readonly excludePatterns?: readonly string[] | null | undefined;
|
|
54
|
+
} | null | undefined;
|
|
55
|
+
readonly screenshot?: boolean | {
|
|
56
|
+
readonly fullPage?: boolean | null | undefined;
|
|
57
|
+
} | null | undefined;
|
|
58
|
+
readonly html?: boolean | {
|
|
59
|
+
readonly [x: string]: unknown;
|
|
60
|
+
} | null | undefined;
|
|
61
|
+
readonly summary?: boolean | {
|
|
62
|
+
readonly prompt?: string | null | undefined;
|
|
63
|
+
} | null | undefined;
|
|
64
|
+
} | null | undefined;
|
|
65
|
+
readonly browserConfig?: {
|
|
66
|
+
readonly scrollFullPage?: boolean | null | undefined;
|
|
67
|
+
} | null | undefined;
|
|
68
|
+
};
|
|
69
|
+
}) => Effect.Effect<string, import("./Config.js").ConfigNotWritable | import("./Config.js").ConfigParseError | import("./Config.js").NotAuthenticated | OAuthTokenExpired | import("effect/ConfigError").ConfigError | import("effect/ParseResult").ParseError | import("@effect/platform/Error").PlatformError | import("./BrowserOAuth.js").BrowserOAuthRequestFailed | ApiRequestFailed | OAuthAuthMethodChanged, never>;
|
|
70
|
+
readonly fetchFetchResult: (options: {
|
|
71
|
+
readonly params: {
|
|
72
|
+
readonly include?: string | null | undefined;
|
|
73
|
+
};
|
|
74
|
+
readonly payload: {
|
|
75
|
+
readonly url: string;
|
|
76
|
+
readonly search?: {
|
|
77
|
+
readonly query: string;
|
|
78
|
+
readonly maxResults?: number | null | undefined;
|
|
79
|
+
readonly minScore?: number | null | undefined;
|
|
80
|
+
} | null | undefined;
|
|
81
|
+
readonly include?: {
|
|
82
|
+
readonly response?: {
|
|
83
|
+
readonly includeHeaders?: boolean | null | undefined;
|
|
84
|
+
} | null | undefined;
|
|
85
|
+
readonly meta?: boolean | null | undefined;
|
|
86
|
+
readonly markdown?: boolean | {
|
|
87
|
+
readonly [x: string]: unknown;
|
|
88
|
+
} | null | undefined;
|
|
89
|
+
readonly json?: boolean | null | undefined;
|
|
90
|
+
readonly appendix?: boolean | null | undefined;
|
|
91
|
+
readonly links?: boolean | {
|
|
92
|
+
readonly sameDomainOnly?: boolean | null | undefined;
|
|
93
|
+
readonly includePatterns?: readonly string[] | null | undefined;
|
|
94
|
+
readonly excludePatterns?: readonly string[] | null | undefined;
|
|
95
|
+
} | null | undefined;
|
|
96
|
+
readonly screenshot?: boolean | {
|
|
97
|
+
readonly fullPage?: boolean | null | undefined;
|
|
98
|
+
} | null | undefined;
|
|
99
|
+
readonly html?: boolean | {
|
|
100
|
+
readonly [x: string]: unknown;
|
|
101
|
+
} | null | undefined;
|
|
102
|
+
readonly summary?: boolean | {
|
|
103
|
+
readonly prompt?: string | null | undefined;
|
|
104
|
+
} | null | undefined;
|
|
105
|
+
} | null | undefined;
|
|
106
|
+
readonly browserConfig?: {
|
|
107
|
+
readonly scrollFullPage?: boolean | null | undefined;
|
|
108
|
+
} | null | undefined;
|
|
109
|
+
};
|
|
110
|
+
}) => Effect.Effect<import("@expandai/sdk/FetchJson").FetchObjectModeResultWithJson, import("./Config.js").ConfigNotWritable | import("./Config.js").ConfigParseError | import("./Config.js").NotAuthenticated | OAuthTokenExpired | import("effect/ConfigError").ConfigError | import("effect/ParseResult").ParseError | import("@effect/platform/Error").PlatformError | import("./BrowserOAuth.js").BrowserOAuthRequestFailed | ApiRequestFailed | OAuthAuthMethodChanged, never>;
|
|
111
|
+
readonly fetchFetchJson: (options: {
|
|
112
|
+
readonly params: {
|
|
113
|
+
readonly include?: string | null | undefined;
|
|
114
|
+
};
|
|
115
|
+
readonly payload: {
|
|
116
|
+
readonly url: string;
|
|
117
|
+
readonly search?: {
|
|
118
|
+
readonly query: string;
|
|
119
|
+
readonly maxResults?: number | null | undefined;
|
|
120
|
+
readonly minScore?: number | null | undefined;
|
|
121
|
+
} | null | undefined;
|
|
122
|
+
readonly include?: {
|
|
123
|
+
readonly response?: {
|
|
124
|
+
readonly includeHeaders?: boolean | null | undefined;
|
|
125
|
+
} | null | undefined;
|
|
126
|
+
readonly meta?: boolean | null | undefined;
|
|
127
|
+
readonly markdown?: boolean | {
|
|
128
|
+
readonly [x: string]: unknown;
|
|
129
|
+
} | null | undefined;
|
|
130
|
+
readonly json?: boolean | null | undefined;
|
|
131
|
+
readonly appendix?: boolean | null | undefined;
|
|
132
|
+
readonly links?: boolean | {
|
|
133
|
+
readonly sameDomainOnly?: boolean | null | undefined;
|
|
134
|
+
readonly includePatterns?: readonly string[] | null | undefined;
|
|
135
|
+
readonly excludePatterns?: readonly string[] | null | undefined;
|
|
136
|
+
} | null | undefined;
|
|
137
|
+
readonly screenshot?: boolean | {
|
|
138
|
+
readonly fullPage?: boolean | null | undefined;
|
|
139
|
+
} | null | undefined;
|
|
140
|
+
readonly html?: boolean | {
|
|
141
|
+
readonly [x: string]: unknown;
|
|
142
|
+
} | null | undefined;
|
|
143
|
+
readonly summary?: boolean | {
|
|
144
|
+
readonly prompt?: string | null | undefined;
|
|
145
|
+
} | null | undefined;
|
|
146
|
+
} | null | undefined;
|
|
147
|
+
readonly browserConfig?: {
|
|
148
|
+
readonly scrollFullPage?: boolean | null | undefined;
|
|
149
|
+
} | null | undefined;
|
|
150
|
+
};
|
|
151
|
+
}) => Effect.Effect<import("@expandai/sdk/FetchJson").FetchObjectModeResultWithJson, import("./Config.js").ConfigNotWritable | import("./Config.js").ConfigParseError | import("./Config.js").NotAuthenticated | OAuthTokenExpired | import("effect/ConfigError").ConfigError | import("effect/ParseResult").ParseError | import("@effect/platform/Error").PlatformError | import("./BrowserOAuth.js").BrowserOAuthRequestFailed | ApiRequestFailed | OAuthAuthMethodChanged, never>;
|
|
152
|
+
readonly fetchFetchSearch: (options: {
|
|
153
|
+
readonly search: {
|
|
154
|
+
readonly query: string;
|
|
155
|
+
readonly maxResults?: number | null | undefined;
|
|
156
|
+
readonly minScore?: number | null | undefined;
|
|
157
|
+
};
|
|
158
|
+
readonly snapshotId: string;
|
|
159
|
+
readonly include?: {
|
|
160
|
+
readonly response?: {
|
|
161
|
+
readonly includeHeaders?: boolean | null | undefined;
|
|
162
|
+
} | null | undefined;
|
|
163
|
+
readonly meta?: boolean | null | undefined;
|
|
164
|
+
readonly markdown?: boolean | {
|
|
165
|
+
readonly [x: string]: unknown;
|
|
166
|
+
} | null | undefined;
|
|
167
|
+
readonly json?: boolean | null | undefined;
|
|
168
|
+
readonly appendix?: boolean | null | undefined;
|
|
169
|
+
readonly links?: boolean | {
|
|
170
|
+
readonly sameDomainOnly?: boolean | null | undefined;
|
|
171
|
+
readonly includePatterns?: readonly string[] | null | undefined;
|
|
172
|
+
readonly excludePatterns?: readonly string[] | null | undefined;
|
|
173
|
+
} | null | undefined;
|
|
174
|
+
readonly screenshot?: boolean | {
|
|
175
|
+
readonly fullPage?: boolean | null | undefined;
|
|
176
|
+
} | null | undefined;
|
|
177
|
+
readonly html?: boolean | {
|
|
178
|
+
readonly [x: string]: unknown;
|
|
179
|
+
} | null | undefined;
|
|
180
|
+
readonly summary?: boolean | {
|
|
181
|
+
readonly prompt?: string | null | undefined;
|
|
182
|
+
} | null | undefined;
|
|
183
|
+
} | null | undefined;
|
|
184
|
+
}) => Effect.Effect<import("@expandai/sdk/FetchJson").FetchSnapshotSearchResultWithJson, import("./Config.js").ConfigNotWritable | import("./Config.js").ConfigParseError | import("./Config.js").NotAuthenticated | OAuthTokenExpired | import("effect/ConfigError").ConfigError | import("effect/ParseResult").ParseError | import("@effect/platform/Error").PlatformError | import("./BrowserOAuth.js").BrowserOAuthRequestFailed | ApiRequestFailed | OAuthAuthMethodChanged, never>;
|
|
185
|
+
readonly fetchBatched: (options: {
|
|
186
|
+
readonly urls: readonly [string, ...string[]];
|
|
187
|
+
readonly include?: {
|
|
188
|
+
readonly response?: {
|
|
189
|
+
readonly includeHeaders?: boolean | null | undefined;
|
|
190
|
+
} | null | undefined;
|
|
191
|
+
readonly meta?: boolean | null | undefined;
|
|
192
|
+
readonly markdown?: boolean | {
|
|
193
|
+
readonly [x: string]: unknown;
|
|
194
|
+
} | null | undefined;
|
|
195
|
+
readonly json?: boolean | null | undefined;
|
|
196
|
+
readonly appendix?: boolean | null | undefined;
|
|
197
|
+
readonly links?: boolean | {
|
|
198
|
+
readonly sameDomainOnly?: boolean | null | undefined;
|
|
199
|
+
readonly includePatterns?: readonly string[] | null | undefined;
|
|
200
|
+
readonly excludePatterns?: readonly string[] | null | undefined;
|
|
201
|
+
} | null | undefined;
|
|
202
|
+
readonly screenshot?: boolean | {
|
|
203
|
+
readonly fullPage?: boolean | null | undefined;
|
|
204
|
+
} | null | undefined;
|
|
205
|
+
readonly html?: boolean | {
|
|
206
|
+
readonly [x: string]: unknown;
|
|
207
|
+
} | null | undefined;
|
|
208
|
+
readonly summary?: boolean | {
|
|
209
|
+
readonly prompt?: string | null | undefined;
|
|
210
|
+
} | null | undefined;
|
|
211
|
+
} | null | undefined;
|
|
212
|
+
readonly browserConfig?: {
|
|
213
|
+
readonly scrollFullPage?: boolean | null | undefined;
|
|
214
|
+
} | null | undefined;
|
|
215
|
+
}) => Effect.Effect<Generated.BatchedRun, import("./Config.js").ConfigNotWritable | import("./Config.js").ConfigParseError | import("./Config.js").NotAuthenticated | OAuthTokenExpired | import("effect/ConfigError").ConfigError | import("effect/ParseResult").ParseError | import("@effect/platform/Error").PlatformError | import("./BrowserOAuth.js").BrowserOAuthRequestFailed | ApiRequestFailed | OAuthAuthMethodChanged, never>;
|
|
216
|
+
readonly fetchGetBatched: (id: string, options: {
|
|
217
|
+
readonly include?: string | null | undefined;
|
|
218
|
+
readonly limit?: string | null | undefined;
|
|
219
|
+
readonly offset?: string | null | undefined;
|
|
220
|
+
}) => Effect.Effect<Generated.BatchedStatus, import("./Config.js").ConfigNotWritable | import("./Config.js").ConfigParseError | import("./Config.js").NotAuthenticated | OAuthTokenExpired | import("effect/ConfigError").ConfigError | import("effect/ParseResult").ParseError | import("@effect/platform/Error").PlatformError | import("./BrowserOAuth.js").BrowserOAuthRequestFailed | ApiRequestFailed | OAuthAuthMethodChanged, never>;
|
|
221
|
+
}, never, ConfigManager | BrowserOAuthService | HttpClient.HttpClient>;
|
|
222
|
+
}>;
|
|
223
|
+
/**
|
|
224
|
+
* Resolves outgoing API auth per call. When the current request scope carries
|
|
225
|
+
* an `Authorization` header (via `CurrentRequestHeaders`), that value is
|
|
226
|
+
* forwarded; otherwise auth comes from `~/.config/expandai/config.json`.
|
|
227
|
+
*/
|
|
228
|
+
export declare class ApiClient extends ApiClient_base {
|
|
229
|
+
}
|
|
230
|
+
export {};
|
|
231
|
+
//# sourceMappingURL=ApiClient.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"ApiClient.d.ts","sourceRoot":"","sources":["../../src/ApiClient.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,UAAU,EAAyC,MAAM,kBAAkB,CAAA;AAGpF,OAAO,KAAK,SAAS,MAAM,yBAAyB,CAAA;AAEpD,OAAO,EAA4B,MAAM,EAAiC,MAAM,EAAE,MAAM,QAAQ,CAAA;AAChG,OAAO,EAAE,mBAAmB,EAAE,MAAM,mBAAmB,CAAA;AACvD,OAAO,EAAE,aAAa,EAAe,iBAAiB,EAAE,MAAM,aAAa,CAAA;;;;;;AAG3E;;;;;;GAMG;AACH,qBAAa,gBAAiB,SAAQ,qBAEpC;IACD,IAAI,OAAO,WAEV;CACD;;;;AAcD,cAAM,sBAAuB,SAAQ,4BAA2C,MAAM,CAAC,MAAM,EAAE,KAAK,CAAC,CAAC;CAAG;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;AA8DzG;;;;GAIG;AACH,qBAAa,SAAU,SAAQ,cAwJ7B;CAAG"}
|
|
@@ -0,0 +1,23 @@
|
|
|
1
|
+
import { Command } from '@effect/cli';
|
|
2
|
+
import { Effect } from 'effect';
|
|
3
|
+
import { BrowserOAuthService } from './BrowserOAuth.js';
|
|
4
|
+
import { ApiKeyConfig, ConfigManager, OAuthConfig } from './Config.js';
|
|
5
|
+
import { Uninstall } from './Install/Uninstall.js';
|
|
6
|
+
type AuthMethod = typeof ApiKeyConfig.Type | typeof OAuthConfig.Type;
|
|
7
|
+
/** Render a user-facing description of the current auth state. Pure given DateTime.now. */
|
|
8
|
+
export declare const formatAuthStatus: (authMethod: AuthMethod) => Effect.Effect<string, never, never>;
|
|
9
|
+
declare const Authentication_base: Effect.Service.Class<Authentication, "@expandai/cli/Authentication", {
|
|
10
|
+
readonly dependencies: readonly [import("effect/Layer").Layer<ConfigManager, import("effect/ConfigError").ConfigError, never>, import("effect/Layer").Layer<BrowserOAuthService, import("effect/ConfigError").ConfigError, never>, import("effect/Layer").Layer<Uninstall, import("effect/ConfigError").ConfigError | import("@effect/platform/Error").BadArgument, never>];
|
|
11
|
+
readonly effect: Effect.Effect<{
|
|
12
|
+
readonly login: () => Effect.Effect<void, unknown, import("@effect/platform/Terminal").Terminal>;
|
|
13
|
+
readonly whoami: () => Effect.Effect<void, import("./Config.js").ConfigParseError | import("./Config.js").NotAuthenticated | import("effect/ConfigError").ConfigError | import("@effect/platform/Error").PlatformError, never>;
|
|
14
|
+
readonly logout: () => Effect.Effect<void, import("./Config.js").ConfigNotWritable | import("effect/ParseResult").ParseError | import("@effect/platform/Error").PlatformError | import("./Install/Domain.js").McpParseError | import("./Install/Domain.js").McpWriteError | import("@effect/platform/Terminal").QuitException, import("@effect/platform/Terminal").Terminal>;
|
|
15
|
+
}, never, ConfigManager | BrowserOAuthService | Uninstall>;
|
|
16
|
+
}>;
|
|
17
|
+
export declare class Authentication extends Authentication_base {
|
|
18
|
+
}
|
|
19
|
+
export declare const LoginCommand: Command.Command<"login", Authentication | import("@effect/platform/Terminal").Terminal, unknown, {}>;
|
|
20
|
+
export declare const WhoamiCommand: Command.Command<"whoami", Authentication, import("./Config.js").ConfigParseError | import("./Config.js").NotAuthenticated | import("effect/ConfigError").ConfigError | import("@effect/platform/Error").PlatformError, {}>;
|
|
21
|
+
export declare const LogoutCommand: Command.Command<"logout", Authentication | import("@effect/platform/Terminal").Terminal, import("./Config.js").ConfigNotWritable | import("effect/ParseResult").ParseError | import("@effect/platform/Error").PlatformError | import("./Install/Domain.js").McpParseError | import("./Install/Domain.js").McpWriteError | import("@effect/platform/Terminal").QuitException, {}>;
|
|
22
|
+
export {};
|
|
23
|
+
//# sourceMappingURL=Authentication.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"Authentication.d.ts","sourceRoot":"","sources":["../../src/Authentication.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,OAAO,EAAU,MAAM,aAAa,CAAA;AAC7C,OAAO,EAA+B,MAAM,EAAiC,MAAM,QAAQ,CAAA;AAE3F,OAAO,EAAE,mBAAmB,EAAE,MAAM,mBAAmB,CAAA;AACvD,OAAO,EAAU,YAAY,EAAE,aAAa,EAAE,WAAW,EAAE,MAAM,aAAa,CAAA;AAC9E,OAAO,EAAE,SAAS,EAAE,MAAM,wBAAwB,CAAA;AAElD,KAAK,UAAU,GAAG,OAAO,YAAY,CAAC,IAAI,GAAG,OAAO,WAAW,CAAC,IAAI,CAAA;AAEpE,2FAA2F;AAC3F,eAAO,MAAM,gBAAgB,iEAe3B,CAAA;;;;;;;;;AAEF,qBAAa,cAAe,SAAQ,mBAyHlC;CAAG;AAEL,eAAO,MAAM,YAAY,sGAGxB,CAAA;AAED,eAAO,MAAM,aAAa,4NAGzB,CAAA;AAED,eAAO,MAAM,aAAa,kXAGzB,CAAA"}
|
|
@@ -0,0 +1,99 @@
|
|
|
1
|
+
import { HttpClient } from '@effect/platform';
|
|
2
|
+
import { Duration, Effect, Schema } from 'effect';
|
|
3
|
+
import { ConfigManager } from './Config.js';
|
|
4
|
+
declare const TokenResponse_base: Schema.Class<TokenResponse, {
|
|
5
|
+
access_token: typeof Schema.String;
|
|
6
|
+
refresh_token: Schema.optional<typeof Schema.String>;
|
|
7
|
+
expires_in: Schema.transform<typeof Schema.Number, typeof Schema.DurationFromSelf>;
|
|
8
|
+
token_type: typeof Schema.String;
|
|
9
|
+
scope: Schema.optional<typeof Schema.String>;
|
|
10
|
+
}, Schema.Struct.Encoded<{
|
|
11
|
+
access_token: typeof Schema.String;
|
|
12
|
+
refresh_token: Schema.optional<typeof Schema.String>;
|
|
13
|
+
expires_in: Schema.transform<typeof Schema.Number, typeof Schema.DurationFromSelf>;
|
|
14
|
+
token_type: typeof Schema.String;
|
|
15
|
+
scope: Schema.optional<typeof Schema.String>;
|
|
16
|
+
}>, never, {
|
|
17
|
+
readonly access_token: string;
|
|
18
|
+
} & {
|
|
19
|
+
readonly expires_in: Duration.Duration;
|
|
20
|
+
} & {
|
|
21
|
+
readonly token_type: string;
|
|
22
|
+
} & {
|
|
23
|
+
readonly refresh_token?: string | undefined;
|
|
24
|
+
} & {
|
|
25
|
+
readonly scope?: string | undefined;
|
|
26
|
+
}, {}, {}>;
|
|
27
|
+
export declare class TokenResponse extends TokenResponse_base {
|
|
28
|
+
}
|
|
29
|
+
declare const BrowserOAuthRequestFailed_base: Schema.TaggedErrorClass<BrowserOAuthRequestFailed, "BrowserOAuthRequestFailed", {
|
|
30
|
+
readonly _tag: Schema.tag<"BrowserOAuthRequestFailed">;
|
|
31
|
+
} & {
|
|
32
|
+
endpoint: typeof Schema.String;
|
|
33
|
+
error: typeof Schema.Defect;
|
|
34
|
+
status: Schema.optional<typeof Schema.Number>;
|
|
35
|
+
}>;
|
|
36
|
+
export declare class BrowserOAuthRequestFailed extends BrowserOAuthRequestFailed_base {
|
|
37
|
+
get message(): string;
|
|
38
|
+
}
|
|
39
|
+
declare const BrowserOAuthCallbackError_base: Schema.TaggedErrorClass<BrowserOAuthCallbackError, "BrowserOAuthCallbackError", {
|
|
40
|
+
readonly _tag: Schema.tag<"BrowserOAuthCallbackError">;
|
|
41
|
+
} & {
|
|
42
|
+
error: typeof Schema.String;
|
|
43
|
+
errorDescription: Schema.optional<typeof Schema.String>;
|
|
44
|
+
}>;
|
|
45
|
+
export declare class BrowserOAuthCallbackError extends BrowserOAuthCallbackError_base {
|
|
46
|
+
get message(): string;
|
|
47
|
+
}
|
|
48
|
+
declare const BrowserOAuthMissingCode_base: Schema.TaggedErrorClass<BrowserOAuthMissingCode, "BrowserOAuthMissingCode", {
|
|
49
|
+
readonly _tag: Schema.tag<"BrowserOAuthMissingCode">;
|
|
50
|
+
}>;
|
|
51
|
+
export declare class BrowserOAuthMissingCode extends BrowserOAuthMissingCode_base {
|
|
52
|
+
get message(): string;
|
|
53
|
+
}
|
|
54
|
+
declare const BrowserOAuthStateMismatch_base: Schema.TaggedErrorClass<BrowserOAuthStateMismatch, "BrowserOAuthStateMismatch", {
|
|
55
|
+
readonly _tag: Schema.tag<"BrowserOAuthStateMismatch">;
|
|
56
|
+
}>;
|
|
57
|
+
export declare class BrowserOAuthStateMismatch extends BrowserOAuthStateMismatch_base {
|
|
58
|
+
get message(): string;
|
|
59
|
+
}
|
|
60
|
+
declare const BrowserOAuthLoopbackFailed_base: Schema.TaggedErrorClass<BrowserOAuthLoopbackFailed, "BrowserOAuthLoopbackFailed", {
|
|
61
|
+
readonly _tag: Schema.tag<"BrowserOAuthLoopbackFailed">;
|
|
62
|
+
} & {
|
|
63
|
+
error: typeof Schema.Defect;
|
|
64
|
+
}>;
|
|
65
|
+
export declare class BrowserOAuthLoopbackFailed extends BrowserOAuthLoopbackFailed_base {
|
|
66
|
+
get message(): string;
|
|
67
|
+
}
|
|
68
|
+
declare const BrowserOAuthTimedOut_base: Schema.TaggedErrorClass<BrowserOAuthTimedOut, "BrowserOAuthTimedOut", {
|
|
69
|
+
readonly _tag: Schema.tag<"BrowserOAuthTimedOut">;
|
|
70
|
+
}>;
|
|
71
|
+
export declare class BrowserOAuthTimedOut extends BrowserOAuthTimedOut_base {
|
|
72
|
+
get message(): string;
|
|
73
|
+
}
|
|
74
|
+
interface AuthorizeUrlInput {
|
|
75
|
+
readonly apiUrl: URL;
|
|
76
|
+
readonly redirectUri: URL;
|
|
77
|
+
readonly state: string;
|
|
78
|
+
readonly codeChallenge: string;
|
|
79
|
+
}
|
|
80
|
+
interface ExchangeCodeInput {
|
|
81
|
+
readonly code: string;
|
|
82
|
+
readonly redirectUri: URL;
|
|
83
|
+
readonly codeVerifier: string;
|
|
84
|
+
}
|
|
85
|
+
export declare const createCodeChallenge: (codeVerifier: string) => Effect.Effect<string, never, never>;
|
|
86
|
+
export declare const buildAuthorizeUrl: (args_0: AuthorizeUrlInput) => Effect.Effect<URL, never, never>;
|
|
87
|
+
declare const BrowserOAuthService_base: Effect.Service.Class<BrowserOAuthService, "@expandai/cli/BrowserOAuthService", {
|
|
88
|
+
readonly dependencies: readonly [import("effect/Layer").Layer<HttpClient.HttpClient, never, never>, import("effect/Layer").Layer<ConfigManager, import("effect/ConfigError").ConfigError, never>];
|
|
89
|
+
readonly effect: Effect.Effect<{
|
|
90
|
+
readonly exchangeCode: (args_0: ExchangeCodeInput) => Effect.Effect<TokenResponse, import("./Config.js").ConfigParseError | import("effect/ConfigError").ConfigError | import("@effect/platform/Error").PlatformError | BrowserOAuthRequestFailed, never>;
|
|
91
|
+
readonly refreshToken: (refreshToken: string) => Effect.Effect<TokenResponse, import("./Config.js").ConfigParseError | import("effect/ConfigError").ConfigError | import("@effect/platform/Error").PlatformError | BrowserOAuthRequestFailed, never>;
|
|
92
|
+
readonly saveToken: (tokenResponse: TokenResponse) => Effect.Effect<void, import("./Config.js").ConfigNotWritable | import("effect/ParseResult").ParseError, never>;
|
|
93
|
+
readonly login: <R>(openAuthorizeUrl: (authorizeUrl: URL) => Effect.Effect<void, unknown, R>) => Effect.Effect<undefined, unknown, R>;
|
|
94
|
+
}, never, ConfigManager | HttpClient.HttpClient>;
|
|
95
|
+
}>;
|
|
96
|
+
export declare class BrowserOAuthService extends BrowserOAuthService_base {
|
|
97
|
+
}
|
|
98
|
+
export {};
|
|
99
|
+
//# sourceMappingURL=BrowserOAuth.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"BrowserOAuth.d.ts","sourceRoot":"","sources":["../../src/BrowserOAuth.ts"],"names":[],"mappings":"AAEA,OAAO,EAAE,UAAU,EAAyC,MAAM,kBAAkB,CAAA;AAEpF,OAAO,EAAY,QAAQ,EAAE,MAAM,EAAyB,MAAM,EAAE,MAAM,QAAQ,CAAA;AAClF,OAAO,EAAE,aAAa,EAAe,MAAM,aAAa,CAAA;;;;;;;;;;;;;;;;;;;;;;;;AAexD,qBAAa,aAAc,SAAQ,kBAMjC;CAAG;;;;;;;;AAEL,qBAAa,yBAA0B,SAAQ,8BAO9C;IACA,IAAI,OAAO,WAEV;CACD;;;;;;;AAED,qBAAa,yBAA0B,SAAQ,8BAM9C;IACA,IAAI,OAAO,WAEV;CACD;;;;AAED,qBAAa,uBAAwB,SAAQ,4BAG5C;IACA,IAAI,OAAO,WAEV;CACD;;;;AAED,qBAAa,yBAA0B,SAAQ,8BAG9C;IACA,IAAI,OAAO,WAEV;CACD;;;;;;AAED,qBAAa,0BAA2B,SAAQ,+BAK/C;IACA,IAAI,OAAO,WAEV;CACD;;;;AAED,qBAAa,oBAAqB,SAAQ,yBAAsE;IAC/G,IAAI,OAAO,WAEV;CACD;AAID,UAAU,iBAAiB;IAC1B,QAAQ,CAAC,MAAM,EAAE,GAAG,CAAA;IACpB,QAAQ,CAAC,WAAW,EAAE,GAAG,CAAA;IACzB,QAAQ,CAAC,KAAK,EAAE,MAAM,CAAA;IACtB,QAAQ,CAAC,aAAa,EAAE,MAAM,CAAA;CAC9B;AAED,UAAU,iBAAiB;IAC1B,QAAQ,CAAC,IAAI,EAAE,MAAM,CAAA;IACrB,QAAQ,CAAC,WAAW,EAAE,GAAG,CAAA;IACzB,QAAQ,CAAC,YAAY,EAAE,MAAM,CAAA;CAC7B;AAgBD,eAAO,MAAM,mBAAmB,+DAE9B,CAAA;AAEF,eAAO,MAAM,iBAAiB,iEAe5B,CAAA;;;;;;;yBA6LgE,CAAC,mCAC/B,GAAG,KAAK,MAAM,CAAC,MAAM,CAAC,IAAI,EAAE,OAAO,EAAE,CAAC,CAAC;;;AAhF3E,qBAAa,mBAAoB,SAAQ,wBAkHvC;CAAG"}
|
|
@@ -0,0 +1,30 @@
|
|
|
1
|
+
import { Command, HelpDoc } from '@effect/cli';
|
|
2
|
+
import { Effect, Option, Schema } from 'effect';
|
|
3
|
+
declare const MarkdownUnavailable_base: Schema.TaggedErrorClass<MarkdownUnavailable, "MarkdownUnavailable", {
|
|
4
|
+
readonly _tag: Schema.tag<"MarkdownUnavailable">;
|
|
5
|
+
} & {
|
|
6
|
+
url: typeof Schema.String;
|
|
7
|
+
}>;
|
|
8
|
+
export declare class MarkdownUnavailable extends MarkdownUnavailable_base {
|
|
9
|
+
get message(): string;
|
|
10
|
+
}
|
|
11
|
+
declare const SnippetsUnavailable_base: Schema.TaggedErrorClass<SnippetsUnavailable, "SnippetsUnavailable", {
|
|
12
|
+
readonly _tag: Schema.tag<"SnippetsUnavailable">;
|
|
13
|
+
} & {
|
|
14
|
+
url: typeof Schema.String;
|
|
15
|
+
query: typeof Schema.String;
|
|
16
|
+
}>;
|
|
17
|
+
export declare class SnippetsUnavailable extends SnippetsUnavailable_base {
|
|
18
|
+
get message(): string;
|
|
19
|
+
}
|
|
20
|
+
export declare const parseUrlArg: (raw: string) => Effect.Effect<URL, HelpDoc.HelpDoc, never>;
|
|
21
|
+
interface FetchCommandConfig {
|
|
22
|
+
readonly url: URL;
|
|
23
|
+
readonly format: 'text' | 'json';
|
|
24
|
+
readonly search: Option.Option<string>;
|
|
25
|
+
readonly maxResults: number;
|
|
26
|
+
readonly minScore: number;
|
|
27
|
+
}
|
|
28
|
+
export declare const FetchCommand: Command.Command<'fetch', never, unknown, FetchCommandConfig>;
|
|
29
|
+
export {};
|
|
30
|
+
//# sourceMappingURL=Fetch.d.ts.map
|