File: /wordpress/mu-plugins/atomic-cli-disk-usage.php
<?php
/**
* Output disk usage information for the document root and tmp directories
*
* [--depth=<number>]
* : Number of directory levels to traverse
* ---
* default: 2
* ---
*/
function atomic_cli_disk_usage( $args, $assoc_args ) {
// Get path depth arg
if ( empty( $assoc_args['depth'] ) ) {
$depth = '2';
} else {
$depth = (string) $assoc_args['depth'];
}
if ( ! ctype_digit( $depth ) ) {
WP_CLI::warning( 'The depth argument must be a positive number.' );
return;
}
$escaped_depth = escapeshellarg( $depth );
// Run the shell command
$command = escapeshellcmd( "/usr/bin/du --bytes --time --max-depth={$escaped_depth} '/srv/htdocs' '/tmp'" );
$result = exec( $command, $output, $result_code );
if ( false === $result || empty( $output ) || 0 !== $result_code ) {
WP_CLI::warning( 'Could not get disk usage information.' );
return;
}
// Define table headers and initialize their string lengths as the column max widths
$headers = array(
'bytes' => 'Bytes',
'date' => 'Date Modified',
'path' => 'Directory',
);
$max_strlen = array(
'bytes' => strlen( $headers['bytes'] ),
'date' => strlen( $headers['date'] ),
'path' => strlen( $headers['path'] ),
);
// Parse the output lines and get the max width of each column
$parsed_results = array();
foreach ( $output as $line ) {
if ( empty( $line ) ) {
continue;
}
$parts = preg_split( '/\s+/', $line );
$parsed_line['bytes'] = $parts[0];
$parsed_line['date'] = "{$parts[1]} {$parts[2]}";
$parsed_line['path'] = $parts[3];
$parsed_results[] = $parsed_line;
$max_strlen['bytes'] = max( $max_strlen['bytes'], strlen( number_format( $parsed_line['bytes'] ) ) );
$max_strlen['date'] = max( $max_strlen['date'], strlen( $parsed_line['date'] ) );
$max_strlen['path'] = max( $max_strlen['path'], strlen( $parsed_line['path'] ) );
}
// Sort by path name in order to easily filter out duplicated parent paths
usort(
$parsed_results,
static function( $a, $b ) {
if ( $a['path'] < $b['path'] ) {
return 1;
}
if ( $a['path'] > $b['path'] ) {
return -1;
}
return 0;
}
);
// Filter out results with a parent directory when child directories are also included
$prev_path = null;
$filtered_results = array();
foreach ( $parsed_results as $parsed_result ) {
if ( null ===$prev_path || ! ( 0 === strpos( $prev_path, $parsed_result['path'] ) ) ) {
$prev_path = $parsed_result['path'];
$filtered_results[] = $parsed_result;
}
}
// Sort the results in descending order by byte size
usort(
$filtered_results,
static function( $a, $b ) {
if ( (int) $a['bytes'] < (int) $b['bytes'] ) {
return 1;
}
if ( (int) $a['bytes'] > (int) $b['bytes'] ) {
return -1;
}
return 0;
}
);
$format = "| %{$max_strlen['bytes']}s | %{$max_strlen['date']}s | %-{$max_strlen['path']}s |\n";
$horiz_sep = '+-' . str_repeat( '-', $max_strlen['bytes'] ) . '-+-' . str_repeat( '-', $max_strlen['date'] ) . '-+-' . str_repeat( '-', $max_strlen['path'] ) . "-+\n";
echo $horiz_sep;
printf( $format, $headers['bytes'], $headers['date'], $headers['path'] );
echo $horiz_sep;
foreach ( $filtered_results as $data ) {
printf( $format, number_format( $data['bytes'] ), $data['date'], $data['path'] );
}
echo $horiz_sep;
}
if ( class_exists( 'WP_CLI' ) ) {
WP_CLI::add_command( 'disk-usage', 'atomic_cli_disk_usage' );
}