Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
8 changes: 4 additions & 4 deletions core/database/migrations/2025_12_25_000000_initial_schema.php
Original file line number Diff line number Diff line change
Expand Up @@ -297,7 +297,7 @@ public function up(): void
$indexPrefix = \DB::getTablePrefix() . $table->getTable();
$table->comment('Site content (documents) - main table storing all site pages, documents, and content resources');
$table->increments('id');
$table->string('type', 20)->default('document')->index('typeidx');
$table->string('type', 20)->default('document')->index("{$indexPrefix}_typeidx");
$table->string('contentType', 50)->default('text/html');
$table->string('pagetitle')->default('');
$table->string('longtitle')->default('');
Expand Down Expand Up @@ -354,9 +354,9 @@ public function up(): void
$table->unsignedInteger('descendant');
$table->unsignedInteger('depth');

$table->index('ancestor', 'closure_ancestor_idx');
$table->index('descendant', 'closure_descendant_idx');
$table->index('depth', 'closure_depth_idx');
$table->index('ancestor', "{$indexPrefix}_closure_ancestor_idx");
$table->index('descendant', "{$indexPrefix}_closure_descendant_idx");
$table->index('depth', "{$indexPrefix}_closure_depth_idx");
$table->unique(['ancestor', 'descendant'], "{$indexPrefix}_ix_unique_path");
});

Expand Down
18 changes: 17 additions & 1 deletion install/src/controllers/connection.php
Original file line number Diff line number Diff line change
@@ -1,6 +1,6 @@
<?php
$installMode = isset($_POST['installmode']) ? (int)$_POST['installmode'] : 0;
$dbTypes = ['mysql' => 'MySQL', 'pgsql' => 'PostgreSQL'];
$dbTypes = ['mysql' => 'MySQL', 'pgsql' => 'PostgreSQL', 'sqlite' => 'SQLite'];

// Determine upgradeability
$upgradeable = 0;
Expand Down Expand Up @@ -50,6 +50,14 @@
$conn = false;
$result = false;
}
} elseif ($database_type === 'sqlite') {
try {
$conn = new PDO('sqlite:' . $database_name);
$result = true;
} catch (PDOException $e) {
$conn = false;
$result = false;
}
}
if (!$conn || !$result) {
$upgradeable = (isset($_POST['installmode']) && $_POST['installmode'] === 'new') ? 0 : 2;
Expand Down Expand Up @@ -92,12 +100,18 @@
$pos = strpos($database_collation, '.');
$database_charset = ($pos !== false) ? substr($database_collation, $pos + 1) : 'utf8';
$database_connection_charset = $database_charset;
} elseif ($database_type === 'sqlite') {
$database_collation = 'utf8';
$database_charset = 'utf8';
$database_connection_charset = 'utf8';
}
} else {
if ($database_type === 'mysql') {
$database_collation = 'utf8mb4_general_ci';
} elseif ($database_type === 'pgsql') {
$database_collation = 'en_US.utf8';
} elseif ($database_type === 'sqlite') {
$database_collation = 'utf8';
}
}

Expand All @@ -107,6 +121,8 @@
$database_connection_method = 'SET CHARACTER SET';
} elseif ($database_type === 'pgsql') {
$database_connection_method = 'SET client_encoding';
} elseif ($database_type === 'sqlite') {
$database_connection_method = '';
}
}
$ph['databaseTypeOptions'] = '';
Expand Down
4 changes: 4 additions & 0 deletions install/src/controllers/connection/collation.php
Original file line number Diff line number Diff line change
Expand Up @@ -89,6 +89,10 @@
}
$output .= '</optgroup></select>';
break;
case 'sqlite':
$output .= '<option value="utf8" selected>utf8</option>';
$output .= '</select>';
break;
}
echo $output;
} catch (Exception $e) {
Expand Down
26 changes: 24 additions & 2 deletions install/src/controllers/connection/databasetest.php
Original file line number Diff line number Diff line change
Expand Up @@ -14,7 +14,11 @@

$database_charset = getDatabaseCharset($database_collation, $driver);
try {
$dbh = new PDO($driver . ':host=' . $host . ';dbname=' . $database_name, $uid, $pwd);
if ($driver === 'sqlite') {
$dbh = new PDO('sqlite:' . EVO_CORE_PATH . "database/$database_name.sqlite");
} else {
$dbh = new PDO($driver . ':host=' . $host . ';dbname=' . $database_name, $uid, $pwd);
}
switch ($driver) {
case 'pgsql':
$result = $dbh->query("SELECT * FROM pg_settings WHERE name='client_encoding'");
Expand Down Expand Up @@ -79,6 +83,18 @@
exit();
}
break;
case 'sqlite':
try {
$result = $dbh->query("SELECT COUNT(*) FROM {$tableprefix}site_content");
} catch (PDOException $e) {
// no table is expected
}

if ($dbh->errorCode() == 0) {
echo $output . '<span id="database_fail">' . $_lang['status_failed_table_prefix_already_in_use'] . '</span>';
exit();
}
break;
}

} catch (PDOException $e) {
Expand All @@ -89,7 +105,11 @@
}

