Issue with spring profile not being picked properties value from server env? - java

I have configured spring.profiles.active environment variable into websphere server and using variable value into spring config file.
My Config.xml is like
<bean id="propertiesUtil" class="common.PropertiesUtil">
<property name="locations">
<list>
<value>classpath:common.properties</value>
<value>classpath:${spring.profiles.active}/env_${spring.profiles.active}_config.properties</value>
</list>
</property>
and getting exception while deploying application into WAS is like :
Caused by: java.io.FileNotFoundException: class path resource
[${spring.profiles.active}/env_${spring.profiles.active}_config.properties]
cannot be opened because it does not exist
pls let me know if i missed anything?

Thanks,
It's working, I have fetched value of spring.profiles.active variable from WAS environment and stored into context scope.

Related

set properties by vm-option in tomcat (local)

I have some question.
Before format My intellij is work very well.
I manage some value for multiple environment and control by some properties file.
Here is some sample.
I have some file for properties like this.
production.properties
test.properties
test-remote.properties
And my tomcat configuration (of course VM options) set like this.
... -Drun.mode=test ...
And here is my root-context.xml.
...
<!-- Root Context: defines shared resources visible to all other web components -->
<bean
class="org.springframework.beans.factory.config.PropertyPlaceholderConfigurer">
<property name="locations">
<list>
<value>classpath:${run.mode}.properties</value>
</list>
</property>
</bean>
...
Before format, as i say, if change the tomcat's vmoption -Drun.mode=SOMETHING, that works. but after format, there is only work test properties.
have you guys any idea about it? I can't imagine even how can i fix it.
Very interesting point is that. test is work well.
But there is not hardcoding for just only use test.properties.
There is a different that tomcat's version.
usually i use 8.5.x and after format i used 9.0.x and there have some ClassNotFound Exception.
After change to use tomcat 8.5.x problem is gone.
But have to figure out why 9.0.x is not running for Properties file select by VM options.

Not able to find Spring "classpath:" location

I have a Spring Project where I am using bean configuration file
beans.xml.Inside the bean Configuration file, i have defined some properties for a PlaceHolder which refers to classPath...While the application is running, the properties are getting loaded from /unknownPath/Dev/Loc1/System.properties
Where
${BUS_ENV}=Dev
${LOCATION1}=Loc1
<bean id="placeholderProperties" class="org.springframework.beans.factory.config.PropertyPlaceholderConfigurer">
<property name="locations">
<list>
<value>classpath:${BUS_ENV}/${LOCATION1}/system.properties</value>
<value>classpath:${BUS_ENV}/lbsprocessor.properties</value>
</list>
</property>
<!-- Force system properties to override any deployed runtime properties -->
<property name="systemPropertiesModeName" value="SYSTEM_PROPERTIES_MODE_OVERRIDE"/>
<property name="ignoreUnresolvablePlaceholders" value="true" />
</bean>
I didn't specify classpath while running my project in IDE
I don't have those files in my resource folder
There are around 65 such files exists(for various reasons) as Dev/Loc1/System.properties
I am not able to find from which location the properties are getting referred. Even after debugging, I couldn't find out what classpath refers to. Please help me with figuring out
If you are using eclipse IDE right click on your project select properties then select Java Build Path. On first tab Source there is one input named Default Output folder that value is your classpath. Check all your properties files are there in that path.
Referring to your point 2 problems might be in these line
<value>classpath:${BUS_ENV}/${LOCATION1}/system.properties</value>
<value>classpath:${BUS_ENV}/lbsprocessor.properties</value>
You are using classpath for file location which means these properties file have to be in the .war file at /Dev/Loc1/System.properties
If properties files are outside of project may be at system level you can access them like this
<value>file:${BUS_ENV}/${LOCATION1}/system.properties</value>
<value>file:${BUS_ENV}/lbsprocessor.properties</value>
eg:
<value>file:/home/testuser/system.properties</value>
I am using Mac OS ,in this we are storing the Configurations as a jar file under
/Library/Java/Extension.So java is directly referring classpath to that location by default.

Did the contextPath is available as a placeHolder for defining the path of a properties files

Let start with some context:
Tomcat container
Autodeploy of war
No Context.xml in tomcat (at least yet)
Two (identical) war deploy with two different context (ROOT.war, test.war, why not one war per feature branch)
Some properties should be different (overwrite) for the two war.
I use something like this for properties:
<bean id="properties" class="org.springframework.beans.factory.config.PropertiesFactoryBean">
<property name="ignoreResourceNotFound" value="true"/>
<property name="locations">
<list>
<value>classpath:internal-common.properties</value>
<value>classpath:${server.contextPath}/context.properties</value>
<value>classpath:dev-overwrite.properties</value>
</list>
</property>
The internal-common and the dev-overwrite work as expected.
I can't found the correct placeHolder (not ${server.contextPath} at least) to have an external properties per context.
What I think can't work and are on lot of answer related to this:
use "env". The two WAR share the same tomcat instance, so the same env
system properties, same reason
have different properties name, I don't want as I want the same war
use the from tomcat. If I can avoid it, this will simplify my process.
extend spring properties object will work also, but I wanted to be sure they are nos easier/simplest solution for this.
Ideally, any placeholder with contextPath information will do the trick.

How to externalize properties file for web application(war)?

I have developed a webapplication which is having jsp and java code. Right now I have placed all the key-value into a env/lifecycle specific properties file (like conf-dev.properties,conf-stg.properties,conf-prod.properties).
I want to externalize these properties file so that it can be placed outside of war(without effecting the war).
right now war file is tightly coupled with properties file. if i have to modify any thing i have to build and make war and deploy.
I have very limited access on deployment server machine (only have access for one folder where i can put my configuration files) & deployment process is handled by CI(jenkin & automated script).
I explored on internet and came to know that we can achieve this using spring, would like to know what is the best way to achieve this?
As you are using Spring I suppose you already use PropertyPlaceholderConfigurer. If not you should ;)
The location of a property file can be anything that can be resolved as spring Resource. This includes classpath, servletcontext and also file references as URIs (file:///... For absolute paths)
https://docs.spring.io/spring/docs/current/javadoc-api/org/springframework/beans/factory/config/PropertyPlaceholderConfigurer.html
<bean id="propertyConfigurer" class="org.springframework.beans.factory.config.PropertyPlaceholderConfigurer">
<property name="location" value="${config.file.location}" />
</bean>
If I understand your question, then you can use Class.getResourceAsStream(String) the linked Javadoc says (in part)
This method delegates to this object's class loader. If this object was loaded by the bootstrap class loader, the method delegates to ClassLoader.getSystemResourceAsStream(java.lang.String).
The better way to externalize env specific properties is to use "user.home" or "user.dir".
Thanks #Martin F..
Resolved:This is the final one i used and its working fine in dev,stage Env.
<bean id="propertyConfigurer" class="org.springframework.beans.factory.config.PropertyPlaceholderConfigurer">
<property name="ignoreUnresolvablePlaceholders" value="false"/>
<property name="order" value="1"/>
<property name="locations">
<list>
<value>classpath:conf-${cisco.life}.properties</value>
<value>file:///${openshift.home}/data/conf-${cisco.life}.properties</value>
<value>file:${openshift.home}/data/conf-${cisco.life}.properties</value>
</list>
</property>
</bean>.
and i used script action hook in openshift to set the lifecycle on system level.
appname=echo $OPENSHIFT_APP_NAME
case "$appname" in
*dev)export JAVA_OPTS_EXT="${JAVA_OPTS_EXT} -Dcisco.life=dev";
echo "setting up env life dev for " $appname
;;
*stage)export JAVA_OPTS_EXT="${JAVA_OPTS_EXT} -Dcisco.life=stg;
echo "setting up env life as stg for " $appname.

how spring property resolver works?

I have property place holder in my spring context.xml file
<bean id="propertyConfigurer" class="com.techpleiad.poc.RMCPropertyUtil">
<property name="basenames" value="file:${config.file.dir}/prop_application" />
<property name="defaultEncoding" value="UTF-8" />
<property name="cacheSeconds" value="30"></property>
</bean>
and this property 'config.file.dir' is not getting resolved.
'config.file.dir' is the environment variable and when i debug the code and check for the basename the file path comes as it is.. '{config.file.dir}/prop_application'
I need to know what spring code/classes are involved in resolving such properties.
How i could debug and resolve this problem?
You'll need to register a PropertySourcesPlaceholderConfigurer with a reference to your property sources (or not since this is an environment property which are implicitly added).
With XML you can do that with
<context:property-placeholder location="classpath:spring.properties" />
With Java config, simply define a static #Bean annotated method which returns a PropertySourcesPlaceholderConfigurer.
You can try with Spring SpEL to get the system properties
#{systemProperties['config.file.dir']}
To read environment variable use
#{systemEnvironment['config.file.dir']}
The systemEnvironment property contains all the environment variables on the machine where the program is running. Meanwhile, the systemProperties contains all the properties that we set in Java when the application started, using the -D argument.

Categories

Resources