Commit
This commit does not belong to any branch on this repository, and may belong to a fork outside of the repository.
- Loading branch information
Showing
16 changed files
with
732 additions
and
36 deletions.
There are no files selected for viewing
180 changes: 180 additions & 0 deletions
180
...c/test/java/org/springframework/security/kerberos/client/TestMultiTierAuthentication.java
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,180 @@ | ||
/* | ||
* Copyright 2009-2015 the original author or authors. | ||
* | ||
* Licensed under the Apache License, Version 2.0 (the "License"); | ||
* you may not use this file except in compliance with the License. | ||
* You may obtain a copy of the License at | ||
* | ||
* http://www.apache.org/licenses/LICENSE-2.0 | ||
* | ||
* Unless required by applicable law or agreed to in writing, software | ||
* distributed under the License is distributed on an "AS IS" BASIS, | ||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. | ||
* See the License for the specific language governing permissions and | ||
* limitations under the License. | ||
*/ | ||
package org.springframework.security.kerberos.client; | ||
|
||
import org.junit.Test; | ||
import org.springframework.core.io.FileSystemResource; | ||
import org.springframework.security.authentication.UsernamePasswordAuthenticationToken; | ||
import org.springframework.security.core.Authentication; | ||
import org.springframework.security.core.authority.AuthorityUtils; | ||
import org.springframework.security.core.userdetails.User; | ||
import org.springframework.security.core.userdetails.UserDetails; | ||
import org.springframework.security.core.userdetails.UserDetailsService; | ||
import org.springframework.security.core.userdetails.UsernameNotFoundException; | ||
import org.springframework.security.kerberos.authentication.KerberosAuthenticationProvider; | ||
import org.springframework.security.kerberos.authentication.KerberosMultiTier; | ||
import org.springframework.security.kerberos.authentication.KerberosServiceAuthenticationProvider; | ||
import org.springframework.security.kerberos.authentication.KerberosServiceRequestToken; | ||
import org.springframework.security.kerberos.authentication.sun.SunJaasKerberosClient; | ||
import org.springframework.security.kerberos.authentication.sun.SunJaasKerberosTicketValidator; | ||
import org.springframework.security.kerberos.test.KerberosSecurityTestcase; | ||
import org.springframework.security.kerberos.test.MiniKdc; | ||
|
||
import java.io.File; | ||
|
||
import static org.junit.Assert.*; | ||
|
||
/** | ||
* @author Bogdan Mustiata | ||
*/ | ||
public class TestMultiTierAuthentication extends KerberosSecurityTestcase { | ||
@Test | ||
public void testServer() throws Exception { | ||
MiniKdc kdc = getKdc(); | ||
File workDir = getWorkDir(); | ||
|
||
File webTierKeytabFile = new File(workDir, "webtier.keytab"); | ||
kdc.createKeyabFile(webTierKeytabFile, "HTTP/webtier@EXAMPLE.COM", "secret"); | ||
|
||
File serviceTierKeytabFile = new File(workDir, "servicetier.keytab"); | ||
kdc.createKeyabFile(serviceTierKeytabFile, "HTTP/servicetier@EXAMPLE.COM", "secret"); | ||
|
||
// | ||
// User logs in as user1/secret | ||
// | ||
KerberosAuthenticationProvider kerberosAuthProvider = | ||
createUserPassAuthenticator(/* debug: */ true); | ||
|
||
Authentication authentication = kerberosAuthProvider | ||
.authenticate(new UsernamePasswordAuthenticationToken("user1", "secret")); | ||
|
||
assertEquals("user1@EXAMPLE.COM", authentication.getName()); | ||
|
||
// | ||
// User creates a ticket for the HTTP/webtier@EXAMPLE.COM, using | ||
// and then calls the service, using the tokenData | ||
// | ||
authentication = KerberosMultiTier.authenticateService( | ||
authentication, "user1", 3600, "HTTP/webtier@EXAMPLE.COM"); | ||
|
||
byte[] tokenData = KerberosMultiTier | ||
.getTokenForService(authentication, "HTTP/webtier@EXAMPLE.COM"); | ||
|
||
assertNotNull(tokenData); | ||
assertTrue(tokenData.length != 0); | ||
|
||
// | ||
// The service HTTP/webtier@EXAMPLE.COM authenticates via tokens. | ||
// | ||
KerberosServiceAuthenticationProvider webTierAuthenticatorProvider = | ||
createServiceAuthenticator( | ||
true, | ||
"HTTP/webtier@EXAMPLE.COM", | ||
"EXAMPLE.COM", | ||
webTierKeytabFile.getCanonicalPath() | ||
); | ||
|
||
|
||
// | ||
// The service HTTP/webtier@EXAMPLE.COM authenticates the user1@EXAMPLE.COM | ||
// using the previously stored token, then authenticates itself further as | ||
// user1@EXAMPLE.COM to the HTTP/servicetier@EXAMPLE.COM. | ||
// | ||
Authentication webTierAuthentication = webTierAuthenticatorProvider | ||
.authenticate(new KerberosServiceRequestToken(tokenData)); | ||
|
||
assertEquals("user1@EXAMPLE.COM", webTierAuthentication.getName()); | ||
|
||
webTierAuthentication = KerberosMultiTier.authenticateService( | ||
webTierAuthentication, "user1@EXAMPLE.COM", 3600, "HTTP/servicetier@EXAMPLE.COM"); | ||
|
||
byte[] workplaceTokenData = KerberosMultiTier.getTokenForService( | ||
webTierAuthentication, "HTTP/servicetier@EXAMPLE.COM"); | ||
|
||
// | ||
// The service HTTP/icr@EXAMPLE.COM authenticates via tokens. | ||
// | ||
webTierAuthenticatorProvider = | ||
createServiceAuthenticator( | ||
true, | ||
"HTTP/servicetier@EXAMPLE.COM", | ||
"EXAMPLE.COM", | ||
serviceTierKeytabFile.getCanonicalPath() | ||
); | ||
|
||
// | ||
// The service HTTP/servicetier@EXAMPLE.COM authenticates via the previously saved | ||
// token, received from the HTTP/webtier@EXAMPLE.COM on behalf of user1@EXAMPLE.COM | ||
// | ||
Authentication serviceTierAuthentication = webTierAuthenticatorProvider | ||
.authenticate(new KerberosServiceRequestToken(workplaceTokenData)); | ||
|
||
assertEquals("user1@EXAMPLE.COM", serviceTierAuthentication.getName()); | ||
} | ||
|
||
/** | ||
* Create a username/password authenticator. | ||
* @return | ||
*/ | ||
private KerberosAuthenticationProvider createUserPassAuthenticator(boolean debug) { | ||
KerberosAuthenticationProvider kerberosAuthenticationProvider = | ||
new KerberosAuthenticationProvider(); | ||
|
||
SunJaasKerberosClient sunJaasKerberosClient = new SunJaasKerberosClient(); | ||
|
||
sunJaasKerberosClient.setDebug(debug); | ||
sunJaasKerberosClient.setMultiTier(true); | ||
|
||
kerberosAuthenticationProvider.setKerberosClient(sunJaasKerberosClient); | ||
kerberosAuthenticationProvider.setUserDetailsService(userDetailsService()); | ||
|
||
return kerberosAuthenticationProvider; | ||
} | ||
|
||
private KerberosServiceAuthenticationProvider createServiceAuthenticator(boolean debug, | ||
String serviceName, | ||
String realmName, | ||
String keytabFileLocation) throws Exception { | ||
KerberosServiceAuthenticationProvider kerberosServiceAuthenticationProvider = | ||
new KerberosServiceAuthenticationProvider(); | ||
|
||
SunJaasKerberosTicketValidator ticketValidator = new SunJaasKerberosTicketValidator(); | ||
ticketValidator.setDebug(debug); | ||
ticketValidator.setServicePrincipal(serviceName); | ||
ticketValidator.setRealmName(realmName); | ||
ticketValidator.setKeyTabLocation(new FileSystemResource(keytabFileLocation)); | ||
ticketValidator.setMultiTier(true); | ||
|
||
ticketValidator.afterPropertiesSet(); | ||
|
||
kerberosServiceAuthenticationProvider.setTicketValidator(ticketValidator); | ||
kerberosServiceAuthenticationProvider.setUserDetailsService(userDetailsService()); | ||
|
||
return kerberosServiceAuthenticationProvider; | ||
} | ||
|
||
private UserDetailsService userDetailsService() { | ||
return new UserDetailsService() { | ||
@Override | ||
public UserDetails loadUserByUsername(String username) throws UsernameNotFoundException { | ||
return new User(username, "notUsed", true, true, true, true, | ||
AuthorityUtils.createAuthorityList("ROLE_USER")); | ||
|
||
} | ||
}; | ||
} | ||
|
||
} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
|
@@ -18,6 +18,7 @@ | |
[libdefaults] | ||
default_realm = {0} | ||
udp_preference_limit = 1 | ||
forwardable = true | ||
|
||
[realms] | ||
{0} = '{' | ||
|
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
62 changes: 62 additions & 0 deletions
62
...src/main/java/org/springframework/security/kerberos/authentication/JaasSubjectHolder.java
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,62 @@ | ||
/* | ||
* Copyright 2009-2015 the original author or authors. | ||
* | ||
* Licensed under the Apache License, Version 2.0 (the "License"); | ||
* you may not use this file except in compliance with the License. | ||
* You may obtain a copy of the License at | ||
* | ||
* http://www.apache.org/licenses/LICENSE-2.0 | ||
* | ||
* Unless required by applicable law or agreed to in writing, software | ||
* distributed under the License is distributed on an "AS IS" BASIS, | ||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. | ||
* See the License for the specific language governing permissions and | ||
* limitations under the License. | ||
*/ | ||
package org.springframework.security.kerberos.authentication; | ||
|
||
import org.springframework.security.kerberos.authentication.sun.SunJaasKerberosClient; | ||
|
||
import javax.security.auth.Subject; | ||
import java.util.HashMap; | ||
import java.util.Map; | ||
|
||
/** | ||
* <p>Holds the Subject of the currently authenticated user, since this | ||
* Jaas object also has the credentials, and permits creating new | ||
* credentials against other Kerberos services.</p> | ||
* @author Bogdan Mustiata | ||
* @see SunJaasKerberosClient | ||
* @see org.springframework.security.kerberos.authentication.KerberosAuthenticationProvider | ||
*/ | ||
public class JaasSubjectHolder { | ||
private Subject jaasSubject; | ||
private String username; | ||
|
||
private Map<String, byte[]> savedTokens = new HashMap<String, byte[]>(); | ||
|
||
public JaasSubjectHolder(Subject jaasSubject) { | ||
this.jaasSubject = jaasSubject; | ||
} | ||
|
||
public JaasSubjectHolder(Subject jaasSubject, String username) { | ||
this.jaasSubject = jaasSubject; | ||
this.username = username; | ||
} | ||
|
||
public String getUsername() { | ||
return username; | ||
} | ||
|
||
public Subject getJaasSubject() { | ||
return jaasSubject; | ||
} | ||
|
||
public void addToken(String targetService, byte[] outToken) { | ||
this.savedTokens.put(targetService, outToken); | ||
} | ||
|
||
public byte[] getToken(String principalName) { | ||
return savedTokens.get(principalName); | ||
} | ||
} |
6 changes: 6 additions & 0 deletions
6
...ain/java/org/springframework/security/kerberos/authentication/KerberosAuthentication.java
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,6 @@ | ||
package org.springframework.security.kerberos.authentication; | ||
|
||
public interface KerberosAuthentication { | ||
|
||
JaasSubjectHolder getJaasSubjectHolder(); | ||
} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Oops, something went wrong.