Thymeleaf 字符串字面量内变量不生效?如何配置data-images动态产品图片
Thymeleaf 动态绑定内嵌JSON的data-images属性实现
问题根因
你遇到的变量不生效、解析异常的问题,本质是两类写法错误导致的:
- 把
${product.zoomedPhotoURL}直接写在无th:前缀的静态data-images属性中,Thymeleaf默认不会解析静态属性文本块内的表达式,只会把整段字符串原封不动输出,前端拿到的就是字面量的${product.zoomedPhotoURL},完全不是真实的产品URL。 - 手动拼接JSON结构时未对动态值做转义,如果产品URL中包含双引号、反斜杠、特殊符号,会直接破坏JSON语法结构,触发前端解析报错。
可落地方案
方案1(生产环境最稳妥,零转义风险):Controller层预组装JSON配置
这种写法完全规避模板内手动拼JSON的转义坑,是项目中最推荐的实现方式:
- 在Controller构建Model数据时,直接组装整个画廊的图片配置数组,用Jackson/Gson等标准序列化工具把数组转成合规的JSON字符串存入Model:
// 示例Controller逻辑 List<Map<String, Object>> galleryList = new ArrayList<>(); // 加入动态主产品放大图 Map<String, Object> mainImg = new HashMap<>(); mainImg.put("src", product.getZoomedPhotoURL()); mainImg.put("w", 700); mainImg.put("h", 1100); galleryList.add(mainImg); // 追加3个固定的附加产品图 galleryList.add(Map.of("src", "/images/product/extra/zoom1.jpg", "w", 700, "h", 1100)); galleryList.add(Map.of("src", "/images/product/extra/zoom2.jpg", "w", 700, "h", 1100)); galleryList.add(Map.of("src", "/images/product/extra/zoom3.jpg", "w", 700, "h", 1100)); // 把配置序列化为JSON字符串存入Model String galleryConfig = objectMapper.writeValueAsString(galleryList); model.addAttribute("galleryConfig", galleryConfig); - 模板中直接将序列化好的JSON绑定到
data-images属性即可,完全不需要手动处理转义:<button class="product-gallery-popup hintT-left" data-hint="Click to enlarge" th:data-images="${galleryConfig}" > <i class="far fa-expand"></i> </button>
方案2(不修改Controller逻辑时,模板内直接实现)
如果不想调整Controller代码,可在模板中通过th:data-images表达式拼接JSON,必须搭配Thymeleaf内置的JSON转义工具方法使用:
<button class="product-gallery-popup hintT-left" data-hint="Click to enlarge" th:data-images="${'[{\"src\":\"' + #escapes.escapeJson(product.zoomedPhotoURL) + '\",\"w\":700,\"h\":1100},' + '{\"src\":\"/images/product/extra/zoom1.jpg\",\"w\":700,\"h\":1100},' + '{\"src\":\"/images/product/extra/zoom2.jpg\",\"w\":700,\"h\":1100},' + '{\"src\":\"/images/product/extra/zoom3.jpg\",\"w\":700,\"h\":1100}]'}" > <i class="far fa-expand"></i> </button>
- 这里使用Thymeleaf3+自带的
#escapes.escapeJson()方法对动态产品URL做JSON格式转义,从根源上避免特殊字符破坏JSON结构。 - 所有动态表达式都写在
th:前缀声明的属性内,Thymeleaf会正确解析并替换变量值,不会出现把${...}当普通字符串输出的问题。
内容的提问来源于stack exchange,提问作者Victor TG
相关产品推荐
相关产品推荐

