🚀 Hostinger Optimized
🖥️ Server: LiteSpeed
💻 System: Linux s20058.bom1.stableserver.net 5.14.0-611.55.1.el9_7.x86_64 #1 SMP PREEMPT_DYNAMIC Tue May 19 15:19:29 EDT 2026 x86_64
👤 User: skhata (1324)
🐘 PHP: 8.4.20
🚫 Disabled: ✨ NONE

💻 Terminal

📁 /home/skhata/chandrasons.com/public
$

📄 functions.php

📁 Path: //home7/skhata/excellenteducation.com.np/includes/functions.php
📊 Size: 8.37 KB
🔒 Perm: 0644
📝 MIME: text/x-php
<?php
require_once __DIR__ . '/../config/db.php';

/** Fetch the single settings row (cached per request). */
function get_settings(): array {
    static $settings = null;
    if ($settings === null) {
        $stmt = db()->query('SELECT * FROM settings WHERE id = 1');
        $settings = $stmt->fetch() ?: [];
    }
    return $settings;
}

/**
 * Write (or rewrite) a thin clean-URL stub file at the site root, e.g.
 * study-abroad-australia.php, that simply forwards to the shared dynamic
 * template with the right slug. Called after saving a country / program /
 * blog post so admin-added content gets a real, crawlable clean URL without
 * needing mod_rewrite. If the slug changed, pass $oldSlug to remove the
 * previous stub file.
 */
function write_route_stub(string $prefix, string $slug, string $targetFile, ?string $oldSlug = null): void {
    $root = __DIR__ . '/..';
    if ($oldSlug && $oldSlug !== $slug) {
        $oldPath = $root . '/' . $prefix . $oldSlug . '.php';
        if (is_file($oldPath)) @unlink($oldPath);
    }
    $path = $root . '/' . $prefix . $slug . '.php';
    $content = "<?php\n// Auto-generated clean-URL route. Do not edit directly - managed by the admin panel.\n\$_GET['slug'] = " . var_export($slug, true) . ";\nrequire __DIR__ . '/" . $targetFile . "';\n";
    file_put_contents($path, $content);
}

/** Convenience getter for one setting key with fallback. */
function setting(string $key, string $default = ''): string {
    $s = get_settings();
    return $s[$key] ?? $default;
}

/** Turn arbitrary text into a URL-safe slug. */
function slugify(string $text): string {
    $text = preg_replace('~[^\pL\d]+~u', '-', $text);
    $text = trim($text, '-');
    $text = iconv('utf-8', 'ascii//TRANSLIT', $text) ?: $text;
    $text = strtolower($text);
    $text = preg_replace('~[^-\w]+~', '', $text);
    return $text ?: 'n-a';
}

/** Escape helper for output in templates. */
function e(?string $value): string {
    return htmlspecialchars($value ?? '', ENT_QUOTES, 'UTF-8');
}

/** Convert stored newlines into paragraph tags for long-text fields. */
function render_paragraphs(?string $text): string {
    $text = trim((string) $text);
    if ($text === '') return '';
    $blocks = preg_split('/\r\n\r\n|\n\n/', $text);
    $html = '';
    foreach ($blocks as $block) {
        $block = trim($block);
        if ($block === '') continue;
        $html .= '<p class="text-gray-500 dark:text-gray-400 leading-relaxed mb-4">' . nl2br(e($block)) . '</p>' . "\n";
    }
    return $html;
}

/** Handle an uploaded image; returns the stored relative path or null. */
function handle_image_upload(string $field, string $subfolder, ?string $existing = null): ?string {
    if (empty($_FILES[$field]) || $_FILES[$field]['error'] === UPLOAD_ERR_NO_FILE) {
        return $existing;
    }
    if ($_FILES[$field]['error'] !== UPLOAD_ERR_OK) {
        return $existing;
    }
    $allowed = ['jpg' => 'image/jpeg', 'jpeg' => 'image/jpeg', 'png' => 'image/png', 'webp' => 'image/webp', 'gif' => 'image/gif'];
    $ext = strtolower(pathinfo($_FILES[$field]['name'], PATHINFO_EXTENSION));
    if (!array_key_exists($ext, $allowed)) {
        return $existing;
    }
    $dir = __DIR__ . '/../uploads/' . trim($subfolder, '/');
    if (!is_dir($dir)) {
        mkdir($dir, 0755, true);
    }
    $filename = uniqid($subfolder . '_', true) . '.' . $ext;
    $dest = $dir . '/' . $filename;
    if (move_uploaded_file($_FILES[$field]['tmp_name'], $dest)) {
        return 'uploads/' . trim($subfolder, '/') . '/' . $filename;
    }
    return $existing;
}

/** Resolve an image value into a full <img> src: absolute URL, Unsplash photo id, or local upload path. */
function resolve_image(?string $value, string $fallback = ''): string {
    $value = trim((string) $value);
    if ($value === '') return $fallback;
    if (str_starts_with($value, 'http://') || str_starts_with($value, 'https://')) return $value;
    if (str_starts_with($value, 'photo-')) return 'https://images.unsplash.com/' . $value . '?q=80&w=900';
    if (str_starts_with($value, 'uploads/') || str_starts_with($value, 'assets/')) return SITE_URL . '/' . $value;
    return $value;
}

