Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Resource Access Manager - Errors unmarshalled incorrectly #2377

Closed
gazoakley opened this issue Dec 28, 2018 · 4 comments
Closed

Resource Access Manager - Errors unmarshalled incorrectly #2377

gazoakley opened this issue Dec 28, 2018 · 4 comments
Labels
service-api This issue is due to a problem in a service API, not the SDK implementation.

Comments

@gazoakley
Copy link

gazoakley commented Dec 28, 2018

Please fill out the sections below to help us address your issue.

Version of AWS SDK for Go?

1.16.9

Version of Go (go version)?

go version go1.11.1 darwin/amd64

What issue did you see?

Errors from RAM do not return a value for err.Code(). See the following response:

2018-12-28T14:55:49.649Z [DEBUG] plugin.terraform-provider-aws: ---[ RESPONSE ]--------------------------------------
2018-12-28T14:55:49.649Z [DEBUG] plugin.terraform-provider-aws: HTTP/2.0 400 Bad Request
2018-12-28T14:55:49.649Z [DEBUG] plugin.terraform-provider-aws: Content-Length: 170
2018-12-28T14:55:49.649Z [DEBUG] plugin.terraform-provider-aws: Content-Type: application/json
2018-12-28T14:55:49.649Z [DEBUG] plugin.terraform-provider-aws: Date: Fri, 28 Dec 2018 14:55:49 GMT
2018-12-28T14:55:49.649Z [DEBUG] plugin.terraform-provider-aws: Via: 1.1 adc13b6f5827d04caa2efba65479257c.cloudfront.net (CloudFront)
2018-12-28T14:55:49.649Z [DEBUG] plugin.terraform-provider-aws: X-Amz-Apigw-Id: Sn3qTErNjoEFnTQ=
2018-12-28T14:55:49.649Z [DEBUG] plugin.terraform-provider-aws: X-Amz-Cf-Id: cwDxF-FGx4aKlAzEDbGl6sLjWOV_gyJSXbkJIHd-9UD_Z5imkRpokg==
2018-12-28T14:55:49.649Z [DEBUG] plugin.terraform-provider-aws: X-Amzn-Requestid: xxxxxxxx-xxxx-xxxx-xxxx-xxxxxxxxxxxx
2018-12-28T14:55:49.649Z [DEBUG] plugin.terraform-provider-aws: X-Amzn-Trace-Id: Root=1-5c263975-f641f0296e96c23f7ca50b73;Sampled=0
2018-12-28T14:55:49.649Z [DEBUG] plugin.terraform-provider-aws: X-Cache: Error from cloudfront
2018-12-28T14:55:49.649Z [DEBUG] plugin.terraform-provider-aws: 
2018-12-28T14:55:49.649Z [DEBUG] plugin.terraform-provider-aws: 
2018-12-28T14:55:49.649Z [DEBUG] plugin.terraform-provider-aws: -----------------------------------------------------
2018-12-28T14:55:49.649Z [DEBUG] plugin.terraform-provider-aws: 2018/12/28 14:55:49 [DEBUG] [aws-sdk-go] {"__type":"UnknownResourceException","message":"ResourceShare arn:aws:ram:eu-west-1:xxxxxxxxxxxx:resource-share/xxxxxxxx-xxxx-xxxx-xxxx-xxxxxxxxxxxx could not be found."}
2018-12-28T14:55:49.649Z [DEBUG] plugin.terraform-provider-aws: 2018/12/28 14:55:49 [DEBUG] [aws-sdk-go] DEBUG: Validate Response RAM/GetResourceShares failed, not retrying, error : ResourceShare arn:aws:ram:eu-west-1:xxxxxxxxxxxx:resource-share/xxxxxxxx-xxxx-xxxx-xxxx-xxxxxxxxxxxx could not be found.
2018-12-28T14:55:49.649Z [DEBUG] plugin.terraform-provider-aws: 	status code: 400, request id: xxxxxxxx-xxxx-xxxx-xxxx-xxxxxxxxxxxx
2018-12-28T14:55:49.649Z [DEBUG] plugin.terraform-provider-aws: 2018/12/28 14:55:49 Error returned
2018-12-28T14:55:49.649Z [DEBUG] plugin.terraform-provider-aws: 2018/12/28 14:55:49 err.Code():
2018-12-28T14:55:49.649Z [DEBUG] plugin.terraform-provider-aws: 2018/12/28 14:55:49 err.Message(): ResourceShare arn:aws:ram:eu-west-1:xxxxxxxxxxxx:resource-share/xxxxxxxx-xxxx-xxxx-xxxx-xxxxxxxxxxxx could not be found.

