modelmix 4.5.26 → 4.5.30
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 +4 -0
- package/index.js +29 -7
- package/package.json +10 -10
- package/pnpm-workspace.yaml +4 -0
- package/skills/modelmix/SKILL.md +2 -2
- package/test/anthropic.test.js +65 -0
package/README.md
CHANGED
|
@@ -136,6 +136,7 @@ Here's a comprehensive list of available methods:
|
|
|
136
136
|
|
|
137
137
|
| Method | Provider | Model | Price (I/O) per 1 M tokens |
|
|
138
138
|
| ------------------- | ---------- | ---------------------------- | -------------------------- |
|
|
139
|
+
| `gpt55()` | OpenAI | gpt-5.5 | [\$5.00 / \$30.00][1] |
|
|
139
140
|
| `gpt54()` | OpenAI | gpt-5.4 | [\$2.50 / \$15.00][1] |
|
|
140
141
|
| `gpt54mini()` | OpenAI | gpt-5.4-mini | [\$0.75 / \$4.50][1] |
|
|
141
142
|
| `gpt54nano()` | OpenAI | gpt-5.4-nano | [\$0.20 / \$1.25][1] |
|
|
@@ -148,8 +149,11 @@ Here's a comprehensive list of available methods:
|
|
|
148
149
|
| `gpt41mini()` | OpenAI | gpt-4.1-mini | [\$0.40 / \$1.60][1] |
|
|
149
150
|
| `gpt41nano()` | OpenAI | gpt-4.1-nano | [\$0.10 / \$0.40][1] |
|
|
150
151
|
| `gptOss()` | Together | gpt-oss-120B | [\$0.15 / \$0.60][7] |
|
|
152
|
+
| `fable5[think]()` | Anthropic | claude-fable-5 | [\$10.00 / \$50.00][2] |
|
|
153
|
+
| `opus48[think]()` | Anthropic | claude-opus-4-8 | [\$5.00 / \$25.00][2] |
|
|
151
154
|
| `opus47[think]()` | Anthropic | claude-opus-4-7 | [\$5.00 / \$25.00][2] |
|
|
152
155
|
| `opus46[think]()` | Anthropic | claude-opus-4-6 | [\$5.00 / \$25.00][2] |
|
|
156
|
+
| `sonnet5[think]()` | Anthropic | claude-sonnet-5 | [\$3.00 / \$15.00][2] |
|
|
153
157
|
| `sonnet46[think]()` | Anthropic | claude-sonnet-4-6 | [\$3.00 / \$15.00][2] |
|
|
154
158
|
| `haiku45[think]()` | Anthropic | claude-haiku-4-5-20251001 | [\$1.00 / \$5.00][2] |
|
|
155
159
|
| `gemini31pro()` | Google | gemini-3.1-pro-preview | [\$2.00 / \$12.00][3] |
|
package/index.js
CHANGED
|
@@ -58,9 +58,11 @@ const MODEL_PRICING = {
|
|
|
58
58
|
'gpt-oss-120b': [0.15, 0.60],
|
|
59
59
|
'openai/gpt-oss-120b:free': [0, 0],
|
|
60
60
|
// Anthropic
|
|
61
|
+
'claude-fable-5': [10.00, 50.00],
|
|
62
|
+
'claude-sonnet-5': [3.00, 15.00],
|
|
63
|
+
'claude-opus-4-8': [5.00, 25.00],
|
|
61
64
|
'claude-opus-4-7': [5.00, 25.00],
|
|
62
65
|
'claude-opus-4-6': [5.00, 25.00],
|
|
63
|
-
'claude-opus-4-5-20251101': [5.00, 25.00],
|
|
64
66
|
'claude-opus-4-1-20250805': [15.00, 75.00],
|
|
65
67
|
'claude-sonnet-4-6': [3.00, 15.00],
|
|
66
68
|
'claude-sonnet-4-5-20250929': [3.00, 15.00],
|
|
@@ -344,6 +346,17 @@ class ModelMix {
|
|
|
344
346
|
if (mix.openrouter) this.attach('openai/gpt-oss-120b:free', new MixOpenRouter({ options, config }));
|
|
345
347
|
return this;
|
|
346
348
|
}
|
|
349
|
+
fable5({ options = {}, config = {} } = {}) {
|
|
350
|
+
return this.attach('claude-fable-5', new MixAnthropic({ options, config }));
|
|
351
|
+
}
|
|
352
|
+
fable5think({ options = {}, config = {} } = {}) {
|
|
353
|
+
options = { ...MixAnthropic.fableThinkingOptions, ...options };
|
|
354
|
+
return this.attach('claude-fable-5', new MixAnthropic({ options, config }));
|
|
355
|
+
}
|
|
356
|
+
opus48think({ options = {}, config = {} } = {}) {
|
|
357
|
+
options = { ...MixAnthropic.thinkingOptions, ...options };
|
|
358
|
+
return this.attach('claude-opus-4-8', new MixAnthropic({ options, config }));
|
|
359
|
+
}
|
|
347
360
|
opus47think({ options = {}, config = {} } = {}) {
|
|
348
361
|
options = { ...MixAnthropic.thinkingOptions, ...options };
|
|
349
362
|
return this.attach('claude-opus-4-7', new MixAnthropic({ options, config }));
|
|
@@ -352,9 +365,8 @@ class ModelMix {
|
|
|
352
365
|
options = { ...MixAnthropic.thinkingOptions, ...options };
|
|
353
366
|
return this.attach('claude-opus-4-6', new MixAnthropic({ options, config }));
|
|
354
367
|
}
|
|
355
|
-
|
|
356
|
-
|
|
357
|
-
return this.attach('claude-opus-4-5-20251101', new MixAnthropic({ options, config }));
|
|
368
|
+
opus48({ options = {}, config = {} } = {}) {
|
|
369
|
+
return this.attach('claude-opus-4-8', new MixAnthropic({ options, config }));
|
|
358
370
|
}
|
|
359
371
|
opus47({ options = {}, config = {} } = {}) {
|
|
360
372
|
return this.attach('claude-opus-4-7', new MixAnthropic({ options, config }));
|
|
@@ -362,9 +374,6 @@ class ModelMix {
|
|
|
362
374
|
opus46({ options = {}, config = {} } = {}) {
|
|
363
375
|
return this.attach('claude-opus-4-6', new MixAnthropic({ options, config }));
|
|
364
376
|
}
|
|
365
|
-
opus45({ options = {}, config = {} } = {}) {
|
|
366
|
-
return this.attach('claude-opus-4-5-20251101', new MixAnthropic({ options, config }));
|
|
367
|
-
}
|
|
368
377
|
opus41({ options = {}, config = {} } = {}) {
|
|
369
378
|
return this.attach('claude-opus-4-1-20250805', new MixAnthropic({ options, config }));
|
|
370
379
|
}
|
|
@@ -372,6 +381,13 @@ class ModelMix {
|
|
|
372
381
|
options = { ...MixAnthropic.thinkingOptions, ...options };
|
|
373
382
|
return this.attach('claude-opus-4-1-20250805', new MixAnthropic({ options, config }));
|
|
374
383
|
}
|
|
384
|
+
sonnet5({ options = {}, config = {} } = {}) {
|
|
385
|
+
return this.attach('claude-sonnet-5', new MixAnthropic({ options, config }));
|
|
386
|
+
}
|
|
387
|
+
sonnet5think({ options = {}, config = {} } = {}) {
|
|
388
|
+
options = { ...MixAnthropic.thinkingOptions, ...options };
|
|
389
|
+
return this.attach('claude-sonnet-5', new MixAnthropic({ options, config }));
|
|
390
|
+
}
|
|
375
391
|
sonnet4({ options = {}, config = {} } = {}) {
|
|
376
392
|
return this.attach('claude-sonnet-4-20250514', new MixAnthropic({ options, config }));
|
|
377
393
|
}
|
|
@@ -2083,6 +2099,12 @@ class MixAnthropic extends MixCustom {
|
|
|
2083
2099
|
temperature: 1
|
|
2084
2100
|
};
|
|
2085
2101
|
|
|
2102
|
+
static fableThinkingOptions = {
|
|
2103
|
+
output_config: { effort: 'max' },
|
|
2104
|
+
thinking: { display: 'summarized' },
|
|
2105
|
+
temperature: 1
|
|
2106
|
+
};
|
|
2107
|
+
|
|
2086
2108
|
getDefaultConfig(customConfig) {
|
|
2087
2109
|
|
|
2088
2110
|
if (!process.env.ANTHROPIC_API_KEY) {
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "modelmix",
|
|
3
|
-
"version": "4.5.
|
|
3
|
+
"version": "4.5.30",
|
|
4
4
|
"description": "🧬 Reliable interface with automatic fallback for AI LLMs.",
|
|
5
5
|
"main": "index.js",
|
|
6
6
|
"repository": {
|
|
@@ -22,9 +22,9 @@
|
|
|
22
22
|
"llama",
|
|
23
23
|
"fallback",
|
|
24
24
|
"kimi",
|
|
25
|
-
"
|
|
25
|
+
"mythos",
|
|
26
26
|
"gpt5",
|
|
27
|
-
"
|
|
27
|
+
"fable",
|
|
28
28
|
"sonnet",
|
|
29
29
|
"openrouter",
|
|
30
30
|
"gemini",
|
|
@@ -49,15 +49,15 @@
|
|
|
49
49
|
"dependencies": {
|
|
50
50
|
"@modelcontextprotocol/sdk": "^1.29.0",
|
|
51
51
|
"bottleneck": "^2.19.5",
|
|
52
|
-
"file-type": "^21.3.
|
|
53
|
-
"lemonlog": "^1.2.
|
|
54
|
-
"ws": "^8.
|
|
52
|
+
"file-type": "^21.3.4",
|
|
53
|
+
"lemonlog": "^1.2.2",
|
|
54
|
+
"ws": "^8.21.0"
|
|
55
55
|
},
|
|
56
56
|
"devDependencies": {
|
|
57
|
-
"chai": "^5.
|
|
57
|
+
"chai": "^5.3.3",
|
|
58
58
|
"mocha": "^11.7.5",
|
|
59
|
-
"nock": "^14.0.
|
|
60
|
-
"sinon": "^21.
|
|
59
|
+
"nock": "^14.0.15",
|
|
60
|
+
"sinon": "^21.1.2"
|
|
61
61
|
},
|
|
62
62
|
"scripts": {
|
|
63
63
|
"test": "mocha test/**/*.js --timeout 10000 --require test/setup.js",
|
|
@@ -70,6 +70,6 @@
|
|
|
70
70
|
"test:live": "mocha test/live.test.js --timeout 10000 --require test/setup.js",
|
|
71
71
|
"test:live.mcp": "mocha test/live.mcp.js --timeout 60000 --require test/setup.js",
|
|
72
72
|
"test:tokens": "mocha test/tokens.test.js --timeout 10000 --require test/setup.js",
|
|
73
|
-
"test:offline": "mocha test/json.test.js test/fallback.test.js test/templates.test.js test/images.test.js test/bottleneck.test.js test/tokens.test.js test/history.test.js --timeout 10000 --require test/setup.js"
|
|
73
|
+
"test:offline": "mocha test/json.test.js test/fallback.test.js test/templates.test.js test/images.test.js test/bottleneck.test.js test/tokens.test.js test/history.test.js test/anthropic.test.js --timeout 10000 --require test/setup.js"
|
|
74
74
|
}
|
|
75
75
|
}
|
package/pnpm-workspace.yaml
CHANGED
package/skills/modelmix/SKILL.md
CHANGED
|
@@ -96,9 +96,9 @@ If `sonnet46` fails, it automatically tries `gpt52`, then `gemini3flash`.
|
|
|
96
96
|
`gpt52()` `gpt52chat()` `gpt51()` `gpt5()` `gpt5mini()` `gpt5nano()` `gpt45()` `gpt41()` `gpt41mini()` `gpt41nano()` `o3()` `o4mini()`
|
|
97
97
|
|
|
98
98
|
### Anthropic
|
|
99
|
-
`
|
|
99
|
+
`fable5()` `opus48()` `opus47()` `opus46()` `opus41()` `sonnet5()` `sonnet46()` `sonnet45()` `sonnet4()` `haiku45()` `haiku35()`
|
|
100
100
|
|
|
101
|
-
Thinking variants: append `think` — e.g. `opus46think()` `
|
|
101
|
+
Thinking variants: append `think` — e.g. `fable5think()` `opus48think()` `opus47think()` `opus46think()` `sonnet5think()` `sonnet46think()` `sonnet45think()` `sonnet4think()` `opus41think()` `haiku45think()`
|
|
102
102
|
|
|
103
103
|
### Google
|
|
104
104
|
`gemini3pro()` `gemini3flash()` `gemini35flash()` `gemini25pro()` `gemini25flash()`
|
|
@@ -0,0 +1,65 @@
|
|
|
1
|
+
const { expect } = require('chai');
|
|
2
|
+
const { ModelMix, MixAnthropic } = require('../index.js');
|
|
3
|
+
|
|
4
|
+
describe('Anthropic Model Registration Tests', () => {
|
|
5
|
+
it('should register Claude Fable 5', () => {
|
|
6
|
+
const model = ModelMix.new();
|
|
7
|
+
model.fable5();
|
|
8
|
+
|
|
9
|
+
expect(model.models).to.have.length(1);
|
|
10
|
+
expect(model.models[0].key).to.equal('claude-fable-5');
|
|
11
|
+
expect(model.models[0].provider).to.be.instanceOf(MixAnthropic);
|
|
12
|
+
});
|
|
13
|
+
|
|
14
|
+
it('should register Claude Fable 5 with max effort thinking', () => {
|
|
15
|
+
const model = ModelMix.new();
|
|
16
|
+
model.fable5think();
|
|
17
|
+
|
|
18
|
+
expect(model.models).to.have.length(1);
|
|
19
|
+
expect(model.models[0].key).to.equal('claude-fable-5');
|
|
20
|
+
expect(model.models[0].provider.options.output_config).to.deep.equal({ effort: 'max' });
|
|
21
|
+
expect(model.models[0].provider.options.thinking).to.deep.equal({ display: 'summarized' });
|
|
22
|
+
});
|
|
23
|
+
|
|
24
|
+
it('should register Claude Opus 4.8', () => {
|
|
25
|
+
const model = ModelMix.new();
|
|
26
|
+
model.opus48();
|
|
27
|
+
|
|
28
|
+
expect(model.models).to.have.length(1);
|
|
29
|
+
expect(model.models[0].key).to.equal('claude-opus-4-8');
|
|
30
|
+
expect(model.models[0].provider).to.be.instanceOf(MixAnthropic);
|
|
31
|
+
});
|
|
32
|
+
|
|
33
|
+
it('should register Claude Opus 4.8 with thinking enabled', () => {
|
|
34
|
+
const model = ModelMix.new();
|
|
35
|
+
model.opus48think();
|
|
36
|
+
|
|
37
|
+
expect(model.models).to.have.length(1);
|
|
38
|
+
expect(model.models[0].key).to.equal('claude-opus-4-8');
|
|
39
|
+
expect(model.models[0].provider.options.thinking).to.deep.equal({
|
|
40
|
+
type: 'enabled',
|
|
41
|
+
budget_tokens: 1638
|
|
42
|
+
});
|
|
43
|
+
});
|
|
44
|
+
|
|
45
|
+
it('should register Claude Sonnet 5', () => {
|
|
46
|
+
const model = ModelMix.new();
|
|
47
|
+
model.sonnet5();
|
|
48
|
+
|
|
49
|
+
expect(model.models).to.have.length(1);
|
|
50
|
+
expect(model.models[0].key).to.equal('claude-sonnet-5');
|
|
51
|
+
expect(model.models[0].provider).to.be.instanceOf(MixAnthropic);
|
|
52
|
+
});
|
|
53
|
+
|
|
54
|
+
it('should register Claude Sonnet 5 with thinking enabled', () => {
|
|
55
|
+
const model = ModelMix.new();
|
|
56
|
+
model.sonnet5think();
|
|
57
|
+
|
|
58
|
+
expect(model.models).to.have.length(1);
|
|
59
|
+
expect(model.models[0].key).to.equal('claude-sonnet-5');
|
|
60
|
+
expect(model.models[0].provider.options.thinking).to.deep.equal({
|
|
61
|
+
type: 'enabled',
|
|
62
|
+
budget_tokens: 1638
|
|
63
|
+
});
|
|
64
|
+
});
|
|
65
|
+
});
|