Skip to content
Draft
Show file tree
Hide file tree
Changes from all commits
Commits
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
14 changes: 11 additions & 3 deletions features/shell.feature
Original file line number Diff line number Diff line change
Expand Up @@ -3,8 +3,12 @@ Feature: WordPress REPL
Scenario: Blank session
Given a WP install

When I run `wp shell < /dev/null`
And I run `wp shell --basic < /dev/null`
And an empty_session file:
"""
"""

When I run `wp shell < empty_session`
And I run `wp shell --basic < empty_session`
Then STDOUT should be empty

Scenario: Persistent environment
Expand Down Expand Up @@ -252,7 +256,11 @@ Feature: WordPress REPL
Scenario: Shell with hook parameter for hook that hasn't fired
Given a WP install

When I try `wp shell --basic --hook=shutdown < /dev/null`
And an empty_session file:
"""
"""

When I try `wp shell --basic --hook=shutdown < empty_session`
Then STDERR should contain:
"""
Error: The 'shutdown' hook has not fired yet
Expand Down
20 changes: 18 additions & 2 deletions src/WP_CLI/Shell/REPL.php
Original file line number Diff line number Diff line change
Expand Up @@ -176,10 +176,12 @@ private function prompt() {
}

private static function create_prompt_cmd( $prompt, $history_path ) {
$prompt = escapeshellarg( $prompt );
$history_path = escapeshellarg( $history_path );
$is_windows = \WP_CLI\Utils\is_windows();

if ( getenv( 'WP_CLI_CUSTOM_SHELL' ) ) {
$shell_binary = (string) getenv( 'WP_CLI_CUSTOM_SHELL' );
} elseif ( $is_windows ) {
$shell_binary = 'powershell.exe';
} elseif ( is_file( '/bin/bash' ) && is_readable( '/bin/bash' ) ) {
// Prefer /bin/bash when available since we use bash-specific commands.
$shell_binary = '/bin/bash';
Expand All @@ -191,10 +193,24 @@ private static function create_prompt_cmd( $prompt, $history_path ) {
$shell_binary = 'bash';
}

$is_powershell = $is_windows && 'powershell.exe' === $shell_binary;

if ( $is_powershell ) {
// PowerShell uses ` (backtick) for escaping but for strings single quotes are literal.
// If prompt contains single quotes, we double them in PowerShell.
$prompt_for_ps = str_replace( "'", "''", $prompt );
$history_path_for_ps = str_replace( "'", "''", $history_path );
$cmd = "\$line = Read-Host -Prompt '{$prompt_for_ps}'; if ( \$line ) { Add-Content -Path '{$history_path_for_ps}' -Value \$line; } Write-Output \$line;";
return "powershell.exe -Command \"{$cmd}\"";
}

if ( ! is_file( $shell_binary ) || ! is_readable( $shell_binary ) ) {
WP_CLI::error( "The shell binary '{$shell_binary}' is not valid. You can override the shell to be used through the WP_CLI_CUSTOM_SHELL environment variable." );
}

$prompt = escapeshellarg( $prompt );
$history_path = escapeshellarg( $history_path );

$is_ksh = self::is_ksh_shell( $shell_binary );
$shell_binary = escapeshellarg( $shell_binary );

Expand Down
Loading