Commit 84533050 authored by Enrique Alcántara's avatar Enrique Alcántara

Merge branch 'sh-eks-error-feedback' into 'master'

EKS: Provide user feedback on AWS authorization errors

See merge request gitlab-org/gitlab!49278
parents b789ef26 d82ba249
...@@ -42,7 +42,13 @@ export const createRole = ({ dispatch, state: { createRolePath } }, payload) => ...@@ -42,7 +42,13 @@ export const createRole = ({ dispatch, state: { createRolePath } }, payload) =>
dispatch('createRoleSuccess', awsData); dispatch('createRoleSuccess', awsData);
}) })
.catch(error => dispatch('createRoleError', { error })); .catch(error => {
let message = error;
if (error?.response?.data?.message) {
message = error.response.data.message;
}
dispatch('createRoleError', { error: message });
});
}; };
export const requestCreateRole = ({ commit }) => { export const requestCreateRole = ({ commit }) => {
......
...@@ -29,7 +29,7 @@ module Clusters ...@@ -29,7 +29,7 @@ module Clusters
rescue *ERRORS => e rescue *ERRORS => e
Gitlab::ErrorTracking.track_exception(e) Gitlab::ErrorTracking.track_exception(e)
Response.new(:unprocessable_entity, {}) Response.new(:unprocessable_entity, response_details(e))
end end
private private
...@@ -47,6 +47,28 @@ module Clusters ...@@ -47,6 +47,28 @@ module Clusters
def credentials def credentials
Clusters::Aws::FetchCredentialsService.new(role).execute Clusters::Aws::FetchCredentialsService.new(role).execute
end end
def response_details(exception)
message =
case exception
when ::Aws::STS::Errors::AccessDenied
_("Access denied: %{error}") % { error: exception.message }
when ::Aws::STS::Errors::ServiceError
_("AWS service error: %{error}") % { error: exception.message }
when ActiveRecord::RecordNotFound
_("Error: Unable to find AWS role for current user")
when ActiveRecord::RecordInvalid
exception.message
when Clusters::Aws::FetchCredentialsService::MissingRoleError
_("Error: No AWS provision role found for user")
when ::Aws::Errors::MissingCredentialsError
_("Error: No AWS credentials were supplied")
else
_('An error occurred while authorizing your role')
end
{ message: message }.compact
end
end end
end end
end end
---
title: 'EKS: Provide user feedback on AWS authorization errors'
merge_request: 49278
author:
type: changed
...@@ -1334,6 +1334,9 @@ msgstr "" ...@@ -1334,6 +1334,9 @@ msgstr ""
msgid "AWS Secret Access Key. Only required if not using role instance credentials" msgid "AWS Secret Access Key. Only required if not using role instance credentials"
msgstr "" msgstr ""
msgid "AWS service error: %{error}"
msgstr ""
msgid "Abort" msgid "Abort"
msgstr "" msgstr ""
...@@ -1373,6 +1376,9 @@ msgstr "" ...@@ -1373,6 +1376,9 @@ msgstr ""
msgid "Access denied! Please verify you can add deploy keys to this repository." msgid "Access denied! Please verify you can add deploy keys to this repository."
msgstr "" msgstr ""
msgid "Access denied: %{error}"
msgstr ""
msgid "Access expiration date" msgid "Access expiration date"
msgstr "" msgstr ""
...@@ -3042,6 +3048,9 @@ msgstr "" ...@@ -3042,6 +3048,9 @@ msgstr ""
msgid "An error occurred while adding formatted title for epic" msgid "An error occurred while adding formatted title for epic"
msgstr "" msgstr ""
msgid "An error occurred while authorizing your role"
msgstr ""
msgid "An error occurred while checking group path. Please refresh and try again." msgid "An error occurred while checking group path. Please refresh and try again."
msgstr "" msgstr ""
...@@ -11082,9 +11091,18 @@ msgstr "" ...@@ -11082,9 +11091,18 @@ msgstr ""
msgid "Error: %{error_message}" msgid "Error: %{error_message}"
msgstr "" msgstr ""
msgid "Error: No AWS credentials were supplied"
msgstr ""
msgid "Error: No AWS provision role found for user"
msgstr ""
msgid "Error: Unable to create deploy freeze" msgid "Error: Unable to create deploy freeze"
msgstr "" msgstr ""
msgid "Error: Unable to find AWS role for current user"
msgstr ""
msgid "ErrorTracking|Active" msgid "ErrorTracking|Active"
msgstr "" msgstr ""
......
...@@ -186,7 +186,7 @@ describe('EKS Cluster Store Actions', () => { ...@@ -186,7 +186,7 @@ describe('EKS Cluster Store Actions', () => {
role_external_id: payload.externalId, role_external_id: payload.externalId,
region: DEFAULT_REGION, region: DEFAULT_REGION,
}) })
.reply(400, error); .reply(400, null);
}); });
it('dispatches createRoleError action', () => it('dispatches createRoleError action', () =>
...@@ -198,6 +198,32 @@ describe('EKS Cluster Store Actions', () => { ...@@ -198,6 +198,32 @@ describe('EKS Cluster Store Actions', () => {
[{ type: 'requestCreateRole' }, { type: 'createRoleError', payload: { error } }], [{ type: 'requestCreateRole' }, { type: 'createRoleError', payload: { error } }],
)); ));
}); });
describe('when request fails with a message', () => {
beforeEach(() => {
const errResp = { message: 'Something failed' };
mock
.onPost(state.createRolePath, {
role_arn: payload.roleArn,
role_external_id: payload.externalId,
region: DEFAULT_REGION,
})
.reply(4, errResp);
});
it('dispatches createRoleError action', () =>
testAction(
actions.createRole,
payload,
state,
[],
[
{ type: 'requestCreateRole' },
{ type: 'createRoleError', payload: { error: 'Something failed' } },
],
));
});
}); });
describe('requestCreateRole', () => { describe('requestCreateRole', () => {
......
...@@ -40,7 +40,7 @@ RSpec.describe Clusters::Aws::AuthorizeRoleService do ...@@ -40,7 +40,7 @@ RSpec.describe Clusters::Aws::AuthorizeRoleService do
shared_examples 'bad request' do shared_examples 'bad request' do
it 'returns an empty hash' do it 'returns an empty hash' do
expect(subject.status).to eq(:unprocessable_entity) expect(subject.status).to eq(:unprocessable_entity)
expect(subject.body).to eq({}) expect(subject.body).to eq({ message: message })
end end
it 'logs the error' do it 'logs the error' do
...@@ -52,12 +52,14 @@ RSpec.describe Clusters::Aws::AuthorizeRoleService do ...@@ -52,12 +52,14 @@ RSpec.describe Clusters::Aws::AuthorizeRoleService do
context 'role does not exist' do context 'role does not exist' do
let(:user) { create(:user) } let(:user) { create(:user) }
let(:message) { 'Error: Unable to find AWS role for current user' }
include_examples 'bad request' include_examples 'bad request'
end end
context 'supplied ARN is invalid' do context 'supplied ARN is invalid' do
let(:role_arn) { 'invalid' } let(:role_arn) { 'invalid' }
let(:message) { 'Validation failed: Role arn must be a valid Amazon Resource Name' }
include_examples 'bad request' include_examples 'bad request'
end end
...@@ -69,18 +71,29 @@ RSpec.describe Clusters::Aws::AuthorizeRoleService do ...@@ -69,18 +71,29 @@ RSpec.describe Clusters::Aws::AuthorizeRoleService do
context 'error fetching credentials' do context 'error fetching credentials' do
let(:error) { Aws::STS::Errors::ServiceError.new(nil, 'error message') } let(:error) { Aws::STS::Errors::ServiceError.new(nil, 'error message') }
let(:message) { 'AWS service error: error message' }
include_examples 'bad request'
end
context 'error in assuming role' do
let(:raw_message) { "User foo is not authorized to perform: sts:AssumeRole on resource bar" }
let(:error) { Aws::STS::Errors::AccessDenied.new(nil, raw_message) }
let(:message) { "Access denied: #{raw_message}" }
include_examples 'bad request' include_examples 'bad request'
end end
context 'credentials not configured' do context 'credentials not configured' do
let(:error) { Aws::Errors::MissingCredentialsError.new('error message') } let(:error) { Aws::Errors::MissingCredentialsError.new('error message') }
let(:message) { "Error: No AWS credentials were supplied" }
include_examples 'bad request' include_examples 'bad request'
end end
context 'role not configured' do context 'role not configured' do
let(:error) { Clusters::Aws::FetchCredentialsService::MissingRoleError.new('error message') } let(:error) { Clusters::Aws::FetchCredentialsService::MissingRoleError.new('error message') }
let(:message) { "Error: No AWS provision role found for user" }
include_examples 'bad request' include_examples 'bad request'
end end
......
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment