Browse Source

SEC-2572: Add spring-security-test method showcase

This will allow for using the showcase in the documentation.
Rob Winch 11 years ago
parent
commit
6d45957eec

+ 79 - 0
test/src/test/java/org/springframework/security/test/context/showcase/CustomUserDetails.java

@@ -0,0 +1,79 @@
+/*
+ * Copyright 2002-2013 the original author or authors.
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License"); you may not
+ * use this file except in compliance with the License. You may obtain a copy of
+ * the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS, WITHOUT
+ * WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the
+ * License for the specific language governing permissions and limitations under
+ * the License.
+ */
+package org.springframework.security.test.context.showcase;
+
+import org.springframework.security.core.GrantedAuthority;
+import org.springframework.security.core.authority.AuthorityUtils;
+import org.springframework.security.core.userdetails.UserDetails;
+
+import java.util.Collection;
+
+/**
+ * @author Rob Winch
+ */
+public class CustomUserDetails implements UserDetails {
+	private final String name;
+	private final String username;
+	private final Collection<? extends GrantedAuthority> authorities;
+
+	public CustomUserDetails(String name, String username) {
+		this.name = name;
+		this.username = username;
+		this.authorities = AuthorityUtils.createAuthorityList("ROLE_USER");
+	}
+
+	@Override
+	public Collection<? extends GrantedAuthority> getAuthorities() {
+		return authorities;
+	}
+
+	@Override
+	public String getPassword() {
+		return null;
+	}
+
+	@Override
+	public String getUsername() {
+		return username;
+	}
+
+	@Override
+	public boolean isAccountNonExpired() {
+		return true;
+	}
+
+	@Override
+	public boolean isAccountNonLocked() {
+		return true;
+	}
+
+	@Override
+	public boolean isCredentialsNonExpired() {
+		return true;
+	}
+
+	@Override
+	public boolean isEnabled() {
+		return true;
+	}
+
+	@Override
+	public String toString() {
+		return "CustomUserDetails{" +
+				"username='" + username + '\'' +
+				'}';
+	}
+}

+ 46 - 0
test/src/test/java/org/springframework/security/test/context/showcase/WithMockCustomUser.java

@@ -0,0 +1,46 @@
+/*
+ * Copyright 2002-2014 the original author or authors.
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package org.springframework.security.test.context.showcase;
+
+import org.springframework.security.test.context.support.WithSecurityContext;
+
+/**
+ * @author Rob Winch
+ */
+@WithSecurityContext(factory = WithMockCustomUserSecurityContextFactory.class)
+public @interface WithMockCustomUser {
+	/**
+	 * The username to be used. The default is rob
+	 * @return
+	 */
+	String username() default "rob";
+
+	/**
+	 * The roles to use. The default is "USER". A {@link org.springframework.security.core.GrantedAuthority} will
+	 * be created for each value within roles. Each value in roles will
+	 * automatically be prefixed with "ROLE_". For example, the default will
+	 * result in "ROLE_USER" being used.
+	 *
+	 * @return
+	 */
+	String[] roles() default { "USER" };
+
+	/**
+	 * The name of the user
+	 * @return
+	 */
+	String name() default "Rob Winch";
+}

+ 44 - 0
test/src/test/java/org/springframework/security/test/context/showcase/WithMockCustomUserSecurityContextFactory.java

@@ -0,0 +1,44 @@
+/*
+ * Copyright 2002-2013 the original author or authors.
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License"); you may not
+ * use this file except in compliance with the License. You may obtain a copy of
+ * the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS, WITHOUT
+ * WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the
+ * License for the specific language governing permissions and limitations under
+ * the License.
+ */
+package org.springframework.security.test.context.showcase;
+
+import org.springframework.security.authentication.UsernamePasswordAuthenticationToken;
+import org.springframework.security.core.Authentication;
+import org.springframework.security.core.GrantedAuthority;
+import org.springframework.security.core.authority.AuthorityUtils;
+import org.springframework.security.core.authority.SimpleGrantedAuthority;
+import org.springframework.security.core.context.SecurityContext;
+import org.springframework.security.core.context.SecurityContextHolder;
+import org.springframework.security.test.context.support.WithSecurityContextFactory;
+
+import java.util.ArrayList;
+import java.util.List;
+
+/**
+ * @author Rob Winch
+ */
+public class WithMockCustomUserSecurityContextFactory implements WithSecurityContextFactory<WithMockCustomUser> {
+	@Override
+	public SecurityContext createSecurityContext(WithMockCustomUser customUser) {
+		SecurityContext context = SecurityContextHolder.createEmptyContext();
+
+		CustomUserDetails principal = new CustomUserDetails(customUser.name(), customUser.username());
+		Authentication auth =
+			new UsernamePasswordAuthenticationToken(principal, "password", principal.getAuthorities());
+		context.setAuthentication(auth);
+		return context;
+	}
+}

+ 83 - 0
test/src/test/java/org/springframework/security/test/context/showcase/WithMockUserTests.java

@@ -0,0 +1,83 @@
+/*
+ * Copyright 2002-2013 the original author or authors.
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License"); you may not
+ * use this file except in compliance with the License. You may obtain a copy of
+ * the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS, WITHOUT
+ * WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the
+ * License for the specific language governing permissions and limitations under
+ * the License.
+ */
+package org.springframework.security.test.context.showcase;
+
+import org.junit.Test;
+import org.junit.runner.RunWith;
+import org.springframework.beans.factory.annotation.Autowired;
+import org.springframework.context.annotation.ComponentScan;
+import org.springframework.context.annotation.Configuration;
+import org.springframework.security.authentication.AuthenticationCredentialsNotFoundException;
+import org.springframework.security.config.annotation.authentication.builders.AuthenticationManagerBuilder;
+import org.springframework.security.config.annotation.method.configuration.EnableGlobalMethodSecurity;
+import org.springframework.security.test.context.DefaultSecurityTestExecutionListeners;
+import org.springframework.security.test.context.showcase.service.HelloMessageService;
+import org.springframework.security.test.context.showcase.service.MessageService;
+import org.springframework.security.test.context.support.WithMockUser;
+import org.springframework.test.context.ContextConfiguration;
+import org.springframework.test.context.junit4.SpringJUnit4ClassRunner;
+
+import static org.fest.assertions.Assertions.assertThat;
+
+/**
+ * @author Rob Winch
+ */
+
+@RunWith(SpringJUnit4ClassRunner.class)
+@ContextConfiguration(classes = WithMockUserTests.Config.class)
+@DefaultSecurityTestExecutionListeners
+public class WithMockUserTests {
+	@Autowired
+	private MessageService messageService;
+
+	@Test(expected = AuthenticationCredentialsNotFoundException.class)
+	public void getMessageUnauthenticated() {
+		messageService.getMessage();
+	}
+
+	@Test
+	@WithMockUser
+	public void getMessageWithMockUser() {
+		String message = messageService.getMessage();
+		assertThat(message).contains("user");
+	}
+
+	@Test
+	@WithMockUser("customUsername")
+	public void getMessageWithMockUserCustomUsername() {
+		String message = messageService.getMessage();
+		assertThat(message).contains("customUsername");
+	}
+
+	@Test
+	@WithMockUser(username="admin",roles={"USER","ADMIN"})
+	public void getMessageWithMockUserCustomUser() {
+		String message = messageService.getMessage();
+		assertThat(message).contains("admin").contains("ROLE_USER").contains("ROLE_ADMIN");
+	}
+
+	@Configuration
+	@EnableGlobalMethodSecurity(prePostEnabled = true)
+	@ComponentScan(basePackageClasses = HelloMessageService.class)
+	static class Config {
+		@Autowired
+		public void configureGlobal(AuthenticationManagerBuilder auth) throws Exception {
+			auth
+				.inMemoryAuthentication()
+					.withUser("user").password("password").roles("USER");
+		}
+	}
+}

+ 99 - 0
test/src/test/java/org/springframework/security/test/context/showcase/WithUserDetailsTests.java

