Skip to content

Commit 8ed0c07

Browse files
Merge pull request #249 from RedisLabs/feat/tgw-accepter-resources
TGW invitation endpoints
2 parents b82843b + 822ac7e commit 8ed0c07

File tree

10 files changed

+644
-22
lines changed

10 files changed

+644
-22
lines changed

.github/workflows/ci.yml

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -9,10 +9,10 @@ jobs:
99

1010
steps:
1111
- name: Checkout
12-
uses: actions/checkout@v5.0.0
12+
uses: actions/checkout@v6.0.1
1313

1414
- name: Install Go
15-
uses: actions/setup-go@v6.0.0
15+
uses: actions/setup-go@v6.1.0
1616
with:
1717
go-version-file: go.mod
1818
cache: true

.github/workflows/codeql-analysis.yml

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -35,7 +35,7 @@ jobs:
3535

3636
steps:
3737
- name: Checkout repository
38-
uses: actions/checkout@v5.0.0
38+
uses: actions/checkout@v6.0.1
3939

4040
# Initializes the CodeQL tools for scanning.
4141
- name: Initialize CodeQL

.github/workflows/vulnerability.yml

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -7,10 +7,10 @@ jobs:
77
runs-on: ubuntu-latest
88
steps:
99
- name: Checkout
10-
uses: actions/checkout@v5.0.0
10+
uses: actions/checkout@v6.0.1
1111

1212
- name: Install Go
13-
uses: actions/setup-go@v6.0.0
13+
uses: actions/setup-go@v6.1.0
1414
with:
1515
go-version-file: go.mod
1616
cache: true

CHANGELOG.md

