如何在 Unix 上获取 Java 中所有已安装文件系统的列表?

声明:本页面是StackOverFlow热门问题的中英对照翻译,遵循CC BY-SA 4.0协议,如果您需要使用它,必须同样遵循CC BY-SA许可,注明原文地址和作者信息,同时你必须将它归于原作者(不是我):StackOverFlow 原文地址: http://stackoverflow.com/questions/14430825/
Warning: these are provided under cc-by-sa 4.0 license. You are free to use/share it, But you must attribute it to the original authors (not me): StackOverFlow

提示:将鼠标放在中文语句上可以显示对应的英文。显示中英文
时间:2020-10-31 16:13:40  来源:igfitidea点击:

How can I get a list of all mounted filesystems in Java on Unix?

javaunixfilesystems

提问by Andrew

I'm running Java on a Unix platform. How can I get a list of all mounted filesystems via the Java 1.6 API?

我在 Unix 平台上运行 Java。如何通过 Java 1.6 API 获取所有已安装文件系统的列表?

I've tried File.listRoots()but that returns a single filesystem (that is, /). If I use df -hI see more than that:

我试过,File.listRoots()但它返回一个单一的文件系统(即/)。如果我使用,df -h我会看到更多:

Filesystem      Size   Used  Avail Capacity   iused     ifree %iused  Mounted on
/dev/disk0s2   931Gi  843Gi   87Gi    91% 221142498  22838244   91%   /
devfs          187Ki  187Ki    0Bi   100%       646         0  100%   /dev
map -hosts       0Bi    0Bi    0Bi   100%         0         0  100%   /net
map auto_home    0Bi    0Bi    0Bi   100%         0         0  100%   /home
/dev/disk1s2   1.8Ti  926Gi  937Gi    50% 242689949 245596503   50%   /Volumes/MyBook
/dev/disk2     1.0Gi  125Mi  875Mi    13%     32014    223984   13%   /Volumes/Google Earth

I would expect to see /homeas well (at a minimum).

我也希望看到/home(至少)。

回答by Erik Martino

In Java7+ you can use nio

在 Java7+ 中你可以使用 nio

import java.io.IOException;
import java.nio.file.FileStore;
import java.nio.file.FileSystems;

public class ListMountedVolumesWithNio {
   public static void main(String[] args) throws IOException {
      for (FileStore store : FileSystems.getDefault().getFileStores()) {
         long total = store.getTotalSpace() / 1024;
         long used = (store.getTotalSpace() - store.getUnallocatedSpace()) / 1024;
         long avail = store.getUsableSpace() / 1024;
         System.out.format("%-20s %12d %12d %12d%n", store, total, used, avail);
      }
   }
}

回答by Cozzamara

Java doesn't provide any access to mount points. You have to run system command mountvia Runtime.exec()and parse its output. Either that, or parse the contents of /etc/mtab.

Java 不提供对挂载点的任何访问。你必须运行系统命令mount通过Runtime.exec()并分析其输出。要么,要么解析/etc/mtab.

回答by mombip

OSHI (Operating System and Hardware Information library for Java) can be useful here: https://github.com/oshi/oshi.

OSHI(Java 操作系统和硬件信息库)在这里很有用:https: //github.com/oshi/oshi

Check out this code:

看看这个代码:

@Test
public void test() {

    final SystemInfo systemInfo = new SystemInfo();
    final OSFileStore[] fileStores = systemInfo.getOperatingSystem().getFileSystem().getFileStores();
    Stream.of(fileStores)
    .peek(fs ->{
        System.out.println("name: "+fs.getName());
        System.out.println("type: "+fs.getType() );
        System.out.println("str: "+fs.toString() );
        System.out.println("mount: "+fs.getMount());
        System.out.println("...");
    }).count();

}

回答by Rinat Mukhamedgaliev

You can try use follow method for resolve issue:

您可以尝试使用以下方法解决问题:

My code

我的代码

public List<String> getHDDPartitions() {
    try {
        BufferedReader bufferedReader = new BufferedReader(new InputStreamReader(new FileInputStream("/proc/mounts"), "UTF-8"));
        String response;
        StringBuilder stringBuilder = new StringBuilder();
        while ((response = bufferedReader.readLine()) != null) {
            stringBuilder.append(response.replaceAll(" +", "\t") + "\n");
        }
        bufferedReader.close();
        return Lists.newArrayList(Arrays.asList(stringBuilder.toString().split("\n")));
    } catch (IOException e) {
        LOGGER.error("{}", ExceptionWriter.INSTANCE.getStackTrace(e));
    }
    return null;
}

