Встановити та зняти - Чому два?


72

setі shoptобидва вбудовані оболонки, які керують різними варіантами. Я часто забуваю, які параметри встановлюються якою командою та які параметри встановлює / знімає ( set -o/+o, shopt -s/-u). Чому існують дві різні команди, які, здається, роблять те саме (і мають різні аргументи для цього)? Чи є який-небудь простий спосіб / мнемонічний запам'ятати, які варіанти йдуть з якою командою?


6
Спробуйте переглянути другий рядок help setі help shoptпереконатися, що навіть їхні автори думають, що вони роблять те саме.
l0b0

2
"Змінити значення атрибутів оболонки" проти "Змінити налаштування кожного параметра оболонки".
Кевін

2
У Bash 4.1.5 (1) -випустіть написано "Встановити або зняти значення параметрів оболонки та позиційних параметрів". та "Встановити та скасувати параметри оболонки." відповідно.
l0b0

Написання вказівок дає змогу зрозуміти те, що ви не знаєте, і змушує спробувати сформулювати речі таким чином, щоб ви не помилялися щодо того, про що ви намагаєтеся писати.
sjas

Відповіді:


40

Наскільки я знаю, set -oваріанти - це ті, які успадковуються від інших оболонок у стилі Борна (переважно ksh), а shoptваріанти - ті, які є специфічними для bash. Я не знаю жодної логіки.


1
Будь-яка документація, що показує shopt, успадковується?
Феліпе Альварес

8
Ну, є set -oваріанти, як posix/ physical/ interactive-commentsяких немає ksh, і shoptтакі, які є в інших оболонках, в тому числі kshдля деяких подібних login_shell/ nullglob. Як ви кажете, логіки немає. Це, мабуть, була ідея на початку (що SHELLOPTS будуть стандартними, а BASHOPTS - специфічними для башти), але це загубилося по дорозі, і тепер це просто закінчується дратує і фіаско дизайну інтерфейсу.
Стефан Шазелас

22

Різниця полягає в змінній змінній середовища, що використовується bash. Налаштування з setкомандою призводить до $SHELLOPTS. Налаштування з shoptкомандою призводить до $BASHOPTS.


9
Тьфу! Це ще більше заплутано. Мій мозок хоче асоціюватися shoptз $ SH ELL OPT S, а не з $ BA SHOPT S.
Бруно Броноскі


8

Легко, але втрачено в історії. setКоманда спочатку була використана для зміни середовища командного рядка вихідних Unix оболонок /bin/sh. Потім, коли розвивалися різні версії Unix, і додавались нові аромати оболонки, люди зрозуміли, що їм потрібно змінити більше (навколишнє середовище) речей, щоб зберегти сценарій оболонки сумісним. У той час Bash отримав дуже популярний і додаткові ш ELL неавтоматичні були потрібні іони, введення shopt.

Насправді ви можете побачити ці спроби сумісності у shoptкоманді.

$ shopt
autocd          off
cdable_vars     off
cdspell         off
checkhash       off
checkjobs       off
checkwinsize    off
cmdhist         on
compat31        off
compat32        off
compat40        off
compat41        off
compat42        off
complete_fullquote      on
direxpand       off
dirspell        off
dotglob         off
execfail        off
expand_aliases  on
extdebug        off
extglob         off
extquote        on
failglob        off
force_fignore   on
globstar        off
globasciiranges off
gnu_errfmt      off
histappend      on
histreedit      off
histverify      off
hostcomplete    on
huponexit       off
interactive_comments    on
lastpipe        off
lithist         off
login_shell     on
mailwarn        off
no_empty_cmd_completion off
nocaseglob      on
nocasematch     off
nullglob        off
progcomp        on
promptvars      on
restricted_shell        off
shift_verbose   off
sourcepath      on
xpg_echo        off

Але не в setкоманді.

