different configuration files for different server - java

Hi How would you solved that?
I have one application in which I have a few configuration files, I make war file and deploy it on the tomcat.
But at the same time I have to make the war file and deploy the same application under different context and/or a server with modified configuration files.
I can create my own task in ant, and replace needed paramaters but there can be possibility of moving to maven, and anyway I'm not sure about it. Or can I use something like spring's property place holder configurer or jgroups

Spring can handle this quite well in a variety of ways. The approach I found most useful and flexible is to setup in each environment a system variable that specifies trhe environment name e.g. test, dev, int, prod, etc.
Spring can then use this system variable to load the correct property files. Depending on your needs these property files can be bundled with the app or loaded from an external location. Theres an example of a similar approach here:
http://www.developer.com/java/ent/print.php/3811931

I'd deploy Spring apps packaged as a WAR to either Tomcat or WebLogic without any changes. It would contain both the META-INF/context.xml for Tomcat and weblogic.xml for WebLogic. No worries, no changes.

What we did was create a folder structure for the properties that were environment specific. Under that folder we created folders for each specific environment targeted for deployment, including local development. It looked like this:
Project
\
-Properties
\
-Local (your PC)
-Dev (shared dev server)
-Test (pre-production)
-Prod (Production)
In each folder we put parallel copies of the properties/config files and put the different configurations only in the file in the appropriate folder. The secret was to control the classpath of the deployment environment. We defined a PROPERTIES classpath entry on every server. On Prod, it would be set to "$ProjectDir/Properties/Prod" while on Test the same variable would be set to "$ProjectDir/Properties/Test".
This way we could have database connection strings for the dev/test/prod database preconfigured and not have to checkout/in the property file each time we wanted to build for a different environment.
This also meant that we could deploy the exact same .war/.ear file to Test and Prod without rebuilding. Any properties that weren't declared in the properties file we handled in a similar way by using the same JNDI name in each environment but using values that were specific to that environment.

http://www.gifnoc.com/config could help as it stores configuration on a central place and the client is pulling from it for different environments

Related

How pass log4j2.xml to Tomcat application

I have application which is running at Tomcat 8 server.
Application use log4j2 for internal logging.
I want to have one application.war and two different log config files like:
log4j2_dev.xml and log4j2_prod.xml depending from environment.
In production environment I want deploy application.war and use log4j2_prod.xml
And in development environment I want deploy application.war and use log4j2_dev.xml
So, how could I specify which file to use during application.war deploying?
PS.
I don't want build two different wars like
application_prod.war and application_dev.war with different configs inside.
Maybe you could specify in your build which config file to use?
E.g. -Dlog4j.configurationFile={path to file}, where path would be determined by building dev or prod?
In the $CATALINA_BASE/bin/setenv.sh file I've added the line:
export LOG4J_CONFIGURATION_FILE=/dev/log4j2_dev.xml

Best way to use configuration file in production

I'm currently working on a java project.
I already built the JAR for the project, and this JAR uses some properties files that have credentials for third party services in them.
So this program reads the configuration files from "src/main/resources". But I don't think this is the best way to bring it to production since the properties files have credentials.
My question is, what is the state of the art to deploy a JAR to production server that reads properties files that have credentials in them?
Do I just put the properties files in "src/main/resources" like I did and it's enough? Is it safe enough?
Or should I not actually push the properties files with credentials in production and there is a better way to do that?
directory
You can manage many configurations on spring-boot for each enviromment ( local, prd, hom, test... )
check this https://stackoverflow.com/a/68012400/7505687
Or you can work on each vars in .proporties overriding all values as your PRD enviromment vars are added.
eg. in application.properties
var.same-config-on-proporties=${ENV_VALUE_FROM_ENVIROMMENT:default-value-if-not-passed-from-env}

How to read different property files for different environment?

I have a web application created in maven. I am using tomcat server on my local as well as on dev unix box. I need to use two different .properties file like local.properties and dev.properties (may be in different folders). My doubt is 'How can we configure the tomcat of local and the tomcat of unix box to read different properties file at the time of deployment?' What are different ways for it.
The easiest and out of the box solution you can use with spring is to have two files, named application-dev.properties and application-prod.properties which will be activated if if you pass -Dspring.profiles.active=dev or prod. You pass this parameter when deploying the app. No configuration, no annotation, no xml. As long as you keep the naming convention application-something.properties
Easiest is pass a system parameter to your JVM to identify the environment, then package up a dev.properties and local.properties in the jar.
#PropertySource(value = {"classpath:local.properties", "classpath:${ENVX}.properties"}, ignoreResourceNotFound = true)
Use a -DENVX=dev for dev (add to your tomcat script), if it is not specified local.properties will be picked up.

Deploying war file to Tomcat with a different path

