buildNavigation($contentDir, $currentLang, $defaultLang),
'homeLabel' => loadMetadata($contentDir, $currentLang, $defaultLang)['slug'] ?? 'Home',
'translations' => loadTranslations($currentLang)
];
}
function renderContentFile(string $filePath): string {
$ext = pathinfo($filePath, PATHINFO_EXTENSION);
ob_start();
if ($ext === 'md') {
if (!class_exists('Parsedown')) {
require_once __DIR__ . '/vendor/Parsedown.php';
}
echo '' . (new Parsedown())->text(file_get_contents($filePath)) . '';
} elseif (in_array($ext, ['html', 'php'])) {
include $filePath;
}
return ob_get_clean();
}
function renderTemplate(string $content, int $statusCode = 200): void {
global $baseTemplate;
extract(prepareTemplateContext());
http_response_code($statusCode);
include $baseTemplate;
exit;
}
function renderFile(string $filePath): void {
global $baseTemplate, $pageTemplate, $contentDir, $currentLang, $defaultLang;
$realPath = realpath($filePath);
if (!$realPath || !str_starts_with($realPath, $contentDir) || !is_readable($realPath)) {
renderTemplate("403 Forbidden
Access denied.
", 403);
}
$ext = pathinfo($realPath, PATHINFO_EXTENSION);
if (in_array($ext, CONTENT_EXTENSIONS)) {
$content = renderContentFile($realPath);
// Prepare template variables
extract(prepareTemplateContext());
$pageDir = dirname($realPath);
$pageMetadata = loadMetadata($pageDir, $currentLang, $defaultLang);
$pageTitle = $pageMetadata['title'] ?? null;
// Wrap content with page template
ob_start();
include $pageTemplate;
$content = ob_get_clean();
// Wrap with base template
include $baseTemplate;
exit;
}
// Serve other file types directly
header('Content-Type: ' . (mime_content_type($realPath) ?: 'application/octet-stream'));
readfile($realPath);
exit;
}
function renderMultipleFiles(array $filePaths, string $pageDir): void {
global $baseTemplate, $pageTemplate, $contentDir, $currentLang, $defaultLang;
// Validate all files are safe
foreach ($filePaths as $filePath) {
$realPath = realpath($filePath);
if (!$realPath || !str_starts_with($realPath, $contentDir) || !is_readable($realPath)) {
renderTemplate("403 Forbidden
Access denied.
", 403);
}
}
// Render all content files in order
$content = implode('', array_map('renderContentFile', $filePaths));
// Prepare template variables
extract(prepareTemplateContext());
$pageMetadata = loadMetadata($pageDir, $currentLang, $defaultLang);
$pageTitle = $pageMetadata['title'] ?? null;
// Wrap content with page template
ob_start();
include $pageTemplate;
$content = ob_get_clean();
// Wrap with base template
include $baseTemplate;
exit;
}