AskOverflow.Dev

AskOverflow.Dev Logo AskOverflow.Dev Logo

AskOverflow.Dev Navigation

  • 主页
  • 系统&网络
  • Ubuntu
  • Unix
  • DBA
  • Computer
  • Coding
  • LangChain

Mobile menu

Close
  • 主页
  • 系统&网络
    • 最新
    • 热门
    • 标签
  • Ubuntu
    • 最新
    • 热门
    • 标签
  • Unix
    • 最新
    • 标签
  • DBA
    • 最新
    • 标签
  • Computer
    • 最新
    • 标签
  • Coding
    • 最新
    • 标签
主页 / server / 问题 / 50585
Accepted
Mark Biek
Mark Biek
Asked: 2009-08-06 12:16:10 +0800 CST2009-08-06 12:16:10 +0800 CST 2009-08-06 12:16:10 +0800 CST

检查卷是否安装在 Bash 脚本中的最佳方法是什么?

  • 772

检查卷是否安装在 Bash 脚本中的最佳方法是什么?

我真正想要的是一种我可以像这样使用的方法:

if <something is mounted at /mnt/foo> 
then
   <Do some stuff>
else
   <Do some different stuff>
fi
linux mount bash
  • 18 18 个回答
  • 267406 Views

18 个回答

  • Voted
  1. Best Answer
    Dan Carley
    2009-08-06T12:27:33+08:002009-08-06T12:27:33+08:00

    避免使用/etc/mtab,因为它可能不一致。

    避免管道mount,因为它不需要那么复杂。

    简单地:

    if grep -qs '/mnt/foo ' /proc/mounts; then
        echo "It's mounted."
    else
        echo "It's not mounted."
    fi
    

    (后面的空格/mnt/foo是为了避免匹配例如/mnt/foo-bar。)

    • 179
  2. Zaptac
    2012-01-05T00:33:41+08:002012-01-05T00:33:41+08:00
    if mountpoint -q /mnt/foo 
    then
       echo "mounted"
    else
       echo "not mounted"
    fi
    

    或者

    mountpoint -q /mnt/foo && echo "mounted" || echo "not mounted"
    
    • 94
  3. Elliptical view
    2018-03-16T08:42:45+08:002018-03-16T08:42:45+08:00

    findmnt -rno SOURCE,TARGET "$1"避免了其他答案中的所有问题。它只用一个命令就可以完成这项工作。


    其他方法有以下缺点:

    • grep -q并且grep -s是一个额外的不必要的步骤,并非所有地方都支持。
    • /proc/\*并非所有地方都支持。(mountpoint也基于proc)。
    • mountinfo基于/proc/..
    • cut -f3 -d' '弄乱路径名中的空格
    • 解析mount的空白是有问题的。它的手册页现在说:

    .. 维护列表模式只是为了向后兼容。

    要获得更健壮和可定制的输出,请使用findmnt (8),尤其是在您的脚本中。


    重击功能:

    #These functions return exit codes: 0 = found, 1 = not found
    
    isDevMounted () { findmnt --source "$1" >/dev/null;} #device only
    isPathMounted() { findmnt --target "$1" >/dev/null;} #path   only
    isMounted    () { findmnt          "$1" >/dev/null;} #device or path
    

    #使用示例:

    if  isDevMounted "/dev/sda10";
       then echo "device is mounted"
       else echo "device is not mounted"
    fi
    
    if isPathMounted "/mnt/C";
       then echo   "path is mounted"
       else echo   "path is not mounted"
    fi
    
    #Universal (device OR path):
    if isMounted     "/dev/sda10";
       then echo "device is mounted"
       else echo "device is not mounted"
    fi
    
    if isMounted     "/mnt/C";
       then echo   "path is mounted"
       else echo   "path is not mounted"
    fi
    
    • 43
  4. chris
    2009-08-06T12:32:13+08:002009-08-06T12:32:13+08:00

    像这样的脚本永远不会是可移植的。unix 中的一个肮脏秘密是只有内核知道文件系统在哪里,并且缺少像 /proc (不可移植)这样的东西,它永远不会给你一个直接的答案。

    我通常使用 df 来发现子目录的挂载点是什么,以及它所在的文件系统。

    例如(需要 posix shell,如 ash / AT&T ksh / bash / 等)

    case $(df  $mount)
    in
      $(df  /)) echo $mount is not mounted ;;
      *) echo $mount has a non-root filesystem mounted on it ;;
    esac
    

    有点告诉你有用的信息。

    • 7
  5. cas
    2009-08-06T12:39:28+08:002009-08-06T12:39:28+08:00

    以下是我在我的 rsync 备份 cron 作业之一中使用的内容。它会检查 /backup 是否已安装,如果没有则尝试安装它(它可能会失败,因为驱动器位于热插拔托架中,甚至可能不存在于系统中)

    注意:以下仅适用于 linux,因为它 greps /proc/mounts - 更便携的版本将运行 'mount | grep /backup',就像马修的回答一样。

      如果 !grep -q /backup /proc/mounts ; 然后
        如果 !挂载/备份;然后
          回声“失败”
          1号出口
        菲
      菲
      回声“成功”。
      # 在这里做事
    
    • 7
  6. Brian Postow
    2009-08-06T12:36:59+08:002009-08-06T12:36:59+08:00

    因为为了挂载,无论如何你都需要有一个目录,它会被挂载,所以我的策略总是创建一个永远不会使用的奇怪文件名的伪造文件,然后检查它是否存在。如果文件在那里,那么那个地方没有安装任何东西......

    我认为这不适用于安装网络驱动器或类似的东西。我将它用于闪存驱动器。

    • 2
  7. Kyle Brandt
    2009-08-06T12:57:57+08:002009-08-06T12:57:57+08:00

    比较设备编号怎么样?我只是想想想最深奥的方法..

    #!/bin/bash
    if [[ $(stat -c "%d" /mnt) -ne $(stat -c "%d" /mnt/foo) ]]; then
        echo "Somethin mounted there I reckon"
    fi
    

    我的逻辑有一个缺陷......

    作为一个函数:

    #!/usr/bin/bash
    function somethingMounted {
            mountpoint="$1"
            if ! device1=$(stat -c "%d" $mountpoint); then
                    echo "Error on stat of mount point, maybe file doesn't exist?" 1>&2
                    return 1
            fi
            if ! device2=$(stat -c "%d" $mountpoint/..); then
                    echo "Error on stat one level up from mount point, maybe file doesn't exist?" 1>&2
                    return 1
            fi
    
            if [[ $device1 -ne $device2 ]]; then
                    #echo "Somethin mounted there I reckon"
                    return 0
            else
                    #echo "Nothin mounted it seems"
                    return 1
            fi
    }
    
    if somethingMounted /tmp; then
            echo "Yup"
    fi
    

    回显错误消息可能是多余的,因为 stat 也会显示错误。

    • 2
  8. Helgi Borg
    2021-10-21T14:29:07+08:002021-10-21T14:29:07+08:00

    此脚本将检查驱动器是否已安装且实际可用。它可以写得更紧凑,但我更喜欢这样简单,因为我对 Bash 不太熟悉。您可能想要更改超时,它设置为 10 秒。在脚本中。

    MNT_DIR=/mnt/foo
    df_result=$(timeout 10 df "$MNT_DIR")
    [[ $df_result =~ $MNT_DIR ]] 
    if [ "$BASH_REMATCH" = "$MNT_DIR" ]
    then
        echo "It's available."
    else
        echo "It's not available."
    fi
    
    • 1
  9. Bruno Bronosky
    2019-11-05T13:13:45+08:002019-11-05T13:13:45+08:00

    我喜欢使用的答案/proc/mounts,但我不喜欢做一个简单的 grep。这会给你带来误报。您真正想知道的是“是否任何行都具有字段号 2 的确切字符串”。所以,问这个问题。(在这种情况下,我正在检查/opt)

    awk -v status=1 '$2 == "/opt" {status=0} END {exit status}' /proc/mounts
    
    # and you can use it in and if like so:
    
    if awk -v status=1 '$2 == "/opt" {status=0} END {exit status}' /proc/mounts; then
      echo "yes"
    else
      echo "no"
    fi
    
    • 1
  10. Craig
    2012-10-25T05:59:24+08:002012-10-25T05:59:24+08:00

    这些都不满足给定目录是另一个挂载点中的子目录的用例。例如,您可能有 /thing,它是一个 NFS 挂载到 host:/real_thing。为此目的在 /proc/mounts /etc/mtab 或“mount”上使用 grep 将不起作用,因为您将寻找一个不存在的安装点。例如,/thing/thingy 不是挂载点,但 /thing 挂载在 host:/real_thing 上。这里投票的最佳答案实际上不是“确定目录/卷是否已安装的最佳方法”。我会投票赞成使用“df -P”(-P POSIX 标准模式)作为更清洁的策略:

    dev=`df -P /thing/thingy | awk 'BEGIN {e=1} $NF ~ /^\/.+/ { e=0 ; print $1 ; exit } END { exit e }'` && {
        echo "Mounted via: $dev"
    } || {
        echo "Not mounted"
    }
    

    运行它的输出将是:

    Mounted via: host:/real_thing
    

    如果你想知道真正的挂载点是什么,没问题:

    mp=`df -P /thing/thingy | awk 'BEGIN {e=1} $NF ~ /^\/.+/ { e=0 ; print $NF ; exit } END { exit e }'` && {
        echo "Mounted on: $mp"
    } || {
        echo "Not mounted"
    }
    

    该命令的输出将是:

    Mounted on: /thing
    

    如果您试图通过任意目录或文件列表创建某种 chroot 来镜像 chroot 外部、chroot 内的挂载点,这一切都非常有用。

    • 1

