43

I'm fairly new to spring so excuse me if this is a dumb question. When I try to launch a program I get the following error: java.lang.IllegalArgumentException: Could not resolve placeholder 'appclient' in string value [${appclient}]. The error is thrown when the following code is executed:

package ca.virology.lib2.common.config.spring.properties;
import ca.virology.lib2.config.spring.PropertiesConfig;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.beans.factory.annotation.Value;
import org.springframework.context.annotation.Configuration;
import org.springframework.context.annotation.Import;
import org.springframework.context.annotation.PropertySource;

@Configuration
@Import({PropertiesConfig.class})
@PropertySource("${appclient}")
public class AppClientProperties {
private static final Logger log = LoggerFactory.getLogger(AppClientProperties.class);
{
    //this initializer block will execute when an instance of this class is created by Spring
    log.info("Loading AppClientProperties");
}
@Value("${appclient.port:}")
private int appClientPort;

@Value("${appclient.host:}")
private String appClientHost;

public int getAppClientPort() {
    return appClientPort;
}

public String getAppClientHost() {
    return appClientHost;
}
}

A property file called appclient.properties exists in the resources folder with the information for host and port. I'm not sure where the "${appclient}" is defined, if it is at all. Maybe it is not even defined and that is causing the problem. Do I need to change the "${appclient}" to something like "{classpath:/appclient.properties}" or am I missing something else?

Brkk
  • 577
  • 1
  • 7
  • 19
  • You could reference the PropertySource using classpath sure: http://docs.spring.io/spring/docs/current/javadoc-api/org/springframework/context/annotation/PropertySource.html – Leandro Carracedo Feb 03 '15 at 19:40
  • I was actually trying to run this program, name it 'B' within a different program, named 'A'. Apparently when you execute the program B individually, it gets the `${appclient}` value as a program argument; however, that didn't happen when I try to run B from A and caused the error I was getting. – Brkk Feb 03 '15 at 20:38
  • If you have multiple properties files and all the properties files have the same key, the issue occurs. If yes use the profile parameter while starting the app. – Sachin Sridhar Feb 03 '21 at 14:45

11 Answers11

29

You are not reading the properties file correctly. The propertySource should pass the parameter as: file:appclient.properties or classpath:appclient.properties. Change the annotation to:

@PropertySource(value={"classpath:appclient.properties"})

However I don't know what your PropertiesConfig file contains, as you're importing that also. Ideally the @PropertySource annotation should have been kept there.

Rohit Jain
  • 209,639
  • 45
  • 409
  • 525
14

Hopefully it will be still helpful, the application.properties (or application.yml) file must be in both the paths:

  • src/main/resource/config
  • src/test/resource/config

containing the same property you are referring

Jonathan
  • 595
  • 5
  • 10
13

If you are using Spring 3.1 and above, you can use something like...

@Configuration
@PropertySource("classpath:foo.properties")
public class PropertiesWithJavaConfig {

@Bean
public static PropertySourcesPlaceholderConfigurer propertySourcesPlaceholderConfigurer() {
  return new PropertySourcesPlaceholderConfigurer();
}
}

You can also go by the xml configuration like...

<?xml version="1.0" encoding="UTF-8"?>
<beans xmlns="http://www.springframework.org/schema/beans"
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xmlns:context="http://www.springframework.org/schema/context"
xsi:schemaLocation="
  http://www.springframework.org/schema/beans 
  http://www.springframework.org/schema/beans/spring-beans-3.2.xsd
  http://www.springframework.org/schema/context 
  http://www.springframework.org/schema/context/spring-context-3.2.xsd">

  <context:property-placeholder location="classpath:foo.properties" />

  </beans>

In earlier versions.

2

In my case , I forgot to add the new property in my application.properties under test folder.Adding it resolved the issue

1

If your config file is in a different path than classpath, you can add the configuration file path as a system property:

java -Dapp.config.path=path_to_config_file -jar your.jar
Andronicus
  • 25,419
  • 17
  • 47
  • 88
  • It works! java -Xdebug -Dct.ctconfig.consul.server=http://{Your QA IP}:8355 -Dspring.profiles.active=qa -Xrunjdwp:server=y,transport=dt_socket,address=8200,suspend=n -jar build/libs/YourAppJar-0.0.1-SNAPSHOT.jar – Sachin Sridhar Feb 03 '21 at 14:39
1

enter image description hereI know It is an old message , but i want to add my case.

If you use more than one profile(dev,test,prod...), check your execute profile.

bmck
  • 211
  • 2
  • 6
0

For properties that need to be managed outside of the WAR:

<context:property-placeholder location="file:///C:/application.yml"/>

For example if inside application.yml are name and id

Then you can create bean in runtime inside xml spring

<bean id="id1" class="my.class.Item">
    <property name="name" value="${name}"/>
    <property name="id" value="${id}"/>
</bean>
Piotr Rogowski
  • 3,642
  • 19
  • 24
0

in my case, the war file generated didn't pick up the properties file so had to clean install again in IntelliJ editor.

Smart Coder
  • 1,435
  • 19
  • 19
0

If the issue occurs in IntelliJ, all you have to do is to install the plugin https://plugins.jetbrains.com/plugin/7861-envfile and follow the steps given.

0

Somehow for me the error was due to missing library slf4j-api. After I added following library the error went away

            <dependency>
                <groupId>org.slf4j</groupId>
                <artifactId>slf4j-api</artifactId>
            </dependency>
sunder
  • 968
  • 2
  • 11
  • 31
-10

My solution was to add a space between the $ and the {.

For example:

@Value("${appclient.port:}")

becomes

@Value("$ {appclient.port:}")
PackBjamin
  • 77
  • 2
  • 5
    For anyone running into this, this will not work. Adding a space will just mean @Value parses the string directly (so the final value becomes `$ {appclient.port:}` instead of, say, `12345`). – Kilves Jan 30 '20 at 13:36
  • yes, that's because it turns into a string and not a template placeholder. – Zander Rootman Sep 13 '22 at 14:52