refactor(validation): implement centralized validation patterns across components
- Introduced `ValidationPatterns` class to standardize validation rules and messages for various fields across multiple components. - Updated components including `General`, `StackForm`, `Create`, and `Show` to utilize the new validation patterns, ensuring consistent validation logic. - Enhanced error messages for required fields and added regex validation for names and descriptions to improve user feedback. - Adjusted styling in the `create.blade.php` view for better visual hierarchy.
This commit is contained in:
@@ -5,9 +5,9 @@ namespace App\Livewire\Server\New;
|
||||
use App\Enums\ProxyTypes;
|
||||
use App\Models\Server;
|
||||
use App\Models\Team;
|
||||
use App\Support\ValidationPatterns;
|
||||
use Illuminate\Support\Collection;
|
||||
use Livewire\Attributes\Locked;
|
||||
use Livewire\Attributes\Validate;
|
||||
use Livewire\Component;
|
||||
|
||||
class ByIp extends Component
|
||||
@@ -18,43 +18,30 @@ class ByIp extends Component
|
||||
#[Locked]
|
||||
public $limit_reached;
|
||||
|
||||
#[Validate('nullable|integer', as: 'Private Key')]
|
||||
public ?int $private_key_id = null;
|
||||
|
||||
#[Validate('nullable|string', as: 'Private Key Name')]
|
||||
public $new_private_key_name;
|
||||
|
||||
#[Validate('nullable|string', as: 'Private Key Description')]
|
||||
public $new_private_key_description;
|
||||
|
||||
#[Validate('nullable|string', as: 'Private Key Value')]
|
||||
public $new_private_key_value;
|
||||
|
||||
#[Validate('required|string', as: 'Name')]
|
||||
public string $name;
|
||||
|
||||
#[Validate('nullable|string', as: 'Description')]
|
||||
public ?string $description = null;
|
||||
|
||||
#[Validate('required|string', as: 'IP Address/Domain')]
|
||||
public string $ip;
|
||||
|
||||
#[Validate('required|string', as: 'User')]
|
||||
public string $user = 'root';
|
||||
|
||||
#[Validate('required|integer|between:1,65535', as: 'Port')]
|
||||
public int $port = 22;
|
||||
|
||||
#[Validate('required|boolean', as: 'Swarm Manager')]
|
||||
public bool $is_swarm_manager = false;
|
||||
|
||||
#[Validate('required|boolean', as: 'Swarm Worker')]
|
||||
public bool $is_swarm_worker = false;
|
||||
|
||||
#[Validate('nullable|integer', as: 'Swarm Cluster')]
|
||||
public $selected_swarm_cluster = null;
|
||||
|
||||
#[Validate('required|boolean', as: 'Build Server')]
|
||||
public bool $is_build_server = false;
|
||||
|
||||
#[Locked]
|
||||
@@ -70,6 +57,50 @@ class ByIp extends Component
|
||||
}
|
||||
}
|
||||
|
||||
protected function rules(): array
|
||||
{
|
||||
return [
|
||||
'private_key_id' => 'nullable|integer',
|
||||
'new_private_key_name' => 'nullable|string',
|
||||
'new_private_key_description' => 'nullable|string',
|
||||
'new_private_key_value' => 'nullable|string',
|
||||
'name' => ValidationPatterns::nameRules(),
|
||||
'description' => ValidationPatterns::descriptionRules(),
|
||||
'ip' => 'required|string',
|
||||
'user' => 'required|string',
|
||||
'port' => 'required|integer|between:1,65535',
|
||||
'is_swarm_manager' => 'required|boolean',
|
||||
'is_swarm_worker' => 'required|boolean',
|
||||
'selected_swarm_cluster' => 'nullable|integer',
|
||||
'is_build_server' => 'required|boolean',
|
||||
];
|
||||
}
|
||||
|
||||
protected function messages(): array
|
||||
{
|
||||
return array_merge(ValidationPatterns::combinedMessages(), [
|
||||
'private_key_id.integer' => 'The Private Key field must be an integer.',
|
||||
'private_key_id.nullable' => 'The Private Key field is optional.',
|
||||
'new_private_key_name.string' => 'The Private Key Name must be a string.',
|
||||
'new_private_key_description.string' => 'The Private Key Description must be a string.',
|
||||
'new_private_key_value.string' => 'The Private Key Value must be a string.',
|
||||
'ip.required' => 'The IP Address/Domain is required.',
|
||||
'ip.string' => 'The IP Address/Domain must be a string.',
|
||||
'user.required' => 'The User field is required.',
|
||||
'user.string' => 'The User field must be a string.',
|
||||
'port.required' => 'The Port field is required.',
|
||||
'port.integer' => 'The Port field must be an integer.',
|
||||
'port.between' => 'The Port field must be between 1 and 65535.',
|
||||
'is_swarm_manager.required' => 'The Swarm Manager field is required.',
|
||||
'is_swarm_manager.boolean' => 'The Swarm Manager field must be true or false.',
|
||||
'is_swarm_worker.required' => 'The Swarm Worker field is required.',
|
||||
'is_swarm_worker.boolean' => 'The Swarm Worker field must be true or false.',
|
||||
'selected_swarm_cluster.integer' => 'The Swarm Cluster field must be an integer.',
|
||||
'is_build_server.required' => 'The Build Server field is required.',
|
||||
'is_build_server.boolean' => 'The Build Server field must be true or false.',
|
||||
]);
|
||||
}
|
||||
|
||||
public function setPrivateKey(string $private_key_id)
|
||||
{
|
||||
$this->private_key_id = $private_key_id;
|
||||
|
||||
@@ -6,82 +6,60 @@ use App\Actions\Server\StartSentinel;
|
||||
use App\Actions\Server\StopSentinel;
|
||||
use App\Events\ServerReachabilityChanged;
|
||||
use App\Models\Server;
|
||||
use App\Support\ValidationPatterns;
|
||||
use Livewire\Attributes\Computed;
|
||||
use Livewire\Attributes\Locked;
|
||||
use Livewire\Attributes\Validate;
|
||||
use Livewire\Component;
|
||||
|
||||
class Show extends Component
|
||||
{
|
||||
public Server $server;
|
||||
|
||||
#[Validate(['required'])]
|
||||
public string $name;
|
||||
|
||||
#[Validate(['nullable'])]
|
||||
public ?string $description = null;
|
||||
|
||||
#[Validate(['required'])]
|
||||
public string $ip;
|
||||
|
||||
#[Validate(['required'])]
|
||||
public string $user;
|
||||
|
||||
#[Validate(['required'])]
|
||||
public string $port;
|
||||
|
||||
#[Validate(['nullable'])]
|
||||
public ?string $validationLogs = null;
|
||||
|
||||
#[Validate(['nullable', 'url'])]
|
||||
public ?string $wildcardDomain = null;
|
||||
|
||||
#[Validate(['required'])]
|
||||
public bool $isReachable;
|
||||
|
||||
#[Validate(['required'])]
|
||||
public bool $isUsable;
|
||||
|
||||
#[Validate(['required'])]
|
||||
public bool $isSwarmManager;
|
||||
|
||||
#[Validate(['required'])]
|
||||
public bool $isSwarmWorker;
|
||||
|
||||
#[Validate(['required'])]
|
||||
public bool $isBuildServer;
|
||||
|
||||
#[Locked]
|
||||
public bool $isBuildServerLocked = false;
|
||||
|
||||
#[Validate(['required'])]
|
||||
public bool $isMetricsEnabled;
|
||||
|
||||
#[Validate(['required'])]
|
||||
public string $sentinelToken;
|
||||
|
||||
#[Validate(['nullable'])]
|
||||
public ?string $sentinelUpdatedAt = null;
|
||||
|
||||
#[Validate(['required', 'integer', 'min:1'])]
|
||||
public int $sentinelMetricsRefreshRateSeconds;
|
||||
|
||||
#[Validate(['required', 'integer', 'min:1'])]
|
||||
public int $sentinelMetricsHistoryDays;
|
||||
|
||||
#[Validate(['required', 'integer', 'min:10'])]
|
||||
public int $sentinelPushIntervalSeconds;
|
||||
|
||||
#[Validate(['nullable', 'url'])]
|
||||
public ?string $sentinelCustomUrl = null;
|
||||
|
||||
#[Validate(['required'])]
|
||||
public bool $isSentinelEnabled;
|
||||
|
||||
#[Validate(['required'])]
|
||||
public bool $isSentinelDebugEnabled;
|
||||
|
||||
#[Validate(['required'])]
|
||||
public string $serverTimezone;
|
||||
|
||||
public function getListeners()
|
||||
@@ -91,6 +69,59 @@ class Show extends Component
|
||||
];
|
||||
}
|
||||
|
||||
protected function rules(): array
|
||||
{
|
||||
return [
|
||||
'name' => ValidationPatterns::nameRules(),
|
||||
'description' => ValidationPatterns::descriptionRules(),
|
||||
'ip' => 'required',
|
||||
'user' => 'required',
|
||||
'port' => 'required',
|
||||
'validationLogs' => 'nullable',
|
||||
'wildcardDomain' => 'nullable|url',
|
||||
'isReachable' => 'required',
|
||||
'isUsable' => 'required',
|
||||
'isSwarmManager' => 'required',
|
||||
'isSwarmWorker' => 'required',
|
||||
'isBuildServer' => 'required',
|
||||
'isMetricsEnabled' => 'required',
|
||||
'sentinelToken' => 'required',
|
||||
'sentinelUpdatedAt' => 'nullable',
|
||||
'sentinelMetricsRefreshRateSeconds' => 'required|integer|min:1',
|
||||
'sentinelMetricsHistoryDays' => 'required|integer|min:1',
|
||||
'sentinelPushIntervalSeconds' => 'required|integer|min:10',
|
||||
'sentinelCustomUrl' => 'nullable|url',
|
||||
'isSentinelEnabled' => 'required',
|
||||
'isSentinelDebugEnabled' => 'required',
|
||||
'serverTimezone' => 'required',
|
||||
];
|
||||
}
|
||||
|
||||
protected function messages(): array
|
||||
{
|
||||
return array_merge(
|
||||
ValidationPatterns::combinedMessages(),
|
||||
[
|
||||
'ip.required' => 'The IP Address field is required.',
|
||||
'user.required' => 'The User field is required.',
|
||||
'port.required' => 'The Port field is required.',
|
||||
'wildcardDomain.url' => 'The Wildcard Domain must be a valid URL.',
|
||||
'sentinelToken.required' => 'The Sentinel Token field is required.',
|
||||
'sentinelMetricsRefreshRateSeconds.required' => 'The Metrics Refresh Rate field is required.',
|
||||
'sentinelMetricsRefreshRateSeconds.integer' => 'The Metrics Refresh Rate must be an integer.',
|
||||
'sentinelMetricsRefreshRateSeconds.min' => 'The Metrics Refresh Rate must be at least 1 second.',
|
||||
'sentinelMetricsHistoryDays.required' => 'The Metrics History Days field is required.',
|
||||
'sentinelMetricsHistoryDays.integer' => 'The Metrics History Days must be an integer.',
|
||||
'sentinelMetricsHistoryDays.min' => 'The Metrics History Days must be at least 1 day.',
|
||||
'sentinelPushIntervalSeconds.required' => 'The Push Interval field is required.',
|
||||
'sentinelPushIntervalSeconds.integer' => 'The Push Interval must be an integer.',
|
||||
'sentinelPushIntervalSeconds.min' => 'The Push Interval must be at least 10 seconds.',
|
||||
'sentinelCustomUrl.url' => 'The Custom Sentinel URL must be a valid URL.',
|
||||
'serverTimezone.required' => 'The Server Timezone field is required.',
|
||||
]
|
||||
);
|
||||
}
|
||||
|
||||
public function mount(string $server_uuid)
|
||||
{
|
||||
try {
|
||||
|
||||
Reference in New Issue
Block a user