blong824
blong824

Reputation: 4030

Override Spring:message tag with database values

I am using Spring to display messages from a properties file. I would like to be able to override the <spring:message> tag to use a value from a database based on the logged in user. If this value is not present I would like it to default to the value currently in the properties file as it does now.

Can someone help me with this code? I've read about AbstractMessageSource but I am unclear on how to implement it.

Thanks

Upvotes: 10

Views: 10344

Answers (3)

PrimosK
PrimosK

Reputation: 13918

You have to implement custom message source. It's a class that extends AbstractMessageSource and implements the abstract resolveCode(java.lang.String, java.util.Locale) method. There is almost same question on SO (it's solution for Grails), but I think it is good point to start from...

Upvotes: 11

blong824
blong824

Reputation: 4030

I ended up creating a class called DatabaseMessageSource included below. I still need to implement some kind of caching so I don't hit the database with each call. This link was helpful too. Thank you skaffman and PrimosK for pointing me in the right direction.

public class DatabaseMessageSource extends ReloadableResourceBundleMessageSource {

    @Autowired
    private MyDao myDao;


    protected MessageFormat resolveCode(String code, Locale locale) {

        MyObj myObj = myDao.findByCode(code);

        MessageFormat format;

        if (myObj!= null && myObj.getId() != null) {

            format = new MessageFormat(myObj.getValue(), locale);

        } else {

            format = super.resolveCode(code, locale);

        }

        return format;

    }

    protected String resolveCodeWithoutArguments(String code, Locale locale) {

        MyObj myObj = myDao.findByCode(code);

        String format;

        if (myObj != null && myObj.getId() != null) {

            format = myObj.getValue();

        } else {

            format = super.resolveCodeWithoutArguments(code, locale);

        }

        return format;

    }

}

I updated my applicationContext to point to the newly created class. I changed it to:

<bean id="messageSource" class="com.mycompany.mypackage.DatabaseMessageSource">
    <property name="basenames">
        <list>
            <value>classpath:defaultMessages</value>
        </list>
    </property>
    <property name="defaultEncoding" value="UTF-8"/>    
</bean>`enter code here`

Upvotes: 3

skaffman
skaffman

Reputation: 403491

You don't need to change the behaviour of <spring:message>, you just need to change the place it gets its messages from.

By default, it uses the messageSource bean in the context, which is of type MessageSource, or some subclass thereof. You can write your own class that implements MessageSource and add that to your context as the messageSource bean.

AbstractMessageSource is just a convenient starting point for writing your own MessageSource. It does some of the work for you, just subclass it.

Upvotes: 1

Related Questions