มีวิธีที่สคริปต์ทุบตีจะรู้ว่ามันทำงานในเบื้องหน้าหรือพื้นหลังและเพื่อให้สามารถทำงานแตกต่างกันเล็กน้อยในแต่ละกรณี?
มีวิธีที่สคริปต์ทุบตีจะรู้ว่ามันทำงานในเบื้องหน้าหรือพื้นหลังและเพื่อให้สามารถทำงานแตกต่างกันเล็กน้อยในแต่ละกรณี?
คำตอบ:
การอ้างอิงman ps
:
Here are the different values that the s, stat and state output
specifiers (header "STAT" or "S") will display to describe the state of
a process.
...
+ is in the foreground process group
ดังนั้นคุณสามารถทำการตรวจสอบง่าย ๆ :
case $(ps -o stat= -p $$) in
*+*) echo "Running in foreground" ;;
*) echo "Running in background" ;;
esac
ดูไฟล์ /etc/bash.bashrc "
บรรทัดที่มี "$ PS1" จากนั้นทำ "man bash" แล้วมองหาโทเค็น PS1
[ -z "$PS1" ] && return
ออกจากสคริปต์ที่ไม่สามารถโต้ตอบได้
โซลูชันก่อนหน้าทั้งหมดเกี่ยวข้องกับกระบวนการวางไข่ ฯลฯ น่าเกลียดมากตั้งแต่นั้นเป็นต้นมา .bashrc
ถูกเรียกทุกครั้งที่มีการเปิดใช้งานเชลล์ bash shell ดังนั้นโซลูชันเหล่านั้นจึงสิ้นสุดการเปิดตัวกระบวนการ 1000 รายการ
ตัวทำความสะอาดส่วนใหญ่ถามถึง bash: bash มีตัวแปรที่กำหนดไว้ล่วงหน้า$-
ซึ่งมี "i" ถ้ามันทำงานในเชลล์แบบโต้ตอบ ตัวอย่างเช่นการใส่สิ่งนี้ลงใน. bashrc ของคุณนั้นสะอาดกว่าและราคาถูกกว่ามากและที่สำคัญที่สุดจะใช้ได้เสมอ!
case "$-" in
*i*) # interactive shell
;;
esac
ในขณะที่คุณอาจคิดว่าการตรวจสอบว่าเชลล์ทำงานในโหมดการโต้ตอบจะให้ผลเหมือนกัน แต่ในทางปฏิบัตินี่ไม่ใช่ แนวคิดมีลักษณะคล้ายกัน แต่แตกต่างกันจริง คุณสามารถเรียกใช้สคริปต์แบบโต้ตอบในอินพุตการป้อนพื้นหลังได้ด้วยหวังว่าจะได้ นอกจากนี้คุณสามารถเปิดใช้สคริปต์ของคุณด้วยการทุบตีกับ-l
อาร์กิวเมนต์ ดังนั้นเราจึงไม่สามารถพึ่งพาการโต้ตอบของ bash เพื่อตรวจสอบว่าสคริปต์ของเราทำงานในพื้นหลังหรือในเบื้องหน้า
คำตอบจาก devnull ถูกต้องจึง เพื่อตรวจสอบว่ากระบวนการทำงานในเบื้องหน้าหรือไม่ยูทิลิตี้ ps ตรวจสอบว่ากลุ่มกระบวนการ (pgrp) เหมือนกับรหัสกลุ่มกระบวนการที่เชื่อมโยงกับเทอร์มินัลการควบคุมของเซสชัน (tpgid)และเพิ่ม+
เครื่องหมายในเอาต์พุตตามกระบวนการ สถานะ.
เมื่อรู้ว่าเราสามารถทดสอบเวอร์ชันทุบตีได้อย่างแน่นอน:
#!/usr/bin/env bash
IFS=$' '
retval=($(</proc/$$/stat))
IFS=$' \t\n'
if [[ "${retval[3]}" == "${retval[7]}" ]]; then
echo "Background" > ./result.txt
else
echo "Foreground" > ./result.txt
fi
exit
ในรหัสข้างต้นเราจะแสดงผลลัพธ์ในไฟล์ข้อความเพราะ stdout
ไม่ได้เชื่อมต่อเมื่อกระบวนการทำงานในพื้นหลัง
โปรดทราบองค์ประกอบที่ 4 และ 8 ของตารางตามลำดับสอดคล้องกับpgrp
และtpgid
( ดูส่วน/ proc / [pid] / statของหน้า man - man 5 proc
)