mirror of
https://github.com/mivodev/mivo.git
synced 2026-01-26 05:25:42 +07:00
142 lines
4.5 KiB
PHP
142 lines
4.5 KiB
PHP
<?php
|
|
|
|
namespace App\Controllers;
|
|
|
|
use App\Core\Controller;
|
|
use App\Core\Database;
|
|
use App\Core\Migrations;
|
|
use App\Config\SiteConfig;
|
|
|
|
class InstallController extends Controller {
|
|
|
|
public function index() {
|
|
// Check if already installed
|
|
if ($this->isInstalled()) {
|
|
header('Location: /login');
|
|
exit;
|
|
}
|
|
|
|
$permissions = $this->checkPermissions();
|
|
|
|
return $this->view('install', [
|
|
'permissions' => $permissions
|
|
]);
|
|
}
|
|
|
|
public function process() {
|
|
if ($this->isInstalled()) {
|
|
header('Location: /login');
|
|
exit;
|
|
}
|
|
|
|
$permissions = $this->checkPermissions();
|
|
if (!$permissions['db_writable'] || !$permissions['root_writable']) {
|
|
\App\Helpers\FlashHelper::set('error', 'Izin Ditolak', 'Pastikan folder app/Database dan root direktori dapat ditulis oleh server web.');
|
|
header('Location: /install');
|
|
exit;
|
|
}
|
|
|
|
$username = $_POST['username'] ?? 'admin';
|
|
$password = $_POST['password'] ?? 'admin';
|
|
|
|
try {
|
|
// 1. Run Migrations
|
|
Migrations::up();
|
|
|
|
// 2. Generate Key if default
|
|
if (SiteConfig::getSecretKey() === 'mikhmonv3remake_secret_key_32bytes') {
|
|
$this->generateKey();
|
|
}
|
|
|
|
// 3. Create Admin
|
|
$db = Database::getInstance();
|
|
$hash = password_hash($password, PASSWORD_DEFAULT);
|
|
|
|
// Check if user exists (edge case where key was default but user existed)
|
|
$check = $db->query("SELECT id FROM users WHERE username = ?", [$username])->fetch();
|
|
if (!$check) {
|
|
$db->query("INSERT INTO users (username, password, created_at) VALUES (?, ?, ?)", [
|
|
$username, $hash, date('Y-m-d H:i:s')
|
|
]);
|
|
} else {
|
|
$db->query("UPDATE users SET password = ? WHERE username = ?", [$hash, $username]);
|
|
}
|
|
|
|
// Success
|
|
\App\Helpers\FlashHelper::set('success', 'Installation Complete', 'System has been successfully installed. Please login.');
|
|
header('Location: /login');
|
|
exit;
|
|
|
|
} catch (\Exception $e) {
|
|
\App\Helpers\FlashHelper::set('error', 'Installation Failed', $e->getMessage());
|
|
header('Location: /install');
|
|
exit;
|
|
}
|
|
}
|
|
|
|
private function checkPermissions() {
|
|
$dbDir = ROOT . '/app/Database';
|
|
$envFile = ROOT . '/.env';
|
|
|
|
return [
|
|
'db_writable' => is_writable($dbDir),
|
|
'env_writable' => file_exists($envFile) ? is_writable($envFile) : is_writable(ROOT),
|
|
'root_writable' => is_writable(ROOT)
|
|
];
|
|
}
|
|
|
|
private function isInstalled() {
|
|
// Check if .env exists and APP_KEY is set to something other than the default/example
|
|
$envPath = ROOT . '/.env';
|
|
if (!file_exists($envPath)) {
|
|
// Check if SiteConfig has a manual override (legacy)
|
|
return SiteConfig::getSecretKey() !== 'mikhmonv3remake_secret_key_32bytes';
|
|
}
|
|
|
|
$key = getenv('APP_KEY');
|
|
$keyChanged = ($key && $key !== 'mikhmonv3remake_secret_key_32bytes');
|
|
|
|
try {
|
|
$db = Database::getInstance();
|
|
$count = $db->query("SELECT count(*) as c FROM users")->fetchColumn();
|
|
$hasUser = ($count > 0);
|
|
} catch (\Exception $e) {
|
|
$hasUser = false;
|
|
}
|
|
|
|
return $keyChanged && $hasUser;
|
|
}
|
|
|
|
private function generateKey() {
|
|
$key = bin2hex(random_bytes(16));
|
|
$envPath = ROOT . '/.env';
|
|
$examplePath = ROOT . '/.env.example';
|
|
|
|
if (!file_exists($envPath)) {
|
|
if (file_exists($examplePath)) {
|
|
copy($examplePath, $envPath);
|
|
} else {
|
|
return; // Cannot generate without source
|
|
}
|
|
}
|
|
|
|
$content = file_get_contents($envPath);
|
|
|
|
if (strpos($content, 'APP_KEY=') !== false) {
|
|
$newContent = preg_replace(
|
|
"/APP_KEY=.*/",
|
|
"APP_KEY=$key",
|
|
$content
|
|
);
|
|
} else {
|
|
$newContent = $content . "\nAPP_KEY=$key";
|
|
}
|
|
|
|
file_put_contents($envPath, $newContent);
|
|
|
|
// Refresh env in current session so next steps use it
|
|
putenv("APP_KEY=$key");
|
|
$_ENV['APP_KEY'] = $key;
|
|
}
|
|
}
|