1

我想rm在某些情况下禁用 except 。我写了一个remove.sh文件中调用的函数,它通过了我想在实际调用之前强加的某些检查rm。但是,仍然可以进入终端并简单地调用rm函数而不是使用remove. 有没有办法禁用该rm功能,除非被调用remove?我希望它对登录终端的用户来说好像该rm功能不“存在”,所有“存在”的是删除功能。

甚至可能更进一步,当用户调用rm它时,它会在屏幕上打印一条声明说使用remove.

作为一个更广泛的问题,除了在某些情况下,有没有办法禁用终端命令?我知道我可以为rm需要 root 设置一个别名,但这是一种简单且不太方便的方法。

#!/bin/bash

function rm {
  if [ $# -le 0 ]; then
    echo "Error: no arguments specified."
  else
    hasDir=0
    for arg in "$@"; do
      if [ -d "$arg" ]; then hasDir=1; fi
    done

    ac="Action canceled."
    resp=("y" "n" "e")

    sure=" "
    while [ "$sure" != "y" ] && [ "$sure" != "n" ]; do
      read -p "PERMANENT ACTION.  Are you sure? (y/n): " sure
    done

    if [ "$sure" == "n" ]; then echo "$ac"; return; fi


    if [ $hasDir -eq 1 ]; then
      direc=" "
      validResp=0
      while [ $validResp -eq 0 ]; do
        read -p "Remove all sub-directories? (y/n/e): " direc
        for ans in "${resp[@]}"; do
          if [ "$direc" == "$ans" ]; then validResp=1; fi
        done
      done

      if [ "$direc" == "e" ]; then echo "$ac"; return; fi
    else
      direc="n"
    fi



    check=" "
    validResp=0
    while [ $validResp -eq 0 ]; do
      read -p "Verify removal of each file? (y/n): " check
      for ans in "${resp[@]}"; do
        if [ "$check" == "$ans" ]; then validResp=1; fi
      done
    done

    if [ "$check" == "e" ]; then echo "$ac"; return; fi


    if [ "$direc" == "n" ]; then
      if [ "$check" == "n" ]; then
        for file in "$@"; do
          if [ ! -d "$file" ]; then command rm -f "$file"; fi
        done
      else 
        for file in "$@"; do
          if [ ! -d "$file" ]; then command rm -i "$file"; fi
        done
      fi
    else
      if [ "$check" == "n" ]; then
        command rm -rf "$@"
      else
        command rm -ir "$@"
      fi
    fi
  fi    
}
4

4 回答 4

5

您可以覆盖rm(或任何其他命令);command内置允许您在必要时访问原始命令。

rm () {
    # Do something in addition to removing the file

    command rm "$@"
}

command禁用 shell 函数查找。

于 2013-02-16T00:21:19.123 回答
1

如果您想捕获 的所有用途rm,那么有一种方法。但是,我必须提到这是一种肮脏的,不推荐的方式。

mv /bin/rm /bin/rm.bak
cp my_rm_script /bin/rm

my_rm_script 应该包含对 /bin/rm.bak 的调用,而不是 /bin/rm。

这将捕获对 command 的所有调用rm

但是,这不适用于busybox 类型的架构,其中二进制文件的名称也很重要。

于 2013-02-16T08:21:46.673 回答
0

这是一个解决方案,它有点奇怪,但完全按照您想要的方式工作。

directory在您的主文件夹中创建一个

$~ mkdir ~/myrm

$~ cd ~/myrm

创建指向二进制文件的rm符号remove链接

$~ ln -s /path/to/remove rm

现在,上面的命令将创建一个链接,该链接基本上rm指向removeremove通过调用rm. 确保在rmelse 使用时赋予可执行权限

$~ chmod 0777 rm

现在是时候将路径放入$PATH变量中了。

$~ PATH=~/myrm/:$PATH

确保它~/myrm:$PATH不是$PATH:myrm。所以现在每当你调用它时,它都会在目录中rm搜索并调用它。rm~/myrm

于 2013-02-16T08:12:19.607 回答
0

您可以使用在您的系统上dpkg-divert安装不同的。rm

另请参阅这篇文章用 dpkg-divert 替换二进制文件以获取使用 shell 脚本的示例。

于 2013-02-16T00:40:09.737 回答