midas-mcp 5.1.4 → 5.3.1
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/dist/analyzer.d.ts +13 -0
- package/dist/analyzer.d.ts.map +1 -1
- package/dist/analyzer.js +336 -11
- package/dist/analyzer.js.map +1 -1
- package/dist/prompts/grow.d.ts +4 -0
- package/dist/prompts/grow.d.ts.map +1 -1
- package/dist/prompts/grow.js +130 -161
- package/dist/prompts/grow.js.map +1 -1
- package/dist/providers.d.ts +15 -0
- package/dist/providers.d.ts.map +1 -1
- package/dist/providers.js +169 -5
- package/dist/providers.js.map +1 -1
- package/dist/state/phase.d.ts +22 -32
- package/dist/state/phase.d.ts.map +1 -1
- package/dist/state/phase.js +44 -21
- package/dist/state/phase.js.map +1 -1
- package/dist/tools/analyze.d.ts.map +1 -1
- package/dist/tools/analyze.js +3 -23
- package/dist/tools/analyze.js.map +1 -1
- package/dist/tools/grow.js +1 -1
- package/dist/tools/grow.js.map +1 -1
- package/dist/tools/phase.js +1 -1
- package/dist/tools/phase.js.map +1 -1
- package/dist/tui.d.ts.map +1 -1
- package/dist/tui.js +136 -5
- package/dist/tui.js.map +1 -1
- package/package.json +1 -1
package/dist/prompts/grow.js
CHANGED
|
@@ -1,240 +1,209 @@
|
|
|
1
1
|
import { z } from 'zod';
|
|
2
|
+
/**
|
|
3
|
+
* GROW phase prompts - focused on the graduation checklist
|
|
4
|
+
* These help users take action on the 6 growth steps
|
|
5
|
+
*/
|
|
2
6
|
export function registerGrowPrompts(server) {
|
|
3
|
-
//
|
|
4
|
-
server.prompt('
|
|
7
|
+
// Announce - Help craft launch posts
|
|
8
|
+
server.prompt('announce_launch', 'Craft a launch announcement for your project', {
|
|
9
|
+
projectName: z.string().describe('Name of your project'),
|
|
10
|
+
oneLiner: z.string().describe('One sentence describing what it does'),
|
|
11
|
+
platform: z.string().optional().describe('Target platform: reddit, twitter, discord, hackernews, producthunt'),
|
|
12
|
+
}, (args) => ({
|
|
5
13
|
messages: [
|
|
6
14
|
{
|
|
7
15
|
role: 'user',
|
|
8
16
|
content: {
|
|
9
17
|
type: 'text',
|
|
10
|
-
text: `
|
|
18
|
+
text: `Help me announce "${args.projectName}" on ${args.platform || 'social media'}.
|
|
11
19
|
|
|
12
|
-
|
|
20
|
+
One-liner: ${args.oneLiner}
|
|
13
21
|
|
|
14
|
-
|
|
15
|
-
1. **
|
|
16
|
-
2. **
|
|
17
|
-
3. **
|
|
18
|
-
4. **Resources** - CPU, memory, disk usage trends
|
|
22
|
+
Write 3 versions:
|
|
23
|
+
1. **Short** (under 280 chars for Twitter/X)
|
|
24
|
+
2. **Medium** (Reddit/Discord post - 2-3 paragraphs)
|
|
25
|
+
3. **Long** (Hacker News/Product Hunt - full story)
|
|
19
26
|
|
|
20
|
-
|
|
21
|
-
-
|
|
22
|
-
-
|
|
23
|
-
-
|
|
27
|
+
Each version should:
|
|
28
|
+
- Lead with the problem, not the solution
|
|
29
|
+
- Be genuine, not salesy
|
|
30
|
+
- Include a clear call to action
|
|
31
|
+
- Avoid buzzwords and hype
|
|
24
32
|
|
|
25
|
-
|
|
33
|
+
Match the platform's tone and culture.`,
|
|
26
34
|
},
|
|
27
35
|
},
|
|
28
36
|
],
|
|
29
37
|
}));
|
|
30
|
-
//
|
|
31
|
-
server.prompt('
|
|
38
|
+
// Network - Help with outreach messages
|
|
39
|
+
server.prompt('outreach_message', 'Write a personal outreach message for potential users', {
|
|
40
|
+
projectName: z.string().describe('Name of your project'),
|
|
41
|
+
targetPerson: z.string().describe('Who you are reaching out to (role/context)'),
|
|
42
|
+
connection: z.string().optional().describe('How you know them or why you chose them'),
|
|
43
|
+
}, (args) => ({
|
|
32
44
|
messages: [
|
|
33
45
|
{
|
|
34
46
|
role: 'user',
|
|
35
47
|
content: {
|
|
36
48
|
type: 'text',
|
|
37
|
-
text: `
|
|
38
|
-
|
|
39
|
-
${args.feedback}
|
|
40
|
-
|
|
41
|
-
---
|
|
42
|
-
|
|
43
|
-
1. **Categorize** each piece:
|
|
44
|
-
- Bug report
|
|
45
|
-
- Feature request
|
|
46
|
-
- UX friction
|
|
47
|
-
- Performance complaint
|
|
48
|
-
- Praise
|
|
49
|
-
|
|
50
|
-
2. **Identify patterns** - Themes appearing multiple times
|
|
49
|
+
text: `Write a personal DM to introduce "${args.projectName}" to ${args.targetPerson}.
|
|
51
50
|
|
|
52
|
-
|
|
51
|
+
${args.connection ? `Connection: ${args.connection}` : ''}
|
|
53
52
|
|
|
54
|
-
|
|
53
|
+
The message should:
|
|
54
|
+
- Be genuinely helpful, not pitchy
|
|
55
|
+
- Acknowledge their time is valuable
|
|
56
|
+
- Explain why you thought of THEM specifically
|
|
57
|
+
- Make it easy to say no
|
|
58
|
+
- Be under 150 words
|
|
55
59
|
|
|
56
|
-
|
|
60
|
+
Write 2 versions: one casual, one more professional.`,
|
|
57
61
|
},
|
|
58
62
|
},
|
|
59
63
|
],
|
|
60
64
|
}));
|
|
61
|
-
//
|
|
62
|
-
server.prompt('
|
|
65
|
+
// Feedback - Help ask good questions
|
|
66
|
+
server.prompt('feedback_questions', 'Generate questions to ask early users', { projectName: z.string().describe('Name of your project') }, (args) => ({
|
|
63
67
|
messages: [
|
|
64
68
|
{
|
|
65
69
|
role: 'user',
|
|
66
70
|
content: {
|
|
67
71
|
type: 'text',
|
|
68
|
-
text: `
|
|
69
|
-
|
|
70
|
-
|
|
71
|
-
|
|
72
|
-
|
|
73
|
-
|
|
74
|
-
|
|
75
|
-
|
|
76
|
-
|
|
77
|
-
|
|
78
|
-
|
|
79
|
-
|
|
80
|
-
-
|
|
81
|
-
-
|
|
82
|
-
|
|
83
|
-
-
|
|
84
|
-
|
|
85
|
-
Output a prioritized list with recommended order.`,
|
|
72
|
+
text: `Create a short user feedback script for "${args.projectName}".
|
|
73
|
+
|
|
74
|
+
Generate 5-7 questions that:
|
|
75
|
+
1. Start with their experience (open-ended)
|
|
76
|
+
2. Identify confusion points
|
|
77
|
+
3. Uncover missing features
|
|
78
|
+
4. Find what they love
|
|
79
|
+
5. End with whether they'd recommend it
|
|
80
|
+
|
|
81
|
+
Rules:
|
|
82
|
+
- No leading questions
|
|
83
|
+
- No yes/no questions
|
|
84
|
+
- Ask about behavior, not opinions
|
|
85
|
+
- Keep it under 5 minutes total
|
|
86
|
+
|
|
87
|
+
Also provide 3 follow-up probes for when they give short answers.`,
|
|
86
88
|
},
|
|
87
89
|
},
|
|
88
90
|
],
|
|
89
91
|
}));
|
|
90
|
-
//
|
|
91
|
-
server.prompt('
|
|
92
|
-
|
|
93
|
-
|
|
92
|
+
// Proof - Help collect and display social proof
|
|
93
|
+
server.prompt('testimonial_request', 'Write a testimonial request message', {
|
|
94
|
+
projectName: z.string().describe('Name of your project'),
|
|
95
|
+
userName: z.string().optional().describe('Name of the user you are asking'),
|
|
94
96
|
}, (args) => ({
|
|
95
97
|
messages: [
|
|
96
98
|
{
|
|
97
99
|
role: 'user',
|
|
98
100
|
content: {
|
|
99
101
|
type: 'text',
|
|
100
|
-
text: `
|
|
101
|
-
|
|
102
|
-
|
|
103
|
-
|
|
104
|
-
|
|
105
|
-
|
|
106
|
-
|
|
107
|
-
|
|
108
|
-
|
|
109
|
-
|
|
110
|
-
|
|
111
|
-
|
|
112
|
-
|
|
113
|
-
2. **What didn't work?**
|
|
114
|
-
- Blockers we hit
|
|
115
|
-
- Time wasted on
|
|
116
|
-
- Communication gaps
|
|
117
|
-
|
|
118
|
-
3. **What surprised us?**
|
|
119
|
-
- Unexpected wins
|
|
120
|
-
- Hidden complexity
|
|
121
|
-
- User behavior we didn't expect
|
|
122
|
-
|
|
123
|
-
4. **Action items**
|
|
124
|
-
- One thing to START doing
|
|
125
|
-
- One thing to STOP doing
|
|
126
|
-
- One thing to CONTINUE doing
|
|
127
|
-
|
|
128
|
-
Output concrete action items for next cycle.`,
|
|
102
|
+
text: `Write a message asking ${args.userName || 'a user'} for a testimonial about "${args.projectName}".
|
|
103
|
+
|
|
104
|
+
The message should:
|
|
105
|
+
- Thank them for using the product
|
|
106
|
+
- Make it easy (suggest 2-3 prompts they can respond to)
|
|
107
|
+
- Offer to write a draft they can edit
|
|
108
|
+
- Ask permission to use their name/photo
|
|
109
|
+
- Be gracious if they decline
|
|
110
|
+
|
|
111
|
+
Also suggest:
|
|
112
|
+
- Where to display testimonials (landing page, GitHub, etc.)
|
|
113
|
+
- How to screenshot/document usage metrics`,
|
|
129
114
|
},
|
|
130
115
|
},
|
|
131
116
|
],
|
|
132
117
|
}));
|
|
133
|
-
//
|
|
134
|
-
server.prompt('
|
|
118
|
+
// Iterate - Help prioritize feedback
|
|
119
|
+
server.prompt('prioritize_feedback', 'Turn user feedback into actionable improvements', { feedback: z.string().describe('Raw user feedback to analyze') }, (args) => ({
|
|
135
120
|
messages: [
|
|
136
121
|
{
|
|
137
122
|
role: 'user',
|
|
138
123
|
content: {
|
|
139
124
|
type: 'text',
|
|
140
|
-
text: `
|
|
141
|
-
|
|
142
|
-
${args.learnings ? `Learnings:\n${args.learnings}\n\n---` : ''}
|
|
143
|
-
|
|
144
|
-
Define:
|
|
125
|
+
text: `Analyze this user feedback and prioritize improvements:
|
|
145
126
|
|
|
146
|
-
|
|
147
|
-
- What are we testing?
|
|
148
|
-
- What do we believe will happen?
|
|
149
|
-
- How will we validate?
|
|
150
|
-
|
|
151
|
-
2. **Scope**
|
|
152
|
-
- Single most important thing to build
|
|
153
|
-
- Explicit non-goals (what we WON'T do)
|
|
154
|
-
- Minimum viable version
|
|
155
|
-
|
|
156
|
-
3. **Success metrics**
|
|
157
|
-
- How do we measure success?
|
|
158
|
-
- Target numbers
|
|
159
|
-
- Timeline
|
|
127
|
+
${args.feedback}
|
|
160
128
|
|
|
161
|
-
|
|
162
|
-
- What could go wrong?
|
|
163
|
-
- Mitigation strategies
|
|
164
|
-
- Kill criteria (when to pivot)
|
|
129
|
+
---
|
|
165
130
|
|
|
166
|
-
|
|
131
|
+
1. **Categorize** each piece:
|
|
132
|
+
- Bug (broken functionality)
|
|
133
|
+
- UX friction (confusing/hard to use)
|
|
134
|
+
- Missing feature (requested addition)
|
|
135
|
+
- Performance (slow/resource issues)
|
|
136
|
+
|
|
137
|
+
2. **Identify the ONE thing** to fix first:
|
|
138
|
+
- Highest impact (affects most users)
|
|
139
|
+
- Lowest effort (quick win)
|
|
140
|
+
- Most urgent (blocking adoption)
|
|
141
|
+
|
|
142
|
+
3. **Write a specific task** for that improvement:
|
|
143
|
+
- What exactly to change
|
|
144
|
+
- How to verify it's fixed
|
|
145
|
+
- What to ignore for now`,
|
|
167
146
|
},
|
|
168
147
|
},
|
|
169
148
|
],
|
|
170
149
|
}));
|
|
171
|
-
//
|
|
172
|
-
server.prompt('
|
|
150
|
+
// Content - Help write about the project
|
|
151
|
+
server.prompt('write_launch_post', 'Write a "what I learned building X" post', {
|
|
152
|
+
projectName: z.string().describe('Name of your project'),
|
|
153
|
+
buildTime: z.string().optional().describe('How long it took to build'),
|
|
154
|
+
techStack: z.string().optional().describe('Main technologies used'),
|
|
155
|
+
}, (args) => ({
|
|
173
156
|
messages: [
|
|
174
157
|
{
|
|
175
158
|
role: 'user',
|
|
176
159
|
content: {
|
|
177
160
|
type: 'text',
|
|
178
|
-
text: `
|
|
179
|
-
|
|
180
|
-
Create handoff document:
|
|
181
|
-
|
|
182
|
-
1. **Context summary**
|
|
183
|
-
- What was built this cycle
|
|
184
|
-
- Current state of the product
|
|
185
|
-
- Active users/usage metrics
|
|
161
|
+
text: `Help me write a "What I learned building ${args.projectName}" post.
|
|
186
162
|
|
|
187
|
-
|
|
188
|
-
|
|
189
|
-
- Process improvements needed
|
|
190
|
-
- Knowledge to preserve
|
|
163
|
+
${args.buildTime ? `Build time: ${args.buildTime}` : ''}
|
|
164
|
+
${args.techStack ? `Tech stack: ${args.techStack}` : ''}
|
|
191
165
|
|
|
192
|
-
|
|
193
|
-
|
|
194
|
-
|
|
195
|
-
|
|
166
|
+
Create an outline covering:
|
|
167
|
+
1. **The problem** - Why I built this
|
|
168
|
+
2. **The journey** - Key decisions and pivots
|
|
169
|
+
3. **Mistakes** - What I'd do differently
|
|
170
|
+
4. **Wins** - What worked well
|
|
171
|
+
5. **Advice** - For others building similar things
|
|
196
172
|
|
|
197
|
-
|
|
198
|
-
|
|
199
|
-
|
|
200
|
-
|
|
173
|
+
Make it:
|
|
174
|
+
- Honest and vulnerable (not a humble brag)
|
|
175
|
+
- Specific with concrete examples
|
|
176
|
+
- Useful for readers (actionable takeaways)
|
|
177
|
+
- Personal but not navel-gazing
|
|
201
178
|
|
|
202
|
-
|
|
179
|
+
Suggest 3 title options.`,
|
|
203
180
|
},
|
|
204
181
|
},
|
|
205
182
|
],
|
|
206
183
|
}));
|
|
207
|
-
//
|
|
208
|
-
server.prompt('
|
|
184
|
+
// Bonus: Quick wins prompt
|
|
185
|
+
server.prompt('growth_quick_wins', 'Get quick wins to grow your project this week', { projectName: z.string().describe('Name of your project') }, (args) => ({
|
|
209
186
|
messages: [
|
|
210
187
|
{
|
|
211
188
|
role: 'user',
|
|
212
189
|
content: {
|
|
213
190
|
type: 'text',
|
|
214
|
-
text: `
|
|
215
|
-
|
|
216
|
-
|
|
217
|
-
|
|
218
|
-
|
|
219
|
-
|
|
220
|
-
|
|
221
|
-
|
|
222
|
-
|
|
223
|
-
|
|
224
|
-
|
|
225
|
-
|
|
226
|
-
|
|
227
|
-
|
|
228
|
-
|
|
229
|
-
|
|
230
|
-
- Avoid premature optimization
|
|
231
|
-
|
|
232
|
-
4. **Verify Improvements**
|
|
233
|
-
- Before/after measurements
|
|
234
|
-
- No regressions introduced
|
|
235
|
-
- Document changes
|
|
236
|
-
|
|
237
|
-
Analyze the codebase and provide specific optimizations.`,
|
|
191
|
+
text: `Give me 5 quick wins to grow "${args.projectName}" this week.
|
|
192
|
+
|
|
193
|
+
Each should be:
|
|
194
|
+
- Completable in under 1 hour
|
|
195
|
+
- Free (no paid ads)
|
|
196
|
+
- Measurable (I can see if it worked)
|
|
197
|
+
|
|
198
|
+
Focus on:
|
|
199
|
+
- Places my target users already hang out
|
|
200
|
+
- Ways to get feedback loops going
|
|
201
|
+
- Low-effort, high-visibility actions
|
|
202
|
+
|
|
203
|
+
For each, give me:
|
|
204
|
+
1. The action (specific, not vague)
|
|
205
|
+
2. Expected outcome
|
|
206
|
+
3. How to measure success`,
|
|
238
207
|
},
|
|
239
208
|
},
|
|
240
209
|
],
|
package/dist/prompts/grow.js.map
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"grow.js","sourceRoot":"","sources":["../../src/prompts/grow.ts"],"names":[],"mappings":"AACA,OAAO,EAAE,CAAC,EAAE,MAAM,KAAK,CAAC;AAExB,MAAM,UAAU,mBAAmB,CAAC,MAAiB;IACnD,
|
|
1
|
+
{"version":3,"file":"grow.js","sourceRoot":"","sources":["../../src/prompts/grow.ts"],"names":[],"mappings":"AACA,OAAO,EAAE,CAAC,EAAE,MAAM,KAAK,CAAC;AAExB;;;GAGG;AACH,MAAM,UAAU,mBAAmB,CAAC,MAAiB;IACnD,qCAAqC;IACrC,MAAM,CAAC,MAAM,CACX,iBAAiB,EACjB,8CAA8C,EAC9C;QACE,WAAW,EAAE,CAAC,CAAC,MAAM,EAAE,CAAC,QAAQ,CAAC,sBAAsB,CAAC;QACxD,QAAQ,EAAE,CAAC,CAAC,MAAM,EAAE,CAAC,QAAQ,CAAC,sCAAsC,CAAC;QACrE,QAAQ,EAAE,CAAC,CAAC,MAAM,EAAE,CAAC,QAAQ,EAAE,CAAC,QAAQ,CAAC,oEAAoE,CAAC;KAC/G,EACD,CAAC,IAAI,EAAE,EAAE,CAAC,CAAC;QACT,QAAQ,EAAE;YACR;gBACE,IAAI,EAAE,MAAM;gBACZ,OAAO,EAAE;oBACP,IAAI,EAAE,MAAM;oBACZ,IAAI,EAAE,qBAAqB,IAAI,CAAC,WAAW,QAAQ,IAAI,CAAC,QAAQ,IAAI,cAAc;;aAEjF,IAAI,CAAC,QAAQ;;;;;;;;;;;;;uCAaa;iBAC5B;aACF;SACF;KACF,CAAC,CACH,CAAC;IAEF,wCAAwC;IACxC,MAAM,CAAC,MAAM,CACX,kBAAkB,EAClB,uDAAuD,EACvD;QACE,WAAW,EAAE,CAAC,CAAC,MAAM,EAAE,CAAC,QAAQ,CAAC,sBAAsB,CAAC;QACxD,YAAY,EAAE,CAAC,CAAC,MAAM,EAAE,CAAC,QAAQ,CAAC,4CAA4C,CAAC;QAC/E,UAAU,EAAE,CAAC,CAAC,MAAM,EAAE,CAAC,QAAQ,EAAE,CAAC,QAAQ,CAAC,yCAAyC,CAAC;KACtF,EACD,CAAC,IAAI,EAAE,EAAE,CAAC,CAAC;QACT,QAAQ,EAAE;YACR;gBACE,IAAI,EAAE,MAAM;gBACZ,OAAO,EAAE;oBACP,IAAI,EAAE,MAAM;oBACZ,IAAI,EAAE,qCAAqC,IAAI,CAAC,WAAW,QAAQ,IAAI,CAAC,YAAY;;EAE9F,IAAI,CAAC,UAAU,CAAC,CAAC,CAAC,eAAe,IAAI,CAAC,UAAU,EAAE,CAAC,CAAC,CAAC,EAAE;;;;;;;;;qDASJ;iBAC1C;aACF;SACF;KACF,CAAC,CACH,CAAC;IAEF,qCAAqC;IACrC,MAAM,CAAC,MAAM,CACX,oBAAoB,EACpB,uCAAuC,EACvC,EAAE,WAAW,EAAE,CAAC,CAAC,MAAM,EAAE,CAAC,QAAQ,CAAC,sBAAsB,CAAC,EAAE,EAC5D,CAAC,IAAI,EAAE,EAAE,CAAC,CAAC;QACT,QAAQ,EAAE;YACR;gBACE,IAAI,EAAE,MAAM;gBACZ,OAAO,EAAE;oBACP,IAAI,EAAE,MAAM;oBACZ,IAAI,EAAE,4CAA4C,IAAI,CAAC,WAAW;;;;;;;;;;;;;;;kEAeZ;iBACvD;aACF;SACF;KACF,CAAC,CACH,CAAC;IAEF,gDAAgD;IAChD,MAAM,CAAC,MAAM,CACX,qBAAqB,EACrB,qCAAqC,EACrC;QACE,WAAW,EAAE,CAAC,CAAC,MAAM,EAAE,CAAC,QAAQ,CAAC,sBAAsB,CAAC;QACxD,QAAQ,EAAE,CAAC,CAAC,MAAM,EAAE,CAAC,QAAQ,EAAE,CAAC,QAAQ,CAAC,iCAAiC,CAAC;KAC5E,EACD,CAAC,IAAI,EAAE,EAAE,CAAC,CAAC;QACT,QAAQ,EAAE;YACR;gBACE,IAAI,EAAE,MAAM;gBACZ,OAAO,EAAE;oBACP,IAAI,EAAE,MAAM;oBACZ,IAAI,EAAE,0BAA0B,IAAI,CAAC,QAAQ,IAAI,QAAQ,6BAA6B,IAAI,CAAC,WAAW;;;;;;;;;;;2CAWvE;iBAChC;aACF;SACF;KACF,CAAC,CACH,CAAC;IAEF,qCAAqC;IACrC,MAAM,CAAC,MAAM,CACX,qBAAqB,EACrB,iDAAiD,EACjD,EAAE,QAAQ,EAAE,CAAC,CAAC,MAAM,EAAE,CAAC,QAAQ,CAAC,8BAA8B,CAAC,EAAE,EACjE,CAAC,IAAI,EAAE,EAAE,CAAC,CAAC;QACT,QAAQ,EAAE;YACR;gBACE,IAAI,EAAE,MAAM;gBACZ,OAAO,EAAE;oBACP,IAAI,EAAE,MAAM;oBACZ,IAAI,EAAE;;EAEhB,IAAI,CAAC,QAAQ;;;;;;;;;;;;;;;;;;4BAkBa;iBACjB;aACF;SACF;KACF,CAAC,CACH,CAAC;IAEF,yCAAyC;IACzC,MAAM,CAAC,MAAM,CACX,mBAAmB,EACnB,0CAA0C,EAC1C;QACE,WAAW,EAAE,CAAC,CAAC,MAAM,EAAE,CAAC,QAAQ,CAAC,sBAAsB,CAAC;QACxD,SAAS,EAAE,CAAC,CAAC,MAAM,EAAE,CAAC,QAAQ,EAAE,CAAC,QAAQ,CAAC,2BAA2B,CAAC;QACtE,SAAS,EAAE,CAAC,CAAC,MAAM,EAAE,CAAC,QAAQ,EAAE,CAAC,QAAQ,CAAC,wBAAwB,CAAC;KACpE,EACD,CAAC,IAAI,EAAE,EAAE,CAAC,CAAC;QACT,QAAQ,EAAE;YACR;gBACE,IAAI,EAAE,MAAM;gBACZ,OAAO,EAAE;oBACP,IAAI,EAAE,MAAM;oBACZ,IAAI,EAAE,4CAA4C,IAAI,CAAC,WAAW;;EAE5E,IAAI,CAAC,SAAS,CAAC,CAAC,CAAC,eAAe,IAAI,CAAC,SAAS,EAAE,CAAC,CAAC,CAAC,EAAE;EACrD,IAAI,CAAC,SAAS,CAAC,CAAC,CAAC,eAAe,IAAI,CAAC,SAAS,EAAE,CAAC,CAAC,CAAC,EAAE;;;;;;;;;;;;;;;yBAe9B;iBACd;aACF;SACF;KACF,CAAC,CACH,CAAC;IAEF,2BAA2B;IAC3B,MAAM,CAAC,MAAM,CACX,mBAAmB,EACnB,+CAA+C,EAC/C,EAAE,WAAW,EAAE,CAAC,CAAC,MAAM,EAAE,CAAC,QAAQ,CAAC,sBAAsB,CAAC,EAAE,EAC5D,CAAC,IAAI,EAAE,EAAE,CAAC,CAAC;QACT,QAAQ,EAAE;YACR;gBACE,IAAI,EAAE,MAAM;gBACZ,OAAO,EAAE;oBACP,IAAI,EAAE,MAAM;oBACZ,IAAI,EAAE,iCAAiC,IAAI,CAAC,WAAW;;;;;;;;;;;;;;;0BAezC;iBACf;aACF;SACF;KACF,CAAC,CACH,CAAC;AACJ,CAAC"}
|
package/dist/providers.d.ts
CHANGED
|
@@ -43,5 +43,20 @@ export declare function getProviderCapabilities(provider: AIProvider): {
|
|
|
43
43
|
thinking: boolean;
|
|
44
44
|
caching: boolean;
|
|
45
45
|
maxContext: number;
|
|
46
|
+
streaming: boolean;
|
|
46
47
|
};
|
|
48
|
+
export interface StreamProgress {
|
|
49
|
+
stage: 'connecting' | 'thinking' | 'streaming' | 'complete';
|
|
50
|
+
tokensReceived: number;
|
|
51
|
+
partialContent: string;
|
|
52
|
+
elapsedMs: number;
|
|
53
|
+
}
|
|
54
|
+
export type StreamCallback = (progress: StreamProgress) => void;
|
|
55
|
+
/**
|
|
56
|
+
* Stream chat response with progress callback
|
|
57
|
+
* Currently only supports Anthropic (best streaming support)
|
|
58
|
+
*/
|
|
59
|
+
export declare function chatStream(prompt: string, options: ChatOptions & {
|
|
60
|
+
onProgress?: StreamCallback;
|
|
61
|
+
}): Promise<ChatResponse>;
|
|
47
62
|
//# sourceMappingURL=providers.d.ts.map
|
package/dist/providers.d.ts.map
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"providers.d.ts","sourceRoot":"","sources":["../src/providers.ts"],"names":[],"mappings":"AAAA;;;;;;;;GAQG;AAEH,OAAO,EAAwC,KAAK,UAAU,EAAE,MAAM,aAAa,CAAC;AAKpF,MAAM,WAAW,WAAW;IAC1B,YAAY,CAAC,EAAE,MAAM,CAAC;IACtB,SAAS,CAAC,EAAE,MAAM,CAAC;IACnB,WAAW,CAAC,EAAE,MAAM,CAAC;IACrB,WAAW,CAAC,EAAE,OAAO,CAAC;IACtB,OAAO,CAAC,EAAE,MAAM,CAAC;CAClB;AAED,MAAM,WAAW,YAAY;IAC3B,OAAO,EAAE,MAAM,CAAC;IAChB,QAAQ,EAAE,UAAU,CAAC;IACrB,KAAK,EAAE,MAAM,CAAC;IACd,WAAW,CAAC,EAAE,MAAM,CAAC;IACrB,YAAY,CAAC,EAAE,MAAM,CAAC;IACtB,MAAM,CAAC,EAAE,OAAO,CAAC;CAClB;AAyCD;;;GAGG;AACH,wBAAsB,IAAI,CAAC,MAAM,EAAE,MAAM,EAAE,OAAO,GAAE,WAAgB,GAAG,OAAO,CAAC,YAAY,CAAC,CA2D3F;AAmUD;;GAEG;AACH,wBAAgB,mBAAmB,CAAC,QAAQ,EAAE,UAAU,GAAG,OAAO,CAEjE;AAED;;GAEG;AACH,wBAAgB,eAAe,IAAI,MAAM,CAGxC;AAED;;GAEG;AACH,wBAAgB,uBAAuB,CAAC,QAAQ,EAAE,UAAU,GAAG;IAC7D,QAAQ,EAAE,OAAO,CAAC;IAClB,OAAO,EAAE,OAAO,CAAC;IACjB,UAAU,EAAE,MAAM,CAAC;CACpB,CAaA"}
|
|
1
|
+
{"version":3,"file":"providers.d.ts","sourceRoot":"","sources":["../src/providers.ts"],"names":[],"mappings":"AAAA;;;;;;;;GAQG;AAEH,OAAO,EAAwC,KAAK,UAAU,EAAE,MAAM,aAAa,CAAC;AAKpF,MAAM,WAAW,WAAW;IAC1B,YAAY,CAAC,EAAE,MAAM,CAAC;IACtB,SAAS,CAAC,EAAE,MAAM,CAAC;IACnB,WAAW,CAAC,EAAE,MAAM,CAAC;IACrB,WAAW,CAAC,EAAE,OAAO,CAAC;IACtB,OAAO,CAAC,EAAE,MAAM,CAAC;CAClB;AAED,MAAM,WAAW,YAAY;IAC3B,OAAO,EAAE,MAAM,CAAC;IAChB,QAAQ,EAAE,UAAU,CAAC;IACrB,KAAK,EAAE,MAAM,CAAC;IACd,WAAW,CAAC,EAAE,MAAM,CAAC;IACrB,YAAY,CAAC,EAAE,MAAM,CAAC;IACtB,MAAM,CAAC,EAAE,OAAO,CAAC;CAClB;AAyCD;;;GAGG;AACH,wBAAsB,IAAI,CAAC,MAAM,EAAE,MAAM,EAAE,OAAO,GAAE,WAAgB,GAAG,OAAO,CAAC,YAAY,CAAC,CA2D3F;AAmUD;;GAEG;AACH,wBAAgB,mBAAmB,CAAC,QAAQ,EAAE,UAAU,GAAG,OAAO,CAEjE;AAED;;GAEG;AACH,wBAAgB,eAAe,IAAI,MAAM,CAGxC;AAED;;GAEG;AACH,wBAAgB,uBAAuB,CAAC,QAAQ,EAAE,UAAU,GAAG;IAC7D,QAAQ,EAAE,OAAO,CAAC;IAClB,OAAO,EAAE,OAAO,CAAC;IACjB,UAAU,EAAE,MAAM,CAAC;IACnB,SAAS,EAAE,OAAO,CAAC;CACpB,CAaA;AAMD,MAAM,WAAW,cAAc;IAC7B,KAAK,EAAE,YAAY,GAAG,UAAU,GAAG,WAAW,GAAG,UAAU,CAAC;IAC5D,cAAc,EAAE,MAAM,CAAC;IACvB,cAAc,EAAE,MAAM,CAAC;IACvB,SAAS,EAAE,MAAM,CAAC;CACnB;AAED,MAAM,MAAM,cAAc,GAAG,CAAC,QAAQ,EAAE,cAAc,KAAK,IAAI,CAAC;AAEhE;;;GAGG;AACH,wBAAsB,UAAU,CAC9B,MAAM,EAAE,MAAM,EACd,OAAO,EAAE,WAAW,GAAG;IAAE,UAAU,CAAC,EAAE,cAAc,CAAA;CAAE,GACrD,OAAO,CAAC,YAAY,CAAC,CAsLvB"}
|
package/dist/providers.js
CHANGED
|
@@ -378,15 +378,179 @@ export function getCurrentModel() {
|
|
|
378
378
|
export function getProviderCapabilities(provider) {
|
|
379
379
|
switch (provider) {
|
|
380
380
|
case 'anthropic':
|
|
381
|
-
return { thinking: true, caching: true, maxContext: 200000 };
|
|
381
|
+
return { thinking: true, caching: true, maxContext: 200000, streaming: true };
|
|
382
382
|
case 'openai':
|
|
383
|
-
return { thinking: false, caching: false, maxContext: 128000 };
|
|
383
|
+
return { thinking: false, caching: false, maxContext: 128000, streaming: true };
|
|
384
384
|
case 'google':
|
|
385
|
-
return { thinking: false, caching: false, maxContext: 1000000 };
|
|
385
|
+
return { thinking: false, caching: false, maxContext: 1000000, streaming: false };
|
|
386
386
|
case 'xai':
|
|
387
|
-
return { thinking: false, caching: false, maxContext: 100000 };
|
|
387
|
+
return { thinking: false, caching: false, maxContext: 100000, streaming: true };
|
|
388
388
|
default:
|
|
389
|
-
return { thinking: false, caching: false, maxContext: 8000 };
|
|
389
|
+
return { thinking: false, caching: false, maxContext: 8000, streaming: false };
|
|
390
390
|
}
|
|
391
391
|
}
|
|
392
|
+
/**
|
|
393
|
+
* Stream chat response with progress callback
|
|
394
|
+
* Currently only supports Anthropic (best streaming support)
|
|
395
|
+
*/
|
|
396
|
+
export async function chatStream(prompt, options) {
|
|
397
|
+
const provider = getActiveProvider();
|
|
398
|
+
const apiKey = getProviderApiKey(provider);
|
|
399
|
+
if (!apiKey) {
|
|
400
|
+
throw new Error(`No API key configured for ${provider}`);
|
|
401
|
+
}
|
|
402
|
+
// Only Anthropic has good streaming support for our use case
|
|
403
|
+
if (provider !== 'anthropic') {
|
|
404
|
+
// Fall back to non-streaming for other providers
|
|
405
|
+
return chat(prompt, options);
|
|
406
|
+
}
|
|
407
|
+
const config = PROVIDER_CONFIGS.anthropic;
|
|
408
|
+
const useThinking = options.useThinking ?? true;
|
|
409
|
+
const maxTokens = options.maxTokens ?? config.maxTokens;
|
|
410
|
+
const onProgress = options.onProgress;
|
|
411
|
+
const startTime = Date.now();
|
|
412
|
+
const body = {
|
|
413
|
+
model: config.model,
|
|
414
|
+
max_tokens: maxTokens,
|
|
415
|
+
stream: true, // Enable streaming
|
|
416
|
+
messages: [{ role: 'user', content: prompt }],
|
|
417
|
+
};
|
|
418
|
+
if (options.systemPrompt) {
|
|
419
|
+
body.system = [
|
|
420
|
+
{
|
|
421
|
+
type: 'text',
|
|
422
|
+
text: options.systemPrompt,
|
|
423
|
+
cache_control: { type: 'ephemeral' },
|
|
424
|
+
},
|
|
425
|
+
];
|
|
426
|
+
}
|
|
427
|
+
if (useThinking) {
|
|
428
|
+
body.thinking = {
|
|
429
|
+
type: 'enabled',
|
|
430
|
+
budget_tokens: config.thinkingBudget,
|
|
431
|
+
};
|
|
432
|
+
}
|
|
433
|
+
// Notify connecting
|
|
434
|
+
onProgress?.({
|
|
435
|
+
stage: 'connecting',
|
|
436
|
+
tokensReceived: 0,
|
|
437
|
+
partialContent: '',
|
|
438
|
+
elapsedMs: Date.now() - startTime,
|
|
439
|
+
});
|
|
440
|
+
const response = await fetch(config.url, {
|
|
441
|
+
method: 'POST',
|
|
442
|
+
headers: {
|
|
443
|
+
'Content-Type': 'application/json',
|
|
444
|
+
[config.authHeader]: apiKey,
|
|
445
|
+
'anthropic-version': '2023-06-01',
|
|
446
|
+
'anthropic-beta': 'prompt-caching-2024-07-31,token-efficient-tools-2025-02-19',
|
|
447
|
+
},
|
|
448
|
+
body: JSON.stringify(body),
|
|
449
|
+
});
|
|
450
|
+
if (!response.ok) {
|
|
451
|
+
const error = await response.text();
|
|
452
|
+
if (response.status === 429) {
|
|
453
|
+
throw new Error(`Rate limited by Anthropic. Wait a moment and try again.`);
|
|
454
|
+
}
|
|
455
|
+
if (response.status === 401) {
|
|
456
|
+
throw new Error(`Invalid API key for Anthropic.`);
|
|
457
|
+
}
|
|
458
|
+
throw new Error(`Anthropic API error (${response.status}): ${error.slice(0, 200)}`);
|
|
459
|
+
}
|
|
460
|
+
if (!response.body) {
|
|
461
|
+
throw new Error('No response body');
|
|
462
|
+
}
|
|
463
|
+
// Parse SSE stream
|
|
464
|
+
const reader = response.body.getReader();
|
|
465
|
+
const decoder = new TextDecoder();
|
|
466
|
+
let buffer = '';
|
|
467
|
+
let content = '';
|
|
468
|
+
let tokensReceived = 0;
|
|
469
|
+
let inThinking = false;
|
|
470
|
+
let inputTokens = 0;
|
|
471
|
+
let outputTokens = 0;
|
|
472
|
+
let cached = false;
|
|
473
|
+
try {
|
|
474
|
+
while (true) {
|
|
475
|
+
const { done, value } = await reader.read();
|
|
476
|
+
if (done)
|
|
477
|
+
break;
|
|
478
|
+
buffer += decoder.decode(value, { stream: true });
|
|
479
|
+
const lines = buffer.split('\n');
|
|
480
|
+
buffer = lines.pop() || ''; // Keep incomplete line in buffer
|
|
481
|
+
for (const line of lines) {
|
|
482
|
+
if (!line.startsWith('data: '))
|
|
483
|
+
continue;
|
|
484
|
+
const data = line.slice(6);
|
|
485
|
+
if (data === '[DONE]')
|
|
486
|
+
continue;
|
|
487
|
+
try {
|
|
488
|
+
const event = JSON.parse(data);
|
|
489
|
+
// Track thinking vs text blocks
|
|
490
|
+
if (event.type === 'content_block_start') {
|
|
491
|
+
inThinking = event.content_block?.type === 'thinking';
|
|
492
|
+
}
|
|
493
|
+
// Accumulate text content (skip thinking blocks)
|
|
494
|
+
if (event.type === 'content_block_delta' && event.delta?.type === 'text_delta' && !inThinking) {
|
|
495
|
+
const text = event.delta.text || '';
|
|
496
|
+
content += text;
|
|
497
|
+
tokensReceived += Math.ceil(text.length / 4); // Rough token estimate
|
|
498
|
+
onProgress?.({
|
|
499
|
+
stage: 'streaming',
|
|
500
|
+
tokensReceived,
|
|
501
|
+
partialContent: content,
|
|
502
|
+
elapsedMs: Date.now() - startTime,
|
|
503
|
+
});
|
|
504
|
+
}
|
|
505
|
+
// Track if we're in thinking mode
|
|
506
|
+
if (event.type === 'content_block_delta' && inThinking) {
|
|
507
|
+
onProgress?.({
|
|
508
|
+
stage: 'thinking',
|
|
509
|
+
tokensReceived: 0,
|
|
510
|
+
partialContent: '',
|
|
511
|
+
elapsedMs: Date.now() - startTime,
|
|
512
|
+
});
|
|
513
|
+
}
|
|
514
|
+
// Capture usage from message_delta or message_stop
|
|
515
|
+
if (event.type === 'message_delta' && event.usage) {
|
|
516
|
+
outputTokens = event.usage.output_tokens ?? 0;
|
|
517
|
+
}
|
|
518
|
+
if (event.type === 'message_start' && event.message?.usage) {
|
|
519
|
+
inputTokens = event.message.usage.input_tokens ?? 0;
|
|
520
|
+
cached = (event.message.usage.cache_read_input_tokens ?? 0) > 0;
|
|
521
|
+
}
|
|
522
|
+
}
|
|
523
|
+
catch {
|
|
524
|
+
// Skip malformed JSON
|
|
525
|
+
}
|
|
526
|
+
}
|
|
527
|
+
}
|
|
528
|
+
}
|
|
529
|
+
finally {
|
|
530
|
+
reader.releaseLock();
|
|
531
|
+
}
|
|
532
|
+
// Final progress notification
|
|
533
|
+
onProgress?.({
|
|
534
|
+
stage: 'complete',
|
|
535
|
+
tokensReceived,
|
|
536
|
+
partialContent: content,
|
|
537
|
+
elapsedMs: Date.now() - startTime,
|
|
538
|
+
});
|
|
539
|
+
// Record metrics
|
|
540
|
+
recordTokens(inputTokens, outputTokens, { provider: 'anthropic', cached });
|
|
541
|
+
try {
|
|
542
|
+
recordCost(process.cwd(), 'anthropic', inputTokens, outputTokens, cached);
|
|
543
|
+
}
|
|
544
|
+
catch {
|
|
545
|
+
// Cost tracking is optional
|
|
546
|
+
}
|
|
547
|
+
return {
|
|
548
|
+
content,
|
|
549
|
+
provider: 'anthropic',
|
|
550
|
+
model: config.model,
|
|
551
|
+
inputTokens,
|
|
552
|
+
outputTokens,
|
|
553
|
+
cached,
|
|
554
|
+
};
|
|
555
|
+
}
|
|
392
556
|
//# sourceMappingURL=providers.js.map
|