`ssh <host>` bir giriş kabuğu, ancak ssh <host> <komut> `değil mi?


12

ssh <host> <command>Sözdizimini kullanarak doğrudan bir SSH ana bilgisayarında bir komut çalıştırdığımda .bashrc, .bash_profile(veya .profile) çıktısını görüyorum ancak çıktısını görmedim .

Örneğin, aşağıdaki komutu her iki dosyanın üstüne yerleştirirsem,

echo ${BASH_SOURCE[0]}

ve el ile kaynak .bash_profile( .bashrcsırayla hangi kaynaklar ), göreceğim

$ . .bash_profile
.bash_profile
.bashrc

Bu, ssh <host>komutun biçimini kullanarak SSH aracılığıyla uzaktan bu bilgisayara oturum açıp açmadığımı gördüğüm çıktı . (Ve .bash_profilegeçici olarak başka bir yere koyarsam , bu çizgilerin hiçbiri yankılanmaz.)

Ancak, doğrudan uzak makinede ssh <host> <command>şeklinde bir komut yürütürsem ssh, çıktı şöyle görünür:

$ ssh <host> echo foo
/home/rlue/.bashrc
foo

Anladığım kadarıyla .bash_profileve arasındaki fark .bashrc, birincisinin giriş kabukları için , ikincisinin etkileşimli, girişsiz kabuklar için olmasıdır .

Aşağıdakileri tamamladım:

  1. ssh <host>Sadece kaynakları .bash_profileise,
  2. ssh <host> <command>sadece kaynaklar .bashrc, yani
  3. birincisi bir giriş kabuğu ve ikincisi değil.

Bu sonuçlar doğru mu? Neden ssh <host> <command>etkileşimli, giriş yapmayan bir kabuk olarak değerlendiriliyor? SSH komutu yürütmek için hala uzak makinede oturum açmıyor mu?


çıktı .bashrc? Bu dosyanın çıktı üretmesi gerekmez. 'Den herhangi bir çıktı .bashrc, taşıma olarak ssh kullanan tüm araçları kırabilir.
kasperd

Yeterince adil. Bu durumda, birkaç satır .bashrchata verirken, benzer satırlar hata .bash_profilevermedi. Sorun teşkil eden hatları düzeltmeden önce tutarsızlığı araştırma fırsatı buldum.
Ryan Lue

Yanıtlar:


12

OpenSSH (büyük olasılıkla çalıştırdığınız şey) bir oturum açma kabuğu oluşturulup oluşturulmayacağına karar verir ve bunu yalnızca belirli bir komut çalıştırmıyorsanız yapar. Gönderen man ssh:

 If command is specified, it is executed on the remote host instead of a
 login shell.

Bu nedenle, bir giriş kabuğu oluşturmak isteyip istemediğini ssh sunucusu için bir uygulama seçimi ve çalıştırmak için bir komut verirseniz, bunu yapmaz.

İken sshsisteme giriş yaptığında yapar bunu bir komut ve çıkış yürütmek yaşıyorsanız, gerçekten çok daha benzer bir giriş ortamını almak için olandan sadece bu komutu çalıştırmak için bir kabuk oluşturmak için bu. Görünüşe göre OpenSSH yazan insanlar ona bu tür bir görev gibi davranmaya karar verdiler.

Komutu yürütmek için etkileşimli olmayan, giriş yapmayan bir kabuk oluştururlar, çünkü bu, başka bir bağlamda / kabukta bir komut çalıştırma ruhudur. Bununla birlikte, normalde, etkileşimli olmayan mermiler otomatik olarak kaynak yapmaz ~/.bashrc, bu da burada açıkça gerçekleşir. bashaslında burada bize yardım etmeye çalışıyor. Gönderen docs

Uzak kabuk arka plan programı tarafından çağrıldı

Bash, uzak kabuk arka plan programı, genellikle rshd veya güvenli kabuk arka plan programı sshd tarafından yürütüldüğü gibi, bir ağ bağlantısına bağlı standart girişi ile ne zaman çalıştırılacağını belirlemeye çalışır. Bash bu şekilde çalıştırıldığını belirlerse, dosya varsa ve okunabilirse ~ / .bashrc'den komutları okur ve yürütür. Sh olarak çağrıldığında bunu yapmayacaktır. Bu davranışı engellemek için --norc seçeneği kullanılabilir ve --rcfile seçeneği başka bir dosyayı okunmaya zorlamak için kullanılabilir, ancak ne rshd ne de sshd genel olarak bu seçeneklerle kabuğu çağırmaz veya belirtmelerine izin vermez.


"... bir oturum açma kabuğu yerine uzak ana bilgisayarda yürütülür." Bu ikiliği anlamıyorum. Komut, bir oturum açma kabuğu yerine uzak ana bilgisayarda mı yürütülüyor veya komut, burada yürütülmekte olan bir oturum açma kabuğu yerine uzak ana bilgisayarda mı yürütülüyor? Eğer öncekiyse, / veya nasıl? (normalde değildir hem? ), hala bağlamında yürütüldüğünde ikinci ise bir kabuk, bir değil? (interaktif, giriş yapmayan bir soru?) Yani sorum da anlambilim hakkında - "giriş kabuğu" neyi ifade ediyor ve OpenSSH neden tek komutlar için bir tane oluşturmayacak şekilde tasarlanmalı?
Ryan Lue

Her marka belli görevleri daha kolay / daha güvenli / bir yaparken vb optimize kabukları farklı "tatlar" @RyanLue sshgiriş yapılmasını gerektirir, uygulayıcılar görünüşte bazı koşullarda, örneğin bir komut ve getiri çalıştırmak için onu soran karar verdi, bunu bir giriş kabuğunun attığı ek adımlara ihtiyaç duymaz / fayda sağlamaz ve bu yüzden bunu atlarlar. Gerçekten de çalışan bir kabuk var, çoğunlukla ortamı kurmayı varsayıyorum ve kabuk giriş yapan kullanıcıya sağlanmayacağından, kullanıcı bunu çalıştırmak için yeni bir kabuk başlatmış gibi davranıyorlar. komut
Eric Renouf

"Yani gerçekten çalışan bir kabuk var, çoğunlukla çevreyi kurmayı düşünüyorum ..." <Ama sadece bunu ssh <host> <command>denedim ve mevcut herhangi bir giriş kabuğunun ortamını devralmadığı anlaşılıyor . Örneğin $ ssh <host> \$PATH, yolu kaynak yapmadan olduğu gibi döndürür .bash_profile(veya .profileolduğu gibi) ... Pratik anlamda, neden bu adımı atlatmak istersiniz?
Ryan Lue

“... uygulayıcılar, görünüşe göre, bazı durumlarda, örneğin bir komutun yerine getirilmesini ve geri dönmesini istemek için, bir giriş kabuğunun attığı ekstra adımlara ihtiyaç duymadığından / faydalanmadığına karar verdiler ve bunu atladılar.” <Ayrıca, özellikle bu tasarım seçimine ilişkin açıklama / fikir edinmek. Benim tanımlamak PATHin .profile- tam tür bir şey, bir uzak ana keyfi bir komutu çalıştırmadan önce yüklenen istediğiniz ediyorum olmadığını?
Ryan Lue

1
@RyanLue the Boks ssh sunucusu ssh'nin farklı kullanımlarını ayırt eder ve her biri için izin verebilir. Uzaktan giriş, uzaktan çalıştırma, uzaktan kopyalama, Belki de bu, açıkladığınız davranışa neden sahip olduğunuzu anlamanıza yardımcı olur. Yüksek güvenlikli bir ortamda uzaktan oturum açma (etkileşimli kullanım) istenmeyebilir. Opensh, .bash_profile veya chroot içinde rbash / rksh ve 'logout' kullanılarak kısıtlanabilir.
bbaassssiiee

4

Neden : kabukları daha düşük seviyede bu davranış yalan ssh host( "giriş kabuğu" harf) bir kullanır uçbirimsiler arasında iletişim kurmak için uzak ana, sshdsunucu süreci ve kabuk; yerine ve ssh host commandarasında borular kullanır . Pseudoterminaller, bir kabuk veya bir komut dilinin " okuma-değerlendirme-yazdırma " modu gibi bir komut yorumlayıcısını etkileşimli olarak kullanmak için gereklidir ; Yazım hatalarının üzerinde geri adım atabilme gibi bir dizi insan dostu özellik uygularlar. Ancak daha fazla yükleri vardır ve (yapılandırmaya bağlı olarak) keyfi verilerin değiştirilmeden geçmesine izin vermez, bu nedenle SSH, etkileşim olmayacaksa bunları kullanmaktan kaçınır.sshdcommand

Bazen SSH'nin emri / hiç komut sezgiselliği bunu yanlış anlar; -tve -Tanahtarlarıyla geçersiz kılınabilir . Örneğin, uzaktaki bir makinede oturum açmak ve askıya alınmış bir screenoturumu hemen yeniden bağlamak için yapmanız gerekenler ssh -t host screen -R; bir terminale bağlı olmamasından şikayetçi ssh host screen -Rolur screen. Gerçekten kullanmak istediğiniz bir durum düşünemiyorum -T, ama bir tane bulursanız orada.


1

İlk önce farklı türleri görmeniz gerekir, bunu okuyabilirsiniz:

/unix/170493/login-non-login-and-interactive-non-interactive-shells

Şimdi bashrc'nizi açarsanız, başlangıçta şunu göreceksiniz:

# If not running interactively, don't do anything
[ -z "$PS1" ] && return

Bu, sisteme nasıl eriştiğinize bağlı olarak, bu dosyanın içindeki kodu yükleyip yüklemediği anlamına gelir.


Tamam, ama bu ilginç bir soru doğuruyor: .bashrcetkileşimli olmayan bir bağlamda çağrıldığında kaynaklanmayacak şekilde yazılabilir ( yani, “istem ifadesi” / $PS1değişkeni yoksa ). Ancak ssh <host> <command> kesinlikle etkileşimli değildir ; olduğunu, bu yok değil bir komut istemi yükseltmek. Öyleyse, OpenSSH neden .bashrcbu görünüşte giriş yapan, etkileşimli olmayan kullanım durumu için giriş yapmayan, etkileşimli bir bilgi istemi (kaynak yapmaya çalışan ) oluşturmak için tasarlandı ?
Ryan Lue
Sitemizi kullandığınızda şunları okuyup anladığınızı kabul etmiş olursunuz: Çerez Politikası ve Gizlilik Politikası.
Licensed under cc by-sa 3.0 with attribution required.