आउटपुट फ़ाइल सामग्री जब वे बदलते हैं


47

मैं फ़ाइल की सामग्री को आउटपुट करना चाहता हूं जब वे बदलते हैं, उदाहरण के लिए यदि मेरे पास फ़ाइल है foobarऔर मैं करता हूं:

magic_command foobar

वर्तमान टर्मिनल को फ़ाइल की सामग्री प्रदर्शित करनी चाहिए और तब तक प्रतीक्षा करनी चाहिए , जब तक मुझे पता नहीं हो, मैं ^ C दबाता हूं।

अगर दूसरे टर्मिनल से मैं करूँ तो:

echo asdf >> foobar

पहले टर्मिनल को मूल फ़ाइल सामग्री (निश्चित रूप से, यह देखते हुए कि मुझे ^ C नहीं दबाया गया था) के अलावा नई गयी लाइन को प्रदर्शित करना चाहिए।

मैं इसे होमवर्क के रूप में चिह्नित करूंगा क्योंकि मैं लिनक्स को जानना और सीखना चाहता हूं, लेकिन यह होमवर्क नहीं है, यह सिर्फ मेरी उत्सुकता है।


जवाबों:


79

आप के tail commandसाथ उपयोग कर सकते हैं -f :

tail -f /var/log/syslog 

यह रियल टाइम शो के लिए अच्छा समाधान है।


आप एक स्क्रिप्ट लिख सकते हैं और अपने स्क्रिप्ट पर अपना आउटपुट रीडायरेक्ट कर सकते हैं।
फ़ारसीगुल्फ़

6
आप -F(कैपिटल एफ) का भी उपयोग कर सकते हैं , जो फ़ाइल को फिर से खोल देगा यदि वह हटा दिया जाता है और रास्ते में फिर से बनाया जाता है।
पेट्रफ

19

यदि आप एक छोटी फ़ाइल दिखाना चाहते हैं, जो एक टर्मिनल स्क्रीन पर फिट होती है, और जो बदल रही है वह संभवतः पूरी फ़ाइल है, तो आप इसका उपयोग कर सकते हैं watch:

watch cat example.txt

Every 2.0s: cat example.txt                                Sun Aug  3 15:25:20 2014

Some text
another line

यह डिफ़ॉल्ट रूप से प्रत्येक 2 सेकंड में पूरी फाइल दिखाता है, जिसमें एक वैकल्पिक हेडर भी शामिल है:

विकल्प -d( --differences) आउटपुट के पिछले संस्करण से या पहले संस्करण से परिवर्तनों को उजागर करेगा।


9

जब मुझे फ़ाइल परिवर्तनों का पता लगाने की आवश्यकता होती है और जो कुछ tail -f filenameकरता है उसके अलावा कुछ और करता है, तो मैंने inotifywaitस्क्रिप्ट का उपयोग परिवर्तन का पता लगाने और उस पर कार्य करने के लिए किया है। उपयोग का एक उदाहरण नीचे दिखाया गया है। देखें man inotifywaitअन्य घटना नाम और स्विच के लिए। inotify-toolsउदाहरण के लिए, आपको पैकेज को स्थापित करने की आवश्यकता हो सकती है sudo apt-get install inotify-tools

यहाँ उदाहरण स्क्रिप्ट कहा जाता है exec-on-change:

 #!/bin/sh

# Detect when file named by param $1 changes.
# When it changes, do command specified by other params.

F=$1
shift
P="$*"

# Result of inotifywait is put in S so it doesn't echo
while  S=$(inotifywait -eMODIFY $F 2>/dev/null)
do
  # Remove printf if timestamps not wanted 
  printf "At %s: \n" "$(date)"
  $P
done

दो कंसोल में मैंने निम्नानुसार कमांड दर्ज की (जहाँ A> का अर्थ कंसोल A में प्रविष्टि है, और B> का अर्थ कंसोल B में प्रविष्टि है)

A> rm t; touch t
B> ./exec-on-change t wc t
A> date >>t
A> date -R >>t
A> date -Ru >>t
A> cat t; rm t

cat tकंसोल A में से निम्न आउटपुट दिखाई दिया:

Thu Aug 16 11:57:01 MDT 2012
Thu, 16 Aug 2012 11:57:04 -0600
Thu, 16 Aug 2012 17:57:07 +0000

exec-on-changeकंसोल बी में दिखाई देने वाले निम्न आउटपुट :

At Thu Aug 16 11:57:01 MDT 2012: 
 1  6 29 t
At Thu Aug 16 11:57:04 MDT 2012: 
 2 12 61 t
At Thu Aug 16 11:57:07 MDT 2012: 
 3 18 93 t

exec-on-changeस्क्रिप्ट समाप्त जब मैं rm'घ t


8

lessइसके समान एक अनुसरण मोड है tail -f- Fजब आप इसे खोलते हैं तो बस हिट करें ।


4

मेरे पास तीन समाधान हैं:

1) tail -f एक अच्छा विचार है

2) हमें भी tailfउपयोग करना है

3) तीसरा एक बैश स्क्रिप्ट है:

#!/bin/bash

GAP=10     #How long to wait
LOGFILE=$1 #File to log to

if [ "$#" -ne "1" ]; then
    echo "USAGE: `basename $0` <file with absolute path>"
    exit 1
fi


#Get current long of the file
len=`wc -l $LOGFILE | awk '{ print $1 }'`
echo "Current size is $len lines."

while :
do
    if [ -N $LOGFILE ]; then
        echo "`date`: New Entries in $LOGFILE: "
        newlen=`wc -l $LOGFILE | awk ' { print $1 }'`
        newlines=`expr $newlen - $len`
        tail -$newlines $LOGFILE
        len=$newlen
    fi
sleep $GAP
done
exit 0
हमारी साइट का प्रयोग करके, आप स्वीकार करते हैं कि आपने हमारी Cookie Policy और निजता नीति को पढ़ और समझा लिया है।
Licensed under cc by-sa 3.0 with attribution required.