Building multi-tenant applications can be a challenging task, especially when it comes to ensuring data security and privacy. Xano provides a powerful no-code solution that simplifies the process of creating secure multi-tenant applications. In this step-by-step guide, we'll walk through how to implement a security technique that ensures users can only access data related to their associated companies.
Understanding the Data Structure
Before diving into the implementation, let's first understand the data structure we'll be working with:
- Company: This table stores information about the different companies.
- Private Information: This table contains sensitive data that needs to be secured.
- Users: This table stores user information.
- Users Company: This table maintains the relationship between users and the companies they are associated with. A user can be associated with multiple companies.
The key to our security implementation lies in the `Users Company` table, which allows us to control access based on the user's association with specific companies.
Step 1: Create a Reusable Security Function
Since we'll be implementing this security measure across multiple endpoints, it's best to create a reusable function that we can call from different parts of our application. Here's how to do it:
- In the Xano console, navigate to the "Functions" section and click "Add Function."
- Name the function "CheckUserAccess" and assign it the "security" tag.
- In the function editor, we'll query the `Users Company` table to check if a relationship exists between the user and the company they're trying to access. We'll use the `company_id` as input and the signed-in user's `auth_id` to perform the query.
let users_company_one = query_all_records(
table: 'users_company',
constraints: [
{
field: 'company_id',
operator: '==',
value: get('company_id')
},
{
field: 'user_id',
operator: '==',
value: auth.id
}
],
output: 'exists'
);
precondition(
users_company_one == true,
'You do not have access to this information',
'access_denied'
);
- Click "Save" and "Publish" the function.
Step 2: Implement the Security Check in Your Endpoints
Now that we have our reusable security function, we can call it from any endpoint that needs to restrict access based on the user's association with a company.
- In the Xano console, navigate to the endpoint you want to secure.
- Drag and drop the `CheckUserAccess` function above the query that retrieves the sensitive data.
- Pass the `company_id` as an input to the `CheckUserAccess` function.
Your endpoint should now look something like this:
let users_company_one = CheckUserAccess(company_id: get('company_id'));
let private_information = query_all_records(
table: 'private_information',
constraints: [
{
field: 'company_id',
operator: '==',
value: get('company_id')
}
]
);
return private_information;
Step 3: Test Your Implementation
To test the security implementation, follow these steps:
- Run the endpoint you've secured, passing in the `company_id` of a company you're associated with as a user.
- Verify that you can access the private information for that company.
- Try running the same endpoint with a `company_id` you're not associated with.
- You should receive an "access denied" error, confirming that the security measure is working as intended.
Conclusion
Implementing secure multi-tenant applications can be a daunting task, but with Xano's no-code platform, it becomes a breeze. By following this step-by-step guide, you can ensure that your users can only access data related to the companies they are associated with, maintaining data privacy and security.
Remember, the power of Xano lies in its ability to simplify complex development tasks, making it accessible to both non-technical users and experienced developers alike. Whether you're a no-code enthusiast, citizen developer, traditional developer, or part of a startup or small business, Xano empowers you to build and deploy secure, scalable applications without writing a single line of code.