Skip to content

Commit

Permalink
Merge pull request #193 from RedisLabs/remove-extra-calls
Browse files Browse the repository at this point in the history
Remove extra API call when retrieving latest backup and import Statuses
  • Loading branch information
matpimenta authored Dec 4, 2024
2 parents 7dcf80f + 09dd092 commit 8e659f2
Show file tree
Hide file tree
Showing 7 changed files with 147 additions and 242 deletions.
10 changes: 10 additions & 0 deletions CHANGELOG.md
Original file line number Diff line number Diff line change
Expand Up @@ -2,6 +2,16 @@
All notable changes to this project will be documented in this file.
See updating [Changelog example here](https://keepachangelog.com/en/1.0.0/).

## 0.21.0

### Added

* Handling API rate limits to wait or retry calls depending on the current window or remaining limits.

### Fixed

* Removed extra API call when retrieving latest backup and import Statuses.

## 0.8.0

### Added
Expand Down
4 changes: 2 additions & 2 deletions internal/model.go
Original file line number Diff line number Diff line change
Expand Up @@ -36,8 +36,8 @@ type Error struct {
Status *string `json:"status,omitempty"`
}

func (o Error) String() string {
return ToString(o)
func (e Error) String() string {
return ToString(e)
}

func (e *Error) StatusCode() string {
Expand Down
46 changes: 2 additions & 44 deletions internal/service.go
Original file line number Diff line number Diff line change
Expand Up @@ -115,56 +115,14 @@ func (a *api) waitForTaskToComplete(ctx context.Context, id string) (*Task, erro
a.logger.Println(err)
}))
if err != nil {
return nil, err
return task, err
}

return task, nil
}

func (a *api) WaitForTask(ctx context.Context, id string) (*Task, error) {
var task *Task
notFoundCount := 0
err := retry.Do(
func() error {
var err error
task, err = a.get(ctx, id)
if err != nil {
// An error is a terminal state (any repeated pre-task 404s will have been exhausted by this point)
return nil
}

status := redis.StringValue(task.Status)

if _, ok := processingStates[status]; !ok {
// The task is no longer processing for whatever reason
return nil
}

return fmt.Errorf("task %s not processed yet: %s", id, status)
},
retry.Attempts(math.MaxUint16),
retry.Delay(1*time.Second),
retry.MaxDelay(30*time.Second),
retry.RetryIf(func(err error) bool {
if !retry.IsRecoverable(err) {
return false
}
if _, ok := err.(*taskNotFoundError); ok {
notFoundCount++
if notFoundCount > max404Errors {
return false
}
}
return true
}),
retry.LastErrorOnly(true), retry.Context(ctx), retry.OnRetry(func(_ uint, err error) {
a.logger.Println(err)
}))
if err != nil {
return nil, err
}

return task, nil
return a.waitForTaskToComplete(ctx, id)
}

func (a *api) get(ctx context.Context, id string) (*Task, error) {
Expand Down
88 changes: 16 additions & 72 deletions latest_backups_test.go
Original file line number Diff line number Diff line change
Expand Up @@ -57,29 +57,6 @@ func TestGetLatestBackup(t *testing.T) {
]
}`,
),
getRequest(
t,
"/tasks/50ec6172-8475-4ef6-8b3c-d61e688d8fe5",
`{
"taskId": "50ec6172-8475-4ef6-8b3c-d61e688d8fe5",
"commandType": "databaseBackupStatusRequest",
"status": "processing-completed",
"description": "Request processing completed successfully and its resources are now being provisioned / de-provisioned.",
"timestamp": "2024-04-15T09:08:07.537915Z",
"response": {
"resourceId": 51051292,
"additionalResourceId": 12,
"resource": {}
},
"links": [
{
"href": "https://api-staging.qa.redislabs.com/v1/tasks/50ec6172-8475-4ef6-8b3c-d61e688d8fe5",
"type": "GET",
"rel": "self"
}
]
}`,
),
))

subject, err := clientFromTestServer(server, "key", "secret")
Expand Down Expand Up @@ -135,29 +112,6 @@ func TestGetFixedLatestBackup(t *testing.T) {
]
}`,
),
getRequest(
t,
"/tasks/ce2cbfea-9b15-4250-a516-f014161a8dd3",
`{
"taskId": "ce2cbfea-9b15-4250-a516-f014161a8dd3",
"commandType": "databaseBackupStatusRequest",
"status": "processing-completed",
"description": "Request processing completed successfully and its resources are now being provisioned / de-provisioned.",
"timestamp": "2024-04-15T09:52:26.101936Z",
"response": {
"resource": {
"status": "success"
}
},
"links": [
{
"href": "https://api-staging.qa.redislabs.com/v1/tasks/ce2cbfea-9b15-4250-a516-f014161a8dd3",
"type": "GET",
"rel": "self"
}
]
}`,
),
))

