Add a 'Clear' button next to the cloud-init script dropdown that:
- Resets the dropdown to default (placeholder option)
- Clears the cloud-init script textarea
- Clears the script name input
- Unchecks the 'save script' checkbox
Improves UX by allowing users to quickly reset cloud-init fields
without manually clearing each field.
🤖 Generated with [Claude Code](https://claude.com/claude-code)
Co-Authored-By: Claude <noreply@anthropic.com>
Remove debug sleep(4) statement from openSearchModal method.
🤖 Generated with [Claude Code](https://claude.com/claude-code)
Co-Authored-By: Claude <noreply@anthropic.com>
- Add manual cache clearing command (search:clear) for testing
- Integrate cloud-init scripts into global search navigation
- Improve form UX by preventing field reset during edit operations
🤖 Generated with [Claude Code](https://claude.com/claude-code)
Co-Authored-By: Claude <noreply@anthropic.com>
Changed backup_log_uuid property to nullable and removed eager initialization in constructor. This allows the ID to be generated when actually needed rather than upfront.
🤖 Generated with [Claude Code](https://claude.com/claude-code)
Co-Authored-By: Claude <noreply@anthropic.com>
Add a new artisan command for manually clearing the global search cache
during development and testing. This is useful when testing new navigation
entries or updates to searchable resources without waiting for the 5-minute
cache TTL.
Command: php artisan search:clear
Usage options:
- search:clear - Clear cache for current user's team
- search:clear --team=1 - Clear cache for specific team ID
- search:clear --all - Clear cache for all teams
This helps developers test global search changes immediately, especially
when adding new navigation routes like cloud-init scripts.
🤖 Generated with [Claude Code](https://claude.com/claude-code)
Co-Authored-By: Claude <noreply@anthropic.com>
Add cloud-init scripts to the global search navigation routes, making
them discoverable via the quick search (Cmd+K / Ctrl+K).
Changes:
- Added dedicated "Cloud-Init Scripts" navigation entry
- Searchable via: cloud-init, scripts, cloud init, cloudinit,
initialization, startup, server setup
- Updated Security entry to include cloud-init in search terms
- Links to /security/cloud-init-scripts route
Users can now quickly navigate to cloud-init script management by
typing "cloud-init" or related terms in global search.
🤖 Generated with [Claude Code](https://claude.com/claude-code)
Co-Authored-By: Claude <noreply@anthropic.com>
Fix multiple UI/UX issues with cloud-init scripts management:
1. Fix card styling - Remove purple box background, use simple border
- Changed from .box class to inline flex/border styling
- Matches cloud provider tokens styling pattern
2. Remove script preview section
- Preview was taking too much space and looked cluttered
- Users can edit to see full script content
3. Make edit modal full width
- Added fullWidth attribute to x-modal-input component
- Provides better editing experience for long scripts
4. Fix fields clearing after update
- Fields were being reset even in edit mode
- Now only reset fields when creating new script
- Edit mode preserves values after save
🤖 Generated with [Claude Code](https://claude.com/claude-code)
Co-Authored-By: Claude <noreply@anthropic.com>
Add comprehensive cloud-init script management interface in the Security
section, allowing users to create, edit, delete, and reuse cloud-init
scripts across their team.
New Components:
- CloudInitScripts: Main listing page with grid view of scripts
- CloudInitScriptForm: Modal form for create/edit operations
Features:
- Create new cloud-init scripts with name and content
- Edit existing scripts
- Delete scripts with confirmation (requires typing script name)
- View script preview (first 200 characters)
- Scripts are encrypted in database
- Full authorization using CloudInitScriptPolicy
- Real-time updates via Livewire events
UI Location:
- Added to Security section nav: /security/cloud-init-scripts
- Positioned between Cloud Tokens and API Tokens
- Follows existing security UI patterns
Files Created:
- app/Livewire/Security/CloudInitScripts.php
- app/Livewire/Security/CloudInitScriptForm.php
- resources/views/livewire/security/cloud-init-scripts.blade.php
- resources/views/livewire/security/cloud-init-script-form.blade.php
Files Modified:
- routes/web.php - Added route
- resources/views/components/security/navbar.blade.php - Added nav link
🤖 Generated with [Claude Code](https://claude.com/claude-code)
Co-Authored-By: Claude <noreply@anthropic.com>
Add cloud-init script fields to the resetSelection() method that's
called when the modal is closed. This ensures a clean slate when
reopening the "Connect a Hetzner Server" view.
Fields reset:
- cloud_init_script
- save_cloud_init_script
- cloud_init_script_name
- selected_cloud_init_script_id
🤖 Generated with [Claude Code](https://claude.com/claude-code)
Co-Authored-By: Claude <noreply@anthropic.com>
Add detailed ray logging to track exactly what is being sent to Hetzner's
API and what response is received. This will help debug cloud-init script
integration and verify that user_data is properly included in the request.
Logs include:
- Request endpoint and full params object
- Complete API response
🤖 Generated with [Claude Code](https://claude.com/claude-code)
Co-Authored-By: Claude <noreply@anthropic.com>
Changes:
1. Remove description field from cloud-init scripts
- Updated migration to remove description column
- Updated model to remove description from fillable array
2. Redesign script name input layout
- Move script name input next to checkbox (always visible)
- Remove conditional rendering - input always shown
- Use placeholder instead of label for cleaner look
3. Fix dropdown type error
- Replace wire:change event with wire:model.live
- Use updatedSelectedCloudInitScriptId() lifecycle hook
- Add "disabled" attribute to placeholder option
- Properly handle empty string vs null in type casting
4. Improve validation
- Require both script content AND name for saving
- Remove description validation rule
- Add selected_cloud_init_script_id validation
5. Auto-populate name when loading saved script
- When user selects saved script, auto-fill the name field
🤖 Generated with [Claude Code](https://claude.com/claude-code)
Co-Authored-By: Claude <noreply@anthropic.com>
This commit adds the ability to use cloud-init scripts when creating Hetzner servers through the integration. Users can write custom scripts that will be executed during server initialization, and optionally save these scripts at the team level for future reuse.
Key features:
- Textarea field for entering cloud-init scripts (bash or cloud-config YAML)
- Checkbox to save scripts for later use at team level
- Dropdown to load previously saved scripts
- Scripts are encrypted in the database
- Full validation and authorization checks
- Comprehensive unit and feature tests
🤖 Generated with [Claude Code](https://claude.com/claude-code)
Co-Authored-By: Claude <noreply@anthropic.com>
Display the monthly cost on the "Buy & Create Server" button
to give users clear visibility of the price before purchasing.
- Add computed property to calculate selected server's monthly price
- Update button text to show price dynamically (e.g., "€12.99/mo")
- Add tests for price formatting and edge cases
- Price updates reactively when user changes server type
🤖 Generated with [Claude Code](https://claude.com/claude-code)
Co-Authored-By: Claude <noreply@anthropic.com>
- Add resource UUIDs (application_uuid, database_uuid, server_uuid, task_uuid) to all webhook notifications
- Standardize URL field naming from various formats (resource_url, task_url, server_url) to consistent 'url' field
- Include parent resource UUIDs for scheduled tasks (application_uuid or service_uuid)
- Add direct URLs to Coolify resources for all notification types
- Update UI to show "Webhook URL (POST)" label for clarity
This enables webhook consumers to:
- Uniquely identify resources using UUIDs used throughout Coolify UI
- Directly link back to Coolify resource pages via the url field
🤖 Generated with [Claude Code](https://claude.com/claude-code)
Co-Authored-By: Claude <noreply@anthropic.com>
Add support for configuring IPv4 and IPv6 public network interfaces when creating servers through the Hetzner integration. Users can now enable or disable IPv4 and IPv6 independently, with both enabled by default.
Features:
- Added enable_ipv4 and enable_ipv6 checkboxes in the server creation form
- Both options are enabled by default as per Hetzner best practices
- IPv4 is preferred when both are enabled
- Fallback to IPv6 when only IPv6 is enabled
- Proper validation and error handling for network configuration
- Comprehensive test coverage for IP address selection logic
🤖 Generated with [Claude Code](https://claude.com/claude-code)
Co-Authored-By: Claude <noreply@anthropic.com>
Simplified webhook channel implementation to match TelegramChannel pattern without typed interface.
Changes:
- Removed SendsWebhook interface file
- Removed interface from Team model
- Removed routeNotificationForWebhook() method
- WebhookChannel now uses untyped $notifiable like TelegramChannel
🤖 Generated with [Claude Code](https://claude.com/claude-code)
Co-Authored-By: Claude <noreply@anthropic.com>
Added actual HTTP POST delivery for webhook notifications and comprehensive Ray debugging for development.
Changes:
- Updated Team model to implement SendsWebhook interface
- Added routeNotificationForWebhook() method to Team
- Enhanced SendWebhookJob with Ray logging for request/response
- Added Ray debugging to WebhookChannel for dispatch tracking
- Added Ray debugging to Webhook Livewire component
🤖 Generated with [Claude Code](https://claude.com/claude-code)
Co-Authored-By: Claude <noreply@anthropic.com>
Add basic WebhookChannel infrastructure:
- Create SendsWebhook interface
- Create WebhookChannel with placeholder implementation (logs instead of sending)
- Update Test notification to support webhook channel
- Add WebhookChannel to HasNotificationSettings trait
- Add toWebhook() method to Test notification
This provides a working foundation that won't break test notifications.
The actual HTTP webhook delivery will be implemented in a follow-up.
🤖 Generated with [Claude Code](https://claude.com/claude-code)
Co-Authored-By: Claude <noreply@anthropic.com>
Add webhook case to the Test notification's via() method
to prepare for future WebhookChannel implementation.
🤖 Generated with [Claude Code](https://claude.com/claude-code)
Co-Authored-By: Claude <noreply@anthropic.com>
Add WebhookNotificationSettings to the policy mappings in
AuthServiceProvider to enable authorization checks for the
webhook notification settings.
🤖 Generated with [Claude Code](https://claude.com/claude-code)
Co-Authored-By: Claude <noreply@anthropic.com>
Add basic infrastructure for custom webhook notifications:
- Create webhook_notification_settings table with event toggles
- Add WebhookNotificationSettings model with encrypted URL
- Integrate webhook settings into Team model and HasNotificationSettings trait
- Create Livewire component and Blade view for webhook configuration
- Add webhook navigation route and UI
This provides the foundation for sending webhook notifications to custom HTTP/HTTPS endpoints when events occur in Coolify.
🤖 Generated with [Claude Code](https://claude.com/claude-code)
Co-Authored-By: Claude <noreply@anthropic.com>
- Replaced the inline query for fetching environments in GlobalSearch with a new static method `ownedByCurrentTeam` in the Environment model, enhancing code readability and maintainability.
- This change simplifies the logic for retrieving environments associated with the current team, promoting better organization of query logic within the model.
- Introduced a comprehensive set of navigation routes for quick access to key sections such as Dashboard, Servers, Projects, and more.
- Enhanced the search functionality to include a 'new' prefix for creating resources directly from the search input.
- Improved UI elements for search results, ensuring better visibility and interaction.