@@ -0,0 +1,99 @@
+/*
+ * Copyright 2002-2013 the original author or authors.
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License"); you may not
+ * use this file except in compliance with the License. You may obtain a copy of
+ * the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS, WITHOUT
+ * WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the
+ * License for the specific language governing permissions and limitations under
+ * the License.
+ */
+package org.springframework.security.test.context.showcase;
+
+import org.junit.Test;
+import org.junit.runner.RunWith;
+import org.springframework.beans.factory.annotation.Autowired;
+import org.springframework.context.annotation.Bean;
+import org.springframework.context.annotation.ComponentScan;
+import org.springframework.context.annotation.Configuration;
+import org.springframework.security.authentication.AuthenticationCredentialsNotFoundException;
+import org.springframework.security.config.annotation.authentication.builders.AuthenticationManagerBuilder;
+import org.springframework.security.config.annotation.method.configuration.EnableGlobalMethodSecurity;
+import org.springframework.security.core.context.SecurityContextHolder;
+import org.springframework.security.core.userdetails.UserDetails;
+import org.springframework.security.core.userdetails.UserDetailsService;
+import org.springframework.security.core.userdetails.UsernameNotFoundException;
+import org.springframework.security.test.context.DefaultSecurityTestExecutionListeners;
+import org.springframework.security.test.context.showcase.service.HelloMessageService;
+import org.springframework.security.test.context.showcase.service.MessageService;
+import org.springframework.security.test.context.support.WithUserDetails;
+import org.springframework.test.context.ContextConfiguration;
+import org.springframework.test.context.junit4.SpringJUnit4ClassRunner;
+
+import static org.fest.assertions.Assertions.assertThat;
+
+/**
+ * @author Rob Winch
+ */
+
+@RunWith(SpringJUnit4ClassRunner.class)
+@ContextConfiguration(classes = WithUserDetailsTests.Config.class)
+@DefaultSecurityTestExecutionListeners
+public class WithUserDetailsTests {
+	@Autowired
+	private MessageService messageService;
+
+	@Test(expected = AuthenticationCredentialsNotFoundException.class)
+	public void getMessageUnauthenticated() {
+		messageService.getMessage();
+	}
+
+	@Test
+	@WithUserDetails
+	public void getMessageWithUserDetails() {
+		String message = messageService.getMessage();
+		assertThat(message).contains("user");
+		assertThat(getPrincipal()).isInstanceOf(CustomUserDetails.class);
+	}
+
+	@Test
+	@WithUserDetails("customUsername")
+	public void getMessageWithUserDetailsCustomUsername() {
+		String message = messageService.getMessage();
+		assertThat(message).contains("customUsername");
+		assertThat(getPrincipal()).isInstanceOf(CustomUserDetails.class);
+	}
+
+	@Configuration
+	@EnableGlobalMethodSecurity(prePostEnabled = true)
+	@ComponentScan(basePackageClasses = HelloMessageService.class)
+	static class Config {
+		@Autowired
+		public void configureGlobal(AuthenticationManagerBuilder auth) throws Exception {
+			auth
+					.userDetailsService(userDetailsService());
+		}
+
+		@Bean
+		public UserDetailsService userDetailsService() {
+			return new CustomUserDetailsService();
+		}
+	}
+
+	private Object getPrincipal() {
+		return SecurityContextHolder.getContext().getAuthentication().getPrincipal();
+	}
+
+	static class CustomUserDetailsService implements UserDetailsService {
+
+		@Override
+		public UserDetails loadUserByUsername(final String username) throws UsernameNotFoundException {
+			return new CustomUserDetails("name", username);
+		}
+	}
+}

+ 34 - 0
test/src/test/java/org/springframework/security/test/context/showcase/service/HelloMessageService.java

@@ -0,0 +1,34 @@
+/*
+ * Copyright 2002-2013 the original author or authors.
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License"); you may not
+ * use this file except in compliance with the License. You may obtain a copy of
+ * the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS, WITHOUT
+ * WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the
+ * License for the specific language governing permissions and limitations under
+ * the License.
+ */
+package org.springframework.security.test.context.showcase.service;
+
+import org.springframework.security.access.prepost.PreAuthorize;
+import org.springframework.security.core.Authentication;
+import org.springframework.security.core.context.SecurityContextHolder;
+import org.springframework.stereotype.Component;
+
+/**
+ * @author Rob Winch
+ */
+@Component
+public class HelloMessageService implements MessageService {
+
+	@PreAuthorize("authenticated")
+	public String getMessage() {
+		Authentication authentication = SecurityContextHolder.getContext().getAuthentication();
+		return "Hello " + authentication;
+	}
+}

+ 10 - 0
test/src/test/java/org/springframework/security/test/context/showcase/service/MessageService.java

@@ -0,0 +1,10 @@
+package org.springframework.security.test.context.showcase.service;
+
+import org.springframework.security.access.prepost.PreAuthorize;
+
+/**
+ * @author Rob Winch
+ */
+public interface MessageService {
+	String getMessage();
+}