一个计算机技术爱好者与学习者

0%

好好学Shell:脚本调用子脚本

1. 前言

Shell脚本调用脚本的方法有两种,第一种是bash调用,在子shell里执行子脚本;第二种是引用调用,在当前脚本里执行子脚本。

《Shell脚本之模块化》一文中,我们主要学习了引用调用。本文中,我们来学习一下bash调用。

2. 调用顺序控制

本节内容主要来自ChatGPT。

在一个 bash 脚本中调用多个子 bash 脚本时,有两种常用的方式来确保子进程执行的顺序和状态,分别是wait&&

2.1. wait

第一种是使用 wait 命令来等待所有子进程执行完毕。
这种方法会阻塞当前进程,直到所有子进程都执行完毕,然后才会继续执行后面的代码。这种方法可以确保所有子进程都已经完成,但是会阻塞当前进程,不能同时执行其他代码。

例如:

1
2
3
4
5
6
#!/bin/bash
./sub_script1.sh &
./sub_script2.sh &
./sub_script3.sh &
wait
echo "All sub scripts completed."

wait说明:

  • wait 在没有任何参数的情况下,wait命令会等待所有后台进程完成,然后再继续执行脚本。
  • wait $PID 在继续脚本之前等待特定进程结束。
  • & 命令后的&符号表示后台任务。
  • $! 获取最后一个后台进程的PID。
  • $? 打印上一个进程的退出状态。

再来一个示例,来自文档:Bash 教程 - 异步任务

async-parent.sh

1
2
3
4
5
6
7
8
9
10
11
12
13
#!/bin/bash
# async-parent : Asynchronous execution demo (parent)
echo "Parent: starting..."
echo "Parent: launching child script..."
async-child.sh &
pid=$!
echo "Parent: child (PID= $pid) launched."
echo "Parent: continuing..."
sleep 2
echo "Parent: pausing to wait for child to finish..."
wait $pid
echo "Parent: child is finished. Continuing..."
echo "Parent: parent is done. Exiting."

async-child.sh

1
2
3
4
5
#!/bin/bash
# async-child : Asynchronous execution demo (child)
echo "Child: child is running..."
sleep 5
echo "Child: child is done. Exiting."

在这个例子中,我们看到该子脚本是非常简单的。真正的操作通过父脚本完成。在父脚本中,子脚本被启动, 并被放置到后台运行。子脚本的进程 ID 记录在 pid 变量中,这个变量的值是 $! shell 参数的值,它总是 包含放到后台执行的最后一个任务的进程 ID 号。

父脚本继续,然后执行一个以子进程 PID 为参数的 wait 命令。这就导致父脚本暂停运行,直到子脚本退出,意味着父脚本结束。

2.2. &&

第二种是使用 && 连接多个子进程。
这种方法会等待上一个子进程执行完毕之后,才会执行下一个子进程。如果有一个子进程执行失败,后面的子进程将不会被执行。这种方法可以确保所有子进程都被执行,但是如果有一个子进程执行失败,整个脚本就会停止执行。

例如:

1
2
3
#!/bin/bash
./sub_script1.sh && ./sub_script2.sh && ./sub_script3.sh
echo "All sub scripts completed."
  • 本文作者: 好好学习的郝
  • 原文链接: https://www.voidking.com/dev-shell-sub-shell/
  • 版权声明: 本文采用 BY-NC-SA 许可协议,转载请注明出处!源站会即时更新知识点并修正错误,欢迎访问~
  • 微信公众号同步更新,欢迎关注~