نوشته شده توسط فرشید نوتاش حقیقت.
در این آموزش یکی از بهترین ویژگیهای خط فرمان یعنی هدایت و تغییر مسیر I/O را خواهیم آموخت.
I/O Redirection مخفف عبارت Input Output Redirection به معنی هدایت ورودی خروجی میباشد و با استفاده از خواهید شد این امکان، میتوان ورودی و خروجی فرمانهای لینوکس را به فایلها و از فایلها هدایت نمود و همچنین چندین فرمان قدرتمند ترکیبی ایجاد کرد. به منظور فراگیری این قابلیت در این بخش با فرمانهای cat، sort، uniq، wc، grep، head و tail آشنا خواهید شد.
خروجی و ورودی استاندارد و خطا
بسیاری از برنامههایی که استفاده میکنیم برخی از انواع خروجیها را ایجاد میکنند. این خروجی اغلب شامل دو نوع است. اول نتایج برنامه را داریم یعنی دادهای که برنامه برای ایجاد آن طراحی شده است. دوم وضعیت و پیامهای خطا را داریم که وضعیت فعلی برنامه را به ما گزارش میکند. اگر فرمانی مانند ls را بررسی کنیم، میبینیم که این فرمان نتایج و پیامهای خطا را بر روی صفحه نمایش میدهد.
اگر این ایده که در لینوکس همه چیز فایل است را به یاد بیاوریم میبینیم که برنامههایی مثل ls نتایج خود را به درون یک فایل خاص با نام Standard Output (خروجی استاندارد) میفرستد و همچنین پیامهای خطا را به درون یک فایل خاص تحت عنوان Standard Error (خطای استاندارد) میفرستند. به صورت پیشفرض هر دوی این فایلها به جای ذخیرهسازی بر روی دیسک به صفحه نمایش لینک میشوند.
بهعلاوه بسیاری از برنامهها، ورودی خود را از تسهیلاتی به نام Standard Input (ورودی استاندارد) میگیرند. I/O Redirection ما را قادر میسازد تا مسیری که خروجی به آن میرود و یا مسیری که ورودی از آن میآید را تغییر دهیم. بهصورت عادی خروجی به صفحهنمایش هدایت میشود و ورودی از صفحهکلید میآید ولی با استفاده از I/O Redirection میتوان این حالت پیشفرض را تغییر داد.
تغییر مسیر (Redirection) خروجی استاندارد
I/O Redirection به ما اجازه میدهد تا مسیری که خروجی میرود را دوباره تعریف کنیم. بهمنظور تغییر جهت و هدایت خروجی استاندارد به یک فایل دیگر به جای هدایت به صفحهنمایش ما از عملگر هدایت یعنی < استفاده شده و در ادامه آن نام فایل را ذکر میکنیم. برای مثال ما میتوانیم به خط فرمان بگوییم که خروجی فرمان ls را به جای آن که آن را در صفحه نمایش نشان دهد به فایل ls-output.txt بفرستد.
در اینجا ما یک لیست بلند از دایرکتوری /usr/bin ایجاد نموده و نتایج را به فایل ls-output.txt فرستادیم. در ادامه خروجی فرمان را آزمایش میکنیم:
اگر محتوای فایل را با فرمان less بررسی کنیم، خواهیم دید که فایل ls-output.txt در واقع حاوی نتایجی از فرمان ls میباشد.
در ادامه آزمون هدایت را این بار با کمی پیچیدگی انجام میدهیم. نام دایرکتوری را به چیزی که وجود ندارد تغییر میدهیم:
یک پیام خطا دریافت نمودیم. این امری کاملاً طبیعی است چرا که دایرکتوری را که وجود ندارد را به آن تخصیص دادهایم. ولی چرا پیام خطا به جای اینکه در فایل ls-output.txt ذخیره گردد بر روی صفحه نمایش نشان داده شد؟ پاسخ این است که برنامه ls پیامهای خطا را به یک خروجی استاندارد ارسال نمیکند و از آن جایی که فقط خروجی استاندارد Standard Output را هدایت کردیم نه Standard Error. در نتیجه هنوز پیامهای خطا در صفحهنمایش نشان داده میشوند. در آموزشهای بعدی نحوه هدایت فایل Standard Error را نمایش خواهیم داد ولی قبل از مجدداً نگاهی دوباره به فایل خروجی خود خواهیم انداخت. با فرمان زیر اطلاعات کامل فایل، نمایش داده خواهد شد.
این فایل اکنون اندازه و حجم آن صفر است. به دلیل این که وقتی ما با استفاده از عملگر > هدایت خروجی را انجام میدهیم، فایل مقصد همیشه از اول شروع به نوشتن میکند. از آن جایی که فرمان ls ما هیچ نتیجهای ایجاد نکرده و فقط یک پیام خطا نمایش داده، عملیات هدایت شروع به نوشتن فایل از اول کرده و سپس به دلیل خطا، نتایج ثبت شده حذف شدند. در واقع هر وقت بخواهیم نتایج فایل را حذف کنیم میتوانیم از چنین ترفندی استفاده کنیم:
بهسادگی با بهکار بردن عملگر هدایت بدون هیچ فرمانی نتایج فایل را حذف میکنیم و یک فایل جدید خالی ایجاد میکنیم. برای آنکه نتایج حذف نشوند بایستی از عملگر >> برای (Redirection) استفاده کنیم. به مثال زیر توجه کنید:
با این کار ما نتیجه فرمان را سه بار تکرار کردیم که در نتیجه اندازه فایل سه برابر افزایش مییابد.
تغییر مسیر (Redirection) خطای استاندارد
هدایت و تغییر مسیر خطاهای استاندارد فاقد یک عملگر اختصاصی هدایت میباشد. بهمنظور هدایت خطاهای استاندارد بایستی به توصیفگر فایل (file descriptor) مراجعه کرد. یک برنامه میتواند خروجی را بر روی هر جریان شمارهگذاری شده فایل، ایجاد کند.
زمانی که ما به سه مورد اول این جریانهای فایل به عنوان ورودی، خروجی و خطای استاندارد نگاه کنید. شل (Shell) آنها را با توصیفگرهای فایل ۰، ۱ و ۲ اشاره میکند. شل علامتگذاری برای هدایت فایلها با استفاده از شماره توصیفگر فراهم میکند. خوب از آنجایی که خطای استاندارد همان فایل توصیفگر شماره ۲ است، میتوان خطای استاندارد را با این علامت انجام داد:
شماره توصیفگر بلافاصله پیش از عملگر هدایت یعنی > قرار میگیرد تا عملیات هدایت خطای استاندارد به فایل ls-error.txt صورت پذیرد.
هدایت خروجی استاندارد و خطای استاندارد به داخل یک فایل
در برخی مواقع نیاز میشود همه خروجی فرمانها را به داخل یک فایل مجزا بریزیم. برای انجام این کار بایستی هم خطای استاندارد و هم خروجی استاندارد را به صورت همزمان هدایت (Redirect) کرد. به این منظور دو روش وجود دارد. روش اول روش رسمی است که بر روی نسخههای قدیمی شل (Shell) هم کار میکند:
با استفاده از این متد، به صورت همرمان دو Redirect را انجام دادیم. اول خروجی استاندارد را به داخل فایل ls-output.txt ریختیم و سپس توصیفگر شماره ۲ یعنی همان خطای استاندارد را به توصیفگر شماره ۱ یعنی خروجی استاندارد هدایت کردیم. در این شیوه هدایت خطای استاندارد بایستی همیشه پس از هدایت خروجی استاندارد صورت پذیرد در غیر این صورت کار نخواهد کرد.
نسخههای اخیر بش (bash) یک شیوه سادهتری برای انجام این ترکیب میباشد:
در این مثال ما با استفاده از علامت &> خطای استاندارد و خروجی استاندارد را بهصورت همزمان به داخل فایل ls-output.txt منتقل کردیم.
جلوگیری از خروجی ناخواسته
بعضی مواقع سکوت واقعاً لذتبخش است و ما از خط فرمان خروجی نمیخواهیم. فقط میخواهیم فرمان را اجرا کرده و از خروجی جلوگیری کنیم. این موضوع بهپروژه برای پیامهای خطا و پیامهای وضعیت کاربرد خوبی دارد. سیستم یک شیوه برای انجام این کار فراهم آورده است. با هدایت خروجی به یک فایل با نام /dev/null این کار انجام میگیرد. برای سرکوب پیامهای خطا از یک فرمان میتوان این کار را به شیوه زیر انجام داد:
هدایت ورودی استاندارد
تا به اینجا هنوز با فرمانی که از ورودی استاندارد استفاده کند، مواجه نشدهایم. به همین منظور برای توضیح هدایت ورودی استاندارد فرمانی را توضیح خواهیم داد.
فرمان cat الحاق فایلها در لینوکس
فرمان cat که از کلمه لاتین Concatenate به معنی الحاق و به هم پیوستن گرفته شده یک یا چند فایل را میخواند و سپس آنها را به یک خروجی استاندارد کپی میکند و به این صورت به کار گرفته میشود:
cat [file...]
میتوان از فرمان cat به منظور نمایش فایلها بدون صفحهبندی استفاده کنید. برای مثال:
این فرمان محتوای فایل ls-output.txt را نشان میدهد. Cat اغلب به منظور نمایش متنهای کوتاه از فایلها به کار میرود. از آنجایی که cat میتواند بیش از یک فایل را بهعنوان آرگومان قبول کند، از آن میتوان بهمنظور اتصال فایلها به یکدیگر نیز استفاده کرد.
فرض کنید که فیلی عظیم را دانلود کردهاید. این فایل به بخشهای کوچکتر تقسیم شده است (فایلهای تصویری موجود در شبکه یوزنت معمولاً به این شیوه به اشتراک گذاشته میشوند) حال میخواهیم این بخشهای کوچک را به هم متصل کنید تا فایل اصلی به حالت اولیه خود برگردد. اگر مثلاً فایلها به این صورت نامگذاری شده باشند:
movie.mpeg.001 movie.mpeg.002 ... movie.mpeg.099
میتوان آنها را با استفاده از فرمان زیر به هم متصل کرد:
با توجه به اینکه Wildcardها همواره به ترتیب بسط پیدا میکنند در نتیجه این آرگومان فایلها را به ترتیب صحیح به هم متصل خواهد کرد.
حال اگر فرمان cat را بدون هیچ آرگومانی وارد کنیم چه اتفاقی خواهد افتاد؟
به نظر میرسد که هیچ اتفاقی نمیافتد ولی در حقیقت به حالت معلق باقی میماند تا ما فرمانی وارد کنیم. فرمان cat شروع به خواندن ورودیهای استاندارد از ابتدا میکند و از آنجایی که ورودیهای استاندارد بهصورت پیشفرض به صفحهکلید متصل شدهاند، پس فرمان cat منتظر میماند تا چیزی تایپ کنیم. متن زیر را وارد کنید:
سپس Ctrl+D را فشرده تا به cat بفهمانید که به آخر فایل در یک ورودی استاندارد رسیدهایم.
در نبود آرگومانهای نام فایل فرمان cat ورودی استاندارد را دریافت و به خروجی استاندارد که همان صفحهنمایش است نشان میدهد. پس ما به این صورت میبینیم که خط تایپ شده تکرار شد.
از این رفتار میتوان به منظور ایجاد فایلهای متنی کوتاه استفاده نمود. مثلاً میخواهیم یک فایل با نام lazy_dog.txt که حاوی متن تایپ شده است ایجاد کنیم. بایستی فرمان را به این شیوه تایپ کنیم:
پس از وارد کردن فرمان فوق، متن مورد نظر خود را تایپ میکنیم. در آخر با فشردن Ctrl+D فایل به پایان میرسد. برای نمایش نتایج وارد شده در فایل خود میتوانیم باز هم از فرمان cat به منظور نمایش استفاده کنیم:
خوب حال میدانیم فرمان cat ورودیهای استاندارد را قبول میکند:
یادآور میشویم که برای خروجی استاندارد از عملگر < استفاده میکردیم. حال برای ورودی استاندارد از عملگر > استفاده میکنیم. با استفاده از این عملگر و فرمان بالا منبع ورودی استاندارد را از صفحهکلید به فایل lazy_dog.txt تغییر دادیم. این کار خیلی کاربردی نیست ولی مفهوم را میرساند. یعنی این بار از یک فایل به عنوان منبع ورودی استاندارد استفاده میکنیم. فرمانهای دیگر استفاده بهتری از ورودی استاندارد خواهند داشت. به این منظور به صفحات manual مراجعه نمایید.
منبع: کتاب The Linux Command Line نوشته William E. Shotts
نوشته آموزش خط فرمان: قسمت هفتم، هدایت و تغییر مسیر اولین بار در لینوکس سیزن پدیدار شد.