解决SSH远程执行命令找不到环境变量的问题

通过SSH执行远程主机的命令或脚本时,经常会出现找不到自定义环境变量的问题。但是,如果通过SSH登录远程主机,然后再执行相同的命令或脚本,那么此时执行又是成功的。两种相似的方法,得到的结果却截然不同,看起来很诡异的现象,根本原因在于这两种方式使用的bash模式不同!

1. 通过SSH登录后再执行命令和脚本

这种方式会使用Bash的interactive + login shell模式,这里面有两个概念需要解释:interactive和login。

login故名思义,即登陆,login shell是指用户以非图形化界面或者以ssh登陆到机器上时获得的第一个shell,简单些说就是需要输入用户名和密码的shell。因此通常不管以何种方式登陆机器后用户获得的第一个shell就是login shell。

interactive意为交互式,这也很好理解,interactive shell会有一个输入提示符,并且它的标准输入、输出和错误输出都会显示在控制台上。所以一般来说只要是需要用户交互的,即一个命令一个命令的输入的shell都是interactive shell。而如果无需用户交互,它便是non-interactive shell。通常来说如bash script.sh此类执行脚本的命令就会启动一个non-interactive shell,它不需要与用户进行交互,执行完后它便会退出创建的Shell。

在interactive + login shell模式中,Shell首先会加载/etc/profile文件,然后再尝试依次去加载下列三个配置文件之一,一旦找到其中一个便不再接着寻找:

  • ~/.bash_profile
  • ~/.bash_login
  • ~/.profile

2. 通过SSH直接执行远程命令和脚本

这种方式会使用Bash的non-interactive + non-login shell模式,它会创建一个shell,执行完脚本之后便退出,不再需要与用户交互。

no-login shell,顾名思义就是不是在登录Linux系统时启动的(比如你在命令行提示符上输入bash启动)。它不会去执行/etc/profile文件,而会去用户的HOME目录检查.bashrc并加载。

系统执行Shell脚本的时候,就是属于这种non-interactive shell。Bash通过BASH_ENV环境变量来记录要加载的文件,默认情况下这个环境变量并没有设置。如果有指定文件,那么Shell会先去加载这个文件里面的内容,然后再开始执行Shell脚本。

3. 结论

由此可见,如果要解决SSH远程执行命令时找不到自定义环境变量的问题,那么可以在登录用户的HOME目录的.bashrc中添加需要的环境变量。

4、示例

当登录之后,直接在某台远程主机:10.0.63.9上执行日期格式化的命令时,打印的是正确的,如下:

[root@dev-appserver2 ~]# buildTimeStamp=2017-09-27T16:58:47.291+08:00; buildTimeStampStr=$(date -d $buildTimeStamp "+%y%m%d%H%M%S"); echo $buildTimeStampStr
170927165847

当在另外一台主机(10.0.251.216)上远程执行ssh命令时,打印的结果不正确(差了八个时区),如下:

[root@host-10-0-251-216 ~]# cat sshtime
buildTimeStamp=2017-09-27T16:58:47.291+08:00; buildTimeStampStr=$(date -d $buildTimeStamp "+%y%m%d%H%M%S"); echo $buildTimeStampStr

[root@host-10-0-251-216 ~]# a=`cat sshtime `
[root@host-10-0-251-216 ~]# echo $a
buildTimeStamp=2017-09-27T16:58:47.291+08:00; buildTimeStampStr=$(date -d $buildTimeStamp "+%y%m%d%H%M%S"); echo $buildTimeStampStr
[root@host-10-0-251-216 ~]# ssh root@10.0.63.9 $a
root@10.0.63.9's password:
170927085847

此时修改10.0.63.9上,root根目录下的.bashrc文件,增加TZ的设置,再次执行ssh打印的结果是正确的:

[root@dev-appserver2 ~]# cat .bashrc
# .bashrc
 
# User specific aliases and functions
 
alias rm='rm -i'
alias cp='cp -i'
alias mv='mv -i'
 
export TZ="Asia/Shanghai"
 
