Multi-Site setup with single CMS instance¶
In this short guide, we will show you how to use the multi-site functionality in your frontend app.
We will use vue.js to fetch data from a single django CMS instance with multiple sites. This implementation
guide can easily be adapted to other frontend frameworks.
Warning
This guide assumes you have a running Django CMS project with multiple sites. If you haven’t configured django CMS for multi-site yet, please follow the Multi-Site Support guide.
Setup Django CMS for Multi-Site¶
Start your django CMS project
python manage.py runserver localhost:8080
Adjust the primary site details in django admin for site A (Site ID 1)
Create a new site in django admin for site B (Site ID 2)
Create a nested pages structure for site A and site B using django CMS page tree admin.
Before building the frontend we want to make sure the page tree is working and returned as expected.
# Fetch the page tree for site A
curl -v -H "X-Site-ID: 1" \
-H "Content-Type: application/json" \
-H "Accept: application/json" \
http://localhost:8080/api/en/pages-tree/
Response
You should get your page tree for each site as a response described in the Pages Endpoints reference.
Hint
Alternatively you can use swagger (see Installation) to test the API endpoints or a app like Bruno
CMS Reference¶
Enable CORS¶
This works fine from console, but for browser requests we have to ensure that CORS (Cross-Origin Resource Sharing) is configured correctly.
See the CORS Support guide for more information.
Setup Vue.js Project¶
Before continuing, you should set up a basic Vue.js project.
Note
We use TypeScript for this example. Make sure to enable it in your Vue.js project.
✔ Add TypeScript? … Yes
Now we will create a simple Vue.js project to fetch the page tree using the X-Site-ID request header:
Replace the content of App.vue with the following code:
<script setup lang="ts">
import { ref } from 'vue';
const siteId = ref('1');
const data = ref(null);
const error = ref(null);
const errorCode = ref(null);
async function fetchData() {
error.value = null;
errorCode.value = null;
try {
const response = await fetch('http://localhost:8080/api/en/pages-tree/', {
headers: { 'X-Site-ID': siteId.value }
});
if (!response.ok) {
error.value = `HTTP error: ${response.statusText}`;
errorCode.value = response.status;
data.value = null;
return;
}
data.value = await response.json();
} catch (err) {
error.value = err.message || 'Unknown error';
errorCode.value = err.code || null;
data.value = null;
}
}
</script>
<template>
<select v-model="siteId" @change="fetchData">
<option value="1">Site 1</option>
<option value="2">Site 2</option>
</select>
<button @click="fetchData">Fetch Page Tree</button>
<pre v-if="data">{{ data }}</pre>
<div v-if="error" style="color: red;">
Error: {{ error }}<br>
<span v-if="errorCode">Error Code: {{ errorCode }}</span>
</div>
</template>
Testing¶
Run your Vue.js project:
npm run dev
Visit http://localhost:5173/ in your browser, assuming you are using the default port for Vue.js.
You can now click the "Fetch Page Tree" button to fetch the page tree for the selected site.
Success
You should see the page tree for the selected site in the browser. See the Pages Endpoints documentation for the expected response.
Error
if you get error you likely forgot to set the X-Site-ID header as allowed in the CORS settings or the domain or port is not allowed in the CORS settings.
See the Installation guide for more information.
Start Building¶
When you are able to fetch the page tree for each site you can start building your frontend app.
Configure Django CMS templates with varous placeholders options
Define and customize plugins according to your needs
Add authentication to your frontend app, which allows content preview in the frontend app