Commit graph

3017 commits

Author SHA1 Message Date
Andras Bacsai
226de35146 Revert "fix: S3 download and database restore output showing same content"
This reverts commit d07cc48369ac4beb0405823bf34aad02200e4a6f.
2025-11-14 10:43:19 +01:00
Andras Bacsai
a5dafe785b fix: S3 download and database restore output showing same content
- Add unique wire keys to activity-monitor components (s3-download-monitor and database-restore-monitor)
- Update dispatch calls to target specific components using ->to() method
- This prevents both activity monitors from listening to the same activityMonitor event and displaying identical output
- S3 download now shows in s3-download-monitor component
- Database restore now shows in database-restore-monitor component

🤖 Generated with [Claude Code](https://claude.com/claude-code)

Co-Authored-By: Claude <noreply@anthropic.com>
2025-11-14 10:43:19 +01:00
Andras Bacsai
6cb3e4d515 fix: S3 restore button disabled state and security scopes
- Add Alpine.js entangle bindings for s3StorageId and s3Path to enable
  reactive button state without server requests
- Change button disabled binding from PHP :disabled to Alpine x-bind:disabled
  for client-side reactivity using deferred wire:model inputs
- Replace S3Storage::findOrFail with ownedByCurrentTeam()->findOrFail in
  checkS3File() and downloadFromS3() methods
- Remove redundant manual team verification since ownedByCurrentTeam scope
  automatically filters to current team

🤖 Generated with [Claude Code](https://claude.com/claude-code)

Co-Authored-By: Claude <noreply@anthropic.com>
2025-11-14 10:43:19 +01:00
Andras Bacsai
800396b443 feat: add S3 storage integration for file import
This commit introduces functionality for integrating S3 storage into the import process. It allows users to select S3 storage, check for file existence, and download files directly from S3. This enhancement improves the flexibility of the import feature by enabling users to work with files stored in S3, addressing a common use case for teams that utilize cloud storage solutions.
2025-11-14 10:43:19 +01:00
Andras Bacsai
20099630fc Fix modal width with proper CSS media queries
Previous approach used invalid inline styles with @media queries,
which browsers ignore. Now using:
- Unique modal ID generated with PHP uniqid()
- <style> tag with proper CSS media queries
- ID selector for scoped styling

This properly constrains modal width on large screens while keeping
full width on mobile.

🤖 Generated with [Claude Code](https://claude.com/claude-code)

Co-Authored-By: Claude <noreply@anthropic.com>
2025-11-14 10:05:00 +01:00
Andras Bacsai
95b847191b Fix Tailwind JIT issue with dynamic width classes
Tailwind JIT compiler doesn't compile dynamically interpolated classes
like lg:max-w-[{{ $maxWidth }}]. Switched to inline styles with media
queries to support dynamic min/max width values.

🤖 Generated with [Claude Code](https://claude.com/claude-code)

Co-Authored-By: Claude <noreply@anthropic.com>
2025-11-14 09:58:53 +01:00
Andras Bacsai
e5f50c2b1f Fix modal width: add maxWidth constraint
The previous fix reduced minWidth but modal still expanded to fit
content. Now:
- Added maxWidth prop to modal-input component (default 48rem)
- Set Edit Domains modal to minWidth=32rem, maxWidth=40rem
- This constrains the modal to a reasonable size range

🤖 Generated with [Claude Code](https://claude.com/claude-code)

Co-Authored-By: Claude <noreply@anthropic.com>
2025-11-14 09:46:05 +01:00
Andras Bacsai
4c7d059469 Reduce width of Edit Domains modal
Reduced the minWidth of the Edit Domains modal from 36rem to 24rem
to provide a more compact and focused user experience. The modal
was previously too wide for the simple domain input form.

🤖 Generated with [Claude Code](https://claude.com/claude-code)

Co-Authored-By: Claude <noreply@anthropic.com>
2025-11-14 09:44:41 +01:00
Andras Bacsai
71c89d9ba8
Merge branch 'next' into improve-scheduled-tasks 2025-11-10 14:21:03 +01:00
Andras Bacsai
e63a270fea
Enhance container status tracking and improve user notifications (#7182) 2025-11-10 13:58:22 +01:00
Andras Bacsai
99e97900a5 feat: add automated PORT environment variable detection and UI warnings
Add detection system for PORT environment variable to help users configure applications correctly:

- Add detectPortFromEnvironment() method to Application model to detect PORT env var
- Add getDetectedPortInfoProperty() computed property in General Livewire component
- Display contextual info banners in UI when PORT is detected:
  - Warning when PORT exists but ports_exposes is empty
  - Warning when PORT doesn't match ports_exposes configuration
  - Info message when PORT matches ports_exposes
- Add deployment logging to warn about PORT/ports_exposes mismatches
- Include comprehensive unit tests for port detection logic

The ports_exposes field remains authoritative for proxy configuration, while
PORT detection provides helpful suggestions to users.
2025-11-10 13:43:27 +01:00
Andras Bacsai
68a9f2ca77 feat: add container restart tracking and crash loop detection
Track container restart counts from Docker and detect crash loops to provide better visibility into application health issues.

- Add restart_count, last_restart_at, and last_restart_type columns to applications table
- Detect restart count increases from Docker inspect data and send notifications
- Show restart count badge in UI with warning icon on Logs navigation
- Distinguish between crash restarts and manual restarts
- Implement 30-second grace period to prevent false "exited" status during crash loops
- Reset restart count on manual stop, restart, and redeploy actions
- Add unit tests for restart count tracking logic

This helps users quickly identify when containers are in crash loops and need attention, even when the container status flickers between states during Docker's restart backoff period.
2025-11-10 13:04:31 +01:00
Andras Bacsai
b22e79caec feat(jobs): improve scheduled tasks with retry logic and queue cleanup
- Add retry configuration to CoolifyTask (3 tries, 600s timeout)
- Add retry configuration to ScheduledTaskJob (3 tries, configurable timeout)
- Add retry configuration to DatabaseBackupJob (2 tries)
- Implement exponential backoff for all jobs (30s, 60s, 120s intervals)
- Add failed() handlers with comprehensive error logging to scheduled-errors channel
- Add execution tracking: started_at, retry_count, duration (decimal), error_details
- Add configurable timeout field to scheduled tasks (60-3600s, default 300s)
- Update UI to include timeout configuration in task creation/editing forms
- Increase ScheduledJobManager lock expiration from 60s to 90s for high-load environments
- Implement safe queue cleanup with restart vs runtime modes
  - Restart mode: aggressive cleanup (marks all processing jobs as failed)
  - Runtime mode: conservative cleanup (only marks jobs >12h as failed, skips deployments)
- Add cleanup:redis --restart flag for system startup
- Integrate cleanup into Dev.php init() for development environment
- Increase scheduled-errors log retention from 7 to 14 days
- Create comprehensive test suite (unit and feature tests)
- Add TESTING_GUIDE.md with manual testing instructions

Fixes issues with jobs failing after single attempt and "attempted too many times" errors
2025-11-10 11:11:18 +01:00
Andras Bacsai
bcd225bd22 feat: Implement required port validation for service applications
- Added `requiredPort` property to `ServiceApplicationView` to track the required port for services.
- Introduced modal confirmation for removing required ports, including methods to confirm or cancel the action.
- Enhanced `Service` model with `getRequiredPort` and `requiresPort` methods to retrieve port information from service templates.
- Implemented `extractPortFromUrl` method in `ServiceApplication` to extract port from FQDN URLs.
- Updated frontend views to display warnings when required ports are missing from domains.
- Created unit tests for service port validation and extraction logic, ensuring correct behavior for various scenarios.
- Added feature tests for Livewire component handling of domain submissions with required ports.
2025-11-06 14:32:36 +01:00
Andras Bacsai
239e28630f style: update background colors to use gray-50 for consistency in auth views 2025-11-06 08:43:43 +01:00
Andras Bacsai
6245c9d971 fix: enhance styling for page width component in Blade template 2025-11-05 09:00:25 +01:00
Andras Bacsai
54964d54d4 fix: clean up utility classes and improve readability in Blade templates 2025-11-05 08:59:05 +01:00
Andras Bacsai
e925111595 Merge branch 'next' into light-mode-wtf 2025-11-04 21:16:15 +01:00
Andras Bacsai
8775b3f74d fix: enhance menu item styles and update theme color meta tag 2025-11-04 21:15:59 +01:00
Andras Bacsai
51b5c0a1dd fix: clean up input attributes for PostgreSQL settings in general.blade.php 2025-11-04 21:06:12 +01:00
Andras Bacsai
7b589abfbe fix: fix SPA toggle nginx regeneration and add confirmation modal
- Fix SPA toggle not triggering nginx configuration regeneration by capturing old value before syncData
- Fix similar issue with is_http_basic_auth_enabled using value comparison instead of isDirty
- Remove redundant application settings save() call
- Add confirmation modal to nginx generation button to prevent accidental overwrites
- Pass correct type parameter (spa/static) to generateNginxConfiguration method
2025-11-04 09:48:59 +01:00
Andras Bacsai
fbaa5eb369 feat: Update ApplicationSetting model to include additional boolean casts
- Changed `$cast` to `$casts` in ApplicationSetting model to enable proper boolean casting for new fields.
- Added boolean fields: `is_spa`, `is_build_server_enabled`, `is_preserve_repository_enabled`, `is_container_label_escape_enabled`, `is_container_label_readonly_enabled`, and `use_build_secrets`.

fix: Update Livewire component to reflect new property names

- Updated references in the Livewire component for the new camelCase property names.
- Adjusted bindings and IDs for consistency with the updated model.

test: Add unit tests for ApplicationSetting boolean casting

- Created tests to verify boolean casting for `is_static` and other boolean fields in ApplicationSetting.
- Ensured all boolean fields are correctly defined in the casts array.

test: Implement tests for SynchronizesModelData trait

- Added tests to verify the functionality of the SynchronizesModelData trait, ensuring it correctly syncs properties between the component and the model.
- Included tests for handling non-existent properties gracefully.
2025-11-04 08:43:33 +01:00
Andras Bacsai
f315e4bd9c feat: add dev_helper_version to instance settings and update related functionality 2025-11-03 08:38:43 +01:00
Andras Bacsai
c00de66389 fix: improve run script and enhance sticky header style
The run script has been updated to ensure that all relevant Docker containers are removed before starting the application, which helps prevent conflicts and ensures a clean environment. Additionally, the sticky header in the project selection view now has a background color applied for better visibility against varying content, improving the user experience during scrolling.
2025-11-02 12:51:13 +01:00
Andras Bacsai
2a8fbb3f6e feat: add token validation functionality for Hetzner and DigitalOcean providers 2025-10-29 23:21:38 +01:00
Andras Bacsai
c95e297f39 fix: update boarding flow logic to complete onboarding when server is created 2025-10-29 23:06:39 +01:00
Andras Bacsai
25183d7c71 fix: remove unnecessary step attribute from maximum storage input fields 2025-10-29 20:43:32 +01:00
Andras Bacsai
54a4fa7eee fix: change SMTP port input type to number for better validation 2025-10-29 20:40:16 +01:00
Andras Bacsai
f0db097a90 fix: clean up formatting and remove unnecessary key binding in stack form component 2025-10-27 17:03:19 +01:00
Andras Bacsai
974a8bdf64 fix: add wire:ignore directive to modal component for improved functionality 2025-10-27 17:03:19 +01:00
Andras Bacsai
28fc3feab0 fix: remove wire:ignore from modal and add wire:key to EditCompose component
- Remove wire:ignore from modal-input.blade.php wrapper to allow child Livewire components to be properly tracked
- Add unique wire:key to EditCompose component for proper identification when teleported
- Fixes 'Unable to call component method' error when saving compose files

🤖 Generated with [Claude Code](https://claude.com/claude-code)

Co-Authored-By: Claude <noreply@anthropic.com>
2025-10-27 17:03:19 +01:00
Andras Bacsai
1ab4b9aa31 refactor: simplify project data retrieval and enhance OAuth settings handling 2025-10-27 17:03:19 +01:00
Andras Bacsai
261dc39f02 fix: Monaco editor empty for docker compose applications
This commit fixes two related issues preventing the Monaco editor from displaying Docker Compose file content:

1. Data Sync Issue:
   - After loadComposeFile() fetches the compose content from Git and updates the database model, the Livewire component properties were never synced
   - Monaco editor binds to component properties via wire:model, so it remained empty
   - Fixed by calling syncFromModel() after refresh() in loadComposeFile() method

2. Script Duplication Issue:
   - Multiple Monaco editors on the same page (compose files, dockerfile, labels) caused race condition
   - Each instance tried to inject the Monaco loader script simultaneously
   - Resulted in "SyntaxError: Identifier '_amdLoaderGlobal' has already been declared"
   - Fixed by adding a global flag to prevent duplicate script injection

🤖 Generated with [Claude Code](https://claude.com/claude-code)

Co-Authored-By: Claude <noreply@anthropic.com>
2025-10-27 12:48:20 +01:00
Andras Bacsai
12766695c4 feat: add dynamic viewport-based height for compose editor
- Add Alpine.js reactive height calculation based on viewport size
- Monaco editor now responds to window resize events
- Fix Livewire component structure by moving style tag inside root div
- Update CLAUDE.md to document critical single root element requirement
- Set minimum editor height of 300px with responsive maximum
- Use CSS custom properties to pass calculated height to components
2025-10-27 11:18:25 +01:00
Andras Bacsai
70024f0ca4
Merge pull request #6984 from Cinzya/feature/fix-allowedall-check
fix(settings): prevent false positives in allowed IPs validation
2025-10-26 11:00:15 +01:00
Andras Bacsai
1c33d131c7 fix: clarify warning message for allowed IPs configuration 2025-10-26 10:59:28 +01:00
Andras Bacsai
6e74317cb5 refactor: streamline allowed IPs validation and enhance UI warnings for API access 2025-10-26 10:57:24 +01:00
Andras Bacsai
f5b513fdbe
Merge pull request #7005 from coollabsio/fix-github-source-appid-null
fix: GitHub source creation and configuration issues
2025-10-26 09:54:48 +01:00
Andras Bacsai
3b9eb42eaf fix: use x-cloak instead of inline style to prevent FOUC
Replaced inline style="display: none;" with x-cloak attribute on the
warning callout to properly prevent flash of unstyled content before
Alpine.js initializes. Alpine 3+ automatically handles x-cloak styling.

🤖 Generated with [Claude Code](https://claude.com/claude-code)

Co-Authored-By: Claude <noreply@anthropic.com>
2025-10-26 09:31:22 +01:00
Andras Bacsai
cae0bb9d52 fix: use break-all to force line wrapping in logs
Changed word-break strategy to properly wrap long lines:
- Changed from break-words to break-all for aggressive wrapping
- Added min-w-0 to container to allow flex shrinking
- Added max-w-full to pre element to respect parent width
- This ensures long URLs and file paths break anywhere to prevent overflow

🤖 Generated with [Claude Code](https://claude.com/claude-code)

Co-Authored-By: Claude <noreply@anthropic.com>
2025-10-25 18:05:47 +02:00
Andras Bacsai
d65bf748c0 fix: prevent horizontal overflow in log text
Added proper overflow handling and word breaking for log content:
- Added overflow-x-hidden to prevent horizontal scrolling in log container
- Added break-words and overflow-wrap-anywhere to force long lines to wrap
- This ensures long log lines (URLs, file paths, etc.) wrap properly on mobile

🤖 Generated with [Claude Code](https://claude.com/claude-code)

Co-Authored-By: Claude <noreply@anthropic.com>
2025-10-25 18:03:23 +02:00
Andras Bacsai
c94aa7bd83 fix: improve proxy logs form layout for better responsive behavior
Restructured the form to prevent overflow issues on mobile:
- Separated input field from controls in distinct sections
- Button and checkboxes now in a wrapping flex container
- All controls stack vertically on mobile for better readability
- Horizontal layout with wrapping on larger screens

🤖 Generated with [Claude Code](https://claude.com/claude-code)

Co-Authored-By: Claude <noreply@anthropic.com>
2025-10-25 18:01:13 +02:00
Andras Bacsai
a1ece556d4 fix: make proxy logs page responsive
The proxy logs form controls were not responsive on mobile devices. The form now stacks vertically on mobile and displays horizontally on larger screens.

Changes:
- Changed form layout to flex-col on mobile, flex-row on sm+ screens
- Made input field full width on mobile (w-full), fixed width (w-96) on sm+ screens
- Adjusted gap spacing for better mobile experience (gap-4 on mobile, gap-2 on sm+)

🤖 Generated with [Claude Code](https://claude.com/claude-code)

Co-Authored-By: Claude <noreply@anthropic.com>
2025-10-25 11:38:23 +02:00
Andras Bacsai
46158a5fe8 chore: add spacing and format callout text in modal
Added pt-2 for proper spacing between checkbox and warning callout,
and formatted the warning text for better readability.

🤖 Generated with [Claude Code](https://claude.com/claude-code)

Co-Authored-By: Claude <noreply@anthropic.com>
2025-10-25 11:35:43 +02:00
Andras Bacsai
4f0eeeb8d4 fix: allow callout to take full width in regular view
Removed max-w-2xl constraint and wrapper div from change.blade.php
so the callout takes full available width in the regular page view.
Modal version (create.blade.php) keeps the constraint for centered display.

🤖 Generated with [Claude Code](https://claude.com/claude-code)

Co-Authored-By: Claude <noreply@anthropic.com>
2025-10-25 11:22:10 +02:00
Andras Bacsai
49f903b9fa fix: left-align callout on regular view, keep centered in modal
Removed mx-auto from change.blade.php (regular page view) so the
callout is left-aligned. The create.blade.php modal version keeps
mx-auto for centered display.

🤖 Generated with [Claude Code](https://claude.com/claude-code)

Co-Authored-By: Claude <noreply@anthropic.com>
2025-10-25 11:21:18 +02:00
Andras Bacsai
fc285625c2 fix: center system-wide warning callout in modal
Added mx-auto to center the callout horizontally within the modal.

🤖 Generated with [Claude Code](https://claude.com/claude-code)

Co-Authored-By: Claude <noreply@anthropic.com>
2025-10-25 11:19:52 +02:00
Andras Bacsai
2f2ab6d775 fix: constrain callout width with max-w-2xl and wrap text properly
Set explicit max-width constraint (max-w-2xl) on callout wrapper
and added whitespace-normal to ensure text wraps properly within
the modal instead of expanding it horizontally.

🤖 Generated with [Claude Code](https://claude.com/claude-code)

Co-Authored-By: Claude <noreply@anthropic.com>
2025-10-25 10:58:26 +02:00
Andras Bacsai
c892a8ce44 fix: prevent system-wide warning callout from making modal too wide
Added max-width constraints and word breaking to ensure the warning
callout text wraps properly within modal constraints instead of
expanding the modal width excessively.

🤖 Generated with [Claude Code](https://claude.com/claude-code)

Co-Authored-By: Claude <noreply@anthropic.com>
2025-10-25 10:56:42 +02:00
Andras Bacsai
6746e44dba fix: make system-wide warning reactive in Create view
The system-wide warning callout was not appearing when the checkbox was toggled because it was only evaluated on initial render.

Changes:
- Wrapped checkbox and warning in Alpine.js x-data scope
- Used @entangle to bind showWarning to the is_system_wide Livewire property
- Added x-show directive to reactively show/hide warning based on checkbox state
- Added x-transition for smooth appearance/disappearance
- Added style="display: none;" to prevent flash of content on load

Now the warning appears immediately when the System Wide checkbox is checked and disappears when unchecked.

🤖 Generated with [Claude Code](https://claude.com/claude-code)

Co-Authored-By: Claude <noreply@anthropic.com>
2025-10-25 10:53:25 +02:00
Andras Bacsai
e13a921403 feat: show message when no resources use GitHub App
Improved the Resources section to show a clear message instead of an empty table when no resources are using the GitHub App.

Changes:
- Added conditional check for empty applications collection
- Shows "No resources are currently using this GitHub App." message when empty
- Only displays the table with headers when there are actual resources
- Changed @forelse to @foreach since we now handle empty state explicitly

This provides better UX by giving clear feedback instead of showing an empty table structure.

🤖 Generated with [Claude Code](https://claude.com/claude-code)

Co-Authored-By: Claude <noreply@anthropic.com>
2025-10-25 10:51:44 +02:00
Andras Bacsai
a69339804c feat: add warnings for system-wide GitHub Apps
Added warning callouts to inform users that system-wide GitHub Apps are not recommended for security reasons.

Changes:
- Added warning callout in Create view when system-wide checkbox is enabled
- Added warning callout in Change view when GitHub App is system-wide
- Warning explains that system-wide apps are shared across all teams and can access repositories from any team
- Recommends creating team-specific GitHub Apps for better security and isolation

The warnings only appear on self-hosted instances where system-wide option is available (not on cloud).

🤖 Generated with [Claude Code](https://claude.com/claude-code)

Co-Authored-By: Claude <noreply@anthropic.com>
2025-10-25 10:50:50 +02:00
Andras Bacsai
06ee7d0132 fix: GitHub source creation and configuration issues
Fixed multiple issues with GitHub App source creation and management:

1. **Fixed null property assignment error on component mount**
   - Changed property types to nullable in Change component (appId, installationId, clientId, etc.)
   - Updated validation rules to allow nullable values
   - Allows mounting component with newly created GitHub Apps that don't have these fields set yet

2. **Fixed Livewire morphing error on manual creation**
   - Modified createGithubAppManually() to redirect after saving
   - Prevents "Cannot read properties of null" error when view structure changes
   - Fields now properly populated after manual creation without requiring page refresh

3. **Fixed is_system_wide not being saved on creation**
   - Removed backwards logic that only saved is_system_wide on cloud instances
   - Added is_system_wide to GithubApp model casts for proper boolean handling
   - System-wide checkbox now works correctly on self-hosted instances

4. **Fixed misleading preview deployment checkbox**
   - Removed instantSave attribute from permission checkboxes in unconfigured state
   - These are configuration options for GitHub App creation, not database fields
   - Prevents "GitHub App updated" success message when nothing was actually saved

5. **Added validation for Refetch Permissions button**
   - Validates App ID and Private Key are set before attempting to fetch
   - Shows clear error messages: "Cannot fetch permissions. Please set the following required fields first: App ID, Private Key"
   - Prevents crash when private key is null or invalid

6. **Better error handling for unsupported private key formats**
   - Detects OpenSSH format keys vs RSA PEM format
   - Shows helpful message: "Please use an RSA private key in PEM format (BEGIN RSA PRIVATE KEY). OpenSSH format keys are not supported."
   - GitHub Apps require RSA PEM format, not OpenSSH format

7. **Made GitHub App view mobile responsive**
   - Updated all flex layouts to stack vertically on mobile (flex-col sm:flex-row)
   - Form fields, buttons, and sections now properly responsive
   - No more cut-off fields on small screens

Added comprehensive test coverage:
- GithubSourceChangeTest.php with 7 tests
- GithubSourceCreateTest.php with 6 tests

🤖 Generated with [Claude Code](https://claude.com/claude-code)

Co-Authored-By: Claude <noreply@anthropic.com>
2025-10-25 10:49:09 +02:00
Andras Bacsai
04ee546a49 fix: make environment variable forms responsive
Replace horizontal scrolling with flex-wrap for checkbox containers
in environment variable forms to improve mobile responsiveness.

🤖 Generated with [Claude Code](https://claude.com/claude-code)

Co-Authored-By: Claude <noreply@anthropic.com>
2025-10-25 10:22:26 +02:00
Andras Bacsai
7c14cd24dc fix: resolve Livewire wire:model binding error in domains input
Fixed JavaScript error "Cannot set properties of null (setting 'fqdn')"
that occurred when typing in the domains input field.

Changed wire:model binding from "application.fqdn" to "fqdn" to properly
use the component property which is synced with the model via the
SynchronizesModelData trait and getModelBindings() method.

🤖 Generated with [Claude Code](https://claude.com/claude-code)

Co-Authored-By: Claude <noreply@anthropic.com>
2025-10-25 10:18:07 +02:00
Andras Bacsai
bb35ae3a5a fix: make modals scrollable on small screens
Fixes #6974

- Add max-height constraints to prevent modals from exceeding viewport
- Enable vertical scrolling with overflow-y-auto on content areas
- Improve mobile responsiveness with consistent padding
- Separate fixed header from scrollable content using flexbox
- Add touch scrolling support for iOS devices

This ensures buttons like "Back" and "Continue" remain accessible
on small devices by allowing users to scroll the modal content.

🤖 Generated with [Claude Code](https://claude.com/claude-code)

Co-Authored-By: Claude <noreply@anthropic.com>
2025-10-24 18:27:16 +02:00
Andras Bacsai
7a52fd4506
Merge pull request #6992 from coollabsio/andrasbacsai/service-logos-color
feat: display service logos in original colors with consistent sizing
2025-10-24 14:52:26 +02:00
Andras Bacsai
340006db75
Merge pull request #6983 from coollabsio/andrasbacsai/fix-dark-mode-flicker
Fix dark mode white screen flicker on page transitions
2025-10-24 13:18:39 +02:00
Andras Bacsai
9d0d8c6729 Fix loading icon showing during automatic status checks
The loading icon was appearing during automatic background status checks
(every 10 seconds) even when users didn't click anything, which caused
confusion and made it seem like something was running unexpectedly.

Changes:
- Added manualCheckStatus() method to Application, Database, and Service
  Heading components that wraps the checkStatus() call
- Updated status component buttons to call manualCheckStatus() instead
  of checkStatus()
- Added wire:target="manualCheckStatus" to loading directives so the
  loading icon only appears when users explicitly click the refresh button
- Added delay.shortest to prevent flickering on fast operations

The automatic wire:poll.10000ms="checkStatus" now runs silently in the
background without showing the loading icon, while manual refreshes
still provide visual feedback to the user.

🤖 Generated with [Claude Code](https://claude.com/claude-code)

Co-Authored-By: Claude <noreply@anthropic.com>
2025-10-24 12:58:52 +02:00
Andras Bacsai
b02689a43e feat: display service logos in original colors with consistent sizing
This commit improves the visual presentation of service, application, and database logos on the new resource selection page:

- Remove grayscale filter: Logos now display in their original colors by default instead of being greyed out
- Dark mode support for SVGs: Updated SVG logos to use `fill="currentColor"` and added `text-black dark:text-white` wrapper for proper light/dark theme adaptation
- Consistent aspect ratios: Removed `aspect-square` and added `object-contain` to preserve original logo proportions
- Uniform sizing: Implemented fixed-size container (4.5rem × 4.5rem) with centered logo positioning to ensure all logos appear at consistent sizes regardless of intrinsic dimensions
- Improved mobile UX: Adjusted sticky search bar positioning from `top-10` to `top-20` to prevent navbar overlap

Files modified:
- resources/views/livewire/project/new/select.blade.php
- resources/views/components/resource-view.blade.php
- app/Livewire/Project/New/Select.php
- public/svgs/*.svg (12 SVG files updated with currentColor)

🤖 Generated with [Claude Code](https://claude.com/claude-code)

Co-Authored-By: Claude <noreply@anthropic.com>
2025-10-24 10:22:33 +02:00
Andras Bacsai
bfa40214ce
Merge pull request #6985 from coollabsio/filter-services-by-category
feat: add category filter dropdown to service selection
2025-10-23 21:07:13 +02:00
Andras Bacsai
4ef0a50e09 feat: add category filter dropdown to service selection
Add a searchable category dropdown filter on the new resource page to help users filter services by category.

Features:
- Category dropdown positioned next to search input
- Auto-focus on search field when dropdown opens
- Case-insensitive category filtering
- Proper acronym formatting (AI, API, CI, etc. displayed in uppercase)
- Loading/disabled state while categories are being fetched
- Category search/filter within dropdown
- Alphabetical sorting (case-insensitive)

Backend changes:
- Extract unique categories from service templates
- Handle comma-separated categories
- Format common acronyms to uppercase
- Case-insensitive natural sorting

Frontend changes:
- Searchable dropdown component with Alpine.js
- Category filter integration with existing search
- Disabled state placeholder during loading
- Auto-focus behavior for better UX

🤖 Generated with [Claude Code](https://claude.com/claude-code)

Co-Authored-By: Claude <noreply@anthropic.com>
2025-10-23 21:02:12 +02:00
Andras Bacsai
630fac4318 fix: eliminate dark mode white screen flicker on page transitions
- Add minimal blocking script immediately after <html> tag to apply dark class before any rendering
- Move theme detection from body to run before <head> parsing
- Add color-scheme meta tag for browser-level dark mode support
- Update theme-color meta tag dynamically based on theme
- Improve queryTheme() logic in settings dropdown for consistent behavior
- Remove duplicate theme detection code from body script

This eliminates the white "flashbang" effect that occurs during Livewire page
navigation, especially noticeable for users with high latency connections.

The solution uses an ultra-minimal (~100 bytes) script that runs before <head>
parsing, preventing FOUC while maintaining optimal performance (~0.1ms impact).

🤖 Generated with [Claude Code](https://claude.com/claude-code)

Co-Authored-By: Claude <noreply@anthropic.com>
2025-10-23 20:46:58 +02:00
Andras Bacsai
ecada60c78 Fix inconsistent modal height in Edit Docker Compose dialog
The modal height was changing when switching between "Source Compose"
and "Deployable Compose" views due to different heights between the
Monaco editor and regular textareas.

Changes:
- Set fixed height (512px) for Monaco editor via CSS
- Increased textarea rows to 25 to match Monaco editor height
- Wrapped both views in a container with consistent styling
- Modal now maintains same height regardless of view

🤖 Generated with [Claude Code](https://claude.com/claude-code)

Co-Authored-By: Claude <noreply@anthropic.com>
2025-10-23 19:18:50 +02:00
Andras Bacsai
2d3a980594
Merge pull request #6977 from coollabsio/andrasbacsai/fix-hetzner-redirect
Fix Hetzner server redirect in onboarding flow
2025-10-23 16:21:44 +02:00
Andras Bacsai
188c86ca45 Improve SSH key filtering and datalist component
- Add ownedAndOnlySShKeys() method to filter out git-related keys
- Update Boarding component to use new filtering method
- Enhance datalist component with better multi-select and single-select handling
- Fix Alpine.js reactivity and improve UI interactions

🤖 Generated with [Claude Code](https://claude.com/claude-code)

Co-Authored-By: Claude <noreply@anthropic.com>
2025-10-23 16:18:20 +02:00
Andras Bacsai
1298286832 feat: add onboarding guide link to global search no results state
Add a prominent call-to-action button linking to the onboarding guide when users don't find any search results. This helps guide new users to helpful documentation when they're searching but not finding what they need.
2025-10-23 16:17:58 +02:00
Andras Bacsai
2e71ef4f11 Fix Hetzner server redirect in onboarding flow
When creating a Hetzner server from the onboarding view, the redirect
to the server details page was not working properly due to modal context.
The standard redirect() call doesn't handle navigation from within modals.

Changes:
- Add from_onboarding flag to ByHetzner component
- Use wire:navigate redirect when in onboarding mode
- Pass from_onboarding=true from boarding view

This ensures proper navigation to the newly created server page instead
of staying on the onboarding view.

🤖 Generated with [Claude Code](https://claude.com/claude-code)

Co-Authored-By: Claude <noreply@anthropic.com>
2025-10-23 16:17:01 +02:00
Andras Bacsai
f0fc7af78c
Merge pull request #6961 from YaRissi/fix/hetzner-deprecated
fix: deprecated hetzner servers
2025-10-22 21:42:24 +02:00
Andras Bacsai
8b9c26a566
Merge pull request #6930 from rosano/patch-1
Fix typo
2025-10-22 21:37:55 +02:00
elmariss
af1374667b fix: filter deprecated server types for Hetzner 2025-10-22 00:13:55 +02:00
Andras Bacsai
8a307ad2a3 Changes auto-committed by Conductor 2025-10-20 14:07:45 +02:00
Rosano
e0d8145050
Fix typo 2025-10-20 11:59:29 +01:00
Andras Bacsai
251a10f5bb Changes auto-committed by Conductor 2025-10-20 10:42:21 +02:00
Andras Bacsai
f7427fdea0 Changes auto-committed by Conductor 2025-10-17 23:04:24 +02:00
Andras Bacsai
dab30da63c
Merge pull request #6862 from coollabsio/andrasbacsai/livewire-model-binding
Complete Livewire legacy model binding migration (25+ components)
2025-10-17 09:27:18 +02:00
Andras Bacsai
2d59418683
Changes auto-committed by Conductor (#6908) 2025-10-16 17:33:42 +02:00
Andras Bacsai
543d6fb334
Merge branch 'next' into andrasbacsai/livewire-model-binding 2025-10-16 17:07:48 +02:00
Andras Bacsai
5e3c50456c Changes auto-committed by Conductor 2025-10-16 17:01:32 +02:00
Andras Bacsai
ac653ddcbc Changes auto-committed by Conductor 2025-10-16 14:34:32 +02:00
Andras Bacsai
aacb6016b0 Changes auto-committed by Conductor 2025-10-16 13:43:52 +02:00
Andras Bacsai
cdf6b5f161 Fix preview domain generation for services with multiple domains
When a docker compose service has multiple comma-separated domains, the
generate() method was only processing the first domain and truncating the rest.

The issue was that Url::fromString() can't parse comma-separated URLs - it only
parses the first one.

Fixed by:
1. Splitting comma-separated domains with explode(',', $domain_string)
2. Processing each domain individually in a foreach loop
3. Generating preview URLs for each domain using the same template/random/pr_id
4. Joining the results back with implode(',', $preview_fqdns)

This ensures all domains get properly transformed for preview deployments.

Example:
- Original: http://domain1.com,http://domain2.com
- Preview: http://57.domain1.com,http://57.domain2.com
- Before fix: http://57.domain1.com,http (truncated)

🤖 Generated with [Claude Code](https://claude.com/claude-code)

Co-Authored-By: Claude <noreply@anthropic.com>
2025-10-16 13:10:29 +02:00
Andras Bacsai
a5c6f53b58 Fix wire:dirty indicator appearing on readonly fields without wire:model binding
The wire:dirty.class was being applied to all form inputs, even those without
wire:model bindings (like readonly fields). This caused the dirty state indicator
to appear on readonly fields when other fields in the form were modified.

Fixed by only applying wire:dirty.class when wire:model binding is present:
- input.blade.php: Moved wire:dirty.class inside @if($modelBinding !== 'null')
- textarea.blade.php: Applied same fix for all textarea variations
- select.blade.php: Applied same fix for select elements

This ensures only fields with actual Livewire bindings show dirty state indicators.

🤖 Generated with [Claude Code](https://claude.com/claude-code)

Co-Authored-By: Claude <noreply@anthropic.com>
2025-10-16 11:09:39 +02:00
Andras Bacsai
837a0f4545 Merge branch 'next' into andrasbacsai/livewire-model-binding
Resolved merge conflicts between Livewire model binding refactoring and UI/CSS updates from next branch. Key integrations:

- Preserved unique HTML ID generation for form components
- Maintained wire:model bindings using $modelBinding
- Integrated new wire:dirty.class styles (border-l-warning pattern)
- Kept both syncData(true) and validateDockerComposeForInjection in StackForm
- Merged security tests and helper improvements from next

🤖 Generated with [Claude Code](https://claude.com/claude-code)

Co-Authored-By: Claude <noreply@anthropic.com>
2025-10-16 11:05:29 +02:00
Andras Bacsai
2a8f02ed58 Changes auto-committed by Conductor 2025-10-16 09:48:32 +02:00
Andras Bacsai
23c1184e86
Merge pull request #6880 from coollabsio/andrasbacsai/fix-new-image-quick-action
fix: 'new image' quick action not progressing to resource selection
2025-10-15 10:51:21 +02:00
Andras Bacsai
66cff9d9b8 fix: 'new image' quick action not progressing to resource selection
Fixed three issues preventing the "new image" quick action from working:

1. Frontend matching logic wasn't checking the quickcommand field
   - Added check for item.quickcommand in the matching logic
   - Now "new image" matches docker-image via its quickcommand "(type: new image)"

2. Search query remained populated after triggering selection flow
   - Clear searchQuery in navigateToResourceCreation() to show selection UI
   - This switches the UI from creatable items list to server selection

3. Redirect wasn't using Livewire's redirect method
   - Changed from redirect()->route() to $this->redirect(route())
   - Ensures proper Livewire component redirect behavior

🤖 Generated with [Claude Code](https://claude.com/claude-code)

Co-Authored-By: Claude <noreply@anthropic.com>
2025-10-15 10:49:07 +02:00
Andras Bacsai
20b4288916 fix: improve Docker image digest handling and add auto-parse feature
- Replace manual regex parsing with DockerImageParser in ApplicationsController
- Fix double-decoration bug where image names like nginx@sha256:hash would
  become nginx:hash@sha256 causing malformed references
- Add auto-parse feature in Livewire DockerImage component
- Users can now paste complete references like nginx:stable@sha256:abc123...
  and fields auto-populate
- Update UI placeholder with examples: nginx, docker.io/nginx:latest,
  ghcr.io/user/app:v1.2.3, nginx:stable@sha256:abc123...
- Add comprehensive unit tests for auto-parse functionality
- All tests passing (20 tests, 73 assertions)

🤖 Generated with [Claude Code](https://claude.com/claude-code)

Co-Authored-By: Claude <noreply@anthropic.com>
2025-10-15 10:19:01 +02:00
Andras Bacsai
81455b1b5f
Merge pull request #6863 from YaRissi/hetzner/cpu_vendor
feat(hetzner): add CPU vendor information to server types in Hetzner integration
2025-10-15 09:03:12 +02:00
Andras Bacsai
ff71b28b81 Fix Monaco editor @entangle error with unique HTML IDs
**Problem:**
Monaco editor was receiving unique HTML IDs (e.g., "customLabels-a09a7773")
and using them in @entangle(), causing errors:
"Livewire property ['customLabels-a09a7773'] cannot be found"

**Root Cause:**
Monaco editor template uses @entangle($id) to bind to Livewire properties.
After our unique ID fix, $id contained the unique HTML ID with suffix,
not the original property name.

**Solution:**
Pass $modelBinding (original property name) instead of $htmlId to Monaco
editor component. This ensures @entangle() uses the correct property name
while HTML elements still get unique IDs.

**Result:**
 Monaco editor @entangle works correctly
 HTML IDs remain unique
 No Livewire property errors

🤖 Generated with [Claude Code](https://claude.com/claude-code)

Co-Authored-By: Claude <noreply@anthropic.com>
2025-10-14 10:34:36 +02:00
Andras Bacsai
a514c837b6 Fix duplicate HTML ID warnings in form components
Resolve browser console warnings about non-unique HTML IDs when multiple
Livewire components with similar form fields appear on the same page.

**Problem:**
Multiple forms using generic IDs like `id="description"` or `id="name"`
caused duplicate ID warnings and potential accessibility/JavaScript issues.

**Solution:**
- Separate `wire:model` binding name from HTML `id` attribute
- Auto-prefix HTML IDs with Livewire component ID for uniqueness
- Preserve existing `wire:model` behavior with property names

**Implementation:**
- Added `$modelBinding` property for wire:model (e.g., "description")
- Added `$htmlId` property for unique HTML ID (e.g., "lw-xyz123-description")
- Updated render() method to generate unique IDs automatically
- Updated all blade templates to use new properties

**Components Updated:**
- Input (text, password, etc.)
- Textarea (including Monaco editor)
- Select
- Checkbox
- Datalist (single & multiple selection)

**Result:**
 All HTML IDs now unique across page
 No console warnings
 wire:model bindings work correctly
 Validation error messages display correctly
 Backward compatible - no changes needed in existing components

🤖 Generated with [Claude Code](https://claude.com/claude-code)

Co-Authored-By: Claude <noreply@anthropic.com>
2025-10-14 10:27:41 +02:00
Andras Bacsai
b911d2b281 feat: update Hetzner affiliate link text and URL
- Change URL to https://coolify.io/hetzner
- Add detailed explanation about credits (€10 for Coolify, €20 for new users)
- Clarify it's only for new accounts
- Improve text formatting with extra spacing
- Apply consistent messaging across both modal and full-page layouts
2025-10-14 09:28:01 +02:00
Andras Bacsai
d4b9b61cbd feat: add Hetzner affiliate link to token form
- Add affiliate link when users add their first Hetzner token
- Shows in both modal and full-page layouts
- Friendly messaging about supporting Coolify and getting credits
2025-10-14 09:25:10 +02:00
elmariss
ea584902ec feat: add CPU vendor information to server types in Hetzner integration 2025-10-13 22:21:35 +02:00
Andras Bacsai
f77ad4cbd9 Complete Livewire legacy model binding migration (25+ components)
This completes the migration from Livewire's legacy `id="model.property"`
pattern to explicit properties with manual synchronization. This allows
disabling the `legacy_model_binding` feature flag.

**Components Migrated (Final Session - 9 components):**
- Server/Proxy.php (1 field)
- Service/EditDomain.php (1 field) - Fixed Collection/string bug & parent sync
- Application/Previews.php (2 fields - array handling)
- Service/EditCompose.php (4 fields)
- Service/FileStorage.php (6 fields)
- Service/Database.php (7 fields)
- Service/ServiceApplicationView.php (10 fields)
- Application/General.php (53 fields) - LARGEST migration
- Application/PreviewsCompose.php (1 field)

**Total Migration Summary:**
- 25+ components migrated across all phases
- 150+ explicit properties added
- 0 legacy bindings remaining (verified via grep)
- All wire:model, id, @entangle bindings updated
- All updater hooks renamed (updatedApplicationX → updatedX)

**Technical Changes:**
- Added explicit public properties (camelCase)
- Implemented syncData(bool $toModel) bidirectional sync
- Updated validation rules (removed model. prefix)
- Updated all action methods (mount, submit, instantSave)
- Fixed updater hooks: updatedBuildPack, updatedBaseDirectory, updatedIsStatic
- Updated Blade views (id & wire:model bindings)
- Applied Collection/string confusion fixes
- Added model refresh + re-sync pattern

**Critical Fixes:**
- EditDomain.php Collection/string confusion (use intermediate variables)
- EditDomain.php parent component sync (refresh + re-sync after save)
- General.php domain field empty (syncData at end of mount)
- General.php wire:model bindings (application.* → property)
- General.php updater hooks (wrong naming convention)

**Files Modified:** 34 files
- 17 PHP Livewire components
- 17 Blade view templates
- 1 MIGRATION_REPORT.md (documentation)

**Ready to disable legacy_model_binding flag in config/livewire.php**

🤖 Generated with [Claude Code](https://claude.com/claude-code)

Co-Authored-By: Claude <noreply@anthropic.com>
2025-10-13 15:38:59 +02:00
Andras Bacsai
acc5dbe105
Merge branch 'next' into andrasbacsai/fix-livewire-field-reset 2025-10-13 10:38:02 +02:00
Andras Bacsai
a15ab54495 refactor: migrate database components from legacy model binding to explicit properties
- Remove global 'refresh' event listeners from all database General components
- Migrate Redis, MySQL, MariaDB, MongoDB, PostgreSQL, and KeyDB components to use explicit public properties instead of wire:model="database.field"
- Implement syncData() method in each component for manual data synchronization between properties and Eloquent models
- Update all validation rules, messages, and attributes to reference new property names
- Update Blade views to bind inputs to explicit properties (e.g., id="name" instead of id="database.name")
- Prepare codebase for disabling Livewire's legacy_model_binding configuration option

This refactoring resolves form field reset issues caused by global refresh events
and follows Livewire 3 best practices for component property management.
2025-10-13 10:01:17 +02:00
Andras Bacsai
de24489aa7 fix(onboarding): auto-select first SSH key for better UX
- Auto-select first SSH key when available instead of requiring explicit selection
- Remove disabled placeholder option from dropdown
- Prevents confusing error when user clicks "Use Selected Key" without changing dropdown
- Improves onboarding flow by having a sensible default selection

🤖 Generated with [Claude Code](https://claude.com/claude-code)

Co-Authored-By: Claude <noreply@anthropic.com>
2025-10-12 18:54:12 +02:00
Andras Bacsai
04625591ea feat(onboarding): add Hetzner integration and fix navigation issues
- Add Hetzner Cloud server creation option to onboarding flow
- Change grid from 2 to 3 columns to accommodate all server options
- Mark both Hetzner and Remote Server as "Recommended"
- Fix Hetzner card height to match other cards
- Remove "select existing server" phase - onboarding always creates new servers
- Fix project loading on page refresh in Project Setup phase
- Fix browser back button navigation - remove aggressive restartBoarding() call
- Fix SSH key dropdown to not auto-select first key - require explicit selection
- Make checkpoint titles more prominent across all phases

🤖 Generated with [Claude Code](https://claude.com/claude-code)

Co-Authored-By: Claude <noreply@anthropic.com>
2025-10-12 18:52:45 +02:00
Andras Bacsai
1902ef886d
Merge branch 'next' into andrasbacsai/onboarding-redesign 2025-10-12 18:02:37 +02:00