Новое в Symfony 3.2: Новые фичи консоли (Часть 2)

В этом второй часть(статья из двух частей), мы рассмотрим еще четыре новых функции, добавленные Symfony 3.2 к компоненту Console, чтобы улучшить его DX (опыт разработчика).

Введен новый класс Terminal

Консольный класс Application определяет несколько методов, чтобы получить размеры (высота и ширина) окна терминала:

use Symfony\Component\Console\Application;

$application = new Application();
$dimensions = $application->getTerminalDimensions(); // [$width, $height]
$height = $application->getTerminalHeight();
$width = $application->getTerminalWidth();

С технической точки зрения получать эту информацию для всех видов терминалов и операционных систем является сложным, запутанным, медленным и подверженым ошибкам процессом. В Symfony 3.2 мы решили перенести всю эту логику в новый класс Terminal:

use Symfony\Component\Console\Terminal;

$height = (new Terminal())->getHeight();
$width = (new Terminal())->getWidth();

Кроме того, мы улучшили логику, чтобы получить/установить размеры, чтобы установить приоритет использования переменных окружения. Если переменные окружения COLUMNS и LINES определены, Terminal использует их значения, чтобы получить размеры. При установке размеров, терминал создает или обновляет значения этих переменных.

Этот новый  класс Terminal будет использоваться в дальнейшем, чтобы получать/устанавливать более подробную информацию о терминале, а не только его размеры. На данный момент, эти изменения позволили нам исправить некоторые крайние случаи в помощнике Progress Bar, когда окно терминала было небольшим.

Введен новый интерфейс StreamableInputInterface

В Symfony 2.8 мы ввели новый стиль для консоли, который упрощает создание последовательных команд. Тем не менее, эти команды было трудно проверить, особенно при использовании помощника ask(), при получении ввода пользователя.

В Symfony 3.2 мы ввели новый StreamableInputInterface и сделали абстрактную его реализацию Symfony\Component\Console\Input\Input. Это изменение позволяет централизовать управление входным потоком в одном классе, и облегчит для тестирования код, связанный с QuestionHelper.

Добавлен метод hasErrors() в ConsoleLogger

В Symfony 3.2, класс ConsoleLogger включает в себя метод с hasErrored(), которая возвращает true, как только одно сообщение уровня ERROR было зарегистрировано. Таким образом, вам не нужно добавлять какие-либо пользовательскую логику, чтобы решить, следует ли вашей команде возвращать код завершения (exit(1)) или нет.

Добавлен «Lockable» trait

В Symfony 2.6 мы ввели lock handler, для обеспечения простой абстракции, чтобы залочить что-либо с помощью блокировки файла. Этот обработчик блокировки в основном используется, для избежания проблем параллелизма, предотвращая множественное выполнение одной и той же команды:

use Symfony\Component\Filesystem\LockHandler;

class UpdateContentsCommand extends Command
{
    protected function execute(InputInterface $input, OutputInterface $output)
    {
        $lock = new LockHandler('update:contents');
        if (!$lock->lock()) {
            // manage lock errors
        }

        // ...
    }
}

В Symfony 3.2 мы сделали обработчик блокировки немного проще в использовании благодаря новому LockableTrait. Эта особенность содержит метод lock(), который создает не-блокируемую блокировки имени текущей команды:

use Symfony\Component\Console\Command\LockableTrait;

class UpdateContentsCommand extends Command
{
    use LockableTrait;

    protected function execute(InputInterface $input, OutputInterface $output)
    {
         if (!$this->lock()) {
             // manage lock errors
         }

        // ...
    }
}

Вы также можете создавать блокировки с пользовательскими именами и даже блокировки блокировок, которые ждут, пока какая нибудь из существующих блокировок не будет снята:

if (!$this->lock('custom_lock_name')) { ... }

// the second boolean argument tells whether the lock is blocking or not
if (!$this->lock('custom_lock_name', true)) { ... }

Добавить комментарий

Ваш e-mail не будет опубликован. Обязательные поля помечены *

два × 5 =