← All posts tagged bash-completion

Self-Perfection
code bash-completion
С некоторых пор предпочитаю указывать пути к дискам/разделам как /dev/disk/by-id/XXX. Указание через /dev/sdX кажется подверженным случайным упсам. Можно опечататься, порядок дисков мог поменяться, в общем легко для деструктивной операции указать не тот диск.

К сожалению, bash-completion для большинства дисковых утилит слишком умён, чтобы предлагать только диски, но слишком туп, чтобы предлагать в том числе пути из /dev/disk/by-*. Приходится извращаться:
ls /dev/disk/by-id/foo<Tab>^A Alt-d pvcreate
Ну, кто пофиксит?
Self-Perfection
Debian code jessie bash-completion
Что-то у меня очень сильно разъехалось на работе на арчике, так что сломалась его загрузка. И по такому поводу, понимая, что чинить его и разруливать обновления за больше чем полугода та ещё морока, да и зачем мне rolling release, если я так редко на работе глобально обновляюсь, решил поставить Debian 8. Ещё отчасти из-за любопытства, потому что хоть убунтоклоны всякие много трогал, на чистом дебиане не сидел.

Итак расскажу я вам про цирк с bash-completion. Кратко: если у вас свой .bashrc, то bash-completion не работает.

Вообще в /etc/skel/.bashrc есть блок, который сорсит нужные файлы. Но у меня-то свои dotfiles. "Странно", - думаю я: "Занафига подключать bash-completion через пользовательский rc, если он ставится глобальносистемно, значит должен включаться через /etc". И действительно, в /etc/bash.bashrc есть блок, который сорсит bash-completion. Но он закомментирован. Но это, конечно, странно, блок для поддержки прикладного инструмента, который ставится дополнительным пакетом, не должен быть в общем конфиге. И действительно, есть /etc/profile.d/bash_completion.sh! Он не закомментирован, и если я делаю source /etc/profile, то bash-completion включается. Почему же он не включается при логине?

Оказывается, в нём есть такое условие 
# Check for interactive bash and that we haven't already been sourced.
if [ -n "$BASH_VERSION" -a -n "$PS1" -a -z "$BASH_COMPLETION_COMPAT_DIR" ]; then
И этот тест проваливается, потому что "$PS1" очень даже -z. Вообще уже это, пожалуй, баг, потому что правильная проверка на интерактивность bash сеанса делается так:
[[ $- = *i* ]] || return
Но никак не проверкой на пустоту $PS1. Однако почему $PS1 пуст? Смотрим выше в /etc/profile:
if [ "$PS1" ]; then
  if [ "$BASH" ] && [ "$BASH" != "/bin/sh" ]; then
	# The file bash.bashrc already sets the default PS1.
	# PS1='\h:\w\$ '
	if [ -f /etc/bash.bashrc ]; then
	  . /etc/bash.bashrc
	fi
  else
	if [ "`id -u`" -eq 0 ]; then
	  PS1='# '
	else
	  PS1='$ '
	fi
  fi
fi
if 
То есть не выставляем $PS1 для bash, т.к. он и так будет выставлен в его /etc/bash.bashrc. А теперь 
$ head /etc/bash.bashrc
# System-wide .bashrc file for interactive bash(1) shells.

# To enable the settings / commands in this file for login shells as well,
# this file has to be sourced in /etc/profile.

# If not running interactively, don't do anything
[ -z "$PS1" ] && return


Снова неправильная проверка на интерактивность и PS1 так и останется не задан, потому что он не задан >_<

Ну что, кто отправит багрепорт/патч?
Дебиан-дебиан, я думал о тебе лучше...