CodeIgniter4 CLI Library
CodeIgniter的CLI库使创建交互式命令行脚本变得简单,包括:
- 提示用户更多信息
- 在终端上写彩色文本
- Beeping(变得更好!)
- 在长任务中显示进度条
- 包装长文本行以适合窗口。
初始化类
您无需创建CLI库的实例,因为它的所有方法都是静态的。相反,您只需要确保您的控制器可以通过use
类上方的一条语句找到它:
<?php namespace App\Controllers;
use CodeIgniter\CLI\CLI;
class MyController extends \CodeIgniter\Controller
{
. . .
}
首次加载文件时,该类会自动初始化。
从用户那里获取输入
有时您需要询问用户更多信息。他们可能没有提供可选的命令行参数,或者脚本可能遇到了现有文件,需要在覆盖前进行确认。这是用prompt()
方法处理的。
您可以通过将其作为第一个参数传递来提供问题:
$color = CLI::prompt('What is your favorite color?');
您可以通过在第二个参数中传递默认值来提供默认答案,如果用户只是按下Enter键,则将使用该默认答案:
$color = CLI::prompt('What is your favorite color?', 'blue');
您可以通过传入允许的答案数组作为第二个参数来限制可接受的答案:
$overwrite = CLI::prompt('File exists. Overwrite?', ['y','n']);
最后,您可以将验证规则作为第三个参数传递给答案输入:
$email = CLI::prompt('What is your email?', null, 'required|valid_email');
提供反馈
write()
提供了几种方法来向用户提供反馈。这可以像单个状态更新一样简单,也可以像包装到用户终端窗口的复杂信息表一样简单。该write()
方法的核心是将字符串作为第一个参数输出的方法:
CLI::write('The rain in Spain falls mainly on the plains.');
您可以通过输入颜色名称作为第二个参数来更改文本的颜色:
CLI::write('File created.', 'green');
这可用于按状态区分消息,或使用其他颜色创建“标题”。您甚至可以通过将颜色名称作为第三个参数传递来设置背景色:
CLI::write('File overwritten.', 'light_red', 'dark_gray');
可以使用以下前景色:
- black
- dark_gray
- blue
- dark_blue
- light_blue
- green
- light_green
- cyan
- light_cyan
- red
- light_red
- purple
- light_purple
- light_yellow
- yellow
- light_gray
- white
较小的数字可用作背景色:
- black
- blue
- green
- cyan
- red
- yellow
- light_gray
- magenta
print()
打印功能与write()
方法相同,除了它不会在换行符之前或之后强制换行。而是将其打印到当前光标所在的屏幕上。这使您可以从不同的呼叫在同一行上打印多个项目。当您要显示状态,执行某些操作然后在同一行上打印“完成”时,这特别有用:
for ($i = 0; $i <= 10; $i++)
{
CLI::print($i);
}
color()
尽管该write()
命令将单行写入终端,并以EOL字符结尾,但是您可以使用该color()
方法制作可以以相同方式使用的字符串片段,除了在打印后不会强制EOL。这使您可以在同一行上创建多个输出。或者,更常见的是,可以在write()
方法内部使用它在内部创建其他颜色的字符串:
CLI::write("fileA \t". CLI::color('/path/to/file', 'white'), 'yellow');
本示例将在窗口中写一行,先以fileA
黄色,然后是制表符,然后 /path/to/file
是白色文本。
error()
如果需要输出错误,则应使用适当命名的error()
方法。像执行操作一样write()
,这会将浅红色文本写入STDERR,而不是STDOUT color()
。如果您有脚本在监视错误,这样它们就不必筛选所有信息,而仅筛选实际的错误消息,这将很有用。您完全按照以下write()
方法使用它:
CLI::error('Cannot write to file: ' . $file);
wrap()
该命令将获取一个字符串,开始在当前行上打印它,并在新行上将其包装为设置的长度。当在您希望在当前窗口中显示而不是离开屏幕的选项列表中显示说明时,这可能会很有用:
CLI::color("task1\t", 'yellow');
CLI::wrap("Some long description goes here that might be longer than the current window.");
默认情况下,字符串将以终端宽度环绕。Windows当前不提供确定窗口大小的方法,因此我们默认使用80个字符。如果您想将宽度限制为更短一些,以确保可以完全适合窗口,请将最大行长作为第二个参数传递。这将在最接近的单词障碍处断开字符串,以便不会损坏单词。
// Wrap the text at max 20 characters wide
CLI::wrap($description, 20);
您可能会发现标题,文件或任务的左侧需要一列,而标题及其说明的右侧则需要一列文本。默认情况下,这将回绕到窗口的左边缘,这不允许事物按列排列。在这种情况下,您可以传递多个空格以填充第一行之后的每一行,以便在左侧留下清晰的列边缘:
// Determine the maximum length of all titles
// to determine the width of the left column
$maxlen = max(array_map('strlen', $titles));
for ($i=0; $i <= count($titles); $i++)
{
CLI::write(
// Display the title on the left of the row
$title[$i] . ' ' .
// Wrap the descriptions in a right-hand column
// with its left side 3 characters wider than
// the longest item on the left.
CLI::wrap($descriptions[$i], 40, $maxlen + 3)
);
}
将创建如下内容:
task1a Lorem Ipsum is simply dummy
text of the printing and typesetting
industry.
task1abc Lorem Ipsum has been the industry's
standard dummy text ever since the
newLine()
该newLine()
方法向用户显示空白行。它不带任何参数:
CLI::newLine();
clearScreen()
您可以使用该clearScreen()
方法清除当前终端窗口。在Windows的大多数版本中,由于Windows不支持此功能,因此只会插入40行空白行。Windows 10 bash集成应更改此:
CLI::clearScreen();
showProgress()
如果您有一个长期运行的任务,想让用户了解进度,则可以使用 showProgress()
显示如下内容的方法:
[####......] 40% Complete
该块在适当位置具有动画效果,效果非常好。
要使用它,请将当前步骤作为第一个参数,并将步骤总数作为第二个参数。完成百分比和显示长度将根据该数字确定。完成后,将pass false
作为第一个参数,进度条将被删除。
$totalSteps = count($tasks);
$currStep = 1;
foreach ($tasks as $task)
{
CLI::showProgress($currStep++, $totalSteps);
$task->run();
}
// Done, so erase it...
CLI::showProgress(false);
table()
$thead = ['ID', 'Title', 'Updated At', 'Active'];
$tbody = [
[7, 'A great item title', '2017-11-15 10:35:02', 1],
[8, 'Another great item title', '2017-11-16 13:46:54', 0]
];
CLI::table($tbody, $thead);
+----+--------------------------+---------------------+--------+
| ID | Title | Updated At | Active |
+----+--------------------------+---------------------+--------+
| 7 | A great item title | 2017-11-16 10:35:02 | 1 |
| 8 | Another great item title | 2017-11-16 13:46:54 | 0 |
+----+--------------------------+---------------------+--------+
wait()
等待一定的秒数,可以选择显示一条等待消息并等待按键。
// wait for specified interval, with countdown displayed
CLI::wait($seconds, true);
// show continuation message and wait for input
CLI::wait(0, false);
// wait for specified interval
CLI::wait($seconds, false);