在本指南中,我们将向 linux 新手展示如何可靠地存储自定义的 shell 脚本,解释如何编写 shell 函数和函数库,以及如何在其它的脚本中使用函数库中的函数。
<a target="_blank"></a>
为了在执行你自己的脚本时不必输入脚本所在位置的完整或绝对路径,脚本必须被存储在 <code>$path</code> 环境变量所定义的路径里的其中一个。
使用下面的命令可以查看你系统中的 <code>$path</code> 环境变量:
<code>$ echo $path</code>
<code>/usr/local/sbin:/usr/local/bin:/usr/sbin:/usr/bin:/sbin:/bin:/usr/games:/usr/local/games</code>
通常来说,如果在用户的家目录下存在名为 <code>bin</code> 的目录,你就可以将 shell 脚本存储在那个目录下,因为那个目录会自动地被包含在用户的 <code>$path</code> 环境变量中(lctt 译注:在 centos 6/7 下是这样的,在 debian 8 下不是这样的,在 ubuntu 16.04 下又是这样的)。
因此,在你的主目录下创建 <code>bin</code> 目录吧(当然这里也可以用来存储 perl、awk 或 python 的脚本,或者其它程序):
<code>$ mkdir ~/bin</code>
接着,建立一个名为 <code>lib</code>(libraries 的简写)的目录来存放你自己的函数库。你也可以在其中存放其它编程语言的函数库,如 c ,python 等语言。在 <code>lib</code> 目录下建立另一个名为 <code>sh</code> 的目录,这个目录将被用来存放你的 shell 函数库:
<code>$ mkdir -p ~/lib/sh</code>
一个 <code>shell 函数</code> 就是在脚本中能够完成特定任务的一组命令。它们的工作原理与其他编程语言中的过程(lctt 译注:可能指的是类似 sql 中的存储过程之类的吧)、子例程、函数类似。
编写一个函数的语法如下:
<code>函数名() { 一系列的命令 }</code>
( lctt 校注:在函数名前可以加上 <code>function</code> 关键字,但也可省略不写)
例如,你可以像下面那样在一个脚本中写一个用来显示日期的函数:
<code>showdate() {date;}</code>
每当你需要显示日期时,只需调用该函数的函数名即可:
<code>$ showdate</code>
简单来说 shell 函数库也是一个 shell 脚本,不过你可以在一个函数库中仅存储其它 shell 脚本中需要调用的函数。
下面展示的是在我的 <code>~/lib/sh</code> 目录下一个名为 <code>libmyfuncs.sh</code> 的库函数:
<code>#!/bin/bash</code>
<code>### function to clearly list directories in path</code>
<code>showpath() {</code>
<code>oldifs="$ifs" ### store old internal field separator</code>
<code>ifs=: ### specify a new internal field separator</code>
<code>for dir in $path<br> do<br> echo $dir<br> done</code>
<code>ifs="$oldifs" ### restore old internal field separator</code>
<code>}</code>
<code>### function to show logged user</code>
<code>showusers() {</code>
<code>echo -e “below are the user logged on the system:\n”</code>
<code>w</code>
<code>### print a user’s details</code>
<code>printuserdets() {</code>
<code>oldifs="$ifs" ### store old internal field separator</code>
<code>ifs=: ### specify a new internal field separator</code>
<code>read -p "enter user name to be searched:" uname ### read username</code>
<code>echo ""</code>
<code>### read and store from a here string values into variables</code>
<code>### using : as a field delimiter</code>
<code>read -r username pass uid gid comments homedir shell <<< "$(cat /etc/passwd | grep "^$uname")"</code>
<code>### print out captured values</code>
<code>echo -e "username is : $username\n"</code>
<code>echo -e "user's id : $uid\n"</code>
<code>echo -e "user's gid : $gid\n"</code>
<code>echo -e "user's comments : $comments\n"</code>
<code>echo -e "user's home dir : $homedir\n"</code>
<code>echo -e "user's shell : $shell\n"</code>
<code>ifs="$oldifs" ### store old internal field separator</code>
保存文件并且给脚本添加执行权限。
要使用某个 <code>lib</code> 目录下的函数,首先你需要按照下面的形式 将包含该函数的函数库导入到需要执行的 shell 脚本中:
<code>$ . /path/to/lib</code>
<code>或</code>
<code>$ source /path/to/lib</code>
(lctt 译注:第一行的 <code>.</code> 和路径间必须是有空格的)
这样你就可以像下面演示的那样,在其它的脚本中使用来自 <code>~/lib/sh/libmyfuncs.sh</code> 的 <code>printuserdets</code> 函数了。
在下面的脚本中,如果要打印出某个特定用户的详细信息,你不必再一一编写代码,而只需要简单地调用已存在的函数即可。
创建一个名为 <code>test.sh</code> 的新文件:
<code>### include lib</code>
<code>. ~/lib/sh/libmyfuncs.sh</code>
<code>### use function from lib</code>
<code>printuserdets</code>
<code>### exit script</code>
<code>exit 0</code>
保存这个文件,并使得这个脚本可被执行,然后运行它:
<code>$ chmod 755 test.sh</code>
<code>$ ./test.sh</code>

编写 shell 函数
在本文中,我们介绍了在哪里可靠地存储 shell 脚本,如何编写自己的 shell 函数和函数库,以及如何在一个普通的 shell 脚本中从函数库中调用库中的某些函数。
原文发布时间为:2017-03-15
本文来自云栖社区合作伙伴“linux中国”