相关问题

  • 多操作系统环境的首选电子邮件客户端

  • 你最喜欢的 Linux 发行版是什么?[关闭]

  • 更改 PHP 的默认配置设置?

  • 保护新的 Ubuntu 服务器 [关闭]

  • (软)Ubuntu 7.10 上的 RAID 6,我应该迁移到 8.10 吗?

Sidebar

Stats

  • 问题 205573
  • 回答 270741
  • 最佳答案 135370
  • 用户 68524
  • 热门
  • 回答
  • Marko Smith

    SFTP 使用什么端口?

    • 6 个回答
  • Marko Smith

    从 IP 地址解析主机名

    • 8 个回答
  • Marko Smith

    如何按大小对 du -h 输出进行排序

    • 30 个回答
  • Marko Smith

    命令行列出 Windows Active Directory 组中的用户?

    • 9 个回答
  • Marko Smith

    Windows 中执行反向 DNS 查找的命令行实用程序是什么?

    • 14 个回答
  • Marko Smith

    如何检查 Windows 机器上的端口是否被阻塞?

    • 4 个回答
  • Marko Smith

    我应该打开哪个端口以允许远程桌面?

    • 9 个回答
  • Marko Smith

    什么是 Pem 文件,它与其他 OpenSSL 生成的密钥文件格式有何不同?

    • 3 个回答
  • Marko Smith

    如何确定bash变量是否为空?

    • 15 个回答
  • Martin Hope
    MikeN 在 Nginx 中,如何在维护子域的同时将所有 http 请求重写为 https? 2009-09-22 06:04:43 +0800 CST
  • Martin Hope
    Tom Feiner 如何按大小对 du -h 输出进行排序 2009-02-26 05:42:42 +0800 CST
  • Martin Hope
    0x89 bash中的双方括号和单方括号有什么区别? 2009-08-10 13:11:51 +0800 CST
  • Martin Hope
    kch 如何更改我的私钥密码? 2009-08-06 21:37:57 +0800 CST
  • Martin Hope
    Kyle Brandt IPv4 子网如何工作? 2009-08-05 06:05:31 +0800 CST
  • Martin Hope
    Noah Goodrich 什么是 Pem 文件,它与其他 OpenSSL 生成的密钥文件格式有何不同? 2009-05-19 18:24:42 +0800 CST
  • Martin Hope
    Brent 如何确定bash变量是否为空? 2009-05-13 09:54:48 +0800 CST
  • Martin Hope
    cletus 您如何找到在 Windows 中打开文件的进程? 2009-05-01 16:47:16 +0800 CST

热门标签

linux nginx windows networking ubuntu domain-name-system amazon-web-services active-directory apache-2.4 ssh

Explore

  • 主页
  • 问题
    • 最新
    • 热门
  • 标签
  • 帮助

Footer

AskOverflow.Dev

关于我们

  • 关于我们
  • 联系我们

Legal Stuff

  • Privacy Policy

Language

  • Pt
  • Server
  • Unix

© 2023 AskOverflow.DEV All Rights Reserve