-
Notifications
You must be signed in to change notification settings - Fork 22
Certificate Management for Multi-Tenant Applications on Qovery #569
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
Merged
Merged
Changes from 5 commits
Commits
Show all changes
11 commits
Select commit
Hold shift + click to select a range
fe35ce4
init doc files
Guimove e28281f
add guillaume author
Guimove ed69d56
add schemas
Guimove e8ef4a3
add images
Guimove 1d68fc6
Update team.toml
Guimove 5f3d34d
remove old user
Guimove bee3bb3
remove old user
Guimove d221621
fix Infrastructure wording
Guimove d0f6420
fix Infrastructure wording
Guimove f2f9cc2
Add mor deatil on the tenant service creation
Guimove c19ed5d
update schemas wording
Guimove File filter
Filter by extension
Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
There are no files selected for viewing
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
234 changes: 234 additions & 0 deletions
234
website/guides/tutorial/certificate_management_for_multi_tenant_infrastructure.md
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,234 @@ | ||
--- | ||
last_modified_on: "2025-08-08" | ||
$schema: "/.meta/.schemas/guides.json" | ||
title: Certificate Management for Multi-Tenant Applications on Qovery | ||
description: Learn how to implement robust SSL/TLS certificate management for multi-tenant SaaS applications using dedicated ingresses per tenant on Qovery | ||
author_github: https://github.com/guimove | ||
tags: ["type: tutorial", "technology: qovery"] | ||
hide_pagination: true | ||
--- | ||
import Alert from '@site/src/components/Alert'; | ||
import Assumptions from '@site/src/components/Assumptions'; | ||
import Jump from '@site/src/components/Jump'; | ||
|
||
Building multi-tenant applications where each customer has their own dedicated URL is a common pattern in SaaS platforms. While Qovery automatically handles TLS/SSL certificate creation and renewal for your custom domains, managing certificates at scale for multi-tenant architectures presents unique challenges. This guide will show you how to implement a robust certificate management strategy using dedicated ingresses for each tenant. | ||
|
||
<!-- | ||
THIS FILE IS AUTOGENERATED! | ||
To make changes please edit the template located at: | ||
website/guides/tutorial/certificate_management_for_multi_tenant_infrastructure.md.erb | ||
--> | ||
|
||
## **The Challenge** | ||
|
||
When building multi-tenant applications on Qovery, the default approach uses a single ingress controller to manage all custom domains for the service. This creates several issues: | ||
|
||
* **Certificate generation failures**: If validation fails for one domain, it can prevent certificate generation for all domains | ||
* **Deployment risks**: A single misconfigured domain can cause the entire deployment to fail | ||
* **Privacy concerns**: Customers can see other tenants' domains when inspecting the SSL certificate | ||
* **Certificate limits**: Let's Encrypt has rate limits that can be reached when managing many domains on a single certificate | ||
acarranoqovery marked this conversation as resolved.
Show resolved
Hide resolved
|
||
|
||
## **The Solution: Dedicated Ingresses Per Tenant** | ||
|
||
<p align="center"> | ||
<img src="/img/certificate_management_for_multi_tenant_infrastructure/archi_overview.png" alt="Certificate Management Architecture Comparison" /> | ||
</p> | ||
|
||
Instead of managing all domains through a single ingress, we'll create a dedicated ingress for each customer. This approach provides: | ||
|
||
* **Isolation**: Each tenant gets their own certificate and ingress configuration | ||
* **Reliability**: Issues with one tenant's domain won't affect others | ||
* **Privacy**: Certificates only contain the specific tenant's domain | ||
* **Scalability**: Easier to manage rate limits and certificate renewals | ||
|
||
## **Implementation Guide** | ||
|
||
### **Prerequisites** | ||
|
||
* A Qovery account with a configured cluster | ||
* DNS management access for your domains | ||
|
||
### **Step 1: Organize Your Infrastructure (Optional but Recommended)** | ||
|
||
<p align="center"> | ||
<img src="/img/certificate_management_for_multi_tenant_infrastructure/environment_structure.png" alt="Qovery Platform" /> | ||
</p> | ||
|
||
While not mandatory, creating separate environments helps maintain a clean separation between your core infrastructure and tenant-specific configurations. | ||
|
||
1. **Create an Infrastructure Environment** | ||
acarranoqovery marked this conversation as resolved.
Outdated
Show resolved
Hide resolved
|
||
|
||
This environment will host your main application components (frontend, API, database, etc.). | ||
|
||
* Navigate to your project dashboard | ||
* Click "Create new environment" | ||
* Name it "Infrastructure" or similar | ||
* Configure your environment settings | ||
|
||
2. **Create a Tenants Environment** | ||
|
||
This dedicated environment will contain all tenant-specific ingress configurations. | ||
|
||
* Create another environment | ||
* Name it "Tenants" or "Customers" | ||
* This provides logical separation and easier management | ||
|
||
### **Step 2: Deploy Your Main Application** | ||
|
||
If you haven't already deployed your application, follow the [Qovery deployment guide](https://hub.qovery.com/guides/getting-started/deploy-your-first-application/). | ||
|
||
For this example, we'll use a simple web application: | ||
|
||
1. **Deploy your container** | ||
|
||
* Use the Qovery UI, our [CLI](https://hub.qovery.com/docs/using-qovery/interface/cli/), our [Terraform Provider](https://hub.qovery.com/docs/using-qovery/integration/terraform-provider/) or our [REST API](https://hub.qovery.com/docs/using-qovery/interface/rest-api/) to deploy your application | ||
* For testing, you can use a simple nginx container | ||
|
||
2. **Configure the application port** | ||
|
||
* Navigate to Settings → Ports | ||
* Click "Add port" | ||
* Configure: | ||
* Port: 80 (or your application's port exposed by your container) | ||
* Protocol: HTTP | ||
* Exposure: Publicly exposed | ||
|
||
<p align="center"> | ||
<img src="/img/certificate_management_for_multi_tenant_infrastructure/edit_port.png" alt="Add Port" /> | ||
</p> | ||
|
||
3. **Add your main domain** (optional) | ||
|
||
* Go to Settings → Domains | ||
* Click "Add domain" | ||
* Enter your primary domain | ||
* Configure the required CNAME records in your DNS provider | ||
|
||
4. **Note important values** | ||
|
||
Before proceeding, save these values from your application's built-in environment variables: | ||
|
||
* `QOVERY_CONTAINER_XXXXXXX_HOST_INTERNAL`: The internal hostname of your application | ||
* `QOVERY_KUBERNETES_NAMESPACE_NAME`: Your environment's namespace | ||
|
||
<p align="center"> | ||
<img src="/img/certificate_management_for_multi_tenant_infrastructure/list_variables.png" alt="List Variables" /> | ||
</p> | ||
|
||
5. You can find these in the Variables section of your application. | ||
|
||
### **Step 3: Create Tenant-Specific Ingresses** | ||
|
||
Now we'll create dedicated ingresses for each tenant using Helm charts. | ||
|
||
<p align="center"> | ||
<img src="/img/certificate_management_for_multi_tenant_infrastructure/implementation_flow.png" alt="Implementation Steps Flow" /> | ||
</p> | ||
|
||
1. **Switch to your Tenants environment** (if you created one) | ||
|
||
2. **Create a new Helm service** | ||
|
||
We'll use an empty Helm chart, Qovery will create an ingress resource. You can use this [empty chart template](https://github.com/Guimove/empty-chart) or create your own. | ||
|
||
* Click "Create new service" | ||
* Select "Helm" | ||
* Name it after your tenant (e.g., "tenant-acme-corp") | ||
* Use the empty chart repository | ||
* Keep default values (no overrides needed) | ||
* Select only “Create” at the end of the create wizard | ||
|
||
<p align="center"> | ||
<img src="/img/certificate_management_for_multi_tenant_infrastructure/deploy_helm_chart.png" alt="Deploy Helm Chart" /> | ||
</p> | ||
|
||
3. **Configure the ingress** | ||
|
||
Navigate to Settings → Ports and add a port: | ||
|
||
* Service name: Use the `QOVERY_CONTAINER_XXXXXXX_HOST_INTERNAL` value | ||
acarranoqovery marked this conversation as resolved.
Outdated
Show resolved
Hide resolved
|
||
* Namespace: Use `QOVERY_KUBERNETES_NAMESPACE_NAME` (if using separate environments) | ||
|
||
<p align="center"> | ||
<img src="/img/certificate_management_for_multi_tenant_infrastructure/tenant_port.png" alt="Tenant Port" /> | ||
</p> | ||
|
||
4. **Add the tenant's custom domain** | ||
|
||
* Go to Settings → Domains | ||
* Add the tenant's specific domain | ||
* Ensure the tenant configures their DNS records | ||
|
||
<p align="center"> | ||
<img src="/img/certificate_management_for_multi_tenant_infrastructure/custom_domain.png" alt="Custom Domain" /> | ||
</p> | ||
|
||
5. **Deploy the service** | ||
|
||
Deploy the Helm chart. Qovery will: | ||
|
||
* Create a dedicated ingress for this tenant | ||
* Generate a separate SSL certificate | ||
* Route traffic to your main application | ||
|
||
### **Step 4: Scale to Multiple Tenants** | ||
|
||
For additional tenants, you have two options: | ||
|
||
1. **Clone existing tenant configuration** | ||
|
||
* Clone an existing tenant service | ||
* Update the name and domain | ||
* Deploy | ||
|
||
2. **Create from scratch** | ||
|
||
* Repeat Step 3 for each new tenant | ||
|
||
## **Troubleshooting** | ||
|
||
### **Certificate Generation Issues** | ||
|
||
1. **Check DNS propagation** | ||
|
||
```shell | ||
dig _acme-challenge.tenant-domain.com CNAME | ||
``` | ||
|
||
2. **Verify ingress configuration** | ||
|
||
* Check the Qovery deployment logs | ||
* Ensure the domain is correctly configured | ||
|
||
3. **Monitor cert-manager logs** | ||
* Access your cluster logs to see certificate generation details | ||
|
||
### **Routing Issues** | ||
|
||
1. **Verify internal service name on the tenant port configuration** | ||
* Ensure the service name matches your application's internal hostname | ||
2. **Check namespace configuration** | ||
* Confirm the namespace is correct if using separate environments | ||
|
||
## **Conclusion** | ||
|
||
By implementing dedicated ingresses for each tenant, you create a more robust, scalable, and secure multi-tenant architecture on Qovery. This approach provides better isolation, easier troubleshooting, and improved privacy for your customers. | ||
|
||
## **Related Resources** | ||
|
||
* [Qovery Custom Domain Documentation](https://hub.qovery.com/docs/using-qovery/configuration/application/#custom-domains) | ||
* [Deploying Applications with Qovery](https://hub.qovery.com/guides/getting-started/deploy-your-first-application/) | ||
* [Environment Management Guide](https://hub.qovery.com/docs/using-qovery/configuration/environment/) | ||
* [Qovery Helm Deployment](https://hub.qovery.com/docs/using-qovery/configuration/helm/) | ||
|
||
## **Next Steps** | ||
|
||
* Explore [Qovery's API](https://hub.qovery.com/docs/using-qovery/interface/rest-api/) to automate tenant provisioning | ||
* Consider implementing [auto-scaling](https://hub.qovery.com/docs/using-qovery/configuration/application/#auto-scaling) on the main service | ||
|
||
<Jump to="/guides/tutorial/">Tutorial</Jump> | ||
|
||
|
||
|
Oops, something went wrong.
Add this suggestion to a batch that can be applied as a single commit.
This suggestion is invalid because no changes were made to the code.
Suggestions cannot be applied while the pull request is closed.
Suggestions cannot be applied while viewing a subset of changes.
Only one suggestion per line can be applied in a batch.
Add this suggestion to a batch that can be applied as a single commit.
Applying suggestions on deleted lines is not supported.
You must change the existing code in this line in order to create a valid suggestion.
Outdated suggestions cannot be applied.
This suggestion has been applied or marked resolved.
Suggestions cannot be applied from pending reviews.
Suggestions cannot be applied on multi-line comments.
Suggestions cannot be applied while the pull request is queued to merge.
Suggestion cannot be applied right now. Please check back later.
Uh oh!
There was an error while loading. Please reload this page.