HTTP
GET /cdna-api/pages/page/api-sandbox?properties={id,name,fullPath,activeRevision{id,layout{id,name},areasContent}}
Authorization: Bearer YOUR_ACCESS_TOKEN
Accept: application/json
The answer on this documentation site's sandbox page, cut to two of its sections. Every layout area describes itself with its input type, and its value sits under one key:
JSON
{
"result": "success",
"data": {
"id": 1885,
"name": "API sandbox",
"fullPath": "/api-sandbox",
"activeRevision": {
"id": 3482,
"layout": {"id": 30, "name": "Hub Page Sections"},
"areasContent": {
"navSection": {"id": 90806, "type": "Text", "category": "text", "editor": "text", "text": "API sandbox"},
"pageSections": {
"id": 90798,
"type": "Component Collection",
"category": "collection",
"collection": [
{
"componentId": 21105,
"componentName": "Section A",
"componentLayout": 40,
"componentGlobal": false,
"body": {"id": 90800, "type": "Richtext", "category": "text", "editor": "richtext", "text": "<p>Section A</p>"}
},
{
"componentId": 21108,
"componentName": "Sandbox figure",
"componentLayout": 58,
"componentGlobal": false,
"image": {"id": 90803, "type": "Image", "category": "image", "imageId": 1185, "imagePath": "/files/images/api-sandbox/api-sandbox-figure.png"},
"alt": {"id": 90804, "type": "Text", "category": "text", "editor": "text", "text": "A blue and green gradient"},
"caption": {"id": 90805, "type": "Text", "category": "text", "editor": "text", "text": "Uploaded through the API"}
}
]
}
}
}
}
}
A small reader that turns the layout areas into plain values, so the rest of the front end never sees the envelope:
JavaScript
// areas.js: turn areasContent into plain values
export function value(area) {
if (!area || typeof area !== 'object') return area ?? null;
switch (area.category) {
case 'collection':
return (area.collection ?? []).map(component);
case 'component':
return area.component ? component(area.component) : null;
case 'image':
return area.imageId ? { id: area.imageId, path: area.imagePath } : null;
default:
if ('active' in area) return area.active; // a switch
return area.text ?? null; // text, rich text, select, date
}
}
function component(c) {
const areas = {};
for (const [name, area] of Object.entries(c)) {
if (!name.startsWith('component')) areas[name] = value(area);
}
return { layout: c.componentLayout, name: c.componentName, global: c.componentGlobal, areas };
}
// usage
const { data } = await response.json();
const areas = Object.fromEntries(
Object.entries(data.activeRevision.areasContent).map(([name, area]) => [name, value(area)])
);
// areas.pageSections[1].areas.image.path === '/files/images/api-sandbox/api-sandbox-figure.png'