Thanks for the feedback.

2009/8/24 Hans Dockter <[email protected]>

>
> On Aug 19, 2009, at 9:27 AM, Trond Andersen wrote:
>
> <snip>
>
>
>> Is this an example on how to approach this:
>>
>> http://docs.codehaus.org/display/GRADLE/Environment+management
>>
>
> I wasn't really aware of this page. Nor did I know about the Groovy
> ConfigSlurper class. Thanks for pointing this put and apologies to Erwan for
> not having paid attention to this.

I used it as a rough outline for what I did in my own script.

>
>
>> This confluence page was made for 0.5.x, but I guess the main concept is
>> similar for Gradle 0.7.
>>
>> With the following scenario:
>>
>> I have a gradle.properties which defines some properties:
>> service.url=http://localhost:8080/MyApp/MyService?wsdl
>> some.property=some value
>> another.property=another value
>>
>> Then I have gradle.properties.systest which defines the following
>> properties
>> service.url=http://systest/MyApp/MyService?wsdl
>> another.property=systest value
>>
>> In the gradle.properties.prod the following property are defined:
>> service.url=http://prod/MyApp/MyService?wsdl
>>
>> Are there any tools in Gradle/Groovy that can be used to accomplish so
>> that the properties which isn't overridden becomes the default value defined
>> in the gradle.properties, but whenever I override them when building for a
>> specific environment, the overridden properties get use?
>>
>
> The ConfigSlurper class seems to offer this. See:
> http://docs.codehaus.org/display/GROOVY/ConfigSlurper (under Special
> "environments" Configuration)

I found the ConfigSlurper. Really handy. Java should have something
similar.

>
>
> The question remains how Gradle should better support this in the future
> out-of-the-box.
>
> Generally there are two ways of configuring. One is via a script the other
> is via a properties file. I think we need both, as scripts are much more
> powerful but properties file are easier to modify by code (e.g. incrementing
> a version property).
>
> This is the current situation with Gradle (trunk):
>
> user specific configuration:
> ~/.gradle/gradle.properties
> ~/init.gradle (or any custom location you may specify)
>
> project specific configuration
> build.gradle
> <PROJECT_HOME>/gradle.properties
>
> The concept of environments is relevant for project specific configuration
> as well as for user specific configuration. At the moment you have to do the
> following.
>
> For project and user specific environment handling:
> 1.) start Gradle with: gradle -PtargetEnvironment=DEV
> 2.) Either use the ConfigSlurper to parse and additional config script or
> do it directly in you build script:
> build.gradle: if (targetEnvironment == DEV) { service.url=
> http://localhost:8080/MyApp/MyService?wsdl }
>
> It is a bit awkward to use environment specific property files as we don't
> offer a way yet to apply them directly to projects.
>
> Here is a proposal on how Gradle can better support profiles and general
> configuration in the future:
>
> We introduce a new command line option E:
>
> 1.) gradle -E dev,full clean compile

This is what I would expect.

>
> 2.) init.gradle and build.gradle:
>
> profiles {
>   dev {
>      url = 'x'
>   }
>   prod { ... }
>   full { .. }
> }

Fits perfectly from my perspective.

>

3.) All property files in user home and project home which end with one of
> the -E parameters are applied (in the order of declaration).
>
> 4.) A project can define a default profile.

Should Gradle maybe use the same way as ConfigSlurper handles it? Outside of
the environment {...} is the default?

>
> 5.) As it is possible to specify a custom location for init files, this
> should also be possible for gradle.properties files. Should it be possible
> to specify more than one init/property file? Should we use the same command
> line options to specify init/property files?

I prefer convention here. If there's a need for customization, I think this
should reference a task/closure/method which does the customization. For
instance - I didn't end up using property files. I just modified the web.xml
and modified the conflig-param section of the web.xml instead. In this
example the need isn't about specifying the property or init file, but more
a possibility to do custom environment handling. See below.

>
> 6.) Make it easy to apply any init/property files from a build.gradle.

Agreed.

I'm going to blog about this, but here's what I did regarding environment
specific version of web.xml:

<pre>
   ....
  def config
  if (System.properties['env.ocs'] != null) {
    logger.info("A spesific environment has been specified
${System.properties['env.ocs']}")
    config = new ConfigSlurper(System.properties['env.ocs'])
            .parse(new File(project.projectDir.path + File.separator +
'env.groovy').toURL())
  } else {
    logger.info("No specific environment has be specified")
    config = new ConfigSlurper().parse(new File(project.projectDir.path +
File.separator + 'env.groovy').toURL())
  }
  def configMap = config.flatten()

  def webApp = new XmlParser().parse(new File(webXmlPath))
  def contextParams = webApp.'context-param';
  logger.info("Found ${contextParams.size()} context parameters")

  contextParams.each { contextParam ->
    logger.info("Found param name: ${contextParam.'param-name'.text()} and
Param value: ${contextParam.'param-value'.text()}")
    def paramName = contextParam.'param-name'.text()
    if (configMap.containsKey(paramName)) {
      logger.info("Modifying ${contextParam.'param-name'.text()} to
${configMap.get(paramName)}")
      contextParam.'param-value'[0].value = [configMap.get(paramName)]
    }
  }
  ...
</pre>

By supplying the -Denv.ocs=prod the ConfigSlurper will parse the environment
specific settings.Then I parse the web.xml and modify it. With Gradle
support this would probably be much more elegant. An important point for me
is that the configuration can be other things that property files.


--------- Trond

Reply via email to