# Source global definitions
if [ -f /etc/bashrc ]; then
    . /etc/bashrc
fi
[root@dev-appserver2 ~]#
[root@host-10-0-251-216 ~]# ssh root@10.0.63.9 $a
root@10.0.63.9's password:
170927165847

  • 1
    点赞
  • 5
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
Geekstuff唯一一本在官网免费下载的101 hacks系列,可以说是为其他的101 hacks的经典之一。本书中的很多技巧对于初学者提高系统管理的工作效率很有帮助。光看看目录,就感觉非常实用! 此为第二版。 -------- 资源为英文,下载请谨慎 中文版linux 101 hacks(第一版): http://download.csdn.net/detail/jiaoxiaogu/4273423 -------- 附目录(中文翻译) 第一章:强大的CD 命令技巧 技巧1:CDPATH : 设置cd 命令的基目录 技巧2:使用cd 和alias 命令快速返回上级目录 技巧3:用一条语句执行―mkdir‖和―cd‖命令 技巧4:用―cd -‖在最近访问的两个目录之间切换 技巧5:用―dirs‖、―pushd‖、―popd‖来操作目录栈 技巧6:用―shopt –s cdspell‖自动纠正―cd‖命令的目录名输入错误 第二章:日期操作 技巧7:设置系统日期和时间 技巧8:设置硬件日期和时间 技巧9:用特定格式显示当前时间 技巧10:显示过去的日期和时间 技巧11:显示未来的日期和时间 第三章:SSH(Secure SHell)客户端命令 技巧12:查看SSH 客户端版本 技巧13:用SSH 登录到远程主机 技巧14:调试SSH 客户端会话 技巧15:用SSH 退出符切换SSH 会话 技巧16:用SSH 退出字符会话,显示信息 第四章:重要的linux 命令 技巧17:grep 命令 技巧18:find 命令 技巧19:禁止标准输出和错误信息的输出 技巧20:join 命令 技巧21:改变字符的大小写 技巧22:xargs 命令 技巧23:sort 命令 技巧24:uniq 命令 技巧25:cut 命令 技巧26:stat 命令 技巧27:diff 命令 技巧28:显示用户总的连接时间 第五章:PS1,PS2,PS3 和PROMPT_COMMAND 技巧29:PS1——默认提示符 技巧30:PS2——再谈提示符 技巧31:PS3——Shell 脚本中使用select 时的提示符 技巧32:PS4——PS4-―set -x"用来修改跟踪输出的前缀 技巧33:PROMPT_COMMAND 环境变量 第六章:用功能强大的彩色终端快速使用PS1 技巧34:在提示符中显示用户名,主机名,当前目录 技巧35:在提示符里显示当前时间 技巧36:任意命令的输出作为提示符 技巧37:改变提示符的前景颜色 技巧38:改变提示符的背景色 技巧39:在提示符中显示多种颜色 技巧40:用tput 改变提示符颜色 技巧41:使用已有的PS1 变量创建自己的提示符 技巧42:通过PS1 调用bash shell 函数 技巧43:通过PS1 中调用shell 脚本 第七章:归档和压缩 技巧 44:zip 命令基础 技巧 45:zip 高级用法 技巧 46:zip 文件的密码保护 技巧 47:检查zip 文件的完整性 技巧 48:tar 命令的基础知识 技巧 49:在tar 中使用gzip, bzip2 第八章:history 命令 技巧 50:使用HISTTIMEFORMAT 在历史中显示TIMESTAMP 技巧 51:用Ctrl + R 搜索历史命令 技巧 52:四种不同的方法快速执行之前的命令 技巧 53:执行历史命令中的特定命令 技巧 54:执行以特定字开头的历史命令 技巧 55:用HISTSIZE 控制历史命令的总数 技巧 56:使用HISTFILE 改变历史文件名 技巧 57:使用HISTCONTROL 来消除命令历史中的连续重复条目 技巧 58:使用HISTCONTROL 在整个历史中去除重复命令 技巧 59:使用HISTCONTROL 强制history 忽略某条特定命令 技巧 60:使用c 选项清除所有的历史命令 技巧 61:替换命令历史中的内容 技巧 62:替换特定命令的特定参数 技巧63:用HISTSIZE 禁用history 技巧64:用HISTIGNORE 让history 在存储时忽略某些指令 第九章:系统管理任务 技巧 65:用 fdisk 进行分区 技巧 66:用 mke2fsk 格式化分区 技巧 67:挂载分区 技巧 68:用tune2fs 进行分区调整 技巧 69:创建交换分区 技巧 70:创建新用户 技巧 71:创建新的组并将用户加入该组 技巧 72:在OpenSSH 中设置SSH 的无密码登陆 技巧 73:与 ssh-agent 一起来使用 ssh-copy-id 技巧 74:crontab 技巧 75:用Magic SysRq 键实现Linux 安全重启 第十章:Apachectl 和 Httpd 实例 技巧76:传递不同的httpd 技巧77:使用一个临时DocumentRoot 而不修改httpd 技巧78:暂时提高Log 的级别 技巧79:显示Apache 内的模块 技巧80:显示httpd 技巧81:验证被修改的httpd 技巧82:显示httpd 的编译参数 技巧83:根据需要加载一个指定模块 第十一章:Bash 脚本 技巧84:.bash_*files 的执行顺序 技巧85:如何在bash shell 中产生随机数 技巧86:调试一个脚本 技巧87:使用引号(Quoting) 技巧88:将数据文件的指定域读取到shell 脚本中 第十二章:监控系统和性能 技巧89:free 命令 技巧90:top 命令 技巧91:ps 命令 技巧92:df 命令 技巧93:kill 命令 技巧94:du 命令 技巧95:lsof 命令 技巧96:sar 命令 技巧97:vmstat 命令 技巧98:netstat 命令 技巧99:sysctl 命令 技巧100:nice 命令 技巧101:renice 命令 第十三章 一些额外的技巧 额外技巧1:让cd 命令对参数大小写不敏感 额外技巧2:一次动作为多次SSH 连接指定密码 额外技巧3:rar 命令用法示例 额外技巧4:用Comm 命令比较两个文件 额外技巧5:Compact-Disk (CD)操作 额外技巧6:DVD 操作 额外技巧7:从CD 或者DVD 创建ISO 文件 额外技巧8:OD 命令用法示例 额外技巧9:Gpg 命令用法示例 额外的技巧10:Tee 命令示例
Shout down –n now 关机时同步备份内存中的数据 useradd + 用户 创建用户 userdel + user 可以用来删除用户 passwd + user 更改用户密码(不加user ,则更改当前用户密码) poweroff 关机 reboot 重启 vim vi 下 :wq 在vim or vi 后保存退出 :q 不保存退出 :q! 强制退出 在非insert 下可用 x来删除光标所在处字符 dw 可以删除一个单词 d 用来删除一行 w - 从当前光标当前位置直到单字/单词末尾,包括空格。 e - 从当前光标当前位置直到单字/单词末尾,但是 *不* 包括空格。 $ - 从当前光标当前位置直到当前行末。 u 来撤销最后执行的命令 dd 删除整行 yy复制 按p 粘贴 gg 到首行 G 到最后一行 输入 p 将最后一次删除的内容置入光标之后 输入 r 和一个字符替换光标所在位置的字符 按下 SHIFT-G 键可以使得当前光标直接跳转到文件最后一行 /string 下搜索 shift +n 向上搜索 n 向下搜 ?string 上搜索 gedit + name 用来图形化编辑 rmdir 删除目录 rm 删除文件 sed 's/cat/dog/' cats 将cats 文件中cat 替换成dog cd – 可以使回到上次的目录 eg./tmp/jack/rose/love 先在love 目录下,后回到jack目录下cd – 后回到love 目录下 /etc/passwd /etc/shadow /etc/group /etc/gshadow 与user 有关的文件 chmod u/g/o/a +/-/= /r/w/x file name 改权限 -r 递归改 R 100=4 W 010=2 X 001=1 数字表示法 chown user file 改文件所有用户 chown user。group file 改文件的用户与所属组 chgrp group file 改文件所有组 usermod –G(g覆盖原组) grpup user改用户属于什么组(共享的组,即同时可以在多个组中) df 查看分区信息 sda 串口硬盘 —h 可读的 du 查看当前目录下的使用情况 fdisk –l 查看磁盘分区信息 mkfs 查看格式化的版本 eg. mkfs.ext4 +设备 格式化 mount 查看挂载信息 virtual-manage 打开虚拟机 eg. mv /usr/bin/passwd /usr/bin/pw 将改密码的命令passwd 改为pw pwd 用户目前存在位置 cp file [file2] directory mv file [file2] directory 剪切 or 改名字 rm –r directory==rmdir rm file rm –rf directory [file] 在/etc/redhat-release 中存放RHEL的版本信息 env LANG= 语言 tail –f file 使查看的文件不断更新查看 cut –d:(:为指定通配符,:可以另外改) –f1(1为通配符前第几个,可以改) file wc 统计单词,行数 sort 排序 command1| command2 command1的输出是command2的输入 DNS全球通用的: 8.8.8.8 DHCP :动态分配IP地址 255.255.255 网络段 0 主机 ifconfig –a 查看所有网卡 mask 子网掩码,分辨网络地址,与主机地址 改IP地址: /etc/sysconfig/network-scripts 在此目录下,文件名与网卡名要一样 Vim ifconfgi eth0(网卡) 在我虚拟机上的是ifcfg-eht0 可以将”dhcp” 改成”static ”(静态的) 增加IPADDR=ip地址 Onboot=yes (用来是否开关此网卡) ipaddr=…… NETMASK=子网掩码 GATEWAY=网关 or service network restart(reload) /etc/init.d/network restart(reload) Ifdown(ifup) eth0 开关网卡 /etc/init.d networkmanager stop /etc/init.d/network restart 重启网络网卡 Chkconfig networkmanager off 关闭此服务 配置dns : vim /etc/resolv.conf nameserver(命令) ip 立刻生效 hostname 主机名 /etc/sysconfig/network (里面有全局网关gateway) hostname +主机名 可以立刻改名,但未写入文件中 /etc/hosts 本地域名解析,可以改自己定义的域名 ip 域名(www……..) startx 启动图形界面 ssh 用户名@ip 以此用户名登陆 scp file1 ip:file2 远程将本机file1拷贝到ip为此的机子的目录下 scp ip:file1 file2 远程将ip 的file1拷贝到本机file2 中 ln –s file1 file2 为file1创建file3的软连接 ln –s file1(绝对路径) file2(绝对路径) 可以为file1 跨目录连接到file2 ln file1 file2 为file1创建file3 的硬连接 同时删除file1 和file2 才能删除文件 分发系统: 1. 支持pxe client 功能,有pxe的网卡 (client端) 2. 有配置文件config system-config-kick 创建kick 文件 (server端) 3. 为安装文件提供Kickstar文件 /etc 4. client端通过pxe处获取config的文件然后重启 用dhcp协议 用tftp协议 tar –cvfz 打包 tar –xzvf 解压 -tvf 查看打包的里面的文件 [abc….] 【】中任意一个单词匹配 [^abc….] 不与[ ]中任意一个单词匹配 ^word 行首匹配 $word 行尾匹配 2> 将错误输入到…….. eg. cp –rf /etc/passwd /tmp 1 > (正确重定向)file 2> (错误重定向) grep …. 过滤只有…. /etc/fstab 查看所有挂载 /dev/sda[number] 挂载点(/mnt) 文件格式(ext4)defaults kdump(备份) 加电自检否 0 0 1 1 2 2 1备份级别高 2备份级别低 0 不会执行 mount –a 重新执行/fstab表的内容 即重新挂载 增加swap分区: 在分区内容下,即command ……下 t l 数字 将分区变成swap的 partx –a 硬盘 mkswap 分区 挂载 swapon 分区 使分区生效 free –m 查看swap 或者swapon –s swapoff 分区 可以使某个swap分区关闭方便其他使用 /etc/inittab 有开机时启动关的数字选项 具体可用 init number 来命令 umask (权限掩码) 可用命令umask 查看 改变umask : umask 0022 隐藏权限:chattr 用lsattr file 可看隐藏权限 chattr +a/e file 改变特殊权限(针对非root用户) chmod u-s file 可以去掉特殊权限 +s 关闭selinux /etc/sysconfig/selinux suid 针对文件 rwsrwxrwx 拥有者有x权限的基础才能有s权限 其他用户可以临时的拥有用户的权限 sgid 针对文件与目录 临时拥有用户组的权限 eg.chgrp group directory chmod g+s(-s) directory 则以后directory 的file全属于组g sbit 针对目录 当other中有x位有t 权限 除文件拥有者,root外对directory内的file 不可删,但可以写入 4 suid 2 sgid 1 sbit chmod u+s directory g+s o+t 有效用户组:排第一位的组 groups user 查看user的组 改有效用户组: 在当前用户下 newgrp group(此组为user属于的组) rpm 包 相当于一个exe文件 rpm包: rpm –i (install) 包名 -v(显示信息) 包名 -h (show) yum库: 将许多包关联,使包可以一起安装不需要用rpm 一个一个的装 ldap:统一名字(在服务器上) authconfig-tui 打开ldap 空格键 确定选中 用图形用户打开ldap: system-config-authentication /etc/init.d/NetworkManager status 查看状态 一般关闭,否则许多网络的服务不能起来 iptables –F 清空所有网卡规则 crontab(计划任务): 查看:crontab –l 编辑: crontab –e –u user 配置文件: 分 时 日 月 周 看最后一行:* * * * * user command(如果不用在此时间则用* eg. 10 8 * * * /bin/echo “jdsj”) 每隔10Min执行一次 */10 * * * *…. 几点到几点: * 8--10 * * * ….. 每天8点到10点做什么 * 9,15 * * * ..每天9点,15点提醒做什么 service crond restart 在设置好提醒后重启服务 提醒会在邮箱中 在/etc/crontab中MAILTO =user则会在邮箱提醒,否则刷屏提醒 /etc/cron.deny 禁止使用计划任务 计划任务中执行脚本: command 处写 sh *.sh(脚本文件) quota(磁盘配额:限制个人所用的磁盘大小):目录在哪分区,则针对某分区进行磁盘配额 检测:edquota –u user edquota –g group 修改fstab表:defaults,usrquota,grpquota 重新挂载 :mount –a or mount –o remount /(directory or device) 强制检测并开启quota :quotacheck –avugcm quota -avug edquota –u user 查看是否开启了:quota –u user ntp :同步时间 vim /etc/ntp.conf 在注释hosts on local ….处 restrict ip 下面: server ip 服务端设置: 在use inaccurate…… server ip fudge….打开注释即可 ntpq –p (查看ntp server是否还在) vim /etc/grub.conf timeout=number 开机读秒数 default=num 启用的内核 vim /etc/inittab id:num:initdefault (启动时用的是否是图形界面等) find /dircetory –name filename –user username(属于user 的文件) -group groupname -user username not –group groupname(其他组) -exec(前面的结果相当于后面命令的输入) 连接前后命令 相当于管道符 eg. find / -user username –exec cp [参数] {} /directory \; vim .bash_profile 环境变量文件 bios mbr boot lo(grub.conf 在开机时识别kernel) kernel 防火墙级别: 1. 硬件防火墙 2. tcp_wrapper(用来分析tcp/ip封包的软件) 3. iptables 基于数据流的防火 4. 内核级别:selinux 5. 服务本身
### 回答1: Win7的命令行上使用ssh命令提示"ssh不是内部命令"可能是因为该命令没有在系统的环境变量中被识别和添加。在Win7系统上,ssh命令默认是不包含在Windows的命令集中的,所以需要手动添加才能顺利使用。 要解决这个问题,可以按照以下步骤进行操作: 1. 确保你的系统中已经正确安装了ssh客户端,如OpenSSH。 2. 打开控制面板,然后点击“系统与安全”。 3. 在新窗口中,点击“系统”。 4. 在左侧导航栏中,点击“高级系统设置”。 5. 在弹出的系统属性窗口中,点击“环境变量”按钮。 6. 在下方的“系统变量”部分,到名为“Path”的变量,并点击“编辑”。 7. 在编辑系统变量窗口中,点击“新建”,然后输入ssh的安装路径,例如C:\Program Files\OpenSSH。 8. 确认所有更改并关闭所有弹窗。 9. 重新启动命令行窗口(如果已经打开的话),然后尝试使用ssh命令进行连接。 完成上述步骤后,ssh命令应该就可以在Win7的命令行中正常使用了。如果问题仍然存在,可以检查ssh的安装路径是否正确,或者尝试重新安装ssh客户端。 ### 回答2: win7中没有自带的SSH命令,因此当我们在命令提示符中输入“ssh”时,系统会提示“ssh不是内部命令,也不是外部命令,也不是可运行的程序或批处理文件”。 SSH(Secure Shell)是一种网络协议,用于在不安全的网络中提供安全的远程登录和执行命令。但在Windows系统中,它并不是默认安装的组件。 要使用SSH功能,我们需要从第三方提供的软件中选择安装并配置。比如,在Windows系统中,我们可以安装OpenSSH或PuTTY等软件来提供SSH功能。 安装OpenSSH的具体步骤如下: 1. 打开控制面板,在“程序”或“程序和功能”(视Windows版本而定)下到“启用或关闭Windows功能”。 2. 在打开的窗口中,到“OpenSSH客户端”和“OpenSSH服务器”复选框,勾选它们。 3. 点击“确定”保存更改。 4. 系统会开始安装并配置OpenSSH组件。 安装PuTTY的具体步骤如下: 1. 打开Web浏览器,搜索并下载PuTTY软件。 2. 安装PuTTY软件,根据安装向导的提示完成安装过程。 3. 安装完成后,打开PuTTY并输入目标主机的IP地址或主机名。 4. 选择SSH协议,并确保端口号设置为22(默认端口号)。 5. 点击“连接”按钮,进行远程连接。 除了以上提到的这两种软件,还有其他类似的SSH软件可供选择,具体安装和使用步骤可能会有所差异。 总结起来,当在Windows 7系统中运行SSH命令时会提示“ssh不是内部命令”,是因为系统没有自带SSH组件。我们需要通过安装第三方软件(如OpenSSH或PuTTY)来实现SSH功能并进行远程连接。 ### 回答3: "win7 ssh不是内部命令"的错误提示很可能是因为Windows 7操作系统没有内置SSH命令。SSH是一种安全的远程管理协议,它允许用户远程登录到其他主机并执行命令。 在Windows 7中,要使用SSH命令,您需要安装第三方的SSH客户端软件,例如PuTTY等。PuTTY是一个广泛使用的SSH、Telnet和串口连接软件,它可以在Windows系统上使用。 要安装PuTTY,您可以按照以下步骤进行操作: 1. 打开您的Web浏览器,然后在搜索引擎中搜索“PuTTY下载”。 2. 从官方网站或其他可信渠道下载PuTTY安装程序。 3. 运行下载的安装程序,并按照提示完成安装过程。 4. 完成安装后,您会在桌面或开始菜单中到PuTTY应用程序。 5. 双击PuTTY应用程序图标打开它。 6. 在PuTTY窗口中,输入您要远程连接的主机的IP地址或域名,并选择SSH作为连接类型。 7. 点击“打开”按钮,PuTTY将会尝试连接到指定的主机。 8. 如果连接成功,您将被要求输入用户名和密码登录到目标主机。 通过上述步骤,您可以在Windows 7上安装和使用SSH客户端软件来远程连接其他主机进行管理和操作。请注意,您可能需要有相应主机的远程访问权限和凭据才能成功连接。

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值