optional config property overriden with empty value

1,376 views
Skip to first unread message

V. Sevel

unread,
Oct 29, 2020, 9:55:59 AM10/29/20
to Quarkus Development mailing list
hello,
I have the following code:
@ConfigProperty(name = "bar")
String bar;
with src/main/application.properties
bar=${foo:default-foo}

when I execute: java -jar target\rest-client-quickstart-1.0-SNAPSHOT-runner.jar
I get bar=default-foo, which is expected

when I execute: java -Dfoo=hello -jar target\rest-client-quickstart-1.0-SNAPSHOT-runner.jar  
I get bar=hello, which is also expected

but when I execute: java -Dfoo= -jar target\rest-client-quickstart-1.0-SNAPSHOT-runner.jar  
I get: javax.enterprise.inject.spi.DeploymentException: No config value of type [java.lang.String] exists for: bar, which I did not expect

if is no value for foo, then I should get 'default-foo'?

it is the same if I had in the code:
@ConfigProperty(name = "foo", defaultValue = "default-foo")
String foo;
and I executed: java -Dfoo= -jar target\rest-client-quickstart-1.0-SNAPSHOT-runner.jar
then I am getting: ERROR [io.qua.run.Application] (main) Failed to start application (with profile prod): java.lang.RuntimeException: Error injecting java.lang.String org.acme.rest.client.CountriesMain.foo

note: I am experimenting those corner cases because I use quarkus to run a tekton task. a task can define input parameters, with an optional default value. this input parameter can be set as a value for an env variable. but I do not have a way to say that an env variable should only be pushed to the container if there is a value. and I would rather define default values in the quarkus app, rather than in tekton. so the only thing I could achieve was to pass an empty env variable, and hope that quarkus would react by ignoring the override. ansd apparently that is not the case.

Roberto Cortez

unread,
Oct 29, 2020, 1:51:58 PM10/29/20
to vvs...@gmail.com, Quarkus Development mailing list
Hi,

From the config perspective, it is different to have a key present with an empty value than no key present at all. The defaultValue fallback is only applied when no key is actually present. In this case, a value existe for the key, which is an empty String, that by following the String conversion rules evaluates to null and you get the exception.If the default was used even on empty values, you will no way to empty configuration names set on lower priority sources (you can think as the default value to be the very last source to use).

I don’t think we have a way to support this use case in a simple way. Probably some creative use of SR Config interceptors may help (for instance, if the resolved value is an empty String you can override it to be null, like it was not found so it fallback to the default).

Let me know if that helps.

Cheers,
Roberto

--
You received this message because you are subscribed to the Google Groups "Quarkus Development mailing list" group.
To unsubscribe from this group and stop receiving emails from it, send an email to quarkus-dev...@googlegroups.com.
To view this discussion on the web visit https://groups.google.com/d/msgid/quarkus-dev/2167019b-4547-4633-ac1a-8411335b7d8en%40googlegroups.com.

V. Sevel

unread,
Oct 30, 2020, 8:10:30 AM10/30/20
to Quarkus Development mailing list
hello roberto. 
I see your point. however I do not understand the "String conversion rules evaluates to null"
where does this come from? why an empty string in config does not translate to an empty string in the execution?
if my yaml file contains empty: '', why wouldn't I get empty.length()==0 in:
@ConfigProperty(name = "empty")
String empty;
I can understand that if I provide an empty value, I get this (empty) value, but it should not complain about a non existent value on one side, and not offer to provide me with the default value on the other?

Roberto Cortez

unread,
Oct 30, 2020, 9:03:45 AM10/30/20
to vvs...@gmail.com, Quarkus Development mailing list
This is from the Conversion rules detailed in the MP Config spec:

Is not exactly the value that you set, but the Converter that is returning the value that provides that behaviour. You could register your own converter and override that behaviour, but still it won’t fix the original ask. In reality what happens is:

Config Source A -> my.prop=“”
Default set -> my.prop=something

On my.prop lookup, and empty String is found in Config Source A and passed to the Converter that returns null and fails any validation if the injected field is not an Optional.

Defaults are only used if no config key is found in higher ordinal sources. Even by overriding the Converter, at this point is already too late because the lookup is already done.

In SR Config we already added a ConfigValue type of object that would allow you to have more control on the config lookup, since it will work as an accessor and before any conversion taking place. Unfortunately, I didn’t add default resolution support to it yet, but maybe that is something that I have to push for.

Cheers,
Roberto

Reply all
Reply to author
Forward
0 new messages