The RAM API returns a JSON object of:

{
  "__type": "UnknownResourceException",
  "message": "ResourceShare arn:aws:ram:eu-west-1:xxxxxxxxxxxx:resource-share/xxxxxxxx-xxxx-xxxx-xxxx-xxxxxxxxxxxx could not be found."
}

I would expect the error object to have .Code() return UnknownResourceException, but it returns an empty string

Steps to reproduce

If you have an runnable example, please include it.

@gazoakley
Copy link
Author

This might be a service model/API issue. RAM is supposed to use the restjson protocol (which uses the attribute code), but their error JSON is modelled after that of jsonrpc (which uses the attribute __type)

@jasdel
Copy link
Contributor

jasdel commented Dec 28, 2018

Thanks for submitting this issue. We'll reach out to the service team to help address this issue. I think the service should be setting the X-Amzn-Errortype header with the error code value as well, which isn't being done.

@jasdel
Copy link
Contributor

jasdel commented Dec 28, 2018

As a short term workaround, until the service corrects the error format returned, you could temporarily swap out the SDK's error unmarshaler for this service replacing it with custom logic to extract the error code. (I'll look at adding this as a customization to the SDK as well for the RAM client)

Define a custom request unmarshal error request handler function. This custom unmarshaler will be compatible with the service when the fix is made on their end.

func custUnmarshalError(r *request.Request) {
	defer r.HTTPResponse.Body.Close()

	var jsonErr struct {
		Code string `json:"code"`
		Type string `json:"__type"`
		Message string `json:"message"`
	}

	if err := json.NewDecoder(r.HTTPResponse.Body).Decode(&jsonErr); err != nil {
		r.Error = awserr.NewRequestFailure(
			awserr.New("SerializationError", r.HTTPResponse.Status, nil),
			r.HTTPResponse.StatusCode,
			r.RequestID,
		)
		return
	}

	code := r.HTTPRequest.Header.Get("X-Amzn-Errortype")
	if len(code) == 0 {
		code = jsonErr.Code
	}
	if len(code) == 0 {
		code = jsonErr.Type
	}

	r.Error = awserr.NewRequestFailure(
		awserr.New(code, jsonErr.Message, nil),
		r.HTTPResponse.StatusCode,
		r.RequestID,
	)
}

When creating the client for RAM swap the restjson.UnmarshalErrorHandler with your custom handler.

svc := ram.New(sess)
svc.Handlers.UnmarshalError.Swap(
	restjson.UnmarshalErrorHandler.Name,
	request.NamedHandler{
		Name: "custom.unmarshalError",
		Fn: custUnmarshalError,
	},
)

@jasdel jasdel added the service-api This issue is due to a problem in a service API, not the SDK implementation. label Dec 28, 2018
jasdel added a commit to jasdel/aws-sdk-go that referenced this issue Jan 3, 2019
Updates SDK integration smoke test code generation to assert that error
codes are non-empty.

Related to aws#2377
jasdel added a commit that referenced this issue Jan 3, 2019
…#2383)

Updates SDK integration smoke test code generation to assert that error codes are non-empty.

Related to #2377
@jasdel
Copy link
Contributor

jasdel commented May 14, 2019

Closing this issue, as ACM corrected their error response message. The SDK's integration test also validate this as well in change, 29ae2fc.

@jasdel jasdel closed this as completed May 14, 2019
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
service-api This issue is due to a problem in a service API, not the SDK implementation.
Projects
None yet
Development

No branches or pull requests

2 participants