/** Simple CSRF token helpers. */
function csrf_token(): string {
    if (session_status() !== PHP_SESSION_ACTIVE) session_start();
    if (empty($_SESSION['csrf_token'])) {
        $_SESSION['csrf_token'] = bin2hex(random_bytes(32));
    }
    return $_SESSION['csrf_token'];
}

function csrf_field(): string {
    return '<input type="hidden" name="csrf_token" value="' . e(csrf_token()) . '">';
}

function csrf_verify(): bool {
    if (session_status() !== PHP_SESSION_ACTIVE) session_start();
    $token = $_POST['csrf_token'] ?? '';
    return !empty($_SESSION['csrf_token']) && hash_equals($_SESSION['csrf_token'], $token);
}

function redirect(string $path): void {
    header('Location: ' . $path);
    exit;
}

function flash_set(string $type, string $message): void {
    if (session_status() !== PHP_SESSION_ACTIVE) session_start();
    $_SESSION['flash'] = ['type' => $type, 'message' => $message];
}

function flash_get(): ?array {
    if (session_status() !== PHP_SESSION_ACTIVE) session_start();
    if (empty($_SESSION['flash'])) return null;
    $f = $_SESSION['flash'];
    unset($_SESSION['flash']);
    return $f;
}

/** Decode a JSON column safely to an array. */
function jd($value): array {
    if (is_array($value)) return $value;
    $decoded = json_decode((string) $value, true);
    return is_array($decoded) ? $decoded : [];
}

/** Turn a textarea (one item per line) into a JSON array string for storage. */
function lines_to_json(string $text): string {
    $lines = preg_split('/\r\n|\r|\n/', $text);
    $lines = array_values(array_filter(array_map('trim', $lines), fn($l) => $l !== ''));
    return json_encode($lines, JSON_UNESCAPED_UNICODE);
}

/** Turn a JSON array column back into a newline-separated textarea value. */
function json_to_lines($value): string {
    return implode("\n", jd($value));
}

/**
 * Turn a textarea of "icon|amount|label" lines into a JSON array of objects
 * for the cost_items column, e.g. "fa-house|AUD 1,400-2,500/mo|Accommodation".
 */
function cost_lines_to_json(string $text): string {
    $lines = preg_split('/\r\n|\r|\n/', $text);
    $items = [];
    foreach ($lines as $line) {
        $line = trim($line);
        if ($line === '') continue;
        $parts = array_map('trim', explode('|', $line));
        $items[] = ['icon' => $parts[0] ?? 'fa-circle', 'amount' => $parts[1] ?? '', 'label' => $parts[2] ?? ''];
    }
    return json_encode($items, JSON_UNESCAPED_UNICODE);
}

/** Turn the cost_items JSON column back into "icon|amount|label" textarea lines. */
function json_to_cost_lines($value): string {
    $items = jd($value);
    $lines = [];
    foreach ($items as $it) {
        $lines[] = ($it['icon'] ?? '') . '|' . ($it['amount'] ?? '') . '|' . ($it['label'] ?? '');
    }
    return implode("\n", $lines);
}

/**
 * Turn a textarea of "Batch Name|Days|Time" lines into JSON for the test
 * preparation schedule column, e.g. "Morning Batch|Sun-Fri|7:00 - 8:30 AM".
 */
function schedule_lines_to_json(string $text): string {
    $lines = preg_split('/\r\n|\r|\n/', $text);
    $items = [];
    foreach ($lines as $line) {
        $line = trim($line);
        if ($line === '') continue;
        $parts = array_map('trim', explode('|', $line));
        $items[] = ['batch' => $parts[0] ?? '', 'days' => $parts[1] ?? '', 'time' => $parts[2] ?? ''];
    }
    return json_encode($items, JSON_UNESCAPED_UNICODE);
}

function json_to_schedule_lines($value): string {
    $items = jd($value);
    $lines = [];
    foreach ($items as $it) {
        $lines[] = ($it['batch'] ?? '') . '|' . ($it['days'] ?? '') . '|' . ($it['time'] ?? '');
    }
    return implode("\n", $lines);
}

/**
 * Turn a textarea of "Question|Answer" lines into JSON for FAQ-style columns.
 */
function faq_lines_to_json(string $text): string {
    $lines = preg_split('/\r\n|\r|\n/', $text);
    $items = [];
    foreach ($lines as $line) {
        $line = trim($line);
        if ($line === '') continue;
        $parts = array_map('trim', explode('|', $line, 2));
        $items[] = ['q' => $parts[0] ?? '', 'a' => $parts[1] ?? ''];
    }
    return json_encode($items, JSON_UNESCAPED_UNICODE);
}

function json_to_faq_lines($value): string {
    $items = jd($value);
    $lines = [];
    foreach ($items as $it) {
        $lines[] = ($it['q'] ?? '') . '|' . ($it['a'] ?? '');
    }
    return implode("\n", $lines);
}
← Back📥 Raw✏️ Edit🔒 Chmod
✨ File Manager Magic ✨