-
Notifications
You must be signed in to change notification settings - Fork 3.9k
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
(aws-lambda/aws-cloudfront): FunctionUrls cannot be added to cloudfront as a http origin #20090
Comments
Came here to request this. |
Awesome this fixed part of my problem! the other slightly weird behaviour was that having a switching to So here is a full example stack that now works import cdk from 'aws-cdk-lib';
import { App, CfnOutput } from 'aws-cdk-lib';
import cf from 'aws-cdk-lib/aws-cloudfront';
import origins from 'aws-cdk-lib/aws-cloudfront-origins';
import { NodejsFunction } from 'aws-cdk-lib/aws-lambda-nodejs';
import lambda from 'aws-cdk-lib/aws-lambda'
export class LfStack extends cdk.Stack {
constructor(scope, id, props) {
super(scope, id, props);
this.lambdaFunction = new NodejsFunction(this, 'Lambda', { entry: './echo.js', })
this.functionUrl = new lambda.FunctionUrl(this, 'LambdaApiUrl', {
function: this.lambdaFunction,
authType: lambda.FunctionUrlAuthType.NONE,
cors: {
allowedOrigins: ["*"],
allowedMethods: [lambda.HttpMethod.GET, lambda.HttpMethod.POST],
allowCredentials: true,
maxAge: cdk.Duration.minutes(1)
}
});
const splitFunctionUrl = cdk.Fn.select(2, cdk.Fn.split('/', this.functionUrl.url));
this.distribution = new cf.Distribution(this, 'Cloudfront', {
defaultBehavior: {
compress: true,
originRequestPolicy: cf.OriginRequestPolicy.CORS_CUSTOM_ORIGIN,
origin: new origins.HttpOrigin(splitFunctionUrl, {
protocolPolicy: cf.OriginProtocolPolicy.HTTPS_ONLY,
originSslProtocols: [cf.OriginSslPolicy.TLS_V1_2],
}),
viewerProtocolPolicy: cf.ViewerProtocolPolicy.HTTPS_ONLY,
allowedMethods: cf.AllowedMethods.ALLOW_ALL,
}
})
new CfnOutput(this, 'CloudfrontUrl', { value: this.distribution.distributionDomainName })
new CfnOutput(this, 'LambdaUrl', { value: this.functionUrl.url })
new CfnOutput(this, 'FunctionArn', { value: this.lambdaFunction.functionArn })
new CfnOutput(this, 'CfnSplitOutput', { value: splitFunctionUrl })
}
}
const app = new App();
new LfStack(app, 'LambdaHttp') where export async function handler(evt) {
console.log(evt)
return {
statusCode: 200, headers: { "Content-Type": "application/json" },
body: JSON.stringify({ "id": evt.requestContext.requestId, "status": 200, statusText: "Ok", path: evt.rawPath, query: evt.rawQueryString })
}
} |
You can use a custom policy like this: example custom request policy |
@blacha - The problem is that Lambda URLs are rejecting requests from CloudFront that have the Host header set to the edge host name and not to the Lambda URL host name. We were just talking to an AWS PM about this on Friday. Because Lambda URLs use exclusively HTTPS they do not need the Host header for multiplexing of many hosts on single IPs (they will use the SNI for that). But, currently, including the Host header causes the request to be rejected if it's not the Lambda URL hostname. Options:
Hope this helps. By the way... you can also sign the origin requests using SignatureV4 from CloudFront using an Origin Request Lambda @ Edge Function then enable AWS_IAM auth on your Lambda URLs. I have projects that are using this technique now, which is part of the reason why I ran into the Host header issue (which is similar for API Gateway). |
One other problem is that the |
@joshwand - It is possible to use Function URL IAM Auth with CloudFront and doing so allows the Function URL to be on the Internet but totally safe, just like all the AWS API endpoints that we use (expose to the Internet but protected with IAM Auth + Sigv4). What you have to do is sign the requests using Signature v4 via a Lambda @ Edge function. This technique works for both Function URLs and for API Gateway (or for any other non-S3 origin that supports IAM auth). It would be great if CloudFront allowed using Origin Access Identities for non-S3 origins, but it's been years since that was first requested and there must be some reason it's not been added yet. Signing with Sigv4 is not particularly difficult, but pulling the entire thing together can be a challenge (it took me about a week the first time around). The repo below is a 100% complete demonstration of how to sign the requests using a Lambda @ Edge Origin Request function and how to deploy all of it into either US-East-1 or other regions using a single CDK deployment that deploys a US-East-1 EdgeFunction child stack. https://github.com/pwrdrvr/lambda-url-signing I hope this helps you and others! Harold |
As this ticket has been resolved, it would be appropriate to close it. |
|
Describe the bug
When trying to connect a function url into a cloudfront distribution with a HttpOrigin fails
Expected Behavior
I would expect to be able to add a LambdaFunctionURL to Cloudfront
Current Behavior
Deployment fails
Reproduction Steps
Given a lambda and cloudfront distribution, trying to hook them together using a HttpOrigin
Possible Solution
No response
Additional Information/Context
I am assuming that HttpOrigin is how you would expect to connect these, I couldnt see anything in github/docs about how to connect a functionurl to cloudfront.
When creating the function url in the AWS Console then manually connecting them it works fine.
CDK CLI Version
2.21.1 (build a6ee543)
Framework Version
No response
Node.js Version
v16.14.2
OS
Ubuntu 22.04 LTS
Language
Typescript
Language Version
Javascript
Other information
No response
The text was updated successfully, but these errors were encountered: