@@ -39,50 +39,48 @@ public function start() {
3939 WP_CLI ::log ( "Detected changes in {$ this ->watch_path }, restarting shell... " );
4040 return self ::EXIT_CODE_RESTART ;
4141 }
42+ $ __repl_input_line = $ this ->prompt ();
4243
43- $ line = $ this ->prompt ();
44-
45- if ( '' === $ line ) {
44+ if ( '' === $ __repl_input_line ) {
4645 continue ;
4746 }
4847
4948 // Check for special exit command
50- if ( 'exit ' === trim ( $ line ) ) {
49+ if ( 'exit ' === trim ( $ __repl_input_line ) ) {
5150 return 0 ;
5251 }
52+ $ __repl_input_line = rtrim ( $ __repl_input_line , '; ' ) . '; ' ;
5353
5454 // Check for special restart command
55- if ( 'restart ' === trim ( $ line ) ) {
55+ if ( 'restart ' === trim ( $ __repl_input_line ) ) {
5656 WP_CLI ::log ( 'Restarting shell... ' );
5757 return self ::EXIT_CODE_RESTART ;
5858 }
5959
60- $ line = rtrim ( $ line , '; ' ) . '; ' ;
61-
62- if ( self ::starts_with ( self ::non_expressions (), $ line ) ) {
60+ if ( self ::starts_with ( self ::non_expressions (), $ __repl_input_line ) ) {
6361 ob_start ();
6462 // phpcs:ignore Squiz.PHP.Eval.Discouraged -- This is meant to be a REPL, no way to avoid eval.
65- eval ( $ line );
66- $ out = (string ) ob_get_clean ();
67- if ( 0 < strlen ( $ out ) ) {
68- $ out = rtrim ( $ out , "\n" ) . "\n" ;
63+ eval ( $ __repl_input_line );
64+ $ __repl_output = (string ) ob_get_clean ();
65+ if ( 0 < strlen ( $ __repl_output ) ) {
66+ $ __repl_output = rtrim ( $ __repl_output , "\n" ) . "\n" ;
6967 }
70- fwrite ( STDOUT , $ out );
68+ fwrite ( STDOUT , $ __repl_output );
7169 } else {
72- if ( ! self ::starts_with ( 'return ' , $ line ) ) {
73- $ line = 'return ' . $ line ;
70+ if ( ! self ::starts_with ( 'return ' , $ __repl_input_line ) ) {
71+ $ __repl_input_line = 'return ' . $ __repl_input_line ;
7472 }
7573
7674 // Write directly to STDOUT, to sidestep any output buffers created by plugins
7775 ob_start ();
7876 // phpcs:ignore Squiz.PHP.Eval.Discouraged -- This is meant to be a REPL, no way to avoid eval.
79- $ evl = eval ( $ line );
80- $ out = (string ) ob_get_clean ();
81- if ( 0 < strlen ( $ out ) ) {
82- echo rtrim ( $ out , "\n" ) . "\n" ;
77+ $ __repl_eval_result = eval ( $ __repl_input_line );
78+ $ __repl_output = (string ) ob_get_clean ();
79+ if ( 0 < strlen ( $ __repl_output ) ) {
80+ echo rtrim ( $ __repl_output , "\n" ) . "\n" ;
8381 }
8482 echo '=> ' ;
85- var_dump ( $ evl );
83+ var_dump ( $ __repl_eval_result );
8684 fwrite ( STDOUT , (string ) ob_get_clean () );
8785 }
8886 }
@@ -154,8 +152,15 @@ private static function create_prompt_cmd( $prompt, $history_path ) {
154152 $ history_path = escapeshellarg ( $ history_path );
155153 if ( getenv ( 'WP_CLI_CUSTOM_SHELL ' ) ) {
156154 $ shell_binary = (string ) getenv ( 'WP_CLI_CUSTOM_SHELL ' );
157- } else {
155+ } elseif ( is_file ( '/bin/bash ' ) && is_readable ( '/bin/bash ' ) ) {
156+ // Prefer /bin/bash when available since we use bash-specific commands.
158157 $ shell_binary = '/bin/bash ' ;
158+ } elseif ( getenv ( 'SHELL ' ) && self ::is_bash_shell ( (string ) getenv ( 'SHELL ' ) ) ) {
159+ // Only use SHELL as fallback if it's bash (we use bash-specific commands).
160+ $ shell_binary = (string ) getenv ( 'SHELL ' );
161+ } else {
162+ // Final fallback for systems without /bin/bash.
163+ $ shell_binary = 'bash ' ;
159164 }
160165
161166 if ( ! is_file ( $ shell_binary ) || ! is_readable ( $ shell_binary ) ) {
@@ -176,6 +181,21 @@ private static function create_prompt_cmd( $prompt, $history_path ) {
176181 return "{$ shell_binary } -c " . escapeshellarg ( $ cmd );
177182 }
178183
184+ /**
185+ * Check if a shell binary is bash or bash-compatible.
186+ *
187+ * @param string $shell_path Path to the shell binary.
188+ * @return bool True if the shell is bash, false otherwise.
189+ */
190+ private static function is_bash_shell ( $ shell_path ) {
191+ if ( ! is_file ( $ shell_path ) || ! is_readable ( $ shell_path ) ) {
192+ return false ;
193+ }
194+ // Check if the basename is exactly 'bash' or starts with 'bash' followed by a version/variant.
195+ $ basename = basename ( $ shell_path );
196+ return 'bash ' === $ basename || 0 === strpos ( $ basename , 'bash- ' );
197+ }
198+
179199 private function set_history_file () {
180200 $ data = getcwd () . get_current_user ();
181201
0 commit comments