Files
fitme3070.pt/shared/platform-tools/backups/config.php
T
andreandClaude Opus 5 4d40adbf64 Vendor platform-tools: everything this site runs is now in one repo
shared/platform-tools was a git submodule. On this branch it is a plain
directory of tracked files, frozen at ea3616abae30106df283e73a3e2f9e5bb0e6ae90
— the same commit fotografia.andmore.pt pins. Contents are byte-identical to
that tree, verified blob by blob.

The submodule caused every deployment failure this site has had:

  - .gitmodules named no `branch`, so the update fell back to
    refs/remotes/origin/HEAD — a ref a plain server-side clone never writes.
    "Atualizar submódulo" failed with "Unable to find refs/remotes/origin/HEAD
    revision in submodule path".
  - Its URL was http://, which the origin answers with 523.
  - This install is deployed by uploading files, and a submodule is invisible
    to that. The tree moved forward while shared/platform-tools stayed on the
    old pin, config/functions_secrets.php died on a missing compat_secrets.php,
    and the whole site — public pages included — went down.

Each of those was separately fixable. Together they mean a second repository
nobody can see from the deployment path, gating whether the first one boots. A
plain directory deploys like every other file and cannot fall out of step.

The cost is that platform-tools updates no longer arrive by bumping a pin; they
are a copy-over-and-commit. shared/platform-tools/VENDORED.md records the
upstream SHA, the procedure, and which four files differ from upstream in line
endings only (social/*.js, .css, functions_publications.php — CRLF upstream,
normalised to LF here; content otherwise identical).

Co-Authored-By: Claude Opus 5 <noreply@anthropic.com>
2026-09-13 23:06:23 +01:00

96 lines
3.7 KiB
PHP

<?php
/**
* Configuração partilhada pelos scripts de backup.
* Assumed location: <host>/shared/platform-tools/backups/config.php
*
* Valores vêm do .env na raiz do projecto (<host>/.env, gitignored). Os
* fallbacks abaixo só são usados se o .env estiver ausente — em produção,
* mete sempre o .env preenchido.
*/
$host_root = dirname(__DIR__, 3);
// Three host patterns coexist:
// - fotografia-style : config/env.php exposes env_load(), needs an explicit call
// - dsa/moremio-style: config/env.php auto-loads .env via an IIFE; require is enough
// - surf-style : no config/ directory at all -- src/config.php plus
// vlucas/phpdotenv, which has already populated $_ENV and
// getenv() by the time a web request reaches here.
// Requiring config/env.php unconditionally fataled on the third layout.
if (is_file($host_root . '/config/env.php')) {
require_once $host_root . '/config/env.php';
if (function_exists('env_load')) {
env_load($host_root . '/.env');
}
}
// Fallback reader for hosts with no config/env.php, and for CLI invocations
// that run before any framework bootstrap: parse .env directly rather than
// assuming something else already did.
if (!function_exists('env')) {
function env(string $key, $default = null) {
$v = getenv($key);
if ($v === false && array_key_exists($key, $_ENV)) $v = $_ENV[$key];
if ($v !== false && $v !== null) return $v;
static $parsed = null;
if ($parsed === null) {
$parsed = [];
$f = dirname(__DIR__, 3) . '/.env';
if (is_file($f) && is_readable($f)) {
foreach (file($f, FILE_IGNORE_NEW_LINES | FILE_SKIP_EMPTY_LINES) as $line) {
$line = trim($line);
if ($line === '' || $line[0] === '#' || !str_contains($line, '=')) continue;
[$k, $val] = array_pad(explode('=', $line, 2), 2, '');
$parsed[trim($k)] = trim(trim($val), " \"'");
}
}
}
return array_key_exists($key, $parsed) ? $parsed[$key] : $default;
}
}
define('BACKUP_TOKEN', env('BACKUP_TOKEN', 'replace_me'));
define('BACKUP_KEEP_DAYS', (int) env('BACKUP_KEEP_DAYS', 7));
// Pasta (relativa à raiz do host) que o backup de ficheiros arquiva. Só os
// uploads têm informação externa — todo o resto é reconstituível a partir do
// git — por isso o default é 'uploads'. Overridável no .env se um host
// guardar os uploads noutro sítio.
define('BACKUP_FILES_DIR', trim((string) env('BACKUP_FILES_DIR', 'uploads'), '/'));
// Credenciais da base de dados — sem fallbacks reais: se o .env faltar, a
// ligação falha alto em vez de tentar um host/utilizador "mágico".
define('DB_HOST', env('DB_HOST', 'localhost'));
define('DB_PORT', (int) env('DB_PORT', 3306));
define('DB_NAME', env('DB_NAME', ''));
define('DB_USER', env('DB_USER', ''));
define('DB_PASS', env('DB_PASS', ''));
define('DB_CHARSET', 'utf8mb4');
/**
* Apaga backups mais antigos que BACKUP_KEEP_DAYS na pasta indicada.
* $pattern — glob pattern para identificar os ficheiros (ex: 'backup_*.zip')
*/
function cleanOldBackups(string $dir, string $pattern): void
{
$cutoff = time() - (BACKUP_KEEP_DAYS * 86400);
$files = glob($dir . '/' . $pattern) ?: [];
$deleted = 0;
foreach ($files as $file) {
if (filemtime($file) < $cutoff) {
if (@unlink($file)) {
$deleted++;
echo "Apagado (antigo): " . basename($file) . "\n";
}
}
}
if ($deleted === 0) {
echo "Rotação: nenhum backup antigo para apagar.\n";
} else {
echo "Rotação: $deleted ficheiro(s) apagado(s).\n";
}
}