Skip to content
This repository has been archived by the owner on Aug 16, 2022. It is now read-only.

Fix call to ListAccounts in a non-org user #337

Merged
merged 4 commits into from
Dec 8, 2021
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
17 changes: 9 additions & 8 deletions client/client.go
Original file line number Diff line number Diff line change
Expand Up @@ -62,8 +62,9 @@ import (
"github.com/aws/aws-sdk-go-v2/service/sts"
"github.com/aws/aws-sdk-go-v2/service/waf"
"github.com/aws/aws-sdk-go-v2/service/wafv2"
"github.com/cloudquery/cq-provider-sdk/provider/schema"
"github.com/hashicorp/go-hclog"

"github.com/cloudquery/cq-provider-sdk/provider/schema"
)

// Provider Client passed as meta to all table fetchers
Expand Down Expand Up @@ -175,7 +176,7 @@ func (s *ServicesManager) InitServicesForAccountAndRegion(accountId string, regi
type Client struct {
// Those are already normalized values after configure and this is why we don't want to hold
// config directly.
accounts []Account
Accounts []Account
regions []string
logLevel *string
maxRetries int
Expand Down Expand Up @@ -212,12 +213,12 @@ func NewAwsClient(logger hclog.Logger, accounts []Account, regions []string) Cli
services: ServicesAccountRegionMap{},
},
logger: logger,
accounts: accounts,
Accounts: accounts,
regions: regions,
}
}
func (c *Client) Logger() hclog.Logger {
return &awsLogger{c.logger, c.accounts}
return &awsLogger{c.logger, c.Accounts}
}

func (c *Client) Services() *Services {
Expand All @@ -226,7 +227,7 @@ func (c *Client) Services() *Services {

func (c *Client) withAccountID(accountID string) *Client {
return &Client{
accounts: c.accounts,
Accounts: c.Accounts,
regions: c.regions,
logLevel: c.logLevel,
maxRetries: c.maxRetries,
Expand All @@ -241,7 +242,7 @@ func (c *Client) withAccountID(accountID string) *Client {

func (c *Client) withAccountIDAndRegion(accountID, region string) *Client {
return &Client{
accounts: c.accounts,
Accounts: c.Accounts,
regions: c.regions,
logLevel: c.logLevel,
maxRetries: c.maxRetries,
Expand All @@ -256,7 +257,7 @@ func (c *Client) withAccountIDAndRegion(accountID, region string) *Client {

func (c *Client) withAccountIDRegionAndNamespace(accountID, region, namespace string) *Client {
return &Client{
accounts: c.accounts,
Accounts: c.Accounts,
regions: c.regions,
logLevel: c.logLevel,
maxRetries: c.maxRetries,
Expand Down Expand Up @@ -369,7 +370,7 @@ func Configure(logger hclog.Logger, providerConfig interface{}) (schema.ClientMe
// set default
client.AccountID = *output.Account
client.Region = client.regions[0]
client.accounts = append(client.accounts, Account{ID: *output.Account, RoleARN: *output.Arn})
client.Accounts = append(client.Accounts, Account{ID: *output.Account, RoleARN: *output.Arn})
}
for _, region := range client.regions {
client.ServicesManager.InitServicesForAccountAndRegion(*output.Account, region, initServices(region, awsCfg))
Expand Down
11 changes: 6 additions & 5 deletions client/errors.go
Original file line number Diff line number Diff line change
Expand Up @@ -5,6 +5,7 @@ import (
"fmt"

"github.com/aws/smithy-go"

"github.com/cloudquery/cq-provider-sdk/provider/schema"
"github.com/cloudquery/cq-provider-sdk/provider/schema/diag"
)
Expand All @@ -16,30 +17,30 @@ func ErrorClassifier(meta schema.ClientMeta, resourceName string, err error) []d
switch ae.ErrorCode() {
case "AccessDenied", "AccessDeniedException", "UnauthorizedOperation", "AuthorizationError":
return []diag.Diagnostic{
diag.FromError(err, diag.WARNING, diag.ACCESS, resourceName, parseSummaryMessage(client.accounts, err, ae), errorCodeDescriptions[ae.ErrorCode()]),
diag.FromError(err, diag.WARNING, diag.ACCESS, resourceName, ParseSummaryMessage(client.Accounts, err, ae), errorCodeDescriptions[ae.ErrorCode()]),
}
case "OptInRequired", "SubscriptionRequiredException", "InvalidClientTokenId":
return []diag.Diagnostic{
diag.FromError(err, diag.WARNING, diag.ACCESS, resourceName, parseSummaryMessage(client.accounts, err, ae), errorCodeDescriptions[ae.ErrorCode()]),
diag.FromError(err, diag.WARNING, diag.ACCESS, resourceName, ParseSummaryMessage(client.Accounts, err, ae), errorCodeDescriptions[ae.ErrorCode()]),
}
case "InvalidAction":
return []diag.Diagnostic{
diag.FromError(err, diag.IGNORE, diag.RESOLVING, resourceName, parseSummaryMessage(client.accounts, err, ae),
diag.FromError(err, diag.IGNORE, diag.RESOLVING, resourceName, ParseSummaryMessage(client.Accounts, err, ae),
"The action is invalid for the service."),
}
}
}
if IsErrorThrottle(err) {
return []diag.Diagnostic{
diag.FromError(err, diag.WARNING, diag.THROTTLE, resourceName, parseSummaryMessage(client.accounts, err, ae),
diag.FromError(err, diag.WARNING, diag.THROTTLE, resourceName, ParseSummaryMessage(client.Accounts, err, ae),
"CloudQuery AWS provider has been throttled, increase max_retries/retry_timeout in provider configuration."),
}
}

return nil
}

func parseSummaryMessage(aa []Account, err error, apiErr smithy.APIError) string {
func ParseSummaryMessage(aa []Account, err error, apiErr smithy.APIError) string {
for {
if op, ok := err.(*smithy.OperationError); ok {
return fmt.Sprintf("%s: %s - %s", op.Service(), op.Operation(), accountObfusactor(aa, apiErr.ErrorMessage()))
Expand Down
10 changes: 9 additions & 1 deletion resources/organizations_accounts.go
Original file line number Diff line number Diff line change
Expand Up @@ -2,11 +2,16 @@ package resources

import (
"context"
"errors"

"github.com/aws/aws-sdk-go-v2/aws"
"github.com/aws/aws-sdk-go-v2/service/organizations"
"github.com/aws/aws-sdk-go-v2/service/organizations/types"

"github.com/cloudquery/cq-provider-aws/client"

"github.com/cloudquery/cq-provider-sdk/provider/schema"
"github.com/cloudquery/cq-provider-sdk/provider/schema/diag"
)

func OrganizationsAccounts() *schema.Table {
Expand Down Expand Up @@ -74,8 +79,11 @@ func fetchOrganizationsAccounts(ctx context.Context, meta schema.ClientMeta, par
var input organizations.ListAccountsInput
for {
response, err := svc.ListAccounts(ctx, &input)
var ade *types.AccessDeniedException
if errors.As(err, &ade) {
return diag.FromError(err, diag.IGNORE, diag.ACCESS, OrganizationsAccounts().Name, client.ParseSummaryMessage(c.Accounts, err, ade), "Missing permissions or account might not be root/organizational unit.")
}
if err != nil {
meta.Logger().Warn("missing permissions or account might not be root/organizational unit", "account", c.AccountID)
return err
}
res <- response.Accounts
Expand Down