View Javadoc
1   /*
2    * MIT License
3    *
4    * Copyright (c) 2010-2024 The Waffle Project Contributors: https://github.com/Waffle/waffle/graphs/contributors
5    *
6    * Permission is hereby granted, free of charge, to any person obtaining a copy
7    * of this software and associated documentation files (the "Software"), to deal
8    * in the Software without restriction, including without limitation the rights
9    * to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
10   * copies of the Software, and to permit persons to whom the Software is
11   * furnished to do so, subject to the following conditions:
12   *
13   * The above copyright notice and this permission notice shall be included in all
14   * copies or substantial portions of the Software.
15   *
16   * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
17   * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
18   * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
19   * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
20   * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
21   * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
22   * SOFTWARE.
23   */
24  package waffle.spring;
25  
26  import java.util.ArrayList;
27  import java.util.Collection;
28  import java.util.Collections;
29  import java.util.List;
30  
31  import org.junit.jupiter.api.AfterEach;
32  import org.junit.jupiter.api.Assertions;
33  import org.junit.jupiter.api.BeforeEach;
34  import org.junit.jupiter.api.Test;
35  import org.springframework.context.ApplicationContext;
36  import org.springframework.context.support.AbstractApplicationContext;
37  import org.springframework.context.support.ClassPathXmlApplicationContext;
38  import org.springframework.security.authentication.UsernamePasswordAuthenticationToken;
39  import org.springframework.security.core.Authentication;
40  import org.springframework.security.core.GrantedAuthority;
41  
42  import waffle.mock.MockWindowsAuthProvider;
43  import waffle.mock.MockWindowsIdentity;
44  import waffle.servlet.WindowsPrincipal;
45  import waffle.windows.auth.PrincipalFormat;
46  import waffle.windows.auth.impl.WindowsAccountImpl;
47  
48  /**
49   * The Class WindowsAuthenticationProviderTest.
50   */
51  class WindowsAuthenticationProviderTest {
52  
53      /** The provider. */
54      private WindowsAuthenticationProvider provider;
55  
56      /** The ctx. */
57      private ApplicationContext ctx;
58  
59      /**
60       * Sets the up.
61       */
62      @BeforeEach
63      void setUp() {
64          final String[] configFiles = new String[] { "springTestAuthBeans.xml" };
65          this.ctx = new ClassPathXmlApplicationContext(configFiles);
66          this.provider = (WindowsAuthenticationProvider) this.ctx.getBean("waffleSpringAuthenticationProvider");
67      }
68  
69      /**
70       * Shut down.
71       */
72      @AfterEach
73      void shutDown() {
74          ((AbstractApplicationContext) this.ctx).close();
75      }
76  
77      /**
78       * Test windows authentication provider.
79       */
80      @Test
81      void testWindowsAuthenticationProvider() {
82          Assertions.assertTrue(this.provider.isAllowGuestLogin());
83          Assertions.assertTrue(this.provider.getAuthProvider() instanceof MockWindowsAuthProvider);
84          Assertions.assertEquals(PrincipalFormat.SID, this.provider.getPrincipalFormat());
85          Assertions.assertEquals(PrincipalFormat.BOTH, this.provider.getRoleFormat());
86      }
87  
88      /**
89       * Test supports.
90       */
91      @Test
92      void testSupports() {
93          Assertions.assertFalse(this.provider.supports(this.getClass()));
94          Assertions.assertTrue(this.provider.supports(UsernamePasswordAuthenticationToken.class));
95      }
96  
97      /**
98       * Test authenticate.
99       */
100     @Test
101     void testAuthenticate() {
102         final MockWindowsIdentity mockIdentity = new MockWindowsIdentity(WindowsAccountImpl.getCurrentUsername(),
103                 new ArrayList<String>());
104         final WindowsPrincipal principal = new WindowsPrincipal(mockIdentity);
105         final UsernamePasswordAuthenticationToken authentication = new UsernamePasswordAuthenticationToken(principal,
106                 "password");
107         final Authentication authenticated = this.provider.authenticate(authentication);
108         Assertions.assertNotNull(authenticated);
109         Assertions.assertTrue(authenticated.isAuthenticated());
110         final Collection<? extends GrantedAuthority> authorities = authenticated.getAuthorities();
111         Assertions.assertEquals(3, authorities.size());
112 
113         final List<String> list = new ArrayList<>();
114         for (final GrantedAuthority grantedAuthority : authorities) {
115             list.add(grantedAuthority.getAuthority());
116         }
117         Collections.sort(list);
118         Assertions.assertEquals("ROLE_EVERYONE", list.get(0));
119         Assertions.assertEquals("ROLE_USER", list.get(1));
120         Assertions.assertEquals("ROLE_USERS", list.get(2));
121         Assertions.assertTrue(authenticated.getPrincipal() instanceof WindowsPrincipal);
122     }
123 
124     /**
125      * Test authenticate with custom granted authority factory.
126      */
127     @Test
128     void testAuthenticateWithCustomGrantedAuthorityFactory() {
129         this.provider.setDefaultGrantedAuthority(null);
130         this.provider.setGrantedAuthorityFactory(new FqnGrantedAuthorityFactory(null, false));
131 
132         final MockWindowsIdentity mockIdentity = new MockWindowsIdentity(WindowsAccountImpl.getCurrentUsername(),
133                 new ArrayList<String>());
134         final WindowsPrincipal principal = new WindowsPrincipal(mockIdentity);
135         final UsernamePasswordAuthenticationToken authentication = new UsernamePasswordAuthenticationToken(principal,
136                 "password");
137 
138         final Authentication authenticated = this.provider.authenticate(authentication);
139         Assertions.assertNotNull(authenticated);
140         Assertions.assertTrue(authenticated.isAuthenticated());
141         final Collection<? extends GrantedAuthority> authorities = authenticated.getAuthorities();
142         Assertions.assertEquals(2, authorities.size());
143 
144         final List<String> list = new ArrayList<>();
145         for (final GrantedAuthority grantedAuthority : authorities) {
146             list.add(grantedAuthority.getAuthority());
147         }
148         Collections.sort(list);
149         Assertions.assertEquals("Everyone", list.get(0));
150         Assertions.assertEquals("Users", list.get(1));
151         Assertions.assertTrue(authenticated.getPrincipal() instanceof WindowsPrincipal);
152     }
153 
154     /**
155      * Test guest is disabled.
156      */
157     @Test
158     void testGuestIsDisabled() {
159         final MockWindowsIdentity mockIdentity = new MockWindowsIdentity("Guest", new ArrayList<String>());
160         this.provider.setAllowGuestLogin(false);
161         final WindowsPrincipal principal = new WindowsPrincipal(mockIdentity);
162         final UsernamePasswordAuthenticationToken authentication = new UsernamePasswordAuthenticationToken(principal,
163                 "password");
164         final Throwable exception = Assertions.assertThrows(GuestLoginDisabledAuthenticationException.class, () -> {
165             this.provider.authenticate(authentication);
166         });
167         Assertions.assertEquals("Guest", exception.getMessage());
168     }
169 
170 }