Skip to content
Merged
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
32 changes: 32 additions & 0 deletions features/bootstrap.feature
Original file line number Diff line number Diff line change
Expand Up @@ -506,3 +506,35 @@ Feature: Bootstrap WP-CLI
Given an empty directory
When I try `{INVOKE_WP_CLI_WITH_PHP_ARGS--ddisable_functions=ini_set} cli info`
Then the return code should be 0

Scenario: Test early root detection

Given an empty directory
And a include.php file:
"""
<?php
namespace WP_CLI\Bootstrap;

// To override posix_geteuid in our namespace
function posix_geteuid() {
return 0;
}
?>
"""

And I try `WP_CLI_EARLY_REQUIRE=include.php wp cli version --debug`

Then STDERR should contain:
"""
WP_CLI\Bootstrap\CheckRoot
"""

And STDERR should not contain:
"""
WP_CLI\Bootstrap\IncludeRequestsAutoloader
"""

And STDERR should contain:
"""
YIKES!
"""
70 changes: 70 additions & 0 deletions php/WP_CLI/Bootstrap/CheckRoot.php
Original file line number Diff line number Diff line change
@@ -0,0 +1,70 @@
<?php

namespace WP_CLI\Bootstrap;

use WP_CLI;
use WP_CLI\Utils;

/**
* Class CheckRoot.
*
* Check if the user is running as root and aborts with a warning if they are.
*
* @package WP_CLI\Bootstrap
*/
class CheckRoot implements BootstrapStep {

/**
* Process this single bootstrapping step.
*
* @param BootstrapState $state Contextual state to pass into the step.
*
* @return BootstrapState Modified state to pass to the next step.
*/
public function process( BootstrapState $state ) {
$config = $state->getValue( 'config', [] );
if ( array_key_exists( 'allow-root', $config ) && true === $config['allow-root'] ) {
// They're aware of the risks and set a flag to allow root.
return $state;
}

if ( getenv( 'WP_CLI_ALLOW_ROOT' ) ) {
// They're aware of the risks and set an environment variable to allow root.
return $state;
}

$args = $state->getValue( 'arguments', [] );
if ( count( $args ) >= 2 && 'cli' === $args[0] && in_array( $args[1], [ 'update', 'info' ], true ) ) {
// Make it easier to update root-owned copies.
return $state;
}

if ( ! function_exists( 'posix_geteuid' ) ) {
// POSIX functions not available.
return $state;
}

if ( posix_geteuid() !== 0 ) {
// Not root.
return $state;
}

WP_CLI::error(
"YIKES! It looks like you're running this as root. You probably meant to " .
"run this as the user that your WordPress installation exists under.\n" .
"\n" .
"If you REALLY mean to run this as root, we won't stop you, but just " .
'bear in mind that any code on this site will then have full control of ' .
"your server, making it quite DANGEROUS.\n" .
"\n" .
"If you'd like to continue as root, please run this again, adding this " .
"flag: --allow-root\n" .
"\n" .
"If you'd like to run it as the user that this site is under, you can " .
"run the following to become the respective user:\n" .
"\n" .
" sudo -u USER -i -- wp <command>\n" .
"\n"
);
}
}
4 changes: 4 additions & 0 deletions php/WP_CLI/Bootstrap/ConfigureRunner.php
Original file line number Diff line number Diff line change
Expand Up @@ -22,6 +22,10 @@ public function process( BootstrapState $state ) {
$runner = new RunnerInstance();
$runner()->init_config();

$state->setValue( 'config', $runner()->config );
$state->setValue( 'arguments', $runner()->arguments );
$state->setValue( 'assoc_args', $runner()->assoc_args );

return $state;
}
}
34 changes: 0 additions & 34 deletions php/WP_CLI/Runner.php
Original file line number Diff line number Diff line change
Expand Up @@ -1103,39 +1103,6 @@ public function init_config() {
$this->required_files['runtime'] = $this->config['require'];
}

private function check_root() {
if ( $this->config['allow-root'] || getenv( 'WP_CLI_ALLOW_ROOT' ) ) {
return; # they're aware of the risks!
}
if ( count( $this->arguments ) >= 2 && 'cli' === $this->arguments[0] && in_array( $this->arguments[1], [ 'update', 'info' ], true ) ) {
return; # make it easier to update root-owned copies
}
if ( ! function_exists( 'posix_geteuid' ) ) {
return; # posix functions not available
}
if ( posix_geteuid() !== 0 ) {
return; # not root
}

WP_CLI::error(
"YIKES! It looks like you're running this as root. You probably meant to " .
"run this as the user that your WordPress installation exists under.\n" .
"\n" .
"If you REALLY mean to run this as root, we won't stop you, but just " .
'bear in mind that any code on this site will then have full control of ' .
"your server, making it quite DANGEROUS.\n" .
"\n" .
"If you'd like to continue as root, please run this again, adding this " .
"flag: --allow-root\n" .
"\n" .
"If you'd like to run it as the user that this site is under, you can " .
"run the following to become the respective user:\n" .
"\n" .
" sudo -u USER -i -- wp <command>\n" .
"\n"
);
}

private function run_alias_group( $aliases ) {
Utils\check_proc_available( 'group alias' );

Expand Down Expand Up @@ -1183,7 +1150,6 @@ public function start() {
WP_CLI::debug( $this->project_config_path_debug, 'bootstrap' );
WP_CLI::debug( 'argv: ' . implode( ' ', $GLOBALS['argv'] ), 'bootstrap' );

$this->check_root();
if ( $this->alias ) {
if ( '@all' === $this->alias && ! isset( $this->aliases['@all'] ) ) {
WP_CLI::error( "Cannot use '@all' when no aliases are registered." );
Expand Down
3 changes: 2 additions & 1 deletion php/bootstrap.php
Original file line number Diff line number Diff line change
Expand Up @@ -22,9 +22,10 @@ function get_bootstrap_steps() {
Bootstrap\DeclareAbstractBaseCommand::class,
Bootstrap\IncludeFrameworkAutoloader::class,
Bootstrap\ConfigureRunner::class,
Bootstrap\IncludeRequestsAutoloader::class,
Bootstrap\InitializeColorization::class,
Bootstrap\InitializeLogger::class,
Bootstrap\CheckRoot::class,
Bootstrap\IncludeRequestsAutoloader::class,
Bootstrap\DefineProtectedCommands::class,
Bootstrap\LoadExecCommand::class,
Bootstrap\LoadRequiredCommand::class,
Expand Down