better handling of aborting sessions

This commit is contained in:
Dax Raad 2025-07-07 20:58:47 -04:00
parent a272b58fe9
commit c7a59ee2b1
14 changed files with 374 additions and 266 deletions

View file

@ -552,167 +552,196 @@ export namespace Session {
], ],
}), }),
}) })
for await (const value of result.fullStream) { try {
l.info("part", { for await (const value of result.fullStream) {
type: value.type, l.info("part", {
}) type: value.type,
switch (value.type) { })
case "start": switch (value.type) {
break case "start":
break
case "tool-input-start": case "tool-input-start":
next.parts.push({ next.parts.push({
type: "tool", type: "tool",
tool: value.toolName, tool: value.toolName,
id: value.id, id: value.id,
state: { state: {
status: "pending", status: "pending",
},
})
Bus.publish(MessageV2.Event.PartUpdated, {
part: next.parts[next.parts.length - 1],
sessionID: next.sessionID,
messageID: next.id,
})
break
case "tool-input-delta":
break
case "tool-call": {
const match = next.parts.find((p): p is MessageV2.ToolPart => p.type === "tool" && p.id === value.toolCallId)
if (match) {
match.state = {
status: "running",
input: value.input,
time: {
start: Date.now(),
}, },
} })
Bus.publish(MessageV2.Event.PartUpdated, { Bus.publish(MessageV2.Event.PartUpdated, {
part: match, part: next.parts[next.parts.length - 1],
sessionID: next.sessionID, sessionID: next.sessionID,
messageID: next.id, messageID: next.id,
}) })
} break
break
}
case "tool-result": {
const match = next.parts.find((p): p is MessageV2.ToolPart => p.type === "tool" && p.id === value.toolCallId)
if (match && match.state.status === "running") {
match.state = {
status: "completed",
input: value.input,
output: value.output.output,
metadata: value.output.metadata,
title: value.output.title,
time: {
start: match.state.time.start,
end: Date.now(),
},
}
Bus.publish(MessageV2.Event.PartUpdated, {
part: match,
sessionID: next.sessionID,
messageID: next.id,
})
}
break
}
case "tool-error": { case "tool-input-delta":
const match = next.parts.find((p): p is MessageV2.ToolPart => p.type === "tool" && p.id === value.toolCallId) break
if (match && match.state.status === "running") {
match.state = {
status: "error",
input: value.input,
error: (value.error as any).toString(),
time: {
start: match.state.time.start,
end: Date.now(),
},
}
Bus.publish(MessageV2.Event.PartUpdated, {
part: match,
sessionID: next.sessionID,
messageID: next.id,
})
}
break
}
case "error": case "tool-call": {
const e = value.error const match = next.parts.find(
log.error("", { (p): p is MessageV2.ToolPart => p.type === "tool" && p.id === value.toolCallId,
error: e, )
}) if (match) {
switch (true) { match.state = {
case MessageV2.OutputLengthError.isInstance(e): status: "running",
next.error = e input: value.input,
break time: {
case LoadAPIKeyError.isInstance(e): start: Date.now(),
next.error = new Provider.AuthError(
{
providerID: input.providerID,
message: e.message,
}, },
{ cause: e }, }
).toObject() Bus.publish(MessageV2.Event.PartUpdated, {
break part: match,
case e instanceof Error: sessionID: next.sessionID,
next.error = new NamedError.Unknown({ message: e.toString() }, { cause: e }).toObject() messageID: next.id,
break })
default: }
next.error = new NamedError.Unknown({ message: JSON.stringify(e) }, { cause: e }) break
} }
Bus.publish(Event.Error, { case "tool-result": {
error: next.error, const match = next.parts.find(
}) (p): p is MessageV2.ToolPart => p.type === "tool" && p.id === value.toolCallId,
break )
if (match && match.state.status === "running") {
case "start-step": match.state = {
next.parts.push({ status: "completed",
type: "step-start", input: value.input,
}) output: value.output.output,
break metadata: value.output.metadata,
title: value.output.title,
case "finish-step": time: {
const usage = getUsage(model.info, value.usage, value.providerMetadata) start: match.state.time.start,
next.cost += usage.cost end: Date.now(),
next.tokens = usage.tokens },
break }
Bus.publish(MessageV2.Event.PartUpdated, {
case "text-start": part: match,
text = { sessionID: next.sessionID,
type: "text", messageID: next.id,
text: "", })
}
break
} }
break
case "text": case "tool-error": {
if (text.text === "") next.parts.push(text) const match = next.parts.find(
text.text += value.text (p): p is MessageV2.ToolPart => p.type === "tool" && p.id === value.toolCallId,
break )
if (match && match.state.status === "running") {
match.state = {
status: "error",
input: value.input,
error: (value.error as any).toString(),
time: {
start: match.state.time.start,
end: Date.now(),
},
}
Bus.publish(MessageV2.Event.PartUpdated, {
part: match,
sessionID: next.sessionID,
messageID: next.id,
})
}
break
}
case "text-end": case "error":
Bus.publish(MessageV2.Event.PartUpdated, { throw value.error
part: text,
sessionID: next.sessionID,
messageID: next.id,
})
break
case "finish": case "start-step":
next.time.completed = Date.now() next.parts.push({
break type: "step-start",
})
break
default: case "finish-step":
l.info("unhandled", { const usage = getUsage(model.info, value.usage, value.providerMetadata)
...value, next.cost += usage.cost
}) next.tokens = usage.tokens
continue break
case "text-start":
text = {
type: "text",
text: "",
}
break
case "text":
if (text.text === "") next.parts.push(text)
text.text += value.text
break
case "text-end":
Bus.publish(MessageV2.Event.PartUpdated, {
part: text,
sessionID: next.sessionID,
messageID: next.id,
})
break
case "finish":
next.time.completed = Date.now()
break
default:
l.info("unhandled", {
...value,
})
continue
}
await updateMessage(next)
}
} catch (e) {
log.error("", {
error: e,
})
switch (true) {
case e instanceof DOMException && e.name === "AbortError":
next.error = new MessageV2.AbortedError(
{ message: e.message },
{
cause: e,
},
).toObject()
break
case MessageV2.OutputLengthError.isInstance(e):
next.error = e
break
case LoadAPIKeyError.isInstance(e):
next.error = new Provider.AuthError(
{
providerID: input.providerID,
message: e.message,
},
{ cause: e },
).toObject()
break
case e instanceof Error:
next.error = new NamedError.Unknown({ message: e.toString() }, { cause: e }).toObject()
break
default:
next.error = new NamedError.Unknown({ message: JSON.stringify(e) }, { cause: e })
}
Bus.publish(Event.Error, {
error: next.error,
})
}
for (const part of next.parts) {
if (part.type === "tool" && part.state.status !== "completed") {
part.state = {
status: "error",
error: "Tool execution aborted",
time: {
start: Date.now(),
end: Date.now(),
},
input: {},
}
} }
await updateMessage(next)
} }
next.time.completed = Date.now() next.time.completed = Date.now()
await updateMessage(next) await updateMessage(next)

