├── .gitignore
├── src
├── main
│ ├── webapp
│ │ ├── index.jsp
│ │ ├── WEB-INF
│ │ │ └── templates
│ │ │ │ └── messages
│ │ │ │ ├── view.html
│ │ │ │ ├── list.html
│ │ │ │ └── form.html
│ │ └── resources
│ │ │ └── js
│ │ │ └── jquery.validate.js
│ ├── resources
│ │ └── log4j.xml
│ └── java
│ │ └── sample
│ │ ├── data
│ │ ├── MessageRepository.java
│ │ └── Message.java
│ │ ├── config
│ │ ├── WebSecurityAppInitializer.java
│ │ ├── WebMvcAppInitializer.java
│ │ ├── WebSecurityConfig.java
│ │ ├── DataConfig.java
│ │ └── WebMvcConfig.java
│ │ └── mvc
│ │ └── MessageController.java
└── test
│ └── java
│ ├── org
│ └── springframework
│ │ └── security
│ │ └── test
│ │ ├── context
│ │ └── showcase
│ │ │ ├── service
│ │ │ ├── MessageService.java
│ │ │ └── HelloMessageService.java
│ │ │ ├── WithMockCustomUser.java
│ │ │ ├── WithMockCustomUserSecurityContextFactory.java
│ │ │ ├── CustomUserDetails.java
│ │ │ ├── WithMockUserTests.java
│ │ │ └── WithUserDetailsTests.java
│ │ └── web
│ │ └── servlet
│ │ └── showcase
│ │ ├── csrf
│ │ ├── DefaultCsrfShowcaseTests.java
│ │ ├── CsrfShowcaseTests.java
│ │ └── CustomCsrfShowcaseTests.java
│ │ ├── login
│ │ ├── AuthenticationTests.java
│ │ ├── CustomLoginRequestBuilderAuthenticationTests.java
│ │ └── CustomConfigAuthenticationTests.java
│ │ └── secured
│ │ ├── DefaultfSecurityRequestsTests.java
│ │ ├── WithUserClassLevelAuthenticationTests.java
│ │ ├── WithUserAuthenticationTests.java
│ │ ├── WithUserDetailsClassLevelAuthenticationTests.java
│ │ ├── WithUserDetailsAuthenticationTests.java
│ │ └── SecurityRequestsTests.java
│ └── sample
│ ├── fest
│ ├── Assertions.java
│ └── MessageAssert.java
│ ├── webdriver
│ ├── pages
│ │ ├── AbstractPage.java
│ │ ├── CreateMessagePage.java
│ │ └── ViewMessagePage.java
│ └── MockMvcHtmlUnitDriverCreateMessageTest.java
│ ├── config
│ └── MockDataConfig.java
│ ├── data
│ └── mock
│ │ └── MockConversionService.java
│ ├── htmlunit
│ └── MockMvcHtmlUnitCreateMessageTest.java
│ └── mockmvc
│ └── MockMvcCreateMessageTest.java
└── pom.xml
/.gitignore:
--------------------------------------------------------------------------------
1 | target
2 | bin
3 | .settings
4 | .classpath
5 | .project
6 | *.iml
7 | .idea
--------------------------------------------------------------------------------
/src/main/webapp/index.jsp:
--------------------------------------------------------------------------------
1 |
2 |
3 | Hello World!
4 |
5 |
--------------------------------------------------------------------------------
/src/test/java/org/springframework/security/test/context/showcase/service/MessageService.java:
--------------------------------------------------------------------------------
1 | package org.springframework.security.test.context.showcase.service;
2 |
3 | import org.springframework.security.access.prepost.PreAuthorize;
4 |
5 | /**
6 | * @author Rob Winch
7 | */
8 | public interface MessageService {
9 | String getMessage();
10 | }
11 |
--------------------------------------------------------------------------------
/src/main/resources/log4j.xml:
--------------------------------------------------------------------------------
1 |
2 |
3 |
4 |
5 |
6 |
7 |
8 |
9 |
10 |
11 |
12 |
13 |
14 |
15 |
16 |
17 |
18 |
--------------------------------------------------------------------------------
/src/main/java/sample/data/MessageRepository.java:
--------------------------------------------------------------------------------
1 | /*
2 | * Copyright 2012 the original author or authors.
3 | *
4 | * Licensed under the Apache License, Version 2.0 (the "License"); you may not use this file except in compliance with
5 | * the License. You may obtain a copy of the License at
6 | *
7 | * http://www.apache.org/licenses/LICENSE-2.0
8 | *
9 | * Unless required by applicable law or agreed to in writing, software distributed under the License is distributed on
10 | * an "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the License for the
11 | * specific language governing permissions and limitations under the License.
12 | */
13 | package sample.data;
14 |
15 | import org.springframework.data.repository.CrudRepository;
16 |
17 | /**
18 | *
19 | * @author Rob Winch
20 | *
21 | */
22 | public interface MessageRepository extends CrudRepository {
23 |
24 | }
25 |
--------------------------------------------------------------------------------
/src/test/java/sample/fest/Assertions.java:
--------------------------------------------------------------------------------
1 | /*
2 | * Copyright 2002-2013 the original author or authors.
3 | *
4 | * Licensed under the Apache License, Version 2.0 (the "License"); you may not
5 | * use this file except in compliance with the License. You may obtain a copy of
6 | * the License at
7 | *
8 | * http://www.apache.org/licenses/LICENSE-2.0
9 | *
10 | * Unless required by applicable law or agreed to in writing, software
11 | * distributed under the License is distributed on an "AS IS" BASIS, WITHOUT
12 | * WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the
13 | * License for the specific language governing permissions and limitations under
14 | * the License.
15 | */
16 | package sample.fest;
17 |
18 | import sample.data.Message;
19 |
20 | /**
21 | * @author Rob Winch
22 | */
23 | public class Assertions extends org.fest.assertions.Assertions {
24 |
25 | public static MessageAssert assertThat(Message message) {
26 | return new MessageAssert(message);
27 | }
28 | }
29 |
--------------------------------------------------------------------------------
/src/main/java/sample/config/WebSecurityAppInitializer.java:
--------------------------------------------------------------------------------
1 | /*
2 | * Copyright 2002-2013 the original author or authors.
3 | *
4 | * Licensed under the Apache License, Version 2.0 (the "License"); you may not
5 | * use this file except in compliance with the License. You may obtain a copy of
6 | * the License at
7 | *
8 | * http://www.apache.org/licenses/LICENSE-2.0
9 | *
10 | * Unless required by applicable law or agreed to in writing, software
11 | * distributed under the License is distributed on an "AS IS" BASIS, WITHOUT
12 | * WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the
13 | * License for the specific language governing permissions and limitations under
14 | * the License.
15 | */
16 | package sample.config;
17 |
18 | import org.springframework.security.web.context.AbstractSecurityWebApplicationInitializer;
19 |
20 | /**
21 | * @author Rob Winch
22 | */
23 | public class WebSecurityAppInitializer extends AbstractSecurityWebApplicationInitializer {
24 | public WebSecurityAppInitializer() {
25 | super(WebSecurityConfig.class);
26 | }
27 | }
28 |
--------------------------------------------------------------------------------
/src/main/webapp/WEB-INF/templates/messages/view.html:
--------------------------------------------------------------------------------
1 |
2 |
3 |
4 |
5 | Messages : View
6 |
7 |
8 |
9 |
10 |
Messages : View
11 |
Some Success message
12 |
13 |
14 | ID
15 | 123
16 | Date
17 | July 11, 2012 2:17:16 PM CDT
18 | Summary
19 | A short summary...
20 | Message
21 | A detailed message that is longer than the summary.
22 |
23 |
24 |
25 |
--------------------------------------------------------------------------------
/src/main/webapp/WEB-INF/templates/messages/list.html:
--------------------------------------------------------------------------------
1 |
2 |
3 |
4 |
5 | Messages : View all
6 |
7 |
8 |
9 |
10 |
Messages : View all
11 |
14 |
15 |
16 |
17 | ID
18 | Created
19 | Summary
20 |
21 |
22 |
23 |
24 | No messages
25 |
26 |
27 | 1
28 | July 11, 2012 2:17:16 PM CDT
29 | The summary
30 |
31 |
32 |
33 |
34 |
35 |
--------------------------------------------------------------------------------
/src/main/java/sample/config/WebMvcAppInitializer.java:
--------------------------------------------------------------------------------
1 | /*
2 | * Copyright 2002-2013 the original author or authors.
3 | *
4 | * Licensed under the Apache License, Version 2.0 (the "License"); you may not
5 | * use this file except in compliance with the License. You may obtain a copy of
6 | * the License at
7 | *
8 | * http://www.apache.org/licenses/LICENSE-2.0
9 | *
10 | * Unless required by applicable law or agreed to in writing, software
11 | * distributed under the License is distributed on an "AS IS" BASIS, WITHOUT
12 | * WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the
13 | * License for the specific language governing permissions and limitations under
14 | * the License.
15 | */
16 | package sample.config;
17 |
18 | import org.springframework.web.servlet.support.AbstractAnnotationConfigDispatcherServletInitializer;
19 |
20 | /**
21 | * @author Rob Winch
22 | */
23 | public class WebMvcAppInitializer extends AbstractAnnotationConfigDispatcherServletInitializer {
24 | @Override
25 | protected Class>[] getRootConfigClasses() {
26 | return null;
27 | }
28 |
29 | @Override
30 | protected Class>[] getServletConfigClasses() {
31 | return new Class[] { DataConfig.class, WebMvcConfig.class};
32 | }
33 |
34 | @Override
35 | protected String[] getServletMappings() {
36 | return new String[] { "/"};
37 | }
38 | }
39 |
--------------------------------------------------------------------------------
/src/test/java/sample/webdriver/pages/AbstractPage.java:
--------------------------------------------------------------------------------
1 | /*
2 | * Copyright 2012 the original author or authors.
3 | *
4 | * Licensed under the Apache License, Version 2.0 (the "License"); you may not use this file except in compliance with
5 | * the License. You may obtain a copy of the License at
6 | *
7 | * http://www.apache.org/licenses/LICENSE-2.0
8 | *
9 | * Unless required by applicable law or agreed to in writing, software distributed under the License is distributed on
10 | * an "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the License for the
11 | * specific language governing permissions and limitations under the License.
12 | */
13 | package sample.webdriver.pages;
14 |
15 | import org.openqa.selenium.WebDriver;
16 | import org.openqa.selenium.WebElement;
17 | import org.openqa.selenium.support.FindBy;
18 |
19 | /**
20 | * Represents the common elements in a page within the message application.
21 | *
22 | * @author Rob Winch
23 | *
24 | */
25 | public class AbstractPage {
26 | protected WebDriver driver;
27 |
28 | @FindBy(css = "label.error, .alert-error")
29 | private WebElement errors;
30 |
31 | public AbstractPage(WebDriver driver) {
32 | setDriver(driver);
33 | }
34 |
35 | public void setDriver(WebDriver driver) {
36 | this.driver = driver;
37 | }
38 |
39 | public String getErrors() {
40 | return errors.getText();
41 | }
42 | }
43 |
--------------------------------------------------------------------------------
/src/test/java/org/springframework/security/test/context/showcase/service/HelloMessageService.java:
--------------------------------------------------------------------------------
1 | /*
2 | * Copyright 2002-2013 the original author or authors.
3 | *
4 | * Licensed under the Apache License, Version 2.0 (the "License"); you may not
5 | * use this file except in compliance with the License. You may obtain a copy of
6 | * the License at
7 | *
8 | * http://www.apache.org/licenses/LICENSE-2.0
9 | *
10 | * Unless required by applicable law or agreed to in writing, software
11 | * distributed under the License is distributed on an "AS IS" BASIS, WITHOUT
12 | * WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the
13 | * License for the specific language governing permissions and limitations under
14 | * the License.
15 | */
16 | package org.springframework.security.test.context.showcase.service;
17 |
18 | import org.springframework.security.access.prepost.PreAuthorize;
19 | import org.springframework.security.core.Authentication;
20 | import org.springframework.security.core.context.SecurityContextHolder;
21 | import org.springframework.stereotype.Component;
22 |
23 | /**
24 | * @author Rob Winch
25 | */
26 | @Component
27 | public class HelloMessageService implements MessageService {
28 |
29 | @PreAuthorize("authenticated")
30 | public String getMessage() {
31 | Authentication authentication = SecurityContextHolder.getContext().getAuthentication();
32 | return "Hello " + authentication;
33 | }
34 | }
35 |
--------------------------------------------------------------------------------
/src/main/java/sample/config/WebSecurityConfig.java:
--------------------------------------------------------------------------------
1 | /*
2 | * Copyright 2002-2013 the original author or authors.
3 | *
4 | * Licensed under the Apache License, Version 2.0 (the "License"); you may not
5 | * use this file except in compliance with the License. You may obtain a copy of
6 | * the License at
7 | *
8 | * http://www.apache.org/licenses/LICENSE-2.0
9 | *
10 | * Unless required by applicable law or agreed to in writing, software
11 | * distributed under the License is distributed on an "AS IS" BASIS, WITHOUT
12 | * WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the
13 | * License for the specific language governing permissions and limitations under
14 | * the License.
15 | */
16 | package sample.config;
17 |
18 | import org.springframework.beans.factory.annotation.Autowired;
19 | import org.springframework.context.annotation.Configuration;
20 | import org.springframework.security.config.annotation.authentication.builders.AuthenticationManagerBuilder;
21 | import org.springframework.security.config.annotation.web.configuration.WebSecurityConfigurerAdapter;
22 | import org.springframework.security.config.annotation.web.servlet.configuration.EnableWebMvcSecurity;
23 |
24 | /**
25 | * @author Rob Winch
26 | */
27 | @EnableWebMvcSecurity
28 | @Configuration
29 | public class WebSecurityConfig extends WebSecurityConfigurerAdapter {
30 | @Autowired
31 | public void configureGlobal(AuthenticationManagerBuilder auth) throws Exception {
32 | auth
33 | .inMemoryAuthentication()
34 | .withUser("user").password("password").roles("USER");
35 | }
36 | }
37 |
--------------------------------------------------------------------------------
/src/main/webapp/WEB-INF/templates/messages/form.html:
--------------------------------------------------------------------------------
1 |
2 |
3 |
4 | Messages : Create
5 |
6 |
7 |
8 |
9 |
Messages : Create
10 |
23 |
24 |
25 |
26 |
33 |
34 |
--------------------------------------------------------------------------------
/src/test/java/org/springframework/security/test/context/showcase/WithMockCustomUser.java:
--------------------------------------------------------------------------------
1 | /*
2 | * Copyright 2002-2014 the original author or authors.
3 | *
4 | * Licensed under the Apache License, Version 2.0 (the "License");
5 | * you may not use this file except in compliance with the License.
6 | * You may obtain a copy of the License at
7 | *
8 | * http://www.apache.org/licenses/LICENSE-2.0
9 | *
10 | * Unless required by applicable law or agreed to in writing, software
11 | * distributed under the License is distributed on an "AS IS" BASIS,
12 | * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13 | * See the License for the specific language governing permissions and
14 | * limitations under the License.
15 | */
16 | package org.springframework.security.test.context.showcase;
17 |
18 | import org.springframework.security.test.context.support.WithSecurityContext;
19 |
20 | /**
21 | * @author Rob Winch
22 | */
23 | @WithSecurityContext(factory = WithMockCustomUserSecurityContextFactory.class)
24 | public @interface WithMockCustomUser {
25 | /**
26 | * The username to be used. The default is rob
27 | * @return
28 | */
29 | String username() default "rob";
30 |
31 | /**
32 | * The roles to use. The default is "USER". A {@link org.springframework.security.core.GrantedAuthority} will
33 | * be created for each value within roles. Each value in roles will
34 | * automatically be prefixed with "ROLE_". For example, the default will
35 | * result in "ROLE_USER" being used.
36 | *
37 | * @return
38 | */
39 | String[] roles() default { "USER" };
40 |
41 | /**
42 | * The name of the user
43 | * @return
44 | */
45 | String name() default "Rob Winch";
46 | }
47 |
--------------------------------------------------------------------------------
/src/test/java/sample/webdriver/pages/CreateMessagePage.java:
--------------------------------------------------------------------------------
1 | /*
2 | * Copyright 2012 the original author or authors.
3 | *
4 | * Licensed under the Apache License, Version 2.0 (the "License"); you may not use this file except in compliance with
5 | * the License. You may obtain a copy of the License at
6 | *
7 | * http://www.apache.org/licenses/LICENSE-2.0
8 | *
9 | * Unless required by applicable law or agreed to in writing, software distributed under the License is distributed on
10 | * an "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the License for the
11 | * specific language governing permissions and limitations under the License.
12 | */
13 | package sample.webdriver.pages;
14 |
15 | import org.openqa.selenium.WebDriver;
16 | import org.openqa.selenium.WebElement;
17 | import org.openqa.selenium.support.FindBy;
18 | import org.openqa.selenium.support.PageFactory;
19 | import sample.data.Message;
20 |
21 | /**
22 | * Represents the page where a {@link Message} is created.
23 | *
24 | * @author Rob Winch
25 | *
26 | */
27 | public class CreateMessagePage extends AbstractPage {
28 | private WebElement summary;
29 |
30 | private WebElement text;
31 |
32 | @FindBy(css = "input[type=submit]")
33 | private WebElement submit;
34 |
35 | public CreateMessagePage(WebDriver driver) {
36 | super(driver);
37 | }
38 |
39 | public T createMessage(Class resultPage, String summary, String details) {
40 | this.summary.sendKeys(summary);
41 | this.text.sendKeys(details);
42 | this.submit.click();
43 | return PageFactory.initElements(driver, resultPage);
44 | }
45 |
46 | public static CreateMessagePage to(WebDriver driver) {
47 | driver.get("http://localhost:9990/mail/messages/form");
48 | return PageFactory.initElements(driver, CreateMessagePage.class);
49 | }
50 | }
--------------------------------------------------------------------------------
/src/test/java/sample/fest/MessageAssert.java:
--------------------------------------------------------------------------------
1 | /*
2 | * Copyright 2002-2013 the original author or authors.
3 | *
4 | * Licensed under the Apache License, Version 2.0 (the "License"); you may not
5 | * use this file except in compliance with the License. You may obtain a copy of
6 | * the License at
7 | *
8 | * http://www.apache.org/licenses/LICENSE-2.0
9 | *
10 | * Unless required by applicable law or agreed to in writing, software
11 | * distributed under the License is distributed on an "AS IS" BASIS, WITHOUT
12 | * WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the
13 | * License for the specific language governing permissions and limitations under
14 | * the License.
15 | */
16 | package sample.fest;
17 |
18 | import org.fest.assertions.ObjectAssert;
19 | import org.springframework.test.util.MatcherAssertionErrors;
20 | import sample.data.Message;
21 |
22 | import java.util.Calendar;
23 |
24 | import static org.fest.assertions.Assertions.assertThat;
25 |
26 | /**
27 | * @author Rob Winch
28 | */
29 | public class MessageAssert extends ObjectAssert {
30 |
31 | public MessageAssert(Message message) {
32 | super(message);
33 | }
34 |
35 | @Override
36 | public MessageAssert isEqualTo(Object expected) {
37 | isEqualToIgnoringGeneratedFields(expected);
38 | Message expectedMessage = (Message) expected;
39 | Message actualMessage = (Message) actual;
40 | assertThat(actualMessage.getId()).isEqualTo(expectedMessage.getId());
41 | assertThat(actualMessage.getCreated()).isEqualTo(expectedMessage.getCreated());
42 | return this;
43 | }
44 |
45 | public MessageAssert isEqualToIgnoringGeneratedFields(Object expected) {
46 | assertThat(expected).isInstanceOf(Message.class);
47 | Message expectedMessage = (Message) expected;
48 | Message actualMessage = (Message) actual;
49 | assertThat(actualMessage.getSummary()).isEqualTo(expectedMessage.getSummary());
50 | assertThat(actualMessage.getText()).isEqualTo(expectedMessage.getText());
51 | return this;
52 | }
53 | }
54 |
--------------------------------------------------------------------------------
/src/main/java/sample/data/Message.java:
--------------------------------------------------------------------------------
1 | /*
2 | * Copyright 2012 the original author or authors.
3 | *
4 | * Licensed under the Apache License, Version 2.0 (the "License"); you may not use this file except in compliance with
5 | * the License. You may obtain a copy of the License at
6 | *
7 | * http://www.apache.org/licenses/LICENSE-2.0
8 | *
9 | * Unless required by applicable law or agreed to in writing, software distributed under the License is distributed on
10 | * an "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the License for the
11 | * specific language governing permissions and limitations under the License.
12 | */
13 | package sample.data;
14 |
15 | import java.util.Calendar;
16 |
17 | import javax.persistence.Entity;
18 | import javax.persistence.GeneratedValue;
19 | import javax.persistence.GenerationType;
20 | import javax.persistence.Id;
21 | import javax.persistence.Version;
22 |
23 | import org.hibernate.validator.constraints.NotEmpty;
24 |
25 | /**
26 | *
27 | * @author Rob Winch
28 | *
29 | */
30 | @Entity
31 | public class Message {
32 | @Id
33 | @GeneratedValue(strategy = GenerationType.AUTO)
34 | private Long id;
35 |
36 | @NotEmpty(message = "Message is required.")
37 | private String text;
38 |
39 | @NotEmpty(message = "Summary is required.")
40 | private String summary;
41 |
42 | @Version
43 | private Calendar created = Calendar.getInstance();
44 |
45 | public Long getId() {
46 | return id;
47 | }
48 |
49 | public void setId(Long id) {
50 | this.id = id;
51 | }
52 |
53 | public Calendar getCreated() {
54 | return created;
55 | }
56 |
57 | public void setCreated(Calendar created) {
58 | this.created = created;
59 | }
60 |
61 | public String getText() {
62 | return text;
63 | }
64 |
65 | public void setText(String text) {
66 | this.text = text;
67 | }
68 |
69 | public String getSummary() {
70 | return summary;
71 | }
72 |
73 | public void setSummary(String summary) {
74 | this.summary = summary;
75 | }
76 | }
77 |
--------------------------------------------------------------------------------
/src/test/java/org/springframework/security/test/context/showcase/WithMockCustomUserSecurityContextFactory.java:
--------------------------------------------------------------------------------
1 | /*
2 | * Copyright 2002-2013 the original author or authors.
3 | *
4 | * Licensed under the Apache License, Version 2.0 (the "License"); you may not
5 | * use this file except in compliance with the License. You may obtain a copy of
6 | * the License at
7 | *
8 | * http://www.apache.org/licenses/LICENSE-2.0
9 | *
10 | * Unless required by applicable law or agreed to in writing, software
11 | * distributed under the License is distributed on an "AS IS" BASIS, WITHOUT
12 | * WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the
13 | * License for the specific language governing permissions and limitations under
14 | * the License.
15 | */
16 | package org.springframework.security.test.context.showcase;
17 |
18 | import org.springframework.security.authentication.UsernamePasswordAuthenticationToken;
19 | import org.springframework.security.core.Authentication;
20 | import org.springframework.security.core.GrantedAuthority;
21 | import org.springframework.security.core.authority.AuthorityUtils;
22 | import org.springframework.security.core.authority.SimpleGrantedAuthority;
23 | import org.springframework.security.core.context.SecurityContext;
24 | import org.springframework.security.core.context.SecurityContextHolder;
25 | import org.springframework.security.test.context.support.WithSecurityContextFactory;
26 |
27 | import java.util.ArrayList;
28 | import java.util.List;
29 |
30 | /**
31 | * @author Rob Winch
32 | */
33 | public class WithMockCustomUserSecurityContextFactory implements WithSecurityContextFactory {
34 | @Override
35 | public SecurityContext createSecurityContext(WithMockCustomUser customUser) {
36 | SecurityContext context = SecurityContextHolder.createEmptyContext();
37 |
38 | CustomUserDetails principal = new CustomUserDetails(customUser.name(), customUser.username());
39 | Authentication auth =
40 | new UsernamePasswordAuthenticationToken(principal, "password", principal.getAuthorities());
41 | context.setAuthentication(auth);
42 | return context;
43 | }
44 | }
45 |
--------------------------------------------------------------------------------
/src/test/java/org/springframework/security/test/context/showcase/CustomUserDetails.java:
--------------------------------------------------------------------------------
1 | /*
2 | * Copyright 2002-2013 the original author or authors.
3 | *
4 | * Licensed under the Apache License, Version 2.0 (the "License"); you may not
5 | * use this file except in compliance with the License. You may obtain a copy of
6 | * the License at
7 | *
8 | * http://www.apache.org/licenses/LICENSE-2.0
9 | *
10 | * Unless required by applicable law or agreed to in writing, software
11 | * distributed under the License is distributed on an "AS IS" BASIS, WITHOUT
12 | * WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the
13 | * License for the specific language governing permissions and limitations under
14 | * the License.
15 | */
16 | package org.springframework.security.test.context.showcase;
17 |
18 | import org.springframework.security.core.GrantedAuthority;
19 | import org.springframework.security.core.authority.AuthorityUtils;
20 | import org.springframework.security.core.userdetails.UserDetails;
21 |
22 | import java.util.Collection;
23 |
24 | /**
25 | * @author Rob Winch
26 | */
27 | public class CustomUserDetails implements UserDetails {
28 | private final String name;
29 | private final String username;
30 | private final Collection extends GrantedAuthority> authorities;
31 |
32 | public CustomUserDetails(String name, String username) {
33 | this.name = name;
34 | this.username = username;
35 | this.authorities = AuthorityUtils.createAuthorityList("ROLE_USER");
36 | }
37 |
38 | @Override
39 | public Collection extends GrantedAuthority> getAuthorities() {
40 | return authorities;
41 | }
42 |
43 | @Override
44 | public String getPassword() {
45 | return null;
46 | }
47 |
48 | @Override
49 | public String getUsername() {
50 | return username;
51 | }
52 |
53 | @Override
54 | public boolean isAccountNonExpired() {
55 | return true;
56 | }
57 |
58 | @Override
59 | public boolean isAccountNonLocked() {
60 | return true;
61 | }
62 |
63 | @Override
64 | public boolean isCredentialsNonExpired() {
65 | return true;
66 | }
67 |
68 | @Override
69 | public boolean isEnabled() {
70 | return true;
71 | }
72 |
73 | @Override
74 | public String toString() {
75 | return "CustomUserDetails{" +
76 | "username='" + username + '\'' +
77 | '}';
78 | }
79 | }
--------------------------------------------------------------------------------
/src/test/java/sample/webdriver/pages/ViewMessagePage.java:
--------------------------------------------------------------------------------
1 | /*
2 | * Copyright 2012 the original author or authors.
3 | *
4 | * Licensed under the Apache License, Version 2.0 (the "License"); you may not use this file except in compliance with
5 | * the License. You may obtain a copy of the License at
6 | *
7 | * http://www.apache.org/licenses/LICENSE-2.0
8 | *
9 | * Unless required by applicable law or agreed to in writing, software distributed under the License is distributed on
10 | * an "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the License for the
11 | * specific language governing permissions and limitations under the License.
12 | */
13 | package sample.webdriver.pages;
14 |
15 | import org.openqa.selenium.WebDriver;
16 | import org.openqa.selenium.WebElement;
17 | import org.openqa.selenium.support.FindBy;
18 | import sample.data.Message;
19 |
20 | import java.text.DateFormat;
21 | import java.text.ParseException;
22 | import java.util.Calendar;
23 | import java.util.Locale;
24 |
25 | /**
26 | * Represents the page where the {@link Message} details can be viewed.
27 | *
28 | * @author Rob Winch
29 | *
30 | */
31 | public class ViewMessagePage extends AbstractPage {
32 | @FindBy(className = "alert-success")
33 | private WebElement success;
34 |
35 | private WebElement id;
36 |
37 | private WebElement created;
38 |
39 | private WebElement summary;
40 |
41 | private WebElement text;
42 |
43 | public ViewMessagePage(WebDriver driver) {
44 | super(driver);
45 | }
46 |
47 | public String getSuccess() {
48 | return success.getText();
49 | }
50 |
51 | public Long getId() {
52 | return Long.parseLong(id.getText());
53 | }
54 |
55 | public Calendar getCreated() throws ParseException {
56 | Calendar result = Calendar.getInstance();
57 | DateFormat format = DateFormat.getDateTimeInstance(DateFormat.LONG, DateFormat.LONG, Locale.ENGLISH);
58 | result.setTime(format.parse(created.getText()));
59 | return result;
60 | }
61 |
62 | public String getSummary() {
63 | return summary.getText();
64 | }
65 |
66 | public String getText() {
67 | return text.getText();
68 | }
69 |
70 | public Message getMessage() throws ParseException {
71 | Message message = new Message();
72 | message.setId(getId());
73 | message.setCreated(getCreated());
74 | message.setSummary(getSummary());
75 | message.setText(getText());
76 | return message;
77 | }
78 | }
79 |
--------------------------------------------------------------------------------
/src/main/java/sample/mvc/MessageController.java:
--------------------------------------------------------------------------------
1 | /*
2 | * Copyright 2012 the original author or authors.
3 | *
4 | * Licensed under the Apache License, Version 2.0 (the "License"); you may not use this file except in compliance with
5 | * the License. You may obtain a copy of the License at
6 | *
7 | * http://www.apache.org/licenses/LICENSE-2.0
8 | *
9 | * Unless required by applicable law or agreed to in writing, software distributed under the License is distributed on
10 | * an "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the License for the
11 | * specific language governing permissions and limitations under the License.
12 | */
13 | package sample.mvc;
14 |
15 | import javax.validation.Valid;
16 |
17 | import org.springframework.beans.factory.annotation.Autowired;
18 | import org.springframework.stereotype.Controller;
19 | import sample.data.Message;
20 | import sample.data.MessageRepository;
21 | import org.springframework.validation.BindingResult;
22 | import org.springframework.web.bind.annotation.ModelAttribute;
23 | import org.springframework.web.bind.annotation.PathVariable;
24 | import org.springframework.web.bind.annotation.RequestMapping;
25 | import org.springframework.web.bind.annotation.RequestMethod;
26 | import org.springframework.web.servlet.ModelAndView;
27 | import org.springframework.web.servlet.mvc.support.RedirectAttributes;
28 |
29 | /**
30 | *
31 | * @author Rob Winch
32 | *
33 | */
34 | @Controller
35 | @RequestMapping("/messages/")
36 | public class MessageController {
37 | private MessageRepository messageRepository;
38 |
39 | @Autowired
40 | public MessageController(MessageRepository messageRepository) {
41 | this.messageRepository = messageRepository;
42 | }
43 |
44 | @RequestMapping
45 | public ModelAndView list() {
46 | Iterable messages = messageRepository.findAll();
47 | return new ModelAndView("messages/list", "messages", messages);
48 | }
49 |
50 | @RequestMapping("{id}")
51 | public ModelAndView view(@PathVariable("id")
52 | Message message) {
53 | return new ModelAndView("messages/view", "message", message);
54 | }
55 |
56 | @RequestMapping(value = "form", method = RequestMethod.GET)
57 | public String createForm(@ModelAttribute
58 | Message message) {
59 | return "messages/form";
60 | }
61 |
62 | @RequestMapping(method = RequestMethod.POST)
63 | public ModelAndView create(@Valid
64 | Message message, BindingResult result, RedirectAttributes redirect) {
65 | if (result.hasErrors()) {
66 | return new ModelAndView("messages/form");
67 | }
68 | message = messageRepository.save(message);
69 | redirect.addFlashAttribute("globalMessage", "Successfully created a new message");
70 | return new ModelAndView("redirect:/messages/{message.id}", "message.id", message.getId());
71 | }
72 | }
73 |
--------------------------------------------------------------------------------
/src/main/java/sample/config/DataConfig.java:
--------------------------------------------------------------------------------
1 | /*
2 | * Copyright 2002-2013 the original author or authors.
3 | *
4 | * Licensed under the Apache License, Version 2.0 (the "License"); you may not
5 | * use this file except in compliance with the License. You may obtain a copy of
6 | * the License at
7 | *
8 | * http://www.apache.org/licenses/LICENSE-2.0
9 | *
10 | * Unless required by applicable law or agreed to in writing, software
11 | * distributed under the License is distributed on an "AS IS" BASIS, WITHOUT
12 | * WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the
13 | * License for the specific language governing permissions and limitations under
14 | * the License.
15 | */
16 | package sample.config;
17 |
18 | import javax.sql.DataSource;
19 |
20 | import org.springframework.context.annotation.Bean;
21 | import org.springframework.context.annotation.Configuration;
22 | import org.springframework.context.annotation.DependsOn;
23 | import org.springframework.core.io.ClassPathResource;
24 | import org.springframework.data.jpa.repository.config.EnableJpaRepositories;
25 | import org.springframework.jdbc.datasource.embedded.EmbeddedDatabaseBuilder;
26 | import org.springframework.jdbc.datasource.embedded.EmbeddedDatabaseType;
27 | import org.springframework.jdbc.datasource.init.ResourceDatabasePopulator;
28 | import org.springframework.orm.jpa.JpaTransactionManager;
29 | import org.springframework.orm.jpa.LocalContainerEntityManagerFactoryBean;
30 | import org.springframework.orm.jpa.vendor.Database;
31 | import org.springframework.orm.jpa.vendor.HibernateJpaVendorAdapter;
32 | import sample.data.Message;
33 | import org.springframework.transaction.PlatformTransactionManager;
34 | import sample.data.MessageRepository;
35 |
36 |
37 | @Configuration
38 | @EnableJpaRepositories(basePackageClasses = MessageRepository.class)
39 | public class DataConfig {
40 |
41 | @Bean
42 | public DataSource dataSource() {
43 | EmbeddedDatabaseBuilder builder = new EmbeddedDatabaseBuilder();
44 | return builder.setType(EmbeddedDatabaseType.HSQL).build();
45 | }
46 |
47 | @Bean
48 | public LocalContainerEntityManagerFactoryBean entityManagerFactory() {
49 | HibernateJpaVendorAdapter vendorAdapter = new HibernateJpaVendorAdapter();
50 | vendorAdapter.setDatabase(Database.HSQL);
51 | vendorAdapter.setGenerateDdl(true);
52 |
53 | LocalContainerEntityManagerFactoryBean factory = new LocalContainerEntityManagerFactoryBean();
54 | factory.setJpaVendorAdapter(vendorAdapter);
55 | factory.setPackagesToScan(Message.class.getPackage().getName());
56 | factory.setDataSource(dataSource());
57 |
58 | return factory;
59 | }
60 |
61 | @Bean
62 | public PlatformTransactionManager transactionManager() {
63 | JpaTransactionManager txManager = new JpaTransactionManager();
64 | txManager.setEntityManagerFactory(entityManagerFactory().getObject());
65 | return txManager;
66 | }
67 | }
--------------------------------------------------------------------------------
/src/test/java/sample/config/MockDataConfig.java:
--------------------------------------------------------------------------------
1 | /*
2 | * Copyright 2002-2013 the original author or authors.
3 | *
4 | * Licensed under the Apache License, Version 2.0 (the "License"); you may not
5 | * use this file except in compliance with the License. You may obtain a copy of
6 | * the License at
7 | *
8 | * http://www.apache.org/licenses/LICENSE-2.0
9 | *
10 | * Unless required by applicable law or agreed to in writing, software
11 | * distributed under the License is distributed on an "AS IS" BASIS, WITHOUT
12 | * WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the
13 | * License for the specific language governing permissions and limitations under
14 | * the License.
15 | */
16 | package sample.config;
17 |
18 | import org.mockito.invocation.InvocationOnMock;
19 | import org.mockito.stubbing.Answer;
20 | import org.springframework.context.annotation.Bean;
21 | import org.springframework.context.annotation.Configuration;
22 | import org.springframework.context.annotation.Scope;
23 | import org.springframework.core.convert.ConversionService;
24 | import org.springframework.core.convert.converter.ConverterRegistry;
25 | import sample.data.Message;
26 | import sample.data.MessageRepository;
27 | import sample.data.mock.MockConversionService;
28 |
29 | import java.util.Calendar;
30 | import java.util.Locale;
31 |
32 | import static org.mockito.Matchers.any;
33 | import static org.mockito.Matchers.anyLong;
34 | import static org.mockito.Mockito.mock;
35 | import static org.mockito.Mockito.when;
36 |
37 | /**
38 | * @author Rob Winch
39 | */
40 | @Configuration
41 | public class MockDataConfig {
42 |
43 | @Bean
44 | public MessageRepository messageRepository() {
45 | final Message message = createMessage();
46 | MessageRepository messages = mock(MessageRepository.class);
47 | when(messages.save(any(Message.class))).thenAnswer(new Answer() {
48 | @Override
49 | public Message answer(InvocationOnMock invocation) throws Throwable {
50 | Object[] args = invocation.getArguments();
51 | Message result = (Message) args[0];
52 | result.setId(message.getId());
53 | result.setCreated(message.getCreated());
54 | return result;
55 | }
56 | });
57 | when(messages.findOne(anyLong())).thenReturn(message);
58 | return messages;
59 | }
60 |
61 | @Bean
62 | public MockConversionService conversionService(T conversionService) {
63 | return new MockConversionService(conversionService);
64 | }
65 |
66 | @Bean
67 | public Message createMessage() {
68 | Calendar created = Calendar.getInstance(Locale.ENGLISH);
69 | // we need to clear out the milliseconds since we are not interested in being that precise
70 | created.set(Calendar.MILLISECOND, 0);
71 | created.getTime().setTime(1397672456000L);
72 | Message message = new Message();
73 | message.setCreated(created);
74 | message.setId(123L);
75 | message.setSummary("Spring Rocks");
76 | message.setText("In case you didn't know, Spring Rocks!");
77 | return message;
78 | }
79 | }
80 |
--------------------------------------------------------------------------------
/src/main/java/sample/config/WebMvcConfig.java:
--------------------------------------------------------------------------------
1 | /*
2 | * Copyright 2002-2013 the original author or authors.
3 | *
4 | * Licensed under the Apache License, Version 2.0 (the "License"); you may not
5 | * use this file except in compliance with the License. You may obtain a copy of
6 | * the License at
7 | *
8 | * http://www.apache.org/licenses/LICENSE-2.0
9 | *
10 | * Unless required by applicable law or agreed to in writing, software
11 | * distributed under the License is distributed on an "AS IS" BASIS, WITHOUT
12 | * WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the
13 | * License for the specific language governing permissions and limitations under
14 | * the License.
15 | */
16 | package sample.config;
17 |
18 | import org.springframework.beans.factory.annotation.Autowired;
19 | import org.springframework.context.annotation.Bean;
20 | import org.springframework.context.annotation.ComponentScan;
21 | import org.springframework.core.Ordered;
22 | import org.springframework.data.repository.support.DomainClassConverter;
23 | import org.springframework.format.support.FormattingConversionService;
24 | import org.springframework.web.servlet.config.annotation.EnableWebMvc;
25 | import org.springframework.web.servlet.config.annotation.ResourceHandlerRegistry;
26 | import org.springframework.web.servlet.config.annotation.ViewControllerRegistry;
27 | import org.springframework.web.servlet.config.annotation.WebMvcConfigurerAdapter;
28 | import org.thymeleaf.spring4.SpringTemplateEngine;
29 | import org.thymeleaf.spring4.view.ThymeleafViewResolver;
30 | import org.thymeleaf.templateresolver.ServletContextTemplateResolver;
31 | import org.thymeleaf.templateresolver.TemplateResolver;
32 | import sample.mvc.MessageController;
33 |
34 | @EnableWebMvc
35 | @ComponentScan(basePackageClasses = MessageController.class)
36 | public class WebMvcConfig extends WebMvcConfigurerAdapter {
37 |
38 | @Autowired
39 | private FormattingConversionService mvcConversionService;
40 |
41 | @Override
42 | public void addViewControllers(ViewControllerRegistry registry) {
43 | registry.addViewController("/login").setViewName("login");
44 | registry.setOrder(Ordered.HIGHEST_PRECEDENCE);
45 | }
46 |
47 | @Override
48 | public void addResourceHandlers(ResourceHandlerRegistry registry) {
49 | registry
50 | .addResourceHandler("/resources/**")
51 | .addResourceLocations("/resources/")
52 | .setCachePeriod(31556926);
53 | registry.setOrder(Ordered.HIGHEST_PRECEDENCE);
54 | }
55 |
56 | @Bean
57 | public TemplateResolver templateResolver() {
58 | TemplateResolver result = new ServletContextTemplateResolver();
59 | result.setPrefix("/WEB-INF/templates/");
60 | result.setSuffix(".html");
61 | result.setTemplateMode("HTML5");
62 | return result;
63 | }
64 |
65 | @Bean
66 | public SpringTemplateEngine templateEngine(TemplateResolver templateResolver) {
67 | SpringTemplateEngine templateEngine = new SpringTemplateEngine();
68 | templateEngine.setTemplateResolver(templateResolver);
69 | return templateEngine;
70 | }
71 |
72 | @Bean
73 | public ThymeleafViewResolver viewResolver(SpringTemplateEngine templateEngine) {
74 | ThymeleafViewResolver viewResolver = new ThymeleafViewResolver();
75 | viewResolver.setTemplateEngine(templateEngine);
76 | return viewResolver;
77 | }
78 |
79 | @Bean
80 | public DomainClassConverter> domainClassConverter() {
81 | return new DomainClassConverter(mvcConversionService);
82 | }
83 | }
--------------------------------------------------------------------------------
/src/test/java/sample/data/mock/MockConversionService.java:
--------------------------------------------------------------------------------
1 | /*
2 | * Copyright 2012 the original author or authors.
3 | *
4 | * Licensed under the Apache License, Version 2.0 (the "License"); you may not use this file except in compliance with
5 | * the License. You may obtain a copy of the License at
6 | *
7 | * http://www.apache.org/licenses/LICENSE-2.0
8 | *
9 | * Unless required by applicable law or agreed to in writing, software distributed under the License is distributed on
10 | * an "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the License for the
11 | * specific language governing permissions and limitations under the License.
12 | */
13 | package sample.data.mock;
14 |
15 | import java.io.Serializable;
16 | import java.util.Collection;
17 | import java.util.Collections;
18 | import java.util.Set;
19 |
20 | import org.springframework.context.ApplicationContext;
21 | import org.springframework.context.ApplicationContextAware;
22 | import org.springframework.core.GenericTypeResolver;
23 | import org.springframework.core.convert.ConversionService;
24 | import org.springframework.core.convert.TypeDescriptor;
25 | import org.springframework.core.convert.converter.ConditionalGenericConverter;
26 | import org.springframework.core.convert.converter.ConverterRegistry;
27 | import org.springframework.data.repository.CrudRepository;
28 | import org.springframework.data.repository.support.DomainClassConverter;
29 | import sample.mvc.MessageController;
30 |
31 | /**
32 | * Allows using Mock {@link CrudRepository} instances (i.e. using Mockito) and still support converting from a String to
33 | * a domain object. This is used internally by Spring on methods like
34 | * {@link MessageController#view(sample.data.Message)}
35 | *
36 | * @author Rob Winch
37 | *
38 | * @param
39 | * @see DomainClassConverter
40 | */
41 | public class MockConversionService implements ApplicationContextAware,
42 | ConditionalGenericConverter {
43 | @SuppressWarnings("rawtypes")
44 | private Collection repositories;
45 |
46 | private final T conversionService;
47 |
48 | public MockConversionService(T conversionService) {
49 | this.conversionService = conversionService;
50 | }
51 |
52 | public Set getConvertibleTypes() {
53 | return Collections.singleton(new ConvertiblePair(Object.class, Object.class));
54 | }
55 |
56 | public Object convert(Object source, TypeDescriptor sourceType, TypeDescriptor targetType) {
57 | CrudRepository repo = getRepository(targetType.getType(), sourceType.getType());
58 | return repo == null ? null : repo.findOne((Serializable) source);
59 | }
60 |
61 | public boolean matches(TypeDescriptor sourceType, TypeDescriptor targetType) {
62 | return getRepository(targetType.getType(), sourceType.getType()) != null;
63 | }
64 |
65 | public void setApplicationContext(ApplicationContext context) {
66 | this.repositories = context.getBeansOfType(CrudRepository.class).values();
67 | this.conversionService.addConverter(this);
68 | }
69 |
70 | private CrudRepository getRepository(Class> domainClass, Class> idClass) {
71 | for (CrudRepository repository : repositories) {
72 | Class>[] typeArgs = GenericTypeResolver.resolveTypeArguments(repository.getClass(), CrudRepository.class);
73 | if (domainClass.equals(typeArgs[0]) && conversionService.canConvert(typeArgs[1], idClass)) {
74 | return repository;
75 | }
76 | }
77 | return null;
78 | }
79 | }
80 |
--------------------------------------------------------------------------------
/src/test/java/org/springframework/security/test/web/servlet/showcase/csrf/DefaultCsrfShowcaseTests.java:
--------------------------------------------------------------------------------
1 | /*
2 | * Copyright 2002-2014 the original author or authors.
3 | *
4 | * Licensed under the Apache License, Version 2.0 (the "License");
5 | * you may not use this file except in compliance with the License.
6 | * You may obtain a copy of the License at
7 | *
8 | * http://www.apache.org/licenses/LICENSE-2.0
9 | *
10 | * Unless required by applicable law or agreed to in writing, software
11 | * distributed under the License is distributed on an "AS IS" BASIS,
12 | * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13 | * See the License for the specific language governing permissions and
14 | * limitations under the License.
15 | */
16 | package org.springframework.security.test.web.servlet.showcase.csrf;
17 | import static org.springframework.security.test.web.servlet.request.SecurityMockMvcRequestPostProcessors.*;
18 | import static org.springframework.test.web.servlet.request.MockMvcRequestBuilders.*;
19 | import static org.springframework.test.web.servlet.result.MockMvcResultMatchers.*;
20 |
21 | import javax.servlet.Filter;
22 |
23 | import org.junit.Before;
24 | import org.junit.Test;
25 | import org.junit.runner.RunWith;
26 | import org.springframework.beans.factory.annotation.Autowired;
27 | import org.springframework.context.annotation.Configuration;
28 | import org.springframework.security.config.annotation.authentication.builders.AuthenticationManagerBuilder;
29 | import org.springframework.security.config.annotation.web.builders.HttpSecurity;
30 | import org.springframework.security.config.annotation.web.configuration.WebSecurityConfigurerAdapter;
31 | import org.springframework.security.config.annotation.web.servlet.configuration.EnableWebMvcSecurity;
32 | import org.springframework.test.context.ContextConfiguration;
33 | import org.springframework.test.context.junit4.SpringJUnit4ClassRunner;
34 | import org.springframework.test.context.web.WebAppConfiguration;
35 | import org.springframework.test.web.servlet.MockMvc;
36 | import org.springframework.test.web.servlet.setup.MockMvcBuilders;
37 | import org.springframework.web.context.WebApplicationContext;
38 | import org.springframework.web.servlet.config.annotation.EnableWebMvc;
39 |
40 | @RunWith(SpringJUnit4ClassRunner.class)
41 | @ContextConfiguration
42 | @WebAppConfiguration
43 | public class DefaultCsrfShowcaseTests {
44 |
45 | @Autowired
46 | private WebApplicationContext context;
47 |
48 | @Autowired
49 | private Filter springSecurityFilterChain;
50 |
51 | private MockMvc mvc;
52 |
53 | @Before
54 | public void setup() {
55 | mvc = MockMvcBuilders
56 | .webAppContextSetup(context)
57 | .defaultRequest(get("/").with(csrf()))
58 | .addFilters(springSecurityFilterChain)
59 | .build();
60 | }
61 |
62 | @Test
63 | public void postWithCsrfWorks() throws Exception {
64 | mvc
65 | .perform(post("/"))
66 | .andExpect(status().isNotFound());
67 | }
68 |
69 | @Test
70 | public void postWithCsrfWorksWithPut() throws Exception {
71 | mvc
72 | .perform(put("/"))
73 | .andExpect(status().isNotFound());
74 | }
75 |
76 | @Configuration
77 | @EnableWebMvcSecurity
78 | @EnableWebMvc
79 | static class Config extends WebSecurityConfigurerAdapter {
80 |
81 | @Override
82 | protected void configure(HttpSecurity http) throws Exception {
83 | }
84 |
85 | @Autowired
86 | public void configureGlobal(AuthenticationManagerBuilder auth) throws Exception {
87 | auth
88 | .inMemoryAuthentication()
89 | .withUser("user").password("password").roles("USER");
90 | }
91 | }
92 | }
93 |
--------------------------------------------------------------------------------
/src/test/java/org/springframework/security/test/web/servlet/showcase/csrf/CsrfShowcaseTests.java:
--------------------------------------------------------------------------------
1 | /*
2 | * Copyright 2002-2014 the original author or authors.
3 | *
4 | * Licensed under the Apache License, Version 2.0 (the "License");
5 | * you may not use this file except in compliance with the License.
6 | * You may obtain a copy of the License at
7 | *
8 | * http://www.apache.org/licenses/LICENSE-2.0
9 | *
10 | * Unless required by applicable law or agreed to in writing, software
11 | * distributed under the License is distributed on an "AS IS" BASIS,
12 | * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13 | * See the License for the specific language governing permissions and
14 | * limitations under the License.
15 | */
16 | package org.springframework.security.test.web.servlet.showcase.csrf;
17 | import static org.springframework.security.test.web.servlet.request.SecurityMockMvcRequestPostProcessors.*;
18 | import static org.springframework.test.web.servlet.request.MockMvcRequestBuilders.*;
19 | import static org.springframework.test.web.servlet.result.MockMvcResultMatchers.*;
20 |
21 | import javax.servlet.Filter;
22 |
23 | import org.junit.Before;
24 | import org.junit.Test;
25 | import org.junit.runner.RunWith;
26 | import org.springframework.beans.factory.annotation.Autowired;
27 | import org.springframework.context.annotation.Configuration;
28 | import org.springframework.security.config.annotation.authentication.builders.AuthenticationManagerBuilder;
29 | import org.springframework.security.config.annotation.web.builders.HttpSecurity;
30 | import org.springframework.security.config.annotation.web.configuration.WebSecurityConfigurerAdapter;
31 | import org.springframework.security.config.annotation.web.servlet.configuration.EnableWebMvcSecurity;
32 | import org.springframework.test.context.ContextConfiguration;
33 | import org.springframework.test.context.junit4.SpringJUnit4ClassRunner;
34 | import org.springframework.test.context.web.WebAppConfiguration;
35 | import org.springframework.test.web.servlet.MockMvc;
36 | import org.springframework.test.web.servlet.setup.MockMvcBuilders;
37 | import org.springframework.web.context.WebApplicationContext;
38 | import org.springframework.web.servlet.config.annotation.EnableWebMvc;
39 |
40 | @RunWith(SpringJUnit4ClassRunner.class)
41 | @ContextConfiguration
42 | @WebAppConfiguration
43 | public class CsrfShowcaseTests {
44 |
45 | @Autowired
46 | private WebApplicationContext context;
47 |
48 | @Autowired
49 | private Filter springSecurityFilterChain;
50 |
51 | private MockMvc mvc;
52 |
53 | @Before
54 | public void setup() {
55 | mvc = MockMvcBuilders
56 | .webAppContextSetup(context)
57 | .addFilters(springSecurityFilterChain)
58 | .build();
59 | }
60 |
61 | @Test
62 | public void postWithCsrfWorks() throws Exception {
63 | mvc
64 | .perform(post("/").with(csrf()))
65 | .andExpect(status().isNotFound());
66 | }
67 |
68 | @Test
69 | public void postWithCsrfWorksWithPut() throws Exception {
70 | mvc
71 | .perform(put("/").with(csrf()))
72 | .andExpect(status().isNotFound());
73 | }
74 |
75 | @Test
76 | public void postWithNoCsrfForbidden() throws Exception {
77 | mvc
78 | .perform(post("/"))
79 | .andExpect(status().isForbidden());
80 | }
81 |
82 | @Configuration
83 | @EnableWebMvcSecurity
84 | @EnableWebMvc
85 | static class Config extends WebSecurityConfigurerAdapter {
86 |
87 | @Override
88 | protected void configure(HttpSecurity http) throws Exception {
89 | }
90 |
91 | @Autowired
92 | public void configureGlobal(AuthenticationManagerBuilder auth) throws Exception {
93 | auth
94 | .inMemoryAuthentication()
95 | .withUser("user").password("password").roles("USER");
96 | }
97 | }
98 | }
99 |
--------------------------------------------------------------------------------
/src/test/java/org/springframework/security/test/context/showcase/WithMockUserTests.java:
--------------------------------------------------------------------------------
1 | /*
2 | * Copyright 2002-2013 the original author or authors.
3 | *
4 | * Licensed under the Apache License, Version 2.0 (the "License"); you may not
5 | * use this file except in compliance with the License. You may obtain a copy of
6 | * the License at
7 | *
8 | * http://www.apache.org/licenses/LICENSE-2.0
9 | *
10 | * Unless required by applicable law or agreed to in writing, software
11 | * distributed under the License is distributed on an "AS IS" BASIS, WITHOUT
12 | * WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the
13 | * License for the specific language governing permissions and limitations under
14 | * the License.
15 | */
16 | package org.springframework.security.test.context.showcase;
17 |
18 | import static org.fest.assertions.Assertions.assertThat;
19 |
20 | import org.junit.Test;
21 | import org.junit.runner.RunWith;
22 | import org.springframework.beans.factory.annotation.Autowired;
23 | import org.springframework.context.annotation.ComponentScan;
24 | import org.springframework.context.annotation.Configuration;
25 | import org.springframework.security.authentication.AuthenticationCredentialsNotFoundException;
26 | import org.springframework.security.config.annotation.authentication.builders.AuthenticationManagerBuilder;
27 | import org.springframework.security.config.annotation.method.configuration.EnableGlobalMethodSecurity;
28 | import org.springframework.security.test.context.showcase.service.HelloMessageService;
29 | import org.springframework.security.test.context.showcase.service.MessageService;
30 | import org.springframework.security.test.context.support.WithMockUser;
31 | import org.springframework.security.test.context.support.WithSecurityContextTestExcecutionListener;
32 | import org.springframework.test.context.ContextConfiguration;
33 | import org.springframework.test.context.TestExecutionListeners;
34 | import org.springframework.test.context.junit4.SpringJUnit4ClassRunner;
35 | import org.springframework.test.context.support.DependencyInjectionTestExecutionListener;
36 | import org.springframework.test.context.support.DirtiesContextTestExecutionListener;
37 | import org.springframework.test.context.transaction.TransactionalTestExecutionListener;
38 | import org.springframework.test.context.web.ServletTestExecutionListener;
39 |
40 | /**
41 | * @author Rob Winch
42 | */
43 |
44 | @RunWith(SpringJUnit4ClassRunner.class)
45 | @ContextConfiguration
46 | @TestExecutionListeners(listeners={ServletTestExecutionListener.class,
47 | DependencyInjectionTestExecutionListener.class,
48 | DirtiesContextTestExecutionListener.class,
49 | TransactionalTestExecutionListener.class,
50 | WithSecurityContextTestExcecutionListener.class})
51 | public class WithMockUserTests {
52 | @Autowired
53 | private MessageService messageService;
54 |
55 | @Test(expected = AuthenticationCredentialsNotFoundException.class)
56 | public void getMessageUnauthenticated() {
57 | messageService.getMessage();
58 | }
59 |
60 | @Test
61 | @WithMockUser
62 | public void getMessageWithMockUser() {
63 | String message = messageService.getMessage();
64 | assertThat(message).contains("user");
65 | }
66 |
67 | @Test
68 | @WithMockUser("customUsername")
69 | public void getMessageWithMockUserCustomUsername() {
70 | String message = messageService.getMessage();
71 | assertThat(message).contains("customUsername");
72 | }
73 |
74 | @Test
75 | @WithMockUser(username="admin",roles={"USER","ADMIN"})
76 | public void getMessageWithMockUserCustomUser() {
77 | String message = messageService.getMessage();
78 | assertThat(message).contains("admin").contains("ROLE_USER").contains("ROLE_ADMIN");
79 | }
80 |
81 | @Configuration
82 | @EnableGlobalMethodSecurity(prePostEnabled = true)
83 | @ComponentScan(basePackageClasses = HelloMessageService.class)
84 | static class Config {
85 | @Autowired
86 | public void configureGlobal(AuthenticationManagerBuilder auth) throws Exception {
87 | auth
88 | .inMemoryAuthentication()
89 | .withUser("user").password("password").roles("USER");
90 | }
91 | }
92 | }
--------------------------------------------------------------------------------
/src/test/java/org/springframework/security/test/web/servlet/showcase/csrf/CustomCsrfShowcaseTests.java:
--------------------------------------------------------------------------------
1 | /*
2 | * Copyright 2002-2014 the original author or authors.
3 | *
4 | * Licensed under the Apache License, Version 2.0 (the "License");
5 | * you may not use this file except in compliance with the License.
6 | * You may obtain a copy of the License at
7 | *
8 | * http://www.apache.org/licenses/LICENSE-2.0
9 | *
10 | * Unless required by applicable law or agreed to in writing, software
11 | * distributed under the License is distributed on an "AS IS" BASIS,
12 | * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13 | * See the License for the specific language governing permissions and
14 | * limitations under the License.
15 | */
16 | package org.springframework.security.test.web.servlet.showcase.csrf;
17 | import static org.springframework.security.test.web.servlet.request.SecurityMockMvcRequestPostProcessors.*;
18 | import static org.springframework.test.web.servlet.request.MockMvcRequestBuilders.*;
19 | import static org.springframework.test.web.servlet.result.MockMvcResultMatchers.*;
20 |
21 | import javax.servlet.Filter;
22 |
23 | import org.junit.Before;
24 | import org.junit.Test;
25 | import org.junit.runner.RunWith;
26 | import org.springframework.beans.factory.annotation.Autowired;
27 | import org.springframework.context.annotation.Bean;
28 | import org.springframework.context.annotation.Configuration;
29 | import org.springframework.security.config.annotation.authentication.builders.AuthenticationManagerBuilder;
30 | import org.springframework.security.config.annotation.web.builders.HttpSecurity;
31 | import org.springframework.security.config.annotation.web.configuration.WebSecurityConfigurerAdapter;
32 | import org.springframework.security.config.annotation.web.servlet.configuration.EnableWebMvcSecurity;
33 | import org.springframework.security.web.csrf.CsrfTokenRepository;
34 | import org.springframework.security.web.csrf.HttpSessionCsrfTokenRepository;
35 | import org.springframework.test.context.ContextConfiguration;
36 | import org.springframework.test.context.junit4.SpringJUnit4ClassRunner;
37 | import org.springframework.test.context.web.WebAppConfiguration;
38 | import org.springframework.test.web.servlet.MockMvc;
39 | import org.springframework.test.web.servlet.setup.MockMvcBuilders;
40 | import org.springframework.web.context.WebApplicationContext;
41 | import org.springframework.web.servlet.config.annotation.EnableWebMvc;
42 |
43 | @RunWith(SpringJUnit4ClassRunner.class)
44 | @ContextConfiguration
45 | @WebAppConfiguration
46 | public class CustomCsrfShowcaseTests {
47 |
48 | @Autowired
49 | private WebApplicationContext context;
50 |
51 | @Autowired
52 | private Filter springSecurityFilterChain;
53 |
54 | @Autowired
55 | private CsrfTokenRepository repository;
56 |
57 | private MockMvc mvc;
58 |
59 | @Before
60 | public void setup() {
61 | mvc = MockMvcBuilders
62 | .webAppContextSetup(context)
63 | .defaultRequest(get("/").with(csrf()))
64 | .addFilters(springSecurityFilterChain)
65 | .build();
66 | }
67 |
68 | @Test
69 | public void postWithCsrfWorks() throws Exception {
70 | mvc
71 | .perform(post("/").with(csrf()))
72 | .andExpect(status().isNotFound());
73 | }
74 |
75 | @Test
76 | public void postWithCsrfWorksWithPut() throws Exception {
77 | mvc
78 | .perform(put("/").with(csrf()))
79 | .andExpect(status().isNotFound());
80 | }
81 |
82 | @Configuration
83 | @EnableWebMvcSecurity
84 | @EnableWebMvc
85 | static class Config extends WebSecurityConfigurerAdapter {
86 |
87 | @Override
88 | protected void configure(HttpSecurity http) throws Exception {
89 | http
90 | .csrf()
91 | .csrfTokenRepository(repo());
92 | }
93 |
94 | @Autowired
95 | public void configureGlobal(AuthenticationManagerBuilder auth) throws Exception {
96 | auth
97 | .inMemoryAuthentication()
98 | .withUser("user").password("password").roles("USER");
99 | }
100 |
101 | @Bean
102 | public CsrfTokenRepository repo() {
103 | HttpSessionCsrfTokenRepository repo = new HttpSessionCsrfTokenRepository();
104 | repo.setParameterName("custom_csrf");
105 | return repo;
106 | }
107 | }
108 | }
109 |
--------------------------------------------------------------------------------
/src/test/java/org/springframework/security/test/web/servlet/showcase/login/AuthenticationTests.java:
--------------------------------------------------------------------------------
1 | /*
2 | * Copyright 2002-2014 the original author or authors.
3 | *
4 | * Licensed under the Apache License, Version 2.0 (the "License");
5 | * you may not use this file except in compliance with the License.
6 | * You may obtain a copy of the License at
7 | *
8 | * http://www.apache.org/licenses/LICENSE-2.0
9 | *
10 | * Unless required by applicable law or agreed to in writing, software
11 | * distributed under the License is distributed on an "AS IS" BASIS,
12 | * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13 | * See the License for the specific language governing permissions and
14 | * limitations under the License.
15 | */
16 | package org.springframework.security.test.web.servlet.showcase.login;
17 |
18 | import static org.springframework.security.test.web.servlet.request.SecurityMockMvcRequestBuilders.*;
19 | import static org.springframework.security.test.web.servlet.response.SecurityMockMvcResultMatchers.*;
20 | import static org.springframework.test.web.servlet.request.MockMvcRequestBuilders.*;
21 | import static org.springframework.test.web.servlet.result.MockMvcResultMatchers.*;
22 | import static org.springframework.security.test.web.servlet.request.SecurityMockMvcRequestPostProcessors.*;
23 |
24 | import javax.servlet.Filter;
25 |
26 | import org.junit.Before;
27 | import org.junit.Test;
28 | import org.junit.runner.RunWith;
29 | import org.springframework.beans.factory.annotation.Autowired;
30 | import org.springframework.context.annotation.Configuration;
31 | import org.springframework.security.config.annotation.authentication.builders.AuthenticationManagerBuilder;
32 | import org.springframework.security.config.annotation.web.configuration.WebSecurityConfigurerAdapter;
33 | import org.springframework.security.config.annotation.web.servlet.configuration.EnableWebMvcSecurity;
34 | import org.springframework.test.context.ContextConfiguration;
35 | import org.springframework.test.context.junit4.SpringJUnit4ClassRunner;
36 | import org.springframework.test.context.web.WebAppConfiguration;
37 | import org.springframework.test.web.servlet.MockMvc;
38 | import org.springframework.test.web.servlet.setup.MockMvcBuilders;
39 | import org.springframework.web.context.WebApplicationContext;
40 | import org.springframework.web.servlet.config.annotation.EnableWebMvc;
41 |
42 | @RunWith(SpringJUnit4ClassRunner.class)
43 | @ContextConfiguration
44 | @WebAppConfiguration
45 | public class AuthenticationTests {
46 |
47 | @Autowired
48 | private WebApplicationContext context;
49 |
50 | @Autowired
51 | private Filter springSecurityFilterChain;
52 |
53 | private MockMvc mvc;
54 |
55 | @Before
56 | public void setup() {
57 | mvc = MockMvcBuilders
58 | .webAppContextSetup(context)
59 | .addFilters(springSecurityFilterChain)
60 | .build();
61 | }
62 |
63 | @Test
64 | public void requiresAuthentication() throws Exception {
65 | mvc
66 | .perform(get("/"))
67 | .andExpect(status().isMovedTemporarily());
68 | }
69 |
70 | @Test
71 | public void httpBasicAuthenticationSuccess() throws Exception {
72 | mvc
73 | .perform(get("/secured/butnotfound").with(httpBasic("user","password")))
74 | .andExpect(status().isNotFound())
75 | .andExpect(authenticated().withUsername("user"));
76 | }
77 |
78 | @Test
79 | public void authenticationSuccess() throws Exception {
80 | mvc
81 | .perform(formLogin())
82 | .andExpect(status().isMovedTemporarily())
83 | .andExpect(redirectedUrl("/"))
84 | .andExpect(authenticated().withUsername("user"));
85 | }
86 |
87 | @Test
88 | public void authenticationFailed() throws Exception {
89 | mvc
90 | .perform(formLogin().user("user").password("invalid"))
91 | .andExpect(status().isMovedTemporarily())
92 | .andExpect(redirectedUrl("/login?error"))
93 | .andExpect(unauthenticated());
94 | }
95 |
96 | @Configuration
97 | @EnableWebMvcSecurity
98 | @EnableWebMvc
99 | static class Config extends WebSecurityConfigurerAdapter {
100 | @Autowired
101 | public void configureGlobal(AuthenticationManagerBuilder auth) throws Exception {
102 | auth
103 | .inMemoryAuthentication()
104 | .withUser("user").password("password").roles("USER");
105 | }
106 | }
107 | }
--------------------------------------------------------------------------------
/src/test/java/org/springframework/security/test/web/servlet/showcase/secured/DefaultfSecurityRequestsTests.java:
--------------------------------------------------------------------------------
1 | /*
2 | * Copyright 2002-2014 the original author or authors.
3 | *
4 | * Licensed under the Apache License, Version 2.0 (the "License");
5 | * you may not use this file except in compliance with the License.
6 | * You may obtain a copy of the License at
7 | *
8 | * http://www.apache.org/licenses/LICENSE-2.0
9 | *
10 | * Unless required by applicable law or agreed to in writing, software
11 | * distributed under the License is distributed on an "AS IS" BASIS,
12 | * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13 | * See the License for the specific language governing permissions and
14 | * limitations under the License.
15 | */
16 | package org.springframework.security.test.web.servlet.showcase.secured;
17 |
18 | import static org.springframework.security.test.web.servlet.request.SecurityMockMvcRequestPostProcessors.*;
19 | import static org.springframework.security.test.web.servlet.response.SecurityMockMvcResultMatchers.*;
20 | import static org.springframework.test.web.servlet.request.MockMvcRequestBuilders.*;
21 | import static org.springframework.test.web.servlet.result.MockMvcResultMatchers.*;
22 |
23 | import javax.servlet.Filter;
24 |
25 | import org.junit.Before;
26 | import org.junit.Test;
27 | import org.junit.runner.RunWith;
28 | import org.springframework.beans.factory.annotation.Autowired;
29 | import org.springframework.context.annotation.Configuration;
30 | import org.springframework.security.config.annotation.authentication.builders.AuthenticationManagerBuilder;
31 | import org.springframework.security.config.annotation.web.builders.HttpSecurity;
32 | import org.springframework.security.config.annotation.web.configuration.WebSecurityConfigurerAdapter;
33 | import org.springframework.security.config.annotation.web.servlet.configuration.EnableWebMvcSecurity;
34 | import org.springframework.test.context.ContextConfiguration;
35 | import org.springframework.test.context.junit4.SpringJUnit4ClassRunner;
36 | import org.springframework.test.context.web.WebAppConfiguration;
37 | import org.springframework.test.web.servlet.MockMvc;
38 | import org.springframework.test.web.servlet.setup.MockMvcBuilders;
39 | import org.springframework.web.context.WebApplicationContext;
40 | import org.springframework.web.servlet.config.annotation.EnableWebMvc;
41 |
42 | @RunWith(SpringJUnit4ClassRunner.class)
43 | @ContextConfiguration
44 | @WebAppConfiguration
45 | public class DefaultfSecurityRequestsTests {
46 |
47 | @Autowired
48 | private WebApplicationContext context;
49 |
50 | @Autowired
51 | private Filter springSecurityFilterChain;
52 |
53 | private MockMvc mvc;
54 |
55 | @Before
56 | public void setup() {
57 | mvc = MockMvcBuilders
58 | .webAppContextSetup(context)
59 | .defaultRequest(get("/").with(user("user").roles("ADMIN")))
60 | .addFilters(springSecurityFilterChain)
61 | .build();
62 | }
63 |
64 | @Test
65 | public void requestProtectedUrlWithUser() throws Exception {
66 | mvc
67 | .perform(get("/"))
68 | // Ensure we got past Security
69 | .andExpect(status().isNotFound())
70 | // Ensure it appears we are authenticated with user
71 | .andExpect(authenticated().withUsername("user"));
72 | }
73 |
74 | @Test
75 | public void requestProtectedUrlWithAdmin() throws Exception {
76 | mvc
77 | .perform(get("/admin"))
78 | // Ensure we got past Security
79 | .andExpect(status().isNotFound())
80 | // Ensure it appears we are authenticated with user
81 | .andExpect(authenticated().withUsername("user"));
82 | }
83 |
84 | @Configuration
85 | @EnableWebMvcSecurity
86 | @EnableWebMvc
87 | static class Config extends WebSecurityConfigurerAdapter {
88 |
89 | @Override
90 | protected void configure(HttpSecurity http) throws Exception {
91 | http
92 | .authorizeRequests()
93 | .antMatchers("/admin/**").hasRole("ADMIN")
94 | .anyRequest().authenticated()
95 | .and()
96 | .formLogin();
97 | }
98 |
99 | @Autowired
100 | public void configureGlobal(AuthenticationManagerBuilder auth) throws Exception {
101 | auth
102 | .inMemoryAuthentication()
103 | .withUser("user").password("password").roles("USER");
104 | }
105 | }
106 | }
--------------------------------------------------------------------------------
/src/test/java/org/springframework/security/test/web/servlet/showcase/login/CustomLoginRequestBuilderAuthenticationTests.java:
--------------------------------------------------------------------------------
1 | /*
2 | * Copyright 2002-2014 the original author or authors.
3 | *
4 | * Licensed under the Apache License, Version 2.0 (the "License");
5 | * you may not use this file except in compliance with the License.
6 | * You may obtain a copy of the License at
7 | *
8 | * http://www.apache.org/licenses/LICENSE-2.0
9 | *
10 | * Unless required by applicable law or agreed to in writing, software
11 | * distributed under the License is distributed on an "AS IS" BASIS,
12 | * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13 | * See the License for the specific language governing permissions and
14 | * limitations under the License.
15 | */
16 | package org.springframework.security.test.web.servlet.showcase.login;
17 |
18 | import static org.springframework.security.test.web.servlet.response.SecurityMockMvcResultMatchers.*;
19 | import static org.springframework.test.web.servlet.result.MockMvcResultMatchers.*;
20 |
21 | import javax.servlet.Filter;
22 |
23 | import org.junit.Before;
24 | import org.junit.Test;
25 | import org.junit.runner.RunWith;
26 | import org.springframework.beans.factory.annotation.Autowired;
27 | import org.springframework.context.annotation.Configuration;
28 | import org.springframework.security.config.annotation.authentication.builders.AuthenticationManagerBuilder;
29 | import org.springframework.security.config.annotation.web.builders.HttpSecurity;
30 | import org.springframework.security.config.annotation.web.configuration.WebSecurityConfigurerAdapter;
31 | import org.springframework.security.config.annotation.web.servlet.configuration.EnableWebMvcSecurity;
32 | import org.springframework.security.test.web.servlet.request.SecurityMockMvcRequestBuilders;
33 | import org.springframework.security.test.web.servlet.request.SecurityMockMvcRequestBuilders.FormLoginRequestBuilder;
34 | import org.springframework.test.context.ContextConfiguration;
35 | import org.springframework.test.context.junit4.SpringJUnit4ClassRunner;
36 | import org.springframework.test.context.web.WebAppConfiguration;
37 | import org.springframework.test.web.servlet.MockMvc;
38 | import org.springframework.test.web.servlet.setup.MockMvcBuilders;
39 | import org.springframework.web.context.WebApplicationContext;
40 | import org.springframework.web.servlet.config.annotation.EnableWebMvc;
41 |
42 | @RunWith(SpringJUnit4ClassRunner.class)
43 | @ContextConfiguration
44 | @WebAppConfiguration
45 | public class CustomLoginRequestBuilderAuthenticationTests {
46 |
47 | @Autowired
48 | private WebApplicationContext context;
49 |
50 | @Autowired
51 | private Filter springSecurityFilterChain;
52 |
53 | private MockMvc mvc;
54 |
55 | @Before
56 | public void setup() {
57 | mvc = MockMvcBuilders
58 | .webAppContextSetup(context)
59 | .addFilters(springSecurityFilterChain)
60 | .build();
61 | }
62 |
63 | @Test
64 | public void authenticationSuccess() throws Exception {
65 | mvc
66 | .perform(login())
67 | .andExpect(status().isMovedTemporarily())
68 | .andExpect(redirectedUrl("/"))
69 | .andExpect(authenticated().withUsername("user"));
70 | }
71 |
72 | @Test
73 | public void authenticationFailed() throws Exception {
74 | mvc
75 | .perform(login().user("notfound").password("invalid"))
76 | .andExpect(status().isMovedTemporarily())
77 | .andExpect(redirectedUrl("/authenticate?error"))
78 | .andExpect(unauthenticated());
79 | }
80 |
81 | static FormLoginRequestBuilder login() {
82 | return SecurityMockMvcRequestBuilders
83 | .formLogin("/authenticate")
84 | .userParameter("user")
85 | .passwordParam("pass");
86 | }
87 |
88 | @Configuration
89 | @EnableWebMvcSecurity
90 | @EnableWebMvc
91 | static class Config extends WebSecurityConfigurerAdapter {
92 |
93 | @Override
94 | protected void configure(HttpSecurity http) throws Exception {
95 | http
96 | .authorizeRequests()
97 | .anyRequest().authenticated()
98 | .and()
99 | .formLogin()
100 | .usernameParameter("user")
101 | .passwordParameter("pass")
102 | .loginPage("/authenticate");
103 | }
104 |
105 | @Autowired
106 | public void configureGlobal(AuthenticationManagerBuilder auth) throws Exception {
107 | auth
108 | .inMemoryAuthentication()
109 | .withUser("user").password("password").roles("USER");
110 | }
111 | }
112 | }
--------------------------------------------------------------------------------
/src/test/java/org/springframework/security/test/context/showcase/WithUserDetailsTests.java:
--------------------------------------------------------------------------------
1 | /*
2 | * Copyright 2002-2013 the original author or authors.
3 | *
4 | * Licensed under the Apache License, Version 2.0 (the "License"); you may not
5 | * use this file except in compliance with the License. You may obtain a copy of
6 | * the License at
7 | *
8 | * http://www.apache.org/licenses/LICENSE-2.0
9 | *
10 | * Unless required by applicable law or agreed to in writing, software
11 | * distributed under the License is distributed on an "AS IS" BASIS, WITHOUT
12 | * WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the
13 | * License for the specific language governing permissions and limitations under
14 | * the License.
15 | */
16 | package org.springframework.security.test.context.showcase;
17 |
18 | import static org.fest.assertions.Assertions.assertThat;
19 |
20 | import org.junit.Test;
21 | import org.junit.runner.RunWith;
22 | import org.springframework.beans.factory.annotation.Autowired;
23 | import org.springframework.context.annotation.Bean;
24 | import org.springframework.context.annotation.ComponentScan;
25 | import org.springframework.context.annotation.Configuration;
26 | import org.springframework.security.authentication.AuthenticationCredentialsNotFoundException;
27 | import org.springframework.security.config.annotation.authentication.builders.AuthenticationManagerBuilder;
28 | import org.springframework.security.config.annotation.method.configuration.EnableGlobalMethodSecurity;
29 | import org.springframework.security.core.context.SecurityContextHolder;
30 | import org.springframework.security.core.userdetails.UserDetails;
31 | import org.springframework.security.core.userdetails.UserDetailsService;
32 | import org.springframework.security.core.userdetails.UsernameNotFoundException;
33 | import org.springframework.security.test.context.showcase.service.HelloMessageService;
34 | import org.springframework.security.test.context.showcase.service.MessageService;
35 | import org.springframework.security.test.context.support.WithSecurityContextTestExcecutionListener;
36 | import org.springframework.security.test.context.support.WithUserDetails;
37 | import org.springframework.test.context.ContextConfiguration;
38 | import org.springframework.test.context.TestExecutionListeners;
39 | import org.springframework.test.context.junit4.SpringJUnit4ClassRunner;
40 | import org.springframework.test.context.support.DependencyInjectionTestExecutionListener;
41 | import org.springframework.test.context.support.DirtiesContextTestExecutionListener;
42 | import org.springframework.test.context.transaction.TransactionalTestExecutionListener;
43 | import org.springframework.test.context.web.ServletTestExecutionListener;
44 |
45 | /**
46 | * @author Rob Winch
47 | */
48 |
49 | @RunWith(SpringJUnit4ClassRunner.class)
50 | @ContextConfiguration
51 | @TestExecutionListeners(listeners={ServletTestExecutionListener.class,
52 | DependencyInjectionTestExecutionListener.class,
53 | DirtiesContextTestExecutionListener.class,
54 | TransactionalTestExecutionListener.class,
55 | WithSecurityContextTestExcecutionListener.class})
56 | public class WithUserDetailsTests {
57 | @Autowired
58 | private MessageService messageService;
59 |
60 | @Test(expected = AuthenticationCredentialsNotFoundException.class)
61 | public void getMessageUnauthenticated() {
62 | messageService.getMessage();
63 | }
64 |
65 | @Test
66 | @WithUserDetails
67 | public void getMessageWithUserDetails() {
68 | String message = messageService.getMessage();
69 | assertThat(message).contains("user");
70 | assertThat(getPrincipal()).isInstanceOf(CustomUserDetails.class);
71 | }
72 |
73 | @Test
74 | @WithUserDetails("customUsername")
75 | public void getMessageWithUserDetailsCustomUsername() {
76 | String message = messageService.getMessage();
77 | assertThat(message).contains("customUsername");
78 | assertThat(getPrincipal()).isInstanceOf(CustomUserDetails.class);
79 | }
80 |
81 | @Configuration
82 | @EnableGlobalMethodSecurity(prePostEnabled = true)
83 | @ComponentScan(basePackageClasses = HelloMessageService.class)
84 | static class Config {
85 | @Autowired
86 | public void configureGlobal(AuthenticationManagerBuilder auth) throws Exception {
87 | auth
88 | .userDetailsService(userDetailsService());
89 | }
90 |
91 | @Bean
92 | public UserDetailsService userDetailsService() {
93 | return new CustomUserDetailsService();
94 | }
95 | }
96 |
97 | private Object getPrincipal() {
98 | return SecurityContextHolder.getContext().getAuthentication().getPrincipal();
99 | }
100 |
101 | static class CustomUserDetailsService implements UserDetailsService {
102 |
103 | @Override
104 | public UserDetails loadUserByUsername(final String username) throws UsernameNotFoundException {
105 | return new CustomUserDetails("name", username);
106 | }
107 | }
108 | }
109 |
--------------------------------------------------------------------------------
/src/test/java/sample/webdriver/MockMvcHtmlUnitDriverCreateMessageTest.java:
--------------------------------------------------------------------------------
1 | package sample.webdriver;
2 |
3 | import org.junit.After;
4 | import org.junit.Before;
5 | import org.junit.Test;
6 | import org.junit.runner.RunWith;
7 | import org.openqa.selenium.WebDriver;
8 | import org.springframework.beans.factory.annotation.Autowired;
9 | import org.springframework.security.test.context.support.WithMockUser;
10 | import org.springframework.security.test.context.support.WithSecurityContextTestExcecutionListener;
11 | import org.springframework.test.context.ContextConfiguration;
12 | import org.springframework.test.context.TestExecutionListeners;
13 | import org.springframework.test.context.junit4.SpringJUnit4ClassRunner;
14 | import org.springframework.test.context.support.DependencyInjectionTestExecutionListener;
15 | import org.springframework.test.context.support.DirtiesContextTestExecutionListener;
16 | import org.springframework.test.context.transaction.TransactionalTestExecutionListener;
17 | import org.springframework.test.context.web.ServletTestExecutionListener;
18 | import org.springframework.test.context.web.WebAppConfiguration;
19 | import org.springframework.test.web.servlet.MockMvc;
20 | import org.springframework.test.web.servlet.htmlunit.webdriver.MockMvcHtmlUnitDriver;
21 | import org.springframework.test.web.servlet.setup.MockMvcBuilders;
22 | import org.springframework.web.context.WebApplicationContext;
23 |
24 | import sample.config.MockDataConfig;
25 | import sample.config.WebMvcConfig;
26 | import sample.config.WebSecurityConfig;
27 | import sample.data.Message;
28 | import sample.webdriver.pages.CreateMessagePage;
29 | import sample.webdriver.pages.ViewMessagePage;
30 |
31 | import java.text.ParseException;
32 |
33 | import javax.servlet.Filter;
34 |
35 | import static org.springframework.security.test.web.servlet.request.SecurityMockMvcRequestPostProcessors.testSecurityContext;
36 | import static org.springframework.test.web.servlet.request.MockMvcRequestBuilders.get;
37 | import static sample.fest.Assertions.assertThat;
38 |
39 | /**
40 | * An end to end test that validates the {@link CreateMessagePage}. A few things to notice:
41 | *
42 | *
43 | * You will see that all the tests are the same as {@link WebDriverCreateMessageITest}. This shows how little difference
44 | * there is in how you would write the tests.
45 | * The only difference is how we initialize our {@link WebDriver}
46 | * We do not need to run the web application on a server for this test since we are using
47 | * {@link org.springframework.test.web.servlet.htmlunit.webdriver.MockMvcHtmlUnitDriver}
48 | *
49 | *
50 | * @author Rob Winch
51 | *
52 | */
53 | @RunWith(SpringJUnit4ClassRunner.class)
54 | @ContextConfiguration(classes = {WebMvcConfig.class, WebSecurityConfig.class, MockDataConfig.class})
55 | @WebAppConfiguration
56 | @TestExecutionListeners(listeners={ServletTestExecutionListener.class,
57 | DependencyInjectionTestExecutionListener.class,
58 | DirtiesContextTestExecutionListener.class,
59 | TransactionalTestExecutionListener.class,
60 | WithSecurityContextTestExcecutionListener.class})
61 | @WithMockUser
62 | public class MockMvcHtmlUnitDriverCreateMessageTest {
63 | @Autowired
64 | private Filter springSecurityFilterChain;
65 |
66 | @Autowired
67 | private WebApplicationContext context;
68 |
69 | @Autowired
70 | private Message expectedMessage;
71 |
72 | private WebDriver driver;
73 |
74 | @Before
75 | public void setup() {
76 | MockMvc mockMvc = MockMvcBuilders
77 | .webAppContextSetup(context)
78 | .addFilters(springSecurityFilterChain)
79 | .build();
80 | driver = new MockMvcHtmlUnitDriver(mockMvc, true);
81 | }
82 |
83 | @After
84 | public void destroy() {
85 | if(driver != null) {
86 | driver.close();
87 | }
88 | }
89 |
90 | @Test
91 | public void missingFieldWithJavascriptValidationDisplaysError() {
92 | CreateMessagePage messagePage = CreateMessagePage.to(driver);
93 | messagePage = messagePage.createMessage(CreateMessagePage.class, "", "");
94 | assertThat(messagePage.getErrors()).isEqualTo("This field is required.");
95 | }
96 |
97 | @Test
98 | public void missingFieldServerSideValidationDisplaysError() {
99 | CreateMessagePage messagePage = CreateMessagePage.to(driver);
100 | messagePage = messagePage.createMessage(CreateMessagePage.class, "Summary", "");
101 | assertThat(messagePage.getErrors()).isEqualTo("Message is required.");
102 | }
103 |
104 | @Test
105 | public void successfullyCreateMessage() throws ParseException {
106 | String expectedSummary = expectedMessage.getSummary();
107 | String expectedText = expectedMessage.getText();
108 |
109 | CreateMessagePage page = CreateMessagePage.to(driver);
110 |
111 | ViewMessagePage viewMessagePage = page.createMessage(ViewMessagePage.class, expectedSummary, expectedText);
112 | assertThat(viewMessagePage.getMessage()).isEqualTo(expectedMessage);
113 | assertThat(viewMessagePage.getSuccess()).isEqualTo("Successfully created a new message");
114 | }
115 | }
116 |
--------------------------------------------------------------------------------
/src/test/java/sample/htmlunit/MockMvcHtmlUnitCreateMessageTest.java:
--------------------------------------------------------------------------------
1 | /*
2 | * Copyright 2002-2013 the original author or authors.
3 | *
4 | * Licensed under the Apache License, Version 2.0 (the "License"); you may not
5 | * use this file except in compliance with the License. You may obtain a copy of
6 | * the License at
7 | *
8 | * http://www.apache.org/licenses/LICENSE-2.0
9 | *
10 | * Unless required by applicable law or agreed to in writing, software
11 | * distributed under the License is distributed on an "AS IS" BASIS, WITHOUT
12 | * WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the
13 | * License for the specific language governing permissions and limitations under
14 | * the License.
15 | */
16 | package sample.htmlunit;
17 |
18 | import static org.fest.assertions.Assertions.assertThat;
19 |
20 | import java.io.IOException;
21 |
22 | import javax.servlet.Filter;
23 |
24 | import org.junit.After;
25 | import org.junit.Before;
26 | import org.junit.Test;
27 | import org.junit.runner.RunWith;
28 | import org.springframework.beans.factory.annotation.Autowired;
29 | import org.springframework.security.test.context.support.WithMockUser;
30 | import org.springframework.security.test.context.support.WithSecurityContextTestExcecutionListener;
31 | import org.springframework.test.context.ContextConfiguration;
32 | import org.springframework.test.context.TestExecutionListeners;
33 | import org.springframework.test.context.junit4.SpringJUnit4ClassRunner;
34 | import org.springframework.test.context.support.DependencyInjectionTestExecutionListener;
35 | import org.springframework.test.context.support.DirtiesContextTestExecutionListener;
36 | import org.springframework.test.context.transaction.TransactionalTestExecutionListener;
37 | import org.springframework.test.context.web.ServletTestExecutionListener;
38 | import org.springframework.test.context.web.WebAppConfiguration;
39 | import org.springframework.test.web.servlet.MockMvc;
40 | import org.springframework.test.web.servlet.htmlunit.MockMvcWebConnection;
41 | import org.springframework.test.web.servlet.setup.MockMvcBuilders;
42 | import org.springframework.web.context.WebApplicationContext;
43 |
44 | import sample.config.MockDataConfig;
45 | import sample.config.WebMvcConfig;
46 | import sample.config.WebSecurityConfig;
47 |
48 | import com.gargoylesoftware.htmlunit.WebClient;
49 | import com.gargoylesoftware.htmlunit.html.HtmlForm;
50 | import com.gargoylesoftware.htmlunit.html.HtmlPage;
51 | import com.gargoylesoftware.htmlunit.html.HtmlSubmitInput;
52 | import com.gargoylesoftware.htmlunit.html.HtmlTextArea;
53 | import com.gargoylesoftware.htmlunit.html.HtmlTextInput;
54 |
55 | /**
56 | * @author Rob Winch
57 | */
58 | @RunWith(SpringJUnit4ClassRunner.class)
59 | @ContextConfiguration(classes = {WebMvcConfig.class, WebSecurityConfig.class, MockDataConfig.class})
60 | @WebAppConfiguration
61 | @TestExecutionListeners(listeners={ServletTestExecutionListener.class,
62 | DependencyInjectionTestExecutionListener.class,
63 | DirtiesContextTestExecutionListener.class,
64 | TransactionalTestExecutionListener.class,
65 | WithSecurityContextTestExcecutionListener.class})
66 | @WithMockUser
67 | public class MockMvcHtmlUnitCreateMessageTest {
68 | @Autowired
69 | private Filter springSecurityFilterChain;
70 |
71 | @Autowired
72 | private WebApplicationContext context;
73 |
74 | private WebClient webClient;
75 |
76 | @Before
77 | public void setup() {
78 | MockMvc mockMvc = MockMvcBuilders
79 | .webAppContextSetup(context)
80 | .addFilters(springSecurityFilterChain)
81 | .build();
82 | webClient = new WebClient();
83 | webClient.setWebConnection(new MockMvcWebConnection(mockMvc));
84 | }
85 |
86 | @After
87 | public void cleanup() {
88 | this.webClient.closeAllWindows();
89 | }
90 |
91 | @Test
92 | public void createMessage() throws IOException {
93 | // Load the Create Message Form
94 | HtmlPage createMsgFormPage = webClient.getPage("http://localhost/mail/messages/form");
95 | // Submit the create message form
96 | HtmlForm form = createMsgFormPage.getHtmlElementById("messageForm");
97 | HtmlTextInput summaryInput = createMsgFormPage.getHtmlElementById("summary");
98 | summaryInput.setValueAttribute("Spring Rocks");
99 | HtmlTextArea textInput = createMsgFormPage.getHtmlElementById("text");
100 | textInput.setText("In case you didn't know, Spring Rocks!");
101 | HtmlSubmitInput submit = form.getOneHtmlElementByAttribute("input", "type", "submit");
102 | HtmlPage newMessagePage = submit.click();
103 |
104 | // verify we successfully created a message and displayed the newly create message
105 | assertThat(newMessagePage.getUrl().toString()).endsWith("/messages/123");
106 | String id = newMessagePage.getHtmlElementById("id").getTextContent();
107 | assertThat(id).isEqualTo("123");
108 | String summary = newMessagePage.getHtmlElementById("summary").getTextContent();
109 | assertThat(summary).isEqualTo("Spring Rocks");
110 | String text = newMessagePage.getHtmlElementById("text").getTextContent();
111 | assertThat(text).isEqualTo("In case you didn't know, Spring Rocks!");
112 | }
113 | }
114 |
--------------------------------------------------------------------------------
/src/test/java/sample/mockmvc/MockMvcCreateMessageTest.java:
--------------------------------------------------------------------------------
1 | /*
2 | * Copyright 2002-2013 the original author or authors.
3 | *
4 | * Licensed under the Apache License, Version 2.0 (the "License"); you may not
5 | * use this file except in compliance with the License. You may obtain a copy of
6 | * the License at
7 | *
8 | * http://www.apache.org/licenses/LICENSE-2.0
9 | *
10 | * Unless required by applicable law or agreed to in writing, software
11 | * distributed under the License is distributed on an "AS IS" BASIS, WITHOUT
12 | * WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the
13 | * License for the specific language governing permissions and limitations under
14 | * the License.
15 | */
16 | package sample.mockmvc;
17 |
18 | import static org.springframework.security.test.web.servlet.request.SecurityMockMvcRequestPostProcessors.*;
19 |
20 | import static org.springframework.test.web.servlet.request.MockMvcRequestBuilders.get;
21 | import static org.springframework.test.web.servlet.request.MockMvcRequestBuilders.post;
22 | import static org.springframework.test.web.servlet.result.MockMvcResultMatchers.redirectedUrl;
23 | import static org.springframework.test.web.servlet.result.MockMvcResultMatchers.status;
24 | import static org.springframework.test.web.servlet.result.MockMvcResultMatchers.xpath;
25 |
26 | import javax.servlet.Filter;
27 |
28 | import org.junit.Before;
29 | import org.junit.Test;
30 | import org.junit.runner.RunWith;
31 | import org.springframework.beans.factory.annotation.Autowired;
32 | import org.springframework.security.test.context.support.WithMockUser;
33 | import org.springframework.security.test.context.support.WithSecurityContextTestExcecutionListener;
34 | import org.springframework.test.context.ContextConfiguration;
35 | import org.springframework.test.context.TestExecutionListeners;
36 | import org.springframework.test.context.junit4.SpringJUnit4ClassRunner;
37 | import org.springframework.test.context.support.DependencyInjectionTestExecutionListener;
38 | import org.springframework.test.context.support.DirtiesContextTestExecutionListener;
39 | import org.springframework.test.context.transaction.TransactionalTestExecutionListener;
40 | import org.springframework.test.context.web.ServletTestExecutionListener;
41 | import org.springframework.test.context.web.WebAppConfiguration;
42 | import org.springframework.test.web.servlet.MockMvc;
43 | import org.springframework.test.web.servlet.request.MockHttpServletRequestBuilder;
44 | import org.springframework.test.web.servlet.setup.MockMvcBuilders;
45 | import org.springframework.web.context.WebApplicationContext;
46 |
47 | import sample.config.MockDataConfig;
48 | import sample.config.WebMvcConfig;
49 | import sample.config.WebSecurityConfig;
50 |
51 | /**
52 | * @author Rob Winch
53 | */
54 | @RunWith(SpringJUnit4ClassRunner.class)
55 | @ContextConfiguration(classes = {WebMvcConfig.class, WebSecurityConfig.class, MockDataConfig.class})
56 | @WebAppConfiguration
57 | @TestExecutionListeners(listeners={ServletTestExecutionListener.class,
58 | DependencyInjectionTestExecutionListener.class,
59 | DirtiesContextTestExecutionListener.class,
60 | TransactionalTestExecutionListener.class,
61 | WithSecurityContextTestExcecutionListener.class})
62 | @WithMockUser
63 | public class MockMvcCreateMessageTest {
64 | @Autowired
65 | private Filter springSecurityFilterChain;
66 |
67 | @Autowired
68 | private WebApplicationContext context;
69 |
70 | private MockMvc mockMvc;
71 |
72 | @Before
73 | public void setup() {
74 | this.mockMvc = MockMvcBuilders
75 | .webAppContextSetup(context)
76 | .defaultRequest(get("/").with(testSecurityContext()))
77 | .addFilters(springSecurityFilterChain)
78 | .build();
79 | }
80 |
81 | @Test
82 | public void createMessage() throws Exception {
83 | MockHttpServletRequestBuilder createMessage = post("/messages/")
84 | .param("summary", "Spring Rocks")
85 | .param("text", "In case you didn't know, Spring Rocks!")
86 | .with(csrf());
87 |
88 | mockMvc.perform(createMessage)
89 | .andExpect(status().is3xxRedirection())
90 | .andExpect(redirectedUrl("/messages/123"));
91 | }
92 |
93 | @Test
94 | public void createMessageForm() throws Exception {
95 | mockMvc.perform(get("/messages/form"))
96 | .andExpect(xpath("//input[@name='summary']").exists())
97 | .andExpect(xpath("//textarea[@name='text']").exists());
98 | }
99 |
100 | @Test
101 | public void createMessageFormSubmit() throws Exception {
102 | String summaryParamName = "summary";
103 | String textParamName = "text";
104 | mockMvc.perform(get("/messages/form"))
105 | .andExpect(xpath("//input[@name='" + summaryParamName + "']").exists())
106 | .andExpect(xpath("//textarea[@name='" + textParamName + "']").exists());
107 |
108 | MockHttpServletRequestBuilder createMessage = post("/messages/")
109 | .param(summaryParamName, "Spring Rocks")
110 | .param(textParamName, "In case you didn't know, Spring Rocks!")
111 | .with(csrf());
112 |
113 | mockMvc.perform(createMessage)
114 | .andExpect(status().is3xxRedirection())
115 | .andExpect(redirectedUrl("/messages/123"));
116 | }
117 | }
118 |
--------------------------------------------------------------------------------
/src/test/java/org/springframework/security/test/web/servlet/showcase/secured/WithUserClassLevelAuthenticationTests.java:
--------------------------------------------------------------------------------
1 | /*
2 | * Copyright 2002-2014 the original author or authors.
3 | *
4 | * Licensed under the Apache License, Version 2.0 (the "License");
5 | * you may not use this file except in compliance with the License.
6 | * You may obtain a copy of the License at
7 | *
8 | * http://www.apache.org/licenses/LICENSE-2.0
9 | *
10 | * Unless required by applicable law or agreed to in writing, software
11 | * distributed under the License is distributed on an "AS IS" BASIS,
12 | * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13 | * See the License for the specific language governing permissions and
14 | * limitations under the License.
15 | */
16 | package org.springframework.security.test.web.servlet.showcase.secured;
17 |
18 | import static org.springframework.security.test.web.servlet.request.SecurityMockMvcRequestPostProcessors.testSecurityContext;
19 | import static org.springframework.security.test.web.servlet.response.SecurityMockMvcResultMatchers.authenticated;
20 | import static org.springframework.test.web.servlet.request.MockMvcRequestBuilders.get;
21 | import static org.springframework.test.web.servlet.result.MockMvcResultMatchers.status;
22 |
23 | import javax.servlet.Filter;
24 |
25 | import org.junit.Before;
26 | import org.junit.Test;
27 | import org.junit.runner.RunWith;
28 | import org.springframework.beans.factory.annotation.Autowired;
29 | import org.springframework.context.annotation.Configuration;
30 | import org.springframework.security.config.annotation.authentication.builders.AuthenticationManagerBuilder;
31 | import org.springframework.security.config.annotation.web.builders.HttpSecurity;
32 | import org.springframework.security.config.annotation.web.configuration.WebSecurityConfigurerAdapter;
33 | import org.springframework.security.config.annotation.web.servlet.configuration.EnableWebMvcSecurity;
34 | import org.springframework.security.test.context.support.WithMockUser;
35 | import org.springframework.security.test.context.support.WithSecurityContextTestExcecutionListener;
36 | import org.springframework.test.context.ContextConfiguration;
37 | import org.springframework.test.context.TestExecutionListeners;
38 | import org.springframework.test.context.junit4.SpringJUnit4ClassRunner;
39 | import org.springframework.test.context.support.DependencyInjectionTestExecutionListener;
40 | import org.springframework.test.context.support.DirtiesContextTestExecutionListener;
41 | import org.springframework.test.context.transaction.TransactionalTestExecutionListener;
42 | import org.springframework.test.context.web.ServletTestExecutionListener;
43 | import org.springframework.test.context.web.WebAppConfiguration;
44 | import org.springframework.test.web.servlet.MockMvc;
45 | import org.springframework.test.web.servlet.setup.MockMvcBuilders;
46 | import org.springframework.web.context.WebApplicationContext;
47 | import org.springframework.web.servlet.config.annotation.EnableWebMvc;
48 |
49 | @RunWith(SpringJUnit4ClassRunner.class)
50 | @ContextConfiguration
51 | @WebAppConfiguration
52 | @TestExecutionListeners(listeners={ServletTestExecutionListener.class,
53 | DependencyInjectionTestExecutionListener.class,
54 | DirtiesContextTestExecutionListener.class,
55 | TransactionalTestExecutionListener.class,
56 | WithSecurityContextTestExcecutionListener.class})
57 | @WithMockUser(roles="ADMIN")
58 | public class WithUserClassLevelAuthenticationTests {
59 |
60 | @Autowired
61 | private WebApplicationContext context;
62 |
63 | @Autowired
64 | private Filter springSecurityFilterChain;
65 |
66 | private MockMvc mvc;
67 |
68 | @Before
69 | public void setup() {
70 | mvc = MockMvcBuilders
71 | .webAppContextSetup(context)
72 | .addFilters(springSecurityFilterChain)
73 | .defaultRequest(get("/").with(testSecurityContext()))
74 | .build();
75 | }
76 |
77 | @Test
78 | public void requestProtectedUrlWithUser() throws Exception {
79 | mvc
80 | .perform(get("/"))
81 | // Ensure we got past Security
82 | .andExpect(status().isNotFound())
83 | // Ensure it appears we are authenticated with user
84 | .andExpect(authenticated().withUsername("user"));
85 | }
86 |
87 | @Test
88 | public void requestProtectedUrlWithAdmin() throws Exception {
89 | mvc
90 | .perform(get("/admin"))
91 | // Ensure we got past Security
92 | .andExpect(status().isNotFound())
93 | // Ensure it appears we are authenticated with user
94 | .andExpect(authenticated().withUsername("user").withRoles("ADMIN"));
95 | }
96 |
97 | @Configuration
98 | @EnableWebMvcSecurity
99 | @EnableWebMvc
100 | static class Config extends WebSecurityConfigurerAdapter {
101 |
102 | @Override
103 | protected void configure(HttpSecurity http) throws Exception {
104 | http
105 | .authorizeRequests()
106 | .antMatchers("/admin/**").hasRole("ADMIN")
107 | .anyRequest().authenticated()
108 | .and()
109 | .formLogin();
110 | }
111 |
112 | @Autowired
113 | public void configureGlobal(AuthenticationManagerBuilder auth) throws Exception {
114 | auth
115 | .inMemoryAuthentication()
116 | .withUser("user").password("password").roles("USER");
117 | }
118 | }
119 | }
--------------------------------------------------------------------------------
/src/test/java/org/springframework/security/test/web/servlet/showcase/secured/WithUserAuthenticationTests.java:
--------------------------------------------------------------------------------
1 | /*
2 | * Copyright 2002-2014 the original author or authors.
3 | *
4 | * Licensed under the Apache License, Version 2.0 (the "License");
5 | * you may not use this file except in compliance with the License.
6 | * You may obtain a copy of the License at
7 | *
8 | * http://www.apache.org/licenses/LICENSE-2.0
9 | *
10 | * Unless required by applicable law or agreed to in writing, software
11 | * distributed under the License is distributed on an "AS IS" BASIS,
12 | * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13 | * See the License for the specific language governing permissions and
14 | * limitations under the License.
15 | */
16 | package org.springframework.security.test.web.servlet.showcase.secured;
17 |
18 | import static org.springframework.security.test.web.servlet.request.SecurityMockMvcRequestPostProcessors.testSecurityContext;
19 | import static org.springframework.security.test.web.servlet.response.SecurityMockMvcResultMatchers.authenticated;
20 | import static org.springframework.test.web.servlet.request.MockMvcRequestBuilders.get;
21 | import static org.springframework.test.web.servlet.result.MockMvcResultMatchers.status;
22 |
23 | import javax.servlet.Filter;
24 |
25 | import org.junit.Before;
26 | import org.junit.Test;
27 | import org.junit.runner.RunWith;
28 | import org.springframework.beans.factory.annotation.Autowired;
29 | import org.springframework.context.annotation.Configuration;
30 | import org.springframework.security.config.annotation.authentication.builders.AuthenticationManagerBuilder;
31 | import org.springframework.security.config.annotation.web.builders.HttpSecurity;
32 | import org.springframework.security.config.annotation.web.configuration.WebSecurityConfigurerAdapter;
33 | import org.springframework.security.config.annotation.web.servlet.configuration.EnableWebMvcSecurity;
34 | import org.springframework.security.test.context.support.WithMockUser;
35 | import org.springframework.security.test.context.support.WithSecurityContextTestExcecutionListener;
36 | import org.springframework.test.context.ContextConfiguration;
37 | import org.springframework.test.context.TestExecutionListeners;
38 | import org.springframework.test.context.junit4.SpringJUnit4ClassRunner;
39 | import org.springframework.test.context.support.DependencyInjectionTestExecutionListener;
40 | import org.springframework.test.context.support.DirtiesContextTestExecutionListener;
41 | import org.springframework.test.context.transaction.TransactionalTestExecutionListener;
42 | import org.springframework.test.context.web.ServletTestExecutionListener;
43 | import org.springframework.test.context.web.WebAppConfiguration;
44 | import org.springframework.test.web.servlet.MockMvc;
45 | import org.springframework.test.web.servlet.setup.MockMvcBuilders;
46 | import org.springframework.web.context.WebApplicationContext;
47 | import org.springframework.web.servlet.config.annotation.EnableWebMvc;
48 |
49 | @RunWith(SpringJUnit4ClassRunner.class)
50 | @ContextConfiguration
51 | @WebAppConfiguration
52 | @TestExecutionListeners(listeners={ServletTestExecutionListener.class,
53 | DependencyInjectionTestExecutionListener.class,
54 | DirtiesContextTestExecutionListener.class,
55 | TransactionalTestExecutionListener.class,
56 | WithSecurityContextTestExcecutionListener.class})
57 | public class WithUserAuthenticationTests {
58 |
59 | @Autowired
60 | private WebApplicationContext context;
61 |
62 | @Autowired
63 | private Filter springSecurityFilterChain;
64 |
65 | private MockMvc mvc;
66 |
67 | @Before
68 | public void setup() {
69 | mvc = MockMvcBuilders
70 | .webAppContextSetup(context)
71 | .addFilters(springSecurityFilterChain)
72 | .defaultRequest(get("/").with(testSecurityContext()))
73 | .build();
74 | }
75 |
76 | @Test
77 | @WithMockUser
78 | public void requestProtectedUrlWithUser() throws Exception {
79 | mvc
80 | .perform(get("/"))
81 | // Ensure we got past Security
82 | .andExpect(status().isNotFound())
83 | // Ensure it appears we are authenticated with user
84 | .andExpect(authenticated().withUsername("user"));
85 | }
86 |
87 | @Test
88 | @WithMockUser(roles="ADMIN")
89 | public void requestProtectedUrlWithAdmin() throws Exception {
90 | mvc
91 | .perform(get("/admin"))
92 | // Ensure we got past Security
93 | .andExpect(status().isNotFound())
94 | // Ensure it appears we are authenticated with user
95 | .andExpect(authenticated().withUsername("user").withRoles("ADMIN"));
96 | }
97 |
98 | @Configuration
99 | @EnableWebMvcSecurity
100 | @EnableWebMvc
101 | static class Config extends WebSecurityConfigurerAdapter {
102 |
103 | @Override
104 | protected void configure(HttpSecurity http) throws Exception {
105 | http
106 | .authorizeRequests()
107 | .antMatchers("/admin/**").hasRole("ADMIN")
108 | .anyRequest().authenticated()
109 | .and()
110 | .formLogin();
111 | }
112 |
113 | @Autowired
114 | public void configureGlobal(AuthenticationManagerBuilder auth) throws Exception {
115 | auth
116 | .inMemoryAuthentication()
117 | .withUser("user").password("password").roles("USER");
118 | }
119 | }
120 | }
--------------------------------------------------------------------------------
/src/test/java/org/springframework/security/test/web/servlet/showcase/login/CustomConfigAuthenticationTests.java:
--------------------------------------------------------------------------------
1 | /*
2 | * Copyright 2002-2014 the original author or authors.
3 | *
4 | * Licensed under the Apache License, Version 2.0 (the "License");
5 | * you may not use this file except in compliance with the License.
6 | * You may obtain a copy of the License at
7 | *
8 | * http://www.apache.org/licenses/LICENSE-2.0
9 | *
10 | * Unless required by applicable law or agreed to in writing, software
11 | * distributed under the License is distributed on an "AS IS" BASIS,
12 | * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13 | * See the License for the specific language governing permissions and
14 | * limitations under the License.
15 | */
16 | package org.springframework.security.test.web.servlet.showcase.login;
17 |
18 | import static org.springframework.security.test.web.servlet.request.SecurityMockMvcRequestBuilders.*;
19 | import static org.springframework.security.test.web.servlet.request.SecurityMockMvcRequestPostProcessors.*;
20 | import static org.springframework.security.test.web.servlet.response.SecurityMockMvcResultMatchers.*;
21 | import static org.springframework.test.web.servlet.result.MockMvcResultMatchers.*;
22 | import static org.springframework.test.web.servlet.request.MockMvcRequestBuilders.*;
23 |
24 | import javax.servlet.Filter;
25 |
26 | import org.junit.Before;
27 | import org.junit.Test;
28 | import org.junit.runner.RunWith;
29 | import org.springframework.beans.factory.annotation.Autowired;
30 | import org.springframework.context.annotation.Bean;
31 | import org.springframework.context.annotation.Configuration;
32 | import org.springframework.security.config.annotation.authentication.builders.AuthenticationManagerBuilder;
33 | import org.springframework.security.config.annotation.web.builders.HttpSecurity;
34 | import org.springframework.security.config.annotation.web.configuration.WebSecurityConfigurerAdapter;
35 | import org.springframework.security.config.annotation.web.servlet.configuration.EnableWebMvcSecurity;
36 | import org.springframework.security.web.context.HttpSessionSecurityContextRepository;
37 | import org.springframework.security.web.context.SecurityContextRepository;
38 | import org.springframework.test.context.ContextConfiguration;
39 | import org.springframework.test.context.junit4.SpringJUnit4ClassRunner;
40 | import org.springframework.test.context.web.WebAppConfiguration;
41 | import org.springframework.test.web.servlet.MockMvc;
42 | import org.springframework.test.web.servlet.setup.MockMvcBuilders;
43 | import org.springframework.web.context.WebApplicationContext;
44 | import org.springframework.web.servlet.config.annotation.EnableWebMvc;
45 |
46 | @RunWith(SpringJUnit4ClassRunner.class)
47 | @ContextConfiguration
48 | @WebAppConfiguration
49 | public class CustomConfigAuthenticationTests {
50 |
51 | @Autowired
52 | private WebApplicationContext context;
53 |
54 | @Autowired
55 | private Filter springSecurityFilterChain;
56 |
57 | @Autowired
58 | private SecurityContextRepository securityContextRepository;
59 |
60 | private MockMvc mvc;
61 |
62 | @Before
63 | public void setup() {
64 | mvc = MockMvcBuilders
65 | .webAppContextSetup(context)
66 | .defaultRequest(get("/"))
67 | .addFilters(springSecurityFilterChain)
68 | .build();
69 | }
70 |
71 | @Test
72 | public void authenticationSuccess() throws Exception {
73 | mvc
74 | .perform(formLogin("/authenticate").user("user","user").password("pass","password"))
75 | .andExpect(status().isMovedTemporarily())
76 | .andExpect(redirectedUrl("/"))
77 | .andExpect(authenticated().withUsername("user"));
78 | }
79 |
80 |
81 | @Test
82 | public void withUserSuccess() throws Exception {
83 | mvc
84 | .perform(get("/").with(user("user")))
85 | .andExpect(status().isNotFound())
86 | .andExpect(authenticated().withUsername("user"));
87 | }
88 |
89 | @Test
90 | public void authenticationFailed() throws Exception {
91 | mvc
92 | .perform(formLogin("/authenticate").user("user","notfound").password("pass","invalid"))
93 | .andExpect(status().isMovedTemporarily())
94 | .andExpect(redirectedUrl("/authenticate?error"))
95 | .andExpect(unauthenticated());
96 | }
97 |
98 | @Configuration
99 | @EnableWebMvcSecurity
100 | @EnableWebMvc
101 | static class Config extends WebSecurityConfigurerAdapter {
102 |
103 | @Override
104 | protected void configure(HttpSecurity http) throws Exception {
105 | http
106 | .authorizeRequests()
107 | .anyRequest().authenticated()
108 | .and()
109 | .securityContext()
110 | .securityContextRepository(securityContextRepository())
111 | .and()
112 | .formLogin()
113 | .usernameParameter("user")
114 | .passwordParameter("pass")
115 | .loginPage("/authenticate");
116 | }
117 |
118 | @Autowired
119 | public void configureGlobal(AuthenticationManagerBuilder auth) throws Exception {
120 | auth
121 | .inMemoryAuthentication()
122 | .withUser("user").password("password").roles("USER");
123 | }
124 |
125 | @Bean
126 | public SecurityContextRepository securityContextRepository() {
127 | HttpSessionSecurityContextRepository repo = new HttpSessionSecurityContextRepository();
128 | repo.setSpringSecurityContextKey("CUSTOM");
129 | return repo;
130 | }
131 | }
132 | }
--------------------------------------------------------------------------------
/src/test/java/org/springframework/security/test/web/servlet/showcase/secured/WithUserDetailsClassLevelAuthenticationTests.java:
--------------------------------------------------------------------------------
1 | /*
2 | * Copyright 2002-2014 the original author or authors.
3 | *
4 | * Licensed under the Apache License, Version 2.0 (the "License");
5 | * you may not use this file except in compliance with the License.
6 | * You may obtain a copy of the License at
7 | *
8 | * http://www.apache.org/licenses/LICENSE-2.0
9 | *
10 | * Unless required by applicable law or agreed to in writing, software
11 | * distributed under the License is distributed on an "AS IS" BASIS,
12 | * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13 | * See the License for the specific language governing permissions and
14 | * limitations under the License.
15 | */
16 | package org.springframework.security.test.web.servlet.showcase.secured;
17 |
18 | import static org.springframework.security.test.web.servlet.request.SecurityMockMvcRequestPostProcessors.*;
19 | import static org.springframework.security.test.web.servlet.response.SecurityMockMvcResultMatchers.*;
20 | import static org.springframework.test.web.servlet.request.MockMvcRequestBuilders.get;
21 | import static org.springframework.test.web.servlet.result.MockMvcResultMatchers.status;
22 |
23 | import javax.servlet.Filter;
24 |
25 | import org.junit.Before;
26 | import org.junit.Test;
27 | import org.junit.runner.RunWith;
28 | import org.springframework.beans.factory.annotation.Autowired;
29 | import org.springframework.context.annotation.Bean;
30 | import org.springframework.context.annotation.Configuration;
31 | import org.springframework.security.config.annotation.authentication.builders.AuthenticationManagerBuilder;
32 | import org.springframework.security.config.annotation.web.builders.HttpSecurity;
33 | import org.springframework.security.config.annotation.web.configuration.WebSecurityConfigurerAdapter;
34 | import org.springframework.security.config.annotation.web.servlet.configuration.EnableWebMvcSecurity;
35 | import org.springframework.security.core.userdetails.UserDetailsService;
36 | import org.springframework.security.test.context.support.WithSecurityContextTestExcecutionListener;
37 | import org.springframework.security.test.context.support.WithUserDetails;
38 | import org.springframework.test.context.ContextConfiguration;
39 | import org.springframework.test.context.TestExecutionListeners;
40 | import org.springframework.test.context.junit4.SpringJUnit4ClassRunner;
41 | import org.springframework.test.context.support.DependencyInjectionTestExecutionListener;
42 | import org.springframework.test.context.support.DirtiesContextTestExecutionListener;
43 | import org.springframework.test.context.transaction.TransactionalTestExecutionListener;
44 | import org.springframework.test.context.web.ServletTestExecutionListener;
45 | import org.springframework.test.context.web.WebAppConfiguration;
46 | import org.springframework.test.web.servlet.MockMvc;
47 | import org.springframework.test.web.servlet.setup.MockMvcBuilders;
48 | import org.springframework.web.context.WebApplicationContext;
49 | import org.springframework.web.servlet.config.annotation.EnableWebMvc;
50 |
51 | @RunWith(SpringJUnit4ClassRunner.class)
52 | @ContextConfiguration
53 | @WebAppConfiguration
54 | @TestExecutionListeners(listeners={ServletTestExecutionListener.class,
55 | DependencyInjectionTestExecutionListener.class,
56 | DirtiesContextTestExecutionListener.class,
57 | TransactionalTestExecutionListener.class,
58 | WithSecurityContextTestExcecutionListener.class})
59 | @WithUserDetails("admin")
60 | public class WithUserDetailsClassLevelAuthenticationTests {
61 |
62 | @Autowired
63 | private WebApplicationContext context;
64 |
65 | @Autowired
66 | private Filter springSecurityFilterChain;
67 |
68 | private MockMvc mvc;
69 |
70 | @Before
71 | public void setup() {
72 | mvc = MockMvcBuilders
73 | .webAppContextSetup(context)
74 | .addFilters(springSecurityFilterChain)
75 | .defaultRequest(get("/").with(testSecurityContext()))
76 | .build();
77 | }
78 |
79 | @Test
80 | public void requestRootUrlWithAdmin() throws Exception {
81 | mvc
82 | .perform(get("/"))
83 | // Ensure we got past Security
84 | .andExpect(status().isNotFound())
85 | // Ensure it appears we are authenticated with user
86 | .andExpect(authenticated().withUsername("admin").withRoles("ADMIN","USER"));
87 | }
88 |
89 | @Test
90 | public void requestProtectedUrlWithAdmin() throws Exception {
91 | mvc
92 | .perform(get("/admin"))
93 | // Ensure we got past Security
94 | .andExpect(status().isNotFound())
95 | // Ensure it appears we are authenticated with user
96 | .andExpect(authenticated().withUsername("admin").withRoles("ADMIN","USER"));
97 | }
98 |
99 | @Configuration
100 | @EnableWebMvcSecurity
101 | @EnableWebMvc
102 | static class Config extends WebSecurityConfigurerAdapter {
103 |
104 | @Override
105 | protected void configure(HttpSecurity http) throws Exception {
106 | http
107 | .authorizeRequests()
108 | .antMatchers("/admin/**").hasRole("ADMIN")
109 | .anyRequest().authenticated()
110 | .and()
111 | .formLogin();
112 | }
113 |
114 | @Bean
115 | @Override
116 | public UserDetailsService userDetailsServiceBean() throws Exception {
117 | return super.userDetailsServiceBean();
118 | }
119 |
120 | @Autowired
121 | public void configureGlobal(AuthenticationManagerBuilder auth) throws Exception {
122 | auth
123 | .inMemoryAuthentication()
124 | .withUser("user").password("password").roles("USER").and()
125 | .withUser("admin").password("password").roles("USER","ADMIN");
126 | }
127 | }
128 | }
--------------------------------------------------------------------------------
/src/test/java/org/springframework/security/test/web/servlet/showcase/secured/WithUserDetailsAuthenticationTests.java:
--------------------------------------------------------------------------------
1 | /*
2 | * Copyright 2002-2014 the original author or authors.
3 | *
4 | * Licensed under the Apache License, Version 2.0 (the "License");
5 | * you may not use this file except in compliance with the License.
6 | * You may obtain a copy of the License at
7 | *
8 | * http://www.apache.org/licenses/LICENSE-2.0
9 | *
10 | * Unless required by applicable law or agreed to in writing, software
11 | * distributed under the License is distributed on an "AS IS" BASIS,
12 | * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13 | * See the License for the specific language governing permissions and
14 | * limitations under the License.
15 | */
16 | package org.springframework.security.test.web.servlet.showcase.secured;
17 |
18 | import static org.springframework.security.test.web.servlet.request.SecurityMockMvcRequestPostProcessors.testSecurityContext;
19 | import static org.springframework.security.test.web.servlet.response.SecurityMockMvcResultMatchers.authenticated;
20 | import static org.springframework.test.web.servlet.request.MockMvcRequestBuilders.get;
21 | import static org.springframework.test.web.servlet.result.MockMvcResultMatchers.status;
22 |
23 | import javax.servlet.Filter;
24 |
25 | import org.junit.Before;
26 | import org.junit.Test;
27 | import org.junit.runner.RunWith;
28 | import org.springframework.beans.factory.annotation.Autowired;
29 | import org.springframework.context.annotation.Bean;
30 | import org.springframework.context.annotation.Configuration;
31 | import org.springframework.security.config.annotation.authentication.builders.AuthenticationManagerBuilder;
32 | import org.springframework.security.config.annotation.web.builders.HttpSecurity;
33 | import org.springframework.security.config.annotation.web.configuration.WebSecurityConfigurerAdapter;
34 | import org.springframework.security.config.annotation.web.servlet.configuration.EnableWebMvcSecurity;
35 | import org.springframework.security.core.userdetails.UserDetailsService;
36 | import org.springframework.security.test.context.support.WithSecurityContextTestExcecutionListener;
37 | import org.springframework.security.test.context.support.WithUserDetails;
38 | import org.springframework.test.context.ContextConfiguration;
39 | import org.springframework.test.context.TestExecutionListeners;
40 | import org.springframework.test.context.junit4.SpringJUnit4ClassRunner;
41 | import org.springframework.test.context.support.DependencyInjectionTestExecutionListener;
42 | import org.springframework.test.context.support.DirtiesContextTestExecutionListener;
43 | import org.springframework.test.context.transaction.TransactionalTestExecutionListener;
44 | import org.springframework.test.context.web.ServletTestExecutionListener;
45 | import org.springframework.test.context.web.WebAppConfiguration;
46 | import org.springframework.test.web.servlet.MockMvc;
47 | import org.springframework.test.web.servlet.setup.MockMvcBuilders;
48 | import org.springframework.web.context.WebApplicationContext;
49 | import org.springframework.web.servlet.config.annotation.EnableWebMvc;
50 |
51 | @RunWith(SpringJUnit4ClassRunner.class)
52 | @ContextConfiguration
53 | @WebAppConfiguration
54 | @TestExecutionListeners(listeners={ServletTestExecutionListener.class,
55 | DependencyInjectionTestExecutionListener.class,
56 | DirtiesContextTestExecutionListener.class,
57 | TransactionalTestExecutionListener.class,
58 | WithSecurityContextTestExcecutionListener.class})
59 | public class WithUserDetailsAuthenticationTests {
60 |
61 | @Autowired
62 | private WebApplicationContext context;
63 |
64 | @Autowired
65 | private Filter springSecurityFilterChain;
66 |
67 | private MockMvc mvc;
68 |
69 | @Before
70 | public void setup() {
71 | mvc = MockMvcBuilders
72 | .webAppContextSetup(context)
73 | .addFilters(springSecurityFilterChain)
74 | .defaultRequest(get("/").with(testSecurityContext()))
75 | .build();
76 | }
77 |
78 | @Test
79 | @WithUserDetails
80 | public void requestProtectedUrlWithUser() throws Exception {
81 | mvc
82 | .perform(get("/"))
83 | // Ensure we got past Security
84 | .andExpect(status().isNotFound())
85 | // Ensure it appears we are authenticated with user
86 | .andExpect(authenticated().withUsername("user"));
87 | }
88 |
89 | @Test
90 | @WithUserDetails("admin")
91 | public void requestProtectedUrlWithAdmin() throws Exception {
92 | mvc
93 | .perform(get("/admin"))
94 | // Ensure we got past Security
95 | .andExpect(status().isNotFound())
96 | // Ensure it appears we are authenticated with user
97 | .andExpect(authenticated().withUsername("admin").withRoles("ADMIN","USER"));
98 | }
99 |
100 | @Configuration
101 | @EnableWebMvcSecurity
102 | @EnableWebMvc
103 | static class Config extends WebSecurityConfigurerAdapter {
104 |
105 | @Override
106 | protected void configure(HttpSecurity http) throws Exception {
107 | http
108 | .authorizeRequests()
109 | .antMatchers("/admin/**").hasRole("ADMIN")
110 | .anyRequest().authenticated()
111 | .and()
112 | .formLogin();
113 | }
114 |
115 | @Bean
116 | @Override
117 | public UserDetailsService userDetailsServiceBean() throws Exception {
118 | return super.userDetailsServiceBean();
119 | }
120 |
121 | @Autowired
122 | public void configureGlobal(AuthenticationManagerBuilder auth) throws Exception {
123 | auth
124 | .inMemoryAuthentication()
125 | .withUser("user").password("password").roles("USER").and()
126 | .withUser("admin").password("password").roles("USER","ADMIN");
127 | }
128 | }
129 | }
--------------------------------------------------------------------------------
/src/test/java/org/springframework/security/test/web/servlet/showcase/secured/SecurityRequestsTests.java:
--------------------------------------------------------------------------------
1 | /*
2 | * Copyright 2002-2014 the original author or authors.
3 | *
4 | * Licensed under the Apache License, Version 2.0 (the "License");
5 | * you may not use this file except in compliance with the License.
6 | * You may obtain a copy of the License at
7 | *
8 | * http://www.apache.org/licenses/LICENSE-2.0
9 | *
10 | * Unless required by applicable law or agreed to in writing, software
11 | * distributed under the License is distributed on an "AS IS" BASIS,
12 | * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13 | * See the License for the specific language governing permissions and
14 | * limitations under the License.
15 | */
16 | package org.springframework.security.test.web.servlet.showcase.secured;
17 |
18 | import static org.springframework.security.test.web.servlet.request.SecurityMockMvcRequestPostProcessors.*;
19 | import static org.springframework.security.test.web.servlet.response.SecurityMockMvcResultMatchers.*;
20 | import static org.springframework.test.web.servlet.request.MockMvcRequestBuilders.*;
21 | import static org.springframework.test.web.servlet.result.MockMvcResultMatchers.*;
22 |
23 | import javax.servlet.Filter;
24 |
25 | import org.junit.Before;
26 | import org.junit.Test;
27 | import org.junit.runner.RunWith;
28 | import org.springframework.beans.factory.annotation.Autowired;
29 | import org.springframework.context.annotation.Bean;
30 | import org.springframework.context.annotation.Configuration;
31 | import org.springframework.security.authentication.TestingAuthenticationToken;
32 | import org.springframework.security.config.annotation.authentication.builders.AuthenticationManagerBuilder;
33 | import org.springframework.security.config.annotation.web.builders.HttpSecurity;
34 | import org.springframework.security.config.annotation.web.configuration.WebSecurityConfigurerAdapter;
35 | import org.springframework.security.config.annotation.web.servlet.configuration.EnableWebMvcSecurity;
36 | import org.springframework.security.core.Authentication;
37 | import org.springframework.security.core.userdetails.UserDetails;
38 | import org.springframework.security.core.userdetails.UserDetailsService;
39 | import org.springframework.test.context.ContextConfiguration;
40 | import org.springframework.test.context.junit4.SpringJUnit4ClassRunner;
41 | import org.springframework.test.context.web.WebAppConfiguration;
42 | import org.springframework.test.web.servlet.MockMvc;
43 | import org.springframework.test.web.servlet.setup.MockMvcBuilders;
44 | import org.springframework.web.context.WebApplicationContext;
45 | import org.springframework.web.servlet.config.annotation.EnableWebMvc;
46 |
47 | @RunWith(SpringJUnit4ClassRunner.class)
48 | @ContextConfiguration
49 | @WebAppConfiguration
50 | public class SecurityRequestsTests {
51 |
52 | @Autowired
53 | private WebApplicationContext context;
54 |
55 | @Autowired
56 | private Filter springSecurityFilterChain;
57 |
58 | @Autowired
59 | private UserDetailsService userDetailsService;
60 |
61 | private MockMvc mvc;
62 |
63 | @Before
64 | public void setup() {
65 | mvc = MockMvcBuilders
66 | .webAppContextSetup(context)
67 | .addFilters(springSecurityFilterChain)
68 | .build();
69 | }
70 |
71 | @Test
72 | public void requestProtectedUrlWithUser() throws Exception {
73 | mvc
74 | .perform(get("/").with(user("user")))
75 | // Ensure we got past Security
76 | .andExpect(status().isNotFound())
77 | // Ensure it appears we are authenticated with user
78 | .andExpect(authenticated().withUsername("user"));
79 | }
80 |
81 | @Test
82 | public void requestProtectedUrlWithAdmin() throws Exception {
83 | mvc
84 | .perform(get("/admin").with(user("admin").password("pass").roles("USER","ADMIN")))
85 | // Ensure we got past Security
86 | .andExpect(status().isNotFound())
87 | // Ensure it appears we are authenticated with admin
88 | .andExpect(authenticated().withUsername("admin"));
89 | }
90 |
91 | @Test
92 | public void requestProtectedUrlWithUserDetails() throws Exception {
93 | UserDetails userDetails = userDetailsService.loadUserByUsername("user");
94 | mvc
95 | .perform(get("/").with(user(userDetails)))
96 | // Ensure we got past Security
97 | .andExpect(status().isNotFound())
98 | // Ensure it appears we are authenticated with user
99 | .andExpect(authenticated().withAuthenticationPrincipal(userDetails));
100 | }
101 |
102 | @Test
103 | public void requestProtectedUrlWithAuthentication() throws Exception {
104 | Authentication authentication = new TestingAuthenticationToken("test", "notused", "ROLE_USER");
105 | mvc
106 | .perform(get("/").with(authentication(authentication)))
107 | // Ensure we got past Security
108 | .andExpect(status().isNotFound())
109 | // Ensure it appears we are authenticated with user
110 | .andExpect(authenticated().withAuthentication(authentication));
111 | }
112 |
113 | @Configuration
114 | @EnableWebMvcSecurity
115 | @EnableWebMvc
116 | static class Config extends WebSecurityConfigurerAdapter {
117 |
118 | @Override
119 | protected void configure(HttpSecurity http) throws Exception {
120 | http
121 | .authorizeRequests()
122 | .antMatchers("/admin/**").hasRole("ADMIN")
123 | .anyRequest().authenticated()
124 | .and()
125 | .formLogin();
126 | }
127 |
128 | @Autowired
129 | public void configureGlobal(AuthenticationManagerBuilder auth) throws Exception {
130 | auth
131 | .inMemoryAuthentication()
132 | .withUser("user").password("password").roles("USER");
133 | }
134 |
135 | @Override
136 | @Bean
137 | public UserDetailsService userDetailsServiceBean() throws Exception {
138 | return super.userDetailsServiceBean();
139 | }
140 | }
141 | }
--------------------------------------------------------------------------------
/pom.xml:
--------------------------------------------------------------------------------
1 |
2 |
4 | 4.0.0
5 | sample
6 | spring-security-test-blog
7 | 4.0.0.M1
8 | spring-security-test
9 | spring-security-test
10 | http://spring.io/spring-security
11 | war
12 |
13 | spring.io
14 | http://spring.io/
15 |
16 |
17 |
18 | The Apache Software License, Version 2.0
19 | http://www.apache.org/licenses/LICENSE-2.0.txt
20 | repo
21 |
22 |
23 |
24 |
25 | rwinch
26 | Rob Winch
27 | rwinch@gopivotal.com
28 |
29 |
30 |
31 | scm:git:git://github.com/spring-projects/spring-security
32 | scm:git:git://github.com/spring-projects/spring-security
33 | https://github.com/spring-projects/spring-security
34 |
35 |
36 |
37 |
38 | maven-compiler-plugin
39 |
40 | 1.7
41 | 1.7
42 |
43 |
44 |
45 | maven-war-plugin
46 |
47 | false
48 |
49 |
50 |
51 | org.apache.tomcat.maven
52 | tomcat7-maven-plugin
53 | 2.2
54 |
55 |
56 |
57 |
58 |
59 | spring-snasphot
60 | https://repo.spring.io/libs-snapshot
61 |
62 |
63 |
64 |
65 | org.springframework.security
66 | spring-security-core
67 | 4.0.0.M1
68 | compile
69 |
70 |
71 | org.springframework.security
72 | spring-security-web
73 | 4.0.0.M1
74 | compile
75 |
76 |
77 | org.springframework.security
78 | spring-security-config
79 | 4.0.0.M1
80 |
81 |
82 | commons-logging
83 | commons-logging
84 | 1.1.3
85 |
86 |
87 |
88 | org.springframework
89 | spring-webmvc
90 | 4.0.2.RELEASE
91 |
92 |
93 |
94 | javax.servlet
95 | javax.servlet-api
96 | 3.0.1
97 | provided
98 |
99 |
100 | junit
101 | junit
102 | 4.11
103 | test
104 |
105 |
106 | org.easytesting
107 | fest-assert
108 | 1.4
109 | test
110 |
111 |
112 | org.springframework.security
113 | spring-security-test
114 | 4.0.0.M1
115 |
116 |
117 | org.springframework
118 | spring-test
119 | 4.0.2.RELEASE
120 | test
121 |
122 |
123 |
124 | org.spockframework
125 | spock-spring
126 | 0.7-groovy-2.0
127 | test
128 |
129 |
130 | org.springframework.security
131 | spring-security-web
132 | 4.0.0.M1
133 | compile
134 |
135 |
136 | org.seleniumhq.selenium
137 | selenium-htmlunit-driver
138 | 2.40.0
139 | test
140 |
141 |
142 | org.mockito
143 | mockito-all
144 | 1.9.5
145 | test
146 |
147 |
148 | org.springframework
149 | spring-context
150 | 4.0.2.RELEASE
151 | compile
152 |
153 |
154 | javax.validation
155 | validation-api
156 | 1.0.0.GA
157 | compile
158 |
159 |
160 | org.thymeleaf
161 | thymeleaf
162 | 2.1.2.RELEASE
163 | compile
164 |
165 |
166 | javax.servlet
167 | javax.servlet-api
168 | 3.0.1
169 | provided
170 |
171 |
172 | org.aspectj
173 | aspectjrt
174 | 1.6.10
175 | compile
176 |
177 |
178 | org.slf4j
179 | slf4j-log4j12
180 | 1.7.6
181 | compile
182 |
183 |
184 | org.springframework
185 | spring-test-mvc-htmlunit
186 | 1.0.0.BUILD-SNAPSHOT
187 | test
188 |
189 |
190 | org.thymeleaf
191 | thymeleaf-spring4
192 | 2.1.2.RELEASE
193 | compile
194 |
195 |
196 | org.hibernate
197 | hibernate-validator
198 | 4.1.0.Final
199 | compile
200 |
201 |
202 | org.gebish
203 | geb-spock
204 | 0.9.2
205 | test
206 |
207 |
208 | junit
209 | junit
210 | 4.8.2
211 | test
212 |
213 |
214 | org.easytesting
215 | fest-assert
216 | 1.4
217 | test
218 |
219 |
220 | org.springframework
221 | spring-webmvc
222 | 4.0.2.RELEASE
223 | compile
224 |
225 |
226 | org.springframework
227 | spring-tx
228 | 4.0.2.RELEASE
229 | compile
230 |
231 |
232 | org.springframework.data
233 | spring-data-jpa
234 | 1.5.1.RELEASE
235 | compile
236 |
237 |
238 | org.springframework.security
239 | spring-security-config
240 | 4.0.0.M1
241 | compile
242 |
243 |
244 | org.hibernate
245 | hibernate-entitymanager
246 | 4.3.4.Final
247 | compile
248 |
249 |
250 | org.spockframework
251 | spock-core
252 | 0.7-groovy-2.0
253 | test
254 |
255 |
256 | org.hsqldb
257 | hsqldb
258 | 2.3.2
259 | compile
260 |
261 |
262 | xml-apis
263 | xml-apis
264 | 1.4.01
265 |
266 |
267 | org.springframework.security
268 | spring-security-test
269 | 4.0.0.M1
270 | test
271 |
272 |
273 | org.hibernate.javax.persistence
274 | hibernate-jpa-2.0-api
275 | 1.0.1.Final
276 | compile
277 |
278 |
279 | org.codehaus.groovy
280 | groovy
281 | 2.2.2
282 | test
283 |
284 |
285 | org.easytesting
286 | fest-assert-core
287 | 2.0M10
288 | test
289 |
290 |
291 | org.seleniumhq.selenium
292 | selenium-support
293 | 2.40.0
294 | test
295 |
296 |
297 | org.springframework
298 | spring-test
299 | 4.0.2.RELEASE
300 | test
301 |
302 |
303 |
304 |
--------------------------------------------------------------------------------
/src/main/webapp/resources/js/jquery.validate.js:
--------------------------------------------------------------------------------
1 | /**
2 | * jQuery Validation Plugin @VERSION
3 | *
4 | * http://bassistance.de/jquery-plugins/jquery-plugin-validation/
5 | * http://docs.jquery.com/Plugins/Validation
6 | *
7 | * Copyright (c) 2012 Jörn Zaefferer
8 | *
9 | * Dual licensed under the MIT and GPL licenses:
10 | * http://www.opensource.org/licenses/mit-license.php
11 | * http://www.gnu.org/licenses/gpl.html
12 | */
13 |
14 | (function($) {
15 |
16 | $.extend($.fn, {
17 | // http://docs.jquery.com/Plugins/Validation/validate
18 | validate: function( options ) {
19 |
20 | // if nothing is selected, return nothing; can't chain anyway
21 | if (!this.length) {
22 | if (options && options.debug && window.console) {
23 | console.warn( "nothing selected, can't validate, returning nothing" );
24 | }
25 | return;
26 | }
27 |
28 | // check if a validator for this form was already created
29 | var validator = $.data(this[0], 'validator');
30 | if ( validator ) {
31 | return validator;
32 | }
33 |
34 | // Add novalidate tag if HTML5.
35 | this.attr('novalidate', 'novalidate');
36 |
37 | validator = new $.validator( options, this[0] );
38 | $.data(this[0], 'validator', validator);
39 |
40 | if ( validator.settings.onsubmit ) {
41 |
42 | this.validateDelegate( ":submit", "click", function(ev) {
43 | if ( validator.settings.submitHandler ) {
44 | validator.submitButton = ev.target;
45 | }
46 | // allow suppressing validation by adding a cancel class to the submit button
47 | if ( $(ev.target).hasClass('cancel') ) {
48 | validator.cancelSubmit = true;
49 | }
50 | });
51 |
52 | // validate the form on submit
53 | this.submit( function( event ) {
54 | if ( validator.settings.debug ) {
55 | // prevent form submit to be able to see console output
56 | event.preventDefault();
57 | }
58 | function handle() {
59 | var hidden;
60 | if ( validator.settings.submitHandler ) {
61 | if (validator.submitButton) {
62 | // insert a hidden input as a replacement for the missing submit button
63 | hidden = $(" ").attr("name", validator.submitButton.name).val(validator.submitButton.value).appendTo(validator.currentForm);
64 | }
65 | validator.settings.submitHandler.call( validator, validator.currentForm, event );
66 | if (validator.submitButton) {
67 | // and clean up afterwards; thanks to no-block-scope, hidden can be referenced
68 | hidden.remove();
69 | }
70 | return false;
71 | }
72 | return true;
73 | }
74 |
75 | // prevent submit for invalid forms or custom submit handlers
76 | if ( validator.cancelSubmit ) {
77 | validator.cancelSubmit = false;
78 | return handle();
79 | }
80 | if ( validator.form() ) {
81 | if ( validator.pendingRequest ) {
82 | validator.formSubmitted = true;
83 | return false;
84 | }
85 | return handle();
86 | } else {
87 | validator.focusInvalid();
88 | return false;
89 | }
90 | });
91 | }
92 |
93 | return validator;
94 | },
95 | // http://docs.jquery.com/Plugins/Validation/valid
96 | valid: function() {
97 | if ( $(this[0]).is('form')) {
98 | return this.validate().form();
99 | } else {
100 | var valid = true;
101 | var validator = $(this[0].form).validate();
102 | this.each(function() {
103 | valid &= validator.element(this);
104 | });
105 | return valid;
106 | }
107 | },
108 | // attributes: space seperated list of attributes to retrieve and remove
109 | removeAttrs: function(attributes) {
110 | var result = {},
111 | $element = this;
112 | $.each(attributes.split(/\s/), function(index, value) {
113 | result[value] = $element.attr(value);
114 | $element.removeAttr(value);
115 | });
116 | return result;
117 | },
118 | // http://docs.jquery.com/Plugins/Validation/rules
119 | rules: function(command, argument) {
120 | var element = this[0];
121 |
122 | if (command) {
123 | var settings = $.data(element.form, 'validator').settings;
124 | var staticRules = settings.rules;
125 | var existingRules = $.validator.staticRules(element);
126 | switch(command) {
127 | case "add":
128 | $.extend(existingRules, $.validator.normalizeRule(argument));
129 | staticRules[element.name] = existingRules;
130 | if (argument.messages) {
131 | settings.messages[element.name] = $.extend( settings.messages[element.name], argument.messages );
132 | }
133 | break;
134 | case "remove":
135 | if (!argument) {
136 | delete staticRules[element.name];
137 | return existingRules;
138 | }
139 | var filtered = {};
140 | $.each(argument.split(/\s/), function(index, method) {
141 | filtered[method] = existingRules[method];
142 | delete existingRules[method];
143 | });
144 | return filtered;
145 | }
146 | }
147 |
148 | var data = $.validator.normalizeRules(
149 | $.extend(
150 | {},
151 | $.validator.metadataRules(element),
152 | $.validator.classRules(element),
153 | $.validator.attributeRules(element),
154 | $.validator.staticRules(element)
155 | ), element);
156 |
157 | // make sure required is at front
158 | if (data.required) {
159 | var param = data.required;
160 | delete data.required;
161 | data = $.extend({required: param}, data);
162 | }
163 |
164 | return data;
165 | }
166 | });
167 |
168 | // Custom selectors
169 | $.extend($.expr[":"], {
170 | // http://docs.jquery.com/Plugins/Validation/blank
171 | blank: function(a) {return !$.trim("" + a.value);},
172 | // http://docs.jquery.com/Plugins/Validation/filled
173 | filled: function(a) {return !!$.trim("" + a.value);},
174 | // http://docs.jquery.com/Plugins/Validation/unchecked
175 | unchecked: function(a) {return !a.checked;}
176 | });
177 |
178 | // constructor for validator
179 | $.validator = function( options, form ) {
180 | this.settings = $.extend( true, {}, $.validator.defaults, options );
181 | this.currentForm = form;
182 | this.init();
183 | };
184 |
185 | $.validator.format = function(source, params) {
186 | if ( arguments.length === 1 ) {
187 | return function() {
188 | var args = $.makeArray(arguments);
189 | args.unshift(source);
190 | return $.validator.format.apply( this, args );
191 | };
192 | }
193 | if ( arguments.length > 2 && params.constructor !== Array ) {
194 | params = $.makeArray(arguments).slice(1);
195 | }
196 | if ( params.constructor !== Array ) {
197 | params = [ params ];
198 | }
199 | $.each(params, function(i, n) {
200 | source = source.replace(new RegExp("\\{" + i + "\\}", "g"), n);
201 | });
202 | return source;
203 | };
204 |
205 | $.extend($.validator, {
206 |
207 | defaults: {
208 | messages: {},
209 | groups: {},
210 | rules: {},
211 | errorClass: "error",
212 | validClass: "valid",
213 | errorElement: "label",
214 | focusInvalid: true,
215 | errorContainer: $( [] ),
216 | errorLabelContainer: $( [] ),
217 | onsubmit: true,
218 | ignore: ":hidden",
219 | ignoreTitle: false,
220 | onfocusin: function(element, event) {
221 | this.lastActive = element;
222 |
223 | // hide error label and remove error class on focus if enabled
224 | if ( this.settings.focusCleanup && !this.blockFocusCleanup ) {
225 | if ( this.settings.unhighlight ) {
226 | this.settings.unhighlight.call( this, element, this.settings.errorClass, this.settings.validClass );
227 | }
228 | this.addWrapper(this.errorsFor(element)).hide();
229 | }
230 | },
231 | onfocusout: function(element, event) {
232 | if ( !this.checkable(element) && (element.name in this.submitted || !this.optional(element)) ) {
233 | this.element(element);
234 | }
235 | },
236 | onkeyup: function(element, event) {
237 | if ( element.name in this.submitted || element === this.lastElement ) {
238 | this.element(element);
239 | }
240 | },
241 | onclick: function(element, event) {
242 | // click on selects, radiobuttons and checkboxes
243 | if ( element.name in this.submitted ) {
244 | this.element(element);
245 | }
246 | // or option elements, check parent select in that case
247 | else if (element.parentNode.name in this.submitted) {
248 | this.element(element.parentNode);
249 | }
250 | },
251 | highlight: function(element, errorClass, validClass) {
252 | if (element.type === 'radio') {
253 | this.findByName(element.name).addClass(errorClass).removeClass(validClass);
254 | } else {
255 | $(element).addClass(errorClass).removeClass(validClass);
256 | }
257 | },
258 | unhighlight: function(element, errorClass, validClass) {
259 | if (element.type === 'radio') {
260 | this.findByName(element.name).removeClass(errorClass).addClass(validClass);
261 | } else {
262 | $(element).removeClass(errorClass).addClass(validClass);
263 | }
264 | }
265 | },
266 |
267 | // http://docs.jquery.com/Plugins/Validation/Validator/setDefaults
268 | setDefaults: function(settings) {
269 | $.extend( $.validator.defaults, settings );
270 | },
271 |
272 | messages: {
273 | required: "This field is required.",
274 | remote: "Please fix this field.",
275 | email: "Please enter a valid email address.",
276 | url: "Please enter a valid URL.",
277 | date: "Please enter a valid date.",
278 | dateISO: "Please enter a valid date (ISO).",
279 | number: "Please enter a valid number.",
280 | digits: "Please enter only digits.",
281 | creditcard: "Please enter a valid credit card number.",
282 | equalTo: "Please enter the same value again.",
283 | accept: "Please enter a value with a valid extension.",
284 | maxlength: $.validator.format("Please enter no more than {0} characters."),
285 | minlength: $.validator.format("Please enter at least {0} characters."),
286 | rangelength: $.validator.format("Please enter a value between {0} and {1} characters long."),
287 | range: $.validator.format("Please enter a value between {0} and {1}."),
288 | max: $.validator.format("Please enter a value less than or equal to {0}."),
289 | min: $.validator.format("Please enter a value greater than or equal to {0}.")
290 | },
291 |
292 | autoCreateRanges: false,
293 |
294 | prototype: {
295 |
296 | init: function() {
297 | this.labelContainer = $(this.settings.errorLabelContainer);
298 | this.errorContext = this.labelContainer.length && this.labelContainer || $(this.currentForm);
299 | this.containers = $(this.settings.errorContainer).add( this.settings.errorLabelContainer );
300 | this.submitted = {};
301 | this.valueCache = {};
302 | this.pendingRequest = 0;
303 | this.pending = {};
304 | this.invalid = {};
305 | this.reset();
306 |
307 | var groups = (this.groups = {});
308 | $.each(this.settings.groups, function(key, value) {
309 | $.each(value.split(/\s/), function(index, name) {
310 | groups[name] = key;
311 | });
312 | });
313 | var rules = this.settings.rules;
314 | $.each(rules, function(key, value) {
315 | rules[key] = $.validator.normalizeRule(value);
316 | });
317 |
318 | function delegate(event) {
319 | var validator = $.data(this[0].form, "validator"),
320 | eventType = "on" + event.type.replace(/^validate/, "");
321 | if (validator.settings[eventType]) {
322 | validator.settings[eventType].call(validator, this[0], event);
323 | }
324 | }
325 | $(this.currentForm)
326 | .validateDelegate("[type='text'], [type='password'], [type='file'], select, textarea, " +
327 | "[type='number'], [type='search'] ,[type='tel'], [type='url'], " +
328 | "[type='email'], [type='datetime'], [type='date'], [type='month'], " +
329 | "[type='week'], [type='time'], [type='datetime-local'], " +
330 | "[type='range'], [type='color'] ",
331 | "focusin focusout keyup", delegate)
332 | .validateDelegate("[type='radio'], [type='checkbox'], select, option", "click", delegate);
333 |
334 | if (this.settings.invalidHandler) {
335 | $(this.currentForm).bind("invalid-form.validate", this.settings.invalidHandler);
336 | }
337 | },
338 |
339 | // http://docs.jquery.com/Plugins/Validation/Validator/form
340 | form: function() {
341 | this.checkForm();
342 | $.extend(this.submitted, this.errorMap);
343 | this.invalid = $.extend({}, this.errorMap);
344 | if (!this.valid()) {
345 | $(this.currentForm).triggerHandler("invalid-form", [this]);
346 | }
347 | this.showErrors();
348 | return this.valid();
349 | },
350 |
351 | checkForm: function() {
352 | this.prepareForm();
353 | for ( var i = 0, elements = (this.currentElements = this.elements()); elements[i]; i++ ) {
354 | this.check( elements[i] );
355 | }
356 | return this.valid();
357 | },
358 |
359 | // http://docs.jquery.com/Plugins/Validation/Validator/element
360 | element: function( element ) {
361 | element = this.validationTargetFor( this.clean( element ) );
362 | this.lastElement = element;
363 | this.prepareElement( element );
364 | this.currentElements = $(element);
365 | var result = this.check( element ) !== false;
366 | if (result) {
367 | delete this.invalid[element.name];
368 | } else {
369 | this.invalid[element.name] = true;
370 | }
371 | if ( !this.numberOfInvalids() ) {
372 | // Hide error containers on last error
373 | this.toHide = this.toHide.add( this.containers );
374 | }
375 | this.showErrors();
376 | return result;
377 | },
378 |
379 | // http://docs.jquery.com/Plugins/Validation/Validator/showErrors
380 | showErrors: function(errors) {
381 | if(errors) {
382 | // add items to error list and map
383 | $.extend( this.errorMap, errors );
384 | this.errorList = [];
385 | for ( var name in errors ) {
386 | this.errorList.push({
387 | message: errors[name],
388 | element: this.findByName(name)[0]
389 | });
390 | }
391 | // remove items from success list
392 | this.successList = $.grep( this.successList, function(element) {
393 | return !(element.name in errors);
394 | });
395 | }
396 | if (this.settings.showErrors) {
397 | this.settings.showErrors.call( this, this.errorMap, this.errorList );
398 | } else {
399 | this.defaultShowErrors();
400 | }
401 | },
402 |
403 | // http://docs.jquery.com/Plugins/Validation/Validator/resetForm
404 | resetForm: function() {
405 | if ( $.fn.resetForm ) {
406 | $( this.currentForm ).resetForm();
407 | }
408 | this.submitted = {};
409 | this.lastElement = null;
410 | this.prepareForm();
411 | this.hideErrors();
412 | this.elements().removeClass( this.settings.errorClass );
413 | },
414 |
415 | numberOfInvalids: function() {
416 | return this.objectLength(this.invalid);
417 | },
418 |
419 | objectLength: function( obj ) {
420 | var count = 0;
421 | for ( var i in obj ) {
422 | count++;
423 | }
424 | return count;
425 | },
426 |
427 | hideErrors: function() {
428 | this.addWrapper( this.toHide ).hide();
429 | },
430 |
431 | valid: function() {
432 | return this.size() === 0;
433 | },
434 |
435 | size: function() {
436 | return this.errorList.length;
437 | },
438 |
439 | focusInvalid: function() {
440 | if( this.settings.focusInvalid ) {
441 | try {
442 | $(this.findLastActive() || this.errorList.length && this.errorList[0].element || [])
443 | .filter(":visible")
444 | .focus()
445 | // manually trigger focusin event; without it, focusin handler isn't called, findLastActive won't have anything to find
446 | .trigger("focusin");
447 | } catch(e) {
448 | // ignore IE throwing errors when focusing hidden elements
449 | }
450 | }
451 | },
452 |
453 | findLastActive: function() {
454 | var lastActive = this.lastActive;
455 | return lastActive && $.grep(this.errorList, function(n) {
456 | return n.element.name === lastActive.name;
457 | }).length === 1 && lastActive;
458 | },
459 |
460 | elements: function() {
461 | var validator = this,
462 | rulesCache = {};
463 |
464 | // select all valid inputs inside the form (no submit or reset buttons)
465 | return $(this.currentForm)
466 | .find("input, select, textarea")
467 | .not(":submit, :reset, :image, [disabled]")
468 | .not( this.settings.ignore )
469 | .filter(function() {
470 | if ( !this.name && validator.settings.debug && window.console ) {
471 | console.error( "%o has no name assigned", this);
472 | }
473 |
474 | // select only the first element for each name, and only those with rules specified
475 | if ( this.name in rulesCache || !validator.objectLength($(this).rules()) ) {
476 | return false;
477 | }
478 |
479 | rulesCache[this.name] = true;
480 | return true;
481 | });
482 | },
483 |
484 | clean: function( selector ) {
485 | return $( selector )[0];
486 | },
487 |
488 | errors: function() {
489 | var errorClass = this.settings.errorClass.replace(' ', '.');
490 | return $( this.settings.errorElement + "." + errorClass, this.errorContext );
491 | },
492 |
493 | reset: function() {
494 | this.successList = [];
495 | this.errorList = [];
496 | this.errorMap = {};
497 | this.toShow = $([]);
498 | this.toHide = $([]);
499 | this.currentElements = $([]);
500 | },
501 |
502 | prepareForm: function() {
503 | this.reset();
504 | this.toHide = this.errors().add( this.containers );
505 | },
506 |
507 | prepareElement: function( element ) {
508 | this.reset();
509 | this.toHide = this.errorsFor(element);
510 | },
511 |
512 | elementValue: function( element ) {
513 | var val = $(element).val();
514 | if( typeof val === 'string' ) {
515 | return val.replace(/\r/g, "");
516 | }
517 | return val;
518 | },
519 |
520 | check: function( element ) {
521 | element = this.validationTargetFor( this.clean( element ) );
522 |
523 | var rules = $(element).rules();
524 | var dependencyMismatch = false;
525 | var val = this.elementValue(element);
526 | var result;
527 |
528 | for (var method in rules ) {
529 | var rule = { method: method, parameters: rules[method] };
530 | try {
531 |
532 | result = $.validator.methods[method].call( this, val, element, rule.parameters );
533 |
534 | // if a method indicates that the field is optional and therefore valid,
535 | // don't mark it as valid when there are no other rules
536 | if ( result === "dependency-mismatch" ) {
537 | dependencyMismatch = true;
538 | continue;
539 | }
540 | dependencyMismatch = false;
541 |
542 | if ( result === "pending" ) {
543 | this.toHide = this.toHide.not( this.errorsFor(element) );
544 | return;
545 | }
546 |
547 | if( !result ) {
548 | this.formatAndAdd( element, rule );
549 | return false;
550 | }
551 | } catch(e) {
552 | if ( this.settings.debug && window.console ) {
553 | console.log("exception occured when checking element " + element.id + ", check the '" + rule.method + "' method", e);
554 | }
555 | throw e;
556 | }
557 | }
558 | if (dependencyMismatch) {
559 | return;
560 | }
561 | if ( this.objectLength(rules) ) {
562 | this.successList.push(element);
563 | }
564 | return true;
565 | },
566 |
567 | // return the custom message for the given element and validation method
568 | // specified in the element's "messages" metadata
569 | customMetaMessage: function(element, method) {
570 | if (!$.metadata) {
571 | return;
572 | }
573 | var meta = this.settings.meta ? $(element).metadata()[this.settings.meta] : $(element).metadata();
574 | return meta && meta.messages && meta.messages[method];
575 | },
576 |
577 | // return the custom message for the given element name and validation method
578 | customMessage: function( name, method ) {
579 | var m = this.settings.messages[name];
580 | return m && (m.constructor === String ? m : m[method]);
581 | },
582 |
583 | // return the first defined argument, allowing empty strings
584 | findDefined: function() {
585 | for(var i = 0; i < arguments.length; i++) {
586 | if (arguments[i] !== undefined) {
587 | return arguments[i];
588 | }
589 | }
590 | return undefined;
591 | },
592 |
593 | defaultMessage: function( element, method) {
594 | return this.findDefined(
595 | this.customMessage( element.name, method ),
596 | this.customMetaMessage( element, method ),
597 | // title is never undefined, so handle empty string as undefined
598 | !this.settings.ignoreTitle && element.title || undefined,
599 | $.validator.messages[method],
600 | "Warning: No message defined for " + element.name + " "
601 | );
602 | },
603 |
604 | formatAndAdd: function( element, rule ) {
605 | var message = this.defaultMessage( element, rule.method ),
606 | theregex = /\$?\{(\d+)\}/g;
607 | if ( typeof message === "function" ) {
608 | message = message.call(this, rule.parameters, element);
609 | } else if (theregex.test(message)) {
610 | message = $.validator.format(message.replace(theregex, '{$1}'), rule.parameters);
611 | }
612 | this.errorList.push({
613 | message: message,
614 | element: element
615 | });
616 |
617 | this.errorMap[element.name] = message;
618 | this.submitted[element.name] = message;
619 | },
620 |
621 | addWrapper: function(toToggle) {
622 | if ( this.settings.wrapper ) {
623 | toToggle = toToggle.add( toToggle.parent( this.settings.wrapper ) );
624 | }
625 | return toToggle;
626 | },
627 |
628 | defaultShowErrors: function() {
629 | var i, elements;
630 | for ( i = 0; this.errorList[i]; i++ ) {
631 | var error = this.errorList[i];
632 | if ( this.settings.highlight ) {
633 | this.settings.highlight.call( this, error.element, this.settings.errorClass, this.settings.validClass );
634 | }
635 | this.showLabel( error.element, error.message );
636 | }
637 | if( this.errorList.length ) {
638 | this.toShow = this.toShow.add( this.containers );
639 | }
640 | if (this.settings.success) {
641 | for ( i = 0; this.successList[i]; i++ ) {
642 | this.showLabel( this.successList[i] );
643 | }
644 | }
645 | if (this.settings.unhighlight) {
646 | for ( i = 0, elements = this.validElements(); elements[i]; i++ ) {
647 | this.settings.unhighlight.call( this, elements[i], this.settings.errorClass, this.settings.validClass );
648 | }
649 | }
650 | this.toHide = this.toHide.not( this.toShow );
651 | this.hideErrors();
652 | this.addWrapper( this.toShow ).show();
653 | },
654 |
655 | validElements: function() {
656 | return this.currentElements.not(this.invalidElements());
657 | },
658 |
659 | invalidElements: function() {
660 | return $(this.errorList).map(function() {
661 | return this.element;
662 | });
663 | },
664 |
665 | showLabel: function(element, message) {
666 | var label = this.errorsFor( element );
667 | if ( label.length ) {
668 | // refresh error/success class
669 | label.removeClass( this.settings.validClass ).addClass( this.settings.errorClass );
670 |
671 | // check if we have a generated label, replace the message then
672 | if ( label.attr("generated") ) {
673 | label.html(message);
674 | }
675 | } else {
676 | // create label
677 | label = $("<" + this.settings.errorElement + "/>")
678 | .attr({"for": this.idOrName(element), generated: true})
679 | .addClass(this.settings.errorClass)
680 | .html(message || "");
681 | if ( this.settings.wrapper ) {
682 | // make sure the element is visible, even in IE
683 | // actually showing the wrapped element is handled elsewhere
684 | label = label.hide().show().wrap("<" + this.settings.wrapper + "/>").parent();
685 | }
686 | if ( !this.labelContainer.append(label).length ) {
687 | if ( this.settings.errorPlacement ) {
688 | this.settings.errorPlacement(label, $(element) );
689 | } else {
690 | label.insertAfter(element);
691 | }
692 | }
693 | }
694 | if ( !message && this.settings.success ) {
695 | label.text("");
696 | if ( typeof this.settings.success === "string" ) {
697 | label.addClass( this.settings.success );
698 | } else {
699 | this.settings.success( label );
700 | }
701 | }
702 | this.toShow = this.toShow.add(label);
703 | },
704 |
705 | errorsFor: function(element) {
706 | var name = this.idOrName(element);
707 | return this.errors().filter(function() {
708 | return $(this).attr('for') === name;
709 | });
710 | },
711 |
712 | idOrName: function(element) {
713 | return this.groups[element.name] || (this.checkable(element) ? element.name : element.id || element.name);
714 | },
715 |
716 | validationTargetFor: function(element) {
717 | // if radio/checkbox, validate first element in group instead
718 | if (this.checkable(element)) {
719 | element = this.findByName( element.name ).not(this.settings.ignore)[0];
720 | }
721 | return element;
722 | },
723 |
724 | checkable: function( element ) {
725 | return (/radio|checkbox/i).test(element.type);
726 | },
727 |
728 | findByName: function( name ) {
729 | // select by name and filter by form for performance over form.find("[name=...]")
730 | var form = this.currentForm;
731 | return $(document.getElementsByName(name)).map(function(index, element) {
732 | return element.form === form && element.name === name && element || null;
733 | });
734 | },
735 |
736 | getLength: function(value, element) {
737 | switch( element.nodeName.toLowerCase() ) {
738 | case 'select':
739 | return $("option:selected", element).length;
740 | case 'input':
741 | if( this.checkable( element) ) {
742 | return this.findByName(element.name).filter(':checked').length;
743 | }
744 | }
745 | return value.length;
746 | },
747 |
748 | depend: function(param, element) {
749 | return this.dependTypes[typeof param] ? this.dependTypes[typeof param](param, element) : true;
750 | },
751 |
752 | dependTypes: {
753 | "boolean": function(param, element) {
754 | return param;
755 | },
756 | "string": function(param, element) {
757 | return !!$(param, element.form).length;
758 | },
759 | "function": function(param, element) {
760 | return param(element);
761 | }
762 | },
763 |
764 | optional: function(element) {
765 | var val = this.elementValue(element);
766 | return !$.validator.methods.required.call(this, val, element) && "dependency-mismatch";
767 | },
768 |
769 | startRequest: function(element) {
770 | if (!this.pending[element.name]) {
771 | this.pendingRequest++;
772 | this.pending[element.name] = true;
773 | }
774 | },
775 |
776 | stopRequest: function(element, valid) {
777 | this.pendingRequest--;
778 | // sometimes synchronization fails, make sure pendingRequest is never < 0
779 | if (this.pendingRequest < 0) {
780 | this.pendingRequest = 0;
781 | }
782 | delete this.pending[element.name];
783 | if ( valid && this.pendingRequest === 0 && this.formSubmitted && this.form() ) {
784 | $(this.currentForm).submit();
785 | this.formSubmitted = false;
786 | } else if (!valid && this.pendingRequest === 0 && this.formSubmitted) {
787 | $(this.currentForm).triggerHandler("invalid-form", [this]);
788 | this.formSubmitted = false;
789 | }
790 | },
791 |
792 | previousValue: function(element) {
793 | return $.data(element, "previousValue") || $.data(element, "previousValue", {
794 | old: null,
795 | valid: true,
796 | message: this.defaultMessage( element, "remote" )
797 | });
798 | }
799 |
800 | },
801 |
802 | classRuleSettings: {
803 | required: {required: true},
804 | email: {email: true},
805 | url: {url: true},
806 | date: {date: true},
807 | dateISO: {dateISO: true},
808 | number: {number: true},
809 | digits: {digits: true},
810 | creditcard: {creditcard: true}
811 | },
812 |
813 | addClassRules: function(className, rules) {
814 | if ( className.constructor === String ) {
815 | this.classRuleSettings[className] = rules;
816 | } else {
817 | $.extend(this.classRuleSettings, className);
818 | }
819 | },
820 |
821 | classRules: function(element) {
822 | var rules = {};
823 | var classes = $(element).attr('class');
824 | if ( classes ) {
825 | $.each(classes.split(' '), function() {
826 | if (this in $.validator.classRuleSettings) {
827 | $.extend(rules, $.validator.classRuleSettings[this]);
828 | }
829 | });
830 | }
831 | return rules;
832 | },
833 |
834 | attributeRules: function(element) {
835 | var rules = {};
836 | var $element = $(element);
837 |
838 | for (var method in $.validator.methods) {
839 | var value;
840 |
841 | // support for in both html5 and older browsers
842 | if (method === 'required') {
843 | value = $element.get(0).getAttribute(method);
844 | // Some browsers return an empty string for the required attribute
845 | // and non-HTML5 browsers might have required="" markup
846 | if (value === "") {
847 | value = true;
848 | } else if (value === "false") {
849 | value = false;
850 | }
851 | // force non-HTML5 browsers to return bool
852 | value = !!value;
853 | } else {
854 | value = $element.attr(method);
855 | }
856 |
857 | if (value) {
858 | rules[method] = value;
859 | } else if ($element[0].getAttribute("type") === method) {
860 | rules[method] = true;
861 | }
862 | }
863 |
864 | // maxlength may be returned as -1, 2147483647 (IE) and 524288 (safari) for text inputs
865 | if (rules.maxlength && /-1|2147483647|524288/.test(rules.maxlength)) {
866 | delete rules.maxlength;
867 | }
868 |
869 | return rules;
870 | },
871 |
872 | metadataRules: function(element) {
873 | if (!$.metadata) {
874 | return {};
875 | }
876 |
877 | var meta = $.data(element.form, 'validator').settings.meta;
878 | return meta ?
879 | $(element).metadata()[meta] :
880 | $(element).metadata();
881 | },
882 |
883 | staticRules: function(element) {
884 | var rules = {};
885 | var validator = $.data(element.form, 'validator');
886 | if (validator.settings.rules) {
887 | rules = $.validator.normalizeRule(validator.settings.rules[element.name]) || {};
888 | }
889 | return rules;
890 | },
891 |
892 | normalizeRules: function(rules, element) {
893 | // handle dependency check
894 | $.each(rules, function(prop, val) {
895 | // ignore rule when param is explicitly false, eg. required:false
896 | if (val === false) {
897 | delete rules[prop];
898 | return;
899 | }
900 | if (val.param || val.depends) {
901 | var keepRule = true;
902 | switch (typeof val.depends) {
903 | case "string":
904 | keepRule = !!$(val.depends, element.form).length;
905 | break;
906 | case "function":
907 | keepRule = val.depends.call(element, element);
908 | break;
909 | }
910 | if (keepRule) {
911 | rules[prop] = val.param !== undefined ? val.param : true;
912 | } else {
913 | delete rules[prop];
914 | }
915 | }
916 | });
917 |
918 | // evaluate parameters
919 | $.each(rules, function(rule, parameter) {
920 | rules[rule] = $.isFunction(parameter) ? parameter(element) : parameter;
921 | });
922 |
923 | // clean number parameters
924 | $.each(['minlength', 'maxlength', 'min', 'max'], function() {
925 | if (rules[this]) {
926 | rules[this] = Number(rules[this]);
927 | }
928 | });
929 | $.each(['rangelength', 'range'], function() {
930 | if (rules[this]) {
931 | rules[this] = [Number(rules[this][0]), Number(rules[this][1])];
932 | }
933 | });
934 |
935 | if ($.validator.autoCreateRanges) {
936 | // auto-create ranges
937 | if (rules.min && rules.max) {
938 | rules.range = [rules.min, rules.max];
939 | delete rules.min;
940 | delete rules.max;
941 | }
942 | if (rules.minlength && rules.maxlength) {
943 | rules.rangelength = [rules.minlength, rules.maxlength];
944 | delete rules.minlength;
945 | delete rules.maxlength;
946 | }
947 | }
948 |
949 | // To support custom messages in metadata ignore rule methods titled "messages"
950 | if (rules.messages) {
951 | delete rules.messages;
952 | }
953 |
954 | return rules;
955 | },
956 |
957 | // Converts a simple string to a {string: true} rule, e.g., "required" to {required:true}
958 | normalizeRule: function(data) {
959 | if( typeof data === "string" ) {
960 | var transformed = {};
961 | $.each(data.split(/\s/), function() {
962 | transformed[this] = true;
963 | });
964 | data = transformed;
965 | }
966 | return data;
967 | },
968 |
969 | // http://docs.jquery.com/Plugins/Validation/Validator/addMethod
970 | addMethod: function(name, method, message) {
971 | $.validator.methods[name] = method;
972 | $.validator.messages[name] = message !== undefined ? message : $.validator.messages[name];
973 | if (method.length < 3) {
974 | $.validator.addClassRules(name, $.validator.normalizeRule(name));
975 | }
976 | },
977 |
978 | methods: {
979 |
980 | // http://docs.jquery.com/Plugins/Validation/Methods/required
981 | required: function(value, element, param) {
982 | // check if dependency is met
983 | if ( !this.depend(param, element) ) {
984 | return "dependency-mismatch";
985 | }
986 | if ( element.nodeName.toLowerCase() === "select" ) {
987 | // could be an array for select-multiple or a string, both are fine this way
988 | var val = $(element).val();
989 | return val && val.length > 0;
990 | }
991 | if ( this.checkable(element) ) {
992 | return this.getLength(value, element) > 0;
993 | }
994 | return $.trim(value).length > 0;
995 | },
996 |
997 | // http://docs.jquery.com/Plugins/Validation/Methods/remote
998 | remote: function(value, element, param) {
999 | if ( this.optional(element) ) {
1000 | return "dependency-mismatch";
1001 | }
1002 |
1003 | var previous = this.previousValue(element);
1004 | if (!this.settings.messages[element.name] ) {
1005 | this.settings.messages[element.name] = {};
1006 | }
1007 | previous.originalMessage = this.settings.messages[element.name].remote;
1008 | this.settings.messages[element.name].remote = previous.message;
1009 |
1010 | param = typeof param === "string" && {url:param} || param;
1011 |
1012 | if ( this.pending[element.name] ) {
1013 | return "pending";
1014 | }
1015 | if ( previous.old === value ) {
1016 | return previous.valid;
1017 | }
1018 |
1019 | previous.old = value;
1020 | var validator = this;
1021 | this.startRequest(element);
1022 | var data = {};
1023 | data[element.name] = value;
1024 | $.ajax($.extend(true, {
1025 | url: param,
1026 | mode: "abort",
1027 | port: "validate" + element.name,
1028 | dataType: "json",
1029 | data: data,
1030 | success: function(response) {
1031 | validator.settings.messages[element.name].remote = previous.originalMessage;
1032 | var valid = response === true;
1033 | if ( valid ) {
1034 | var submitted = validator.formSubmitted;
1035 | validator.prepareElement(element);
1036 | validator.formSubmitted = submitted;
1037 | validator.successList.push(element);
1038 | validator.showErrors();
1039 | } else {
1040 | var errors = {};
1041 | var message = response || validator.defaultMessage( element, "remote" );
1042 | errors[element.name] = previous.message = $.isFunction(message) ? message(value) : message;
1043 | validator.showErrors(errors);
1044 | }
1045 | previous.valid = valid;
1046 | validator.stopRequest(element, valid);
1047 | }
1048 | }, param));
1049 | return "pending";
1050 | },
1051 |
1052 | // http://docs.jquery.com/Plugins/Validation/Methods/minlength
1053 | minlength: function(value, element, param) {
1054 | var length = $.isArray( value ) ? value.length : this.getLength($.trim(value), element);
1055 | return this.optional(element) || length >= param;
1056 | },
1057 |
1058 | // http://docs.jquery.com/Plugins/Validation/Methods/maxlength
1059 | maxlength: function(value, element, param) {
1060 | var length = $.isArray( value ) ? value.length : this.getLength($.trim(value), element);
1061 | return this.optional(element) || length <= param;
1062 | },
1063 |
1064 | // http://docs.jquery.com/Plugins/Validation/Methods/rangelength
1065 | rangelength: function(value, element, param) {
1066 | var length = $.isArray( value ) ? value.length : this.getLength($.trim(value), element);
1067 | return this.optional(element) || ( length >= param[0] && length <= param[1] );
1068 | },
1069 |
1070 | // http://docs.jquery.com/Plugins/Validation/Methods/min
1071 | min: function( value, element, param ) {
1072 | return this.optional(element) || value >= param;
1073 | },
1074 |
1075 | // http://docs.jquery.com/Plugins/Validation/Methods/max
1076 | max: function( value, element, param ) {
1077 | return this.optional(element) || value <= param;
1078 | },
1079 |
1080 | // http://docs.jquery.com/Plugins/Validation/Methods/range
1081 | range: function( value, element, param ) {
1082 | return this.optional(element) || ( value >= param[0] && value <= param[1] );
1083 | },
1084 |
1085 | // http://docs.jquery.com/Plugins/Validation/Methods/email
1086 | email: function(value, element) {
1087 | // contributed by Scott Gonzalez: http://projects.scottsplayground.com/email_address_validation/
1088 | return this.optional(element) || /^((([a-z]|\d|[!#\$%&'\*\+\-\/=\?\^_`{\|}~]|[\u00A0-\uD7FF\uF900-\uFDCF\uFDF0-\uFFEF])+(\.([a-z]|\d|[!#\$%&'\*\+\-\/=\?\^_`{\|}~]|[\u00A0-\uD7FF\uF900-\uFDCF\uFDF0-\uFFEF])+)*)|((\x22)((((\x20|\x09)*(\x0d\x0a))?(\x20|\x09)+)?(([\x01-\x08\x0b\x0c\x0e-\x1f\x7f]|\x21|[\x23-\x5b]|[\x5d-\x7e]|[\u00A0-\uD7FF\uF900-\uFDCF\uFDF0-\uFFEF])|(\\([\x01-\x09\x0b\x0c\x0d-\x7f]|[\u00A0-\uD7FF\uF900-\uFDCF\uFDF0-\uFFEF]))))*(((\x20|\x09)*(\x0d\x0a))?(\x20|\x09)+)?(\x22)))@((([a-z]|\d|[\u00A0-\uD7FF\uF900-\uFDCF\uFDF0-\uFFEF])|(([a-z]|\d|[\u00A0-\uD7FF\uF900-\uFDCF\uFDF0-\uFFEF])([a-z]|\d|-|\.|_|~|[\u00A0-\uD7FF\uF900-\uFDCF\uFDF0-\uFFEF])*([a-z]|\d|[\u00A0-\uD7FF\uF900-\uFDCF\uFDF0-\uFFEF])))\.)+(([a-z]|[\u00A0-\uD7FF\uF900-\uFDCF\uFDF0-\uFFEF])|(([a-z]|[\u00A0-\uD7FF\uF900-\uFDCF\uFDF0-\uFFEF])([a-z]|\d|-|\.|_|~|[\u00A0-\uD7FF\uF900-\uFDCF\uFDF0-\uFFEF])*([a-z]|[\u00A0-\uD7FF\uF900-\uFDCF\uFDF0-\uFFEF])))$/i.test(value);
1089 | },
1090 |
1091 | // http://docs.jquery.com/Plugins/Validation/Methods/url
1092 | url: function(value, element) {
1093 | // contributed by Scott Gonzalez: http://projects.scottsplayground.com/iri/
1094 | return this.optional(element) || /^(https?|ftp):\/\/(((([a-z]|\d|-|\.|_|~|[\u00A0-\uD7FF\uF900-\uFDCF\uFDF0-\uFFEF])|(%[\da-f]{2})|[!\$&'\(\)\*\+,;=]|:)*@)?(((\d|[1-9]\d|1\d\d|2[0-4]\d|25[0-5])\.(\d|[1-9]\d|1\d\d|2[0-4]\d|25[0-5])\.(\d|[1-9]\d|1\d\d|2[0-4]\d|25[0-5])\.(\d|[1-9]\d|1\d\d|2[0-4]\d|25[0-5]))|((([a-z]|\d|[\u00A0-\uD7FF\uF900-\uFDCF\uFDF0-\uFFEF])|(([a-z]|\d|[\u00A0-\uD7FF\uF900-\uFDCF\uFDF0-\uFFEF])([a-z]|\d|-|\.|_|~|[\u00A0-\uD7FF\uF900-\uFDCF\uFDF0-\uFFEF])*([a-z]|\d|[\u00A0-\uD7FF\uF900-\uFDCF\uFDF0-\uFFEF])))\.)+(([a-z]|[\u00A0-\uD7FF\uF900-\uFDCF\uFDF0-\uFFEF])|(([a-z]|[\u00A0-\uD7FF\uF900-\uFDCF\uFDF0-\uFFEF])([a-z]|\d|-|\.|_|~|[\u00A0-\uD7FF\uF900-\uFDCF\uFDF0-\uFFEF])*([a-z]|[\u00A0-\uD7FF\uF900-\uFDCF\uFDF0-\uFFEF])))\.?)(:\d*)?)(\/((([a-z]|\d|-|\.|_|~|[\u00A0-\uD7FF\uF900-\uFDCF\uFDF0-\uFFEF])|(%[\da-f]{2})|[!\$&'\(\)\*\+,;=]|:|@)+(\/(([a-z]|\d|-|\.|_|~|[\u00A0-\uD7FF\uF900-\uFDCF\uFDF0-\uFFEF])|(%[\da-f]{2})|[!\$&'\(\)\*\+,;=]|:|@)*)*)?)?(\?((([a-z]|\d|-|\.|_|~|[\u00A0-\uD7FF\uF900-\uFDCF\uFDF0-\uFFEF])|(%[\da-f]{2})|[!\$&'\(\)\*\+,;=]|:|@)|[\uE000-\uF8FF]|\/|\?)*)?(\#((([a-z]|\d|-|\.|_|~|[\u00A0-\uD7FF\uF900-\uFDCF\uFDF0-\uFFEF])|(%[\da-f]{2})|[!\$&'\(\)\*\+,;=]|:|@)|\/|\?)*)?$/i.test(value);
1095 | },
1096 |
1097 | // http://docs.jquery.com/Plugins/Validation/Methods/date
1098 | date: function(value, element) {
1099 | return this.optional(element) || !/Invalid|NaN/.test(new Date(value));
1100 | },
1101 |
1102 | // http://docs.jquery.com/Plugins/Validation/Methods/dateISO
1103 | dateISO: function(value, element) {
1104 | return this.optional(element) || /^\d{4}[\/\-]\d{1,2}[\/\-]\d{1,2}$/.test(value);
1105 | },
1106 |
1107 | // http://docs.jquery.com/Plugins/Validation/Methods/number
1108 | number: function(value, element) {
1109 | return this.optional(element) || /^-?(?:\d+|\d{1,3}(?:,\d{3})+)?(?:\.\d+)?$/.test(value);
1110 | },
1111 |
1112 | // http://docs.jquery.com/Plugins/Validation/Methods/digits
1113 | digits: function(value, element) {
1114 | return this.optional(element) || /^\d+$/.test(value);
1115 | },
1116 |
1117 | // http://docs.jquery.com/Plugins/Validation/Methods/creditcard
1118 | // based on http://en.wikipedia.org/wiki/Luhn
1119 | creditcard: function(value, element) {
1120 | if ( this.optional(element) ) {
1121 | return "dependency-mismatch";
1122 | }
1123 | // accept only spaces, digits and dashes
1124 | if (/[^0-9 \-]+/.test(value)) {
1125 | return false;
1126 | }
1127 | var nCheck = 0,
1128 | nDigit = 0,
1129 | bEven = false;
1130 |
1131 | value = value.replace(/\D/g, "");
1132 |
1133 | for (var n = value.length - 1; n >= 0; n--) {
1134 | var cDigit = value.charAt(n);
1135 | nDigit = parseInt(cDigit, 10);
1136 | if (bEven) {
1137 | if ((nDigit *= 2) > 9) {
1138 | nDigit -= 9;
1139 | }
1140 | }
1141 | nCheck += nDigit;
1142 | bEven = !bEven;
1143 | }
1144 |
1145 | return (nCheck % 10) === 0;
1146 | },
1147 |
1148 | // http://docs.jquery.com/Plugins/Validation/Methods/accept
1149 | accept: function(value, element, param) {
1150 | param = typeof param === "string" ? param.replace(/,/g, '|') : "png|jpe?g|gif";
1151 | return this.optional(element) || value.match(new RegExp(".(" + param + ")$", "i"));
1152 | },
1153 |
1154 | // http://docs.jquery.com/Plugins/Validation/Methods/equalTo
1155 | equalTo: function(value, element, param) {
1156 | // bind to the blur event of the target in order to revalidate whenever the target field is updated
1157 | // TODO find a way to bind the event just once, avoiding the unbind-rebind overhead
1158 | var target = $(param).unbind(".validate-equalTo").bind("blur.validate-equalTo", function() {
1159 | $(element).valid();
1160 | });
1161 | return value === target.val();
1162 | }
1163 |
1164 | }
1165 |
1166 | });
1167 |
1168 | // deprecated, use $.validator.format instead
1169 | $.format = $.validator.format;
1170 |
1171 | }(jQuery));
1172 |
1173 | // ajax mode: abort
1174 | // usage: $.ajax({ mode: "abort"[, port: "uniqueport"]});
1175 | // if mode:"abort" is used, the previous request on that port (port can be undefined) is aborted via XMLHttpRequest.abort()
1176 | (function($) {
1177 | var pendingRequests = {};
1178 | // Use a prefilter if available (1.5+)
1179 | if ( $.ajaxPrefilter ) {
1180 | $.ajaxPrefilter(function(settings, _, xhr) {
1181 | var port = settings.port;
1182 | if (settings.mode === "abort") {
1183 | if ( pendingRequests[port] ) {
1184 | pendingRequests[port].abort();
1185 | }
1186 | pendingRequests[port] = xhr;
1187 | }
1188 | });
1189 | } else {
1190 | // Proxy ajax
1191 | var ajax = $.ajax;
1192 | $.ajax = function(settings) {
1193 | var mode = ( "mode" in settings ? settings : $.ajaxSettings ).mode,
1194 | port = ( "port" in settings ? settings : $.ajaxSettings ).port;
1195 | if (mode === "abort") {
1196 | if ( pendingRequests[port] ) {
1197 | pendingRequests[port].abort();
1198 | }
1199 | return (pendingRequests[port] = ajax.apply(this, arguments));
1200 | }
1201 | return ajax.apply(this, arguments);
1202 | };
1203 | }
1204 | }(jQuery));
1205 |
1206 | // provides cross-browser focusin and focusout events
1207 | // IE has native support, in other browsers, use event caputuring (neither bubbles)
1208 |
1209 | // provides delegate(type: String, delegate: Selector, handler: Callback) plugin for easier event delegation
1210 | // handler is only called when $(event.target).is(delegate), in the scope of the jquery-object for event.target
1211 | (function($) {
1212 | // only implement if not provided by jQuery core (since 1.4)
1213 | // TODO verify if jQuery 1.4's implementation is compatible with older jQuery special-event APIs
1214 | if (!jQuery.event.special.focusin && !jQuery.event.special.focusout && document.addEventListener) {
1215 | $.each({
1216 | focus: 'focusin',
1217 | blur: 'focusout'
1218 | }, function( original, fix ){
1219 | $.event.special[fix] = {
1220 | setup:function() {
1221 | this.addEventListener( original, handler, true );
1222 | },
1223 | teardown:function() {
1224 | this.removeEventListener( original, handler, true );
1225 | },
1226 | handler: function(e) {
1227 | var args = arguments;
1228 | args[0] = $.event.fix(e);
1229 | args[0].type = fix;
1230 | return $.event.handle.apply(this, args);
1231 | }
1232 | };
1233 | function handler(e) {
1234 | e = $.event.fix(e);
1235 | e.type = fix;
1236 | return $.event.handle.call(this, e);
1237 | }
1238 | });
1239 | }
1240 | $.extend($.fn, {
1241 | validateDelegate: function(delegate, type, handler) {
1242 | return this.bind(type, function(event) {
1243 | var target = $(event.target);
1244 | if (target.is(delegate)) {
1245 | return handler.apply(target, arguments);
1246 | }
1247 | });
1248 | }
1249 | });
1250 | }(jQuery));
--------------------------------------------------------------------------------