1

I'm refactoring old code and would like to have an enumeration of come constant values that are scattered all over the place in some central place instead, e.g. I've gathered all information regarding our JMS-topics in a central place like so:

public enum Topic {
    CAKES("cakes",42),
    FRUITS("fruits_v2",47); // 47 = 42+inflation

    public final String jmsTopicName;
    public final int importantNumber;

    Topic(String jmsTopicName, int number) {
        this.jmsTopicName = jmsTopicName;
        this.importantNumber = number;
    }
}

Problem: When I want to use the field jmsTopicName in annotations like so:

@MessageDriven(activationConfig = {
        @ActivationConfigProperty(propertyName = "destinationType", propertyValue = "javax.jms.Topic"),
        @ActivationConfigProperty(propertyName = "subscriptionDurability", propertyValue = "NonDurable"),
        @ActivationConfigProperty(propertyName = "destination", propertyValue = "topic/" + Topic.FRUITS.jmsTopicName)})
public class FruitBasketMDB implements MessageListener {
// do stuff here
}

I'm not allowed to because (understandbly) the compiler cannot see that FRUITS.jmsTopicName is actually a constant and not something that the constructor of Topic calculates at runtime. I have tried hacks like FRUITS.name() to convince the compiler that the value in the annotation really is absolutely constant, but it it isn't convinced so far.

My workaround for now is have a separate class full of string constants:

public final class TopicNames{

    private TopicNames(){}

    public static final String CAKES="cakes";
    public static final String FRUITS="fruits_v2";

}

and using those both to define the enum constants and the MDB annotations. That's good in that it reduces the places where such constants are defined in the code from many to only two - the enum constants and the string constants.

My question is, if we can get this from two all the way down to one somehow.

(Yes, of course I could move the string constants into the enum class itself, but that's not really a solution in my mind. It's still two places where some aspect of the same thing is defined)

Johannes Hahn
  • 363
  • 3
  • 18
  • Reduce your question. Just add what is your requirement and what you to achieve. – Anish B. Jun 04 '20 at 16:41
  • 1
    @AnishB. I'm sorry that I don't have a repo for this right now. The code I'm actually working on is proprietary, millions of lines, decades old and borderline unintelligible in certain places. I'll try to set up a minimal working example I can link to when I'm home. – Johannes Hahn Jun 04 '20 at 16:44
  • Look at this : https://stackoverflow.com/questions/13253624/how-to-supply-enum-value-to-an-annotation-from-a-constant-in-java . May be this can help you ? – Anish B. Jun 04 '20 at 16:45
  • The JLS explains what can be used as an annotation element value, [here](https://docs.oracle.com/javase/specs/jls/se14/html/jls-9.html#jls-9.7.1). For Strings, the value would have to be a constant expression. An enum field access cannot be a constant expression. – Sotirios Delimanolis Jun 04 '20 at 17:20

0 Answers0