import {RivendellApi} from './RivendellApi'; import {MoriaApi} from './MoriaApi'; import RivendellApiError = RivendellApi.ApiError; import MoriaApiError = MoriaApi.ApiError; export function formatError(error: Error) { if (error instanceof RivendellApiError) { if (error.response?.status === 403) { return 'Could not authenticate with the credential configured in ~/.opti/credentials.json.'; } else { return sanitize(errorMessageFromJsonResponse(error)); } } else if (error instanceof MoriaApiError) { return sanitize(errorMessageFromJsonResponse(error)); } else { return sanitize(error.message); } } function errorMessageFromJsonResponse(error: MoriaApiError | RivendellApiError) { const contentType = error.response?.headers?.get('content-type'); if (contentType?.includes('application/json') && error.responseText) { const response = JSON.parse(error.responseText); // protocol is that detail will have either a `message` or an `invalids` child if (response.detail) { return response.detail.message ? response.detail.message : response.detail.invalids .map((violation: { [key: string]: string }) => `* ${violation.field} ${violation.reason}`) .join('\n'); } } return error.message; } function sanitize(body: any) { return body.replace('FAILED_PRECONDITION: ', '').replace('INTERNAL: ', ''); }