--- title: Environment --- # Working with environments Environment is a VRaptor's feature that allow you to define different components and settings based on the environment like: production, testing, development, and so on. You can, for example, deactivate the e-mail service in the development environment and enable only in production. ## How to configure There are 3 ways to configure your environment. The first way is adding the lines below in your `web.xml`. As example, you can configure the environment name as `PRODUCTION`: ~~~ #!xml br.com.caelum.vraptor.environment PRODUCTION ~~~ The second way is adding a JVM property. For this you can start your Application Server or Servlet Container with this JVM parameter: ~~~ #!properties -Dbr.com.caelum.vraptor.environment=PRODUCTION ~~~ And the third option is setting an environment variable under your Operating System, simple adding the `VRAPTOR_ENV` variable. Windows example: ~~~ set VRAPTOR_ENV=PRODUCTION ~~~ Unix example: ~~~ export VRAPTOR_ENV=PRODUCTION ~~~ **Note:** The environment variable of Operating System have more priority than JVM properties, that have more priority than `web.xml` configuration. So, as example, if your application uses both `web.xml` and JVM properties, the configuration over `web.xml` will ignored. ## Setting an environment properties You only need to create a properties file with the name of your environment in your classpath. As example, to set the properties for `PRODUCTION` environment you only need to create a file called `production.properties` like this: ~~~ #!properties test_environment=false email=production.mail@mail.com ~~~ If you have a common properties for other environments you can create a file called `environment.properties` with these common properties. So VRaptor will ask for properties first in the environment file, and if not found, will ask in the `environment.properties` file. You can also override properties using System Properties. Properties defined by System Properties will override any other definitions. **Note:** You can only use System Properties to override existing properties in property files and not to define a new one. Considering that you have the environment.properties below: ~~~ #!properties my.prop hello ~~~ You can override the existing my.prop with a System Property like this: ~~~ #!java System.setProperty("my.prop", "bye"); environment.get("my.prop"); //bye ~~~ If the key doesn't exists in properties file, get method will throw a NoSuchElementException. ## Getting environment properties in your code There are two methods to get the properties: `get` and `getOrDefault`. The first method returns the property value if the value exists, or an `MissingResourceException` if not found. And with `getOrDefault` you can return a default value if the key is not found. Take a look in the code below: ~~~ #!java @Controller public class MyController { private final Environment environment; private final MailSender sender; /** * @deprecated CDI eyes only */ protected MyController(){ this(null, null); } @Inject public MyController(Environment environment, MailSender sender) { this.environment = environment; this.sender = sender; } public void sendMail(String email) { if(environment.isDevelopment()) { sender.sendMailTo(environment.get("email")); } else { sender.sendMailTo(email); } } } ~~~ In the code above, `environment.get("email")` we will get the property `email`. But if this property is not always present, we can use the `getOrDefault` method to return a default value. ~~~ #!java public void sendMail(String email) { if(environment.isDevelopment()) { sender.sendMailTo(environment.getOrDefault("email"), "noreply@vraptor.org"); } else { sender.sendMailTo(email); } } ~~~ ## Getting environment properties in your JSP ~~~ #!jsp

You are now in the test environment. Your actions here will not affect the system.

Send an e-mail to: ${environment.get('email')} ~~~ ## Accessing configuration files according to the environment If you need to access a file in a different setting for your libraries according to your environment, you can also use the environemnt. Just put, for example, your `hibernate.cfg.xml` under directories located with the name of your environment: *development* and *production* (for example). `Environment.getResource (...)` returns the resource according to your current environment: ~~~ #!java cfg = new AnnotationConfiguration(); cfg.configure(environment.getResource("/hibernate.cfg.xml")); ~~~ To keep compatibility with applications that don't not environment, if the file isn't found in the directory with the name of the environment, it will be loaded from classpath. ## Injecting the value of your configuration programmatically You can also inject your settings programmatically using `@Property` annotation, like: ~~~ #!java @Controller public class MyController { @Inject @Property("email") private String email; public void sendMail(String email) { sender.sendMailTo(email); } } ~~~ If your environment is `DEVELOPMENT`, the value for key `email` will be loaded using `development.properties`. And if your environment is `PRODUCTION` the value will be loaded from `production.properties`. This feature allow you to keep away from conditional statements like: `if (environment.isDevelopment ()) {...}` in your code. And if the field name is the same from the key, you can use only the `@Property` annotation without define a value, like this: ~~~ #!java @Controller public class MyController { @Inject @Property private String email; public void sendMail(String email) { sender.sendMailTo(email); } } ~~~ You can also set a default value for this property: ~~~ #!java @Inject @Property(defaultValue = "config.properties") private String fileName; ~~~