From 0371a810e7067f710ea805eb5651167da7dca7e6 Mon Sep 17 00:00:00 2001 From: Khalim Conn-Kowlessar Date: Thu, 24 Aug 2023 13:17:19 +0100 Subject: [PATCH] adding custom domain back into serverless script --- backend/README.md | 132 ++++++++++++++++++++++++++++++---------------- serverless.yml | 14 ++--- 2 files changed, 95 insertions(+), 51 deletions(-) diff --git a/backend/README.md b/backend/README.md index 70739265..fa1d0068 100644 --- a/backend/README.md +++ b/backend/README.md @@ -198,60 +198,104 @@ mapped to the appropriate API stage. Remember to replace api and the CloudFront domain with your actual subdomain and CloudFront domain. -### Thoughts for authenticating the frontend with the backend +Certainly! Here's a detailed documentation for your README: -To provide secure communication between your frontend Next.js application and your backend FastAPI service, you have -several options. Here are a few popular approaches: +* * * -- JWT (JSON Web Tokens): Since you're already using JWT for authentication in the frontend, you can also use this to - authenticate requests to your FastAPI backend. This involves passing the JWT token in the Authorization header of the - request from your frontend to the backend. Then, you can use a JWT decoder on the backend to validate the token. This - can be done using libraries such as PyJWT in your FastAPI application. +Deployment Troubleshooting for `fastapi-lambda` +----------------------------------------------- -- API Keys: This is another common approach where you issue unique keys for each user/service that needs to access the - backend API. Each API call then includes this key in the request header. FastAPI can easily validate these keys. While - this approach is simpler than JWT, it provides less flexibility and security, as it doesn't allow for claims or - scopes. +### Context: -- OAuth2.0: OAuth2 is a protocol that allows applications to request authorization to access resources on behalf of a - user. FastAPI has direct support for OAuth2 using the OAuth2PasswordBearer class, which can be used for issuing access - tokens to clients. Note that this could be overkill if you're already using JWT and the calls to your backend are not - on behalf of a user. +When deploying the `fastapi-lambda` using Serverless Framework, you may encounter issues related to domain management, +especially if you're using a custom domain for your API. This documentation provides troubleshooting steps and details +on how to resolve potential conflicts. -- Mutual TLS (mTLS): Mutual TLS is a method of two-way communication encryption where both client and server - authenticate each other. This can be more complex to setup but can provide an additional layer of security in some - scenarios. +### Potential Issues & Solutions: -No matter which method we choose, you should always serve your applications over HTTPS to ensure that all data, -including tokens or keys, is encrypted during transmission. -Also, ensure that you handle the JWT tokens carefully, especially if they are stored in the client's browser, as they -could be vulnerable to Cross-Site Scripting (XSS) or Cross-Site Request Forgery (CSRF) attacks. Consider httpOnly -cookies for storing tokens if your use case allows it. +#### 1\. Conflict with Existing CloudFront Distribution: -### I think that we could use both JWT + API Key. +**Error Message**: -# Notes: +csharpCopy code -Using both JWT and API keys can provide an additional layer of security and -could be a good approach for our requirements. +`One or more aliases specified for the distribution includes an incorrectly configured DNS record that points to another CloudFront distribution.` -1. JSON Web Tokens (JWT) are useful for carrying user context between services. With JWT, you can embed user-specific - data (like user ID, roles, permissions, etc.) in a secure, tamper-proof token. This can be validated by your FastAPI - backend to authenticate and authorize the user. -2. -3. API Keys can serve as an identifier for the client application (in this case, your Next.js frontend). It can provide - a straightforward way to track and control how the client application is calling the backend API. +**Cause**: This can occur if there's an existing CNAME record in your DNS provider pointing to a CloudFront +distribution. -Here's a rough workflow of how these can be used together: +**Solution**: -A user logs in to the Next.js frontend using NextAuth and receives a JWT. -This JWT is stored securely in the client's browser. -For each request from the frontend to the backend, the JWT is included in the Authorization header. -In addition to the JWT, an API key unique to the frontend application is included in each request (possibly in a custom -header like X-API-Key). -The backend service validates both the JWT (for user authentication and authorization) and the API key (for client -application validation). -This approach provides a double check for each request: +* Check your DNS provider (e.g., Google Domains) and verify the CNAME record for `api.dev.hestia.homes`. +* Temporarily remove or update the conflicting CNAME record. +* Run the `sls create_domain` command again. +* Update the DNS settings in your DNS provider based on the new configuration provided by + the `serverless-domain-manager` plugin. + +#### 2\. Conflict with Route53: + +**Error Message**: + +csharpCopy code + +`Deleting RestApi failed. Please remove all base path mappings related to the RestApi in your domains.` + +**Cause**: This can occur if there are residual AWS configurations, especially in Route53, from previous deployments. + +**Solution**: + +* Navigate to the AWS Route53 Console. +* Identify and delete any residual Hosted Zones or Record Sets related to `api.dev.hestia.homes`. +* Ensure that you have backed up any necessary configurations before deleting. + +#### 3\. Other AWS Resources Conflicts: + +You might encounter issues where AWS resources, such as S3 buckets or CloudFront distributions, are not properly deleted +or are conflicting with new deployments. + +**Solution**: + +* Navigate to the respective AWS service dashboard. +* Manually identify and rectify any conflicting resources. This might involve emptying S3 buckets or deleting CloudFront + distributions. +* Ensure backups and proper precautions before deleting any resources. + +### Additional Notes: + +* **Backup Configurations**: Always backup your configurations before making changes. This ensures that you can revert + to a previous state if needed. +* **DNS Propagation**: Remember that DNS changes can take some time to propagate globally. After making DNS changes, you + might not see immediate effects. +* **CloudFront Distributions**: If you can't find a CloudFront distribution in the AWS CloudFront console, it's possible + that it was automatically created by another AWS service like API Gateway. It might need to be managed or deleted from + that service's dashboard. + +### After succesfully running creating the custom domain + +After successfully creating the custom domain with the `serverless-domain-manager` plugin, you should add back the CNAME +record into Google Domains (or whatever platform is being used to manage domains now) +to ensure that the custom domain properly points to the CloudFront distribution managed by +AWS. + +Here's what you should do: + +1. **Log in to Google Domains**: + + * Go to [Google Domains](https://domains.google.com/). + * Navigate to the management page for `hestia.homes`. +2. **Add/Update the CNAME Record**: + + * Find the section for custom resource records. + * Add (or update if it already exists) a CNAME record for `api.dev`. + * Point it to the CloudFront distribution domain name (e.g., `d2d269kjy1nyhz.cloudfront.net.`). Ensure you include + the trailing dot at the end. This can be found in API gateway +3. **Check DNS Propagation**: + + * Keep in mind that DNS changes might take some time to propagate. You can use online tools + like [DNS Checker](https://www.dnschecker.org/) to verify the propagation status worldwide. + * Test your API endpoint `api.dev.hestia.homes` to ensure it's resolving correctly and accessing your Lambda + function. + +By following these steps, you should have your custom domain properly configured and pointing to your AWS Lambda +function via the CloudFront distribution. -The JWT verifies that the request comes from a legitimate, authenticated user. -The API key verifies that the request comes from a trusted client application. \ No newline at end of file diff --git a/serverless.yml b/serverless.yml index 6ee356cc..89eb666a 100644 --- a/serverless.yml +++ b/serverless.yml @@ -32,14 +32,14 @@ provider: - arn:aws:s3:::${env:PLAN_TRIGGER_BUCKET}/* -#plugins: -# - serverless-domain-manager +plugins: + - serverless-domain-manager -#custom: -# customDomain: -# domainName: api.${self:provider.environment.DOMAIN_NAME} -# createRoute53Record: true -# certificateArn: ${ssm:/ssl_certificate_arn} +custom: + customDomain: + domainName: api.${self:provider.environment.DOMAIN_NAME} + createRoute53Record: true + certificateArn: ${ssm:/ssl_certificate_arn} functions: app: