سؤال متى يجب علي استخدام #! / bin / bash و #! / bin / sh؟


متى #!/bin/bash أكثر ملاءمة من #!/bin/sh في النصي قذيفة؟


97
2017-10-10 07:02


الأصل


عندما تستخدم bash وظائف وبناء الجملة بدلا من sh وظائف وبناء الجملة. - Mokubai♦
نرى stackoverflow.com/questions/5725296/... - SPRBRN
إذا كان يساعد أي شخص ، لقد لاحظت ذلك vim سوف تبرز bashإذا كان السيناريو الخاص بك لديه #!/bin/sh كوخ. أنا فقط تغييره إلى bash إذا أصبحت الأشياء مشعورة بما يكفي لبدء استخدام ميزات bash. - SeldomNeedy
SeldomNeedy بعض الأشياء التي يسلط الضوء عليها بشكل افتراضي تعمل بشكل جيد في أي قذيفة POSIX بالرغم من ذلك. $(...) هو بغيض للغاية. أيضا ، بعض منهم خفية [<(...) و cmd >& file لا تحصل على أي تسليط للخطأ ، على سبيل المثال ، فهي لا تحتوي على تمييز خاص لما تعنيه ، مع أو بدون g:is_bash] - Random832
@ Random832 يبدو أن هناك بعض النشاط في هذا الموضوع مؤخرًا vim's issue-tracker. - SeldomNeedy


الأجوبة:


بالمختصر:

  • هناك العديد من قذائف التي تنفذ مجموعة شاملة من مواصفات POSIX sh. على أنظمة مختلفة ، /bin/sh قد يكون رابطًا إلى الرماد و bash و dash و ksh و zsh و c. (سوف يكون دائما متوافق مع sh - على الرغم من csh أو الأسماك.)

  • ما دمت تتمسك بها sh ميزات فقط ، يمكنك (وربما ينبغي أن) استخدامها #!/bin/sh والسيناريو ينبغي أن تعمل بشكل جيد ، بغض النظر عن أي قذيفة هو.

  • إذا بدأت في استخدام الميزات الخاصة بباش (مثل المصفوفات) ، فيجب عليك طلب bash - على وجه التحديد ، /bin/sh يستدعي بالفعل باش ك النظام ، قد لا يعمل كل شخص آخر النظام ، ولن يتم تشغيل البرنامج النصي الخاص بك هناك. (ينطبق نفس الشيء على zsh و ksh.) يمكنك استخدامه shellcheck لتحديد bashisms.

  • حتى إذا كان البرنامج النصي مخصصًا للاستخدام الشخصي فقط ، فقد تلاحظ تغير بعض أنظمة التشغيل /bin/sh أثناء الترقيات - على سبيل المثال على ديبيان ، كان هذا هو "باش" ، ولكن تم استبداله لاحقًا بشرطة صغيرة جدًا. البرامج النصية التي تستخدم bashisms ولكن كان #!/bin/sh كسر فجأة.

ومع ذلك:

  • حتى في #!/bin/bash ليس صحيحا جدا. على أنظمة مختلفة ، قد باش في العيش /usr/bin أو /usr/pkg/bin أو /usr/local/bin.

  • خيار أكثر موثوقية هو #!/usr/bin/env bashوالذي يستخدم $ PATH. (على الرغم من أن env الأداة نفسها ليست مضمونة بدقة سواء ، /usr/bin/env لا يزال يعمل على أنظمة أكثر من /bin/bash هل.)


143
2017-10-10 14:03



إجابة لطيفة. هل تقصد أن تجعلها CW؟ - Mokubai♦
مجرد ملاحظة إذا تم تشغيل باش من /bin/sh ثم سيحاول تقليد sh ميزات (انظر صفحة رجل) ، غير متأكد من ميزات bash المحددة المتوفرة في هذا الوضع. env أداة هي أداة posix يجب أن يكون موجودا في معظم التوزيع ، ولكن أنا غير متأكد من ذلك لأن البعض قد لا يحترم posix. - Brice
لا ، في الواقع POSIX ينص على وجه التحديد لا يمكن أن يفترض أن يكون في /bin: "يجب أن تشير التطبيقات إلى أن PATH القياسي إلى shell لا يمكن افتراضه إما / bin / sh أو / usr / bin / sh ، ويجب أن يتم تحديده من خلال استجواب PATH الذي يتم إرجاعه بواسطة getconf PATH ، مما يضمن أن اسم المسار الذي تم إرجاعه هو مطلق اسم المسار وليس قذيفة مدمجة". انظر أيضا هذا السؤال وعلى وجه التحديد هذا الجواب. - terdon
حسنًا ، حسنًا ، يعني هذا أن POSIX لا يحدد طريقة محمولة لامتلاكها #! مخطوطات العمل؟ - grawity
POSIX sh ليس بورن: إنه مشتق من ksh المبكر أكثر من كونه سليل مباشر لبورن. من السهل تمييزها: echo foo ^ cat تنبعث foo ^ cat في POSIX sh ، وتصدر فقط foo في بورن (كما ^ هي حرف الأنبوب هناك). - Charles Duffy


استخدم shebang المطابق للصدفة التي استخدمتها بالفعل لتطوير وتصحيح البرنامج النصي الخاص بك. أي. إذا كانت shell تسجيل الدخول الخاص بك bash، وتشغيل البرنامج النصي الخاص بك كما قابل للتنفيذ في محطة الخاص بك ، واستخدام #!/bin/bash. لا تفترض فقط أنك لم تستخدم المصفوفات (أو أيا كان bash الميزة التي تعرفها) ، فأنت في أمان لاختيار أي قشرة تحلو لك. هناك العديد من الاختلافات الطفيفة بين القذائف (echo، وظائف ، حلقات ، سمها ما شئت) والتي لا يمكن اكتشافها دون اختبار مناسب.

فكر في هذا: إذا غادرت #!/bin/bash ولا يمتلك المستخدمون ذلك ، سيشاهدون رسالة خطأ واضحة ، شيء من هذا القبيل

Error: /bin/bash not found

يمكن لمعظم المستخدمين إصلاح هذا الأمر خلال دقيقة واحدة عن طريق تثبيت الحزمة المناسبة. من ناحية أخرى ، إذا قمت باستبدال shebang بها #!/bin/sh واختبارها على نظام حيث /bin/sh هو رابط ل /bin/bash، مستخدميك الذين ليس لديهم bash سيكون في ورطة. سترى على الأرجح رسالة خطأ مشفرة مثل:

Error in script.sh line 123: error parsing token xyz

قد يستغرق هذا عدة ساعات لإصلاحها ، ولن يكون هناك أي دليل حول نوع الصدفة التي كان يجب استخدامها.

لا توجد أسباب كثيرة وراء رغبتك في استخدام قشرة مختلفة في shebang. أحد الأسباب هو أن الصدفة التي استخدمتها غير منتشرة. واحد آخر هو الحصول على الأداء مع sh وهو أسرع بشكل ملحوظ على بعض الأنظمة ، وسيكون النص الخاص بك هو اختناق الأداء. في هذه الحالة ، اختبر النص البرمجي تمامًا مع الغلاف المستهدف ، ثم غيّر كلمة shebang.


18
2017-10-14 13:55



@ هستور لم أحصل على تعليقك. سيحدد shebang بالتأكيد أي نوع من القذائف سيتم استخدامه لتشغيل النص البرمجي ، هل تعتقد أن جوابي يعني خلاف ذلك؟ - Dmitry Grigoryev
انسى ذلك. أنا أساءت فهم الجزء "لماذا تريد استخدام"... - Hastur


يجب عليك فقط استخدام أي وقت مضى #! /bin/sh.

يجب عدم استخدام امتدادات bash (أو zsh ، أو fish ، أو ...) في برنامج نصي shell ، أبدًا.

يجب عليك فقط كتابة نصوص shell التي تعمل مع أي تنفيذ لغة القشرة (بما في ذلك جميع برامج "الأداة المساعدة" التي تترافق مع الغلاف نفسه). في هذه الأيام تستطيع المحتمل يأخذ POSIX.1-2001 (ليس -2008) كمسؤول عن ما تستطيعه المرافق والأدوات المساعدة ، ولكن يجب أن تدرك أنه قد تتم دعوتك في يوم من الأيام إلى نقل النص البرمجي إلى نظام قديم (مثل Solaris أو AIX) تم تجميد القوقعة والمرافق عام 1992.

