feat: add app and database modules
This commit is contained in:
@@ -0,0 +1,246 @@
|
||||
<?php
|
||||
|
||||
namespace App\Http\Requests\SystemSettings;
|
||||
|
||||
use Illuminate\Foundation\Http\FormRequest;
|
||||
|
||||
class UpdateSystemConfigRequest extends FormRequest
|
||||
{
|
||||
public function authorize(): bool
|
||||
{
|
||||
$user = $this->user();
|
||||
if (!$user) {
|
||||
return false;
|
||||
}
|
||||
|
||||
// Allow if Developer or legacy manage permission exists
|
||||
if ($user->hasRole('Developer') || $user->can('manage global settings')) {
|
||||
return true;
|
||||
}
|
||||
|
||||
// Allow if any granular manage global settings permission exists (direct or via role)
|
||||
return $user->getAllPermissions()
|
||||
->contains(fn ($p) => str_starts_with($p->name, 'manage global settings:'));
|
||||
}
|
||||
|
||||
public function rules(): array
|
||||
{
|
||||
return [
|
||||
'app_name' => ['sometimes', 'required', 'string', 'min:3', 'max:100'],
|
||||
'app_tagline' => ['nullable', 'string', 'max:150'],
|
||||
'app_tagline1' => ['nullable', 'string', 'max:150'],
|
||||
'app_tagline2' => ['nullable', 'string', 'max:300'],
|
||||
'footer_text' => ['nullable', 'string', 'max:200'],
|
||||
'default_locale' => ['nullable', 'string', 'max:10'],
|
||||
'instance_mode' => ['nullable', 'string', 'in:Production,Trial,Demo'],
|
||||
'app_logo' => ['nullable', 'image', 'mimes:jpg,jpeg,png,webp', 'max:2048'],
|
||||
'app_favicon' => ['nullable', 'image', 'mimes:png,ico,webp', 'max:1024'],
|
||||
'enable_landing_page' => ['nullable', 'boolean'],
|
||||
'feature_notification_center' => ['nullable', 'boolean'],
|
||||
'feature_google_oauth' => ['nullable', 'boolean'],
|
||||
'google_client_id' => ['nullable', 'string', 'max:255'],
|
||||
'google_client_secret' => ['nullable', 'string', 'max:255'],
|
||||
'feature_facebook_oauth' => ['nullable', 'boolean'],
|
||||
'facebook_app_id' => ['nullable', 'string', 'max:255'],
|
||||
'facebook_app_secret' => ['nullable', 'string', 'max:255'],
|
||||
'feature_github_oauth' => ['nullable', 'boolean'],
|
||||
'github_client_id' => ['nullable', 'string', 'max:255'],
|
||||
'github_client_secret' => ['nullable', 'string', 'max:255'],
|
||||
'social_login_callback_url' => ['nullable', 'string', 'max:255'],
|
||||
|
||||
// Regional
|
||||
'regional_timezone' => ['nullable', 'string', 'max:100'],
|
||||
'regional_date_format' => ['nullable', 'string', 'max:20'],
|
||||
'regional_time_format' => ['nullable', 'string', 'max:20'],
|
||||
|
||||
// Login Security
|
||||
'login_max_attempts' => ['nullable', 'integer', 'min:1', 'max:20'],
|
||||
'login_lockout_duration' => ['nullable', 'integer', 'min:1', 'max:1440'],
|
||||
'login_lockout_notify' => ['nullable', 'boolean'],
|
||||
'two_factor_auth' => ['nullable', 'boolean'],
|
||||
'two_factor_method' => ['nullable', 'string', 'in:email,app'],
|
||||
'captcha_enabled' => ['nullable', 'boolean'],
|
||||
'captcha_site_key' => ['nullable', 'string', 'max:255'],
|
||||
'captcha_secret_key' => ['nullable', 'string', 'max:255'],
|
||||
'captcha_version' => ['nullable', 'string', 'in:v2,v3'],
|
||||
'login_log_enabled' => ['nullable', 'boolean'],
|
||||
|
||||
// Password Policy
|
||||
'password_min_length' => ['nullable', 'integer', 'min:8', 'max:100'],
|
||||
'password_max_length' => ['nullable', 'integer', 'min:8', 'max:255'],
|
||||
'password_require_uppercase' => ['nullable', 'boolean'],
|
||||
'password_require_lowercase' => ['nullable', 'boolean'],
|
||||
'password_require_numeric' => ['nullable', 'boolean'],
|
||||
'password_require_special' => ['nullable', 'boolean'],
|
||||
'password_expiry_days' => ['nullable', 'integer', 'min:0', 'max:365'],
|
||||
'password_history_count' => ['nullable', 'integer', 'min:0', 'max:10'],
|
||||
'password_reset_link_expiry' => ['nullable', 'integer', 'min:1', 'max:10080'],
|
||||
|
||||
// Session Security
|
||||
'session_driver' => ['nullable', 'string', 'in:file,redis,database'],
|
||||
'session_lifetime' => ['nullable', 'integer', 'min:1', 'max:10080'],
|
||||
'session_single_session' => ['nullable', 'boolean'],
|
||||
'session_auto_logout_idle' => ['nullable', 'integer', 'min:1', 'max:10080'],
|
||||
'session_allow_remember_me' => ['nullable', 'boolean'],
|
||||
'session_remember_me_duration' => ['nullable', 'integer', 'min:1', 'max:365'],
|
||||
'session_secure_cookie' => ['nullable', 'boolean'],
|
||||
'session_encrypt' => ['nullable', 'boolean'],
|
||||
'session_concurrent_limit' => ['nullable', 'integer', 'min:0', 'max:50'],
|
||||
|
||||
// WebAuthn
|
||||
'two_factor_trust_days' => ['nullable', 'integer', 'min:1', 'max:365'],
|
||||
'webauthn_enabled' => ['nullable', 'boolean'],
|
||||
|
||||
// IP & Access Control
|
||||
'ip_whitelist_admin' => ['nullable', 'string'],
|
||||
'ip_blacklist' => ['nullable', 'string'],
|
||||
'rate_limit_per_ip' => ['nullable', 'integer', 'min:1', 'max:1000'],
|
||||
'auto_block_ip' => ['nullable', 'boolean'],
|
||||
'threshold_auto_block' => ['nullable', 'integer', 'min:1', 'max:5000'],
|
||||
'force_https' => ['nullable', 'boolean'],
|
||||
'hsts_enabled' => ['nullable', 'boolean'],
|
||||
'cors_origins' => ['nullable', 'string'],
|
||||
'cors_methods' => ['nullable', 'string'],
|
||||
'cors_headers' => ['nullable', 'string'],
|
||||
|
||||
// Notifications
|
||||
'mail_driver' => ['nullable', 'string', 'in:smtp,mailgun,ses,mail'],
|
||||
'mail_host' => ['nullable', 'string', 'max:255'],
|
||||
'mail_port' => ['nullable', 'integer', 'min:1', 'max:65535'],
|
||||
'mail_username' => ['nullable', 'string', 'max:255'],
|
||||
'mail_password' => ['nullable', 'string', 'max:255'],
|
||||
'mail_encryption' => ['nullable', 'string', 'in:tls,ssl,null'],
|
||||
'mail_from_address' => ['nullable', 'email', 'max:255'],
|
||||
'mail_from_name' => ['nullable', 'string', 'max:255'],
|
||||
'telegram_bot_token' => ['nullable', 'string', 'max:255'],
|
||||
'telegram_chat_id' => ['nullable', 'string', 'max:255'],
|
||||
|
||||
// Backups
|
||||
'backup_db_enabled' => ['nullable', 'boolean'],
|
||||
'backup_db_driver' => ['nullable', 'string', 'in:local,s3,gdrive'],
|
||||
'backup_db_frequency' => ['nullable', 'string', 'in:hourly,daily,weekly,monthly'],
|
||||
'backup_db_time' => ['nullable', 'string', 'regex:/^[0-9]{2}:[0-9]{2}$/'],
|
||||
'backup_db_retention' => ['nullable', 'integer', 'min:1', 'max:365'],
|
||||
'backup_db_compress' => ['nullable', 'boolean'],
|
||||
'backup_db_encrypt' => ['nullable', 'boolean'],
|
||||
'backup_db_encrypt_key' => ['nullable', 'string', 'min:32', 'max:255'],
|
||||
'backup_db_exclude' => ['nullable', 'string'],
|
||||
'backup_db_notify_on' => ['nullable', 'string', 'in:success,failed,both,none'],
|
||||
'backup_db_notify_to' => ['nullable', 'string', 'max:255'],
|
||||
|
||||
// Google Drive Backups
|
||||
'gdrive_client_id' => ['nullable', 'string', 'max:500'],
|
||||
'gdrive_client_secret' => ['nullable', 'string', 'max:500'],
|
||||
'gdrive_refresh_token' => ['nullable', 'string', 'max:1000'],
|
||||
'gdrive_folder' => ['nullable', 'string', 'max:255'],
|
||||
|
||||
// S3 Backups
|
||||
's3_key' => ['nullable', 'string', 'max:255'],
|
||||
's3_secret' => ['nullable', 'string', 'max:255'],
|
||||
's3_region' => ['nullable', 'string', 'max:100'],
|
||||
's3_bucket' => ['nullable', 'string', 'max:255'],
|
||||
's3_endpoint' => ['nullable', 'string', 'max:500'],
|
||||
|
||||
// Maintenance Mode
|
||||
'maintenance_mode_enabled' => ['nullable', 'boolean'],
|
||||
'maintenance_mode_message' => ['nullable', 'string', 'max:1000'],
|
||||
'maintenance_mode_title' => ['nullable', 'string', 'max:200'],
|
||||
'maintenance_mode_secret' => ['nullable', 'string', 'alpha_dash', 'max:100'],
|
||||
'maintenance_mode_allowed_ips' => ['nullable', 'string'],
|
||||
'maintenance_mode_end_at' => ['nullable', 'date'],
|
||||
'maintenance_mode_retry' => ['nullable', 'integer', 'min:0', 'max:3600'],
|
||||
'maintenance_mode_image' => ['nullable', 'image', 'mimes:jpg,jpeg,png,webp', 'max:2048'],
|
||||
|
||||
// Content & Legal
|
||||
'page_help_content' => ['nullable', 'string'],
|
||||
'page_tos_content' => ['nullable', 'string'],
|
||||
'page_privacy_content' => ['nullable', 'string'],
|
||||
'page_about_content' => ['nullable', 'string'],
|
||||
'page_security_content' => ['nullable', 'string'],
|
||||
'require_pdp_on_registration' => ['nullable', 'boolean'],
|
||||
'feature_cookie_banner' => ['nullable', 'boolean'],
|
||||
'pdp_document_version' => ['nullable', 'integer', 'min:1'],
|
||||
'tos_document_version' => ['nullable', 'integer', 'min:1'],
|
||||
'pdp_dpo_email' => ['nullable', 'email', 'max:255'],
|
||||
'pdp_company_address' => ['nullable', 'string', 'max:500'],
|
||||
|
||||
// AI Configuration
|
||||
'ai_enabled' => ['nullable', 'boolean'],
|
||||
'ai_provider' => ['nullable', 'string', 'in:gpt,gemini,claude,deepseek,grok,mistral,ollama,openrouter'],
|
||||
'ai_gpt_key' => ['nullable', 'string', 'max:255'],
|
||||
'ai_gemini_key' => ['nullable', 'string', 'max:255'],
|
||||
'ai_claude_key' => ['nullable', 'string', 'max:255'],
|
||||
'ai_deepseek_key' => ['nullable', 'string', 'max:255'],
|
||||
'ai_grok_key' => ['nullable', 'string', 'max:255'],
|
||||
'ai_mistral_key' => ['nullable', 'string', 'max:255'],
|
||||
'ai_ollama_base_url' => ['nullable', 'string', 'max:255'],
|
||||
'ai_openrouter_key' => ['nullable', 'string', 'max:255'],
|
||||
'ai_default_model' => ['nullable', 'string', 'max:100'],
|
||||
'ai_system_instruction' => ['nullable', 'string', 'max:5000'],
|
||||
'ai_temperature' => ['nullable', 'numeric', 'min:0', 'max:2'],
|
||||
'ai_max_tokens' => ['nullable', 'integer', 'min:1', 'max:32000'],
|
||||
|
||||
// SAP RFC Configuration
|
||||
'sap_rfc_ashost' => ['nullable', 'string', 'max:255'],
|
||||
'sap_rfc_sysnr' => ['nullable', 'string', 'max:20'],
|
||||
'sap_rfc_client' => ['nullable', 'string', 'max:20'],
|
||||
'sap_rfc_user' => ['nullable', 'string', 'max:255'],
|
||||
'sap_rfc_passwd' => ['nullable', 'string', 'max:255'],
|
||||
'sap_rfc_router' => ['nullable', 'string', 'max:255'],
|
||||
'sap_rfc_trace' => ['nullable', 'string', 'in:0,1,2'],
|
||||
'engine_pulse_enabled' => ['nullable', 'boolean'],
|
||||
'engine_telescope_enabled' => ['nullable', 'boolean'],
|
||||
'engine_swagger_enabled' => ['nullable', 'boolean'],
|
||||
'engine_horizon_enabled' => ['nullable', 'boolean'],
|
||||
'ai_healing_enabled' => ['nullable', 'boolean'],
|
||||
];
|
||||
}
|
||||
|
||||
protected function prepareForValidation(): void
|
||||
{
|
||||
$booleans = [
|
||||
'feature_notification_center',
|
||||
'feature_google_oauth',
|
||||
'feature_facebook_oauth',
|
||||
'feature_github_oauth',
|
||||
'login_lockout_notify',
|
||||
'two_factor_auth',
|
||||
'captcha_enabled',
|
||||
'login_log_enabled',
|
||||
'password_require_uppercase',
|
||||
'password_require_lowercase',
|
||||
'password_require_numeric',
|
||||
'password_require_special',
|
||||
'webauthn_enabled',
|
||||
'session_single_session',
|
||||
'session_allow_remember_me',
|
||||
'session_secure_cookie',
|
||||
'session_encrypt',
|
||||
'auto_block_ip',
|
||||
'force_https',
|
||||
'hsts_enabled',
|
||||
'backup_db_enabled',
|
||||
'backup_db_compress',
|
||||
'backup_db_encrypt',
|
||||
'maintenance_mode_enabled',
|
||||
'require_pdp_on_registration',
|
||||
'feature_cookie_banner',
|
||||
'ai_enabled',
|
||||
'enable_landing_page',
|
||||
'engine_pulse_enabled',
|
||||
'engine_telescope_enabled',
|
||||
'engine_swagger_enabled',
|
||||
'engine_horizon_enabled',
|
||||
'ai_healing_enabled',
|
||||
];
|
||||
|
||||
$updates = [];
|
||||
foreach ($booleans as $key) {
|
||||
$updates[$key] = $this->boolean($key);
|
||||
}
|
||||
|
||||
if (!empty($updates)) {
|
||||
$this->merge($updates);
|
||||
}
|
||||
}
|
||||
}
|
||||
Reference in New Issue
Block a user