If I deploy a war file to Tomcat, called for example foo-bar-1.1.2.war, how can I deploy it so that it is extracted to webapps/bar and its URL root is /bar/...?
My intention here is to keep the war file in the webapps server with its version information so that I know which version is installed but have it overwrite a previous version of the app.
I could deploy the war file using PSI Probe. This would allow me to specify a target context for the web app. However, it means that I would lose any version information in the war file name.
Tomcat will always extract the contents of a war file, to a folder of the same name (when it's configured to deploy wars - as default etc.).
You can extract it to a folder name of your choice. So if you unzip the contents of foo.war to a folder called bar/ manually, instead of just dropping the war into the web apps folder, it'll still load the web application.
However, this is totally unnecessary as you can specify the URL pattern of the application without messing with the folder / war file name at all by overriding the context root element for your application:
This is often set in the Tomcat server.xml - but that practice is fairly widely discouraged. Instead, I'd suggest you use context.xml in the META-INF folder of your web application / war file:
<Context path="/bar" .../>
When the application is deployed, the context.xml should be copied to /conf/Catalina/localhost but renamed to foo.xml
Note that conext roots must be unique and there are some additional considerations if you're using the autoDeploy or deployOnStartup operations (Source http://tomcat.apache.org/tomcat-7.0-doc/config/context.html).
Other options include:
Clean the web apps folder each deployment and drop your new foo-1.1.0 war in.
Include the version number in a flat file. foo/version1
Or simply include the version in a config / XML file.
You could also use Ant (or an equivalent tool) to automate your deployments (and perform any of the above).
There is an important point to emphasize about the path attribute of the context fragment definition. To cite the documentation on the topic:
When autoDeploy or deployOnStartup operations are performed by a Host, the name and context path of the web application are derived from the name(s) of the file(s) that define(s) the web application.
deployOnStartup is the default behavior of Tomcat hosts.
To follow the documentation, this has a very important consequence:
the context path may not be defined in a META-INF/context.xml
According to the ways of defining a Tomcat context, this lets only two solutions:
In individual files (with a ".xml" extension) in the $CATALINA_BASE/conf/[enginename]/[hostname]/ directory
Inside a Host element in the main conf/server.xml, which is a discouraged solution in a production environment as it requires restarting the server
Another solution takes advantage of the unpackWARs attribute.
In my point of view, for these reasons, the general and easy way to implement a subtle path in a production environment is taking advantage of the naming of war files (what could include versions management and be a solution to your problem). A single sharp (e.g. test#path.war) in the war file names implies a segment in the context path (e.g. /test/path). A double sharp introduces the version number (e.g. test#path##112.war). This works whether or not unpacking war files, hot deployment or not, is deployment agnostic (manager or file system) and manages multiples versions of a same archive.
But if there is the need to have a path distinct from the archive name, it seems the only solution is the descriptor in the /conf/[enginename]/[hostname]/ directory or the server.xml file. For these, you need an access to the server filesystem.
The relevant solution is highly related to the way Tomcat is configured and managed in the everyday.
If you just want to include a version info in your war file name, you can name it like: my-app##1.2.3.war. It gets unpacked to the directory my-app##1.2.3 but the context will be just my-app (i.e. http://host/my-app/).
Works at least with Tomcat 7.0.55

log4j is not working in weblogic server?

I am using weblogic 10.3.4, I am trying to write log with log4j. but at runtime my application is not getting any log4j.properties. even this is not generating any warning as "initialization of log4j has error".
I have tried my properties file to put in src folder, classes folder and then I created one jar and put it in domain lib. still its not picking. even when I am writing log with same jar in standalone application, its working fine.
please help me with valuable suggestions.
I tried the solution proposed at Oracle forums.
Excerpt from that link at Oracle forums:
I've only modified the scritp startWebLogic.cmd:
set LOG4J_CONFIG_FILE=log4j.xml
set SAVE_JAVA_OPTIONS=%JAVA_OPTIONS% -Dlog4j.configuration=%LOG4J_CONFIG_FILE%
#REM set SAVE_CLASSPATH=%CLASSPATH%
set SAVE_CLASSPATH=%CLASSPATH%;C:\Oracle\Middleware\user_projects\domains\domain\config
In this way I've put all the config folder inside the classpath, and I can use it in future to hold other libraries configuration files (for example oracle coherence config).
I tried this approach on a different properties file as well and that worked well!
You need to either specify where the application should find its log4j.properties, or put it onto the classpath of the application. Where the classpath is varies, but in general WEB-INF/classes should work. Other options depend upon how you're deploying the application.
A better long term strategy is to configure your system so that you can change the log4j.properties depending upon the environment. When you're in production, you won't want all of the debug information to appear. Look at the answer to this question or this question for more ideas. One strategy is to define a variable on the command line which gets picked up and defines a directory which contains your configuration files. This works for Tomcat, but there may be other, better, strategies for Weblogic.
It is not a good idea to change the configuration of your server, in particular, don't replace the log4j.jar or log4j.properties in your server directories. The server will depend upon the version that it was designed to use, which may or may not be the same as your version. You can do everything you need to do by changing the war that you're deploying.
I have used this code:
ClassLoader cl = this.getClass().getClassLoader();
URL log4jCfg = cl.getResource(configFile);
if (log4jCfg != null) {
DOMConfigurator.configure(log4jCfg);
}
log.info("log4j is now working on Web App.");
In my case, we used XML configuration:
log4jCfg = "mylog4j.xml";
In WebLogic, we were able to place such file (mylog4j.xml), equivalent to your log4j.properties file, at WebLogic's domain path (specific to the domain were we deploy). This means that domain folder belongs to your application's path. I just tested it with Web applications, I'm not sure if with SOA or EJB projects it works the same way.
When you deploy any application on any server that application should use servers log4j jar.
So if you have added any log4j jar in your application jar/tar/ear, remove it and copy log4j.properties file in the conf folder of the server from where server is picking its configuration files. Or just copy your log4j property content in servers log4j property file.

Categories

Resources