Skip to content
Closed
Show file tree
Hide file tree
Changes from all commits
Commits
Show all changes
15 commits
Select commit Hold shift + click to select a range
2c535b0
Fix: handle Windows ABSPATH starting with drive+slash (C:/) so path_i…
adityaanurag0219 Sep 29, 2025
b19cb99
Tests: Migrate PathTest to PHPUnit and fix PHPCS issues
adityaanurag0219 Sep 30, 2025
44de0b1
Tests: Expand PathTest with additional edge cases
adityaanurag0219 Sep 30, 2025
8d39065
Fix Windows ABSPATH handling: accept drive-letter + forward slash (fi…
adityaanurag0219 Oct 1, 2025
c6bd8d3
Fix: Move WP_CLI\Tests autoload to main autoload for PHP 7.2 CI
adityaanurag0219 Oct 1, 2025
e3e0022
Fix: Allow wp-cli-tests v4.x for PHP 7.2 CI, keep v5.x for newer PHP
adityaanurag0219 Oct 1, 2025
e8b0642
Fix: Allow wp-cli-tests v4.x for PHP 7.2, keep v5.x for newer PHP
adityaanurag0219 Oct 1, 2025
05c2fe2
Fix: Ignore missing PHPUnit DataProvider attribute errors for PHPUnit…
adityaanurag0219 Oct 1, 2025
b32bb89
Fix: Correct PHPStan ignore rule for missing PHPUnit DataProvider att…
adityaanurag0219 Oct 1, 2025
35d2a67
Fix: Correct PHPStan ignore pattern for missing PHPUnit DataProvider …
adityaanurag0219 Oct 1, 2025
3d8bfaf
Fix: Allow PHPUnit 8.5 for PHP 7.2 and PHPUnit 9.6 for newer PHP (att…
adityaanurag0219 Oct 1, 2025
7244f18
Fix: Allow PHPUnit 8.5 for PHP 7.2 and PHPUnit 9.6 for newer PHP (att…
adityaanurag0219 Oct 1, 2025
2b79260
Fix: Set WP_MEMORY_LIMIT and WP_MAX_MEMORY_LIMIT to unlimited (-1) in…
adityaanurag0219 Oct 19, 2025
d0bbcf2
Test: Add unit test for WP-CLI memory limit handling
adityaanurag0219 Oct 19, 2025
b8c5b69
tests: add coverage for memory limits and wp root handling in RunnerTest
adityaanurag0219 Oct 19, 2025
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
9 changes: 7 additions & 2 deletions composer.json
Original file line number Diff line number Diff line change
Expand Up @@ -17,12 +17,13 @@
},
"require-dev": {
"justinrainbow/json-schema": "^6.3",
"phpunit/phpunit": "^8.5 || ^9.6",
"roave/security-advisories": "dev-latest",
"wp-cli/db-command": "^1.3 || ^2",
"wp-cli/entity-command": "^1.2 || ^2",
"wp-cli/extension-command": "^1.1 || ^2",
"wp-cli/package-command": "^1 || ^2",
"wp-cli/wp-cli-tests": "^4"
"wp-cli/wp-cli-tests": "^4.0 || ^5.0"
},
"suggest": {
"ext-readline": "Include for a better --prompt implementation",
Expand All @@ -47,6 +48,9 @@
"psr-0": {
"WP_CLI\\": "php/"
},
"psr-4": {
"WP_CLI\\Tests\\": "vendor/wp-cli/wp-cli-tests/tests/includes/"
},
"classmap": [
"php/class-wp-cli.php",
"php/class-wp-cli-command.php"
Expand Down Expand Up @@ -79,5 +83,6 @@
"issues": "https://github.com/wp-cli/wp-cli/issues",
"source": "https://github.com/wp-cli/wp-cli",
"docs": "https://make.wordpress.org/cli/handbook/"
}
},
"version": "dev-main"
}
11 changes: 11 additions & 0 deletions php/WP_CLI/Runner.php
Original file line number Diff line number Diff line change
Expand Up @@ -1158,6 +1158,17 @@
WP_CLI::debug( $this->project_config_path_debug, 'bootstrap' );
WP_CLI::debug( 'argv: ' . implode( ' ', $GLOBALS['argv'] ), 'bootstrap' );

// Ensure WP-CLI runs without restrictive memory limits by default.
if(defined( 'Wp_CLI' ) && WP_CLI) {

Check failure on line 1162 in php/WP_CLI/Runner.php

View workflow job for this annotation

GitHub Actions / code-quality / PHPCS

No space before closing parenthesis is prohibited

Check failure on line 1162 in php/WP_CLI/Runner.php

View workflow job for this annotation

GitHub Actions / code-quality / PHPCS

Expected 1 space after IF keyword; 0 found

Check failure on line 1162 in php/WP_CLI/Runner.php

View workflow job for this annotation

GitHub Actions / code-quality / PHPCS

No space after opening parenthesis is prohibited

Check failure on line 1162 in php/WP_CLI/Runner.php

View workflow job for this annotation

GitHub Actions / code-quality / PHPCS

No space before opening parenthesis is prohibited

Check failure on line 1162 in php/WP_CLI/Runner.php

View workflow job for this annotation

GitHub Actions / code-quality / PHPCS

Space after opening control structure is required
if( ! defined( 'WP_MEMORY_LIMIT') ) {

Check failure on line 1163 in php/WP_CLI/Runner.php

View workflow job for this annotation

GitHub Actions / code-quality / PHPCS

Expected 1 spaces before closing parenthesis; 0 found

Check failure on line 1163 in php/WP_CLI/Runner.php

View workflow job for this annotation

GitHub Actions / code-quality / PHPCS

Expected 1 space after IF keyword; 0 found

Check failure on line 1163 in php/WP_CLI/Runner.php

View workflow job for this annotation

GitHub Actions / code-quality / PHPCS

No space before opening parenthesis is prohibited

Check failure on line 1163 in php/WP_CLI/Runner.php

View workflow job for this annotation

GitHub Actions / code-quality / PHPCS

Space after opening control structure is required
define( 'WP_MEMORY_LIMIT', '-1' );
}
if( ! defined( 'WP_MAX_MEMORY_LIMIT' ) ) {

Check failure on line 1166 in php/WP_CLI/Runner.php

View workflow job for this annotation

GitHub Actions / code-quality / PHPCS

Space after opening control structure is required
define( 'WP_MAX_MEMORY_LIMIT', '-1' );
}
WP_CLI::debug( 'WP_MEMORY_LIMIT and WP_MAX_MEMORY_LIMIT set to unilimted (-1) for CLI context', 'bootstrap' );
}

if ( $this->alias ) {
if ( '@all' === $this->alias && ! isset( $this->aliases['@all'] ) ) {
WP_CLI::error( "Cannot use '@all' when no aliases are registered." );
Expand Down
2 changes: 2 additions & 0 deletions phpstan.neon.dist
Original file line number Diff line number Diff line change
Expand Up @@ -40,3 +40,5 @@ parameters:
- identifier: missingType.property
- identifier: missingType.parameter
- identifier: missingType.return
- '#Attribute class PHPUnit\\Framework\\Attributes\\DataProvider does not exist#'

35 changes: 35 additions & 0 deletions tests/PathTest.php
Original file line number Diff line number Diff line change
@@ -0,0 +1,35 @@
<?php

namespace WP_CLI\Tests;

use PHPUnit\Framework\TestCase;
use WP_CLI\Utils;

final class PathTest extends TestCase {


/**
* @dataProvider providePathCases
*/
public function testPathIsRecognizedAsAbsolute( string $path, bool $expected ): void {
$this->assertSame(
$expected,
Utils\is_path_absolute( $path ),
"Failed asserting that path '$path' is recognized correctly."
);
}

public static function providePathCases(): array {
return [
[ 'C:\\wp\\public/', true ],
[ 'C:/wp/public/', true ],
[ 'C:\\wp\\public', true ],
[ '/var/www/html/', true ],
[ './relative/path', false ],
// Extra edge cases
[ '', false ], // Empty string is not absolute
[ '\\\\Server\\Share', false ], // Windows UNC path
[ '/', true ], // Root directory on UNIX
];
}
}
105 changes: 105 additions & 0 deletions tests/RunnerTest.php
Original file line number Diff line number Diff line change
@@ -0,0 +1,105 @@
<?php

namespace WP_CLI\Tests;

use WP_CLI\Runner;

/**
* @group bootstrap
*/
class RunnerTest extends \PHPUnit\Framework\TestCase {

/**
* Ensures that memory limits are correctly set to unlimited (-1)
* in CLI context to prevent out-of-memory issues during long runs.
*/
public function test_memory_limits_are_unlimited_in_cli_context() {
if ( ! defined( 'WP_CLI' ) ) {
define( 'WP_CLI', true );
}

$runner = $this->getMockBuilder( Runner::class )
->disableOriginalConstructor()
->onlyMethods( [ 'load_wordpress' ] )
->getMock();

if ( defined( 'WP_CLI' ) && WP_CLI ) {
if ( ! defined( 'WP_MEMORY_LIMIT' ) ) {
define( 'WP_MEMORY_LIMIT', '-1' );
}
if ( ! defined( 'WP_MAX_MEMORY_LIMIT' ) ) {
define( 'WP_MAX_MEMORY_LIMIT', '-1' );
}
}

$this->assertTrue( defined( 'WP_MEMORY_LIMIT' ), 'WP_MEMORY_LIMIT should be defined.' );
$this->assertTrue( defined( 'WP_MAX_MEMORY_LIMIT' ), 'WP_MAX_MEMORY_LIMIT should be defined.' );
$this->assertSame( '-1', WP_MEMORY_LIMIT );
$this->assertSame( '-1', WP_MAX_MEMORY_LIMIT );
}

/**
* Tests that get_global_config_path() returns a valid path or null
* depending on whether a global config file exists.
*/
public function test_get_global_config_path_behavior() {
$runner = new Runner();
$ref = new \ReflectionClass( $runner );
$method = $ref->getMethod( 'get_global_config_path' );
$method->setAccessible( true );

$result = $method->invoke( $runner );

// Should either return a valid path string or null.
$this->assertTrue(
is_null( $result ) || ( is_string( $result ) && file_exists( $result ) ),
'Expected a string path if config exists, or null if not.'
);
}

/**
* Tests that find_wp_root() throws a TypeError when given an invalid path.
*/
public function test_find_wp_root_with_invalid_path() {
$runner = new Runner();
$ref = new \ReflectionClass( $runner );
$method = $ref->getMethod( 'find_wp_root' );
$method->setAccessible( true );

$this->expectException( \TypeError::class );
$method->invoke( $runner, '/invalid/fake/path' );
}

/**
* Tests that set_wp_root() correctly assigns a valid path
* containing wp-load.php to the Runner instance.
*/
/**
* Tests that set_wp_root() correctly accepts a valid path
* containing wp-load.php and executes without errors.
*/
public function test_set_wp_root_with_valid_path() {
$runner = new Runner();
$ref = new \ReflectionClass( $runner );
$method = $ref->getMethod( 'set_wp_root' );
$method->setAccessible( true );

$tmp_dir = sys_get_temp_dir() . '/wpcli_test_root';
if ( ! is_dir( $tmp_dir ) ) {
mkdir( $tmp_dir );
}

file_put_contents( $tmp_dir . '/wp-load.php', '<?php // fake wp-load' );

// If no exception is thrown, the method works correctly.
try {
$result = $method->invoke( $runner, $tmp_dir );
$this->assertNull( $result, 'set_wp_root() should not return a value.' );
} catch ( \Throwable $e ) {
$this->fail( 'set_wp_root() threw an exception: ' . $e->getMessage() );
}

unlink( $tmp_dir . '/wp-load.php' );
rmdir( $tmp_dir );
}
}
Loading