public List<Map<String, String>> getMapMounts() {
    List<Map<String, String>> resultList = Lists.newArrayList();
    for (String mountPoint : getHDDPartitions()) {
        Map<String, String> result = Maps.newHashMap();
        String[] mount = mountPoint.split("\t");
        result.put("FileSystem", mount[2]);
        result.put("MountPoint", mount[1]);
        result.put("Permissions", mount[3]);
        result.put("User", mount[4]);
        result.put("Group", mount[5]);
        result.put("Total", String.valueOf(new File(mount[1]).getTotalSpace()));
        result.put("Free", String.valueOf(new File(mount[1]).getFreeSpace()));
        result.put("Used", String.valueOf(new File(mount[1]).getTotalSpace() - new File(mount[1]).getFreeSpace()));
        result.put("Free Percent", String.valueOf(getFreeSpacePercent(new File(mount[1]).getTotalSpace(), new File(mount[1]).getFreeSpace())));
        resultList.add(result);
    }
    return resultList;
}

private Integer getFreeSpacePercent(long total, long free) {
    Double result = (Double.longBitsToDouble(free) / Double.longBitsToDouble(total)) * 100;
    return result.intValue();
}

回答by user229487

You can call the getmntent function (use "man getmntent" to get more information) using JNA.

您可以使用 JNA 调用 getmntent 函数(使用“man getmntent”来获取更多信息)。

Here is some example code to get you started:

以下是一些示例代码,可帮助您入门:

import java.util.Arrays;
import java.util.List;

import com.sun.jna.Library;
import com.sun.jna.Native;
import com.sun.jna.Pointer;
import com.sun.jna.Structure;

public class MntPointTest {
    public static class mntent extends Structure {
        public String mnt_fsname; //Device or server for filesystem
        public String mnt_dir; //Directory mounted on
        public String mnt_type; //Type of filesystem: ufs, nfs, etc.
        public String mnt_opts;
        public int mnt_freq;
        public int mnt_passno;

        @Override
        protected List getFieldOrder() {
            return Arrays.asList("mnt_fsname", "mnt_dir", "mnt_type", "mnt_opts", "mnt_freq", "mnt_passno");
        }
    }

    public interface CLib extends Library {
        CLib INSTANCE = (CLib) Native.loadLibrary("c", CLib.class);

        Pointer setmntent(String file, String mode);
        mntent getmntent(Pointer stream);
        int endmntent(Pointer stream);
    }

    public static void main(String[] args) {
        mntent mntEnt;
        Pointer stream = CLib.INSTANCE.setmntent("/etc/mtab", "r");
        while ((mntEnt = CLib.INSTANCE.getmntent(stream)) != null) {
            System.out.println("Mounted from: " + mntEnt.mnt_fsname);
            System.out.println("Mounted on: " + mntEnt.mnt_dir);
            System.out.println("File system type: " + mntEnt.mnt_type);
            System.out.println("-------------------------------");
        }

        CLib.INSTANCE.endmntent(stream);
    }
}

回答by Andrew

I was already on the way to using mountwhen @Cozzamara pointed out that's the way to go. What I ended up with is:

mount当@Cozzamara 指出这是要走的路时,我已经开始使用了。我最终得到的是:

    // get the list of mounted filesystems
    // Note: this is Unix specific, as it requires the "mount" command
    Process mountProcess = Runtime.getRuntime ().exec ( "mount" );
    BufferedReader mountOutput = new BufferedReader ( new InputStreamReader ( mountProcess.getInputStream () ) );
    List<File> roots = new ArrayList<File> ();
    while ( true ) {

        // fetch the next line of output from the "mount" command
        String line = mountOutput.readLine ();
        if ( line == null )
            break;

        // the line will be formatted as "... on <filesystem> (...)"; get the substring we need
        int indexStart = line.indexOf ( " on /" );
        int indexEnd = line.indexOf ( " ", indexStart );
        roots.add ( new File ( line.substring ( indexStart + 4, indexEnd - 1 ) ) );
    }
    mountOutput.close ();