careervivid 1.12.6 → 1.12.8
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 +250 -150
- package/dist/agent/providers/AnthropicProvider.d.ts +1 -0
- package/dist/agent/providers/AnthropicProvider.d.ts.map +1 -1
- package/dist/agent/providers/AnthropicProvider.js +30 -1
- package/dist/agent/providers/OpenAIProvider.d.ts +1 -0
- package/dist/agent/providers/OpenAIProvider.d.ts.map +1 -1
- package/dist/agent/providers/OpenAIProvider.js +43 -1
- package/package.json +1 -1
package/README.md
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
# careervivid · CLI
|
|
2
2
|
|
|
3
|
-
> **Your AI-powered career terminal —
|
|
3
|
+
> **Your AI-powered career terminal — autonomous job applications, resume editing, job pipeline tracking, and portfolio publishing from the command line.**
|
|
4
4
|
|
|
5
5
|
[](https://www.npmjs.com/package/careervivid)
|
|
6
6
|
[](LICENSE)
|
|
@@ -12,17 +12,19 @@
|
|
|
12
12
|
|
|
13
13
|
- [Quick Start](#quick-start)
|
|
14
14
|
- [Commands](#commands)
|
|
15
|
-
- [cv agent](#cv-agent) ⭐ **
|
|
16
|
-
- [cv
|
|
15
|
+
- [cv agent](#cv-agent) ⭐ **AI Agent**
|
|
16
|
+
- [cv agent --jobs](#cv-agent---jobs) 🤖 **Autonomous Job Applications**
|
|
17
|
+
- [cv agent --resume](#cv-agent---resume) 📄 **Resume CRUD**
|
|
17
18
|
- [cv jobs](#cv-jobs)
|
|
19
|
+
- [cv publish](#cv-publish)
|
|
18
20
|
- [cv whiteboard](#cv-whiteboard)
|
|
19
|
-
- [cv workspace](#cv-workspace)
|
|
20
21
|
- [cv profile](#cv-profile)
|
|
21
22
|
- [cv auth](#cv-auth)
|
|
22
23
|
- [cv login](#cv-login)
|
|
23
24
|
- [cv config](#cv-config)
|
|
24
25
|
- [AI Credits](#ai-credits)
|
|
25
26
|
- [Bring Your Own API Key (BYO)](#bring-your-own-api-key-byo)
|
|
27
|
+
- [browser-use Setup (Autonomous Apply)](#browser-use-setup-autonomous-apply)
|
|
26
28
|
- [Whiteboard Templates](#whiteboard-templates)
|
|
27
29
|
- [AI Agent Integration (MCP / CI)](#ai-agent-integration-mcp--ci)
|
|
28
30
|
- [Updating](#updating)
|
|
@@ -42,11 +44,11 @@ cv login
|
|
|
42
44
|
# → copy your API key, then:
|
|
43
45
|
cv auth set-key cv_live_YOUR_KEY_HERE
|
|
44
46
|
|
|
45
|
-
# 3. Start the AI agent
|
|
47
|
+
# 3. Start the AI agent
|
|
46
48
|
cv agent
|
|
47
49
|
|
|
48
|
-
# 4. Or
|
|
49
|
-
cv
|
|
50
|
+
# 4. Or jump straight into job-hunting mode
|
|
51
|
+
cv agent --jobs
|
|
50
52
|
```
|
|
51
53
|
|
|
52
54
|
> **Free tier includes 100 AI credits/month** — no credit card required.
|
|
@@ -59,132 +61,202 @@ cv publish my-article.md --tags "typescript,react"
|
|
|
59
61
|
|
|
60
62
|
### `cv agent`
|
|
61
63
|
|
|
62
|
-
An **autonomous AI agent** that runs interactively in your terminal.
|
|
64
|
+
An **autonomous AI agent** that runs interactively in your terminal. Choose from CareerVivid Cloud (credits deducted from your account) or Bring Your Own API Key.
|
|
63
65
|
|
|
64
66
|
```bash
|
|
65
67
|
cv agent # General-purpose agent (Gemini Flash Lite)
|
|
66
|
-
cv agent --resume #
|
|
67
|
-
cv agent --jobs # Job-hunting mode: search,
|
|
68
|
+
cv agent --resume # Resume CRUD mode: read, update fields, tailor
|
|
69
|
+
cv agent --jobs # Job-hunting mode: search, apply, track pipeline
|
|
68
70
|
cv agent --coding # Full coding toolkit: file I/O, shell execution, search
|
|
69
|
-
cv agent --pro # Gemini Pro with extended thinking
|
|
71
|
+
cv agent --pro # Gemini Pro with extended thinking
|
|
70
72
|
```
|
|
71
73
|
|
|
72
74
|
**Options:**
|
|
73
75
|
|
|
74
76
|
| Option | Description |
|
|
75
77
|
|---|---|
|
|
76
|
-
| `--resume` |
|
|
77
|
-
| `--jobs` |
|
|
78
|
+
| `--resume` | Resume CRUD tools — read, set fields, tailor for a job, delete |
|
|
79
|
+
| `--jobs` | Job hunting + autonomous apply tools |
|
|
78
80
|
| `--coding` | Enable full coding tool suite (file read/write, shell, search) |
|
|
79
81
|
| `--pro` | Use `gemini-3.1-pro-preview` with thinking mode |
|
|
80
82
|
| `--think <budget>` | Enable thinking mode with a specific token budget (e.g. `8192`) |
|
|
81
|
-
| `--verbose` | Show thinking tokens in output
|
|
83
|
+
| `--verbose` | Show thinking tokens in output |
|
|
82
84
|
| `--provider <name>` | Override provider: `careervivid` \| `openai` \| `anthropic` \| `openrouter` \| `gemini` \| `custom` |
|
|
83
85
|
| `--model <model>` | Override model (e.g. `gpt-4o`, `claude-opus-4-5`) |
|
|
84
86
|
| `--api-key <key>` | BYO API key for this session (not saved) |
|
|
85
87
|
| `--base-url <url>` | Custom OpenAI-compatible base URL |
|
|
86
88
|
|
|
87
|
-
**
|
|
89
|
+
**Configure your default provider:**
|
|
88
90
|
|
|
89
91
|
```bash
|
|
90
|
-
|
|
91
|
-
|
|
92
|
+
cv agent config
|
|
93
|
+
# → Interactive wizard: pick provider, model, API key
|
|
94
|
+
```
|
|
92
95
|
|
|
93
|
-
|
|
94
|
-
cv agent --resume
|
|
96
|
+
---
|
|
95
97
|
|
|
96
|
-
|
|
97
|
-
cv agent --provider openai --model gpt-4o --api-key sk-...
|
|
98
|
+
### `cv agent --jobs`
|
|
98
99
|
|
|
99
|
-
|
|
100
|
-
cv agent --provider anthropic --model claude-opus-4-5 --api-key sk-ant-...
|
|
100
|
+
The most powerful mode. A conversational agent that thinks like a senior recruiter, manages your pipeline, and can **autonomously fill out job applications** using [browser-use](https://github.com/browser-use/browser-use).
|
|
101
101
|
|
|
102
|
-
|
|
103
|
-
cv agent --
|
|
102
|
+
```bash
|
|
103
|
+
cv agent --jobs
|
|
104
104
|
```
|
|
105
105
|
|
|
106
|
-
**
|
|
106
|
+
**What it can do in a conversation:**
|
|
107
|
+
|
|
108
|
+
| You say... | Agent action |
|
|
109
|
+
|---|---|
|
|
110
|
+
| `"Find me ML engineering jobs"` | `search_jobs` → scores results vs. resume → `verify_search_results` to confirm all URLs work |
|
|
111
|
+
| `"Apply to this job: <URL>"` | `apply_to_job` → launches browser → fills form → stops before Submit for your review |
|
|
112
|
+
| `"What's in my pipeline?"` | `list_local_jobs` → shows Kanban board |
|
|
113
|
+
| `"What should I work on next?"` | `score_pipeline` → priority-ranked by attention × excitement × fit |
|
|
114
|
+
| `"I got an interview at Stripe"` | `update_local_job` → sets status to Interviewing, suggests follow-up |
|
|
115
|
+
| `"What am I neglecting?"` | `flag_stale_jobs` → surfaces cold applications |
|
|
116
|
+
| `"Show me my analytics"` | `get_pipeline_metrics` → apply rate, avg score, salary data |
|
|
117
|
+
|
|
118
|
+
**Autonomous Apply Harness** (`apply_to_job` tool):
|
|
119
|
+
|
|
120
|
+
The agent uses a multi-stage harness to fill job applications:
|
|
121
|
+
|
|
122
|
+
1. **URL Verification** — Every job link is verified live before the agent acts. Broken, hallucinated, or redirect-to-homepage URLs are rejected automatically.
|
|
123
|
+
2. **ATS Detection** — Automatically detects Ashby, Greenhouse, Lever, Workday, iCIMS, and more.
|
|
124
|
+
3. **TypeScript Adapter** — Fast-fills known fields (firstName, email, phone, LinkedIn, GitHub) using pre-loaded profile data.
|
|
125
|
+
4. **browser-use AI handoff** — For complex fields (cover letter, work auth, custom questions), the browser-use agent takes over with a rich task prompt built from your resume.
|
|
126
|
+
5. **Manual review gate** — The browser stays open. The agent **never** clicks Submit — you review and submit yourself.
|
|
127
|
+
|
|
128
|
+
> **Requires browser-use setup** — see [browser-use Setup](#browser-use-setup-autonomous-apply).
|
|
129
|
+
|
|
130
|
+
**Pipeline tracking (local CSV):**
|
|
131
|
+
|
|
132
|
+
The jobs agent also manages a local `jobs.csv` pipeline (v2 schema) with 8 attention metrics:
|
|
133
|
+
|
|
134
|
+
| Field | Description |
|
|
135
|
+
|---|---|
|
|
136
|
+
| `attention_score` (1–10) | How top-of-mind is this company? |
|
|
137
|
+
| `excitement` (1–10) | Pure enthusiasm for the role |
|
|
138
|
+
| `apply_effort` | Low / Medium / High |
|
|
139
|
+
| `prep_time_hours` | Estimated research hours |
|
|
140
|
+
| `company_stage` | Seed / Series A-C / Public / Enterprise |
|
|
141
|
+
| `open_roles_count` | How many roles are currently open |
|
|
142
|
+
| `interview_rounds` | Known number of interview rounds |
|
|
143
|
+
| `last_activity_date` | Auto-stamped on every update |
|
|
144
|
+
|
|
145
|
+
**Priority Score = 40% attention + 30% excitement + 20% fit + 10% recency**
|
|
146
|
+
|
|
147
|
+
---
|
|
148
|
+
|
|
149
|
+
### `cv agent --resume`
|
|
150
|
+
|
|
151
|
+
Full CRUD control over your CareerVivid resume from the terminal.
|
|
107
152
|
|
|
108
153
|
```bash
|
|
109
|
-
cv agent
|
|
110
|
-
# → Interactive wizard: pick provider, model, API key
|
|
154
|
+
cv agent --resume
|
|
111
155
|
```
|
|
112
156
|
|
|
113
|
-
|
|
157
|
+
**Available tools:**
|
|
114
158
|
|
|
115
|
-
|
|
159
|
+
| Tool | What you can say |
|
|
160
|
+
|---|---|
|
|
161
|
+
| `get_resume` | `"Show me my resume"` / `"Load my resume"` |
|
|
162
|
+
| `list_resumes` | `"What resumes do I have?"` |
|
|
163
|
+
| `set_resume_fields` | `"Set my last name to Zhu"` / `"Update my phone to +1-408-599-4164"` |
|
|
164
|
+
| `tailor_resume` | `"Tailor my resume for this job description: ..."` |
|
|
165
|
+
| `delete_resume` | `"Delete the old untitled resume"` |
|
|
116
166
|
|
|
117
|
-
|
|
167
|
+
**Supported fields for `set_resume_fields`:**
|
|
118
168
|
|
|
119
169
|
```
|
|
120
|
-
|
|
121
|
-
|
|
170
|
+
firstName, lastName, email, phone
|
|
171
|
+
address, city, state, country, postalCode
|
|
172
|
+
jobTitle, currentCompany
|
|
173
|
+
linkedin, github, portfolio
|
|
174
|
+
summary (professional summary)
|
|
175
|
+
addSkill / removeSkill
|
|
176
|
+
resumeTitle (document name)
|
|
122
177
|
```
|
|
123
178
|
|
|
124
|
-
|
|
125
|
-
|---|---|
|
|
126
|
-
| `-t, --title <title>` | Post title (auto-inferred from first `#` heading if omitted) |
|
|
127
|
-
| `--type <type>` | `article` \| `whiteboard` (auto-inferred from file extension) |
|
|
128
|
-
| `--format <format>` | `markdown` \| `mermaid` (auto-inferred from file extension) |
|
|
129
|
-
| `--tags <tags>` | Comma-separated tags, e.g. `typescript,firebase,react` |
|
|
130
|
-
| `--cover <url>` | URL to a cover image |
|
|
131
|
-
| `--dry-run` | Validate payload without publishing |
|
|
132
|
-
| `--json` | Machine-readable JSON output (ideal for AI agents) |
|
|
179
|
+
**Example conversation:**
|
|
133
180
|
|
|
134
|
-
```
|
|
135
|
-
|
|
136
|
-
|
|
137
|
-
|
|
181
|
+
```
|
|
182
|
+
You: Set my last name to Zhu and my phone to +1-408-599-4164
|
|
183
|
+
Agent: ✅ Resume updated — review at https://careervivid.app/edit/...
|
|
184
|
+
|
|
185
|
+
You: Add Python and TypeScript to my skills
|
|
186
|
+
Agent: ✅ Skills updated
|
|
187
|
+
|
|
188
|
+
You: Tailor my resume for this job description: [paste JD]
|
|
189
|
+
Agent: ✅ Tailored copy created — https://careervivid.app/edit/...
|
|
138
190
|
```
|
|
139
191
|
|
|
140
192
|
---
|
|
141
193
|
|
|
142
194
|
### `cv jobs`
|
|
143
195
|
|
|
144
|
-
|
|
196
|
+
Non-interactive job commands (use `cv agent --jobs` for a conversational experience).
|
|
145
197
|
|
|
146
198
|
| Subcommand | Description |
|
|
147
199
|
|---|---|
|
|
148
|
-
| `cv jobs hunt` | AI-powered job search scored against your resume → auto-saves to
|
|
149
|
-
| `cv jobs
|
|
200
|
+
| `cv jobs hunt` | AI-powered job search scored against your resume → auto-saves to tracker |
|
|
201
|
+
| `cv jobs apply <url>` | Autonomous apply harness for a specific URL |
|
|
202
|
+
| `cv jobs update` | Interactively update a job application status |
|
|
150
203
|
| `cv jobs list` | View your current job tracker board |
|
|
151
204
|
|
|
152
205
|
```bash
|
|
153
206
|
cv jobs hunt --role "Software Engineer" --score 60
|
|
207
|
+
cv jobs apply https://jobs.ashbyhq.com/openai/...
|
|
154
208
|
cv jobs list
|
|
155
209
|
cv jobs update
|
|
156
210
|
```
|
|
157
211
|
|
|
158
|
-
> **Tip:** Use `cv agent --jobs` for a conversational job-hunting experience instead.
|
|
159
|
-
|
|
160
212
|
---
|
|
161
213
|
|
|
162
|
-
### `cv
|
|
214
|
+
### `cv publish`
|
|
163
215
|
|
|
164
|
-
|
|
216
|
+
Publish a Markdown article or Mermaid diagram to your CareerVivid portfolio.
|
|
165
217
|
|
|
166
|
-
|
|
218
|
+
```bash
|
|
219
|
+
cv publish <file> [options]
|
|
220
|
+
cv publish - # read from stdin
|
|
221
|
+
```
|
|
222
|
+
|
|
223
|
+
| Option | Description |
|
|
167
224
|
|---|---|
|
|
168
|
-
|
|
|
169
|
-
|
|
|
170
|
-
|
|
|
225
|
+
| `-t, --title <title>` | Post title (auto-inferred from first `#` heading if omitted) |
|
|
226
|
+
| `--type <type>` | `article` \| `whiteboard` (auto-inferred from file extension) |
|
|
227
|
+
| `--format <format>` | `markdown` \| `mermaid` (auto-inferred from file extension) |
|
|
228
|
+
| `--tags <tags>` | Comma-separated tags, e.g. `typescript,firebase,react` |
|
|
229
|
+
| `--cover <url>` | URL to a cover image |
|
|
230
|
+
| `--public` | Publish as public (visible to all users) |
|
|
231
|
+
| `--private` | Publish as private (only visible to you — **this is the default**) |
|
|
232
|
+
| `--dry-run` | Validate payload without publishing |
|
|
233
|
+
| `--json` | Machine-readable JSON output |
|
|
171
234
|
|
|
172
|
-
**
|
|
235
|
+
> **Privacy default:** All articles published via `cv publish` or `cv agent` are **private by default**. Use `--public` to make them visible to the community.
|
|
173
236
|
|
|
174
237
|
```bash
|
|
175
|
-
cv
|
|
176
|
-
cv
|
|
238
|
+
cv publish article.md --title "How I Built a CLI" --tags "node,typescript"
|
|
239
|
+
cv publish article.md --public # share with community
|
|
240
|
+
cv publish architecture.mmd --title "System Architecture"
|
|
241
|
+
cat writeup.md | cv publish - --title "Architecture Breakdown" --json
|
|
177
242
|
```
|
|
178
243
|
|
|
179
244
|
---
|
|
180
245
|
|
|
181
|
-
### `cv
|
|
246
|
+
### `cv whiteboard`
|
|
182
247
|
|
|
183
|
-
|
|
248
|
+
Create and publish Mermaid architecture diagrams.
|
|
184
249
|
|
|
185
250
|
| Subcommand | Description |
|
|
186
251
|
|---|---|
|
|
187
|
-
| `cv
|
|
252
|
+
| `cv whiteboard new [file]` | Scaffold a Mermaid diagram from a built-in template |
|
|
253
|
+
| `cv whiteboard publish <file>` | Publish a `.mmd` diagram to your portfolio |
|
|
254
|
+
| `cv whiteboard list-templates` | List all available built-in templates |
|
|
255
|
+
|
|
256
|
+
```bash
|
|
257
|
+
cv new my-diagram --template system-arch
|
|
258
|
+
cv list-templates
|
|
259
|
+
```
|
|
188
260
|
|
|
189
261
|
---
|
|
190
262
|
|
|
@@ -196,10 +268,6 @@ Manage your CareerVivid profile.
|
|
|
196
268
|
|---|---|
|
|
197
269
|
| `cv profile export` | Export resume data to other formats (e.g. `gdoc`) |
|
|
198
270
|
|
|
199
|
-
```bash
|
|
200
|
-
cv profile export --format gdoc
|
|
201
|
-
```
|
|
202
|
-
|
|
203
271
|
---
|
|
204
272
|
|
|
205
273
|
### `cv auth`
|
|
@@ -213,8 +281,6 @@ Manage your CareerVivid API key. Get your key at [careervivid.app/developer](htt
|
|
|
213
281
|
| `cv auth remove` | Remove the saved key |
|
|
214
282
|
| `cv auth whoami` | Show the currently authenticated user |
|
|
215
283
|
|
|
216
|
-
The key is stored at `~/.careervividrc.json` with `chmod 600` permissions. You can also set it via environment variable:
|
|
217
|
-
|
|
218
284
|
```bash
|
|
219
285
|
cv auth set-key cv_live_YOUR_KEY_HERE
|
|
220
286
|
cv auth check
|
|
@@ -228,7 +294,7 @@ CV_API_KEY=cv_live_YOUR_KEY_HERE cv publish article.md
|
|
|
228
294
|
|
|
229
295
|
### `cv login`
|
|
230
296
|
|
|
231
|
-
Open the CareerVivid sign-in page
|
|
297
|
+
Open the CareerVivid sign-in page and interactively save your API key.
|
|
232
298
|
|
|
233
299
|
```bash
|
|
234
300
|
cv login
|
|
@@ -246,35 +312,28 @@ View and modify CLI configuration stored at `~/.careervividrc.json`.
|
|
|
246
312
|
| `cv config get <key>` | Print a single config value |
|
|
247
313
|
| `cv config set <key> <value>` | Update a config value |
|
|
248
314
|
|
|
249
|
-
**Available
|
|
315
|
+
**Available keys:**
|
|
250
316
|
|
|
251
317
|
| Key | Description |
|
|
252
318
|
|---|---|
|
|
253
|
-
| `apiKey` | Your CareerVivid API key
|
|
254
|
-
| `apiUrl` | Optional API endpoint override
|
|
255
|
-
| `targetCompanies` |
|
|
256
|
-
| `llmProvider` |
|
|
257
|
-
| `llmModel` |
|
|
258
|
-
| `llmApiKey` |
|
|
259
|
-
| `llmBaseUrl` | Custom OpenAI-compatible base URL
|
|
319
|
+
| `apiKey` | Your CareerVivid API key |
|
|
320
|
+
| `apiUrl` | Optional API endpoint override |
|
|
321
|
+
| `targetCompanies` | Target companies for `cv jobs hunt` |
|
|
322
|
+
| `llmProvider` | Default BYO LLM provider |
|
|
323
|
+
| `llmModel` | Default BYO model |
|
|
324
|
+
| `llmApiKey` | BYO LLM API key (masked in output) |
|
|
325
|
+
| `llmBaseUrl` | Custom OpenAI-compatible base URL |
|
|
260
326
|
|
|
261
327
|
```bash
|
|
262
|
-
cv config show
|
|
263
|
-
cv config get targetCompanies
|
|
264
328
|
cv config set targetCompanies "OpenAI, Google, Vercel"
|
|
265
329
|
cv config set llmProvider openai
|
|
266
330
|
cv config set llmModel gpt-4o
|
|
267
|
-
cv config set llmApiKey sk-...
|
|
268
331
|
```
|
|
269
332
|
|
|
270
|
-
> **Security:** API keys are always masked in `cv config show` output. Internal platform credentials are never exposed.
|
|
271
|
-
|
|
272
333
|
---
|
|
273
334
|
|
|
274
335
|
## AI Credits
|
|
275
336
|
|
|
276
|
-
CareerVivid uses a simple AI credit system for platform-managed AI features (powered by Gemini).
|
|
277
|
-
|
|
278
337
|
| Plan | Credits / Month | Price |
|
|
279
338
|
|---|---|---|
|
|
280
339
|
| **Free** | 100 credits | $0 |
|
|
@@ -283,46 +342,32 @@ CareerVivid uses a simple AI credit system for platform-managed AI features (pow
|
|
|
283
342
|
|
|
284
343
|
**Credit costs per agent turn:**
|
|
285
344
|
|
|
286
|
-
| Model | Credits
|
|
345
|
+
| Model | Credits |
|
|
287
346
|
|---|---|
|
|
288
|
-
| `gemini-3.1-flash-lite-preview`
|
|
347
|
+
| `gemini-3.1-flash-lite-preview` | 0.5 cr |
|
|
289
348
|
| `gemini-2.5-flash` | 1 cr |
|
|
290
349
|
| `gemini-3.1-pro-preview` (`--pro`) | 2 cr |
|
|
291
350
|
|
|
292
|
-
> **Bring Your Own Key:**
|
|
351
|
+
> **Bring Your Own Key:** Using `--provider openai` (or any non-CareerVivid provider) deducts **zero credits** — you pay your provider directly.
|
|
293
352
|
|
|
294
|
-
Get your
|
|
353
|
+
Get your key and check balance at [careervivid.app/developer](https://careervivid.app/developer).
|
|
295
354
|
|
|
296
355
|
---
|
|
297
356
|
|
|
298
357
|
## Bring Your Own API Key (BYO)
|
|
299
358
|
|
|
300
|
-
|
|
301
|
-
|
|
302
|
-
**Supported providers:**
|
|
303
|
-
|
|
304
|
-
| Provider | `--provider` value | Models |
|
|
359
|
+
| Provider | `--provider` | Notes |
|
|
305
360
|
|---|---|---|
|
|
306
|
-
| CareerVivid (default) | `careervivid` | Gemini Flash Lite, Flash, Pro |
|
|
307
|
-
| OpenAI | `openai` | gpt-4o,
|
|
361
|
+
| CareerVivid (default) | `careervivid` | Gemini Flash Lite, Flash, Pro — credits from your account |
|
|
362
|
+
| OpenAI | `openai` | gpt-4o, o3-mini, … |
|
|
308
363
|
| Anthropic | `anthropic` | claude-opus-4-5, claude-sonnet-4-5, … |
|
|
309
364
|
| Google Gemini (direct) | `gemini` | gemini-2.5-flash, gemini-3.1-pro-preview, … |
|
|
310
|
-
| OpenRouter | `openrouter` |
|
|
311
|
-
|
|
|
312
|
-
| Qwen / Alibaba | `custom` | `--base-url https://dashscope.aliyuncs.com/compatible-mode/v1` |
|
|
313
|
-
| GLM / Zhipu | `custom` | `--base-url https://open.bigmodel.cn/api/paas/v4` |
|
|
314
|
-
| Any OpenAI-compatible | `custom` | `--base-url <your-url>` |
|
|
315
|
-
|
|
316
|
-
**Examples:**
|
|
365
|
+
| OpenRouter | `openrouter` | 100+ models: Kimi, GLM, Qwen, Mistral, Llama, … |
|
|
366
|
+
| Custom OpenAI-compatible | `custom` | Any endpoint via `--base-url` |
|
|
317
367
|
|
|
318
368
|
```bash
|
|
319
|
-
# OpenAI
|
|
320
369
|
cv agent --provider openai --model gpt-4o --api-key sk-...
|
|
321
|
-
|
|
322
|
-
# Anthropic
|
|
323
370
|
cv agent --provider anthropic --model claude-opus-4-5 --api-key sk-ant-...
|
|
324
|
-
|
|
325
|
-
# OpenRouter (access 100+ models)
|
|
326
371
|
cv agent --provider openrouter --model mistralai/mistral-7b-instruct --api-key sk-or-...
|
|
327
372
|
|
|
328
373
|
# Save a provider permanently
|
|
@@ -331,9 +376,59 @@ cv agent config
|
|
|
331
376
|
|
|
332
377
|
---
|
|
333
378
|
|
|
379
|
+
## browser-use Setup (Autonomous Apply)
|
|
380
|
+
|
|
381
|
+
The `apply_to_job` tool in `cv agent --jobs` and `cv jobs apply` use [browser-use](https://github.com/browser-use/browser-use) — a Python AI browser automation library — to fill job applications.
|
|
382
|
+
|
|
383
|
+
### Prerequisites
|
|
384
|
+
|
|
385
|
+
- Python 3.11+ with pip
|
|
386
|
+
- A virtual environment (recommended)
|
|
387
|
+
|
|
388
|
+
### Setup (one-time)
|
|
389
|
+
|
|
390
|
+
```bash
|
|
391
|
+
# 1. Create a Python virtual environment
|
|
392
|
+
mkdir -p ~/careervivid/browser-use
|
|
393
|
+
cd ~/careervivid/browser-use
|
|
394
|
+
python3 -m venv .venv
|
|
395
|
+
source .venv/bin/activate
|
|
396
|
+
|
|
397
|
+
# 2. Install browser-use
|
|
398
|
+
pip install browser-use
|
|
399
|
+
|
|
400
|
+
# 3. Install Playwright browsers
|
|
401
|
+
playwright install chromium
|
|
402
|
+
|
|
403
|
+
# 4. Verify
|
|
404
|
+
python -c "import browser_use; print('browser-use ready')"
|
|
405
|
+
```
|
|
406
|
+
|
|
407
|
+
### How it works
|
|
408
|
+
|
|
409
|
+
When you run `cv agent --jobs` and ask to apply to a job:
|
|
410
|
+
|
|
411
|
+
1. The agent calls `apply_to_job` with the job URL
|
|
412
|
+
2. The CLI spawns `src/apply/browser_sidecar.py` (bundled with the npm package)
|
|
413
|
+
3. The sidecar launches a real Chrome browser (non-headless) using your profile
|
|
414
|
+
4. An AI agent fills the form field-by-field using your resume data
|
|
415
|
+
5. The browser **stays open** — you review every field and submit manually
|
|
416
|
+
|
|
417
|
+
> The agent will **never** click the final Submit button. You remain in full control.
|
|
418
|
+
|
|
419
|
+
### Resume PDF
|
|
420
|
+
|
|
421
|
+
Place your resume at `~/.careervivid/resume.pdf` and the sidecar will upload it automatically to resume upload fields.
|
|
422
|
+
|
|
423
|
+
```bash
|
|
424
|
+
cp ~/Downloads/MyResume.pdf ~/.careervivid/resume.pdf
|
|
425
|
+
```
|
|
426
|
+
|
|
427
|
+
---
|
|
428
|
+
|
|
334
429
|
## Whiteboard Templates
|
|
335
430
|
|
|
336
|
-
Run `cv list-templates` to see all templates
|
|
431
|
+
Run `cv list-templates` to see all available templates:
|
|
337
432
|
|
|
338
433
|
| Template | Description |
|
|
339
434
|
|---|---|
|
|
@@ -346,42 +441,11 @@ Run `cv list-templates` to see all templates. Available out of the box:
|
|
|
346
441
|
| `ci-cd` | CI/CD pipeline (lint → test → build → deploy) |
|
|
347
442
|
| `mindmap` | Mind map / concept breakdown |
|
|
348
443
|
|
|
349
|
-
```bash
|
|
350
|
-
cv new my-pipeline --template ci-cd
|
|
351
|
-
code my-pipeline.mmd
|
|
352
|
-
cv whiteboard publish my-pipeline.mmd --title "Our CI/CD Pipeline"
|
|
353
|
-
```
|
|
354
|
-
|
|
355
444
|
---
|
|
356
445
|
|
|
357
446
|
## AI Agent Integration (MCP / CI)
|
|
358
447
|
|
|
359
|
-
|
|
360
|
-
|
|
361
|
-
### System Prompt for Cursor / Claude / Gemini
|
|
362
|
-
|
|
363
|
-
```
|
|
364
|
-
# CareerVivid CLI Rules
|
|
365
|
-
|
|
366
|
-
You have access to the `cv` CLI tool. Use it to help the user build their
|
|
367
|
-
CareerVivid portfolio and manage their job search.
|
|
368
|
-
|
|
369
|
-
## Available commands
|
|
370
|
-
- cv publish <file> Publish an article or diagram
|
|
371
|
-
- cv agent --resume Discuss the user's resume
|
|
372
|
-
- cv agent --jobs Job hunting conversations
|
|
373
|
-
- cv jobs hunt --role "..." AI-powered job search
|
|
374
|
-
- cv jobs list View job tracker
|
|
375
|
-
|
|
376
|
-
## Publishing rules
|
|
377
|
-
1. Generate the file locally first.
|
|
378
|
-
2. Tell the user: "I drafted a CareerVivid post. Review and confirm."
|
|
379
|
-
3. Wait for explicit confirmation before running cv publish.
|
|
380
|
-
4. Use --json flag for machine-readable output.
|
|
381
|
-
5. NEVER include real API keys or secrets in published content.
|
|
382
|
-
```
|
|
383
|
-
|
|
384
|
-
### Automated Pipeline
|
|
448
|
+
Use `--json` for structured output in automated pipelines.
|
|
385
449
|
|
|
386
450
|
```bash
|
|
387
451
|
# Pipe AI-generated markdown directly
|
|
@@ -389,20 +453,34 @@ echo "# My Architecture\n\nExplains the new service..." \
|
|
|
389
453
|
| cv publish - --title "New Service Explained" --tags "architecture" --json
|
|
390
454
|
|
|
391
455
|
# Output:
|
|
392
|
-
# { "postId": "abc123", "url": "https://careervivid.app/community/post/abc123" }
|
|
456
|
+
# [{ "postId": "abc123", "url": "https://careervivid.app/community/post/abc123" }]
|
|
393
457
|
```
|
|
394
458
|
|
|
395
|
-
|
|
459
|
+
**System prompt for Cursor / Claude / Gemini:**
|
|
396
460
|
|
|
397
|
-
|
|
461
|
+
```
|
|
462
|
+
You have access to the `cv` CLI tool.
|
|
463
|
+
|
|
464
|
+
Available commands:
|
|
465
|
+
- cv publish <file> Publish an article (private by default, use --public to share)
|
|
466
|
+
- cv agent --resume Resume CRUD: read, update fields, tailor
|
|
467
|
+
- cv agent --jobs Job hunting + autonomous apply
|
|
468
|
+
- cv jobs hunt --role "..." AI job search
|
|
469
|
+
- cv jobs apply <url> Autonomous form filling (stops before submit)
|
|
470
|
+
- cv jobs list View job tracker
|
|
398
471
|
|
|
399
|
-
|
|
400
|
-
|
|
472
|
+
Rules:
|
|
473
|
+
1. Never include real API keys in published content.
|
|
474
|
+
2. Always use --json for machine-readable output.
|
|
475
|
+
3. Articles are PRIVATE by default. Only use --public if user explicitly requests it.
|
|
401
476
|
```
|
|
402
477
|
|
|
403
|
-
|
|
478
|
+
---
|
|
479
|
+
|
|
480
|
+
## Updating
|
|
404
481
|
|
|
405
482
|
```bash
|
|
483
|
+
npm install -g careervivid
|
|
406
484
|
cv -v
|
|
407
485
|
```
|
|
408
486
|
|
|
@@ -422,19 +500,41 @@ cv auth check
|
|
|
422
500
|
CV_API_KEY=cv_live_YOUR_KEY cv publish article.md
|
|
423
501
|
```
|
|
424
502
|
|
|
503
|
+
**`browser_sidecar.py not found`**
|
|
504
|
+
```bash
|
|
505
|
+
# browser-use is not set up. Follow the browser-use Setup section above.
|
|
506
|
+
# Verify your venv path:
|
|
507
|
+
ls ~/careervivid/browser-use/.venv/bin/python
|
|
508
|
+
```
|
|
509
|
+
|
|
510
|
+
**`aiohttp is not defined` or `ainvoke() takes 2 positional arguments`**
|
|
511
|
+
```bash
|
|
512
|
+
# Update to the latest version (fixed in v1.12.5+)
|
|
513
|
+
npm install -g careervivid@latest
|
|
514
|
+
```
|
|
515
|
+
|
|
516
|
+
**`❌ No API key found` when using CareerVivid Cloud**
|
|
517
|
+
```bash
|
|
518
|
+
cv auth check # verify your CV API key is set
|
|
519
|
+
cv agent config # reconfigure your LLM provider
|
|
520
|
+
```
|
|
521
|
+
|
|
425
522
|
**`cannot add command 'agent'` error (< v1.12.2)**
|
|
426
523
|
```bash
|
|
427
524
|
npm install -g careervivid@latest
|
|
428
525
|
```
|
|
429
526
|
|
|
527
|
+
**Job URL is broken / agent says it can't confirm the link**
|
|
528
|
+
The agent uses a live URL verification harness. If a link fails verification it will tell you instead of sending you to a broken page. Search for the role directly on the company's careers page or LinkedIn.
|
|
529
|
+
|
|
530
|
+
**Article shows as public even though I said private**
|
|
531
|
+
Update to v1.12.6+ — articles are now private by default. Use `--public` or tell the agent `"publish publicly"` to share with the community.
|
|
532
|
+
|
|
430
533
|
**Permission denied on `~/.careervividrc.json`**
|
|
431
534
|
```bash
|
|
432
535
|
chmod 600 ~/.careervividrc.json
|
|
433
536
|
```
|
|
434
537
|
|
|
435
|
-
**Mermaid diagram not rendering**
|
|
436
|
-
Run `cv new --template flowchart --print` to validate your Mermaid syntax.
|
|
437
|
-
|
|
438
538
|
---
|
|
439
539
|
|
|
440
540
|
## Resources
|
|
@@ -14,6 +14,7 @@ export interface AnthropicProviderOptions {
|
|
|
14
14
|
export declare class AnthropicProvider implements LLMProvider {
|
|
15
15
|
private apiKey;
|
|
16
16
|
constructor(options: AnthropicProviderOptions);
|
|
17
|
+
private geminiSchemaToJsonSchema;
|
|
17
18
|
private toAnthropicTools;
|
|
18
19
|
private toAnthropicMessages;
|
|
19
20
|
generate(request: LLMRequest): Promise<LLMResponse>;
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"AnthropicProvider.d.ts","sourceRoot":"","sources":["../../../src/agent/providers/AnthropicProvider.ts"],"names":[],"mappings":"AAAA;;;;;;;;GAQG;AAEH,OAAO,KAAK,EACV,WAAW,EACX,UAAU,EACV,WAAW,EACX,cAAc,EACf,MAAM,kBAAkB,CAAC;AAK1B,MAAM,WAAW,wBAAwB;IACvC,MAAM,EAAE,MAAM,CAAC;CAChB;AAED,qBAAa,iBAAkB,YAAW,WAAW;IACnD,OAAO,CAAC,MAAM,CAAS;gBAEX,OAAO,EAAE,wBAAwB;IAK7C,OAAO,CAAC,gBAAgB;
|
|
1
|
+
{"version":3,"file":"AnthropicProvider.d.ts","sourceRoot":"","sources":["../../../src/agent/providers/AnthropicProvider.ts"],"names":[],"mappings":"AAAA;;;;;;;;GAQG;AAEH,OAAO,KAAK,EACV,WAAW,EACX,UAAU,EACV,WAAW,EACX,cAAc,EACf,MAAM,kBAAkB,CAAC;AAK1B,MAAM,WAAW,wBAAwB;IACvC,MAAM,EAAE,MAAM,CAAC;CAChB;AAED,qBAAa,iBAAkB,YAAW,WAAW;IACnD,OAAO,CAAC,MAAM,CAAS;gBAEX,OAAO,EAAE,wBAAwB;IAK7C,OAAO,CAAC,wBAAwB;IAwBhC,OAAO,CAAC,gBAAgB;IAUxB,OAAO,CAAC,mBAAmB;IAgErB,QAAQ,CAAC,OAAO,EAAE,UAAU,GAAG,OAAO,CAAC,WAAW,CAAC;IA+DnD,cAAc,CAClB,OAAO,EAAE,UAAU,EACnB,OAAO,EAAE,CAAC,KAAK,EAAE,cAAc,KAAK,IAAI,GACvC,OAAO,CAAC,WAAW,CAAC;CA+GxB"}
|
|
@@ -14,12 +14,41 @@ export class AnthropicProvider {
|
|
|
14
14
|
constructor(options) {
|
|
15
15
|
this.apiKey = options.apiKey;
|
|
16
16
|
}
|
|
17
|
+
// ── Convert Gemini @google/genai Type enum values to JSON Schema ──────────
|
|
18
|
+
geminiSchemaToJsonSchema(schema) {
|
|
19
|
+
if (!schema || typeof schema !== "object")
|
|
20
|
+
return schema;
|
|
21
|
+
const TYPE_MAP = {
|
|
22
|
+
OBJECT: "object", STRING: "string", NUMBER: "number",
|
|
23
|
+
INTEGER: "integer", BOOLEAN: "boolean", ARRAY: "array",
|
|
24
|
+
object: "object", string: "string", number: "number",
|
|
25
|
+
integer: "integer", boolean: "boolean", array: "array",
|
|
26
|
+
};
|
|
27
|
+
const result = {};
|
|
28
|
+
if (schema.type)
|
|
29
|
+
result.type = TYPE_MAP[schema.type] ?? schema.type.toLowerCase();
|
|
30
|
+
if (schema.description)
|
|
31
|
+
result.description = schema.description;
|
|
32
|
+
if (schema.enum)
|
|
33
|
+
result.enum = schema.enum;
|
|
34
|
+
if (schema.required)
|
|
35
|
+
result.required = schema.required;
|
|
36
|
+
if (schema.properties && typeof schema.properties === "object") {
|
|
37
|
+
result.properties = {};
|
|
38
|
+
for (const [key, val] of Object.entries(schema.properties)) {
|
|
39
|
+
result.properties[key] = this.geminiSchemaToJsonSchema(val);
|
|
40
|
+
}
|
|
41
|
+
}
|
|
42
|
+
if (schema.items)
|
|
43
|
+
result.items = this.geminiSchemaToJsonSchema(schema.items);
|
|
44
|
+
return result;
|
|
45
|
+
}
|
|
17
46
|
// ── Convert our Tool[] to Anthropic tool definitions ─────────────────────
|
|
18
47
|
toAnthropicTools(tools) {
|
|
19
48
|
return tools.map((t) => ({
|
|
20
49
|
name: t.name,
|
|
21
50
|
description: t.description,
|
|
22
|
-
input_schema: t.parameters,
|
|
51
|
+
input_schema: this.geminiSchemaToJsonSchema(t.parameters),
|
|
23
52
|
}));
|
|
24
53
|
}
|
|
25
54
|
// ── Convert Gemini Content[] to Anthropic messages[] ─────────────────────
|
|
@@ -27,6 +27,7 @@ export declare class OpenAIProvider implements LLMProvider {
|
|
|
27
27
|
private baseUrl;
|
|
28
28
|
private extraHeaders;
|
|
29
29
|
constructor(options: OpenAIProviderOptions);
|
|
30
|
+
private geminiSchemaToJsonSchema;
|
|
30
31
|
private toOpenAITools;
|
|
31
32
|
private toOpenAIMessages;
|
|
32
33
|
generate(request: LLMRequest): Promise<LLMResponse>;
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"OpenAIProvider.d.ts","sourceRoot":"","sources":["../../../src/agent/providers/OpenAIProvider.ts"],"names":[],"mappings":"AAAA;;;;;;;;;;;;;;;;GAgBG;AAEH,OAAO,KAAK,EACV,WAAW,EACX,UAAU,EACV,WAAW,EACX,cAAc,EACf,MAAM,kBAAkB,CAAC;AAG1B,MAAM,WAAW,qBAAqB;IACpC,MAAM,EAAE,MAAM,CAAC;IACf,OAAO,CAAC,EAAE,MAAM,CAAC;IACjB,iEAAiE;IACjE,YAAY,CAAC,EAAE,MAAM,CAAC,MAAM,EAAE,MAAM,CAAC,CAAC;CACvC;AAED,qBAAa,cAAe,YAAW,WAAW;IAChD,OAAO,CAAC,MAAM,CAAS;IACvB,OAAO,CAAC,OAAO,CAAS;IACxB,OAAO,CAAC,YAAY,CAAyB;gBAEjC,OAAO,EAAE,qBAAqB;
|
|
1
|
+
{"version":3,"file":"OpenAIProvider.d.ts","sourceRoot":"","sources":["../../../src/agent/providers/OpenAIProvider.ts"],"names":[],"mappings":"AAAA;;;;;;;;;;;;;;;;GAgBG;AAEH,OAAO,KAAK,EACV,WAAW,EACX,UAAU,EACV,WAAW,EACX,cAAc,EACf,MAAM,kBAAkB,CAAC;AAG1B,MAAM,WAAW,qBAAqB;IACpC,MAAM,EAAE,MAAM,CAAC;IACf,OAAO,CAAC,EAAE,MAAM,CAAC;IACjB,iEAAiE;IACjE,YAAY,CAAC,EAAE,MAAM,CAAC,MAAM,EAAE,MAAM,CAAC,CAAC;CACvC;AAED,qBAAa,cAAe,YAAW,WAAW;IAChD,OAAO,CAAC,MAAM,CAAS;IACvB,OAAO,CAAC,OAAO,CAAS;IACxB,OAAO,CAAC,YAAY,CAAyB;gBAEjC,OAAO,EAAE,qBAAqB;IAY1C,OAAO,CAAC,wBAAwB;IA2ChC,OAAO,CAAC,aAAa;IAarB,OAAO,CAAC,gBAAgB;IAgElB,QAAQ,CAAC,OAAO,EAAE,UAAU,GAAG,OAAO,CAAC,WAAW,CAAC;IA2DnD,cAAc,CAClB,OAAO,EAAE,UAAU,EACnB,OAAO,EAAE,CAAC,KAAK,EAAE,cAAc,KAAK,IAAI,GACvC,OAAO,CAAC,WAAW,CAAC;CAuGxB;AAED;;GAEG;AACH,wBAAgB,8BAA8B,CAC5C,WAAW,EAAE,QAAQ,GAAG,YAAY,GAAG,MAAM,GAAG,KAAK,GAAG,MAAM,GAAG,QAAQ,EACzE,MAAM,EAAE,MAAM,EACd,aAAa,CAAC,EAAE,MAAM,GACrB,cAAc,CAqBhB"}
|
|
@@ -24,6 +24,48 @@ export class OpenAIProvider {
|
|
|
24
24
|
this.baseUrl = (options.baseUrl || "https://api.openai.com/v1").replace(/\/$/, "");
|
|
25
25
|
this.extraHeaders = options.extraHeaders || {};
|
|
26
26
|
}
|
|
27
|
+
// ── Convert Gemini @google/genai Type enum values to JSON Schema ──────────
|
|
28
|
+
// Gemini uses uppercase strings like "OBJECT", "STRING", "ARRAY".
|
|
29
|
+
// OpenAI-compatible APIs (OpenRouter, OpenAI, etc.) use lowercase JSON Schema.
|
|
30
|
+
geminiSchemaToJsonSchema(schema) {
|
|
31
|
+
if (!schema || typeof schema !== "object")
|
|
32
|
+
return schema;
|
|
33
|
+
const TYPE_MAP = {
|
|
34
|
+
OBJECT: "object",
|
|
35
|
+
STRING: "string",
|
|
36
|
+
NUMBER: "number",
|
|
37
|
+
INTEGER: "integer",
|
|
38
|
+
BOOLEAN: "boolean",
|
|
39
|
+
ARRAY: "array",
|
|
40
|
+
// Already lowercase passthrough
|
|
41
|
+
object: "object",
|
|
42
|
+
string: "string",
|
|
43
|
+
number: "number",
|
|
44
|
+
integer: "integer",
|
|
45
|
+
boolean: "boolean",
|
|
46
|
+
array: "array",
|
|
47
|
+
};
|
|
48
|
+
const result = {};
|
|
49
|
+
if (schema.type) {
|
|
50
|
+
result.type = TYPE_MAP[schema.type] ?? schema.type.toLowerCase();
|
|
51
|
+
}
|
|
52
|
+
if (schema.description)
|
|
53
|
+
result.description = schema.description;
|
|
54
|
+
if (schema.enum)
|
|
55
|
+
result.enum = schema.enum;
|
|
56
|
+
if (schema.required)
|
|
57
|
+
result.required = schema.required;
|
|
58
|
+
if (schema.properties && typeof schema.properties === "object") {
|
|
59
|
+
result.properties = {};
|
|
60
|
+
for (const [key, val] of Object.entries(schema.properties)) {
|
|
61
|
+
result.properties[key] = this.geminiSchemaToJsonSchema(val);
|
|
62
|
+
}
|
|
63
|
+
}
|
|
64
|
+
if (schema.items) {
|
|
65
|
+
result.items = this.geminiSchemaToJsonSchema(schema.items);
|
|
66
|
+
}
|
|
67
|
+
return result;
|
|
68
|
+
}
|
|
27
69
|
// ── convert our Tool[] to OpenAI function definitions ────────────────────
|
|
28
70
|
toOpenAITools(tools) {
|
|
29
71
|
return tools.map((t) => ({
|
|
@@ -31,7 +73,7 @@ export class OpenAIProvider {
|
|
|
31
73
|
function: {
|
|
32
74
|
name: t.name,
|
|
33
75
|
description: t.description,
|
|
34
|
-
parameters: t.parameters,
|
|
76
|
+
parameters: this.geminiSchemaToJsonSchema(t.parameters),
|
|
35
77
|
},
|
|
36
78
|
}));
|
|
37
79
|
}
|