在.bashrc中回显时,SCP不起作用?


80

我在Fedora中有两个用户:

  1. 瓦尼
  2. 根(非常明显!)

我的Wani用户的.bashrc内容是:

# .bashrc
echo "Hello"
# Source global definitions
if [ -f /etc/bashrc ]; then
    . /etc/bashrc
fi

# User specific aliases and functions

现在,登录到root用户后,键入以下命令:

[root@Dell Wani]# touch try.txt
[root@Dell Wani]# service sshd start
[root@Dell Wani]# scp try.txt Wani@localhost:~/
Wani@localhost's password: 
Hello
[root@Dell Wani]# 

现在,我登录Wani,然后键入:

[Wani@Dell ~]$ cat try.txt
cat: try.txt: No such file or directory
[Wani@Dell ~]$ 

现在,我再次登录到root并使用以下命令键入相同的命令-v

[root@Dell Wani]# scp -v morph.log Wani@localhost:
Executing: program /usr/bin/ssh host localhost, user Wani, command scp -v -t -- .
OpenSSH_5.6p1, OpenSSL 1.0.0j-fips 10 May 2012
debug1: Reading configuration data /etc/ssh/ssh_config
debug1: Applying options for *
debug1: Connecting to localhost [127.0.0.1] port 22.
debug1: Connection established.
debug1: permanently_set_uid: 0/0
debug1: identity file /root/.ssh/id_rsa type -1
debug1: identity file /root/.ssh/id_rsa-cert type -1
debug1: identity file /root/.ssh/id_dsa type -1
debug1: identity file /root/.ssh/id_dsa-cert type -1
debug1: Remote protocol version 2.0, remote software version OpenSSH_5.6
debug1: match: OpenSSH_5.6 pat OpenSSH*
debug1: Enabling compatibility mode for protocol 2.0
debug1: Local version string SSH-2.0-OpenSSH_5.6
debug1: SSH2_MSG_KEXINIT sent
debug1: SSH2_MSG_KEXINIT received
debug1: kex: server->client aes128-ctr hmac-md5 none
debug1: kex: client->server aes128-ctr hmac-md5 none
debug1: SSH2_MSG_KEX_DH_GEX_REQUEST(1024<1024<8192) sent
debug1: expecting SSH2_MSG_KEX_DH_GEX_GROUP
debug1: SSH2_MSG_KEX_DH_GEX_INIT sent
debug1: expecting SSH2_MSG_KEX_DH_GEX_REPLY
debug1: Host 'localhost' is known and matches the RSA host key.
debug1: Found key in /root/.ssh/known_hosts:2
debug1: ssh_rsa_verify: signature correct
debug1: SSH2_MSG_NEWKEYS sent
debug1: expecting SSH2_MSG_NEWKEYS
debug1: SSH2_MSG_NEWKEYS received
debug1: Roaming not allowed by server
debug1: SSH2_MSG_SERVICE_REQUEST sent
debug1: SSH2_MSG_SERVICE_ACCEPT received
debug1: Authentications that can continue: publickey,gssapi-keyex,gssapi-     with-mic,password
debug1: Next authentication method: gssapi-keyex
debug1: No valid Key exchange context
debug1: Next authentication method: gssapi-with-mic
debug1: Unspecified GSS failure.  Minor code may provide more information
Credentials cache file '/tmp/krb5cc_0' not found

debug1: Unspecified GSS failure.  Minor code may provide more information
Credentials cache file '/tmp/krb5cc_0' not found

debug1: Unspecified GSS failure.  Minor code may provide more information


debug1: Unspecified GSS failure.  Minor code may provide more information


debug1: Next authentication method: publickey
debug1: Trying private key: /root/.ssh/id_rsa
debug1: Trying private key: /root/.ssh/id_dsa
debug1: Next authentication method: password
Wani@localhost's password: 
debug1: Authentication succeeded (password).
Authenticated to localhost ([127.0.0.1]:22).
debug1: channel 0: new [client-session]
debug1: Requesting no-more-sessions@openssh.com
debug1: Entering interactive session.
debug1: Sending environment.
debug1: Sending env XMODIFIERS = @im=none
debug1: Sending env LANG = en_US.UTF-8
debug1: Sending command: scp -v -t -- .
Hello
[root@Dell Wani]# debug1: client_input_channel_req: channel 0 rtype exit-status      reply      0
debug1: channel 0: free: client-session, nchannels 1
debug1: fd 0 clearing O_NONBLOCK
debug1: fd 1 clearing O_NONBLOCK
Transferred: sent 1664, received 1976 bytes, in 0.1 seconds
Bytes per second: sent 22961.5, received 27266.8
debug1: Exit status 0

(然后按Enter键)

[root@Dell Wani]# 

谁能说明这里到底发生了什么?为什么文件没有从根目录复制到Wani?


