Skip to content

Commit 0a98d40

Browse files
authored
Merge pull request #25 from vast-data/async_result_processing
refactor AsyncResult logic
2 parents 0fe2d12 + 386ff9c commit 0a98d40

File tree

101 files changed

+829
-1369
lines changed

Some content is hidden

Large Commits have some content hidden by default. Use the searchbox below for content that may be hidden.

101 files changed

+829
-1369
lines changed

CHANGELOG.md

Lines changed: 12 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -2,6 +2,18 @@
22

33
All notable changes to this project will be documented in this file.
44

5+
## 0.107.0
6+
7+
BREAKING CHANGES:
8+
9+
* **EmptyRecord Removed**: The `EmptyRecord` type has been completely removed from the library. All methods that previously returned `EmptyRecord` now return `Record` instead.
10+
11+
ENHANCEMENTS:
12+
13+
* **Async Task Processing Utilities**: Added new helper functions in the `untyped` package for simplified async task handling
14+
* `MaybeWaitAsyncResult(record, rest, timeout)`: Automatically detects and waits for async tasks with a timeout
15+
* `MaybeWaitAsyncResultWithContext(ctx, record, rest, timeout)`: Context-aware version with timeout support
16+
517
## 0.106.0
618

719
ENHANCEMENTS:

client.go

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -25,7 +25,7 @@ type (
2525
// RecordSet is a collection of Record objects.
2626
RecordSet = core.RecordSet
2727

28-
// Renderable is the interface for Record, RecordSet, and EmptyRecord.
28+
// Renderable is the interface for Record and RecordSet.
2929
Renderable = core.Renderable
3030

3131
// DisplayableRecord is an interface for records that can be displayed.

codegen/README.md

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -134,7 +134,7 @@ delete:
134134
135135
**Generated (Simplified):**
136136
```go
137-
func (u *UserKey) UserKeyDeleteAccessKeys(id any, accessKey string) (core.EmptyRecord, error) {
137+
func (u *UserKey) UserKeyDeleteAccessKeys(id any, accessKey string) error {
138138
// Body automatically constructed: {"access_key": accessKey}
139139
}
140140
```

codegen/cmd/generate-untyped-resources/main.go

Lines changed: 6 additions & 14 deletions
Original file line numberDiff line numberDiff line change
@@ -33,7 +33,7 @@ type MethodInfo struct {
3333
HasParams bool
3434
HasBody bool
3535
ReceiverName string
36-
ReturnsNoContent bool // True if returns 204 No Content (use core.EmptyRecord)
36+
ReturnsNoContent bool // True if returns 204 No Content (use core.Record)
3737
ReturnsArray bool // True if returns an array (use core.RecordSet)
3838
// For simplified bodies (up to 3 fields become inline parameters)
3939
SimplifiedBody bool // True if body has 1-3 fields
@@ -214,7 +214,7 @@ func generateMethodInfo(resourceName string, extraMethod apibuilder.ExtraMethod,
214214
returns204, err := api.Returns204NoContent(extraMethod.Method, extraMethod.Path)
215215
if err == nil && returns204 {
216216
methodInfo.ReturnsNoContent = true
217-
fmt.Printf(" ℹ️ Method returns 204 No Content, using core.EmptyRecord\n")
217+
fmt.Printf(" ℹ️ Method returns 204 No Content, using core.Record\n")
218218
}
219219

220220
// Check if this is a bare array response BEFORE schema unwrapping
@@ -480,18 +480,10 @@ func ({{$.ReceiverName}} *{{$.Name}}) {{.Name}}WithContext_{{.HTTPMethod}}(ctx c
480480
if err != nil {
481481
return nil, err
482482
}
483-
// Create async task from result
484-
task := asyncResultFromRecord(ctx, result, {{$.ReceiverName}}.Rest)
485-
// If waitTimeout is 0, return task immediately without waiting (async background operation)
486-
if waitTimeout == 0 {
487-
return task, nil
488-
}
489-
// Wait for task completion with the specified timeout
490-
if _, err := task.Wait(waitTimeout); err != nil {
491-
return task, err
492-
}
493-
return task, nil
494-
{{else}}{{if .ReturnsNoContent}}_, err := core.Request[core.EmptyRecord](ctx, {{$.ReceiverName}}, http.{{.GoHTTPMethod}}, resourcePath, {{if .HasParams}}params{{else}}nil{{end}}, {{if or .HasBody .SimplifiedBody}}body{{else}}nil{{end}})
483+
484+
asyncResult, _, err := MaybeWaitAsyncResultWithContext(ctx, result, {{$.ReceiverName}}.Rest, waitTimeout)
485+
return asyncResult, err
486+
{{else}}{{if .ReturnsNoContent}}_, err := core.Request[core.Record](ctx, {{$.ReceiverName}}, http.{{.GoHTTPMethod}}, resourcePath, {{if .HasParams}}params{{else}}nil{{end}}, {{if or .HasBody .SimplifiedBody}}body{{else}}nil{{end}})
495487
return err
496488
{{else}}{{if .ReturnsArray}}result, err := core.Request[core.RecordSet](ctx, {{$.ReceiverName}}, http.{{.GoHTTPMethod}}, resourcePath, {{if .HasParams}}params{{else}}nil{{end}}, {{if or .HasBody .SimplifiedBody}}body{{else}}nil{{end}})
497489
if err != nil {

codegen/misc/verify_autogen.sh

Lines changed: 6 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -6,7 +6,7 @@
66
# 2. core.Params in function signatures (untyped parameters)
77
# 3. core.Record in function return types (untyped records)
88
# 4. core.RecordSet in function return types (untyped record sets)
9-
# 5. core.EmptyRecord in function return types (untyped empty records)
9+
# 5. EmptyRecord references (removed type that should not appear)
1010
#
1111
# Usage: ./verify_autogen.sh [path_to_typed_resources]
1212
#
@@ -90,14 +90,15 @@ else
9090
fi
9191
echo ""
9292
93-
# Check 5: core.EmptyRecord in function return types
94-
echo "Checking for core.EmptyRecord in function return types..."
95-
core_emptyrecord=$(grep -n "func.*core\.EmptyRecord" "$TYPED_DIR"/*_autogen.go 2>/dev/null | grep -v "// " | grep -v "//" || true)
93+
# Check 5: Verify no references to removed EmptyRecord type remain
94+
echo "Checking for any references to removed EmptyRecord type..."
95+
core_emptyrecord=$(grep -n "EmptyRecord" "$TYPED_DIR"/*_autogen.go 2>/dev/null | grep -v "// " | grep -v "//" || true)
9696
if [ -n "$core_emptyrecord" ]; then
97+
echo "Found references to removed EmptyRecord type:"
9798
echo "$core_emptyrecord" | while read line; do echo " $line"; done
9899
errors=$((errors + 1))
99100
else
100-
echo "No core.EmptyRecord found in function return types"
101+
echo "No references to removed EmptyRecord type found"
101102
fi
102103
echo ""
103104

codegen/templates/extramethods-only.tpl

Lines changed: 5 additions & 13 deletions
Original file line numberDiff line numberDiff line change
@@ -98,19 +98,11 @@ func (r *{{$.Name}}) {{.Name}}WithContext_{{.HTTPMethod}}(ctx context.Context{{i
9898
if err != nil {
9999
return nil, err
100100
}
101-
// Create async task from result
102-
task := untyped.NewAsyncResult(ctx, result.RecordID(), r.Untyped)
103-
// If waitTimeout is 0, return task immediately without waiting (async background operation)
104-
if waitTimeout == 0 {
105-
return task, nil
106-
}
107-
// Wait for task completion with the specified timeout
108-
if _, err := task.Wait(waitTimeout); err != nil {
109-
return task, err
110-
}
111-
return task, nil
112-
{{else}}{{if .ReturnsNoContent}}{{if and (or (and .HasParams .BodyFields) (and .HasBody .BodyFields)) (not .SimplifiedBody)}}_, err = core.Request[core.EmptyRecord](ctx, r.Untyped.GetResourceMap()[r.GetResourceType()], http.{{.GoHTTPMethod}}, resourcePath, reqParams, reqBody)
113-
return err{{else}}_, err := core.Request[core.EmptyRecord](ctx, r.Untyped.GetResourceMap()[r.GetResourceType()], http.{{.GoHTTPMethod}}, resourcePath, reqParams, reqBody)
101+
102+
asyncResult, _, err := untyped.MaybeWaitAsyncResultWithContext(ctx, result, r.Untyped, waitTimeout)
103+
return asyncResult, err
104+
{{else}}{{if .ReturnsNoContent}}{{if and (or (and .HasParams .BodyFields) (and .HasBody .BodyFields)) (not .SimplifiedBody)}}_, err = core.Request[core.Record](ctx, r.Untyped.GetResourceMap()[r.GetResourceType()], http.{{.GoHTTPMethod}}, resourcePath, reqParams, reqBody)
105+
return err{{else}}_, err := core.Request[core.Record](ctx, r.Untyped.GetResourceMap()[r.GetResourceType()], http.{{.GoHTTPMethod}}, resourcePath, reqParams, reqBody)
114106
return err{{end}}
115107
{{else}}{{if .ReturnsTextPlain}}record, err := core.Request[core.Record](ctx, r.Untyped.GetResourceMap()[r.GetResourceType()], http.{{.GoHTTPMethod}}, resourcePath, reqParams, reqBody)
116108
if err != nil {

codegen/templates/resource.tpl

Lines changed: 13 additions & 57 deletions
Original file line numberDiff line numberDiff line change
@@ -276,17 +276,8 @@ func (r *{{.Name}}) UpdateWithContext(ctx context.Context, id any{{range .Update
276276
return nil, err
277277
}
278278

279-
// Create async task from result
280-
task := untyped.NewAsyncResult(ctx, record.RecordID(), r.Untyped)
281-
282-
// Wait for task completion if timeout > 0
283-
if waitTimeout > 0 {
284-
if _, err := task.Wait(waitTimeout); err != nil {
285-
return task, err
286-
}
287-
}
288-
289-
return task, nil
279+
asyncResult, _, err := untyped.MaybeWaitAsyncResultWithContext(ctx, record, r.Untyped, waitTimeout)
280+
return asyncResult, err
290281
}
291282
{{else}}
292283
// Update updates an existing {{.LowerName}} and returns an async task{{if .UpdateSummary}}
@@ -314,17 +305,8 @@ func (r *{{.Name}}) UpdateWithContext(ctx context.Context, id any, req *{{.Name}
314305
return nil, err
315306
}
316307

317-
// Create async task from result
318-
task := untyped.NewAsyncResult(ctx, record.RecordID(), r.Untyped)
319-
320-
// Wait for task completion if timeout > 0
321-
if waitTimeout > 0 {
322-
if _, err := task.Wait(waitTimeout); err != nil {
323-
return task, err
324-
}
325-
}
326-
327-
return task, nil
308+
asyncResult, _, err := untyped.MaybeWaitAsyncResultWithContext(ctx, record, r.Untyped, waitTimeout)
309+
return asyncResult, err
328310
}
329311
{{end}}
330312
{{else}}
@@ -440,17 +422,8 @@ func (r *{{.Name}}) DeleteWithContext(ctx context.Context, req *{{.Name}}SearchP
440422
return nil, err
441423
}
442424

443-
// Create async task from result
444-
task := untyped.NewAsyncResult(ctx, record.RecordID(), r.Untyped)
445-
446-
// Wait for task completion if timeout > 0
447-
if waitTimeout > 0 {
448-
if _, err := task.Wait(waitTimeout); err != nil {
449-
return task, err
450-
}
451-
}
452-
453-
return task, nil
425+
asyncResult, _, err := untyped.MaybeWaitAsyncResultWithContext(ctx, record, r.Untyped, waitTimeout)
426+
return asyncResult, err
454427
}
455428
{{else}}
456429
// Delete deletes a {{.LowerName}} with search parameters{{if or .DeleteQueryParams .DeleteBodyParams}}
@@ -520,17 +493,8 @@ func (r *{{.Name}}) DeleteByIdWithContext(ctx context.Context, id any{{range .De
520493
return nil, err
521494
}
522495

523-
// Create async task from result
524-
task := untyped.NewAsyncResult(ctx, record.RecordID(), r.Untyped)
525-
526-
// Wait for task completion if timeout > 0
527-
if waitTimeout > 0 {
528-
if _, err := task.Wait(waitTimeout); err != nil {
529-
return task, err
530-
}
531-
}
532-
533-
return task, nil
496+
asyncResult, _, err := untyped.MaybeWaitAsyncResultWithContext(ctx, record, r.Untyped, waitTimeout)
497+
return asyncResult, err
534498
}
535499
{{else}}
536500
// DeleteById deletes a {{.LowerName}} by ID{{if .DeleteSummary}}
@@ -710,19 +674,11 @@ func (r *{{$.Name}}) {{.Name}}WithContext_{{.HTTPMethod}}(ctx context.Context{{i
710674
if err != nil {
711675
return nil, err
712676
}
713-
// Create async task from result
714-
task := untyped.NewAsyncResult(ctx, result.RecordID(), r.Untyped)
715-
// If waitTimeout is 0, return task immediately without waiting (async background operation)
716-
if waitTimeout == 0 {
717-
return task, nil
718-
}
719-
// Wait for task completion with the specified timeout
720-
if _, err := task.Wait(waitTimeout); err != nil {
721-
return task, err
722-
}
723-
return task, nil
724-
{{else}}{{if .ReturnsNoContent}}{{if and (or (and .HasParams .BodyFields) (and .HasBody .BodyFields)) (not .SimplifiedBody)}}_, err = core.Request[core.EmptyRecord](ctx, r.Untyped.GetResourceMap()[r.GetResourceType()], http.{{.GoHTTPMethod}}, resourcePath, reqParams, reqBody)
725-
return err{{else}}_, err := core.Request[core.EmptyRecord](ctx, r.Untyped.GetResourceMap()[r.GetResourceType()], http.{{.GoHTTPMethod}}, resourcePath, reqParams, reqBody)
677+
678+
asyncResult, _, err := untyped.MaybeWaitAsyncResultWithContext(ctx, result, r.Untyped, waitTimeout)
679+
return asyncResult, err
680+
{{else}}{{if .ReturnsNoContent}}{{if and (or (and .HasParams .BodyFields) (and .HasBody .BodyFields)) (not .SimplifiedBody)}}_, err = core.Request[core.Record](ctx, r.Untyped.GetResourceMap()[r.GetResourceType()], http.{{.GoHTTPMethod}}, resourcePath, reqParams, reqBody)
681+
return err{{else}}_, err := core.Request[core.Record](ctx, r.Untyped.GetResourceMap()[r.GetResourceType()], http.{{.GoHTTPMethod}}, resourcePath, reqParams, reqBody)
726682
return err{{end}}
727683
{{else}}{{if .ReturnsTextPlain}}record, err := core.Request[core.Record](ctx, r.Untyped.GetResourceMap()[r.GetResourceType()], http.{{.GoHTTPMethod}}, resourcePath, reqParams, reqBody)
728684
if err != nil {

0 commit comments

Comments
 (0)