从 jar 中的 属性 文件中读取特定的 属性

Read specific property from a property file in a jar

我需要从位于每个 jar 的根级别的 属性 文件 "version.properties" 中读取 属性 "product.build.number"。我天真的做法是:

  private static int getProductBuildNumber(File artefactFile) throws FileNotFoundException, IOException
  {
    try (ZipInputStream zip = new ZipInputStream(new FileInputStream(
        artefactFile)))
    {

      Set<String> possClasses = new HashSet<>();

      for (ZipEntry entry = zip.getNextEntry(); entry != null; entry = zip
          .getNextEntry())
      {
        if (!entry.isDirectory() && entry.getName().toLowerCase().equals(
            "version.properties"))
        {
          List<String> lines = IOUtils.readLines(zip, (String) null);

          for (String line : lines)
          {
            if (line.startsWith("product.build.number"))
            {
              String[] split = line.split("=");
              if (split.length == 2)
              {
                return Integer.parseInt(split[1]);
              }

            }
          }

        }
      }
    }

    throw new IOException("product.build.number not found.");

  }

我想还有更优雅、更可靠的方法。有什么想法吗?

尝试类似(未测试)的方法:

private static int getProductBuildNumber(Path artefactFilePath) throws IOException{
   try(FileSystem zipFileSystem = FileSystems.newFileSystem(artefactFilePath, null)){
      Path versionPropertiesPath = zipFileSystem.getPath("/version.properties");
      Properties versionProperties = new Properties();
      try (InputStream is = Files.newInputStream(versionPropertiesPath)){
          versionProperties.load(is);
      }
      return Integer.parseInt(versionProperties.getProperty("product.build.number"));
   }
}

您还没有说 .jar 文件是否在您的 class路径中。

如果它们在您的 class 路径中,您应该使用 Class.getResourceAsStream 来阅读条目:

try (InputStream propStream = getClass().getResourceAsStream("/version.properties")) {
    // ...
}

如果 .jar 文件不在您的 class 路径中,您应该创建一个 jar:URL 从该文件。 URL 的格式在 JarURLConnection documentation.

中描述

请注意 java.io.File 已过时,您应该始终使用 Path 代替:

private static int getProductBuildNumber(Path artefactFile)
throws IOException {
    URL propsURL = new URL("jar:" + artefactFile.toUri() + "!/version.properties");
    try (InputStream propStream = propsURL.openStream()) {
        // ...
    }
}

无论数据的位置如何,您应该始终使用 Properties class 来读取属性。 (自己解析属性文件意味着您必须考虑注释、Unicode 转义、续行和所有可能的 name/value 分隔符。)

Properties props = new Properties();
try (InputStream propStream = getClass().getResourceAsStream("/version.properties")) {
    props.load(propStream);
}

int buildNumber = Integer.parseInt(
    props.getProperty("product.build.number"));