diff --git a/.github/workflows/build-phar.yml b/.github/workflows/build-phar.yml new file mode 100644 index 0000000..98b3e78 --- /dev/null +++ b/.github/workflows/build-phar.yml @@ -0,0 +1,64 @@ +name: Build and test phar + +on: + push: + branches: + - main + - '[0-9]+.[0-9]+.[0-9]+' + pull_request: + +jobs: + build-phar: + name: Build and test phar (PHP ${{ matrix.php-version }}) + runs-on: ubuntu-latest + strategy: + fail-fast: true + matrix: + php-version: ['7.4', '8.1', '8.2'] + + steps: + - name: Checkout + uses: actions/checkout@v4 + + - name: Setup PHP for building + uses: shivammathur/setup-php@v2 + with: + php-version: '8.1' + tools: composer:v2 + extensions: phar + ini-values: phar.readonly=0 + + - name: Install humbug/box + run: composer global require humbug/box:^4.0 + + - name: Build phar + run: box compile + + - name: Setup PHP ${{ matrix.php-version }} for testing + if: matrix.php-version != '8.1' + uses: shivammathur/setup-php@v2 + with: + php-version: ${{ matrix.php-version }} + extensions: phar + + - name: Verify phar boots + run: php slic.phar help + + - name: Verify phar version output + run: php slic.phar help 2>&1 | grep -q "version" + + - name: Verify phar upgrade check + run: php slic.phar upgrade + + - name: Verify no test files in phar + run: | + php -r " + foreach (new RecursiveIteratorIterator(new Phar('slic.phar')) as \$f) { + \$path = (string) \$f; + if (preg_match('#/(tests|docs|\.github)/#', \$path)) { + echo 'FAIL: found excluded file: ' . \$path . PHP_EOL; + exit(1); + } + } + echo 'OK: no test/docs/.github files in phar' . PHP_EOL; + " diff --git a/.github/workflows/release-phar.yml b/.github/workflows/release-phar.yml new file mode 100644 index 0000000..e40587c --- /dev/null +++ b/.github/workflows/release-phar.yml @@ -0,0 +1,41 @@ +name: Build and release slic.phar + +on: + push: + tags: + - '[0-9]+.[0-9]+.[0-9]+' + - 'v[0-9]+.[0-9]+.[0-9]+' + +permissions: + contents: write + +jobs: + build-phar: + name: Build phar and create release + runs-on: ubuntu-latest + steps: + - name: Checkout code + uses: actions/checkout@v4 + + - name: Setup PHP + uses: shivammathur/setup-php@v2 + with: + php-version: '8.1' + tools: composer:v2 + extensions: phar + ini-values: phar.readonly=0 + + - name: Install humbug/box + run: composer global require humbug/box:^4.0 + + - name: Build phar + run: box compile + + - name: Verify phar works + run: php slic.phar help + + - name: Create GitHub release + uses: softprops/action-gh-release@v2 + with: + files: slic.phar + generate_release_notes: true diff --git a/.gitignore b/.gitignore index 77766ae..96094b7 100644 --- a/.gitignore +++ b/.gitignore @@ -44,3 +44,6 @@ _plugins # PHPUnit cache .phpunit.result.cache + +# Phar build artifacts +*.phar diff --git a/box.json b/box.json new file mode 100644 index 0000000..823b000 --- /dev/null +++ b/box.json @@ -0,0 +1,36 @@ +{ + "main": "slic.php", + "output": "slic.phar", + "shebang": "#!/usr/bin/env php", + "directories": [ + "src", + "includes", + "containers", + "completions" + ], + "files": [ + "slic.php", + "version.php", + ".env.slic", + "slic-stack.yml", + "slic-stack.site.yml", + "slic-stack.worktree.yml" + ], + "blacklist": [ + "tests", + "docs", + "vendor", + ".github", + ".git", + "_wordpress", + "_plugins", + ".cache", + ".idea", + ".data" + ], + "compactors": [ + "KevinGH\\Box\\Compactor\\Php" + ], + "compression": "NONE", + "chmod": "0755" +} diff --git a/composer.json b/composer.json index 5b53091..b4dcde9 100644 --- a/composer.json +++ b/composer.json @@ -4,7 +4,7 @@ "type": "project", "license": "GPL-2.0-or-later", "require": { - "php": ">=8.2" + "php": ">=7.4" }, "require-dev": { "phpunit/phpunit": "^11.0" diff --git a/composer.lock b/composer.lock index 8b1057e..cbdb1cc 100644 --- a/composer.lock +++ b/composer.lock @@ -4,7 +4,7 @@ "Read more about it at https://getcomposer.org/doc/01-basic-usage.md#installing-dependencies", "This file is @generated automatically" ], - "content-hash": "b388d73aaec46a4546e7ec2780b48839", + "content-hash": "d134efd2fa9b49b4e1273d1277292399", "packages": [], "packages-dev": [ { @@ -1795,7 +1795,7 @@ "prefer-stable": false, "prefer-lowest": false, "platform": { - "php": ">=8.2" + "php": ">=7.4" }, "platform-dev": {}, "plugin-api-version": "2.6.0" diff --git a/slic.php b/slic.php index 5e1d672..b68408b 100644 --- a/slic.php +++ b/slic.php @@ -291,7 +291,7 @@ $subcommand = $args( 'subcommand', 'help' ); // Both these variables will be used by commands. -$run_settings_file = root( '/.env.slic.run' ); +$run_settings_file = \StellarWP\Slic\slic_data_dir() . '/.env.slic.run'; $cli_name = basename( $argv[0] ); if ( 'help' !== $subcommand ) { diff --git a/src/commands/composer.php b/src/commands/composer.php index b186927..3ad736d 100644 --- a/src/commands/composer.php +++ b/src/commands/composer.php @@ -58,7 +58,7 @@ echo magenta( "Error: set-version requires a Composer version number, either 1 or 2." . PHP_EOL ); exit( 1 ); } - $run_settings_file = root( '/.env.slic.run' ); + $run_settings_file = slic_data_dir() . '/.env.slic.run'; write_env_file( $run_settings_file, [ 'SLIC_COMPOSER_VERSION' => (int) $version ], true ); echo colorize( "Composer version set to $version\n" ); @@ -69,7 +69,7 @@ exit( slic_realtime()( [ 'exec', 'slic', $composer_bin, '--version' ] ) ); case 'reset-version': $version = 2; - $run_settings_file = root( '/.env.slic.run' ); + $run_settings_file = slic_data_dir() . '/.env.slic.run'; write_env_file( $run_settings_file, [ 'SLIC_COMPOSER_VERSION' => (int) $version ], true ); echo colorize( "Composer version reset to default: $default_version\n" ); diff --git a/src/commands/php-version.php b/src/commands/php-version.php index 041ccb8..1dcef94 100644 --- a/src/commands/php-version.php +++ b/src/commands/php-version.php @@ -65,7 +65,7 @@ } // Read .env.slic.run to get runtime value. -$run_env_file = root( '/.env.slic.run' ); +$run_env_file = slic_data_dir() . '/.env.slic.run'; $runtime_version = null; if ( file_exists( $run_env_file ) ) { $run_env = read_env_file( $run_env_file ); diff --git a/src/commands/reset.php b/src/commands/reset.php index d094d86..81e8c4d 100644 --- a/src/commands/reset.php +++ b/src/commands/reset.php @@ -38,7 +38,7 @@ quietly_tear_down_stack(); -$run_settings_file = root( '/.env.slic.run' ); +$run_settings_file = slic_data_dir() . '/.env.slic.run'; echo "Removing {$run_settings_file} ... "; echo ( ! file_exists( $run_settings_file ) || unlink( $run_settings_file ) ) ? light_cyan( 'done' ) diff --git a/src/commands/upgrade.php b/src/commands/upgrade.php index 183f9f9..b75bd72 100644 --- a/src/commands/upgrade.php +++ b/src/commands/upgrade.php @@ -17,14 +17,139 @@ return; } -$today = date( 'Y-m-d' ); -chdir( SLIC_ROOT_DIR ); -$status = passthru( 'git checkout main && git pull' ); +if ( is_phar() ) { + phar_self_update(); +} else { + git_upgrade(); +} + +/** + * Upgrades slic via git pull on the main branch. + */ +function git_upgrade() { + chdir( SLIC_ROOT_DIR ); + $status = passthru( 'git checkout main && git pull' ); -if ( ! $status ) { - unlink( SLIC_ROOT_DIR . '/.remote-version' ); + if ( ! $status ) { + $remote_version_file = slic_data_dir() . '/.remote-version'; + if ( file_exists( $remote_version_file ) ) { + unlink( $remote_version_file ); + } - $status = passthru( 'php slic update' ); + $status = passthru( PHP_BINARY . ' ' . escapeshellarg( $GLOBALS['argv'][0] ) . ' update' ); + } + + exit( $status ); } -exit( $status ); +/** + * Self-updates the phar archive from GitHub Releases. + */ +function phar_self_update() { + $current_version = CLI_VERSION; + + echo colorize( "Checking for updates..." . PHP_EOL ); + + $latest_version = fetch_latest_github_release_version(); + + if ( null === $latest_version ) { + echo magenta( "Error: Could not check for updates. Please try again later." . PHP_EOL ); + exit( 1 ); + } + + if ( version_compare( $latest_version, $current_version, '<=' ) ) { + echo light_cyan( "You are already running the latest version ({$current_version})." . PHP_EOL ); + exit( 0 ); + } + + echo colorize( "Updating from {$current_version} to {$latest_version}..." . PHP_EOL ); + + // Fetch the release to get the slic.phar asset URL. + $context = stream_context_create( [ + 'http' => [ + 'method' => 'GET', + 'header' => "User-Agent: slic-cli\r\nAccept: application/vnd.github.v3+json\r\n", + 'timeout' => 10, + ], + ] ); + + $response = @file_get_contents( 'https://api.github.com/repos/stellarwp/slic/releases/latest', false, $context ); + + if ( false === $response ) { + echo magenta( "Error: Could not fetch release information." . PHP_EOL ); + exit( 1 ); + } + + $release = json_decode( $response, true ); + + if ( ! is_array( $release ) || empty( $release['assets'] ) ) { + echo magenta( "Error: No assets found in the latest release." . PHP_EOL ); + exit( 1 ); + } + + // Find the slic.phar asset. + $phar_url = null; + foreach ( $release['assets'] as $asset ) { + if ( $asset['name'] === 'slic.phar' ) { + $phar_url = $asset['browser_download_url']; + break; + } + } + + if ( null === $phar_url ) { + echo magenta( "Error: slic.phar not found in the latest release assets." . PHP_EOL ); + exit( 1 ); + } + + // Download the new phar. + $download_context = stream_context_create( [ + 'http' => [ + 'method' => 'GET', + 'header' => "User-Agent: slic-cli\r\n", + 'timeout' => 60, + 'follow_location' => true, + ], + ] ); + + $new_phar = @file_get_contents( $phar_url, false, $download_context ); + + if ( false === $new_phar || empty( $new_phar ) ) { + echo magenta( "Error: Failed to download the new phar." . PHP_EOL ); + exit( 1 ); + } + + // Get the path to the currently running phar. + $phar_path = \Phar::running( false ); + + if ( empty( $phar_path ) ) { + echo magenta( "Error: Could not determine the running phar path." . PHP_EOL ); + exit( 1 ); + } + + // Write the new phar to a temp file first, then rename for atomicity. + $tmp_path = $phar_path . '.tmp'; + + if ( false === file_put_contents( $tmp_path, $new_phar ) ) { + echo magenta( "Error: Could not write the new phar to {$tmp_path}." . PHP_EOL ); + exit( 1 ); + } + + // Make the temp file executable. + chmod( $tmp_path, 0755 ); + + // Replace the old phar with the new one. + if ( ! rename( $tmp_path, $phar_path ) ) { + unlink( $tmp_path ); + echo magenta( "Error: Could not replace the phar at {$phar_path}." . PHP_EOL ); + exit( 1 ); + } + + // Clear the cached remote version. + $remote_version_file = slic_data_dir() . '/.remote-version'; + if ( file_exists( $remote_version_file ) ) { + unlink( $remote_version_file ); + } + + echo light_cyan( "Successfully updated slic to version {$latest_version}." . PHP_EOL ); + exit( 0 ); +} diff --git a/src/slic.php b/src/slic.php index 1d1d1ef..df3b402 100644 --- a/src/slic.php +++ b/src/slic.php @@ -10,6 +10,57 @@ require_once __DIR__ . '/xdebug.php'; +/** + * Returns whether the current script is running inside a phar archive. + * + * @return bool + */ +function is_phar() { + return strlen( \Phar::running() ) > 0; +} + +/** + * Returns the directory to use for writable data files. + * + * When running as a phar archive, the phar filesystem is read-only, so writable files + * (.env.slic.run, .build-version, .remote-version, .cache, etc.) must be stored in a + * real filesystem directory. This function returns: + * - When phar: the value of SLIC_DATA_DIR env var, or ~/.slic + * - When git clone: SLIC_ROOT_DIR (the project root) + * + * @return string The absolute path to the writable data directory. + */ +function slic_data_dir() { + if ( ! is_phar() ) { + return SLIC_ROOT_DIR; + } + + $data_dir = getenv( 'SLIC_DATA_DIR' ); + + if ( ! empty( $data_dir ) ) { + if ( ! is_dir( $data_dir ) ) { + mkdir( $data_dir, 0755, true ); + } + + return rtrim( $data_dir, '/' ); + } + + $home = getenv( 'HOME' ) ?: getenv( 'USERPROFILE' ); + + if ( empty( $home ) ) { + // Fallback: use system temp directory. + $home = sys_get_temp_dir(); + } + + $data_dir = $home . '/.slic'; + + if ( ! is_dir( $data_dir ) ) { + mkdir( $data_dir, 0755, true ); + } + + return $data_dir; +} + /** * Get the CLI header. * @@ -287,7 +338,7 @@ function setup_slic_env( $root_dir, $reset = false, $stack_id = null ) { } // Start by loading the run file for all stacks, if any. - $run_file = $root_dir . '/.env.slic.run'; + $run_file = slic_data_dir() . '/.env.slic.run'; $staged_php_version = null; if ( is_file( $run_file ) ) { @@ -369,11 +420,11 @@ function setup_slic_env( $root_dir, $reset = false, $stack_id = null ) { // Set up XDebug host for Linux xdebug_setup_linux_host(); - $default_wp_dir = root( '/_wordpress' ); + $default_wp_dir = slic_data_dir() . '/_wordpress'; $wp_dir = getenv( 'SLIC_WP_DIR' ); - if ( $wp_dir === './_wordpress' || $wp_dir === $default_wp_dir ) { - // Default WordPress directory, inside slic. + if ( $wp_dir === './_wordpress' || $wp_dir === root( '/_wordpress' ) || $wp_dir === $default_wp_dir ) { + // Default WordPress directory, inside slic data dir. $wp_dir = ensure_dir( $default_wp_dir ); } else if ( ! is_dir( $wp_dir ) ) { // Custom WordPress directory, it falls on the user to have it set up correctly. @@ -384,12 +435,12 @@ function setup_slic_env( $root_dir, $reset = false, $stack_id = null ) { $wp_themes_dir = $wp_dir . '/wp-content/themes'; putenv( 'SLIC_WP_DIR=' . $wp_dir ); - putenv( 'SLIC_PLUGINS_DIR=' . ensure_dir( getenv( 'SLIC_PLUGINS_DIR' ) ?: root( '_plugins' ) ) ); + putenv( 'SLIC_PLUGINS_DIR=' . ensure_dir( getenv( 'SLIC_PLUGINS_DIR' ) ?: slic_data_dir() . '/_plugins' ) ); putenv( 'SLIC_THEMES_DIR=' . ensure_dir( getenv( 'SLIC_THEMES_DIR' ) ?: $wp_themes_dir ) ); putenv( 'SLIC_CACHE=' . cache() ); if ( empty( getenv( 'COMPOSER_CACHE_DIR' ) ) ) { - ensure_dir( root( '.cache' ) ); + ensure_dir( slic_data_dir() . '/.cache' ); putenv( 'COMPOSER_CACHE_DIR=' . cache( '/composer' ) ); } @@ -490,7 +541,7 @@ function slic_set_php_version( $version, $require_confirm = false, $skip_rebuild $message .= PHP_EOL . "The PHP version will be set for the current stack."; } else { // Apply this version to all the stacks. - $run_settings_file = root( '/.env.slic.run' ); + $run_settings_file = slic_data_dir() . '/.env.slic.run'; $message .= PHP_EOL . "The PHP version will be set for all stacks."; } @@ -533,7 +584,7 @@ function slic_set_php_version( $version, $require_confirm = false, $skip_rebuild * @return void */ function slic_clear_staged_php_flag() { - $run_settings_file = root( '/.env.slic.run' ); + $run_settings_file = slic_data_dir() . '/.env.slic.run'; write_env_file( $run_settings_file, [ 'SLIC_PHP_VERSION_STAGED' => false ], true ); } @@ -1088,7 +1139,7 @@ function rebuild_stack(): void { * Write the current CLI_VERSION to the build-version file */ function write_build_version() { - file_put_contents( SLIC_ROOT_DIR . '/.build-version', CLI_VERSION ); + file_put_contents( slic_data_dir() . '/.build-version', CLI_VERSION ); } /** @@ -1137,7 +1188,7 @@ function slic_info() { ); // Read .env.slic.run directly to show runtime state. - $run_env_file = root( '/.env.slic.run' ); + $run_env_file = slic_data_dir() . '/.env.slic.run'; $run_env = []; if ( file_exists( $run_env_file ) ) { $run_env = read_env_file( $run_env_file ); @@ -1150,7 +1201,7 @@ function slic_info() { file_exists( $slic_root . '/.env.slic' ) ? " - " . $slic_root . '/.env.slic' : null, file_exists( $slic_root . '/.env.slic.local' ) ? " - " . $slic_root . '/.env.slic.local' : null, file_exists( $target_path . '/.env.slic.local' ) ? " - " . $target_path . '/.env.slic.local' : null, - file_exists( $slic_root . '/.env.slic.run' ) ? " - " . $slic_root . '/.env.slic.run' : null, + file_exists( slic_data_dir() . '/.env.slic.run' ) ? " - " . slic_data_dir() . '/.env.slic.run' : null, ] ) ) . PHP_EOL . PHP_EOL; echo colorize( "Current configuration:" . PHP_EOL ); @@ -1221,7 +1272,7 @@ function composer_cache_status() { * @param callable $args The closure that will produce the current interactive request arguments. */ function slic_handle_composer_cache( callable $args ) { - $run_settings_file = root( '/.env.slic.run' ); + $run_settings_file = slic_data_dir() . '/.env.slic.run'; $toggle = $args( 'toggle', 'status' ); if ( 'status' === $toggle ) { @@ -1274,7 +1325,7 @@ function build_prompt_status() { * @param callable $args The closure that will produce the current interactive request arguments. */ function slic_handle_build_prompt( callable $args ) { - $run_settings_file = root( '/.env.slic.run' ); + $run_settings_file = slic_data_dir() . '/.env.slic.run'; $toggle = $args( 'toggle', 'on' ); if ( 'status' === $toggle ) { @@ -1313,7 +1364,7 @@ function is_interactive() { * @param callable $args The closure that will produce the current interactive request arguments. */ function slic_handle_interactive( callable $args ) { - $run_settings_file = root( '/.env.slic.run' ); + $run_settings_file = slic_data_dir() . '/.env.slic.run'; $toggle = $args( 'toggle', 'on' ); if ( 'status' === $toggle ) { @@ -1666,29 +1717,22 @@ function maybe_prompt_for_repo_update() { $check_date = null; $cli_version = CLI_VERSION; $today = date( 'Y-m-d' ); + $data_dir = slic_data_dir(); - if ( is_file( SLIC_ROOT_DIR . '/.remote-version' ) ) { - list( $check_date, $remote_version ) = explode( ':', file_get_contents( SLIC_ROOT_DIR . '/.remote-version' ) ); + if ( is_file( $data_dir . '/.remote-version' ) ) { + list( $check_date, $remote_version ) = explode( ':', file_get_contents( $data_dir . '/.remote-version' ) ); } if ( empty( $remote_version ) || empty( $check_date ) || $today > $check_date ) { - $current_dir = getcwd(); - chdir( SLIC_ROOT_DIR ); - - $tags = explode( "\n", shell_exec( 'git ls-remote --tags origin' ) ); + $remote_version = fetch_latest_remote_version(); - chdir( $current_dir ); - - foreach ( $tags as &$tag ) { - $tag_parts = explode( '/', $tag ); - $tag = array_pop( $tag_parts ); + if ( null !== $remote_version ) { + file_put_contents( $data_dir . '/.remote-version', "{$today}:{$remote_version}" ); } + } - natsort( $tags ); - - $remote_version = array_pop( $tags ); - - file_put_contents( SLIC_ROOT_DIR . '/.remote-version', "{$today}:{$remote_version}" ); + if ( null === $remote_version ) { + return; } // If the version of the CLI is the same as the most recently built version, bail. @@ -1703,19 +1747,76 @@ function maybe_prompt_for_repo_update() { echo magenta( "****************************************************************" . PHP_EOL ); } +/** + * Fetches the latest remote version from git tags or GitHub Releases API. + * + * @return string|null The latest remote version, or null on failure. + */ +function fetch_latest_remote_version() { + if ( is_phar() ) { + return fetch_latest_github_release_version(); + } + + $current_dir = getcwd(); + chdir( SLIC_ROOT_DIR ); + + $tags = explode( "\n", shell_exec( 'git ls-remote --tags origin' ) ); + + chdir( $current_dir ); + + foreach ( $tags as &$tag ) { + $tag_parts = explode( '/', $tag ); + $tag = array_pop( $tag_parts ); + } + + natsort( $tags ); + + return array_pop( $tags ); +} + +/** + * Fetches the latest release version from the GitHub Releases API. + * + * @return string|null The latest version tag, or null on failure. + */ +function fetch_latest_github_release_version() { + $context = stream_context_create( [ + 'http' => [ + 'method' => 'GET', + 'header' => "User-Agent: slic-cli\r\nAccept: application/vnd.github.v3+json\r\n", + 'timeout' => 5, + ], + ] ); + + $response = @file_get_contents( 'https://api.github.com/repos/stellarwp/slic/releases/latest', false, $context ); + + if ( false === $response ) { + return null; + } + + $data = json_decode( $response, true ); + + if ( ! is_array( $data ) || empty( $data['tag_name'] ) ) { + return null; + } + + return ltrim( $data['tag_name'], 'v' ); +} + /** * If slic stack is out of date, prompt for an execution of slic update. */ function maybe_prompt_for_stack_update() { $build_version = '0.0.1'; $cli_version = CLI_VERSION; + $data_dir = slic_data_dir(); - if ( is_file( SLIC_ROOT_DIR . '/.build-version' ) ) { - $build_version = file_get_contents( SLIC_ROOT_DIR . '/.build-version' ); + if ( is_file( $data_dir . '/.build-version' ) ) { + $build_version = file_get_contents( $data_dir . '/.build-version' ); } // If there isn't a .env.slic.run, this is likely a fresh install. Bail. - if ( ! file_exists( SLIC_ROOT_DIR . '/.env.slic.run' ) ) { + if ( ! file_exists( $data_dir . '/.env.slic.run' ) ) { return; } @@ -1743,7 +1844,7 @@ function maybe_prompt_for_stack_update() { * @param callable $args The closure that will produce the current subdirectories build arguments. */ function slic_handle_build_subdir( callable $args ) { - $run_settings_file = root( '/.env.slic.run' ); + $run_settings_file = slic_data_dir() . '/.env.slic.run'; $toggle = $args( 'toggle', 'on' ); if ( 'status' === $toggle ) { @@ -1889,8 +1990,9 @@ function collect_target_suites() { * @return bool Whether the current system is ARM-based, or not. */ function is_arm64() { - $arm64_architecture_file = __DIR__ . '/../.architecture_arm64'; - $x86_architecture_file = __DIR__ . '/../.architecture_x86'; + $data_dir = slic_data_dir(); + $arm64_architecture_file = $data_dir . '/.architecture_arm64'; + $x86_architecture_file = $data_dir . '/.architecture_x86'; if ( is_file( $arm64_architecture_file ) ) { return true; @@ -1951,7 +2053,7 @@ function setup_architecture_env() { * @return string The absolute path to the created directory or file. */ function cache( $path = '/', $create = true ) { - $cache_root_dir = __DIR__ . '/../.cache'; + $cache_root_dir = slic_data_dir() . '/.cache'; if ( ! is_dir( $cache_root_dir ) && ! mkdir( $cache_root_dir, 0755, true ) && ! is_dir( $cache_root_dir ) ) { echo magenta( "Failed to create cache root directory {$cache_root_dir}." ); diff --git a/src/stacks.php b/src/stacks.php index 5f0ee9d..d67f028 100644 --- a/src/stacks.php +++ b/src/stacks.php @@ -11,7 +11,7 @@ * @return string The absolute path to the .env.slic.stacks file. */ function slic_stacks_registry_file() { - return dirname(__DIR__) . '/.env.slic.stacks'; + return slic_data_dir() . '/.env.slic.stacks'; } /** @@ -497,7 +497,7 @@ function slic_stacks_get_project_name($stack_id) { */ function slic_stacks_get_state_file($stack_id) { $hash = substr(md5($stack_id), 0, 8); - return dirname(__DIR__) . '/.env.slic.run.' . $hash; + return slic_data_dir() . '/.env.slic.run.' . $hash; } /** @@ -918,7 +918,7 @@ function slic_stacks_detect_worktree($path) { * @return bool True if migration was performed, false otherwise. */ function slic_stacks_migrate_legacy() { - $root_dir = dirname( __DIR__ ); + $root_dir = slic_data_dir(); $legacy_run_file = $root_dir . '/.env.slic.run'; $registry_file = slic_stacks_registry_file(); diff --git a/src/utils.php b/src/utils.php index 35c0920..d9d9ede 100644 --- a/src/utils.php +++ b/src/utils.php @@ -733,7 +733,7 @@ function normalize_php_version( $version ) { */ function get_stack_env_file( $stack_id = null ) { if ( null === $stack_id ) { - return root( '.env.slic.run' ); + return slic_data_dir() . '/.env.slic.run'; } // Load stacks.php functions if not already loaded diff --git a/src/xdebug.php b/src/xdebug.php index 496cb34..d6e395f 100644 --- a/src/xdebug.php +++ b/src/xdebug.php @@ -208,7 +208,7 @@ function slic_handle_xdebug( callable $args ) { $run_settings_file = get_stack_env_file( $stack_id ); } else { // Fall back to legacy file if no stack - $run_settings_file = root( '/.env.slic.run' ); + $run_settings_file = slic_data_dir() . '/.env.slic.run'; } $toggle = $args( 'toggle', 'on' );