$ set -o
allexport       off
braceexpand     on
emacs           on
errexit         off
errtrace        off
functrace       off
hashall         on
histexpand      on
history         on
igncr           off
ignoreeof       off
interactive-comments    on
keyword         off
monitor         on
noclobber       off
noexec          off
noglob          off
nolog           off
notify          off
nounset         off
onecmd          off
physical        off
pipefail        off
posix           off
privileged      off
verbose         off
vi              off
xtrace          off

2
setяк спосіб встановити параметри не було в оригінальних оболонках Unix, він був введений оболонкою Борна в кінці 70-х. set -o nameСам пізніше був доданий оболонкою Корна, вказаною, але необов'язковою в POSIX, як і раніше не підтримується "сучасними" версіями оболонки Борна, як /bin/shSolaris 10.
Stéphane Chazelas

5

З книги "Сценарії оболонок Linux з Bash", стор. 63:

Історично склалося, що setкоманда була використана для включення опції включення і виключення. Зі збільшенням кількості варіантів їх setстало складніше використовувати, оскільки варіанти представлені однобуквеними кодами. Як результат, Bash надає команду shopt( shell option ), щоб увімкнути та вимкнути параметри назви замість літери. Ви можете встановити певні параметри лише листом. Інші доступні лише під shoptкомандою. Це робить пошук та встановлення певного варіанту заплутаною задачею.


3

Схоже, що "встановити" параметри успадковуються підпакетами, а знімки - ні.


Гарний улов. Цікаво, чи це навмисний вибір чи побічний ефект.
Кевін

2
@ User29778 Принаймні , під Баш 4.1.5 (1) параметри , встановлені з setне успадковуються subshells.Both setі shoptваріанти не успадковуються подоболочек.
Мартін

Чи можете ви вказати на документацію, яка описує характеристики успадкування як setі shopt?
Феліпе Альварес

9
Обидва set -oі shoptопції успадковуються подоболочкі ( (...), $(...), деталі трубопроводів). Будь вони успадковані іншими bashвикликами , залежить від того , SHELLOPTSчи BASHOPTSзнаходяться в навколишньому середовищі чи ні.
Стефан Шазелас

0

setпоходить з оболонки бурна (sh) і є частиною стандарту POSIX, shoptоднак це не так і є специфічним для оболонки (bash):

0 sjas@ssg 14:31:45 ~  
set | grep -e SHELLOPTS -e BASHOPTS
BASHOPTS=checkwinsize:cmdhist:complete_fullquote:dotglob:expand_aliases:extglob:extquote:force_fignore:histappend:interactive_comments:progcomp:promptvars:sourcepath
SHELLOPTS=braceexpand:emacs:hashall:histexpand:history:interactive-comments:monitor

0 sjas@ssg 14:31:51 ~  
shopt | column -t | grep -v off
checkwinsize             on
cmdhist                  on
complete_fullquote       on
dotglob                  on
expand_aliases           on
extglob                  on
extquote                 on
force_fignore            on
histappend               on
interactive_comments     on
progcomp                 on
promptvars               on
sourcepath               on

0 sjas@ssg 14:31:57 ~  
set -o | column -t | grep -v off
braceexpand           on
emacs                 on
hashall               on
histexpand            on
history               on
interactive-comments  on
monitor               on

0 sjas@ssg 14:37:41 ~ 
sh 

$ set -o
Current option settings
errexit         off
noglob          off
ignoreeof       off
interactive     on
monitor         on
noexec          off
stdin           on
xtrace          off
verbose         off
vi              off
emacs           off
noclobber       off
allexport       off
notify          off
nounset         off
priv            off
nolog           off
debug           off

$ shopt
sh: 3: shopt: not found

$ 
Використовуючи наш веб-сайт, ви визнаєте, що прочитали та зрозуміли наші Політику щодо файлів cookie та Політику конфіденційності.
Licensed under cc by-sa 3.0 with attribution required.