Lines changed: 5 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -2,6 +2,11 @@
22
All notable changes to this project will be documented in this file.
33
See updating [Changelog example here](https://keepachangelog.com/en/1.0.0/).
44

5+
## 0.44.0 (5th December 2025)
6+
7+
### Added:
8+
* Added Transit Gateway invitation support: `ListInvitations()`, `AcceptInvitation()`, and `RejectInvitation()` methods for both Pro and Active-Active subscriptions
9+
510
## 0.43.0 (11th November 2025)
611

712
### Added:

go.mod

Lines changed: 6 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -2,21 +2,21 @@ module github.com/RedisLabs/rediscloud-go-api
22

33
go 1.24.0
44

5-
toolchain go1.25.3
5+
toolchain go1.25.5
66

77
require (
88
github.com/avast/retry-go/v4 v4.7.0
99
github.com/stretchr/testify v1.11.1
10-
golang.org/x/tools v0.38.0
10+
golang.org/x/tools v0.39.0
1111
)
1212

1313
require (
1414
github.com/davecgh/go-spew v1.1.1 // indirect
1515
github.com/pmezard/go-difflib v1.0.0 // indirect
1616
github.com/stretchr/objx v0.5.2 // indirect
17-
golang.org/x/mod v0.29.0 // indirect
18-
golang.org/x/sync v0.17.0 // indirect
19-
golang.org/x/sys v0.37.0 // indirect
20-
golang.org/x/telemetry v0.0.0-20251008203120-078029d740a8 // indirect
17+
golang.org/x/mod v0.30.0 // indirect
18+
golang.org/x/sync v0.18.0 // indirect
19+
golang.org/x/sys v0.38.0 // indirect
20+
golang.org/x/telemetry v0.0.0-20251111182119-bc8e575c7b54 // indirect
2121
gopkg.in/yaml.v3 v3.0.1 // indirect
2222
)

go.sum

Lines changed: 10 additions & 10 deletions
Original file line numberDiff line numberDiff line change
@@ -10,16 +10,16 @@ github.com/stretchr/objx v0.5.2 h1:xuMeJ0Sdp5ZMRXx/aWO6RZxdr3beISkG5/G/aIRr3pY=
1010
github.com/stretchr/objx v0.5.2/go.mod h1:FRsXN1f5AsAjCGJKqEizvkpNtU+EGNCLh3NxZ/8L+MA=
1111
github.com/stretchr/testify v1.11.1 h1:7s2iGBzp5EwR7/aIZr8ao5+dra3wiQyKjjFuvgVKu7U=
1212
github.com/stretchr/testify v1.11.1/go.mod h1:wZwfW3scLgRK+23gO65QZefKpKQRnfz6sD981Nm4B6U=
13-
golang.org/x/mod v0.29.0 h1:HV8lRxZC4l2cr3Zq1LvtOsi/ThTgWnUk/y64QSs8GwA=
14-
golang.org/x/mod v0.29.0/go.mod h1:NyhrlYXJ2H4eJiRy/WDBO6HMqZQ6q9nk4JzS3NuCK+w=
15-
golang.org/x/sync v0.17.0 h1:l60nONMj9l5drqw6jlhIELNv9I0A4OFgRsG9k2oT9Ug=
16-
golang.org/x/sync v0.17.0/go.mod h1:9KTHXmSnoGruLpwFjVSX0lNNA75CykiMECbovNTZqGI=
17-
golang.org/x/sys v0.37.0 h1:fdNQudmxPjkdUTPnLn5mdQv7Zwvbvpaxqs831goi9kQ=
18-
golang.org/x/sys v0.37.0/go.mod h1:OgkHotnGiDImocRcuBABYBEXf8A9a87e/uXjp9XT3ks=
19-
golang.org/x/telemetry v0.0.0-20251008203120-078029d740a8 h1:LvzTn0GQhWuvKH/kVRS3R3bVAsdQWI7hvfLHGgh9+lU=
20-
golang.org/x/telemetry v0.0.0-20251008203120-078029d740a8/go.mod h1:Pi4ztBfryZoJEkyFTI5/Ocsu2jXyDr6iSdgJiYE/uwE=
21-
golang.org/x/tools v0.38.0 h1:Hx2Xv8hISq8Lm16jvBZ2VQf+RLmbd7wVUsALibYI/IQ=
22-
golang.org/x/tools v0.38.0/go.mod h1:yEsQ/d/YK8cjh0L6rZlY8tgtlKiBNTL14pGDJPJpYQs=
13+
golang.org/x/mod v0.30.0 h1:fDEXFVZ/fmCKProc/yAXXUijritrDzahmwwefnjoPFk=
14+
golang.org/x/mod v0.30.0/go.mod h1:lAsf5O2EvJeSFMiBxXDki7sCgAxEUcZHXoXMKT4GJKc=
15+
golang.org/x/sync v0.18.0 h1:kr88TuHDroi+UVf+0hZnirlk8o8T+4MrK6mr60WkH/I=
16+
golang.org/x/sync v0.18.0/go.mod h1:9KTHXmSnoGruLpwFjVSX0lNNA75CykiMECbovNTZqGI=
17+
golang.org/x/sys v0.38.0 h1:3yZWxaJjBmCWXqhN1qh02AkOnCQ1poK6oF+a7xWL6Gc=
18+
golang.org/x/sys v0.38.0/go.mod h1:OgkHotnGiDImocRcuBABYBEXf8A9a87e/uXjp9XT3ks=
19+
golang.org/x/telemetry v0.0.0-20251111182119-bc8e575c7b54 h1:E2/AqCUMZGgd73TQkxUMcMla25GB9i/5HOdLr+uH7Vo=
20+
golang.org/x/telemetry v0.0.0-20251111182119-bc8e575c7b54/go.mod h1:hKdjCMrbv9skySur+Nek8Hd0uJ0GuxJIoIX2payrIdQ=
21+
golang.org/x/tools v0.39.0 h1:ik4ho21kwuQln40uelmciQPp9SipgNDdrafrYA4TmQQ=
22+
golang.org/x/tools v0.39.0/go.mod h1:JnefbkDPyD8UU2kI5fuf8ZX4/yUeh9W877ZeBONxUqQ=
2323
gopkg.in/check.v1 v0.0.0-20161208181325-20d25e280405 h1:yhCVgyC4o1eVCa2tZl7eS0r+SDo693bJlVdllGtEeKM=
2424
gopkg.in/check.v1 v0.0.0-20161208181325-20d25e280405/go.mod h1:Co6ibVJAznAaIkqp8huTwlJQCZ016jof/cbN4VW5Yz0=
2525
gopkg.in/yaml.v3 v3.0.1 h1:fxVm/GzAzEWqLHuvctI91KS9hhNmmWOoWu0XTYJS7CA=

service/transit_gateway/attachments/model.go

Lines changed: 26 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -38,6 +38,32 @@ type updateCidrs struct {
3838
Cidrs *[]*string `json:"cidrs,omitempty"`
3939
}
4040

41+
type TransitGatewayInvitation struct {
42+
Id *int `json:"id,omitempty"`
43+
Name *string `json:"name,omitempty"`
44+
ResourceShareUid *string `json:"resourceShareUid,omitempty"`
45+
AwsAccountId *string `json:"awsAccountId,omitempty"`
46+
Status *string `json:"status,omitempty"`
47+
SharedDate *string `json:"sharedDate,omitempty"`
48+
}
49+
50+
type InvitationsResource struct {
51+
Resources []*TransitGatewayInvitation `json:"resources,omitempty"`
52+
}
53+
54+
type InvitationsResponse struct {
55+
CommandType *string `json:"commandType,omitempty"`
56+
Description *string `json:"description,omitempty"`
57+
Status *string `json:"status,omitempty"`
58+
ID *string `json:"taskId,omitempty"`
59+
Response *InvitationResponseData `json:"response,omitempty"`
60+
}
61+
62+
type InvitationResponseData struct {
63+
ResourceId *int `json:"resourceId,omitempty"`
64+
Resource *InvitationsResource `json:"resource,omitempty"`
65+
}
66+
4167
type NotFound struct {
4268
subId int
4369
}

service/transit_gateway/attachments/service.go

Lines changed: 128 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -114,6 +114,66 @@ func (a *API) DeleteActiveActive(ctx context.Context, subscription int, regionId
114114
return nil
115115
}
116116

117+
func (a *API) ListInvitations(ctx context.Context, subscription int) ([]*TransitGatewayInvitation, error) {
118+
message := fmt.Sprintf("list TGw invitations for subscription %d", subscription)
119+
address := fmt.Sprintf("/subscriptions/%d/transitGateways/invitations", subscription)
120+
invitations, err := a.listInvitations(ctx, message, address)
121+
if err != nil {
122+
return nil, wrap404Error(subscription, err)
123+
}
124+
return invitations, nil
125+
}
126+
127+
func (a *API) ListInvitationsActiveActive(ctx context.Context, subscription int, regionId int) ([]*TransitGatewayInvitation, error) {
128+
message := fmt.Sprintf("list TGw invitations for subscription %d in region %d", subscription, regionId)
129+
address := fmt.Sprintf("/subscriptions/%d/regions/%d/transitGateways/invitations", subscription, regionId)
130+
invitations, err := a.listInvitations(ctx, message, address)
131+
if err != nil {
132+
return nil, wrap404ErrorActiveActive(subscription, regionId, err)
133+
}
134+
return invitations, nil
135+
}
136+
137+
func (a *API) AcceptInvitation(ctx context.Context, subscription int, tgwInvitationId int) error {
138+
message := fmt.Sprintf("accept TGw invitation %d for subscription %d", tgwInvitationId, subscription)
139+
address := fmt.Sprintf("/subscriptions/%d/transitGateways/invitations/%d/accept", subscription, tgwInvitationId)
140+
err := a.acceptInvitation(ctx, message, address)
141+
if err != nil {
142+
return wrap404Error(subscription, err)
143+
}
144+
return nil
145+
}
146+
147+
func (a *API) AcceptInvitationActiveActive(ctx context.Context, subscription int, regionId int, tgwInvitationId int) error {
148+
message := fmt.Sprintf("accept TGw invitation %d for subscription %d in region %d", tgwInvitationId, subscription, regionId)
149+
address := fmt.Sprintf("/subscriptions/%d/regions/%d/transitGateways/invitations/%d/accept", subscription, regionId, tgwInvitationId)
150+
err := a.acceptInvitation(ctx, message, address)
151+
if err != nil {
152+
return wrap404ErrorActiveActive(subscription, regionId, err)
153+
}
154+
return nil
155+
}
156+
157+
func (a *API) RejectInvitation(ctx context.Context, subscription int, tgwInvitationId int) error {
158+
message := fmt.Sprintf("reject TGw invitation %d for subscription %d", tgwInvitationId, subscription)
159+
address := fmt.Sprintf("/subscriptions/%d/transitGateways/invitations/%d/reject", subscription, tgwInvitationId)
160+
err := a.rejectInvitation(ctx, message, address)
161+
if err != nil {
162+
return wrap404Error(subscription, err)
163+
}
164+
return nil
165+
}
166+
167+
func (a *API) RejectInvitationActiveActive(ctx context.Context, subscription int, regionId int, tgwInvitationId int) error {
168+
message := fmt.Sprintf("reject TGw invitation %d for subscription %d in region %d", tgwInvitationId, subscription, regionId)
169+
address := fmt.Sprintf("/subscriptions/%d/regions/%d/transitGateways/invitations/%d/reject", subscription, regionId, tgwInvitationId)
170+
err := a.rejectInvitation(ctx, message, address)
171+
if err != nil {
172+
return wrap404ErrorActiveActive(subscription, regionId, err)
173+
}
174+
return nil
175+
}
176+
117177
func (a *API) get(ctx context.Context, message string, address string) (*GetAttachmentsTask, error) {
118178
var task internal.TaskResponse
119179
err := a.client.Get(ctx, message, address, &task)
@@ -124,8 +184,11 @@ func (a *API) get(ctx context.Context, message string, address string) (*GetAtta
124184
a.logger.Printf("Waiting for tgwGetRequest %d to complete", task.ID)
125185

126186
err = a.taskWaiter.Wait(ctx, *task.ID)
187+
if err != nil {
188+
return nil, err
189+
}
127190

128-
a.logger.Printf("tgwGetRequest %d completed, possibly with error", task.ID, err)
191+
a.logger.Printf("tgwGetRequest %d completed", task.ID)
129192

130193
var getAttachmentsTask *GetAttachmentsTask
131194
err = a.client.Get(ctx,
@@ -194,6 +257,70 @@ func (a *API) delete(ctx context.Context, message string, address string) error
194257
return nil
195258
}
196259

260+
func (a *API) listInvitations(ctx context.Context, message string, address string) ([]*TransitGatewayInvitation, error) {
261+
var task internal.TaskResponse
262+
err := a.client.Get(ctx, message, address, &task)
263+
if err != nil {
264+
return nil, err
265+
}
266+
267+
a.logger.Printf("Waiting for tgwListInvitationsRequest %d to complete", task.ID)
268+
269+
err = a.taskWaiter.Wait(ctx, *task.ID)
270+
if err != nil {
271+
return nil, err
272+
}
273+
274+
a.logger.Printf("tgwListInvitationsRequest %d completed", task.ID)
275+
276+
var invitationsResponse *InvitationsResponse
277+
err = a.client.Get(ctx,
278+
fmt.Sprintf("retrieve completed tgwListInvitationsRequest task %d", task.ID),
279+
"/tasks/"+*task.ID,
280+
&invitationsResponse,
281+
)
282+
283+
if err != nil {
284+
return nil, fmt.Errorf("failed to retrieve completed tgwListInvitationsRequest %d: %w", task.ID, err)
285+
}
286+
287+
return invitationsResponse.Response.Resource.Resources, nil
288+
}
289+
290+
func (a *API) acceptInvitation(ctx context.Context, message string, address string) error {
291+
var task internal.TaskResponse
292+
err := a.client.Put(ctx, message, address, nil, &task)
293+
if err != nil {
294+
return err
295+
}
296+
297+
a.logger.Printf("Waiting for task %s to finish accepting the TGw invitation", task)
298+
299+
err = a.taskWaiter.Wait(ctx, *task.ID)
300+
if err != nil {
301+
return fmt.Errorf("failed when accepting TGw invitation %w", err)
302+
}
303+
304+
return nil
305+
}
306+
307+
func (a *API) rejectInvitation(ctx context.Context, message string, address string) error {
308+
var task internal.TaskResponse
309+
err := a.client.Put(ctx, message, address, nil, &task)
310+
if err != nil {
311+
return err
312+
}
313+
314+
a.logger.Printf("Waiting for task %s to finish rejecting the TGw invitation", task)
315+
316+
err = a.taskWaiter.Wait(ctx, *task.ID)
317+
if err != nil {
318+
return fmt.Errorf("failed when rejecting TGw invitation %w", err)
319+
}
320+
321+
return nil
322+
}
323+
197324
func wrap404Error(subId int, err error) error {
198325
if v, ok := err.(*internal.HTTPError); ok && v.StatusCode == http.StatusNotFound {
199326
return &NotFound{subId: subId}

0 commit comments

Comments
 (0)