นามแฝงไม่“ แทนที่” รายการเส้นทางหรือไม่


9

บรรทัดสุดท้ายของฉัน.bash_profileคือ:

alias cp=/usr/local/bin/gcp

อย่างไรก็ตามที่ถูกแบนโดยรายการในของฉัน$PATH:

$which cp
/bin/cp
11:54:32/OCspark $type cp
cp is aliased to `/usr/local/bin/gcp'

ฉันคิดว่านามแฝงจะแทนที่PATH.. ?


1
สำหรับบันทึก: ในทางเทคนิคนามแฝงจะไม่แทนที่ค่าใด ๆ ในPATHenvar
can-ned_food

ข้อควรระวังที่บังคับใช้: โดยทั่วไปการเปลี่ยนชื่อคำสั่งทั่วไปไม่ใช่วิธีปฏิบัติที่ดี วิธีนี้สามารถกัดคุณได้สองวิธี 1) หากคุณทำงานในระบบอื่นและใช้คำสั่งตามนิสัยคุณจะได้รับพฤติกรรมที่ไม่คาดคิดของคำสั่งพื้นฐาน 2) หากใครก็ตามที่ใช้ระบบของคุณแม้จะให้คำแนะนำ / ช่วยคุณแก้ปัญหาพวกเขาก็จะได้รับพฤติกรรมที่ไม่คาดคิดจากการปรับแต่งของคุณ คำสั่งที่กำหนดเองนั้นใช้ได้ แต่อย่าตั้งชื่อพวกมันเหมือนกับคำสั่งทั่วไปที่มีอยู่
Joe

@ Joe จริงๆแล้วมันเป็นมากกว่าของแบบย้อนกลับที่นี่: ระบบปฏิบัติการ / x รุ่นCPขาดตัวเลือกจากระวังดังนั้นจึงไม่ประพฤติตามที่คาดไว้ (ยกเว้นให้กับผู้ที่ * เช่น hobbled รุ่น Mac)
javadba

คำตอบ:


21

whichคำสั่งส่งกลับเพียง executables: มันรู้อะไรเกี่ยวกับชื่อแทนเพราะมันเป็นโปรแกรมภายนอกและมีกลไกสำหรับการส่งผ่านข้อมูลไปยังนามแฝงกระบวนการเด็กไม่มี

หากคุณป้อนคำสั่งtype -a cpคุณจะเห็นการตีความที่เป็นไปได้ทั้งหมดตามลำดับที่ต้องการ ซึ่งรวมถึงนามแฝงใด ๆ เนื่องจากtypeเป็นbashคำสั่งภายใน

สิ่งสำคัญคือต้องตระหนักว่านามแฝงจะไม่ถูกตีความโดยกระบวนการย่อยเช่นสคริปต์หรือตัวแก้ไขเชิงโต้ตอบซึ่งมีตัวเลือกในการเรียกใช้คำสั่งระบบ

หากคุณสร้างcpฟังก์ชั่นเวอร์ชั่นของคุณจะทำงานในสคริปต์ แต่ไม่ใช่จากโปรแกรมอื่น:

cp() { /usr/local/bin/gcp "$@"; }

หากคุณต้องการcpทำงานทุกที่ให้เพิ่ม$HOME/binที่หัวPATHรายการแล้วชี้$HOME/bin/cpไปที่:

ln -s /usr/local/bin/gcp $HOME/bin/cp

สิ่งนี้ทำให้ลิงก์สัญลักษณ์แม้ว่าคุณสามารถทำให้เป็นฮาร์ดลิงก์ที่มีประสิทธิภาพมากกว่าเล็กน้อย (ละเว้น-s) แต่โดยปกติจะต้องได้รับอนุญาตรูท ( sudo ln ...) การสร้างฟังก์ชั่นและการเพิ่มPATHตัวแปรจะทำในหนึ่งในbashสคริปต์เริ่มต้นพร้อมสิทธิ์ผู้ใช้


1
แม้ว่า CentOS (และ AIUI ทั้งหมด RedHat) โปรไฟล์มาตรฐาน (ยกเว้นแทนที่) สร้างนามแฝงสำหรับการwhichทำงานที่/usr/bin/whichมีอินพุต pip จากการส่งออกของaliasและตัวเลือกที่บอกให้อ่านอินพุตนั้นและใช้เพื่อแสดงชื่อแทนถ้าตรงกับ คำสั่ง ดูunix.stackexchange.com/questions/10525/ …
dave_thompson_085

@ dave_thompson_085 - ความคิดเห็นที่น่าสนใจ: ฉันไม่ได้ใช้การกระจายเหล่านั้น ผมใช้ Ubuntu และฉันจะได้รับมากผลเช่นเดียวกันโดยเพียงแค่ aliasing เพื่อwhich typeจากนั้นwhich -aดำเนินการเช่นโปรแกรมภายนอกโดยเพิ่ม alias และนิยามฟังก์ชัน โดยทั่วไปแล้วฉันทำไม่ได้alias which=typeเพราะฉันชอบที่จะใช้$(which ProgName)เมื่อฉันต้องการบังคับให้ใช้โปรแกรมภายนอกโดยข้ามนามแฝงหรือนิยามฟังก์ชันใด ๆ
AFH

1
เชื่อมโยงอย่างหนักสามารถ filesystems ไม่ข้ามดังนั้นไม่ใช่สัญลักษณ์ข้อเสนอแนะจะทำงานเฉพาะในกรณีที่ไดเรกทอรีบ้านของคุณอยู่ในระบบแฟ้มเดียวกับln /usr/local/binมันจะทำงานผิดปกติหากคุณอัปเดตgcpเนื่องจากลิงก์ถาวรของคุณอาจยังอ้างอิงถึงเวอร์ชันเก่า
ไร้ประโยชน์

@ ไม่มีประโยชน์ - คะแนนที่ถูกต้องซึ่งเป็นส่วนหนึ่งของเหตุผลที่ฉันแก้ไขคำตอบของฉันเพื่อแนะนำลิงก์สัญลักษณ์ก่อนแม้ว่าฉันคิดว่าสิทธิ์อาจเป็นสิ่งที่สำคัญที่สุดในการพิจารณา สำหรับการอัปเดตgcpนั้นจะขึ้นอยู่กับว่าการอัปเดตนั้นกระทำโดยเปิดและเขียนหรือโดยการลบและสร้างใหม่อีกครั้ง โปรดทราบว่ามันไม่สำคัญว่าจะใช้พา ธ แหล่งที่มาแบบสัมบูรณ์หรือสัมพัทธ์เพื่อสร้างฮาร์ดลิงก์ในขณะที่ลิงก์สัญลักษณ์มักต้องการพา ธ สัมบูรณ์ ลิงค์ถูกใช้อย่างกว้างขวางในระบบปฏิบัติการและส่วนใหญ่เป็นสัญลักษณ์
AFH

1
@ can-ned_food - มันไม่ง่ายเหมือนการตั้งค่าในเชลล์ปัจจุบัน: มันจะต้องมีการตั้งค่าในแต่ละสคริปต์พร้อมกับการนำเข้านามแฝง
AFH

13

นามแฝงอยู่ภายในเชลล์ โปรแกรมอื่น ๆ จะไม่ทราบเกี่ยวกับพวกเขา

whichไม่ใช่ Bash builtin (มันเป็น builtin ในเชลล์อื่น ๆ เช่น zsh) เนื่องจากwhichไม่มีข้อมูลที่เป็นเอกสิทธิ์ในนามแฝงของ Bash whichเพียงแค่ค้นหาPATHคำที่กำหนด

typeในทางกลับกันคือ Bash builtin ดังนั้นจึงสามารถรายงานชื่อแทนได้


2
และนอกจากนี้ชื่อแทนจะถูกขยายถ้าคำแรกในคำสั่ง บางทีนั่นอาจไม่เกี่ยวข้อง
can-ned_food
โดยการใช้ไซต์ของเรา หมายความว่าคุณได้อ่านและทำความเข้าใจนโยบายคุกกี้และนโยบายความเป็นส่วนตัวของเราแล้ว
Licensed under cc by-sa 3.0 with attribution required.