From f444c22bd9eb0ad06e66b3ca167171ddec2836e4 Mon Sep 17 00:00:00 2001 From: "stainless-app[bot]" <142633134+stainless-app[bot]@users.noreply.github.com> Date: Wed, 26 Nov 2025 21:41:16 +0000 Subject: [PATCH 1/2] feat: Generate log streaming --- .stats.yml | 6 +++--- api.md | 2 +- client_test.go | 8 ++++---- instance.go | 45 +++++++++++++++++++++++---------------------- 4 files changed, 31 insertions(+), 30 deletions(-) diff --git a/.stats.yml b/.stats.yml index e97e7e3..2410f40 100644 --- a/.stats.yml +++ b/.stats.yml @@ -1,4 +1,4 @@ configured_endpoints: 18 -openapi_spec_url: https://storage.googleapis.com/stainless-sdk-openapi-specs/kernel%2Fhypeman-5058541cc0e298a6fc3e9cda1af0e32586d1f39c5666946e15f546c1aedc18ea.yml -openapi_spec_hash: 7f572ac0c7f9dc4f5fc7d9883a53d6c7 -config_hash: 35db4c99791f175865381f13a8ad6075 +openapi_spec_url: https://storage.googleapis.com/stainless-sdk-openapi-specs/kernel%2Fhypeman-ce51f144a3d2de556750203edbaa5bfeefe874660737c35a4fc37dfb30057dd5.yml +openapi_spec_hash: 27663b6503056317abcb578ac7b67c06 +config_hash: b4e65d240d7bca1ba6162ee2098c8ac2 diff --git a/api.md b/api.md index 81083cd..aa4b3c7 100644 --- a/api.md +++ b/api.md @@ -33,9 +33,9 @@ Methods: - client.Instances.Get(ctx context.Context, id string) (hypeman.Instance, error) - client.Instances.List(ctx context.Context) ([]hypeman.Instance, error) - client.Instances.Delete(ctx context.Context, id string) error +- client.Instances.Logs(ctx context.Context, id string, query hypeman.InstanceLogsParams) (string, error) - client.Instances.PutInStandby(ctx context.Context, id string) (hypeman.Instance, error) - client.Instances.RestoreFromStandby(ctx context.Context, id string) (hypeman.Instance, error) -- client.Instances.StreamLogs(ctx context.Context, id string, query hypeman.InstanceStreamLogsParams) (string, error) ## Volumes diff --git a/client_test.go b/client_test.go index ae40805..95a6577 100644 --- a/client_test.go +++ b/client_test.go @@ -271,10 +271,10 @@ func TestContextDeadlineStreaming(t *testing.T) { }, }), ) - stream := client.Instances.StreamLogsStreaming( + stream := client.Instances.LogsStreaming( deadlineCtx, "id", - hypeman.InstanceStreamLogsParams{}, + hypeman.InstanceLogsParams{}, ) for stream.Next() { _ = stream.Current() @@ -320,10 +320,10 @@ func TestContextDeadlineStreamingWithRequestTimeout(t *testing.T) { }, }), ) - stream := client.Instances.StreamLogsStreaming( + stream := client.Instances.LogsStreaming( context.Background(), "id", - hypeman.InstanceStreamLogsParams{}, + hypeman.InstanceLogsParams{}, option.WithRequestTimeout((100 * time.Millisecond)), ) for stream.Next() { diff --git a/instance.go b/instance.go index 78f1bbd..69a15d7 100644 --- a/instance.go +++ b/instance.go @@ -82,6 +82,25 @@ func (r *InstanceService) Delete(ctx context.Context, id string, opts ...option. return } +// Streams instance console logs as Server-Sent Events. Returns the last N lines +// (controlled by `tail` parameter), then optionally continues streaming new lines +// if `follow=true`. +func (r *InstanceService) LogsStreaming(ctx context.Context, id string, query InstanceLogsParams, opts ...option.RequestOption) (stream *ssestream.Stream[string]) { + var ( + raw *http.Response + err error + ) + opts = slices.Concat(r.Options, opts) + opts = append([]option.RequestOption{option.WithHeader("Accept", "text/event-stream")}, opts...) + if id == "" { + err = errors.New("missing required id parameter") + return + } + path := fmt.Sprintf("instances/%s/logs", id) + err = requestconfig.ExecuteNewRequest(ctx, http.MethodGet, path, query, &raw, opts...) + return ssestream.NewStream[string](ssestream.NewDecoder(raw), err) +} + // Put instance in standby (pause, snapshot, delete VMM) func (r *InstanceService) PutInStandby(ctx context.Context, id string, opts ...option.RequestOption) (res *Instance, err error) { opts = slices.Concat(r.Options, opts) @@ -106,23 +125,6 @@ func (r *InstanceService) RestoreFromStandby(ctx context.Context, id string, opt return } -// Stream instance logs (SSE) -func (r *InstanceService) StreamLogsStreaming(ctx context.Context, id string, query InstanceStreamLogsParams, opts ...option.RequestOption) (stream *ssestream.Stream[string]) { - var ( - raw *http.Response - err error - ) - opts = slices.Concat(r.Options, opts) - opts = append([]option.RequestOption{option.WithHeader("Accept", "text/event-stream")}, opts...) - if id == "" { - err = errors.New("missing required id parameter") - return - } - path := fmt.Sprintf("instances/%s/logs", id) - err = requestconfig.ExecuteNewRequest(ctx, http.MethodGet, path, query, &raw, opts...) - return ssestream.NewStream[string](ssestream.NewDecoder(raw), err) -} - type Instance struct { // Auto-generated unique identifier (CUID2 format) ID string `json:"id,required"` @@ -278,17 +280,16 @@ func (r *InstanceNewParamsNetwork) UnmarshalJSON(data []byte) error { return apijson.UnmarshalRoot(data, r) } -type InstanceStreamLogsParams struct { - // Follow logs (stream with SSE) +type InstanceLogsParams struct { + // Continue streaming new lines after initial output Follow param.Opt[bool] `query:"follow,omitzero" json:"-"` // Number of lines to return from end Tail param.Opt[int64] `query:"tail,omitzero" json:"-"` paramObj } -// URLQuery serializes [InstanceStreamLogsParams]'s query parameters as -// `url.Values`. -func (r InstanceStreamLogsParams) URLQuery() (v url.Values, err error) { +// URLQuery serializes [InstanceLogsParams]'s query parameters as `url.Values`. +func (r InstanceLogsParams) URLQuery() (v url.Values, err error) { return apiquery.MarshalWithSettings(r, apiquery.QuerySettings{ ArrayFormat: apiquery.ArrayQueryFormatComma, NestedFormat: apiquery.NestedQueryFormatBrackets, From be0af39e8cef813c79e4a5d37f76cd8b5e72df27 Mon Sep 17 00:00:00 2001 From: "stainless-app[bot]" <142633134+stainless-app[bot]@users.noreply.github.com> Date: Wed, 26 Nov 2025 21:41:31 +0000 Subject: [PATCH 2/2] release: 0.4.0 --- .release-please-manifest.json | 2 +- CHANGELOG.md | 8 ++++++++ README.md | 2 +- internal/version.go | 2 +- 4 files changed, 11 insertions(+), 3 deletions(-) diff --git a/.release-please-manifest.json b/.release-please-manifest.json index 6b7b74c..da59f99 100644 --- a/.release-please-manifest.json +++ b/.release-please-manifest.json @@ -1,3 +1,3 @@ { - ".": "0.3.0" + ".": "0.4.0" } \ No newline at end of file diff --git a/CHANGELOG.md b/CHANGELOG.md index 2f810d5..b85f65e 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -1,5 +1,13 @@ # Changelog +## 0.4.0 (2025-11-26) + +Full Changelog: [v0.3.0...v0.4.0](https://github.com/onkernel/hypeman-go/compare/v0.3.0...v0.4.0) + +### Features + +* Generate log streaming ([f444c22](https://github.com/onkernel/hypeman-go/commit/f444c22bd9eb0ad06e66b3ca167171ddec2836e4)) + ## 0.3.0 (2025-11-26) Full Changelog: [v0.2.0...v0.3.0](https://github.com/onkernel/hypeman-go/compare/v0.2.0...v0.3.0) diff --git a/README.md b/README.md index 0e79a1e..3b84f9c 100644 --- a/README.md +++ b/README.md @@ -28,7 +28,7 @@ Or to pin the version: ```sh -go get -u 'github.com/onkernel/hypeman-go@v0.3.0' +go get -u 'github.com/onkernel/hypeman-go@v0.4.0' ``` diff --git a/internal/version.go b/internal/version.go index 7cb1898..5c62cac 100644 --- a/internal/version.go +++ b/internal/version.go @@ -2,4 +2,4 @@ package internal -const PackageVersion = "0.3.0" // x-release-please-version +const PackageVersion = "0.4.0" // x-release-please-version