mirror of
https://github.com/shlinkio/shlink.git
synced 2026-02-28 04:03:12 +08:00
189 lines
7.3 KiB
PHP
189 lines
7.3 KiB
PHP
<?php
|
|
|
|
declare(strict_types=1);
|
|
|
|
namespace Shlinkio\Shlink\Core\Config;
|
|
|
|
use Shlinkio\Shlink\Core\Config\Options\ExtraPathMode;
|
|
use Shlinkio\Shlink\Core\ShortUrl\Model\ShortUrlMode;
|
|
|
|
use function date_default_timezone_get;
|
|
use function file_get_contents;
|
|
use function is_file;
|
|
use function Shlinkio\Shlink\Config\env;
|
|
use function Shlinkio\Shlink\Config\parseEnvVar;
|
|
use function sprintf;
|
|
|
|
use const Shlinkio\Shlink\DEFAULT_REDIRECT_CACHE_LIFETIME;
|
|
use const Shlinkio\Shlink\DEFAULT_REDIRECT_STATUS_CODE;
|
|
use const Shlinkio\Shlink\DEFAULT_SHORT_CODES_LENGTH;
|
|
|
|
enum EnvVars: string
|
|
{
|
|
case APP_ENV = 'APP_ENV';
|
|
case DELETE_SHORT_URL_THRESHOLD = 'DELETE_SHORT_URL_THRESHOLD';
|
|
case DB_DRIVER = 'DB_DRIVER';
|
|
case DB_NAME = 'DB_NAME';
|
|
case DB_USER = 'DB_USER';
|
|
case DB_PASSWORD = 'DB_PASSWORD';
|
|
case DB_HOST = 'DB_HOST';
|
|
case DB_UNIX_SOCKET = 'DB_UNIX_SOCKET';
|
|
case DB_PORT = 'DB_PORT';
|
|
case DB_USE_ENCRYPTION = 'DB_USE_ENCRYPTION';
|
|
case GEOLITE_LICENSE_KEY = 'GEOLITE_LICENSE_KEY';
|
|
case CACHE_NAMESPACE = 'CACHE_NAMESPACE';
|
|
case REDIS_SERVERS = 'REDIS_SERVERS';
|
|
case REDIS_SENTINEL_SERVICE = 'REDIS_SENTINEL_SERVICE';
|
|
case REDIS_SERVERS_USER = 'REDIS_SERVERS_USER';
|
|
case REDIS_SERVERS_PASSWORD = 'REDIS_SERVERS_PASSWORD';
|
|
case REDIS_PUB_SUB_ENABLED = 'REDIS_PUB_SUB_ENABLED';
|
|
case MERCURE_ENABLED = 'MERCURE_ENABLED';
|
|
case MERCURE_PUBLIC_HUB_URL = 'MERCURE_PUBLIC_HUB_URL';
|
|
case MERCURE_INTERNAL_HUB_URL = 'MERCURE_INTERNAL_HUB_URL';
|
|
case MERCURE_JWT_SECRET = 'MERCURE_JWT_SECRET';
|
|
case RABBITMQ_ENABLED = 'RABBITMQ_ENABLED';
|
|
case RABBITMQ_HOST = 'RABBITMQ_HOST';
|
|
case RABBITMQ_PORT = 'RABBITMQ_PORT';
|
|
case RABBITMQ_USER = 'RABBITMQ_USER';
|
|
case RABBITMQ_PASSWORD = 'RABBITMQ_PASSWORD';
|
|
case RABBITMQ_VHOST = 'RABBITMQ_VHOST';
|
|
case RABBITMQ_USE_SSL = 'RABBITMQ_USE_SSL';
|
|
case MATOMO_ENABLED = 'MATOMO_ENABLED';
|
|
case MATOMO_BASE_URL = 'MATOMO_BASE_URL';
|
|
case MATOMO_SITE_ID = 'MATOMO_SITE_ID';
|
|
case MATOMO_API_TOKEN = 'MATOMO_API_TOKEN';
|
|
case DEFAULT_INVALID_SHORT_URL_REDIRECT = 'DEFAULT_INVALID_SHORT_URL_REDIRECT';
|
|
case DEFAULT_REGULAR_404_REDIRECT = 'DEFAULT_REGULAR_404_REDIRECT';
|
|
case DEFAULT_BASE_URL_REDIRECT = 'DEFAULT_BASE_URL_REDIRECT';
|
|
case REDIRECT_STATUS_CODE = 'REDIRECT_STATUS_CODE';
|
|
case REDIRECT_CACHE_LIFETIME = 'REDIRECT_CACHE_LIFETIME';
|
|
case REDIRECT_CACHE_VISIBILITY = 'REDIRECT_CACHE_VISIBILITY';
|
|
case BASE_PATH = 'BASE_PATH';
|
|
case SHORT_URL_TRAILING_SLASH = 'SHORT_URL_TRAILING_SLASH';
|
|
case SHORT_URL_MODE = 'SHORT_URL_MODE';
|
|
case ANONYMIZE_REMOTE_ADDR = 'ANONYMIZE_REMOTE_ADDR';
|
|
case TRACK_ORPHAN_VISITS = 'TRACK_ORPHAN_VISITS';
|
|
case DISABLE_TRACK_PARAM = 'DISABLE_TRACK_PARAM';
|
|
case DISABLE_TRACKING = 'DISABLE_TRACKING';
|
|
case DISABLE_IP_TRACKING = 'DISABLE_IP_TRACKING';
|
|
case DISABLE_REFERRER_TRACKING = 'DISABLE_REFERRER_TRACKING';
|
|
case DISABLE_UA_TRACKING = 'DISABLE_UA_TRACKING';
|
|
case DISABLE_TRACKING_FROM = 'DISABLE_TRACKING_FROM';
|
|
case DEFAULT_SHORT_CODES_LENGTH = 'DEFAULT_SHORT_CODES_LENGTH';
|
|
case IS_HTTPS_ENABLED = 'IS_HTTPS_ENABLED';
|
|
case DEFAULT_DOMAIN = 'DEFAULT_DOMAIN';
|
|
case AUTO_RESOLVE_TITLES = 'AUTO_RESOLVE_TITLES';
|
|
case REDIRECT_EXTRA_PATH_MODE = 'REDIRECT_EXTRA_PATH_MODE';
|
|
case MULTI_SEGMENT_SLUGS_ENABLED = 'MULTI_SEGMENT_SLUGS_ENABLED';
|
|
case ROBOTS_ALLOW_ALL_SHORT_URLS = 'ROBOTS_ALLOW_ALL_SHORT_URLS';
|
|
case ROBOTS_USER_AGENTS = 'ROBOTS_USER_AGENTS';
|
|
case TIMEZONE = 'TIMEZONE';
|
|
case MEMORY_LIMIT = 'MEMORY_LIMIT';
|
|
case INITIAL_API_KEY = 'INITIAL_API_KEY';
|
|
case SKIP_INITIAL_GEOLITE_DOWNLOAD = 'SKIP_INITIAL_GEOLITE_DOWNLOAD';
|
|
case REAL_TIME_UPDATES_TOPICS = 'REAL_TIME_UPDATES_TOPICS';
|
|
case CORS_ALLOW_ORIGIN = 'CORS_ALLOW_ORIGIN';
|
|
case CORS_ALLOW_CREDENTIALS = 'CORS_ALLOW_CREDENTIALS';
|
|
case CORS_MAX_AGE = 'CORS_MAX_AGE';
|
|
case TRUSTED_PROXIES = 'TRUSTED_PROXIES';
|
|
case LOGS_FORMAT = 'LOGS_FORMAT';
|
|
|
|
public function loadFromEnv(): mixed
|
|
{
|
|
return env($this->value) ?? $this->loadFromFileEnv() ?? $this->defaultValue();
|
|
}
|
|
|
|
/**
|
|
* Checks if an equivalent environment variable exists with the `_FILE` suffix. If so, it loads its value as a file,
|
|
* reads it, and returns its contents.
|
|
* This is useful when loading Shlink with docker compose and using secrets.
|
|
* See https://docs.docker.com/compose/use-secrets/
|
|
*/
|
|
private function loadFromFileEnv(): string|int|bool|null
|
|
{
|
|
$file = env(sprintf('%s_FILE', $this->value));
|
|
if ($file === null || ! is_file($file)) {
|
|
return null;
|
|
}
|
|
|
|
$content = file_get_contents($file);
|
|
return $content ? parseEnvVar($content) : null;
|
|
}
|
|
|
|
private function defaultValue(): string|int|bool|null
|
|
{
|
|
return match ($this) {
|
|
self::APP_ENV => 'prod',
|
|
self::MEMORY_LIMIT => '512M',
|
|
self::TIMEZONE => date_default_timezone_get(),
|
|
|
|
self::DEFAULT_SHORT_CODES_LENGTH => DEFAULT_SHORT_CODES_LENGTH,
|
|
self::SHORT_URL_MODE => ShortUrlMode::STRICT->value,
|
|
self::IS_HTTPS_ENABLED, self::AUTO_RESOLVE_TITLES => true,
|
|
self::MULTI_SEGMENT_SLUGS_ENABLED,
|
|
self::SHORT_URL_TRAILING_SLASH => false,
|
|
self::DEFAULT_DOMAIN, self::BASE_PATH => '',
|
|
self::CACHE_NAMESPACE => 'Shlink',
|
|
self::REDIRECT_EXTRA_PATH_MODE => ExtraPathMode::DEFAULT->value,
|
|
|
|
self::REDIS_PUB_SUB_ENABLED,
|
|
self::MATOMO_ENABLED,
|
|
self::ROBOTS_ALLOW_ALL_SHORT_URLS => false,
|
|
|
|
self::DB_NAME => 'shlink',
|
|
self::DB_HOST => self::DB_UNIX_SOCKET->loadFromEnv(),
|
|
self::DB_DRIVER => 'sqlite',
|
|
self::DB_PORT => match (self::DB_DRIVER->loadFromEnv()) {
|
|
'postgres' => '5432',
|
|
'mssql' => '1433',
|
|
default => '3306',
|
|
},
|
|
self::DB_USE_ENCRYPTION => false,
|
|
|
|
self::MERCURE_ENABLED => self::MERCURE_PUBLIC_HUB_URL->existsInEnv(),
|
|
self::MERCURE_INTERNAL_HUB_URL => self::MERCURE_PUBLIC_HUB_URL->loadFromEnv(),
|
|
|
|
self::RABBITMQ_ENABLED, self::RABBITMQ_USE_SSL => false,
|
|
self::RABBITMQ_PORT => 5672,
|
|
self::RABBITMQ_VHOST => '/',
|
|
|
|
self::REDIRECT_STATUS_CODE => DEFAULT_REDIRECT_STATUS_CODE->value,
|
|
self::REDIRECT_CACHE_LIFETIME => DEFAULT_REDIRECT_CACHE_LIFETIME,
|
|
|
|
self::ANONYMIZE_REMOTE_ADDR, self::TRACK_ORPHAN_VISITS => true,
|
|
self::DISABLE_TRACKING,
|
|
self::DISABLE_IP_TRACKING,
|
|
self::DISABLE_REFERRER_TRACKING,
|
|
self::DISABLE_UA_TRACKING => false,
|
|
|
|
self::CORS_ALLOW_ORIGIN => '*',
|
|
self::CORS_ALLOW_CREDENTIALS => false,
|
|
self::CORS_MAX_AGE => 3600,
|
|
|
|
self::LOGS_FORMAT => 'console',
|
|
|
|
default => null,
|
|
};
|
|
}
|
|
|
|
public function existsInEnv(): bool
|
|
{
|
|
return $this->loadFromEnv() !== null;
|
|
}
|
|
|
|
public static function isProdEnv(): bool
|
|
{
|
|
return self::APP_ENV->loadFromEnv() === 'prod';
|
|
}
|
|
|
|
public static function isDevEnv(): bool
|
|
{
|
|
return self::APP_ENV->loadFromEnv() === 'dev';
|
|
}
|
|
|
|
public static function isTestEnv(): bool
|
|
{
|
|
return self::APP_ENV->loadFromEnv() === 'test';
|
|
}
|
|
}
|