You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

Struts 6.3.0.1+JDK17下如何强制显示英文数字不受locale影响?

解决Struts 6.3.0.1中数字显示不受Locale影响的问题

问题背景

在Struts 6.3.0.1 + JDK8环境下,以下代码输出1, 2, 3,:

<s:iterator begin="1" end="3">
    <s:property value="top"/>,
</s:iterator>

切换到JDK17并配置struts.locale=fa_IR后,输出变为波斯语数字۱, ۲, ۳,。网站依赖英文数字运行,曾尝试通过session.setAttribute(Config.FMT_LOCALE, new Locale("en", "US"));解决但未生效。

可行解决方案

方案1:强制指定数字格式化的Locale

使用Struts的getText方法结合数字格式化模式,显式指定英文Locale:

<s:iterator begin="1" end="3">
    <s:property value="%{getText('{0,number,#}', {top}, new java.util.Locale('en', 'US'))}" />,
</s:iterator>

或者使用<s:formatNumber>标签直接指定Locale:

<s:iterator begin="1" end="3">
    <s:formatNumber value="%{top}" locale="en_US" pattern="#"/>,
</s:iterator>

方案2:直接将数字转为字符串输出

跳过Struts的Locale格式化逻辑,将数字直接转为字符串:

<s:iterator begin="1" end="3">
    <s:property value="%{String.valueOf(top)}" />,
</s:iterator>

此方法简单直接,适合不需要复杂数字格式化的场景。

方案3:全局配置数字格式化Locale

如果需要全局统一强制使用英文数字格式化,可以自定义NumberFormatProvider,在应用启动时注册:

import java.text.NumberFormat;
import java.text.spi.NumberFormatProvider;
import java.util.Locale;

public class EnglishNumberFormatProvider extends NumberFormatProvider {
    @Override
    public NumberFormat getInstance(Locale locale) {
        return NumberFormat.getInstance(Locale.US);
    }

    @Override
    public NumberFormat getIntegerInstance(Locale locale) {
        return NumberFormat.getIntegerInstance(Locale.US);
    }

    // 按需实现其他NumberFormat方法(如getCurrencyInstance等)
}

然后在src/main/resources/META-INF/services/java.text.spi.NumberFormatProvider文件中添加:

com.yourpackage.EnglishNumberFormatProvider

此方法会覆盖所有Locale下的数字格式化行为,适合全局需要统一英文数字的场景。

方案4:临时切换请求Locale

通过自定义拦截器,在请求处理时临时将Struts的Locale切换为en_US,处理完后恢复原Locale:

public class ForceEnglishNumberLocaleInterceptor extends AbstractInterceptor {
    @Override
    public String intercept(ActionInvocation invocation) throws Exception {
        ActionContext context = invocation.getInvocationContext();
        Locale originalLocale = context.getLocale();
        try {
            context.setLocale(Locale.US);
            return invocation.invoke();
        } finally {
            context.setLocale(originalLocale);
        }
    }
}

然后在struts.xml中注册并添加到拦截器栈:

<interceptors>
    <interceptor name="forceEnglishNumber" class="com.yourpackage.ForceEnglishNumberLocaleInterceptor"/>
    <interceptor-stack name="defaultStack">
        <interceptor-ref name="forceEnglishNumber"/>
        <interceptor-ref name="defaultStack"/>
    </interceptor-stack>
</interceptors>

注意此方法会影响所有依赖Locale的标签行为,需根据业务场景评估是否适用。

内容的提问来源于stack exchange,提问作者Alireza Fattahi

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.07.08 23:49:53