cp呢 有cp try.txt ~Wani/工作吗?
nneonneo 2012年

实际上,交互式命令或您的虚假输出.bashrc可能会破坏某些非交互式方案。尝试将代码作为条件case $- in *i*或类似条件。
Tripleee 2012年

@nneonneo:可行。实际上,即使我有两个用户在不同的计算机上,也不会复制该文件!
Nehal J Wani 2012年

1
我所见过的所有帖子都描述了为什么此问题存在于各种bashrc文件等中。但是,当SCP / STFP到计算机上时,您不能拥有并且不能更改启动脚本,那么解决方案是什么?
ChuckB

我最终将所有回声重定向到stderr。有效,但是...
Andreas

Answers:


77

使用echo.bashrc将打破scp,因为scp期望看到在标准输入/输出频道其协议数据。有关此问题的更多讨论,请参见https://bugzilla.redhat.com/show_bug.cgi?id=20527

有一些解决方法:

  • “交互式”标志的条件(例如case $- in *i*,由三元组建议)
  • 使用该tty实用程序检测交互式外壳(例如if tty > /dev/nullif [ -t 0 ]
  • 检查值 $SSH_TTY

我想您应该使用适合您的任何一种。不幸的是,我不知道最好的(最便携式/最可靠)的选择是什么。


6
只是为了澄清“ case”命令是:case $- in *i*) echo This is safe since the shell is interactive; esac
mlathe

shopt也是一种替代选择
vesperto

1
由于我的主机始终通过SSH访问,因此始终设置SSH_TTY。使用-t 0条件对我来说效果很好。我现在在我的bashrc上使用以下函数。 safe_echo() { if [[ -t 0 ]];then echo -e "$*" fi }
Sandip Bhattacharya

if [[ "$SSH_TTY" == */dev/pts/* ]] ; then如果将要打印的内容放入stdout,则scp可以正常工作。
BeatingBytes

@BeatingBytes和@Sandip Bhattacharya,[[不是可移植的,我也不认为它是posix。在尝试这个dash壳: if [[ 0 = 0 ]]; then echo x; else echo y; fi。你得到dash: 3: [[: not found
椭圆视图

19

要增加nneonneo的选项,您还可以使用带有

if [[ $- =~ "i" ]]

我认为这可能是bash中最清晰的方法。


[[不是便携式的,我也不认为它是posix。在尝试这个dash壳: if [[ 0 = 0 ]]; then echo x; else echo y; fi。你得到dash: 3: [[: not found
椭圆视图


10

默认的Ubuntu.bashrc包含下面的代码片段,其已经采取照顾的问题:

# If not running interactively, don't do anything
case $- in
    *i*) ;;
    *) return;;
esac

4
较短的时间:[[ $- != *i* ]] && return
phil294

2
您的答案中提供的表格与POSIX兼容。由于使用了[[功能,您在注释中提供的不是POSIX 。对于bashrc文件不是那么有问题;),但是您可能希望能够在另一个上下文/ shell中使用它。
Totor

4

在中.bashrc,将STDERR用作输出:

echo "# Important Notice" >&2

更新:不要使用它!最近,我们遇到了一个问题,由于的echoSTDERR,(封闭源)工具失败了.bashrc。该工具(使用rcp)根本不会在STDOUT或STDERR上都没有输出。当它得到回声时,它卡住了。获得的经验教训:分别为人类和机器(脚本)建立帐户,或者仅通过停止跟踪.bashrc


低估了“为人和机器分别设置帐户”。
安德烈亚斯(Andreas)

1

测试交互式外壳的最可移植的方法似乎是:

test -t 0
if [ $? -eq 0 ]
then
    # interactive
    ;
else
    # non-interactive
    ;
fi

0

nneonneo的解决方案也对我有用。但是由于我的默认外壳是TCSH,因此我必须对修复进行如下修改(在.tcshrc中):

if ( $?SSH_TTY ) then
    exec /bin/bash
endif

只是想我会为大家的利益分享。


0

如果您使用的是Red Hat Enterprise Linux(RHEL)或其他版本,请将执行echo或所需操作的脚本拖放到/etc/profile.d/中。


0

如果您还想要echo语句(来自@Blauhirn的答案),则可以继续将您的echo语句放置在大小写条件之后。

case $- in
    *i*) ;;
    *) return;;
esac

echo "Your Greeting/Warning Message/s here!"

-1
if [ 0 -eq $(shopt -q login_shell; echo $?) ]; then
  echo "do something?"
fi

资源


为OP提供一些上下文将是很好的。
aljabear

可以从其他答案和问题本身中提取上下文和相关信息。这只是在已知的情况下以低信噪比进行操作的另一种方式。
vesperto
By using our site, you acknowledge that you have read and understand our Cookie Policy and Privacy Policy.
Licensed under cc by-sa 3.0 with attribution required.