-
Notifications
You must be signed in to change notification settings - Fork 6
Commit
This commit does not belong to any branch on this repository, and may belong to a fork outside of the repository.
- Loading branch information
0 parents
commit 347ca97
Showing
9 changed files
with
558 additions
and
0 deletions.
There are no files selected for viewing
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,28 @@ | ||
name: release | ||
|
||
on: | ||
push: | ||
tags: | ||
- '*' | ||
|
||
jobs: | ||
goreleaser: | ||
runs-on: ubuntu-latest | ||
steps: | ||
- uses: actions/checkout@v3 | ||
with: | ||
fetch-depth: 0 | ||
|
||
- run: git fetch --force --tags | ||
|
||
- uses: actions/setup-go@v4 | ||
with: | ||
go-version: stable | ||
|
||
- uses: goreleaser/goreleaser-action@v4 | ||
with: | ||
distribution: goreleaser | ||
version: latest | ||
args: release --clean | ||
env: | ||
GITHUB_TOKEN: ${{ secrets.GORELEASER_GITHUB_TOKEN }} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,2 @@ | ||
|
||
dist/ |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,54 @@ | ||
# This is an example .goreleaser.yml file with some sensible defaults. | ||
# Make sure to check the documentation at https://goreleaser.com | ||
before: | ||
hooks: | ||
- go mod tidy | ||
builds: | ||
- env: | ||
- CGO_ENABLED=0 | ||
goos: | ||
- linux | ||
- windows | ||
- darwin | ||
goarch: | ||
- arm64 | ||
- amd64 | ||
archives: | ||
- format: tar.gz | ||
# this name template makes the OS and Arch compatible with the results of uname. | ||
name_template: >- | ||
{{ .ProjectName }}_ | ||
{{- title .Os }}_ | ||
{{- if eq .Arch "amd64" }}x86_64 | ||
{{- else if eq .Arch "386" }}i386 | ||
{{- else }}{{ .Arch }}{{ end }} | ||
{{- if .Arm }}v{{ .Arm }}{{ end }} | ||
# use zip for windows archives | ||
format_overrides: | ||
- goos: windows | ||
format: zip | ||
brews: | ||
- name: rdsconn | ||
tap: | ||
owner: aidansteele | ||
name: homebrew-taps | ||
commit_author: | ||
name: Aidan Steele | ||
email: [email protected] | ||
homepage: https://github.com/aidansteele/rdsconn | ||
description: rdsconn makes connecting to an AWS RDS instance inside a VPC from your laptop easier | ||
checksum: | ||
name_template: 'checksums.txt' | ||
snapshot: | ||
name_template: "{{ incpatch .Version }}-next" | ||
changelog: | ||
sort: asc | ||
filters: | ||
exclude: | ||
- '^docs:' | ||
- '^test:' | ||
|
||
# The lines beneath this are called `modelines`. See `:help modeline` | ||
# Feel free to remove those if you don't want/use them. | ||
# yaml-language-server: $schema=https://goreleaser.com/static/schema.json | ||
# vim: set ts=2 sw=2 tw=0 fo=cnqoj |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,41 @@ | ||
# rdsconn | ||
|
||
On June 14th, 2023 AWS [launched][aws-blog] new connectivity options for | ||
_EC2 Instance Connect_. This functionality also works for non-EC2 resources in | ||
VPCs. You _could_ run the official AWS CLI (>= v2.12.0) using the following command, | ||
but `rdsconn` aims to make the RDS experience easier. | ||
|
||
``` | ||
aws ec2-instance-connect open-tunnel \ | ||
--private-ip-address 10.1.2.150 \ | ||
--instance-connect-endpoint-id eice-06d8b7ad48example \ | ||
--remote-port 5432 \ | ||
--local-port 5432 | ||
``` | ||
|
||
## Installation | ||
|
||
On macOS, `brew install aidansteele/taps/rdsconn`. On other platforms: see | ||
published binaries in the releases tab of the GitHub repo. | ||
|
||
## Usage | ||
|
||
1. Create an EC2 Instance Connect endpoint in your VPC. Ensure that your RDS DB | ||
instance's security group allows the EIC endpoint to connect to it. | ||
2. Have valid AWS credentials configured. E.g. either as environment variables, | ||
default credentials in your config file, or a profile with `AWS_PROFILE=name` | ||
env var set. | ||
3. Run `rdsconn proxy`. The CLI will prompt you to select an RDS DB instance from | ||
the list of DBs in your account. Hit enter to confirm selection. | ||
4. The message `Proxy running. Now waiting to serve connections to localhost:5432...` | ||
will appear. You can now run `psql ... -h 127.0.0.1` (or `mysql ...`) | ||
|
||
## Future plans | ||
|
||
* Flesh out this README more | ||
* Detect incorrect configurations and provide helpful error messages to user. | ||
E.g. missing endpoints, security groups, routes, etc. | ||
* Add a `client` subcommand that uses RDS IAM authentication to launch and | ||
authenticate a child process `psql` CLI (using PGPASSWORD etc env vars) | ||
|
||
[aws-blog]: https://aws.amazon.com/blogs/compute/secure-connectivity-from-public-to-private-introducing-ec2-instance-connect-endpoint-june-13-2023/ |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,115 @@ | ||
package ec2ic | ||
|
||
import ( | ||
"context" | ||
"crypto/sha256" | ||
"encoding/hex" | ||
"fmt" | ||
"github.com/aws/aws-sdk-go-v2/aws" | ||
"github.com/aws/aws-sdk-go-v2/aws/signer/v4" | ||
"github.com/aws/aws-sdk-go-v2/service/ec2" | ||
"github.com/gorilla/websocket" | ||
"io" | ||
"net" | ||
"net/http" | ||
"net/url" | ||
"time" | ||
) | ||
|
||
type Dialer struct { | ||
cfg aws.Config | ||
endpointId string | ||
endpointDns string | ||
duration time.Duration | ||
} | ||
|
||
func NewDialer(ctx context.Context, cfg aws.Config, endpointId string, duration time.Duration) (*Dialer, error) { | ||
api := ec2.NewFromConfig(cfg) | ||
|
||
if duration == 0 { | ||
duration = time.Hour | ||
} | ||
|
||
describe, err := api.DescribeInstanceConnectEndpoints(ctx, &ec2.DescribeInstanceConnectEndpointsInput{InstanceConnectEndpointIds: []string{endpointId}}) | ||
if err != nil { | ||
return nil, fmt.Errorf("describing ec2 instance connect endpoint: %w", err) | ||
} | ||
|
||
return &Dialer{ | ||
cfg: cfg, | ||
endpointId: endpointId, | ||
endpointDns: *describe.InstanceConnectEndpoints[0].DnsName, | ||
duration: duration, | ||
}, nil | ||
} | ||
|
||
func (icd *Dialer) DialContext(ctx context.Context, network, address string) (net.Conn, error) { | ||
if network != "tcp" && network != "tcp4" { | ||
return nil, fmt.Errorf("only tcp supported") | ||
} | ||
|
||
host, port, err := net.SplitHostPort(address) | ||
if err != nil { | ||
return nil, fmt.Errorf("splitting host and port: %w", err) | ||
} | ||
|
||
resolved, err := net.ResolveIPAddr("ip", host) | ||
if err != nil { | ||
return nil, fmt.Errorf("resolving private ip: %w", err) | ||
} | ||
|
||
q := url.Values{} | ||
q.Set("instanceConnectEndpointId", icd.endpointId) | ||
q.Set("maxTunnelDuration", fmt.Sprintf("%d", int(icd.duration.Seconds()))) | ||
q.Set("remotePort", port) | ||
q.Set("privateIpAddress", resolved.String()) | ||
|
||
r, _ := http.NewRequest("GET", fmt.Sprintf("wss://%s/openTunnel?%s", icd.endpointDns, q.Encode()), nil) | ||
|
||
sum := sha256.Sum256([]byte{}) | ||
sumStr := hex.EncodeToString(sum[:]) | ||
|
||
creds, err := icd.cfg.Credentials.Retrieve(ctx) | ||
if err != nil { | ||
panic(fmt.Sprintf("%+v", err)) | ||
} | ||
|
||
s := v4.NewSigner() | ||
signed, _, err := s.PresignHTTP(ctx, creds, r, sumStr, "ec2-instance-connect", icd.cfg.Region, time.Now()) | ||
if err != nil { | ||
panic(fmt.Sprintf("%+v", err)) | ||
} | ||
|
||
conn, _, err := websocket.DefaultDialer.DialContext(ctx, signed, http.Header{}) | ||
if err != nil { | ||
return nil, fmt.Errorf("dialing websocket: %w", err) | ||
} | ||
|
||
return &icdConn{ | ||
Conn: conn, | ||
r: websocket.JoinMessages(conn, ""), | ||
}, nil | ||
} | ||
|
||
type icdConn struct { | ||
*websocket.Conn | ||
r io.Reader | ||
} | ||
|
||
var _ net.Conn = (*icdConn)(nil) | ||
|
||
func (i *icdConn) Read(b []byte) (n int, err error) { | ||
return i.r.Read(b) | ||
} | ||
|
||
func (i *icdConn) Write(b []byte) (n int, err error) { | ||
err = i.Conn.WriteMessage(websocket.BinaryMessage, b) | ||
n = len(b) | ||
return | ||
} | ||
|
||
func (i *icdConn) SetDeadline(t time.Time) error { | ||
i.SetReadDeadline(t) | ||
i.SetWriteDeadline(t) | ||
return nil | ||
} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,29 @@ | ||
module github.com/aidansteele/rdsconn | ||
|
||
go 1.20 | ||
|
||
require ( | ||
github.com/aws/aws-sdk-go-v2 v1.18.1 // indirect | ||
github.com/aws/aws-sdk-go-v2/config v1.18.26 // indirect | ||
github.com/aws/aws-sdk-go-v2/credentials v1.13.25 // indirect | ||
github.com/aws/aws-sdk-go-v2/feature/ec2/imds v1.13.4 // indirect | ||
github.com/aws/aws-sdk-go-v2/internal/configsources v1.1.34 // indirect | ||
github.com/aws/aws-sdk-go-v2/internal/endpoints/v2 v2.4.28 // indirect | ||
github.com/aws/aws-sdk-go-v2/internal/ini v1.3.35 // indirect | ||
github.com/aws/aws-sdk-go-v2/service/ec2 v1.100.0 // indirect | ||
github.com/aws/aws-sdk-go-v2/service/internal/presigned-url v1.9.28 // indirect | ||
github.com/aws/aws-sdk-go-v2/service/rds v1.45.1 // indirect | ||
github.com/aws/aws-sdk-go-v2/service/sso v1.12.11 // indirect | ||
github.com/aws/aws-sdk-go-v2/service/ssooidc v1.14.11 // indirect | ||
github.com/aws/aws-sdk-go-v2/service/sts v1.19.1 // indirect | ||
github.com/aws/smithy-go v1.13.5 // indirect | ||
github.com/chzyer/readline v0.0.0-20180603132655-2972be24d48e // indirect | ||
github.com/gorilla/websocket v1.5.0 // indirect | ||
github.com/inconshreveable/mousetrap v1.1.0 // indirect | ||
github.com/jmespath/go-jmespath v0.4.0 // indirect | ||
github.com/manifoldco/promptui v0.9.0 // indirect | ||
github.com/spf13/cobra v1.7.0 // indirect | ||
github.com/spf13/pflag v1.0.5 // indirect | ||
golang.org/x/sync v0.3.0 // indirect | ||
golang.org/x/sys v0.0.0-20181122145206-62eef0e2fa9b // indirect | ||
) |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,58 @@ | ||
github.com/aws/aws-sdk-go-v2 v1.18.1 h1:+tefE750oAb7ZQGzla6bLkOwfcQCEtC5y2RqoqCeqKo= | ||
github.com/aws/aws-sdk-go-v2 v1.18.1/go.mod h1:uzbQtefpm44goOPmdKyAlXSNcwlRgF3ePWVW6EtJvvw= | ||
github.com/aws/aws-sdk-go-v2/config v1.18.26 h1:ivCHcSmKd1+9rBlqVsxZHB35eCW88KWbMdG2VL3BuBw= | ||
github.com/aws/aws-sdk-go-v2/config v1.18.26/go.mod h1:NVmd//z/PNl7U+ZU2EnuffxOA060JWzgbH3BnqQrUoY= | ||
github.com/aws/aws-sdk-go-v2/credentials v1.13.25 h1:5wROoMcUC7nAE66e0b3IIht6Tos76M4HC+GQw8MeqxU= | ||
github.com/aws/aws-sdk-go-v2/credentials v1.13.25/go.mod h1:W9I2660WXSwZQ23mM1Ks72+UGeyirIxuU7/KzN7daeA= | ||
github.com/aws/aws-sdk-go-v2/feature/ec2/imds v1.13.4 h1:LxK/bitrAr4lnh9LnIS6i7zWbCOdMsfzKFBI6LUCS0I= | ||
github.com/aws/aws-sdk-go-v2/feature/ec2/imds v1.13.4/go.mod h1:E1hLXN/BL2e6YizK1zFlYd8vsfi2GTjbjBazinMmeaM= | ||
github.com/aws/aws-sdk-go-v2/internal/configsources v1.1.34 h1:A5UqQEmPaCFpedKouS4v+dHCTUo2sKqhoKO9U5kxyWo= | ||
github.com/aws/aws-sdk-go-v2/internal/configsources v1.1.34/go.mod h1:wZpTEecJe0Btj3IYnDx/VlUzor9wm3fJHyvLpQF0VwY= | ||
github.com/aws/aws-sdk-go-v2/internal/endpoints/v2 v2.4.28 h1:srIVS45eQuewqz6fKKu6ZGXaq6FuFg5NzgQBAM6g8Y4= | ||
github.com/aws/aws-sdk-go-v2/internal/endpoints/v2 v2.4.28/go.mod h1:7VRpKQQedkfIEXb4k52I7swUnZP0wohVajJMRn3vsUw= | ||
github.com/aws/aws-sdk-go-v2/internal/ini v1.3.35 h1:LWA+3kDM8ly001vJ1X1waCuLJdtTl48gwkPKWy9sosI= | ||
github.com/aws/aws-sdk-go-v2/internal/ini v1.3.35/go.mod h1:0Eg1YjxE0Bhn56lx+SHJwCzhW+2JGtizsrx+lCqrfm0= | ||
github.com/aws/aws-sdk-go-v2/service/ec2 v1.100.0 h1:Wo/HHkC8PcVPXAB9WNwMmGHiA+b6VsJiT/DW2nB2D1w= | ||
github.com/aws/aws-sdk-go-v2/service/ec2 v1.100.0/go.mod h1:tIctCeX9IbzsUTKHt53SVEcgyfxV2ElxJeEB+QUbc4M= | ||
github.com/aws/aws-sdk-go-v2/service/internal/presigned-url v1.9.28 h1:bkRyG4a929RCnpVSTvLM2j/T4ls015ZhhYApbmYs15s= | ||
github.com/aws/aws-sdk-go-v2/service/internal/presigned-url v1.9.28/go.mod h1:jj7znCIg05jXlaGBlFMGP8+7UN3VtCkRBG2spnmRQkU= | ||
github.com/aws/aws-sdk-go-v2/service/rds v1.45.1 h1:Pxwe38BtUudOFqCNBFrzw0Gxufs0YioaTFnpubJTg7Y= | ||
github.com/aws/aws-sdk-go-v2/service/rds v1.45.1/go.mod h1:goBDR4OPrsnKpYyU0GHGcEnlTmL8O+eKGsWeyOAFJ5M= | ||
github.com/aws/aws-sdk-go-v2/service/sso v1.12.11 h1:cNrMc266RsZJ8V1u1OQQONKcf9HmfxQFqgcpY7ZJBhY= | ||
github.com/aws/aws-sdk-go-v2/service/sso v1.12.11/go.mod h1:HuCOxYsF21eKrerARYO6HapNeh9GBNq7fius2AcwodY= | ||
github.com/aws/aws-sdk-go-v2/service/ssooidc v1.14.11 h1:h2VhtCE5PBiJefmlVCjJRSzBfFcQeAE10SXIGkXw1jQ= | ||
github.com/aws/aws-sdk-go-v2/service/ssooidc v1.14.11/go.mod h1:E4VrHCPzmVB/KFXtqBGKb3c8zpbNBgKe3fisDNLAW5w= | ||
github.com/aws/aws-sdk-go-v2/service/sts v1.19.1 h1:ehPTnLR/es8TL1fpBfq8qw9cAwOpQr47fLmZD9yhHjk= | ||
github.com/aws/aws-sdk-go-v2/service/sts v1.19.1/go.mod h1:dp0yLPsLBOi++WTxzCjA/oZqi6NPIhoR+uF7GeMU9eg= | ||
github.com/aws/smithy-go v1.13.5 h1:hgz0X/DX0dGqTYpGALqXJoRKRj5oQ7150i5FdTePzO8= | ||
github.com/aws/smithy-go v1.13.5/go.mod h1:Tg+OJXh4MB2R/uN61Ko2f6hTZwB/ZYGOtib8J3gBHzA= | ||
github.com/chzyer/logex v1.1.10/go.mod h1:+Ywpsq7O8HXn0nuIou7OrIPyXbp3wmkHB+jjWRnGsAI= | ||
github.com/chzyer/readline v0.0.0-20180603132655-2972be24d48e h1:fY5BOSpyZCqRo5OhCuC+XN+r/bBCmeuuJtjz+bCNIf8= | ||
github.com/chzyer/readline v0.0.0-20180603132655-2972be24d48e/go.mod h1:nSuG5e5PlCu98SY8svDHJxuZscDgtXS6KTTbou5AhLI= | ||
github.com/chzyer/test v0.0.0-20180213035817-a1ea475d72b1/go.mod h1:Q3SI9o4m/ZMnBNeIyt5eFwwo7qiLfzFZmjNmxjkiQlU= | ||
github.com/cpuguy83/go-md2man/v2 v2.0.2/go.mod h1:tgQtvFlXSQOSOSIRvRPT7W67SCa46tRHOmNcaadrF8o= | ||
github.com/davecgh/go-spew v1.1.0/go.mod h1:J7Y8YcW2NihsgmVo/mv3lAwl/skON4iLHjSsI+c5H38= | ||
github.com/google/go-cmp v0.5.8/go.mod h1:17dUlkBOakJ0+DkrSSNjCkIjxS6bF9zb3elmeNGIjoY= | ||
github.com/gorilla/websocket v1.5.0 h1:PPwGk2jz7EePpoHN/+ClbZu8SPxiqlu12wZP/3sWmnc= | ||
github.com/gorilla/websocket v1.5.0/go.mod h1:YR8l580nyteQvAITg2hZ9XVh4b55+EU/adAjf1fMHhE= | ||
github.com/inconshreveable/mousetrap v1.1.0 h1:wN+x4NVGpMsO7ErUn/mUI3vEoE6Jt13X2s0bqwp9tc8= | ||
github.com/inconshreveable/mousetrap v1.1.0/go.mod h1:vpF70FUmC8bwa3OWnCshd2FqLfsEA9PFc4w1p2J65bw= | ||
github.com/jmespath/go-jmespath v0.4.0 h1:BEgLn5cpjn8UN1mAw4NjwDrS35OdebyEtFe+9YPoQUg= | ||
github.com/jmespath/go-jmespath v0.4.0/go.mod h1:T8mJZnbsbmF+m6zOOFylbeCJqk5+pHWvzYPziyZiYoo= | ||
github.com/jmespath/go-jmespath/internal/testify v1.5.1/go.mod h1:L3OGu8Wl2/fWfCI6z80xFu9LTZmf1ZRjMHUOPmWr69U= | ||
github.com/manifoldco/promptui v0.9.0 h1:3V4HzJk1TtXW1MTZMP7mdlwbBpIinw3HztaIlYthEiA= | ||
github.com/manifoldco/promptui v0.9.0/go.mod h1:ka04sppxSGFAtxX0qhlYQjISsg9mR4GWtQEhdbn6Pgg= | ||
github.com/pmezard/go-difflib v1.0.0/go.mod h1:iKH77koFhYxTK1pcRnkKkqfTogsbg7gZNVY4sRDYZ/4= | ||
github.com/russross/blackfriday/v2 v2.1.0/go.mod h1:+Rmxgy9KzJVeS9/2gXHxylqXiyQDYRxCVz55jmeOWTM= | ||
github.com/spf13/cobra v1.7.0 h1:hyqWnYt1ZQShIddO5kBpj3vu05/++x6tJ6dg8EC572I= | ||
github.com/spf13/cobra v1.7.0/go.mod h1:uLxZILRyS/50WlhOIKD7W6V5bgeIt+4sICxh6uRMrb0= | ||
github.com/spf13/pflag v1.0.5 h1:iy+VFUOCP1a+8yFto/drg2CJ5u0yRoB7fZw3DKv/JXA= | ||
github.com/spf13/pflag v1.0.5/go.mod h1:McXfInJRrz4CZXVZOBLb0bTZqETkiAhM9Iw0y3An2Bg= | ||
github.com/stretchr/objx v0.1.0/go.mod h1:HFkY916IF+rwdDfMAkV7OtwuqBVzrE8GR6GFx+wExME= | ||
golang.org/x/sync v0.3.0 h1:ftCYgMx6zT/asHUrPw8BLLscYtGznsLAnjq5RH9P66E= | ||
golang.org/x/sync v0.3.0/go.mod h1:FU7BRWz2tNW+3quACPkgCx/L+uEAv1htQ0V83Z9Rj+Y= | ||
golang.org/x/sys v0.0.0-20181122145206-62eef0e2fa9b h1:MQE+LT/ABUuuvEZ+YQAMSXindAdUh7slEmAkup74op4= | ||
golang.org/x/sys v0.0.0-20181122145206-62eef0e2fa9b/go.mod h1:STP8DvDyc/dI5b8T5hshtkjS+E42TnysNCUPdjciGhY= | ||
gopkg.in/check.v1 v0.0.0-20161208181325-20d25e280405/go.mod h1:Co6ibVJAznAaIkqp8huTwlJQCZ016jof/cbN4VW5Yz0= | ||
gopkg.in/yaml.v2 v2.2.8/go.mod h1:hI93XBmqTisBFMUTm0b8Fm+jr3Dg1NNxqwp+5A1VGuI= | ||
gopkg.in/yaml.v3 v3.0.1/go.mod h1:K4uyk7z7BCEPqu6E+C64Yfv1cQ7kz7rIZviUmN+EgEM= |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,57 @@ | ||
package main | ||
|
||
import ( | ||
"context" | ||
"fmt" | ||
"github.com/aws/aws-sdk-go-v2/config" | ||
"github.com/aws/aws-sdk-go-v2/service/rds" | ||
"github.com/spf13/cobra" | ||
) | ||
|
||
func main() { | ||
rootCmd := &cobra.Command{ | ||
RunE: runList, | ||
} | ||
|
||
proxyCmd := &cobra.Command{ | ||
Use: "proxy", | ||
Aliases: []string{"p"}, | ||
RunE: runProxy, | ||
} | ||
|
||
proxyCmd.PersistentFlags().String("endpoint-id", "", "") | ||
proxyCmd.PersistentFlags().Int("local-port", 0, "") | ||
|
||
rootCmd.AddCommand(proxyCmd) | ||
|
||
ctx := context.Background() | ||
err := rootCmd.ExecuteContext(ctx) | ||
if err != nil { | ||
panic(fmt.Sprintf("%+v", err)) | ||
} | ||
} | ||
|
||
func runList(cmd *cobra.Command, args []string) error { | ||
ctx := cmd.Context() | ||
|
||
cfg, err := config.LoadDefaultConfig(ctx) | ||
if err != nil { | ||
return fmt.Errorf(": %w", err) | ||
} | ||
|
||
rdsapi := rds.NewFromConfig(cfg) | ||
|
||
p := rds.NewDescribeDBInstancesPaginator(rdsapi, &rds.DescribeDBInstancesInput{}) | ||
for p.HasMorePages() { | ||
page, err := p.NextPage(ctx) | ||
if err != nil { | ||
return fmt.Errorf(": %w", err) | ||
} | ||
|
||
for _, instance := range page.DBInstances { | ||
fmt.Fprintln(cmd.OutOrStdout(), *instance.DBInstanceIdentifier) | ||
} | ||
} | ||
|
||
return nil | ||
} |
Oops, something went wrong.