try {
$dbh = new PDO($driver . ':host=' . $host . ($driver === 'pgsql' ? ';dbname=postgres' : ''), $uid, $pwd);
if ($driver === 'sqlite') {
$dbh = new PDO('sqlite:' . EVO_CORE_PATH . "database/$database_name.sqlite");
} else {
$dbh = new PDO($driver . ':host=' . $host . ($driver === 'pgsql' ? ';dbname=postgres' : ''), $uid, $pwd);
}
switch ($driver) {
case 'pgsql':
try {
Expand Down Expand Up @@ -118,6 +138,8 @@
exit();
}
break;
case 'sqlite':
break;
}

echo $output . '<span id="database_pass"> ' . $_lang['status_passed'] . '</span>';
Expand Down
6 changes: 5 additions & 1 deletion install/src/controllers/connection/servertest.php
Original file line number Diff line number Diff line change
Expand Up @@ -6,7 +6,11 @@

$output = $_lang['status_connecting'];
try {
$dbh = new PDO($method . ':host=' . $host . ($method === 'pgsql' ? ';dbname=postgres' : ''), $uid, $pwd);
if ($method === 'sqlite') {
$dbh = new PDO('sqlite::memory:');
} else {
$dbh = new PDO($method . ':host=' . $host . ($method === 'pgsql' ? ';dbname=postgres' : ''), $uid, $pwd);
}
$output .= '<span id="server_pass"> ' . $_lang['status_passed_server'] . '</span>';
} catch (PDOException $e) {
$output .= '<span id="server_fail"> ' . $_lang['status_failed'] . ' ' . $e->getMessage() . '</span>';
Expand Down
9 changes: 8 additions & 1 deletion install/src/controllers/install.php
Original file line number Diff line number Diff line change
Expand Up @@ -71,7 +71,11 @@

global $conn;
try {
$dbh = new PDO($_POST['database_type'] . ':host=' . $_POST['databasehost'] . ';dbname=' . $_POST['database_name'], $database_user, $database_password);
if ($_POST['database_type'] === 'sqlite') {
$dbh = new PDO('sqlite:' . $_POST['database_name']);
} else {
$dbh = new PDO($_POST['database_type'] . ':host=' . $_POST['databasehost'] . ';dbname=' . $_POST['database_name'], $database_user, $database_password);
}

include dirname(__DIR__) . '/processor/result.php';

Expand Down Expand Up @@ -109,6 +113,9 @@
$confph['database_engine'] = ", 'innodb'";
}
break;
case 'sqlite':
$confph['database_port'] = '';
break;
}
$configString = file_get_contents(dirname(__DIR__, 2) . '/stubs/files/config/database/connections/default.tpl');
$configString = parse($configString, $confph);
Expand Down
10 changes: 10 additions & 0 deletions install/src/controllers/options.php
Original file line number Diff line number Diff line change
Expand Up @@ -76,6 +76,16 @@
if (!isset($database_connection_method) || empty($database_connection_method)) {
$database_connection_method = 'SET client_encoding';
}
} elseif ($db_config['driver'] === 'sqlite') {
try {
$conn = new PDO('sqlite:' . $db_config['database']);
$database_collation = 'utf8';
$database_charset = 'utf8';
$database_connection_charset = 'utf8';
$database_connection_method = '';
} catch (PDOException $e) {
//
}
}

