@lov3kaizen/agentsea-crews 1.0.0 → 1.1.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.
- package/README.md +27 -1
- package/dist/{chunk-G3PAPYOI.mjs → chunk-6JLVFEU6.mjs} +13 -13
- package/dist/{chunk-QMK3HWFX.mjs → chunk-V6VK6BOL.mjs} +164 -31
- package/dist/index.js +193 -56
- package/dist/index.mjs +19 -14
- package/dist/nestjs/index.js +163 -31
- package/dist/nestjs/index.mjs +1 -1
- package/dist/templates/index.js +175 -43
- package/dist/templates/index.mjs +2 -2
- package/package.json +7 -7
package/README.md
CHANGED
|
@@ -50,7 +50,7 @@ const config: CrewConfig = {
|
|
|
50
50
|
{
|
|
51
51
|
name: 'researcher',
|
|
52
52
|
role: researcherRole,
|
|
53
|
-
model: 'claude-sonnet-4-
|
|
53
|
+
model: 'claude-sonnet-4-6',
|
|
54
54
|
provider: 'anthropic',
|
|
55
55
|
},
|
|
56
56
|
],
|
|
@@ -70,6 +70,32 @@ const result = await crew.kickoff();
|
|
|
70
70
|
console.log(result.finalOutput);
|
|
71
71
|
```
|
|
72
72
|
|
|
73
|
+
> **Execution model.** By default, crew agents execute against real LLMs via
|
|
74
|
+
> `@lov3kaizen/agentsea-core` providers (a required peer dependency), so make
|
|
75
|
+
> sure the relevant API key is set (e.g. `ANTHROPIC_API_KEY`). Supported
|
|
76
|
+
> providers out of the box: `anthropic`, `openai`, `gemini`, `ollama`.
|
|
77
|
+
>
|
|
78
|
+
> - To plug in a different integration, pass an `execute` function on the crew
|
|
79
|
+
> config (or to `createCrewAgent`).
|
|
80
|
+
> - For offline scaffolding and tests, set `mock: true` on the crew config to
|
|
81
|
+
> get deterministic mock responses without any network calls.
|
|
82
|
+
>
|
|
83
|
+
> ```typescript
|
|
84
|
+
> // Offline / test mode
|
|
85
|
+
> const crew = createCrew({ ...config, mock: true });
|
|
86
|
+
>
|
|
87
|
+
> // Custom execution backend
|
|
88
|
+
> const crew2 = createCrew({
|
|
89
|
+
> ...config,
|
|
90
|
+
> execute: async (input, systemPrompt) => ({
|
|
91
|
+
> output: await myLlm(systemPrompt, input),
|
|
92
|
+
> tokensUsed: 0,
|
|
93
|
+
> latencyMs: 0,
|
|
94
|
+
> iterations: 1,
|
|
95
|
+
> }),
|
|
96
|
+
> });
|
|
97
|
+
> ```
|
|
98
|
+
|
|
73
99
|
### Using Templates
|
|
74
100
|
|
|
75
101
|
```typescript
|
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
import {
|
|
2
2
|
createCrew
|
|
3
|
-
} from "./chunk-
|
|
3
|
+
} from "./chunk-V6VK6BOL.mjs";
|
|
4
4
|
|
|
5
5
|
// src/templates/ResearchCrew.ts
|
|
6
6
|
var researcherRole = {
|
|
@@ -149,7 +149,7 @@ function createResearchCrewConfig(options = {}) {
|
|
|
149
149
|
{
|
|
150
150
|
name: "researcher",
|
|
151
151
|
role: researcherRole,
|
|
152
|
-
model: options.model ?? "claude-
|
|
152
|
+
model: options.model ?? "claude-opus-4-8",
|
|
153
153
|
provider: options.provider ?? "anthropic",
|
|
154
154
|
tools: ["web-search", "read-document", ...options.tools ?? []],
|
|
155
155
|
temperature: 0.3
|
|
@@ -157,7 +157,7 @@ function createResearchCrewConfig(options = {}) {
|
|
|
157
157
|
{
|
|
158
158
|
name: "analyst",
|
|
159
159
|
role: analystRole,
|
|
160
|
-
model: options.model ?? "claude-
|
|
160
|
+
model: options.model ?? "claude-opus-4-8",
|
|
161
161
|
provider: options.provider ?? "anthropic",
|
|
162
162
|
tools: ["calculator", "data-analysis", ...options.tools ?? []],
|
|
163
163
|
temperature: 0.2
|
|
@@ -167,7 +167,7 @@ function createResearchCrewConfig(options = {}) {
|
|
|
167
167
|
agents.push({
|
|
168
168
|
name: "writer",
|
|
169
169
|
role: writerRole,
|
|
170
|
-
model: options.model ?? "claude-
|
|
170
|
+
model: options.model ?? "claude-opus-4-8",
|
|
171
171
|
provider: options.provider ?? "anthropic",
|
|
172
172
|
tools: ["text-editor", ...options.tools ?? []],
|
|
173
173
|
temperature: 0.5
|
|
@@ -380,7 +380,7 @@ Your target audience is: ${options.audience}` : "";
|
|
|
380
380
|
...editorRole,
|
|
381
381
|
systemPrompt: editorRole.systemPrompt + contentTypePrompt + audiencePrompt
|
|
382
382
|
},
|
|
383
|
-
model: options.model ?? "claude-
|
|
383
|
+
model: options.model ?? "claude-opus-4-8",
|
|
384
384
|
provider: options.provider ?? "anthropic",
|
|
385
385
|
tools: ["text-editor", ...options.tools ?? []],
|
|
386
386
|
temperature: 0.3
|
|
@@ -391,7 +391,7 @@ Your target audience is: ${options.audience}` : "";
|
|
|
391
391
|
...writerRole2,
|
|
392
392
|
systemPrompt: writerRole2.systemPrompt + contentTypePrompt + audiencePrompt
|
|
393
393
|
},
|
|
394
|
-
model: options.model ?? "claude-
|
|
394
|
+
model: options.model ?? "claude-opus-4-8",
|
|
395
395
|
provider: options.provider ?? "anthropic",
|
|
396
396
|
tools: ["web-search", "text-editor", ...options.tools ?? []],
|
|
397
397
|
temperature: 0.7
|
|
@@ -399,7 +399,7 @@ Your target audience is: ${options.audience}` : "";
|
|
|
399
399
|
{
|
|
400
400
|
name: "proofreader",
|
|
401
401
|
role: proofreaderRole,
|
|
402
|
-
model: options.model ?? "claude-
|
|
402
|
+
model: options.model ?? "claude-opus-4-8",
|
|
403
403
|
provider: options.provider ?? "anthropic",
|
|
404
404
|
tools: ["grammar-checker", "spell-checker", ...options.tools ?? []],
|
|
405
405
|
temperature: 0.1
|
|
@@ -638,7 +638,7 @@ You specialize in: ${options.languages.join(", ")}` : "";
|
|
|
638
638
|
...seniorDeveloperRole,
|
|
639
639
|
systemPrompt: seniorDeveloperRole.systemPrompt + languagePrompt + strictnessPrompt
|
|
640
640
|
},
|
|
641
|
-
model: options.model ?? "claude-
|
|
641
|
+
model: options.model ?? "claude-opus-4-8",
|
|
642
642
|
provider: options.provider ?? "anthropic",
|
|
643
643
|
tools: ["code-analyzer", "linter", ...options.tools ?? []],
|
|
644
644
|
temperature: 0.2
|
|
@@ -651,7 +651,7 @@ You specialize in: ${options.languages.join(", ")}` : "";
|
|
|
651
651
|
...securityAnalystRole,
|
|
652
652
|
systemPrompt: securityAnalystRole.systemPrompt + languagePrompt
|
|
653
653
|
},
|
|
654
|
-
model: options.model ?? "claude-
|
|
654
|
+
model: options.model ?? "claude-opus-4-8",
|
|
655
655
|
provider: options.provider ?? "anthropic",
|
|
656
656
|
tools: [
|
|
657
657
|
"security-scanner",
|
|
@@ -668,7 +668,7 @@ You specialize in: ${options.languages.join(", ")}` : "";
|
|
|
668
668
|
...performanceEngineerRole,
|
|
669
669
|
systemPrompt: performanceEngineerRole.systemPrompt + languagePrompt
|
|
670
670
|
},
|
|
671
|
-
model: options.model ?? "claude-
|
|
671
|
+
model: options.model ?? "claude-opus-4-8",
|
|
672
672
|
provider: options.provider ?? "anthropic",
|
|
673
673
|
tools: ["profiler", "complexity-analyzer", ...options.tools ?? []],
|
|
674
674
|
temperature: 0.2
|
|
@@ -926,7 +926,7 @@ You support ${options.productName}.` : "";
|
|
|
926
926
|
...tier1AgentRole,
|
|
927
927
|
systemPrompt: tier1AgentRole.systemPrompt + contextAddition
|
|
928
928
|
},
|
|
929
|
-
model: options.model ?? "claude-
|
|
929
|
+
model: options.model ?? "claude-opus-4-8",
|
|
930
930
|
provider: options.provider ?? "anthropic",
|
|
931
931
|
tools: ["knowledge-base", "ticket-system", ...options.tools ?? []],
|
|
932
932
|
temperature: 0.4
|
|
@@ -939,7 +939,7 @@ You support ${options.productName}.` : "";
|
|
|
939
939
|
...specialistRole,
|
|
940
940
|
systemPrompt: specialistRole.systemPrompt + contextAddition
|
|
941
941
|
},
|
|
942
|
-
model: options.model ?? "claude-
|
|
942
|
+
model: options.model ?? "claude-opus-4-8",
|
|
943
943
|
provider: options.provider ?? "anthropic",
|
|
944
944
|
tools: [
|
|
945
945
|
"diagnostic-tools",
|
|
@@ -957,7 +957,7 @@ You support ${options.productName}.` : "";
|
|
|
957
957
|
...escalationManagerRole,
|
|
958
958
|
systemPrompt: escalationManagerRole.systemPrompt + contextAddition
|
|
959
959
|
},
|
|
960
|
-
model: options.model ?? "claude-
|
|
960
|
+
model: options.model ?? "claude-opus-4-8",
|
|
961
961
|
provider: options.provider ?? "anthropic",
|
|
962
962
|
tools: [
|
|
963
963
|
"crm",
|
|
@@ -1387,8 +1387,81 @@ var AgentCapabilities = class {
|
|
|
1387
1387
|
}
|
|
1388
1388
|
};
|
|
1389
1389
|
|
|
1390
|
+
// src/agents/CoreExecutor.ts
|
|
1391
|
+
async function loadProvider(providerName) {
|
|
1392
|
+
const ctorName = resolveProviderCtorName(providerName);
|
|
1393
|
+
let core;
|
|
1394
|
+
try {
|
|
1395
|
+
core = await import("@lov3kaizen/agentsea-core");
|
|
1396
|
+
} catch {
|
|
1397
|
+
throw new Error(
|
|
1398
|
+
'CrewAgent requires "@lov3kaizen/agentsea-core" to execute against a real LLM. Install it, or pass a custom `execute` function (or `mock: true`) to createCrewAgent / createCrew.'
|
|
1399
|
+
);
|
|
1400
|
+
}
|
|
1401
|
+
const Ctor = core[ctorName];
|
|
1402
|
+
return new Ctor();
|
|
1403
|
+
}
|
|
1404
|
+
function resolveProviderCtorName(providerName) {
|
|
1405
|
+
switch ((providerName ?? "").toLowerCase()) {
|
|
1406
|
+
case "anthropic":
|
|
1407
|
+
case "claude":
|
|
1408
|
+
return "AnthropicProvider";
|
|
1409
|
+
case "openai":
|
|
1410
|
+
case "gpt":
|
|
1411
|
+
return "OpenAIProvider";
|
|
1412
|
+
case "gemini":
|
|
1413
|
+
case "google":
|
|
1414
|
+
return "GeminiProvider";
|
|
1415
|
+
case "ollama":
|
|
1416
|
+
return "OllamaProvider";
|
|
1417
|
+
default:
|
|
1418
|
+
throw new Error(
|
|
1419
|
+
`CrewAgent: unsupported provider "${providerName}". Supported providers are: anthropic, openai, gemini, ollama. Pass a custom \`execute\` function to createCrewAgent for any other provider.`
|
|
1420
|
+
);
|
|
1421
|
+
}
|
|
1422
|
+
}
|
|
1423
|
+
function createCoreExecutor(config, options = {}) {
|
|
1424
|
+
let providerPromise;
|
|
1425
|
+
const getProvider = () => {
|
|
1426
|
+
if (!providerPromise) {
|
|
1427
|
+
providerPromise = options.provider ? Promise.resolve(options.provider) : loadProvider(config.provider);
|
|
1428
|
+
}
|
|
1429
|
+
return providerPromise;
|
|
1430
|
+
};
|
|
1431
|
+
return async (input, systemPrompt) => {
|
|
1432
|
+
const provider = await getProvider();
|
|
1433
|
+
const start = Date.now();
|
|
1434
|
+
const response = await provider.generateResponse(
|
|
1435
|
+
[{ role: "user", content: input }],
|
|
1436
|
+
{
|
|
1437
|
+
model: config.model,
|
|
1438
|
+
systemPrompt,
|
|
1439
|
+
temperature: config.temperature,
|
|
1440
|
+
maxTokens: config.maxTokens
|
|
1441
|
+
}
|
|
1442
|
+
);
|
|
1443
|
+
return {
|
|
1444
|
+
output: response.content,
|
|
1445
|
+
tokensUsed: response.usage.inputTokens + response.usage.outputTokens,
|
|
1446
|
+
latencyMs: Date.now() - start,
|
|
1447
|
+
iterations: 1
|
|
1448
|
+
};
|
|
1449
|
+
};
|
|
1450
|
+
}
|
|
1451
|
+
|
|
1390
1452
|
// src/agents/CrewAgent.ts
|
|
1391
1453
|
import { nanoid as nanoid3 } from "nanoid";
|
|
1454
|
+
function modelCostWeight(model) {
|
|
1455
|
+
const m = (model ?? "").toLowerCase();
|
|
1456
|
+
if (m.includes("opus") || m.includes("gpt-5") || m.includes("o3")) return 5;
|
|
1457
|
+
if (m.includes("sonnet") || m.includes("gpt-4.1") || m.includes("gpt-4") && !m.includes("mini") || m.includes("gemini-1.5-pro") || m.includes("gemini-2.5-pro")) {
|
|
1458
|
+
return 3;
|
|
1459
|
+
}
|
|
1460
|
+
if (m.includes("haiku") || m.includes("mini") || m.includes("flash") || m.includes("llama") || m.includes("mistral")) {
|
|
1461
|
+
return 1;
|
|
1462
|
+
}
|
|
1463
|
+
return 3;
|
|
1464
|
+
}
|
|
1392
1465
|
var CrewAgent = class _CrewAgent {
|
|
1393
1466
|
id;
|
|
1394
1467
|
name;
|
|
@@ -1427,10 +1500,11 @@ var CrewAgent = class _CrewAgent {
|
|
|
1427
1500
|
*/
|
|
1428
1501
|
async execute(input) {
|
|
1429
1502
|
if (!this.executeFunc) {
|
|
1503
|
+
const tokensUsed = 100 + Math.min(input.length, 400);
|
|
1430
1504
|
const mockResult = {
|
|
1431
1505
|
output: `[Mock response from ${this.name}]: ${input.slice(0, 100)}...`,
|
|
1432
|
-
tokensUsed
|
|
1433
|
-
latencyMs:
|
|
1506
|
+
tokensUsed,
|
|
1507
|
+
latencyMs: 0,
|
|
1434
1508
|
iterations: 1
|
|
1435
1509
|
};
|
|
1436
1510
|
this.totalTokensUsed += mockResult.tokensUsed;
|
|
@@ -1533,16 +1607,27 @@ ${JSON.stringify(task.context, null, 2)}`);
|
|
|
1533
1607
|
) ?? true
|
|
1534
1608
|
).map((c) => c.name);
|
|
1535
1609
|
const estimatedTime = this.estimateTaskTime(task);
|
|
1610
|
+
const estimatedCost = this.estimateTaskCost(estimatedTime);
|
|
1536
1611
|
const reasoning = this.generateBidReasoning(task, confidence, matchedCaps);
|
|
1537
1612
|
return Promise.resolve({
|
|
1538
1613
|
agentName: this.name,
|
|
1539
1614
|
taskId: task.id ?? "unknown",
|
|
1540
1615
|
confidence,
|
|
1541
1616
|
estimatedTime,
|
|
1617
|
+
estimatedCost,
|
|
1542
1618
|
reasoning,
|
|
1543
1619
|
capabilities: matchedCaps
|
|
1544
1620
|
});
|
|
1545
1621
|
}
|
|
1622
|
+
/**
|
|
1623
|
+
* Estimate a relative cost for handling a task. Combines the agent's model
|
|
1624
|
+
* price tier with the estimated effort so the auction `cheapest` criterion
|
|
1625
|
+
* can distinguish a cheap-but-slower model from an expensive-but-faster one.
|
|
1626
|
+
* The unit is arbitrary and only meaningful relative to other bids.
|
|
1627
|
+
*/
|
|
1628
|
+
estimateTaskCost(estimatedTime) {
|
|
1629
|
+
return modelCostWeight(this.model) * Math.max(estimatedTime, 1);
|
|
1630
|
+
}
|
|
1546
1631
|
/**
|
|
1547
1632
|
* Check if agent has all required capabilities
|
|
1548
1633
|
*/
|
|
@@ -1728,7 +1813,13 @@ Please provide helpful guidance based on your expertise.
|
|
|
1728
1813
|
}
|
|
1729
1814
|
};
|
|
1730
1815
|
function createCrewAgent(options) {
|
|
1731
|
-
|
|
1816
|
+
if (options.execute || options.mock) {
|
|
1817
|
+
return new CrewAgent(options);
|
|
1818
|
+
}
|
|
1819
|
+
return new CrewAgent({
|
|
1820
|
+
...options,
|
|
1821
|
+
execute: createCoreExecutor(options.config, { provider: options.provider })
|
|
1822
|
+
});
|
|
1732
1823
|
}
|
|
1733
1824
|
|
|
1734
1825
|
// src/agents/AgentRegistry.ts
|
|
@@ -2437,9 +2528,9 @@ var AuctionStrategy = class extends BaseDelegationStrategy {
|
|
|
2437
2528
|
}, bids[0]);
|
|
2438
2529
|
case "cheapest":
|
|
2439
2530
|
return bids.reduce((best, bid) => {
|
|
2440
|
-
const
|
|
2441
|
-
const
|
|
2442
|
-
return
|
|
2531
|
+
const bestCost = best.estimatedCost ?? best.estimatedTime ?? Infinity;
|
|
2532
|
+
const bidCost = bid.estimatedCost ?? bid.estimatedTime ?? Infinity;
|
|
2533
|
+
return bidCost < bestCost ? bid : best;
|
|
2443
2534
|
}, bids[0]);
|
|
2444
2535
|
case "confidence":
|
|
2445
2536
|
default:
|
|
@@ -2928,9 +3019,8 @@ var ConsensusStrategy = class extends BaseDelegationStrategy {
|
|
|
2928
3019
|
*/
|
|
2929
3020
|
async collectVotes(task, voters, candidates) {
|
|
2930
3021
|
const votes = [];
|
|
2931
|
-
const candidateNames = candidates.map((c) => c.name);
|
|
2932
3022
|
for (const voter of voters) {
|
|
2933
|
-
const vote = await this.getVote(voter, task,
|
|
3023
|
+
const vote = await this.getVote(voter, task, candidates);
|
|
2934
3024
|
if (vote) {
|
|
2935
3025
|
votes.push(vote);
|
|
2936
3026
|
}
|
|
@@ -2938,33 +3028,35 @@ var ConsensusStrategy = class extends BaseDelegationStrategy {
|
|
|
2938
3028
|
return votes;
|
|
2939
3029
|
}
|
|
2940
3030
|
/**
|
|
2941
|
-
* Get a vote from an agent
|
|
3031
|
+
* Get a vote from an agent.
|
|
3032
|
+
*
|
|
3033
|
+
* Each voter ranks the candidates by how well their capabilities fit the
|
|
3034
|
+
* task (the same `calculateTaskScore` signal the BestMatch/Auction strategies
|
|
3035
|
+
* use), plus a small self-preference bias so an agent leans toward itself when
|
|
3036
|
+
* candidates are otherwise comparable. This is fully deterministic — given the
|
|
3037
|
+
* same agents and task it always produces the same votes — and explainable,
|
|
3038
|
+
* which is what consensus needs. (A future enhancement could replace this with
|
|
3039
|
+
* an actual LLM deliberation per voter; the tally/agreement logic is unchanged.)
|
|
2942
3040
|
*/
|
|
2943
3041
|
getVote(voter, task, candidates) {
|
|
2944
|
-
|
|
2945
|
-
|
|
2946
|
-
|
|
2947
|
-
|
|
2948
|
-
|
|
2949
|
-
|
|
2950
|
-
scores.push({
|
|
2951
|
-
name: candidateName,
|
|
2952
|
-
score: Math.random() * randomFactor
|
|
2953
|
-
});
|
|
3042
|
+
if (candidates.length === 0) return Promise.resolve(null);
|
|
3043
|
+
const SELF_PREFERENCE_BONUS = 0.15;
|
|
3044
|
+
const scores = candidates.map((candidate) => {
|
|
3045
|
+
let score = candidate.calculateTaskScore(task);
|
|
3046
|
+
if (candidate.name === voter.name) {
|
|
3047
|
+
score += SELF_PREFERENCE_BONUS;
|
|
2954
3048
|
}
|
|
2955
|
-
|
|
2956
|
-
|
|
3049
|
+
return { name: candidate.name, score };
|
|
3050
|
+
});
|
|
3051
|
+
scores.sort((a, b) => b.score - a.score || a.name.localeCompare(b.name));
|
|
2957
3052
|
const selected = scores[0];
|
|
2958
3053
|
if (!selected) return Promise.resolve(null);
|
|
2959
|
-
|
|
2960
|
-
if (this.weightedVoting) {
|
|
2961
|
-
weight = voter.calculateTaskScore(task) || 0.5;
|
|
2962
|
-
}
|
|
3054
|
+
const weight = this.weightedVoting ? voter.calculateTaskScore(task) || 0.5 : 1;
|
|
2963
3055
|
return Promise.resolve({
|
|
2964
3056
|
voter: voter.name,
|
|
2965
3057
|
candidate: selected.name,
|
|
2966
3058
|
weight,
|
|
2967
|
-
reasoning: `
|
|
3059
|
+
reasoning: `Ranked "${selected.name}" highest by capability fit for the task (score: ${selected.score.toFixed(2)})`
|
|
2968
3060
|
});
|
|
2969
3061
|
}
|
|
2970
3062
|
/**
|
|
@@ -3837,13 +3929,24 @@ var ConflictResolver = class {
|
|
|
3837
3929
|
resolved: /* @__PURE__ */ new Date()
|
|
3838
3930
|
};
|
|
3839
3931
|
}
|
|
3932
|
+
/**
|
|
3933
|
+
* Normalize response content for equality comparison: trim, collapse runs of
|
|
3934
|
+
* whitespace, and lowercase. This groups textually-equivalent answers (ignoring
|
|
3935
|
+
* incidental formatting) over their FULL content rather than a fragile first-N
|
|
3936
|
+
* characters prefix. Note: this is exact-match-after-normalization, not semantic
|
|
3937
|
+
* similarity — agents that express the same idea with different wording will not
|
|
3938
|
+
* group. Semantic grouping would require embeddings (future enhancement).
|
|
3939
|
+
*/
|
|
3940
|
+
normalizeContent(content) {
|
|
3941
|
+
return content.trim().replace(/\s+/g, " ").toLowerCase();
|
|
3942
|
+
}
|
|
3840
3943
|
/**
|
|
3841
3944
|
* Resolve by voting
|
|
3842
3945
|
*/
|
|
3843
3946
|
resolveByVoting(conflict, _context) {
|
|
3844
3947
|
const votes = /* @__PURE__ */ new Map();
|
|
3845
3948
|
for (const response of conflict.responses) {
|
|
3846
|
-
const key = response.content
|
|
3949
|
+
const key = this.normalizeContent(response.content);
|
|
3847
3950
|
const current = votes.get(key) ?? 0;
|
|
3848
3951
|
votes.set(key, current + response.confidence);
|
|
3849
3952
|
}
|
|
@@ -3856,7 +3959,7 @@ var ConflictResolver = class {
|
|
|
3856
3959
|
}
|
|
3857
3960
|
}
|
|
3858
3961
|
const winner = conflict.responses.find(
|
|
3859
|
-
(r) => r.content
|
|
3962
|
+
(r) => this.normalizeContent(r.content) === winningKey
|
|
3860
3963
|
);
|
|
3861
3964
|
return Promise.resolve({
|
|
3862
3965
|
conflictId: conflict.id,
|
|
@@ -3872,7 +3975,31 @@ var ConflictResolver = class {
|
|
|
3872
3975
|
* Resolve by authority
|
|
3873
3976
|
*/
|
|
3874
3977
|
resolveByAuthority(conflict, _context) {
|
|
3875
|
-
|
|
3978
|
+
const ranked = conflict.responses.map((r) => ({
|
|
3979
|
+
response: r,
|
|
3980
|
+
authority: typeof r.metadata?.authority === "number" ? r.metadata.authority : void 0
|
|
3981
|
+
})).filter(
|
|
3982
|
+
(x) => x.authority !== void 0
|
|
3983
|
+
);
|
|
3984
|
+
if (ranked.length === 0) {
|
|
3985
|
+
return Promise.resolve({
|
|
3986
|
+
...this.resolveByConfidence(conflict),
|
|
3987
|
+
strategy: "authority",
|
|
3988
|
+
explanation: "No authority metadata provided; fell back to highest confidence"
|
|
3989
|
+
});
|
|
3990
|
+
}
|
|
3991
|
+
const winnerEntry = ranked.reduce(
|
|
3992
|
+
(best, cur) => cur.authority > best.authority ? cur : best
|
|
3993
|
+
);
|
|
3994
|
+
return Promise.resolve({
|
|
3995
|
+
conflictId: conflict.id,
|
|
3996
|
+
strategy: "authority",
|
|
3997
|
+
winner: winnerEntry.response,
|
|
3998
|
+
explanation: `Selected response from highest-authority agent "${winnerEntry.response.agentName}" (authority: ${winnerEntry.authority})`,
|
|
3999
|
+
successful: true,
|
|
4000
|
+
escalated: false,
|
|
4001
|
+
resolved: /* @__PURE__ */ new Date()
|
|
4002
|
+
});
|
|
3876
4003
|
}
|
|
3877
4004
|
/**
|
|
3878
4005
|
* Resolve by consensus
|
|
@@ -3880,7 +4007,7 @@ var ConflictResolver = class {
|
|
|
3880
4007
|
resolveByConsensus(conflict, _context) {
|
|
3881
4008
|
const contentGroups = /* @__PURE__ */ new Map();
|
|
3882
4009
|
for (const response of conflict.responses) {
|
|
3883
|
-
const key = response.content
|
|
4010
|
+
const key = this.normalizeContent(response.content);
|
|
3884
4011
|
const group = contentGroups.get(key) ?? [];
|
|
3885
4012
|
group.push(response);
|
|
3886
4013
|
contentGroups.set(key, group);
|
|
@@ -4044,7 +4171,12 @@ var Crew = class {
|
|
|
4044
4171
|
*/
|
|
4045
4172
|
initializeAgents() {
|
|
4046
4173
|
for (const agentConfig of this.config.agents) {
|
|
4047
|
-
const agent = createCrewAgent({
|
|
4174
|
+
const agent = createCrewAgent({
|
|
4175
|
+
config: agentConfig,
|
|
4176
|
+
execute: this.config.execute,
|
|
4177
|
+
mock: this.config.mock,
|
|
4178
|
+
provider: this.config.provider
|
|
4179
|
+
});
|
|
4048
4180
|
this.addAgent(agent);
|
|
4049
4181
|
}
|
|
4050
4182
|
}
|
|
@@ -4555,6 +4687,7 @@ export {
|
|
|
4555
4687
|
ExecutionContext,
|
|
4556
4688
|
createExecutionContext,
|
|
4557
4689
|
AgentCapabilities,
|
|
4690
|
+
createCoreExecutor,
|
|
4558
4691
|
CrewAgent,
|
|
4559
4692
|
createCrewAgent,
|
|
4560
4693
|
AgentRegistry,
|