我有一个Spring Boot REST Service,它提供了一些方法。它们受CSRF和用户名/密码基本身份验证(https)保护。
但是,当我尝试执行POST请求时,它失败并显示状态代码403和消息“无法验证提供的CSRF令牌,因为找不到会话”
这是我的客户代码:
ApiMessage msg = new ApiMessage("Client1", "Key1", "Value1");
// Set up Basic Authentication
HttpAuthenticationFeature feature = HttpAuthenticationFeature.basicBuilder()
.nonPreemptive()
.credentials(ApiUser, ApiUserPassword)
.build();
ClientConfig clientConfig = new ClientConfig();
clientConfig.register(feature);
Client client = ClientBuilder.newClient(clientConfig);
// Set up client and target (ApiHost = URI for the request Ressource)
WebTarget target = client.target(ApiHost);
WebTarget checkTarget = target.path("check");
Invocation.Builder invocationBuilder = checkTarget.request(MediaType.APPLICATION_JSON);
// Do a first request to get the CSRF Header
Response response = invocationBuilder.post(Entity.entity(msg, MediaType.APPLICATION_JSON));
if (response.getStatus() == 200) {
System.out.println("Without CSRF - everything worked. ");
} else if (response.getStatus() == 403) {
System.out.println("CSRF Protection: " + response.getStatus() + response.readEntity(String.class));
// Get CSRF Token out of the response
Map<String, NewCookie> cookies = response.getCookies();
String csrf = cookies.get("XSRF-TOKEN").getValue();
// Add the Token to the header and POST again
invocationBuilder.header("X-XSRF-TOKEN", csrf);
response = invocationBuilder.post(Entity.entity(msg, MediaType.APPLICATION_JSON));
if (response.getStatus() != 200) {
System.out.println("Error: " + response.getStatus() + response.readEntity(String.class));
} else {
System.out.println("With CSRF - everything worked. ");
}
} else {
System.out.println(response.getStatus() + " " + response.readEntity(String.class));
}
第一个请求以状态403结束,并显示消息“无法验证提供的CSRF令牌,因为未找到您的会话”。 之后,我从响应头中提取CSRF令牌。 但是使用CSRF头的第二个请求失败并出现相同的错误。
在Postman中做同样的事情也可以。
任何想法都是我的错误以及我做错了什么?
答案 0 :(得分:0)
可能还需要发送一个会话cookie,比如JSESSIONID。得到那个cookie。从NewCookie
您创建Cookie
并将其添加到请求
NewCookie session = cookies.get("JSESSIONID");
Cookie cookie = session.toCookie();
invocationBuilder.cookie(cookie);
如果它不是JSESSIONID,请检查所有Cookie。它可能是别的东西。