Properties.store() - 抑制时间戳注释

时间:2011-05-31 07:34:11

标签: java properties

是否可以强制Properties不在前面添加日期评论?我的意思是这里的第一行:

#Thu May 26 09:43:52 CEST 2011
main=pkg.ClientMain
args=myargs

我想完全摆脱它。我需要我的配置文件是差异相同的,除非有有意义的更改。

6 个答案:

答案 0 :(得分:10)

不要猜。此时间戳打印在private method on Properties中,并且没有控制该行为的属性。

只有我想到的想法:子类Properties,覆盖store并复制/粘贴store0方法的内容,以便不会打印日期评论。

- 提供自定义BufferedWriter,打印所有第一行(如果您添加真实评论,则会失败,因为之前会打印自定义评论时间戳......)

答案 1 :(得分:10)

鉴于源代码或属性,不,这是不可能的。顺便说一句,因为Properties实际上是一个哈希表,因为它的键没有排序,所以你不能依赖于属性总是以相同的顺序。

如果我有此要求,我会使用自定义算法来存储属性。使用Properties的源代码作为入门者。

答案 2 :(得分:5)

基于https://stackoverflow.com/a/6184414/242042这里是我编写的实现,它删除了第一行并对键进行了排序。

public class CleanProperties extends Properties {
    private static class StripFirstLineStream extends FilterOutputStream {

        private boolean firstlineseen = false;

        public StripFirstLineStream(final OutputStream out) {
            super(out);
        }

        @Override
        public void write(final int b) throws IOException {
            if (firstlineseen) {
                super.write(b);
            } else if (b == '\n') {
                firstlineseen = true;
            }
        }

    }

    private static final long serialVersionUID = 7567765340218227372L;

    @Override
    public synchronized Enumeration<Object> keys() {
        return Collections.enumeration(new TreeSet<>(super.keySet()));
    }

    @Override
    public void store(final OutputStream out, final String comments) throws IOException {
        super.store(new StripFirstLineStream(out), null);
    }
}

清洁看起来像这样

    final Properties props = new CleanProperties();
    try (final Reader inStream = Files.newBufferedReader(file, Charset.forName("ISO-8859-1"))) {
        props.load(inStream);
    } catch (final MalformedInputException mie) {
        throw new IOException("Malformed on " + file, mie);
    }
    if (props.isEmpty()) {
        Files.delete(file);
        return;
    }

    try (final OutputStream os = Files.newOutputStream(file)) {
        props.store(os, "");
    }

答案 3 :(得分:1)

如果您尝试在给定的xxx.conf文件中进行修改,那将非常有用。

用于在商店方法中跳过第一行(#Thu May 26 09:43:52 CEST 2011)的write方法。 write方法一直运行到第一行结束。之后它会正常运行。

public class CleanProperties extends Properties {
    private static class StripFirstLineStream extends FilterOutputStream {

        private boolean firstlineseen = false;

        public StripFirstLineStream(final OutputStream out) {
            super(out);
        }

        @Override
        public void write(final int b) throws IOException {
            if (firstlineseen) {
                super.write(b);
            } else if (b == '\n') {
                // Used to go to next line if did use this line
                // you will get the continues output from the give file
                super.write('\n');

                firstlineseen = true;
            }
        }

    }


    private static final long serialVersionUID = 7567765340218227372L;

    @Override
    public synchronized Enumeration<java.lang.Object> keys() {
        return Collections.enumeration(new TreeSet<>(super.keySet()));
    }

    @Override
    public void store(final OutputStream out, final String comments)
        throws IOException {
        super.store(new StripFirstLineStream(out), null);
    }
}

答案 4 :(得分:0)

当发生有意义的配置更改时,您是否只能在应用程序中标记,如果设置了该文件,则只写入文件?

您可能希望查看Commons Configuration,它在编写和阅读属性文件等内容时具有更大的灵活性。特别是,它有一些方法试图将完全相同的属性文件(包括间距,注释等)写为现有的属性文件。

答案 5 :(得分:0)

您可以通过关注以下Stack Overflow帖子来解决此问题,以保持顺序:

以标准顺序书写: How can I write Java properties in a defined order?

然后将属性写入字符串,并根据需要删除注释。最后写入文件。

ByteArrayOutputStream baos = new ByteArrayOutputStream();
properties.store(baos,null);

String propertiesData = baos.toString(StandardCharsets.UTF_8.name());

propertiesData = propertiesData.replaceAll("^#.*(\r|\n)+",""); // remove all comments

FileUtils.writeStringToFile(fileTarget,propertiesData,StandardCharsets.UTF_8);

// you may want to validate the file is readable by reloading and doing tests to validate the expected number of keys matches
InputStream is = new FileInputStream(fileTarget);
Properties testResult = new Properties();
testResult.load(is);