cryptoiz-mcp 4.2.0 β†’ 4.4.0

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.
Files changed (2) hide show
  1. package/package.json +1 -1
  2. package/src/index.js +36 -23
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "cryptoiz-mcp",
3
- "version": "4.2.0",
3
+ "version": "4.4.0",
4
4
  "description": "CryptoIZ MCP Server β€” Solana DEX signals with x402 micropayments. Pay $0.01 USDC per call.",
5
5
  "type": "module",
6
6
  "main": "src/index.js",
package/src/index.js CHANGED
@@ -11,9 +11,22 @@ const SVM_PRIVATE_KEY = process.env.SVM_PRIVATE_KEY || '';
11
11
  const CRYPTOIZ_WALLET = new PublicKey('DsKmdkYx49Xc1WhqMUAztwhdYPTqieyC98VmnnJdgpXX');
12
12
  const USDC_MINT = new PublicKey('EPjFWdd5AufqSSqeM2qN1xzybapC8G4wEGGkZwyTDt1v');
13
13
  const SOL_RPC = 'https://api.mainnet-beta.solana.com';
14
- const AMOUNT = 10000;
15
-
16
- async function payAndFetch(url) {
14
+ // Tiered pricing per tool (USDC 6 decimals)
15
+ const PRICES = {
16
+ get_alpha_scanner: 50000, // $0.05
17
+ get_divergence: 20000, // $0.02
18
+ get_accumulation: 20000, // $0.02
19
+ get_btc_regime: 10000, // $0.01
20
+ };
21
+ const PRICE_LABELS = {
22
+ get_alpha_scanner: '$0.05',
23
+ get_divergence: '$0.02',
24
+ get_accumulation: '$0.02',
25
+ get_btc_regime: '$0.01',
26
+ };
27
+
28
+ async function payAndFetch(url, tool = 'get_alpha_scanner') {
29
+ const AMOUNT = PRICES[tool] || 10000;
17
30
  if (!SVM_PRIVATE_KEY) return { error: 'SVM_PRIVATE_KEY not set.' };
18
31
  const first = await fetch(url);
19
32
  if (first.status !== 402) return first.json();
@@ -37,7 +50,7 @@ const N = (v, d=2) => v != null && v !== 'N/A' ? parseFloat(v).toFixed(d) : 'N/A
37
50
  const sign = v => { const n = parseFloat(v||0); return n > 0 ? `+${n}` : `${n}`; };
38
51
  const shortCA = ca => ca ? `${ca.slice(0,6)}...${ca.slice(-4)}` : 'N/A';
39
52
  const dexLink = ca => ca ? `[Chart πŸ“Š](https://dexscreener.com/solana/${ca})` : 'N/A';
40
- const jupLink = ca => ca ? `[Buy πŸ›’](https://jup.ag/swap?inputCurrency=So11111111111111111111111111111111111111112&outputCurrency=${ca})` : 'N/A';
53
+
41
54
 
42
55
  // ══════════════════════════════════════════════════════════════════
43
56
  // ALPHA SCANNER β€” Markdown Table Format
@@ -59,11 +72,11 @@ function formatAlpha(data) {
59
72
  : 'βœ… Clear';
60
73
  const startMC = s.market_cap_when_signal_formed ? s.market_cap_when_signal_formed : 'N/A';
61
74
  const signalTime = s.signal_formed_at ? new Date(s.signal_formed_at).toLocaleDateString('id-ID') : 'N/A';
62
- return `| ${i} | **${s.name}** | \`${s.contract_address||'N/A'}\` | ${N(s.alpha_score)} | ${s.phase||'N/A'} | ${sign(s.whale_delta)} | ${sign(s.dolphin_delta)} | ${s.market_cap_now||'N/A'} | ${startMC} | ${signalTime} | ${N(s.score_safety)} | ${risk} | ${dexLink(s.contract_address)} | ${jupLink(s.contract_address)} |`;
75
+ return `| ${i} | **${s.name}** | \`${s.contract_address||'N/A'}\` | ${N(s.alpha_score)} | ${s.phase||'N/A'} | ${sign(s.whale_delta)} | ${sign(s.dolphin_delta)} | ${s.market_cap_now||'N/A'} | ${startMC} | ${signalTime} | ${N(s.score_safety)} | ${risk} | ${dexLink(s.contract_address)} |`;
63
76
  };
64
77
 
65
- const tableHeader = `| # | Token | Contract Address (CA) | Score | Phase | Whale Ξ” | Dolphin Ξ” | MC Now | Start MC | Signal Date | Safety | Risk | Chart | Buy |
66
- |---|-------|----------------------|-------|-------|---------|-----------|--------|----------|-------------|--------|------|-------|-----|`;
78
+ const tableHeader = `| # | Token | CA | Score | Phase | Whale Ξ” | Dolphin Ξ” | MC Now | Start MC | Signal Date | Safety | Risk | Chart |
79
+ |---|-------|-----|-------|-------|---------|-----------|--------|----------|-------------|--------|------|-------|`;
67
80
 
68
81
  let out = [];
69
82
 
@@ -82,7 +95,7 @@ function formatAlpha(data) {
82
95
  early.forEach((s, i) => out.push(tableRow(s, i+1)));
83
96
  out.push(``);
84
97
  out.push(`**Full CA for copy-paste:**`);
85
- early.forEach(s => out.push(`- **${s.name}:** \`${s.contract_address}\` β†’ ${jupLink(s.contract_address)}`));
98
+ early.forEach(s => out.push(`- **${s.name}:** \`${s.contract_address}\` β†’ ${dexLink(s.contract_address)}`))
86
99
  out.push(``);
87
100
  }
88
101
 
@@ -93,7 +106,7 @@ function formatAlpha(data) {
93
106
  building.forEach((s, i) => out.push(tableRow(s, i+1)));
94
107
  out.push(``);
95
108
  out.push(`**Full CA for copy-paste:**`);
96
- building.forEach(s => out.push(`- **${s.name}:** \`${s.contract_address}\` β†’ ${jupLink(s.contract_address)}`));
109
+ building.forEach(s => out.push(`- **${s.name}:** \`${s.contract_address}\` β†’ ${dexLink(s.contract_address)}`))
97
110
  out.push(``);
98
111
  }
99
112
 
@@ -125,11 +138,11 @@ function formatDivergence(data) {
125
138
  const date = data.fetched_at?.split('T')[0];
126
139
  const byType = data.signals_by_type || {};
127
140
 
128
- const tableHeader = `| # | Token | Contract Address (CA) | Div Score | Confidence | Whale Now→Prev | Dolphin Δ | Price | MC | Detected | Trade |
129
- |---|-------|----------------------|-----------|------------|----------------|-----------|-------|-----|----------|-------|`;
141
+ const tableHeader = `| # | Token | CA | Div Score | Confidence | Whale Now→Prev | Dolphin Δ | Price | MC | Detected | Chart |
142
+ |---|-------|-----|-----------|------------|----------------|-----------|-------|-----|----------|-------|`;
130
143
 
131
144
  const tableRow = (s, i) =>
132
- `| ${i} | **${s.name||'N/A'}** | \`${s.contract_address||'N/A'}\` | ${N(s.divergence_score)} | ${N(s.confidence_pct)}% | ${s.whale_holders_now||'?'}β†’${s.whale_holders_prev||'?'} (+${s.whale_delta||0}) | ${sign(s.dolphin_delta)} | $${s.price_now_usd||'N/A'} | ${s.market_cap_usd||'N/A'} | ${s.detected||'N/A'} | ${jupLink(s.contract_address)} |`;
145
+ `| ${i} | **${s.name||'N/A'}** | \`${s.contract_address||'N/A'}\` | ${N(s.divergence_score)} | ${N(s.confidence_pct)}% | ${s.whale_holders_now||'?'}β†’${s.whale_holders_prev||'?'} (+${s.whale_delta||0}) | ${sign(s.dolphin_delta)} | $${s.price_now_usd||'N/A'} | ${s.market_cap_usd||'N/A'} | ${s.detected||'N/A'} | ${dexLink(s.contract_address)} |`;
133
146
 
134
147
  let out = [];
135
148
  out.push(`## πŸ“Š CryptoIZ Divergence Scanner`);
@@ -166,7 +179,7 @@ function formatDivergence(data) {
166
179
  sigs.forEach((s, i) => out.push(tableRow(s, i+1)));
167
180
  out.push(``);
168
181
  out.push(`**Full CA for copy-paste:**`);
169
- sigs.forEach(s => out.push(`- **${s.name}:** \`${s.contract_address}\` β†’ ${jupLink(s.contract_address)}`));
182
+ sigs.forEach(s => out.push(`- **${s.name}:** \`${s.contract_address}\` β†’ ${dexLink(s.contract_address)}`));
170
183
  out.push(``);
171
184
  });
172
185
 
@@ -183,11 +196,11 @@ function formatAccumulation(data) {
183
196
  const tokens = data.tokens || [];
184
197
  const date = data.fetched_at?.split('T')[0];
185
198
 
186
- const tableHeader = `| # | Token | Contract Address (CA) | Composite | Strength | Structure | AccDist | Holder | Market | MC | Price | Trade |
187
- |---|-------|----------------------|-----------|----------|-----------|---------|--------|--------|-----|-------|-------|`;
199
+ const tableHeader = `| # | Token | CA | Composite | Strength | Structure | AccDist | Holder | Market | MC | Price | Chart |
200
+ |---|-------|-----|-----------|----------|-----------|---------|--------|--------|-----|-------|-------|`;
188
201
 
189
202
  const tableRow = (t, i) =>
190
- `| ${i} | **${t.name||'N/A'}** | \`${t.contract_address||'N/A'}\` | **${N(t.score_composite)}** | ${t.accumulation_strength||'N/A'} | ${N(t.score_structure)} | ${N(t.score_accdist)} | ${N(t.score_holder)} | ${N(t.score_market)} | ${t.market_cap_now||'N/A'} | $${t.price_now_usd||'N/A'} | ${jupLink(t.contract_address)} |`;
203
+ `| ${i} | **${t.name||'N/A'}** | \`${t.contract_address||'N/A'}\` | **${N(t.score_composite)}** | ${t.accumulation_strength||'N/A'} | ${N(t.score_structure)} | ${N(t.score_accdist)} | ${N(t.score_holder)} | ${N(t.score_market)} | ${t.market_cap_now||'N/A'} | $${t.price_now_usd||'N/A'} | ${dexLink(t.contract_address)} |`;
191
204
 
192
205
  let out = [];
193
206
  out.push(`## πŸ’° CryptoIZ Accumulation Dashboard`);
@@ -202,7 +215,7 @@ function formatAccumulation(data) {
202
215
  tokens.forEach((t, i) => out.push(tableRow(t, i+1)));
203
216
  out.push(``);
204
217
  out.push(`**Full CA for copy-paste:**`);
205
- tokens.slice(0, 10).forEach(t => out.push(`- **${t.name}:** \`${t.contract_address}\` β†’ ${jupLink(t.contract_address)}`));
218
+ tokens.slice(0, 10).forEach(t => out.push(`- **${t.name}:** \`${t.contract_address}\` β†’ ${dexLink(t.contract_address)}`));
206
219
  out.push(``);
207
220
  out.push(`---`);
208
221
  out.push(`⚠️ *Not financial advice. Always DYOR. Data: [CryptoIZ](https://cryptoiz.org) | @cryptoiz_IDN*`);
@@ -378,7 +391,7 @@ const TOOLS = [
378
391
  // ══════════════════════════════════════════════════════════════════
379
392
  // SERVER
380
393
  // ══════════════════════════════════════════════════════════════════
381
- const server = new Server({ name: 'cryptoiz-mcp', version: '4.2.0' }, { capabilities: { tools: {} } });
394
+ const server = new Server({ name: 'cryptoiz-mcp', version: '4.4.0' }, { capabilities: { tools: {} } });
382
395
  server.setRequestHandler(ListToolsRequestSchema, async () => ({ tools: TOOLS }));
383
396
  server.setRequestHandler(CallToolRequestSchema, async (request) => {
384
397
  const { name, arguments: args } = request.params;
@@ -386,7 +399,7 @@ server.setRequestHandler(CallToolRequestSchema, async (request) => {
386
399
  if (name === 'get_status') return { content: [{ type: 'text', text: formatStatus() }] };
387
400
 
388
401
  if (name === 'get_alpha_scanner') {
389
- const data = await payAndFetch(`${GATEWAY_URL}?tool=get_alpha_scanner`);
402
+ const data = await payAndFetch(`${GATEWAY_URL}?tool=get_alpha_scanner`, 'get_alpha_scanner');
390
403
  if (data.error) return { content: [{ type: 'text', text: `❌ ${data.error}` }], isError: true };
391
404
  if (args?.min_score && data.signals) { data.signals = data.signals.filter(s => parseFloat(s.alpha_score) >= args.min_score); data.total_signals = data.signals.length; }
392
405
  if (args?.entry_class && data.signals) { data.signals = data.signals.filter(s => s.signal_class === args.entry_class); data.total_signals = data.signals.length; }
@@ -397,20 +410,20 @@ server.setRequestHandler(CallToolRequestSchema, async (request) => {
397
410
  const p = new URLSearchParams({ tool: 'get_divergence' });
398
411
  if (args?.timeframe) p.set('tf', args.timeframe);
399
412
  if (args?.limit) p.set('limit', String(args.limit));
400
- const data = await payAndFetch(`${GATEWAY_URL}?${p}`);
413
+ const data = await payAndFetch(`${GATEWAY_URL}?${p}`, 'get_divergence');
401
414
  if (data.error) return { content: [{ type: 'text', text: `❌ ${data.error}` }], isError: true };
402
415
  return { content: [{ type: 'text', text: formatDivergence(data) }] };
403
416
  }
404
417
 
405
418
  if (name === 'get_accumulation') {
406
- const data = await payAndFetch(`${GATEWAY_URL}?tool=get_accumulation`);
419
+ const data = await payAndFetch(`${GATEWAY_URL}?tool=get_accumulation`, 'get_accumulation');
407
420
  if (data.error) return { content: [{ type: 'text', text: `❌ ${data.error}` }], isError: true };
408
421
  if (args?.min_composite && data.tokens) { data.tokens = data.tokens.filter(t => parseFloat(t.score_composite) >= args.min_composite); data.total_tokens = data.tokens.length; }
409
422
  return { content: [{ type: 'text', text: formatAccumulation(data) }] };
410
423
  }
411
424
 
412
425
  if (name === 'get_btc_regime') {
413
- const data = await payAndFetch(`${GATEWAY_URL}?tool=get_btc_regime`);
426
+ const data = await payAndFetch(`${GATEWAY_URL}?tool=get_btc_regime`, 'get_btc_regime');
414
427
  if (data.error) return { content: [{ type: 'text', text: `❌ ${data.error}` }], isError: true };
415
428
  return { content: [{ type: 'text', text: formatBTC(data) }] };
416
429
  }
@@ -418,7 +431,7 @@ server.setRequestHandler(CallToolRequestSchema, async (request) => {
418
431
  if (name === 'get_token_ca') {
419
432
  const tokenName = args?.token_name || '';
420
433
  if (!tokenName) return { content: [{ type: 'text', text: '❌ Please provide a token_name. Example: "Aliens"' }], isError: true };
421
- const data = await payAndFetch(`${GATEWAY_URL}?tool=get_alpha_scanner`);
434
+ const data = await payAndFetch(`${GATEWAY_URL}?tool=get_alpha_scanner`, 'get_alpha_scanner');
422
435
  return { content: [{ type: 'text', text: await getTokenCA(tokenName, data) }] };
423
436
  }
424
437