有 Java 编程相关的问题?

你可以在下面搜索框中键入要查询的问题!

java如何从Maven中的属性文件生成枚举?

原名是 “如何使用ant从属性文件生成枚举?”

我想迭代所有属性并生成包含所有属性的枚举类

我正在考虑编写自定义任务,但我想我需要将其放入额外的jar中:|

我正在使用maven,我想在生成源代码阶段使用它


共 (2) 个答案

  1. # 1 楼答案

    虽然我在某种程度上同意Peter Tilemans,但我也受到了这个问题的诱惑,我使用groovy和GMaven-Plugin创建了一个解决方案编辑:GMaven最棒的一点是,您可以直接访问maven对象模型,而无需先创建插件,并且仍然拥有groovy的全部编程能力

    在这种情况下,我要做的是创建一个名为src/main/groovy的源文件夹,它不是实际构建过程的一部分(因此不会对jar/war等产生影响)。在那里,我可以放置groovy源文件,从而允许eclipse将它们用作groovy源文件夹,用于自动完成等,而无需更改构建

    所以在这个文件夹中我有三个文件:EnumGenerator。groovy,enumTemplate。txt和enum。属性(为了简单起见,我这样做了,您可能会从其他地方获得属性文件)

    这是:

    枚举生成器。groovy

    import java.util.Arrays;
    import java.util.HashMap;
    import java.util.TreeMap;
    import java.io.File;
    import java.util.Properties;
    
    class EnumGenerator{
    
        public EnumGenerator(
            File targetDir, 
            File propfile,
            File templateFile,
            String pkgName,
            String clsName 
        ) {
            def properties = new Properties();
            properties.load(propfile.newInputStream());
            def bodyText = generateBody( new TreeMap( properties) );
            def enumCode = templateFile.getText();
            def templateMap = [ body:bodyText, packageName:pkgName, className: clsName  ];
            templateMap.each{ key, value -> 
                                    enumCode = enumCode.replace( "\${$key}", value ) } 
            writeToFile( enumCode, targetDir, pkgName, clsName )
        }
    
        void writeToFile( code, dir, pkg, cls ) {
            def parentDir = new File( dir, pkg.replace('.','/') )
            parentDir.mkdirs();
            def enumFile = new File ( parentDir, cls + '.java' )
            enumFile.write(code)
            System.out.println( "Wrote file $enumFile successfully" )
        }
    
        String generateBody( values ) {
    
            // create constructor call PROPERTY_KEY("value")
            // from property.key=value
            def body = "";
            values.eachWithIndex{
                key, value, index ->
                    body += 
                    ( 
                        (index > 0 ? ",\n\t" : "\t")
                        + toConstantCase(key) + '("' + value + '")'
                    )   
            }
            body += ";";
            return body;
    
        }
    
        String toConstantCase( value ) {
            // split camelCase and dot.notation to CAMEL_CASE and DOT_NOTATION
            return Arrays.asList( 
                value.split( "(?:(?=\\p{Upper})|\\.)" ) 
            ).join('_').toUpperCase();
        }
    
    }
    

    枚举模板。txt

    package ${packageName};
    
    public enum ${className} {
    
    ${body}
    
        private ${className}(String value){
            this.value = value;
        }
    
        private String value;
    
        public String getValue(){
            return this.value;
        }
    
    }
    

    枚举。属性

    simple=value
    not.so.simple=secondvalue
    propertyWithCamelCase=thirdvalue
    

    以下是pom配置:

    <plugin>
        <groupId>org.codehaus.groovy.maven</groupId>
        <artifactId>gmaven-plugin</artifactId>
        <version>1.0</version>
        <executions>
            <execution>
                <id>create-enum</id>
                <phase>generate-sources</phase>
                <goals>
                    <goal>execute</goal>
                </goals>
                <configuration>
                    <scriptpath>
                        <element>${pom.basedir}/src/main/groovy</element>
                    </scriptpath>
                    <source>
                        import java.io.File
                        import EnumGenerator
    
                        File groovyDir = new File( pom.basedir,
                          "src/main/groovy")
                        new EnumGenerator(
                            new File( pom.build.directory,
                              "generated-sources/enums"),
                            new File( groovyDir,
                              "enum.properties"),
                            new File( groovyDir,
                              "enumTemplate.txt"),
                            "com.mycompany.enums",
                            "ServiceProperty" 
                        );
    
                    </source>
                </configuration>
            </execution>
        </executions>
    </plugin>
    

    结果如下:

    package com.mycompany.enums;
    
    public enum ServiceProperty {
    
        NOT_SO_SIMPLE("secondvalue"),
        PROPERTY_WITH_CAMEL_CASE("thirdvalue"),
        SIMPLE("value");
    
        private ServiceProperty(String value){
            this.value = value;
        }
    
        private String value;
    
        public String getValue(){
            return this.value;
        }
    
    }
    

    使用该模板,可以自定义枚举以满足您的需要。由于gmaven在maven中嵌入了groovy,您不必安装任何东西或更改构建配置

    唯一需要记住的是,您需要使用buildhelper插件来add the generated source folder到构建

  2. # 2 楼答案

    我强烈建议你重新考虑一下

    您有可能最终对来自配置文件的值进行硬编码,这些值可能随时更改

    我认为,围绕HashMap或BidiMap读取属性文件的一个小包装类将获得几乎相同的好处,开发人员以后也不会因为属性文件中的一个小更改而发现大量编译错误

    我已经完成了我的代码生成工作。它们非常适合解析器和协议处理程序,但对于我不幸使用它们的每一个其他用例,它们都是定时炸弹