ТЛ; др
В общем, вы не можете.
Википедия говорит, что для сценариев запуска / выключения POSIX (sh
)
Не указано (.profile
приведен в качестве примера)
И я не нашел даже этого примера в POSIX.1-2017.
На практике /etc/profile
и т.д. / профиль и ~/.profile
поставляются (по крайней мере , в Linux, с помощью нескольких sh
реализаций я работал с). В контексте вашего вопроса проблема заключается в том, что они получены только из логинов. Не каждая оболочка является оболочкой входа в систему. Не каждая интерактивная оболочка является оболочкой входа в систему.
Кроме того, единственная концепция оболочки входа в систему, похоже, не определена POSIX (кто-то поправит меня, если я ошибаюсь). Этот документ не определяет -l
как обязательную опцию sh
, хотя на практике многие реализации используют его для принудительного поведения оболочки входа в систему.
Даже если /etc/profile
был проанализирован родительским процессом (((… -)grand-)grand) вашей текущей не входящей в систему оболочки, вы никак не могли унаследовать определенные здесь псевдонимы, потому что псевдонимы не могут быть экспортированы; они не распространяются в среде, как экспортированные переменные. Функция вместо псевдонима вам тоже не поможет.
Мой вывод таков: в общем, вы не можете ожидать, что sh
автоматически получит любой файл. Чтобы сделать каждый источник sh
конкретным файлом, в котором определен ваш псевдоним, вам нужно найти (или написать) реализацию, которая делает это.
Пользователь может получить файл вручную . /path/to/file
.
Однако есть подход, который позволяет вам заставить ls
работать как ls -l
. Это можно сделать с помощью сценария-оболочки, который заменяет /bin/ls
и exec
-s на /bin/real_ls -l "$@"
(где real_ls
- это реальное имя ls
переименованное). Такой подход не редкость, сравните этот ответ . Есть недостатки и подводные камни, хотя.
- Если действительный
ls
является символической ссылкой на двоичный файл со швейцарским армейским ножом, такой как busybox
, двоичный файл будет сбит с толку, если он будет вызван именем real_ls
.
Этого легко избежать, используя /another/dir/ls
вместо real_ls
. Но даже тогда
- будущее обновление системы может перезаписать ваш пользовательский
/bin/ls
.
Теперь этого можно избежать, оставив реальные ls
виде /bin/ls
, поместив свои пользовательские ls
в /another/dir
и добавив /another/dir
в PATH
в качестве первой записи для всех пользователей (обычно это можно сделать через /etc/profile
). Но потом
- каждый скрипт, который использует
ls
и измененную PATH
(в отличие от /bin/ls
, полный путь) найдет ваш пользовательский ls
.
Это может иметь неприятные последствия. Если у вас есть псевдоним, сценарий (запущенный в подоболочке, а не из источника) не унаследует его. Скрипт может определить независимый псевдоним для себя, в любом случае ls
внутри скрипта не зависит ни от какого "внешнего" псевдонима; но это может легко зависеть от того, к чему разрешает исполняемый файл ls
. Изменение поведения ls
для каждого пользователя может немного расстроить его, хотя, надеюсь, он адаптируется в своих интерактивных оболочках. Но изменение поведения ls
для каждого существующего сценария является неправильным, особенно потому, что ls
определяется POSIX, и в определении явно указано, что его поведение должно зависеть от наличия опции -l
. Замена ls
вашими пользовательскими ls
где ls
и ls -l
эквивалентны, нарушит его соответствие POSIX.
Хорошо, ls
- не лучший пример, потому что в любом случае не следует анализировать его вывод. С другой стороны, вы никогда не знаете, каким образом пользователи (не) используют какой-либо инструмент.
Также обратите внимание, что возможно иметь реализацию sh
где ls
- встроенная функция. В этом случае искажение с /bin/ls
или / и PATH
не может переопределить то, что означает простой ls
; псевдоним или функция может.
Если вы хотите иметь "глобальный" псевдоним с другим именем, например,
alias ll='ls -l'
тогда переход на скрипт /bin/ll
выглядит для меня совершенно безопасным. ls
нетронутым, ничего не сломано. Сценарий может выглядеть так:
#!/bin/sh
exec ls -l "$@"