$_POST['database_name'] = $db_config['database'];
Expand Down
15 changes: 12 additions & 3 deletions install/src/controllers/summary.php
Original file line number Diff line number Diff line change
Expand Up @@ -211,13 +211,22 @@ function f_owc($path, $data, $mode = null)
$database_charset = substr($database_collation, 0, strpos($database_collation, '_') - 1);
$database_connection_charset = $_POST['database_connection_charset'];
$database_connection_method = $_POST['database_connection_method'];
$dbase = '`' . strip_tags($_POST['database_name']) . '`';
if ($database_type === 'sqlite') {
$database_name = strip_tags($_POST['database_name']); // TODO: replace strip_tags with validation everywhere
$dbase = EVO_CORE_PATH . "database/$database_name.sqlite";
} else {
$dbase = '`' . strip_tags($_POST['database_name']) . '`';
}
$table_prefix = strip_tags($_POST['tableprefix']);
}
echo '<p>' . $_lang['creating_database_connection'];
$host = explode(':', $database_server, 2);
try {
$dbh = new PDO($database_type . ':host=' . $database_server . ';dbname=' . $_POST['database_name'], $database_user, $database_password);
if ($database_type === 'sqlite') {
$dbh = new PDO('sqlite:' . $dbase);
} else {
$dbh = new PDO($database_type . ':host=' . $database_server . ';dbname=' . $_POST['database_name'], $database_user, $database_password);
}
echo '<span class="ok">' . $_lang['ok'] . '</span></p>';
} catch (PDOException $e) {
$errors++;
Expand All @@ -226,7 +235,7 @@ function f_owc($path, $data, $mode = null)
}

