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

Question about Origins #23

Closed
picosam opened this issue Feb 15, 2020 · 10 comments
Closed

Question about Origins #23

picosam opened this issue Feb 15, 2020 · 10 comments

Comments

@picosam
Copy link

picosam commented Feb 15, 2020

Thanks a lot for such a complete and useful work! When looking at the example of reusing auth with my own Cloudfront distribution, I see the following:

        Origins:
          - DomainName: example.org
            Id: dummy-origin
            CustomOriginConfig:
              OriginProtocolPolicy: match-viewer
          - DomainName: example.com
            Id: protected-origin
            CustomOriginConfig:
              OriginProtocolPolicy: match-viewer

Are we supposed to replace example.org and example.com there with other values? Also, are we supposed to add our own S3 Bucket where we'll be deploying our SPA?

Thanks again,
Sammy

@ottokruse
Copy link
Collaborator

Hi @picosam ! Great to hear this is of use to you.

  • You should only replace "example.com" in the origin "protected-origin" with your own origin domain name (can be an S3 bucket too if that's what you wanna protect). Now that you mention it I see it is indeed confusing with the "dummy origin" example.ORG, I'll try to make that more clear.

  • The dummy origin "example.org" can remain there, as it is the origin behind the Lambda@Edge functions for parseAuth and such; they will always respond to the request instead of allowing the request to pass through to the origin. Hence "dummy origin", it is there because a CloudFront behavior needs to have an origin, but requests will never be forwarded to it.

  • Indeed if you set parameter "CreateCloudFrontDistribution" to false then you need to create the S3 Bucket yourself. I tried to explain that in the parameter description btw: "Set to 'false' to skip the creation of a CloudFront distribution and associated resources, such as the private S3 bucket and the sample React app. This may be of use to you, if you just want to create the Lambda@Edge functions to use with your own CloudFront distribution."

  • If you want a protected S3 bucket, you might as wel set "CreateCloudFrontDistribution" to true, then you'll get an S3 bucket with a sample React app in it. You can just delete that React app and upload your own SPA/files to that S3 bucket.

Let me know if this clears things up.

@picosam
Copy link
Author

picosam commented Feb 19, 2020

Thank you very much @ottokruse, your response is clear and I believe your description was as well; I guess I just assumed incorrectly there was more to dummy-origin than that.

Your code is not only of use but very valuable to us: we're going to be using it to protect our Test and Staging environments, hence the need to use our own CloudFront Distributions. You do confirm that we can easily spin-off multiple SPA Distrubtions/Buckets without the lambda@edge functions being redeployed every time, right?

The thing is that (and I'm going to try and look into that today) I'll have to have a different User Pool for each "set" of Test/Staging environments though, to prevent different protected resources from being accessed by users who shouldn't be seeing them.

@ottokruse
Copy link
Collaborator

Great to hear that!

"You do confirm that we can easily spin-off multiple SPA Distrubtions/Buckets without the lambda@edge functions being redeployed every time, right?"

In the sample solution the userPoolId and such is added into the Lambda@Edge functions (configuration.json). So if you need to use different user pools you need different Lamda@Edge functions.

You can of course change the code, then you can do whatever.

The Lambda@Edge functions are configuration-wise not aware of the bucket they protect, nor of the CloudFront distribution they are used in. So you can re-use the Lambda@Edge functions for multiple S3 buckets/CloudFront distributions.

@picosam
Copy link
Author

picosam commented Feb 19, 2020

Ok, so I deployed with a pretty complex distribution and it all does work as intended :-)
I guess what I would like to try and change would be indeed to use the exact same Lambda@Edge functions and the same UserPool deployed with different (future) buckets/distributions.

The Lambda@Edge functions are configuration-wise not aware of the bucket they protect, nor of the CloudFront distribution they are used in.

Does that statement stand even relative to the redirect URLs after signing in/out?

@ottokruse
Copy link
Collaborator

The Lambda@Edge functions are aware of e.g. the special paths (signin/signout/parseauth/refreshauth), but not of the host (domain name) on which they are running. They grab the hostname from the incoming "Host" http header.

So as long as your CloudFront distributions use the same special paths, you could reuse the Lambda@Edge functions.

@ottokruse
Copy link
Collaborator

ottokruse commented Feb 20, 2020

BTW maybe you could solve your use case more easily by having one user pool, but putting the users in that pool into separate groups. Then, implement some sort of mapping between group and allowed origin. This will require you to change the Lambda@Edge code a bit, but having one user pool might be nicer, as users who are in multiple groups then only have to sign in once.

Update: excuse me, reading back I think you were going in this direction already.

@picosam
Copy link
Author

picosam commented Feb 20, 2020

Thank you! Yes, this is exactly what I'm trying to do: have one user pool -- except I thought I would need to create a different App Client per CloudFront distribution. What's stopping me is the following:

      Configuration: !Sub >
        {
          "userPoolId": "${UserPool}",
          "clientId": "${UserPoolClient}",
          "oauthScopes": ${OAuthScopes},
          "cognitoAuthDomain": "${UserPoolDomain.DomainName}",
          "redirectPathSignIn": "${RedirectPathSignIn}",
          "redirectPathSignOut": "${RedirectPathSignOut}",
          "redirectPathAuthRefresh": "${RedirectPathAuthRefresh}",
          "cookieSettings": ${CookieSettings},
          "httpHeaders": ${HttpHeaders}
        }

as it seems that the App Client ID is being saved "within" each lambda function and I'm looking for how to have that be "dynamic" somehow.

Again, thanks a lot for all this help.

@ottokruse
Copy link
Collaborator

Yeah probably implement some kind of mapping between domain names, groups and client id's.

{
  "domainNames": {
    "example.org": {
      "allowedCognitoGroups": [
        "them",
        "others"
      ],
      "clientId": "dfasgfagfasgfsdgsgf"
    },
   ...
  },
  ...
}

That'll be some fun coding, enjoy :)

@picosam
Copy link
Author

picosam commented Feb 20, 2020

Great. If you don't mind, I'm going to ask someone who works with me to contribute via pull requests.

@ottokruse
Copy link
Collaborator

Sure! Great.

Shall we close this issue for now?

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

No branches or pull requests

2 participants