subject, err := clientFromTestServer(server, "key", "secret")
Expand Down Expand Up @@ -230,36 +184,26 @@ func TestGetAALatestBackup(t *testing.T) {
]
}`,
),
getRequest(
t,
"/tasks/ce2cbfea-9b15-4250-a516-f014161a8dd3",
`{
"taskId": "ce2cbfea-9b15-4250-a516-f014161a8dd3",
"commandType": "databaseBackupStatusRequest",
"status": "processing-error",
"description": "Task request failed during processing. See error information for failure details.",
"timestamp": "2024-04-15T09:52:26.101936Z",
"response": {
"error": {
"type": "DATABASE_BACKUP_DISABLED",
"status": "400 BAD_REQUEST",
"description": "Database backup is disabled"
}
},
"links": [
{
"href": "https://api-staging.qa.redislabs.com/v1/tasks/ce2cbfea-9b15-4250-a516-f014161a8dd3",
"type": "GET",
"rel": "self"
}
]
}`,
),
))

subject, err := clientFromTestServer(server, "key", "secret")
require.NoError(t, err)

_, err = subject.LatestBackup.GetActiveActive(context.TODO(), 12, 34, "eu-west-2")
actual, err := subject.LatestBackup.GetActiveActive(context.TODO(), 12, 34, "eu-west-2")
require.NoError(t, err)

assert.Equal(t, &latest_backups.LatestBackupStatus{
CommandType: redis.String("databaseBackupStatusRequest"),
Description: redis.String("Task request failed during processing. See error information for failure details."),
Status: redis.String("processing-error"),
ID: redis.String("ce2cbfea-9b15-4250-a516-f014161a8dd3"),
Response: &latest_backups.Response{
Error: &latest_backups.Error{
Type: redis.String("DATABASE_BACKUP_DISABLED"),
Description: redis.String("Database backup is disabled"),
Status: redis.String("400 BAD_REQUEST"),
},
},
}, actual)

}
103 changes: 15 additions & 88 deletions latest_imports_test.go
Original file line number Diff line number Diff line change
Expand Up @@ -61,38 +61,27 @@ func TestGetLatestImportTooEarly(t *testing.T) {
]
}`,
),
getRequest(
t,
"/tasks/1dfd6084-21df-40c6-829c-e9b4790e207e",
`{
"taskId": "1dfd6084-21df-40c6-829c-e9b4790e207e",
"commandType": "databaseImportStatusRequest",
"status": "processing-error",
"description": "Task request failed during processing. See error information for failure details.",
"timestamp": "2024-04-15T10:19:07.331898Z",
"response": {
"error": {
"type": "SUBSCRIPTION_NOT_ACTIVE",
"status": "403 FORBIDDEN",
"description": "Cannot preform any actions for subscription that is not in an active state"
}
},
"links": [
{
"href": "https://api-staging.qa.redislabs.com/v1/tasks/1dfd6084-21df-40c6-829c-e9b4790e207e",
"type": "GET",
"rel": "self"
}
]
}`,
),
))

subject, err := clientFromTestServer(server, "key", "secret")
require.NoError(t, err)

_, err = subject.LatestImport.Get(context.TODO(), 12, 34)
actual, err := subject.LatestImport.Get(context.TODO(), 12, 34)
require.NoError(t, err)

assert.Equal(t, &latest_imports.LatestImportStatus{
CommandType: redis.String("databaseImportStatusRequest"),
Description: redis.String("Task request failed during processing. See error information for failure details."),
Status: redis.String("processing-error"),
ID: redis.String("1dfd6084-21df-40c6-829c-e9b4790e207e"),
Response: &latest_imports.Response{
Error: &latest_imports.Error{
Type: redis.String("SUBSCRIPTION_NOT_ACTIVE"),
Description: redis.String("Cannot preform any actions for subscription that is not in an active state"),
Status: redis.String("403 FORBIDDEN"),
},
},
}, actual)
}

func TestGetFixedLatestImport(t *testing.T) {
Expand Down Expand Up @@ -143,31 +132,6 @@ func TestGetFixedLatestImport(t *testing.T) {
]
}`,
),
getRequest(
t,
"/tasks/e9232e43-3781-4263-a38e-f4d150e03475",
`{
"taskId": "e9232e43-3781-4263-a38e-f4d150e03475",
"commandType": "databaseImportStatusRequest",
"status": "processing-completed",
"description": "Request processing completed successfully and its resources are now being provisioned / de-provisioned.",
"timestamp": "2024-04-15T10:44:35.225468Z",
"response": {
"resourceId": 51051302,
"additionalResourceId": 110777,
"resource": {
"status": "importing"
}
},
"links": [
{
"href": "https://api-staging.qa.redislabs.com/v1/tasks/e9232e43-3781-4263-a38e-f4d150e03475",
"type": "GET",
"rel": "self"
}
]
}`,
),
))

subject, err := clientFromTestServer(server, "key", "secret")
Expand Down Expand Up @@ -251,43 +215,6 @@ func TestGetLatestImport(t *testing.T) {
]
}`,
),
getRequest(
t,
"/tasks/e9232e43-3781-4263-a38e-f4d150e03475",
`{
"taskId": "e9232e43-3781-4263-a38e-f4d150e03475",
"commandType": "databaseImportStatusRequest",
"status": "processing-completed",
"description": "Request processing completed successfully and its resources are now being provisioned / de-provisioned.",
"timestamp": "2024-04-15T10:44:35.225468Z",
"response": {
"resourceId": 51051302,
"additionalResourceId": 110777,
"resource": {
"failureReason": "file-corrupted",
"failureReasonParams": [
{
"key": "bytes_configured_bdb_limit",
"value": "1234"
},
{
"key": "bytes_of_expected_dataset",
"value": "5678"
}
],
"lastImportTime": "2024-05-21T10:36:26Z",
"status": "failed"
}
},
"links": [
{
"href": "https://api-staging.qa.redislabs.com/v1/tasks/e9232e43-3781-4263-a38e-f4d150e03475",
"type": "GET",
"rel": "self"
}
]
}`,
),
))

subject, err := clientFromTestServer(server, "key", "secret")
Expand Down
Loading

0 comments on commit 8e659f2

Please sign in to comment.