2011-12-06 64 views
0

我試圖捕獲正在運行的VNC會話。所以我使用如下將'ps -a -u user -F`的輸出分配給SHELL變量

STAT = `ps -a -u user -F | grep "Xvnc :" | grep -v grep` 

如果VNC會話正在運行,命令「ps -a -u user -F」的輸出是多行。然後STAT被分配所有行。我只是隻對一行感興趣,因爲我只想爲「用戶」運行VNC的所有SESSION NUMBER。我嘗試了下面的命令,使用「@」作爲我的分隔符(用「\ n」來分析STAT)。它似乎沒有工作

STAT = `ps -a -u user -F | grep "Xvnc :" | grep -v grep | tr -s "\n" "@" 

我只需要抓住VNC會話號碼。任何建議感激。

+1

請示出了樣品第一個命令的輸出以及它所需的輸出。 –

+0

通過「會話號碼」,你的意思是像「:2」「:3」之類的東西? (X顯示號碼?) – BRFennPocock

回答

1

如果你的ps版本支持它,你最好重新格式化它的輸出以便於解析。在我的系統上,我可以這樣做:

$ ps -o command= -C Xvnc 
Xvnc :1 

$ ps_output="$(ps -o command= -C Xvnc)" 

$ vnc_display="${ps_output#Xvnc :}" 

$ echo $vnc_display 
1 

當然這種方法有一些限制。它不會選擇特定的用戶,如果您使用Xnc的其他命令行選項,或者您有多個會話正在運行,它將不起作用。因此,相反,你可能想要做這樣的事情:

$ grep -z "^:" "/proc/$(pgrep -u user Xvnc)/cmdline" 
:1 

設置與命令替換參數,然後去除可能結腸,如果這就是你想要的。如果單個用戶正在運行多個VNC會話,這仍然不起作用。您必須改寫$(pgrep -u user Xvnc)的結果。如果你不關心漂亮解析輸出,因爲人是無論如何處理的結果,你總是可以只是這樣做:

$ ps $(pgrep -u user Xvnc) 
    PID TTY  STAT TIME COMMAND 
3600 pts/2 S  0:00 Xvnc :2 
3606 pts/2 S  0:00 Xvnc :3 

其工作原理是通過運行pgrep命令,這將會對搜索過程符合指定標準(在這種情況下,用戶名爲user,命令名稱爲Xvnc)。下面是它的輸出是什麼樣子:

$ pgrep -u user Xvnc 
3600 
3606 

Encosing這$()配合外殼的命令替換設備。這需要輸出一個命令並將其替換爲命令行的一部分。 (運行info "(bash)Command Substitution")瞭解更多信息)。當您運行ps $(pgrep -u user Xvnc),它使得shell將其解釋爲這樣:

$ ps 3600 3606 

這將產生相同的輸出。你可以看到什麼是bash做的,如果你使用set -x調試選項:

$ set -x 
$ ps $(pgrep -u user Xvnc) 
++ pgrep -u user Xvnc 
+ ps 3600 3606 
    PID TTY  STAT TIME COMMAND 
3600 pts/2 S  0:00 Xvnc :2 
3606 pts/2 S  0:00 Xvnc :3 
+0

*非常好,這將進入我的工具箱。 – BRFennPocock

+0

太棒了。我可以有一些解釋abt「ps $(pgrep -u用戶xvnc) – Mike

+0

當然,添加了額外的解釋 –

0

要處理的會話號列表:

$ for snumber in $(ps -a -u USERNAME -F | grep -o -P '[X]vnc :\d+' | awk -F':' '{ print $2 }'); do echo Session ${snumber}; done 
Session 2 
Session 1 
$ 

要具有會話號列表在一個變量:

LIST=$(ps -a -u USERNAME -F | grep -o -P '[X]vnc :\d+' | awk -F':' '{ print $2 }' | tr '\n' ' ' | sed 's; $;;') 
+0

好的答案。有點修改這一點,因爲我只對會話編號說感興趣8.修改上述命令如下 - ps -a -u cad -F | grep -o -P「Xvnc:\ d +」| grep「Xvnc:8」 - 我得到一個錯誤,說「grep沒有這樣的文件或目錄和Xvnc沒有這樣的文件或進入 – Mike

+0

@Mike :你顯然修改了它的錯誤:) – 2011-12-06 20:58:57

+0

grep所做的一切就是「輸出」匹配模式「Xvnc:\ d +」=> Xvnc後跟:至少一位數的字符串部分。什麼是MISTAKE將管道連接到'grep'以從N個Xvnc會話中尋找特定的「數字」? – Mike

0

如果你只是想X顯示數字(例如:1,:2),你可以嘗試:

STAT=`ps -a -u ${USER} -F | \ 
    perl -ne '$\=" ";if (/^.{64,}Xvnc.*?:([0-9]+)/){print $1}' 

這可能是深奧的條件下更安全,因爲它尋找Xvnc之前跳過ps輸出的第64列,而正則表達式是複雜的足以讓它無法與自己匹配。這將加載$STAT以X顯示ID的空格分隔列表,例如, 「2 4 6」或類似的,適合於在for n in $STAT; do echo "$USER is on :$n"; done

使用(斷開的:

$\=" ";  # print a space after every print command 
    if (/^  # start of line (matches the input line 
     .{64,} # at least 64 characters 
     Xvnc  # the bit you wanted 
     .*?  # any other spaces or parameters that might be around 
     :  # find a colon 
     (\d+) # find, and keep, at least one digit 
     /x)  # (the /x only so I can put comments into the regex here) 
    { print $1 } # print the digits that we found in() group 1 

perl -ne提出的自動while(<>){}環代替讀取輸入)

+0

感謝您的好解釋 – Mike