我正在使用Spring来保护我的Rest API并处理我选择了基本身份验证方法的身份验证。 当我测试我的方法时,我用来发送标题参数“Authentication:basic login:password”。
这种方法适用于“GET”方法但不适用于“POST”,这是正常的吗?
一些细节。
此测试使用get方法 - >工作正常:
@Test
public void testListAll() throws Exception {
Assert.assertNotNull(mockMvc);
String userName = "user1";
String userPassword = "user1";
String userAuthorisation = "Basic " +
Base64.getEncoder().encodeToString((userName + ":" + userPassword).getBytes());
String response = mockMvc.perform(get("/api/persons")
.header("Authorization", userAuthorisation))
.andExpect(status().isOk())
.andReturn().getResponse().getContentAsString();
Assert.assertNotNull(response);
Assert.assertFalse(response.isEmpty());
List persons = (new ObjectMapper()).readValue(response, List.class);
Assert.assertNotNull(persons);
Assert.assertTrue(persons.size() >= 14);
}
...但不是这个使用POST的人:
@Test
public void shouldCreatePerson() throws Exception {
String firstName = Tools.generateValidString((int)(Math.random()*100) + 1 );
String lastName = Tools.generateValidString((int) (Math.random() * 100) + 1);
String editorName = "user2";
String editorPassword = "user2";
String editorAuthorisation = "Basic " +
Base64.getEncoder().encodeToString((editorName +":"+ editorPassword).getBytes());
String response = mockMvc.perform(post("/api/persons/create")
.header("Authorization", editorAuthorisation)
.param("firstName", firstName)
.param("lastName", lastName)
.param("isMale", "true"))
.andExpect(status().isOk())
.andReturn().getResponse().getContentAsString();
Assert.assertNotNull(response);
Assert.assertFalse(response.isEmpty());
Person person = (new ObjectMapper()).readValue(response, Person.class);
Assert.assertNotNull(person);
Assert.assertTrue(person.getFirstName().equals(firstName));
Assert.assertTrue(person.getLastName().equals(lastName));
person = personRepository.findOne(person.getId());
Assert.assertNotNull(person);
personRepository.delete(person.getId());
}
弹簧安全配置(我使用H2嵌入式数据库获取用户详细信息):
<jdbc:embedded-database id="dataSource" type="H2">
<jdbc:script execution="INIT" location="classpath:security.sql"/>
</jdbc:embedded-database>
<security:jdbc-user-service data-source-ref="dataSource" id="userService"/>
....和:
<http auto-config="true">
<http-basic entry-point-ref="restAuthenticationEntryPoint"/>
<intercept-url pattern="/api/**" access="isAuthenticated()" method="GET" />
<intercept-url pattern="/api/**" access="hasRole('ROLE_EDITOR')" method="POST" />
</http>
<global-method-security secured-annotations="enabled"/>
更新方法的RequestMapping类
@RestController
@RequestMapping("/api/persons")
public class PersonUpdateController {
@Qualifier("personService")
@Autowired
private PersonService personService;
@Qualifier("errorCodeReader")
@Autowired
private ErrorCodeReader codeReader;
@RequestMapping(value = "/create", method = RequestMethod.POST)
public Person createSimplePerson(
@RequestParam String firstName,
@RequestParam String lastName,
@RequestParam boolean isMale
) {
Person person;
try {
if (isMale) {
person = personService.create(firstName,lastName,Person.MALE);
}else {
person = personService.create(firstName,lastName,Person.FEMALE);
}
return person;
} catch (IncorrectGenderException | InvalidPersonNameException e) {
e.printStackTrace();
throw new RestException(codeReader.getError("InvalidPersonName"),"Invalid Person Names",
"First name or last name is invalid");
}
}
}
类RestAuthenticationEntryPoint:
@Component( "restAuthenticationEntryPoint" )
public class RestAuthenticationEntryPoint implements AuthenticationEntryPoint {
@Override
public void commence( HttpServletRequest request, HttpServletResponse response,
AuthenticationException authException ) throws IOException {
response.sendError( HttpServletResponse.SC_UNAUTHORIZED, "Unauthorized" );
}
}
我收到此错误:
java.lang.AssertionError: Status
预计:200 实际:403
只需将方法从POST改为GET,它就能正常工作(状态200)!!
提前感谢。