View file

@ -7,6 +7,7 @@ import { convertToModelMessages, type ModelMessage, type UIMessage } from "ai"
export namespace MessageV2 { export namespace MessageV2 {
export const OutputLengthError = NamedError.create("MessageOutputLengthError", z.object({})) export const OutputLengthError = NamedError.create("MessageOutputLengthError", z.object({}))
export const AbortedError = NamedError.create("MessageAbortedError", z.object({}))
export const ToolStatePending = z export const ToolStatePending = z
.object({ .object({
@ -148,7 +149,12 @@ export namespace MessageV2 {
completed: z.number().optional(), completed: z.number().optional(),
}), }),
error: z error: z
.discriminatedUnion("name", [Provider.AuthError.Schema, NamedError.Unknown.Schema, OutputLengthError.Schema]) .discriminatedUnion("name", [
Provider.AuthError.Schema,
NamedError.Unknown.Schema,
OutputLengthError.Schema,
AbortedError.Schema,
])
.optional(), .optional(),
system: z.string().array(), system: z.string().array(),
modelID: z.string(), modelID: z.string(),

View file

@ -320,6 +320,8 @@ func (m *messagesComponent) renderView(width int) {
error = "Message output length exceeded" error = "Message output length exceeded"
case opencode.ProviderAuthError: case opencode.ProviderAuthError:
error = err.Data.Message error = err.Data.Message
case opencode.MessageAbortedError:
error = "Request was aborted"
case opencode.UnknownError: case opencode.UnknownError:
error = err.Data.Message error = err.Data.Message
} }

View file

@ -2,15 +2,15 @@ name: CI
on: on:
push: push:
branches-ignore: branches-ignore:
- "generated" - 'generated'
- "codegen/**" - 'codegen/**'
- "integrated/**" - 'integrated/**'
- "stl-preview-head/**" - 'stl-preview-head/**'
- "stl-preview-base/**" - 'stl-preview-base/**'
pull_request: pull_request:
branches-ignore: branches-ignore:
- "stl-preview-head/**" - 'stl-preview-head/**'
- "stl-preview-base/**" - 'stl-preview-base/**'
jobs: jobs:
lint: lint:

View file

@ -1,3 +1,3 @@
{ {
".": "0.1.0-alpha.8" ".": "0.1.0-alpha.8"
} }

View file

@ -1,4 +1,4 @@
configured_endpoints: 20 configured_endpoints: 20
openapi_spec_url: https://storage.googleapis.com/stainless-sdk-openapi-specs/opencode%2Fopencode-15eeb028f79b9a065b4e54a6ea6a58631e9bd5004f97820f0c79d18e3f8bac84.yml openapi_spec_url: https://storage.googleapis.com/stainless-sdk-openapi-specs/opencode%2Fopencode-4955370de3d0a21bb41c4e51257210b3284deb5bc3dbace6e7572de0d1635c9e.yml
openapi_spec_hash: 38c8bacb6c8e4c46852a3e81e3fb9fda openapi_spec_hash: b7591d636977423cd7455aa02caa718f
config_hash: e03e9d1aad76081fa1163086e89f201b config_hash: de53ecf98e1038f2cc2fd273b582f082

View file

@ -6,7 +6,7 @@ Full Changelog: [v0.1.0-alpha.7...v0.1.0-alpha.8](https://github.com/sst/opencod
### Features ### Features
- **api:** update via SDK Studio ([651e937](https://github.com/sst/opencode-sdk-go/commit/651e937c334e1caba3b968e6cac865c219879519)) * **api:** update via SDK Studio ([651e937](https://github.com/sst/opencode-sdk-go/commit/651e937c334e1caba3b968e6cac865c219879519))
## 0.1.0-alpha.7 (2025-06-30) ## 0.1.0-alpha.7 (2025-06-30)
@ -14,12 +14,13 @@ Full Changelog: [v0.1.0-alpha.6...v0.1.0-alpha.7](https://github.com/sst/opencod
### Features ### Features
- **api:** update via SDK Studio ([13550a5](https://github.com/sst/opencode-sdk-go/commit/13550a5c65d77325e945ed99fe0799cd1107b775)) * **api:** update via SDK Studio ([13550a5](https://github.com/sst/opencode-sdk-go/commit/13550a5c65d77325e945ed99fe0799cd1107b775))
- **api:** update via SDK Studio ([7b73730](https://github.com/sst/opencode-sdk-go/commit/7b73730c7fa62ba966dda3541c3e97b49be8d2bf)) * **api:** update via SDK Studio ([7b73730](https://github.com/sst/opencode-sdk-go/commit/7b73730c7fa62ba966dda3541c3e97b49be8d2bf))
### Chores ### Chores
- **ci:** only run for pushes and fork pull requests ([bea59b8](https://github.com/sst/opencode-sdk-go/commit/bea59b886800ef555f89c47a9256d6392ed2e53d)) * **ci:** only run for pushes and fork pull requests ([bea59b8](https://github.com/sst/opencode-sdk-go/commit/bea59b886800ef555f89c47a9256d6392ed2e53d))
## 0.1.0-alpha.6 (2025-06-28) ## 0.1.0-alpha.6 (2025-06-28)
@ -27,7 +28,7 @@ Full Changelog: [v0.1.0-alpha.5...v0.1.0-alpha.6](https://github.com/sst/opencod
### Bug Fixes ### Bug Fixes
- don't try to deserialize as json when ResponseBodyInto is []byte ([5988d04](https://github.com/sst/opencode-sdk-go/commit/5988d04839cb78b6613057280b91b72a60fef33d)) * don't try to deserialize as json when ResponseBodyInto is []byte ([5988d04](https://github.com/sst/opencode-sdk-go/commit/5988d04839cb78b6613057280b91b72a60fef33d))
## 0.1.0-alpha.5 (2025-06-27) ## 0.1.0-alpha.5 (2025-06-27)
@ -35,7 +36,7 @@ Full Changelog: [v0.1.0-alpha.4...v0.1.0-alpha.5](https://github.com/sst/opencod
### Features ### Features
- **api:** update via SDK Studio ([9e39a59](https://github.com/sst/opencode-sdk-go/commit/9e39a59b3d5d1bd5e64633732521fb28362cc70e)) * **api:** update via SDK Studio ([9e39a59](https://github.com/sst/opencode-sdk-go/commit/9e39a59b3d5d1bd5e64633732521fb28362cc70e))
## 0.1.0-alpha.4 (2025-06-27) ## 0.1.0-alpha.4 (2025-06-27)
@ -43,7 +44,7 @@ Full Changelog: [v0.1.0-alpha.3...v0.1.0-alpha.4](https://github.com/sst/opencod
### Features ### Features
- **api:** update via SDK Studio ([9609d1b](https://github.com/sst/opencode-sdk-go/commit/9609d1b1db7806d00cb846c9914cb4935cdedf52)) * **api:** update via SDK Studio ([9609d1b](https://github.com/sst/opencode-sdk-go/commit/9609d1b1db7806d00cb846c9914cb4935cdedf52))
## 0.1.0-alpha.3 (2025-06-27) ## 0.1.0-alpha.3 (2025-06-27)
@ -51,7 +52,7 @@ Full Changelog: [v0.1.0-alpha.2...v0.1.0-alpha.3](https://github.com/sst/opencod
### Features ### Features
- **api:** update via SDK Studio ([57f3230](https://github.com/sst/opencode-sdk-go/commit/57f32309023cc1f0f20c20d02a3907e390a71f61)) * **api:** update via SDK Studio ([57f3230](https://github.com/sst/opencode-sdk-go/commit/57f32309023cc1f0f20c20d02a3907e390a71f61))
## 0.1.0-alpha.2 (2025-06-27) ## 0.1.0-alpha.2 (2025-06-27)
@ -59,7 +60,7 @@ Full Changelog: [v0.1.0-alpha.1...v0.1.0-alpha.2](https://github.com/sst/opencod
### Features ### Features
- **api:** update via SDK Studio ([a766f1c](https://github.com/sst/opencode-sdk-go/commit/a766f1c54f02bbc1380151b0e22d97cc2c5892e6)) * **api:** update via SDK Studio ([a766f1c](https://github.com/sst/opencode-sdk-go/commit/a766f1c54f02bbc1380151b0e22d97cc2c5892e6))
## 0.1.0-alpha.1 (2025-06-27) ## 0.1.0-alpha.1 (2025-06-27)
@ -67,6 +68,6 @@ Full Changelog: [v0.0.1-alpha.0...v0.1.0-alpha.1](https://github.com/sst/opencod
### Features ### Features
- **api:** update via SDK Studio ([27b7376](https://github.com/sst/opencode-sdk-go/commit/27b7376310466ee17a63f2104f546b53a2b8361a)) * **api:** update via SDK Studio ([27b7376](https://github.com/sst/opencode-sdk-go/commit/27b7376310466ee17a63f2104f546b53a2b8361a))
- **api:** update via SDK Studio ([0a73e04](https://github.com/sst/opencode-sdk-go/commit/0a73e04c23c90b2061611edaa8fd6282dc0ce397)) * **api:** update via SDK Studio ([0a73e04](https://github.com/sst/opencode-sdk-go/commit/0a73e04c23c90b2061611edaa8fd6282dc0ce397))
- **api:** update via SDK Studio ([9b7883a](https://github.com/sst/opencode-sdk-go/commit/9b7883a144eeac526d9d04538e0876a9d18bb844)) * **api:** update via SDK Studio ([9b7883a](https://github.com/sst/opencode-sdk-go/commit/9b7883a144eeac526d9d04538e0876a9d18bb844))

View file

@ -9,6 +9,15 @@ import (
type Error = apierror.Error type Error = apierror.Error
// This is an alias to an internal type.
type MessageAbortedError = shared.MessageAbortedError
// This is an alias to an internal type.
type MessageAbortedErrorName = shared.MessageAbortedErrorName
// This is an alias to an internal value.
const MessageAbortedErrorNameMessageAbortedError = shared.MessageAbortedErrorNameMessageAbortedError
// This is an alias to an internal type. // This is an alias to an internal type.
type ProviderAuthError = shared.ProviderAuthError type ProviderAuthError = shared.ProviderAuthError

View file

@ -1,5 +1,6 @@
# Shared Response Types # Shared Response Types
- <a href="https://pkg.go.dev/github.com/sst/opencode-sdk-go/shared">shared</a>.<a href="https://pkg.go.dev/github.com/sst/opencode-sdk-go/shared#MessageAbortedError">MessageAbortedError</a>
- <a href="https://pkg.go.dev/github.com/sst/opencode-sdk-go/shared">shared</a>.<a href="https://pkg.go.dev/github.com/sst/opencode-sdk-go/shared#ProviderAuthError">ProviderAuthError</a> - <a href="https://pkg.go.dev/github.com/sst/opencode-sdk-go/shared">shared</a>.<a href="https://pkg.go.dev/github.com/sst/opencode-sdk-go/shared#ProviderAuthError">ProviderAuthError</a>
- <a href="https://pkg.go.dev/github.com/sst/opencode-sdk-go/shared">shared</a>.<a href="https://pkg.go.dev/github.com/sst/opencode-sdk-go/shared#UnknownError">UnknownError</a> - <a href="https://pkg.go.dev/github.com/sst/opencode-sdk-go/shared">shared</a>.<a href="https://pkg.go.dev/github.com/sst/opencode-sdk-go/shared#UnknownError">UnknownError</a>

View file

@ -52,10 +52,10 @@ type EventListResponse struct {
// [EventListResponseEventPermissionUpdatedProperties], // [EventListResponseEventPermissionUpdatedProperties],
// [EventListResponseEventFileEditedProperties], // [EventListResponseEventFileEditedProperties],
// [EventListResponseEventInstallationUpdatedProperties], // [EventListResponseEventInstallationUpdatedProperties],
// [EventListResponseEventStorageWriteProperties],
// [EventListResponseEventMessageUpdatedProperties], // [EventListResponseEventMessageUpdatedProperties],
// [EventListResponseEventMessageRemovedProperties], // [EventListResponseEventMessageRemovedProperties],
// [EventListResponseEventMessagePartUpdatedProperties], // [EventListResponseEventMessagePartUpdatedProperties],
// [EventListResponseEventStorageWriteProperties],
// [EventListResponseEventSessionUpdatedProperties], // [EventListResponseEventSessionUpdatedProperties],
// [EventListResponseEventSessionDeletedProperties], // [EventListResponseEventSessionDeletedProperties],
// [EventListResponseEventSessionIdleProperties], // [EventListResponseEventSessionIdleProperties],
@ -96,11 +96,11 @@ func (r *EventListResponse) UnmarshalJSON(data []byte) (err error) {
// [EventListResponseEventLspClientDiagnostics], // [EventListResponseEventLspClientDiagnostics],
// [EventListResponseEventPermissionUpdated], [EventListResponseEventFileEdited], // [EventListResponseEventPermissionUpdated], [EventListResponseEventFileEdited],
// [EventListResponseEventInstallationUpdated], // [EventListResponseEventInstallationUpdated],
// [EventListResponseEventStorageWrite], [EventListResponseEventMessageUpdated], // [EventListResponseEventMessageUpdated], [EventListResponseEventMessageRemoved],
// [EventListResponseEventMessageRemoved],
// [EventListResponseEventMessagePartUpdated], // [EventListResponseEventMessagePartUpdated],
// [EventListResponseEventSessionUpdated], [EventListResponseEventSessionDeleted], // [EventListResponseEventStorageWrite], [EventListResponseEventSessionUpdated],
// [EventListResponseEventSessionIdle], [EventListResponseEventSessionError], // [EventListResponseEventSessionDeleted], [EventListResponseEventSessionIdle],
// [EventListResponseEventSessionError],
// [EventListResponseEventFileWatcherUpdated]. // [EventListResponseEventFileWatcherUpdated].
func (r EventListResponse) AsUnion() EventListResponseUnion { func (r EventListResponse) AsUnion() EventListResponseUnion {
return r.union return r.union
@ -109,11 +109,11 @@ func (r EventListResponse) AsUnion() EventListResponseUnion {
// Union satisfied by [EventListResponseEventLspClientDiagnostics], // Union satisfied by [EventListResponseEventLspClientDiagnostics],
// [EventListResponseEventPermissionUpdated], [EventListResponseEventFileEdited], // [EventListResponseEventPermissionUpdated], [EventListResponseEventFileEdited],
// [EventListResponseEventInstallationUpdated], // [EventListResponseEventInstallationUpdated],
// [EventListResponseEventStorageWrite], [EventListResponseEventMessageUpdated], // [EventListResponseEventMessageUpdated], [EventListResponseEventMessageRemoved],
// [EventListResponseEventMessageRemoved],
// [EventListResponseEventMessagePartUpdated], // [EventListResponseEventMessagePartUpdated],
// [EventListResponseEventSessionUpdated], [EventListResponseEventSessionDeleted], // [EventListResponseEventStorageWrite], [EventListResponseEventSessionUpdated],
// [EventListResponseEventSessionIdle], [EventListResponseEventSessionError] or // [EventListResponseEventSessionDeleted], [EventListResponseEventSessionIdle],
// [EventListResponseEventSessionError] or
// [EventListResponseEventFileWatcherUpdated]. // [EventListResponseEventFileWatcherUpdated].
type EventListResponseUnion interface { type EventListResponseUnion interface {
implementsEventListResponse() implementsEventListResponse()
@ -143,11 +143,6 @@ func init() {
Type: reflect.TypeOf(EventListResponseEventInstallationUpdated{}), Type: reflect.TypeOf(EventListResponseEventInstallationUpdated{}),
DiscriminatorValue: "installation.updated", DiscriminatorValue: "installation.updated",
}, },
apijson.UnionVariant{
TypeFilter: gjson.JSON,
Type: reflect.TypeOf(EventListResponseEventStorageWrite{}),
DiscriminatorValue: "storage.write",
},
apijson.UnionVariant{ apijson.UnionVariant{
TypeFilter: gjson.JSON, TypeFilter: gjson.JSON,
Type: reflect.TypeOf(EventListResponseEventMessageUpdated{}), Type: reflect.TypeOf(EventListResponseEventMessageUpdated{}),
@ -163,6 +158,11 @@ func init() {
Type: reflect.TypeOf(EventListResponseEventMessagePartUpdated{}), Type: reflect.TypeOf(EventListResponseEventMessagePartUpdated{}),
DiscriminatorValue: "message.part.updated", DiscriminatorValue: "message.part.updated",
}, },
apijson.UnionVariant{
TypeFilter: gjson.JSON,
Type: reflect.TypeOf(EventListResponseEventStorageWrite{}),
DiscriminatorValue: "storage.write",
},
apijson.UnionVariant{ apijson.UnionVariant{
TypeFilter: gjson.JSON, TypeFilter: gjson.JSON,
Type: reflect.TypeOf(EventListResponseEventSessionUpdated{}), Type: reflect.TypeOf(EventListResponseEventSessionUpdated{}),
@ -462,68 +462,6 @@ func (r EventListResponseEventInstallationUpdatedType) IsKnown() bool {
return false return false
} }
type EventListResponseEventStorageWrite struct {
Properties EventListResponseEventStorageWriteProperties `json:"properties,required"`
Type EventListResponseEventStorageWriteType `json:"type,required"`
JSON eventListResponseEventStorageWriteJSON `json:"-"`
}
// eventListResponseEventStorageWriteJSON contains the JSON metadata for the struct
// [EventListResponseEventStorageWrite]
type eventListResponseEventStorageWriteJSON struct {
Properties apijson.Field
Type apijson.Field
raw string
ExtraFields map[string]apijson.Field
}
func (r *EventListResponseEventStorageWrite) UnmarshalJSON(data []byte) (err error) {
return apijson.UnmarshalRoot(data, r)
}
func (r eventListResponseEventStorageWriteJSON) RawJSON() string {
return r.raw
}
func (r EventListResponseEventStorageWrite) implementsEventListResponse() {}
type EventListResponseEventStorageWriteProperties struct {
Key string `json:"key,required"`
Content interface{} `json:"content"`
JSON eventListResponseEventStorageWritePropertiesJSON `json:"-"`
}
// eventListResponseEventStorageWritePropertiesJSON contains the JSON metadata for
// the struct [EventListResponseEventStorageWriteProperties]
type eventListResponseEventStorageWritePropertiesJSON struct {
Key apijson.Field
Content apijson.Field
raw string
ExtraFields map[string]apijson.Field
}
func (r *EventListResponseEventStorageWriteProperties) UnmarshalJSON(data []byte) (err error) {
return apijson.UnmarshalRoot(data, r)
}
func (r eventListResponseEventStorageWritePropertiesJSON) RawJSON() string {
return r.raw
}
type EventListResponseEventStorageWriteType string
const (
EventListResponseEventStorageWriteTypeStorageWrite EventListResponseEventStorageWriteType = "storage.write"
)
func (r EventListResponseEventStorageWriteType) IsKnown() bool {
switch r {
case EventListResponseEventStorageWriteTypeStorageWrite:
return true
}
return false
}
type EventListResponseEventMessageUpdated struct { type EventListResponseEventMessageUpdated struct {
Properties EventListResponseEventMessageUpdatedProperties `json:"properties,required"` Properties EventListResponseEventMessageUpdatedProperties `json:"properties,required"`
Type EventListResponseEventMessageUpdatedType `json:"type,required"` Type EventListResponseEventMessageUpdatedType `json:"type,required"`
@ -710,6 +648,68 @@ func (r EventListResponseEventMessagePartUpdatedType) IsKnown() bool {
return false return false
} }
type EventListResponseEventStorageWrite struct {
Properties EventListResponseEventStorageWriteProperties `json:"properties,required"`
Type EventListResponseEventStorageWriteType `json:"type,required"`
JSON eventListResponseEventStorageWriteJSON `json:"-"`
}
// eventListResponseEventStorageWriteJSON contains the JSON metadata for the struct
// [EventListResponseEventStorageWrite]
type eventListResponseEventStorageWriteJSON struct {
Properties apijson.Field
Type apijson.Field
raw string
ExtraFields map[string]apijson.Field
}
func (r *EventListResponseEventStorageWrite) UnmarshalJSON(data []byte) (err error) {
return apijson.UnmarshalRoot(data, r)
}
func (r eventListResponseEventStorageWriteJSON) RawJSON() string {
return r.raw
}
func (r EventListResponseEventStorageWrite) implementsEventListResponse() {}
type EventListResponseEventStorageWriteProperties struct {
Key string `json:"key,required"`
Content interface{} `json:"content"`
JSON eventListResponseEventStorageWritePropertiesJSON `json:"-"`
}
// eventListResponseEventStorageWritePropertiesJSON contains the JSON metadata for
// the struct [EventListResponseEventStorageWriteProperties]
type eventListResponseEventStorageWritePropertiesJSON struct {
Key apijson.Field
Content apijson.Field
raw string
ExtraFields map[string]apijson.Field
}
func (r *EventListResponseEventStorageWriteProperties) UnmarshalJSON(data []byte) (err error) {
return apijson.UnmarshalRoot(data, r)
}
func (r eventListResponseEventStorageWritePropertiesJSON) RawJSON() string {
return r.raw
}
type EventListResponseEventStorageWriteType string
const (
EventListResponseEventStorageWriteTypeStorageWrite EventListResponseEventStorageWriteType = "storage.write"
)
func (r EventListResponseEventStorageWriteType) IsKnown() bool {
switch r {
case EventListResponseEventStorageWriteTypeStorageWrite:
return true
}
return false
}
type EventListResponseEventSessionUpdated struct { type EventListResponseEventSessionUpdated struct {
Properties EventListResponseEventSessionUpdatedProperties `json:"properties,required"` Properties EventListResponseEventSessionUpdatedProperties `json:"properties,required"`
Type EventListResponseEventSessionUpdatedType `json:"type,required"` Type EventListResponseEventSessionUpdatedType `json:"type,required"`
@ -972,13 +972,15 @@ func (r *EventListResponseEventSessionErrorPropertiesError) UnmarshalJSON(data [
// //
// Possible runtime types of the union are [shared.ProviderAuthError], // Possible runtime types of the union are [shared.ProviderAuthError],
// [shared.UnknownError], // [shared.UnknownError],
// [EventListResponseEventSessionErrorPropertiesErrorMessageOutputLengthError]. // [EventListResponseEventSessionErrorPropertiesErrorMessageOutputLengthError],
// [shared.MessageAbortedError].
func (r EventListResponseEventSessionErrorPropertiesError) AsUnion() EventListResponseEventSessionErrorPropertiesErrorUnion { func (r EventListResponseEventSessionErrorPropertiesError) AsUnion() EventListResponseEventSessionErrorPropertiesErrorUnion {
return r.union return r.union
} }
// Union satisfied by [shared.ProviderAuthError], [shared.UnknownError] or // Union satisfied by [shared.ProviderAuthError], [shared.UnknownError],
// [EventListResponseEventSessionErrorPropertiesErrorMessageOutputLengthError]. // [EventListResponseEventSessionErrorPropertiesErrorMessageOutputLengthError] or
// [shared.MessageAbortedError].
type EventListResponseEventSessionErrorPropertiesErrorUnion interface { type EventListResponseEventSessionErrorPropertiesErrorUnion interface {
ImplementsEventListResponseEventSessionErrorPropertiesError() ImplementsEventListResponseEventSessionErrorPropertiesError()
} }
@ -1002,6 +1004,11 @@ func init() {
Type: reflect.TypeOf(EventListResponseEventSessionErrorPropertiesErrorMessageOutputLengthError{}), Type: reflect.TypeOf(EventListResponseEventSessionErrorPropertiesErrorMessageOutputLengthError{}),
DiscriminatorValue: "MessageOutputLengthError", DiscriminatorValue: "MessageOutputLengthError",
}, },
apijson.UnionVariant{
TypeFilter: gjson.JSON,
Type: reflect.TypeOf(shared.MessageAbortedError{}),
DiscriminatorValue: "MessageAbortedError",
},
) )
} }
@ -1052,11 +1059,12 @@ const (
EventListResponseEventSessionErrorPropertiesErrorNameProviderAuthError EventListResponseEventSessionErrorPropertiesErrorName = "ProviderAuthError" EventListResponseEventSessionErrorPropertiesErrorNameProviderAuthError EventListResponseEventSessionErrorPropertiesErrorName = "ProviderAuthError"
EventListResponseEventSessionErrorPropertiesErrorNameUnknownError EventListResponseEventSessionErrorPropertiesErrorName = "UnknownError" EventListResponseEventSessionErrorPropertiesErrorNameUnknownError EventListResponseEventSessionErrorPropertiesErrorName = "UnknownError"
EventListResponseEventSessionErrorPropertiesErrorNameMessageOutputLengthError EventListResponseEventSessionErrorPropertiesErrorName = "MessageOutputLengthError" EventListResponseEventSessionErrorPropertiesErrorNameMessageOutputLengthError EventListResponseEventSessionErrorPropertiesErrorName = "MessageOutputLengthError"
EventListResponseEventSessionErrorPropertiesErrorNameMessageAbortedError EventListResponseEventSessionErrorPropertiesErrorName = "MessageAbortedError"
) )
func (r EventListResponseEventSessionErrorPropertiesErrorName) IsKnown() bool { func (r EventListResponseEventSessionErrorPropertiesErrorName) IsKnown() bool {
switch r { switch r {
case EventListResponseEventSessionErrorPropertiesErrorNameProviderAuthError, EventListResponseEventSessionErrorPropertiesErrorNameUnknownError, EventListResponseEventSessionErrorPropertiesErrorNameMessageOutputLengthError: case EventListResponseEventSessionErrorPropertiesErrorNameProviderAuthError, EventListResponseEventSessionErrorPropertiesErrorNameUnknownError, EventListResponseEventSessionErrorPropertiesErrorNameMessageOutputLengthError, EventListResponseEventSessionErrorPropertiesErrorNameMessageAbortedError:
return true return true
} }
return false return false
@ -1160,10 +1168,10 @@ const (
EventListResponseTypePermissionUpdated EventListResponseType = "permission.updated" EventListResponseTypePermissionUpdated EventListResponseType = "permission.updated"
EventListResponseTypeFileEdited EventListResponseType = "file.edited" EventListResponseTypeFileEdited EventListResponseType = "file.edited"
EventListResponseTypeInstallationUpdated EventListResponseType = "installation.updated" EventListResponseTypeInstallationUpdated EventListResponseType = "installation.updated"
EventListResponseTypeStorageWrite EventListResponseType = "storage.write"
EventListResponseTypeMessageUpdated EventListResponseType = "message.updated" EventListResponseTypeMessageUpdated EventListResponseType = "message.updated"
EventListResponseTypeMessageRemoved EventListResponseType = "message.removed" EventListResponseTypeMessageRemoved EventListResponseType = "message.removed"
EventListResponseTypeMessagePartUpdated EventListResponseType = "message.part.updated" EventListResponseTypeMessagePartUpdated EventListResponseType = "message.part.updated"
EventListResponseTypeStorageWrite EventListResponseType = "storage.write"
EventListResponseTypeSessionUpdated EventListResponseType = "session.updated" EventListResponseTypeSessionUpdated EventListResponseType = "session.updated"
EventListResponseTypeSessionDeleted EventListResponseType = "session.deleted" EventListResponseTypeSessionDeleted EventListResponseType = "session.deleted"
EventListResponseTypeSessionIdle EventListResponseType = "session.idle" EventListResponseTypeSessionIdle EventListResponseType = "session.idle"
@ -1173,7 +1181,7 @@ const (
func (r EventListResponseType) IsKnown() bool { func (r EventListResponseType) IsKnown() bool {
switch r { switch r {
case EventListResponseTypeLspClientDiagnostics, EventListResponseTypePermissionUpdated, EventListResponseTypeFileEdited, EventListResponseTypeInstallationUpdated, EventListResponseTypeStorageWrite, EventListResponseTypeMessageUpdated, EventListResponseTypeMessageRemoved, EventListResponseTypeMessagePartUpdated, EventListResponseTypeSessionUpdated, EventListResponseTypeSessionDeleted, EventListResponseTypeSessionIdle, EventListResponseTypeSessionError, EventListResponseTypeFileWatcherUpdated: case EventListResponseTypeLspClientDiagnostics, EventListResponseTypePermissionUpdated, EventListResponseTypeFileEdited, EventListResponseTypeInstallationUpdated, EventListResponseTypeMessageUpdated, EventListResponseTypeMessageRemoved, EventListResponseTypeMessagePartUpdated, EventListResponseTypeStorageWrite, EventListResponseTypeSessionUpdated, EventListResponseTypeSessionDeleted, EventListResponseTypeSessionIdle, EventListResponseTypeSessionError, EventListResponseTypeFileWatcherUpdated:
return true return true
} }
return false return false

View file

@ -60,5 +60,8 @@
} }
], ],
"release-type": "go", "release-type": "go",
"extra-files": ["internal/version.go", "README.md"] "extra-files": [
} "internal/version.go",
"README.md"
]
}

View file

@ -340,13 +340,14 @@ func (r *AssistantMessageError) UnmarshalJSON(data []byte) (err error) {
// the specific types for more type safety. // the specific types for more type safety.
// //
// Possible runtime types of the union are [shared.ProviderAuthError], // Possible runtime types of the union are [shared.ProviderAuthError],
// [shared.UnknownError], [AssistantMessageErrorMessageOutputLengthError]. // [shared.UnknownError], [AssistantMessageErrorMessageOutputLengthError],
// [shared.MessageAbortedError].
func (r AssistantMessageError) AsUnion() AssistantMessageErrorUnion { func (r AssistantMessageError) AsUnion() AssistantMessageErrorUnion {
return r.union return r.union
} }
// Union satisfied by [shared.ProviderAuthError], [shared.UnknownError] or // Union satisfied by [shared.ProviderAuthError], [shared.UnknownError],
// [AssistantMessageErrorMessageOutputLengthError]. // [AssistantMessageErrorMessageOutputLengthError] or [shared.MessageAbortedError].
type AssistantMessageErrorUnion interface { type AssistantMessageErrorUnion interface {
ImplementsAssistantMessageError() ImplementsAssistantMessageError()
} }
@ -370,6 +371,11 @@ func init() {
Type: reflect.TypeOf(AssistantMessageErrorMessageOutputLengthError{}), Type: reflect.TypeOf(AssistantMessageErrorMessageOutputLengthError{}),
DiscriminatorValue: "MessageOutputLengthError", DiscriminatorValue: "MessageOutputLengthError",
}, },
apijson.UnionVariant{
TypeFilter: gjson.JSON,
Type: reflect.TypeOf(shared.MessageAbortedError{}),
DiscriminatorValue: "MessageAbortedError",
},
) )
} }
@ -418,11 +424,12 @@ const (
AssistantMessageErrorNameProviderAuthError AssistantMessageErrorName = "ProviderAuthError" AssistantMessageErrorNameProviderAuthError AssistantMessageErrorName = "ProviderAuthError"
AssistantMessageErrorNameUnknownError AssistantMessageErrorName = "UnknownError" AssistantMessageErrorNameUnknownError AssistantMessageErrorName = "UnknownError"
AssistantMessageErrorNameMessageOutputLengthError AssistantMessageErrorName = "MessageOutputLengthError" AssistantMessageErrorNameMessageOutputLengthError AssistantMessageErrorName = "MessageOutputLengthError"
AssistantMessageErrorNameMessageAbortedError AssistantMessageErrorName = "MessageAbortedError"
) )
func (r AssistantMessageErrorName) IsKnown() bool { func (r AssistantMessageErrorName) IsKnown() bool {
switch r { switch r {
case AssistantMessageErrorNameProviderAuthError, AssistantMessageErrorNameUnknownError, AssistantMessageErrorNameMessageOutputLengthError: case AssistantMessageErrorNameProviderAuthError, AssistantMessageErrorNameUnknownError, AssistantMessageErrorNameMessageOutputLengthError, AssistantMessageErrorNameMessageAbortedError:
return true return true
} }
return false return false
@ -889,7 +896,7 @@ func (r ToolPart) implementsAssistantMessagePart() {}
type ToolPartState struct { type ToolPartState struct {
Status ToolPartStateStatus `json:"status,required"` Status ToolPartStateStatus `json:"status,required"`
Error string `json:"error"` Error string `json:"error"`
// This field can have the runtime type of [interface{}]. // This field can have the runtime type of [interface{}], [map[string]interface{}].
Input interface{} `json:"input"` Input interface{} `json:"input"`
// This field can have the runtime type of [map[string]interface{}]. // This field can have the runtime type of [map[string]interface{}].
Metadata interface{} `json:"metadata"` Metadata interface{} `json:"metadata"`
@ -1002,24 +1009,24 @@ func (r ToolPartType) IsKnown() bool {
} }
type ToolStateCompleted struct { type ToolStateCompleted struct {
Input map[string]interface{} `json:"input,required"`
Metadata map[string]interface{} `json:"metadata,required"` Metadata map[string]interface{} `json:"metadata,required"`
Output string `json:"output,required"` Output string `json:"output,required"`
Status ToolStateCompletedStatus `json:"status,required"` Status ToolStateCompletedStatus `json:"status,required"`
Time ToolStateCompletedTime `json:"time,required"` Time ToolStateCompletedTime `json:"time,required"`
Title string `json:"title,required"` Title string `json:"title,required"`
Input interface{} `json:"input"`
JSON toolStateCompletedJSON `json:"-"` JSON toolStateCompletedJSON `json:"-"`
} }
// toolStateCompletedJSON contains the JSON metadata for the struct // toolStateCompletedJSON contains the JSON metadata for the struct
// [ToolStateCompleted] // [ToolStateCompleted]
type toolStateCompletedJSON struct { type toolStateCompletedJSON struct {
Input apijson.Field
Metadata apijson.Field Metadata apijson.Field
Output apijson.Field Output apijson.Field
Status apijson.Field Status apijson.Field
Time apijson.Field Time apijson.Field
Title apijson.Field Title apijson.Field
Input apijson.Field
raw string raw string
ExtraFields map[string]apijson.Field ExtraFields map[string]apijson.Field
} }
@ -1072,19 +1079,19 @@ func (r toolStateCompletedTimeJSON) RawJSON() string {
} }
type ToolStateError struct { type ToolStateError struct {
Error string `json:"error,required"` Error string `json:"error,required"`
Status ToolStateErrorStatus `json:"status,required"` Input map[string]interface{} `json:"input,required"`
Time ToolStateErrorTime `json:"time,required"` Status ToolStateErrorStatus `json:"status,required"`
Input interface{} `json:"input"` Time ToolStateErrorTime `json:"time,required"`
JSON toolStateErrorJSON `json:"-"` JSON toolStateErrorJSON `json:"-"`
} }
// toolStateErrorJSON contains the JSON metadata for the struct [ToolStateError] // toolStateErrorJSON contains the JSON metadata for the struct [ToolStateError]
type toolStateErrorJSON struct { type toolStateErrorJSON struct {
Error apijson.Field Error apijson.Field
Input apijson.Field
Status apijson.Field Status apijson.Field
Time apijson.Field Time apijson.Field
Input apijson.Field
raw string raw string
ExtraFields map[string]apijson.Field ExtraFields map[string]apijson.Field
} }

View file

@ -6,6 +6,47 @@ import (
"github.com/sst/opencode-sdk-go/internal/apijson" "github.com/sst/opencode-sdk-go/internal/apijson"
) )
type MessageAbortedError struct {
Data interface{} `json:"data,required"`
Name MessageAbortedErrorName `json:"name,required"`
JSON messageAbortedErrorJSON `json:"-"`
}
// messageAbortedErrorJSON contains the JSON metadata for the struct
// [MessageAbortedError]
type messageAbortedErrorJSON struct {
Data apijson.Field
Name apijson.Field
raw string
ExtraFields map[string]apijson.Field
}
func (r *MessageAbortedError) UnmarshalJSON(data []byte) (err error) {
return apijson.UnmarshalRoot(data, r)
}
func (r messageAbortedErrorJSON) RawJSON() string {
return r.raw
}
func (r MessageAbortedError) ImplementsEventListResponseEventSessionErrorPropertiesError() {}
func (r MessageAbortedError) ImplementsAssistantMessageError() {}
type MessageAbortedErrorName string
const (
MessageAbortedErrorNameMessageAbortedError MessageAbortedErrorName = "MessageAbortedError"
)
func (r MessageAbortedErrorName) IsKnown() bool {
switch r {
case MessageAbortedErrorNameMessageAbortedError:
return true
}
return false
}
type ProviderAuthError struct { type ProviderAuthError struct {
Data ProviderAuthErrorData `json:"data,required"` Data ProviderAuthErrorData `json:"data,required"`
Name ProviderAuthErrorName `json:"name,required"` Name ProviderAuthErrorName `json:"name,required"`

View file

@ -34,6 +34,7 @@ resources:
models: models:
unknownError: UnknownError unknownError: UnknownError
providerAuthError: ProviderAuthError providerAuthError: ProviderAuthError
messageAbortedError: MessageAbortedError
event: event:
methods: methods: