英文:
Wicket 9: usage of JavaScriptFilteredIntoFooterHeaderResponse seems to cause trouble with renderHead
问题
我使用Wicket 9,并包括wicket-spring-boot-starter 3.0.4。
在我的演示项目中,需要将JavaScript放在<body>
的末尾。因此,我按照https://ci.apache.org/projects/wicket/guide/9.x/single.html#_put_javascript_inside_page_body中的说明进行操作。
我还通过在我的页面中实现Component#renderHead(IHeaderResponse)
来添加资源(CSS和JS)。
在Wicket 8中(来自wicket-spring-boot-starter 2.1.9),一切都按预期工作。
但是在Wicket 9中,为了使我的应用程序运行,我首先在WicketApplicationInitConfiguration#init(WebApplication)
中添加了webApplication.getCspSettings().blocking().disabled();
。我的应用程序启动了,但生成的页面不包含<head>
部分,因此由于缺少资源,应用程序无法正常工作。
为了使<head>
元素在我的页面中出现并包含所有引用,我注释掉了所有与在<body>
中呈现JavaScript相关的代码。
但是我的应用程序不使用这个"解决方法"。
我做错了什么吗?
@ApplicationInitExtension
public class DemoWicketInitializer implements WicketApplicationInitConfiguration {
@Override
public void init(WebApplication webApplication) {
webApplication.getCspSettings().blocking().disabled();
webApplication.getHeaderResponseDecorators().add(response ->
new ResourceAggregator(
new JavaScriptFilteredIntoFooterHeaderResponse(response, "scripts")
)
);
webApplication.getMarkupSettings().setDefaultMarkupEncoding("UTF-8");
}
}
@WicketHomePage
public class MyPage extends WebPage {
@Override
public void renderHead(IHeaderResponse response) {
super.renderHead(response);
response.render(JavaScriptHeaderItem.forUrl(
"https://api.mapbox.com/mapbox-gl-js/v1.8.1/mapbox-gl.js"));
response.render(JavaScriptHeaderItem.forUrl(
"https://api.mapbox.com/mapbox-gl-js/plugins/mapbox-gl-draw/v1.0.9/mapbox-gl-draw.js"));
// 这段JS代码必须出现在<body>中。################################
response.render(JavaScriptHeaderItem.forReference(new PackageResourceReference(getClass(),
"js/demoMapbox.js")));
response.render(CssHeaderItem.forUrl(
"https://api.mapbox.com/mapbox-gl-js/v1.8.1/mapbox-gl.css"));
response.render(CssHeaderItem.forUrl(
"https://api.mapbox.com/mapbox-gl-js/plugins/mapbox-gl-draw/v1.0.9/mapbox-gl-draw.css"));
}
public MyPage(PageParameters parameters) {
// 一些组件
add(new HeaderResponseContainer("scriptBlock", "scripts"));
}
}
<?xml version="1.0" encoding="UTF-8"?>
<html xmlns="http://www.w3.org/1999/xhtml" xmlns:wicket="http://wicket.apache.org" lang="de">
<head>
</head>
<body>
<h1>Wicket und Mapbox</h1>
<div id="ndsmap" style="width: 800px; height: 500px"></div>
<a href="#" wicket:id="sendPostDrawingAction">als POST</a><br>
<h4>Zeichnung als GeoJSON</h4>
<p wicket:id="drawingJson"></p>
<h4>Polygone WGS84</h4>
<p wicket:id="geoWGS84"></p>
<h4>Polygone UTM32N</h4>
<p wicket:id="geoUTM32N"></p>
<wicket:container wicket:id="scriptBlock"/>
</body>
</html>
public class ServletInitializer extends SpringBootServletInitializer {
@Override
protected SpringApplicationBuilder configure(SpringApplicationBuilder application) {
return application.sources(DemoWicketMapboxApplication.class);
}
}
英文:
I'm using Wicket 9 by including wicket-spring-boot-starter 3.0.4 .
In my demo project, it's necessary to put JavaScript at the end of <body>
. So I followed the explanations in https://ci.apache.org/projects/wicket/guide/9.x/single.html#_put_javascript_inside_page_body
I also added resources (CSS and JS) via an implementation of Component#renderHead(IHeaderReponse)
in my page.
All works as expected with Wicket 8 (from wicket-spring-boot-starter 2.1.9).
With Wicket 9 , to make my App run, I first put webApplication.getCspSettings().blocking().disabled();
in WicketApplicationInitConfiguration#init(WebApplication)
. My App starts, but the generated Page doesn't contain a <head>
section, and so the app doesn't work because of missing resources.
To make the <head>
element appear in my page with all references, I commented out all code that refers to the rendering of JavaScript in <body>
.
But my app doesn't work with this "workaround".
Am I doing something wrong?
<!-- language: lang-java -->
@ApplicationInitExtension
public class DemoWicketInitializer implements WicketApplicationInitConfiguration {
@Override
public void init(WebApplication webApplication) {
webApplication.getCspSettings().blocking().disabled();
webApplication.getHeaderResponseDecorators().add(response -> new ResourceAggregator(
new JavaScriptFilteredIntoFooterHeaderResponse(response, "scripts")));
webApplication.getMarkupSettings().setDefaultMarkupEncoding("UTF-8");
}
}
<!-- language: lang-java -->
@WicketHomePage
public class MyPage extends WebPage {
@Override
public void renderHead(IHeaderResponse response) {
super.renderHead(response);
response.render(JavaScriptHeaderItem.forUrl(
"https://api.mapbox.com/mapbox-gl-js/v1.8.1/mapbox-gl.js"));
response.render(JavaScriptHeaderItem.forUrl(
"https://api.mapbox.com/mapbox-gl-js/plugins/mapbox-gl-draw/v1.0.9/mapbox-gl-draw.js"));
// this piece of JS has to appear in <body>. ################################
response.render(JavaScriptHeaderItem.forReference(new PackageResourceReference(getClass(),
"js/demoMapbox.js")));
response.render(CssHeaderItem.forUrl(
"https://api.mapbox.com/mapbox-gl-js/v1.8.1/mapbox-gl.css"));
response.render(CssHeaderItem.forUrl(
"https://api.mapbox.com/mapbox-gl-js/plugins/mapbox-gl-draw/v1.0.9/mapbox-gl-draw.css"));
}
public MyPage(PageParameters parameters) {
// some components
add(new HeaderResponseContainer("scriptBlock", "scripts"));
}
}
<!-- language: lang-html -->
<?xml version="1.0" encoding="UTF-8"?>
<html xmlns="http://www.w3.org/1999/xhtml" xmlns:wicket="http://wicket.apache.org" lang="de">
<head>
</head>
<body>
<h1>Wicket und Mapbox</h1>
<div id="ndsmap" style="width: 800px; height: 500px"></div>
<a href="#" wicket:id="sendPostDrawingAction">als POST</a><br>
<h4>Zeichnung als GeoJSON</h4>
<p wicket:id="drawingJson"></p>
<h4>Polygone WGS84</h4>
<p wicket:id="geoWGS84"></p>
<h4>Polygone UTM32N</h4>
<p wicket:id="geoUTM32N"></p>
<wicket:container wicket:id="scriptBlock"/>
</body>
</html>
<!-- language: lang-java -->
public class ServletInitializer extends SpringBootServletInitializer {
@Override
protected SpringApplicationBuilder configure(SpringApplicationBuilder application) {
return application.sources(DemoWicketMapboxApplication.class);
}
}
答案1
得分: 3
看起来CSP机制正在干扰JavaScriptFilteredIntoFooterHeaderResponse。我将在JIRA上提出这个问题。与此同时,作为一种解决方法,您可以使用setHeaderResponseDecorator(已弃用)而不是getHeaderResponseDecorators:
setHeaderResponseDecorator(response -> new ResourceAggregator(
new JavaScriptFilteredIntoFooterHeaderResponse(response, "scripts")));
这应该使您的应用程序正常工作。
更新
如在jira上指出,这不是一个错误。由于现在我们已经默认添加了一个CSP的ResourceAggregator,要添加一个进一步的响应装饰器,我们应该执行以下操作:
getHeaderResponseDecorators().add(response ->
new JavaScriptFilteredIntoFooterHeaderResponse(response, "scripts"));
我们将相应地更新Wicket 9.x及其迁移指南的文档。
英文:
it looks like CSP mechanism is interfering with JavaScriptFilteredIntoFooterHeaderResponse. I will open an issue about this on JIRA. In the meantime as workaround you can use setHeaderResponseDecorator (which is deprecated) instead of getHeaderResponseDecorators:
setHeaderResponseDecorator(response -> new ResourceAggregator(
new JavaScriptFilteredIntoFooterHeaderResponse(response, "scripts")));
This should make your app work.
UPDATE
as pointed out on jira this is not a bug. Since now we already add a ResourceAggregator by default with CSP, to add a further response decorator we should do the following:
getHeaderResponseDecorators().add(response ->
new JavaScriptFilteredIntoFooterHeaderResponse(response, "scripts"));
We will update the documentation for Wicket 9.x and its migration guide accordingly.
通过集体智慧和协作来改善编程学习和解决问题的方式。致力于成为全球开发者共同参与的知识库,让每个人都能够通过互相帮助和分享经验来进步。
评论