I have this simple form executed into React page:
import React, {useState} from 'react';
import { Link } from 'react-router-dom';
import {LambdaClient, InvokeCommand, LogType} from "@aws-sdk/client-lambda"; // ES Modules import
const { fromTemporaryCredentials } = require("@aws-sdk/credential-providers");
const FooterOne = ({ footerLight, style, footerGradient }) => {
const handleSubmit = async (event) => {
event.preventDefault();
const credentials = await fromTemporaryCredentials({
params: {
RoleArn: "arn:aws:lambda:us-east-1:123456789:function:email-submit",
},
clientConfig: {
region: 'us-west-2',
},
})();
try {
const client = new LambdaClient({
region: 'us-west-2',
credentials,
});
const command = new InvokeCommand({
FunctionName: "email-submit",
Payload: JSON.stringify("payload"),
LogType: LogType.Tail,
});
const { Payload, LogResult } = await client.send(command);
const result = Buffer.from(Payload).toString();
const logs = Buffer.from(LogResult, "base64").toString();
return { logs, result };
} catch (error) {
console.error('Error invoking function:', error);
// Handle errors as needed
}
};
return (
<>
<form onSubmit={handleSubmit}>
<input
type='text'
placeholder='Enter your email'
name='email'
required=''
autoComplete='off'
/>
<input
type='submit'
value='Subscribe'
data-wait='Please wait...'
/>
</form>
</>
);
};
export default FooterOne;
Lambda code into AWS Lambda:
export const handler = async (event) => {
// TODO implement
const response = {
statusCode: 200,
body: JSON.stringify('Hello from Lambda!'),
};
return response;
};
But I get error:
Uncaught (in promise) Error: Credential is missing
at SignatureV4.credentialProvider (runtimeConfig.browser.js:22:1)
at SignatureV4.signRequest (SignatureV4.js:103:1)
at SignatureV4.sign (SignatureV4.js:58:1)
at awsAuthMiddleware.js:24:1
at async retryMiddleware.js:27:1
at async loggerMiddleware.js:3:1
at async fromTemporaryCredentials.js:20:1
at async handleSubmit (FooterOne.js:12:1)
Do you know how I can fix this issue?
2
Answers
Sounds like you haven’t got your AWS .credentials setup. aka. pseudo username/password kind of stuff.
Google it. (I know it’s complex, I’m not being flippant, but it’s just one of those annoying thing you need to know about how AWS .Credentials Files work)
You need to be providing authentication details that your code can use to prove it has permission to access the service your code is trying to talk to to so that it can access. aka. something like this;
Honestly, it’s no different than phoning your bank. The Bank being your Code in this context.
They aren’t going to talk to you until you can prove your identity and that you are authorised to speak to them.
Your code is you. You on the phone. Think like you, as code.
Figure this out, and you’ll solve your own problem.
I see a Role ARN in your code inside
fromTemporaryCredentials
method, which your application assumes and gets the credential against.So essentially, you just need to give this IAM Role
arn:aws:lambda:us-east-1:12345678:function:email-submit
enough permissions to invoke your Lambda function.No need to create an additional IAM Role. Just try by attaching
AWSLambda_FullAccess
managed policy to this role. If it works, then you can create a new policy with the principle of least privilege.