LE Blog

Инженер с поэтической душой

02.03.2016 firtree_right Лось

Сейчас меня уже почти не спрашивают: «Почему лось?» Отчасти потому, что я не очень продвигаю этого персонажа, а отчасти потому, что люди думают, что мне просто нравятся лоси, или я их коллекционирую. Второе приводит, например, к тому, что мне дарят разных игрушечных лосей. Это забавный результат, поэтому я считаю, что репутацию местного сумасшедшего нужно поддерживать. Как следствие я начал использовать лосей в повседневной работе.

Терминал

Первым делом нужно, чтобы лось приветствовал меня при каждом открытии терминала или новой его вкладки. Примерно так:

лось в терминале

При этом хотелось бы, чтобы у него было разное случайное выражение лица. Для этого нужно в ~/.bash_profile (или какой у вас файл для создания окружения) написать следующее:

eye=(o O @ . - \* \~ °)
let left=${RANDOM}%${#eye[*]}
let right=${RANDOM}%${#eye[*]}

cat << EOF

 _  _        _  _  _
| || | ____ | || || |
\    |/    \|      /
 \____ ${eye[$left]}  ${eye[$right]} ______/
      |    |________
      |             }=
      | __  ____  _ |
      ||  ||    || ||
      ||  ||    || ||
      ""  ""    "" ""

EOF

Базовая работа с массивами. Встроенная в баш функция случайного числа. Обязательно предварять косой чертой «*» и «~», чтобы они не стали списком файлов и домашней директорией. По-моему — красота!

Spec runner

И, конечно же, для любителей разработки через тестирование нужен правильный репортер:

elk-spec

Здесь нужно пользоваться эскейп кодами для управления положением каретки, то есть курсора. Мало кто помнит, но курсор можно двигать во все стороны на любое количество позиций. Данный пример я собрал для раннера тестов на жасмине. Да, да, я разрабатываю в том числе на node.js и тестирую с помощью jasmine. Ключевая функция для рисования лося вот:

function printElk() {
  if (specCount > 1) {
    print('\x1b[5A');
  }
  if (specCount % 2 === 0) {
    print(Array(specCount + 1).join(' ') + '     ^^' + eyes() + '^^\n');
    print(Array(specCount + 1).join(' ') + '  _____ U\n');
    print(specTrail + '~(  _  /\n');
    print(Array(specCount + 1).join(' ') + '  || ||\n');
    print(Array(specCount + 1).join(' ') + '  ^^ ^^\n');
  } else {
    print(Array(specCount + 1).join(' ') + '      ^^' + eyes() + '^^\n');
    print(Array(specCount + 1).join(' ') + '  _____ U\n');
    print(specTrail + '`(  _  /\n');
    print(Array(specCount + 1).join(' ') + '  // \\\\\n');
    print(Array(specCount + 1).join(' ') + ' ^^   ^^\n');
  }
}

Здесь specTrail и eyes следят за историей вопроса, а вся функция вместо того, чтобы как раньше, ставить точку или F, поднимается на пять строчек вверх и переписывает их полностью.

Бонус

Это не про лося, но тем не менее. Вообще, я считаю, что всегда лучше потратить немного времени, чтобы сделать всё удобно и интересно. Мелочи решают!

Эту вещь придумал не я. Скорее всего, до меня её придумали неоднократно, и я не могу найти первоисточник. Тем не менее, считаю, что это очень полезная вещь, и нужно ей поделиться. Речь идёт о том, чтобы показывать статус завершения предыдущей команды в строке запроса баша.

export PS1="\[\e]0;\u@\h: \W\a\`if [ \$? = 0 ];then echo \[\e[32m\]^_^\[\e[0m\];else echo \[\e[31m\]o_O\[\e[0m\];fi\`[\u@\h: \w][\$(rvm-prompt v)][\$(nvm_version)]\$(parse_git_branch)\$ "

Это моя строка запроса. В её начале мы видим или зелёный довольный смайлик, или красный удивлённый. Благодаря вот этой части:

\`if [ \$? = 0 ];then echo \[\e[32m\]^_^\[\e[0m\];else echo \[\e[31m\]o_O\[\e[0m\];fi\`

Когда сделал себе и привык, то теперь просто не понимаю, как другие без этого обходятся.

Материалы для самостоятельного изучения

  1. $RANDOM.
  2. elk_reporter.js.
  3. Управление курсором в баше.