我已经编写了一个 bash 脚本,该脚本应该cd
放在一个目录中。
我的问题是只有子 shell 中的目录发生了变化。
我读过很多类似的问题,但我想知道是否有解决方案除了使用别名、函数或获取脚本。
如果你不明白我的意思,这里有一个例子:
user@linux ~: cat ./myscript.sh
#!/bin/bash
cd /any/directory
user@linux ~: ./myscript.sh
user@linux ~:
请注意我的脚本是很多更长,所以我不想使用函数!
答案1
如果您希望 cd 命令在当前 shell 中生效,则必须在当前 shell 中运行该脚本,因为子 shell 中的更改不会传播回父 shell。
$ pwd
/afs/user/i/ahmad
$ cat test1
#!/bin/bash
cd /etc
$ . test1 #runs test1 in current shell even if its not executable
$ pwd
/etc
使用 echo 和 eval:
在父 shell 中使用 eval。在 shell 脚本 echo 命令中,您希望由父 shell 运行:
echo "cd $filepath"
在父 shell 中,您可以使用 eval 来启动 shell 脚本:
eval `sh foo.sh`
例子:
$ cat test1.sh
#!/bin/bash
echo "cd /etc"
$ eval `sh test1.sh`
$ pwd
/etc
答案2
当您运行脚本时,它会启动单独的进程,具有自己的参数、函数等。该进程从父 shell 继承环境,但之后它们是不同的生命体。您不能以cd
与在一个进程中从另一个进程内运行发送任何其他命令相同的方式从子 shell 中的父 shell 中的某个位置进行操作。换句话说,没有像这样的魔法
command "run in process 123456"
现在,虽然您无法向进程发送要执行的命令,但实际上您可以发送信号到一个带有命令的进程kill
。因此,如果您提前为这种情况准备了父 shell,您可以trap
发出信号并运行一些命令。
这是一个最小的例子:
/home/jimmij $ trap 'cd /tmp' INT
/home/jimmij $ cat myscript.sh
#!/bin/bash
echo Changing parent directory
kill -s SIGINT $PPID
/home/jimmij $ ./myscript.sh
Changing parent directory
/tmp $