ما ، على محمل الجد؟!

نعم بجد.

هذا هو الشيء: شل هو رهيب لغة برمجة. الشيء الوحيد الذي سارت عليه هو ذلك /bin/sh هو مترجم البرنامج النصي الوحيد والوحيد كل يضمن تثبيت Unix أن يكون.

وهنا الشيء الآخر: بعض التكرار من المترجم بيرل 5 الأساسية (/usr/bin/perl) هو أكثر من من المرجح أن تكون متاحة على تركيب يونكس تم اختيارها عشوائيا من (/(usr|opt)(/(local|sfw|pkg)?)?/bin/bash هو. لغات البرمجة الجيدة الأخرى (Python ، Ruby ، ​​node.js ، إلخ. - حتى أنني سأشمل PHP و Tcl في تلك الفئة عند المقارنة مع shell) تكون أيضًا متوفرة تقريبًا مثل bash والأصداف الممتدة الأخرى.

لذلك ، إذا كان لديك خيار كتابة برنامج نصي bash ، لديك خيار استخدام لغة برمجة ليست رهيبة ، بدلاً من ذلك.

الآن، بسيط مخطوطات shell ، النوع الذي يدير بعض البرامج في تسلسل من مهمة cron أو شيء ما ، لا يوجد شيء خاطئ في تركها كنصوص shell. لكن مخطوطات shell البسيطة لا تحتاج إلى صفائف أو وظائف أو [[ حتى في. ويجب أن تكتب فقط معقد مخطوطات shell عندما لا يكون لديك أي خيار آخر. البرامج النصية autoconf ، على سبيل المثال ، لا تزال مخطوطات shell بشكل صحيح. لكن يجب تشغيل هذه النصوص كل تجسد /bin/sh ذات الصلة بالبرنامج الذي يتم تهيئته. وهذا يعني أنه لا يمكنهم استخدام أي ملحقات. ربما لا يجب أن تهتم بملكية Unixes القديمة هذه الأيام ، ولكن ربما ينبغي الاهتمام بالمناطق المفتوحة المصدر الحالية ، والتي لا يتم تثبيت بعضها bash بشكل افتراضي ، والبيئات المضمنة التي تمنحك فقط الحد الأدنى من قذيفة و busybox.

في الختام ، في اللحظة التي تجد نفسك فيها يريد ميزة غير متوفرة في لغة shell المحمولة ، هذه علامة على أن البرنامج النصي أصبح معقدًا للغاية بحيث لا يبقى نصًا شيلًا. أعد كتابتها بلغة أفضل بدلاً من ذلك.


5
2017-10-11 06:30



عذرا ولكن هذا سخيف بعض الشيء. نعم ، إذا كنت تكتب شيئًا سيكون i) موزعًا و ii) إلى بيئات مختلفة ، فيجب أن تلتزم بالأمور الأساسية sh. هذا ، ومع ذلك ، هو بعيد كل البعد عن القول أنه يجب عليك أبدا استخدام قذائف أخرى. هناك الآلاف (ربما أكثر) من النصوص المكتوبة كل يوم ، والغالبية العظمى منها لن تعمل إلا على جهاز واحد. نصيحتك منطقية على رمز الإنتاج ، ولكن ليس لوظائف "sysdaminy" اليومية التي تتم كتابة معظم النصوص. إذا كنت على علم بأن البرنامج النصي الخاص بي لن يتم استخدامه إلا من قِبَلِي وعلى جهاز Linux ، فإن bash جيد. - terdon
terdon النقطة هي أنه إذا كان لديك خيار كتابة برنامج نصي bash ، فلديك أيضًا خيار كتابة نص برل (أو أيًا كان) ، وهذا هو دائما الخيار الأفضل. - zwol
terdon الجواب بالتأكيد ليس سخيفة ، تعليقك بدلاً من ذلك هو ببساطة ساذج. مخطوطات Shell رهيبة للتصحيح مقارنة بـ Perl و هكذا ، والتي يمكن للمرء بسهولة استخدام IDEs كاملة مع تصحيح الأخطاء الرسومية وجميع. بالإضافة إلى ذلك ، فإن معظم النصوص المكتوبة كل يوم لبعض الأشياء الصغيرة يجب أن يتم تغييرها وتغييرها من جديد ، وتنمو ، ويتم نسخها كأمثلة لزملائها أو الشبكة الخ. ليس هناك على الأرجح أي سبب لاتخاذ مثل هذا الخطر. - Thorsten Schöning
@ ThorstenSchöning قلت القليل سخيف. لو كان هذا يونيكس ولينكس او حتى Stack Overflow ربما أوافق إذا كنا نتحدث عن أفضل الممارسات العامة ، أو المبرمجين المحترفين ، فمن الأفضل التمسك بـ POSIX sh الأساسي. ومع ذلك ، هذا هو مستخدم سوبر، وهو موقع يستهدف المستخدمين النهائيين ويخبر الناس بعدم استخدام الباش أو zsh مطلقًا عند كتابة نصوص القوالب ، في رأيي ، بشكل متطرف. - terdon
إنه في الواقع أكثر من المهم ، في رأيي ، تثبيط المستخدمين النهائيين من كتابة البرامج النصية قذيفة معقدة. يمتلك المحترفون مستوى أعلى من المهارات في المتوسط ​​(وبالتالي يكونون أكثر قدرة على التعامل مع أخطار البرمجة النصية المعقدة) ، يجب أن يعرفوا بدقة ما هي البيئات التي يحتاجون إلى حملها ، ويتقاضون أجوراً لعدم الاستسلام في الإحباط. - zwol


بشكل عام إذا كان الوقت أكثر أهمية من الوظائف ، فستستخدم shell الأسرع. غالباً ما يتم استخدام sh في الاندفاع ويميل لاستخدامه في مهام cron الخاصة بالجذر أو عمليات الدُفعة حيث يتم حساب كل ثانية (نانو) ثانية.


3
2017-10-11 20:36



يمكن أن يؤدي تحميل مترجم شفوي إضافي من نظام الملفات إلى نفي مثل هذه الميزة ، وأي شيء تكون فيه النانوسيكند (التي تكون بنفس درجة حجم دورة الماكينة الفعلية) هو نطاق المبرمجين C ولغة التجميع. - rackandboneman
النانو ثانية فقط تحدث فرقا في وظائف cron إذا كان لديك المليارات منهم ، و cron لن تكون قادرة على التعامل مع الكثير على أي حال. - Dmitry Grigoryev
حتى إذا كان مبالغًا في mckenzm قليلاً ، فلا يمكن إنكار أن الحصول على أداء أفضل أفضل! لا تتعطل في الجزء "نانو". (لا تحسب النانوسيكند حتى في C إلا إذا كانت حلقة داخلية على نظام في الوقت الحقيقي أو هكذا!) - jpaugh
jpaugh ما لم تكن تعمل بنظام (قديم) يفترض أن عمليات معينة ستستغرق فترة زمنية محددة على الأقل. يحدث! - JAB


لتكون أكثر إيجازًا ، استخدم sh إذا كانت قابلية النقل عبر معظم الأنظمة أكثر أهمية و bash إذا كنت ترغب في استخدام بعض ميزاته المحددة ، مثل المصفوفات ، إذا كان إصدار باش يدعمها.


2
2017-11-24 18:41





  • sh (لمعظم الحالات) ، bash إذا كانت مطلوبة على وجه التحديد (أو ksh ، أو أيا كان)

الطريق الأسلم. عندما تكون مشفرة ، سيكون / usr / bin /shellOfChoice ولكن هناك اتفاقية جديدة أحاول استخدامها دائمًا الآن - مثل "المواقع الافتراضية" عبر تغيير PATH قد يتغير:

#! / usr / bin / env sh أو
 #! / usr / bin / env bash
أو على سبيل المثال ، perl scripts
 #! / usr / bin / env perl -w

وبالطبع ، عندما يكون لديك سبب لنص برمجي حتى لا تأخذ PATH جديدًا تلقائيًا ، فاستمر في جعله مشفرًا - ثم / usr / bin / يجب أن يكون هذا هو المسار الأكثر احتمالًا لاستخدامه.


1