@hallofame/cloudflare-agent 0.1.9 → 0.1.10

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/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@hallofame/cloudflare-agent",
3
- "version": "0.1.9",
3
+ "version": "0.1.10",
4
4
  "description": "Hall Of Fame autonomous agent for Cloudflare Agents and Workers AI",
5
5
  "type": "module",
6
6
  "license": "MIT",
@@ -4,6 +4,7 @@ import { activityPrompt, systemPrompt } from './prompt'
4
4
  import { Agent } from 'agents'
5
5
  import { HallOfFameClient } from './HallOfFameClient'
6
6
  import { SocialMemory } from './SocialMemory'
7
+ import { WorkersAIResponse } from './WorkersAIResponse'
7
8
 
8
9
  const TOKEN_KEY = 'halloffame-token'
9
10
  const DEFAULT_MODEL = '@cf/google/gemma-4-26b-a4b-it'
@@ -12,11 +13,6 @@ const MAX_TOOL_STEPS = 12
12
13
 
13
14
  type ModelMessage = Record<string, unknown>
14
15
 
15
- interface ModelResponse {
16
- response?: string
17
- tool_calls?: unknown[]
18
- }
19
-
20
16
  interface ActivityContext {
21
17
  checks: Record<string, 'ok' | 'unavailable'>
22
18
  data: Record<string, unknown>
@@ -179,14 +175,18 @@ export class HallOfFameAgent extends Agent<Env, AgentState> {
179
175
  ...(visionImage ? { image: visionImage } : {}),
180
176
  }
181
177
  visionImage = undefined
182
- const result = (await this.env.AI.run(
178
+ const rawResult = await this.env.AI.run(
183
179
  (this.env.HOF_MODEL ?? DEFAULT_MODEL) as keyof AiModels,
184
180
  input as never,
185
- )) as ModelResponse
186
- const calls = this.parseToolCalls(result.tool_calls)
181
+ )
182
+ const result = new WorkersAIResponse(rawResult).normalize()
183
+ const calls = this.parseToolCalls(result.toolCalls)
187
184
 
188
185
  if (calls.length === 0) {
189
- const summary = result.response?.trim() || 'Activity cycle completed without a summary.'
186
+ if (!result.text) {
187
+ throw new Error('Workers AI returned neither text nor tool calls.')
188
+ }
189
+ const summary = result.text
190
190
  const updatedMemory = memory.addActivity(summary)
191
191
  this.setState({
192
192
  ...this.state,
@@ -203,8 +203,8 @@ export class HallOfFameAgent extends Agent<Env, AgentState> {
203
203
 
204
204
  messages.push({
205
205
  role: 'assistant',
206
- content: result.response ?? '',
207
- tool_calls: result.tool_calls,
206
+ content: result.text,
207
+ tool_calls: result.toolCalls,
208
208
  })
209
209
 
210
210
  for (const call of calls) {
@@ -0,0 +1,44 @@
1
+ export interface NormalizedModelResponse {
2
+ text: string
3
+ toolCalls: unknown[]
4
+ }
5
+
6
+ export class WorkersAIResponse {
7
+ constructor(private readonly value: unknown) {}
8
+
9
+ normalize(): NormalizedModelResponse {
10
+ const result = this.record(this.value)
11
+ const choice = Array.isArray(result.choices) ? this.record(result.choices[0]) : {}
12
+ const message = this.record(choice.message)
13
+ const content = result.response ?? message.content
14
+
15
+ return {
16
+ text: this.text(content),
17
+ toolCalls: this.toolCalls(result.tool_calls ?? message.tool_calls),
18
+ }
19
+ }
20
+
21
+ private text(value: unknown): string {
22
+ if (typeof value === 'string') return value.trim()
23
+ if (!Array.isArray(value)) return ''
24
+
25
+ return value
26
+ .map((part) => {
27
+ const item = this.record(part)
28
+
29
+ return typeof item.text === 'string' ? item.text : ''
30
+ })
31
+ .join('')
32
+ .trim()
33
+ }
34
+
35
+ private toolCalls(value: unknown): unknown[] {
36
+ return Array.isArray(value) ? value : []
37
+ }
38
+
39
+ private record(value: unknown): Record<string, unknown> {
40
+ return typeof value === 'object' && value !== null && !Array.isArray(value)
41
+ ? (value as Record<string, unknown>)
42
+ : {}
43
+ }
44
+ }