// check the database collation if not specified in the configuration
if (!isset ($database_connection_charset) || empty ($database_connection_charset)) {
if ($database_type === 'mysql' && empty ($database_connection_charset)) {
if (!$rs = mysqli_query($conn, "show session variables like 'collation_database'")) {
$rs = mysqli_query($conn, "show session variables like 'collation_server'");
}
Expand Down
26 changes: 14 additions & 12 deletions install/src/functions.php
Original file line number Diff line number Diff line change
Expand Up @@ -44,6 +44,8 @@ function getDatabaseCharset($database_collation, $driver): string {
$database_charset = 'UTF8';
}
$database_charset = str_ireplace(['utf-8', 'utf8'], 'UTF8', $database_charset);
} elseif ($driver === 'sqlite') {
$database_charset = 'utf8';
} else {
// MySQL 5.7 & 8.0: "utf8mb4_general_ci", "utf8_unicode_ci", "latin1_swedish_ci"
// MySQL 8.0+: "utf8mb4_0900_ai_ci" (with version number)
Expand All @@ -70,20 +72,20 @@ function install_sessionCheck()
echo '
<html>
<head>
<title>Install Problem</title>
<style type="text/css">
*{margin:0;padding:0}
body{margin:150px;background:#eee;}
.install{padding:10px;border:3px solid #ffc565;background:#ffddb4;margin:0 auto;text-align:center;}
p{ margin:20px 0; }
a{margin-top:30px;padding:5px;}
</style>
<title>Install Problem</title>
<style type="text/css">
*{margin:0;padding:0}
body{margin:150px;background:#eee;}
.install{padding:10px;border:3px solid #ffc565;background:#ffddb4;margin:0 auto;text-align:center;}
p{ margin:20px 0; }
a{margin-top:30px;padding:5px;}
</style>
</head>
<body>
<div class="install">
<p>' . $_lang["session_problem"] . '</p>
<p><a href="./">' . $_lang["session_problem_try_again"] . '</a></p>
</div>
<div class="install">
<p>' . $_lang["session_problem"] . '</p>
<p><a href="./">' . $_lang["session_problem_try_again"] . '</a></p>
</div>
</body>
</html>';
exit;
Expand Down
41 changes: 32 additions & 9 deletions install/src/template/actions/connection.tpl
Original file line number Diff line number Diff line change
Expand Up @@ -140,20 +140,43 @@
};
});

// Toggle server credential fields based on database type
function toggleServerCredentials() {
var type = document.getElementById('database_type').value;
var isSqlite = (type === 'sqlite');
var serverFields = ['databasehost', 'databaseloginname', 'databaseloginpassword'];
serverFields.forEach(function(id) {
var el = document.getElementById(id);
var p = el.parentElement;
p.style.display = isSqlite ? 'none' : 'block';
if (isSqlite) {
p.classList.remove('has-error');
el.value = '';
}
});
}

document.getElementById('database_type').addEventListener('change', toggleServerCredentials);
// Initial toggle on load
toggleServerCredentials();

// get collation from the database server
document.getElementById('servertest').addEventListener('click', function(e) {
e.preventDefault();

if (form.databasehost.value === '') {
form.databasehost.parentElement.classList.add('has-error');
form.databasehost.focus();
return false;
}
var type = form.database_type.value;
if (type !== 'sqlite') {
if (form.databasehost.value === '') {
form.databasehost.parentElement.classList.add('has-error');
form.databasehost.focus();
return false;
}

if (form.databaseloginname.value === '') {
form.databaseloginname.parentElement.classList.add('has-error');
form.databaseloginname.focus();
return false;
if (form.databaseloginname.value === '') {
form.databaseloginname.parentElement.classList.add('has-error');
form.databaseloginname.focus();
return false;
}
}

var url = 'index.php?s=1&action=connection/collation';
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -15,8 +15,9 @@ public function up()
{
Schema::create('manager_users', function(Blueprint $table)
{
$indexPrefix = \DB::getTablePrefix() . $table->getTable();
$table->integer('id', true);
$table->string('username', 100)->default('')->unique('username');
$table->string('username', 100)->default('')->unique("{$indexPrefix}_username");
$table->string('password', 100)->default('');
});
}
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -57,8 +57,12 @@ public function up()
$prefix = DB::getTablePrefix();
$site_content_table_name = (new \EvolutionCMS\Models\SiteContent())->getTable();
$indexPrefix = $prefix . $site_content_table_name;
if(isset($_POST['database_type']) && $_POST['database_type'] != 'pgsql')
DB::statement('ALTER TABLE '.$prefix.$site_content_table_name." ADD FULLTEXT {$indexPrefix}_content_ft_idx(pagetitle, description, content)");
if (isset($_POST['database_type']) && $_POST['database_type'] === 'mysql') {
DB::statement(
'ALTER TABLE ' . $prefix . $site_content_table_name
. " ADD FULLTEXT {$indexPrefix}_content_ft_idx(pagetitle, description, content)"
);
}
}


Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -25,8 +25,11 @@ public function up()
$prefix = DB::getTablePrefix();
$site_content_tmplvar = (new \EvolutionCMS\Models\SiteTmplvarContentvalue())->getTable();
$indexPrefix = $prefix . $site_content_tmplvar;
if(isset($_POST['database_type']) && $_POST['database_type'] != 'pgsql')
DB::statement('ALTER TABLE '.$prefix.$site_content_tmplvar." ADD FULLTEXT {$indexPrefix}_content_ft_idx(value)");
if (isset($_POST['database_type']) && $_POST['database_type'] === 'mysql') {
DB::statement(
'ALTER TABLE ' . $prefix . $site_content_tmplvar . " ADD FULLTEXT {$indexPrefix}_content_ft_idx(value)"
);
}
}


Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -15,8 +15,9 @@ public function up()
{
Schema::create('user_attributes', function(Blueprint $table)
{
$indexPrefix = \DB::getTablePrefix() . $table->getTable();
$table->integer('id', true);
$table->integer('internalKey')->default(0)->index("{}_userid");
$table->integer('internalKey')->default(0)->index("{$indexPrefix}_userid");
$table->string('fullname', 100)->default('');
$table->integer('role')->default(0);
$table->string('email', 100)->default('');
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -15,8 +15,9 @@ public function up()
{
Schema::create('web_user_settings', function(Blueprint $table)
{
$table->integer('webuser')->index('webuserid');
$table->string('setting_name', 50)->default('')->index();
$indexPrefix = \DB::getTablePrefix() . $table->getTable();
$table->integer('webuser')->index("{$indexPrefix}_webuserid");
$table->string('setting_name', 50)->default('')->index("{$indexPrefix}_setting_name");
$table->text('setting_value', 65535)->nullable();
$table->primary(['webuser','setting_name']);
});
Expand Down