« Back to History
mm_page.php
|
20260723_000646.php
Initial Domain Snapshot
Copy Code
<?php /** * mm_page.php * Reusable page wrapper for Mr manager (safe header/footer + prefer main.css) * * Usage (top of page): * require_once __DIR__.'/templates/mm_page.php'; * mm_start_page('Page Title', ['debug'=>true]); // call before output * * Body HTML... * * At end of page: * mm_end_page(); * * This helper will: * - try to include __DIR__.'/partials/header.php' (safe include) * - if header not available, emit a minimal <head> and link to main.css if found * - try to include footer safely * - provide a small debug panel if ?mm_debug=1 * * NOTES: * - It purposely uses include (not require) to avoid fatal errors caused by missing header/footer. * - If your header/footer call header('Location:...') the debug panel will show that location when debug enabled. * - It tries several likely paths for main.css. Adjust paths array below if your project stores CSS elsewhere. */ if (!function_exists('mm_include_safe')) { // Safe "include" that returns diagnostic info function mm_include_safe(string $file): array { $res = ['file'=>$file,'exists'=>false,'included'=>false,'error'=>null,'headers'=>[]]; try { $res['exists'] = file_exists($file); if (!$res['exists']) return $res; ob_start(); include $file; // include not require so missing will not fatal $out = ob_get_clean(); // echo included output to current buffer (so caller sees header contents) echo $out; $res['included'] = true; if (function_exists('headers_list')) $res['headers'] = headers_list(); } catch (Throwable $e) { @ob_end_clean(); $res['error'] = $e->getMessage(); // render a small, safe error box to page but not fatal echo '<div style="margin:12px 0;padding:10px;border-radius:8px;background:#fff1f1;border:1px solid #ffc7c7;color:#8a1a1a;">' .'Include error in <b>'.htmlspecialchars($file).'</b>: '.htmlspecialchars($e->getMessage()) .'</div>'; } return $res; } // Try to resolve a likely web href for main.css. This is best-effort. function mm_css_href(): ?string { // Candidate filesystem locations (adjust if your repo differs) $candidates = [ __DIR__ . '/../assets/main.css', __DIR__ . '/../../assets/main.css', __DIR__ . '/../assets/css/main.css', __DIR__ . '/../../assets/css/main.css', __DIR__ . '/../main.css', __DIR__ . '/main.css', $_SERVER['DOCUMENT_ROOT'] . '/assets/main.css', $_SERVER['DOCUMENT_ROOT'] . '/assets/css/main.css', $_SERVER['DOCUMENT_ROOT'] . '/erp/assets/main.css', ]; foreach ($candidates as $path) { if ($path && file_exists($path)) { $real = realpath($path); // attempt to convert to web path relative to DOCUMENT_ROOT $docroot = realpath($_SERVER['DOCUMENT_ROOT'] ?? '') ?: null; if ($docroot && $real && strpos($real, $docroot) === 0) { $web = '/' . ltrim(str_replace('\\','/', substr($real, strlen($docroot))), '/'); return $web; } // fallback: relative to current script URL $rel = str_replace('\\','/', $real); $here = str_replace('\\','/', realpath(__DIR__)); $web_rel = str_replace($here, '', $rel); if ($web_rel && strpos($web_rel, '/') === 0) { $base = rtrim(dirname($_SERVER['PHP_SELF'] ?? '/'), '/'); return $base . $web_rel; } // last resort return file path (not ideal but maybe served) return $path; } } return null; } // Open/emit page header safely. Call once at top of page. function mm_start_page(string $title = 'Mr manager', array $opts = []) { // allow pages to bypass header auth checks if used by header/footer if (!defined('MM_SKIP_HEADER_AUTH')) define('MM_SKIP_HEADER_AUTH', true); if (!defined('MM_SKIP_FOOTER_AUTH')) define('MM_SKIP_FOOTER_AUTH', true); $debugFlag = (bool)($opts['debug'] ?? (isset($_GET['mm_debug']) && $_GET['mm_debug'] == '1')); // Try includes in these likely locations relative to repo $hdr_paths = [ __DIR__ . '/../partials/header.php', __DIR__ . '/../../erp/partials/header.php', __DIR__ . '/partials/header.php', __DIR__ . '/../erp/partials/header.php', ]; $found = null; foreach ($hdr_paths as $p) { if (file_exists($p)) { $found = $p; break; } } // Attempt safe include $hdr_res = ['exists'=>false,'included'=>false,'error'=>null,'headers'=>[]]; if ($found) { $hdr_res = mm_include_safe($found); } // If header was not included, emit a minimal <head> and link main.css if found if (empty($hdr_res['included'])) { // emit head echo "<!doctype html>\n<html lang=\"en\">\n<head>\n<meta charset=\"utf-8\">\n"; echo "<meta name=\"viewport\" content=\"width=device-width,initial-scale=1\">\n"; echo "<title>".htmlspecialchars($title)."</title>\n"; // link main.css if found $css = mm_css_href(); if ($css) { echo "<link rel=\"stylesheet\" href=\"".htmlspecialchars($css)."\">\n"; } else { // small fallback styles so page remains usable echo "<style>:root{--mm-green:#34A853;--bg:#F5FFF7}body{font-family:system-ui,-apple-system,Segoe UI,Roboto,Arial;background:var(--bg);margin:0;color:#222}.wrap{max-width:1100px;margin:20px auto;padding:12px}.card{background:#fff;padding:12px;border-radius:10px;border:1px solid #eee}</style>\n"; } echo "</head>\n<body>\n"; } // expose debug info if asked if ($debugFlag) { echo '<pre style="background:#0b0f10;color:#8df58d;padding:10px;border-radius:8px;margin:12px 0;white-space:pre-wrap">'; echo "mm_start_page() debug\n"; echo "Title: ".htmlspecialchars($title)."\n"; echo "Header found: ".($found ? $found : 'none')."\n"; if (!empty($hdr_res['error'])) echo "Header error: ".htmlspecialchars($hdr_res['error'])."\n"; if (!empty($hdr_res['headers'])) { echo "Headers sent by header.php:\n"; foreach($hdr_res['headers'] as $h) echo " $h\n"; } echo "</pre>"; } // store state so mm_end_page knows if it should output closing tags // (we store in global variable to avoid polluting user namespace) $GLOBALS['_MM_PAGE_STATE'] = [ 'header_included' => !empty($hdr_res['included']), 'debug' => $debugFlag, 'title' => $title, ]; } // End page, include footer safe, optionally print debug function mm_end_page() { $state = $GLOBALS['_MM_PAGE_STATE'] ?? ['header_included'=>false,'debug'=>false]; $debugFlag = (bool)$state['debug']; // try multiple footer locations $ftr_paths = [ __DIR__ . '/../partials/footer.php', __DIR__ . '/../../erp/partials/footer.php', __DIR__ . '/partials/footer.php', __DIR__ . '/../erp/partials/footer.php', ]; $found = null; foreach ($ftr_paths as $p) { if (file_exists($p)) { $found = $p; break; } } $ftr_res = ['exists'=>false,'included'=>false,'error'=>null,'headers'=>[]]; if ($found) $ftr_res = mm_include_safe($found); if ($debugFlag) { echo '<pre style="background:#0b0f10;color:#8df58d;padding:10px;border-radius:8px;margin:12px 0;white-space:pre-wrap">'; echo "mm_end_page() debug\n"; echo "Footer found: ".($found ? $found : 'none')."\n"; if (!empty($ftr_res['error'])) echo "Footer error: ".htmlspecialchars($ftr_res['error'])."\n"; if (!empty($ftr_res['headers'])) { echo "Headers sent by footer.php:\n"; foreach($ftr_res['headers'] as $h) echo " $h\n"; } echo "</pre>"; } // if header wasn't included earlier we emitted <html><body> in mm_start_page — close them now if (empty($state['header_included'])) { echo "</body>\n</html>"; } } } // end function definitions