001/** 002 * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS HEADER. 003 * 004 * Copyright (c) 2007 Sun Microsystems Inc. All Rights Reserved 005 * 006 * The contents of this file are subject to the terms 007 * of the Common Development and Distribution License 008 * (the License). You may not use this file except in 009 * compliance with the License. 010 * 011 * You can obtain a copy of the License at 012 * https://opensso.dev.java.net/public/CDDLv1.0.html or 013 * opensso/legal/CDDLv1.0.txt 014 * See the License for the specific language governing 015 * permission and limitations under the License. 016 * 017 * When distributing Covered Code, include this CDDL 018 * Header Notice in each file and include the License file 019 * at opensso/legal/CDDLv1.0.txt. 020 * If applicable, add the following below the CDDL Header, 021 * with the fields enclosed by brackets [] replaced by 022 * your own identifying information: 023 * "Portions Copyrighted [year] [name of copyright owner]" 024 * 025 * $Id: TrustAuthorityClient.java,v 1.29 2009/10/13 23:19:48 mallas Exp $ 026 * 027 */ 028 029package com.sun.identity.wss.sts; 030 031import org.w3c.dom.Element; 032import org.w3c.dom.Node; 033 034import java.io.InputStream; 035import java.util.List; 036import java.util.Map; 037import java.util.HashMap; 038import java.util.List; 039import java.util.Set; 040import java.util.Iterator; 041import java.util.ArrayList; 042import java.util.logging.Level; 043import java.lang.reflect.Method; 044import java.lang.reflect.Constructor; 045import javax.servlet.ServletContext; 046import javax.xml.soap.SOAPMessage; 047import javax.xml.soap.SOAPException; 048import javax.security.auth.Subject; 049import javax.xml.namespace.QName; 050import javax.crypto.spec.SecretKeySpec; 051import java.security.Key; 052 053import com.sun.identity.shared.xml.XMLUtils; 054import com.sun.identity.shared.debug.Debug; 055import com.sun.identity.wss.security.SecurityToken; 056import com.sun.identity.wss.provider.ProviderConfig; 057import com.sun.identity.wss.provider.TrustAuthorityConfig; 058import com.sun.identity.wss.provider.STSConfig; 059import com.sun.identity.wss.security.AssertionToken; 060import com.sun.identity.wss.security.FAMSecurityToken; 061import com.sun.identity.wss.security.SAML2Token; 062import com.sun.identity.wss.security.UserNameToken; 063import com.sun.identity.wss.logging.LogUtil; 064import com.sun.identity.classloader.FAMClassLoader; 065import com.sun.identity.wss.security.SecurityMechanism; 066import com.sun.identity.wss.trust.WSTrustFactory; 067import com.sun.identity.wss.trust.WSTException; 068import com.sun.identity.wss.trust.RequestSecurityToken; 069import com.sun.identity.wss.trust.RequestSecurityTokenResponse; 070import com.sun.identity.wss.trust.RequestSecurityTokenResponseCollection; 071import com.sun.identity.common.SystemConfigurationUtil; 072import com.sun.identity.shared.jaxrpc.SOAPClient; 073import com.sun.identity.wss.security.handler.SOAPRequestHandler; 074import com.sun.identity.wss.security.SecurityException; 075import com.sun.identity.wss.trust.RequestedProofToken; 076import com.sun.identity.wss.trust.BinarySecret; 077import com.sun.identity.wss.trust.ClaimType; 078 079/** 080 * The class <code>TrustAuthorityClient</code> is a client API class that is 081 * used to obtain the Security Tokens from the trusted authority services such 082 * as Security Token Service (STS) or Liberty Discovery Service. 083 * 084 * In this current OpenSSO 8.0 release, this client API is used as STS client 085 * API class that retrieves Security Tokens from STS service by making WS-Trust 086 * request and receiving WS-Trust response. 087 * 088 * @supported.all.api 089 */ 090public class TrustAuthorityClient { 091 092 private static Debug debug = STSUtils.debug; 093 private static Class clientTokenClass; 094 private static final String KEYTYPE = "KeyType"; 095 private byte[] secretKey; 096 097 /** 098 * Creates a new instance of TrustAuthorityClient. 099 */ 100 public TrustAuthorityClient() { 101 } 102 103 /** 104 * Returns the <code>SecurityToken</code> for the web services client from 105 * a trusted authority, which is Security Token Service (STS). 106 * The web services client configuation and web service 107 * information is identified by the client provider configuration. 108 * 109 * @param pc Provider configuration of the web services client. 110 * @param credential User's credential. The user's credential could be 111 * Single Sign-On Token or a SAML Assertion or any other object. 112 * @return SecurityToken security token for the web services consumer. 113 * @exception FAMSTSException if it's unable to retrieve security token. 114 */ 115 public SecurityToken getSecurityToken( 116 ProviderConfig pc, 117 Object credential) throws FAMSTSException { 118 return getSecurityToken(pc,null,null,null,credential,null,null, null); 119 } 120 121 /** 122 * Returns the <code>SecurityToken</code> for the web services client from 123 * a trusted authority, which is Security Token Service (STS). 124 * The web services client configuation and web service 125 * information is identified by the client provider configuration. 126 * 127 * @param pc Provider configuration of the web services client. 128 * @param credential User's credential. The user's credential could be 129 * Single Sign-On Token or a SAML Assertion or any other object. 130 * @param context Web context under which this class is running. 131 * @return SecurityToken security token for the web services consumer. 132 * @exception FAMSTSException if it's unable to retrieve security token. 133 */ 134 public SecurityToken getSecurityToken( 135 ProviderConfig pc, 136 Object credential, 137 ServletContext context) throws FAMSTSException { 138 return getSecurityToken(pc,null,null,null,credential,null,null,context); 139 } 140 141 /** 142 * Returns the <code>SecurityToken</code> for the web services client from 143 * a trusted authority, which is Security Token Service (STS). 144 * 145 * @param wspEndPoint Web Service Provider end point. 146 * @param stsEndPoint Security Token Service end point. 147 * @param stsMexEndPoint Security Token Service MEX end point. 148 * @param credential User's credential. The user's credential could be 149 * Single Sign-On Token or a SAML Assertion or any other object. 150 * @param securityMech Required Security Mechanism by Web Service Client. 151 * @param context web context under which this class is running. 152 * @return SecurityToken security token for the web services consumer. 153 * @exception FAMSTSException if it's unable to retrieve security token. 154 */ 155 public SecurityToken getSecurityToken( 156 String wspEndPoint, 157 String stsEndPoint, 158 String stsMexEndPoint, 159 Object credential, 160 String securityMech, 161 ServletContext context) throws FAMSTSException { 162 return getSecurityToken(null,wspEndPoint,stsEndPoint,stsMexEndPoint, 163 credential,securityMech,null,context); 164 } 165 /** 166 * Returns the <code>SecurityToken</code> for the web services client from 167 * a trusted authority, which is Security Token Service (STS). 168 * 169 * @param wspEndPoint Web Service Provider end point. 170 * @param stsEndPoint Security Token Service end point. 171 * @param stsMexEndPoint Security Token Service MEX end point. 172 * @param credential User's credential. The user's credential could be 173 * Single Sign-On Token or a SAML Assertion or any other object. 174 * @param securityMech Required Security Mechanism by Web Service Client. 175 * @param tokenType the token type for the returned security token. 176 * @param context web context under which this class is running. 177 * @return SecurityToken security token for the web services consumer. 178 * @exception FAMSTSException if it's unable to retrieve security token. 179 */ 180 public SecurityToken getSecurityToken( 181 String wspEndPoint, 182 String stsEndPoint, 183 String stsMexEndPoint, 184 Object credential, 185 String securityMech, 186 String tokenType, 187 ServletContext context) throws FAMSTSException { 188 return getSecurityToken(null,wspEndPoint,stsEndPoint,stsMexEndPoint, 189 credential,securityMech,tokenType,context); 190 } 191 192 // Gets Security Token from Security Token Service. 193 private SecurityToken getSecurityToken( 194 ProviderConfig pc, 195 String wspEndPoint, 196 String stsEndPoint, 197 String stsMexEndPoint, 198 Object credential, 199 String securityMech, 200 String tokenType, 201 ServletContext context) throws FAMSTSException { 202 203 String keyTypeURI = STSConstants.WST13_PUBLIC_KEY; 204 String stsAgentName = null; 205 String wstVersion = STSConstants.WST_VERSION_13; 206 List claims = null; 207 if (pc != null) { 208 List securityMechanisms = pc.getSecurityMechanisms(); 209 if(securityMechanisms == null || securityMechanisms.isEmpty()) { 210 if(debug.messageEnabled()) { 211 debug.message("TrustAuthorityClient.getSecurityToken::"+ 212 "Security Mechanisms are not configured"); 213 } 214 return null; 215 } 216 securityMech = (String)securityMechanisms.get(0); 217 218 STSConfig stsConfig = null; 219 TrustAuthorityConfig taconfig = pc.getTrustAuthorityConfig(); 220 if(taconfig instanceof STSConfig) { 221 stsConfig = (STSConfig)taconfig; 222 } else { 223 throw new FAMSTSException( 224 STSUtils.bundle.getString("invalidtaconfig")); 225 } 226 stsAgentName = stsConfig.getName(); 227 stsEndPoint = stsConfig.getEndpoint(); 228 stsMexEndPoint = stsConfig.getMexEndpoint(); 229 String keyType = stsConfig.getKeyType(); 230 if(keyType.equals(STSConstants.SYMMETRIC_KEY)) { 231 keyTypeURI = STSConstants.WST13_SYMMETRIC_KEY; 232 } 233 wstVersion = stsConfig.getProtocolVersion(); 234 if(STSConstants.WST_VERSION_10.equals(wstVersion)) { 235 if(keyType.equals(STSConstants.SYMMETRIC_KEY)) { 236 keyTypeURI = STSConstants.WST10_SYMMETRIC_KEY; 237 } else { 238 keyTypeURI = STSConstants.WST10_PUBLIC_KEY; 239 } 240 } 241 String stsSecMech = (String)stsConfig.getSecurityMech().get(0); 242 if(stsSecMech.equals( 243 SecurityMechanism.WSS_NULL_KERBEROS_TOKEN_URI) || 244 stsSecMech.equals( 245 SecurityMechanism.WSS_NULL_USERNAME_TOKEN_PLAIN_URI) || 246 stsSecMech.equals( 247 SecurityMechanism.WSS_NULL_USERNAME_TOKEN_URI) || 248 stsSecMech.equals( 249 SecurityMechanism.WSS_NULL_SAML2_SV_URI) || 250 stsSecMech.equals( 251 SecurityMechanism.WSS_NULL_SAML_SV_URI) || 252 stsSecMech.equals(SecurityMechanism.STS_SECURITY_URI)) { 253 if(STSConstants.WST_VERSION_10.equals(wstVersion)) { 254 keyTypeURI = STSConstants.WST10_BEARER_KEY; 255 } else { 256 keyTypeURI = STSConstants.WST13_BEARER_KEY; 257 } 258 } 259 List requestedClaims = stsConfig.getRequestedClaims(); 260 if(requestedClaims != null && !requestedClaims.isEmpty()) { 261 claims = getClaims(requestedClaims); 262 } 263 264 wspEndPoint = pc.getWSPEndpoint(); 265 } else { 266 Map attrMap = STSUtils.getAgentAttributes(stsEndPoint, 267 "STSEndpoint", null, TrustAuthorityConfig.STS_TRUST_AUTHORITY); 268 stsAgentName = (String)attrMap.get("Name"); 269 Set versionSet = (Set)attrMap.get(STSConstants.WST_VERSION_ATTR); 270 wstVersion = (String)versionSet.iterator().next(); 271 if((wstVersion == null) || wstVersion.length() == 0) { 272 wstVersion = STSConstants.WST_VERSION_13; 273 } 274 275 Set keySet = (Set)attrMap.get(KEYTYPE); 276 String keyType = STSConstants.PUBLIC_KEY; 277 278 if(keySet != null) { 279 keyType = (String)keySet.iterator().next(); 280 } 281 282 if(keyType.equals(STSConstants.SYMMETRIC_KEY)) { 283 keyTypeURI = STSConstants.WST13_SYMMETRIC_KEY; 284 } 285 if(STSConstants.WST_VERSION_10.equals(wstVersion)) { 286 if(keyType.equals(STSConstants.SYMMETRIC_KEY)) { 287 keyTypeURI = STSConstants.WST10_SYMMETRIC_KEY; 288 } else { 289 keyTypeURI = STSConstants.WST10_PUBLIC_KEY; 290 } 291 } 292 Set values = (Set)attrMap.get("SecurityMech"); 293 if (values != null && !values.isEmpty()) { 294 String stsSecMechTemp = (String)values.iterator().next(); 295 if(stsSecMechTemp.equals( 296 SecurityMechanism.WSS_NULL_KERBEROS_TOKEN_URI) || 297 stsSecMechTemp.equals( 298 SecurityMechanism.WSS_NULL_USERNAME_TOKEN_PLAIN_URI) || 299 stsSecMechTemp.equals( 300 SecurityMechanism.WSS_NULL_USERNAME_TOKEN_URI) || 301 stsSecMechTemp.equals( 302 SecurityMechanism.WSS_NULL_SAML2_SV_URI) || 303 stsSecMechTemp.equals( 304 SecurityMechanism.WSS_NULL_SAML_SV_URI) || 305 stsSecMechTemp.equals(SecurityMechanism.STS_SECURITY_URI)) { 306 if(wstVersion.equals(STSConstants.WST_VERSION_10)) { 307 keyTypeURI = STSConstants.WST10_BEARER_KEY; 308 } else { 309 keyTypeURI = STSConstants.WST13_BEARER_KEY; 310 } 311 } 312 } 313 314 Set requestedClaims = (Set)attrMap.get("RequestedClaims"); 315 if (requestedClaims != null && !requestedClaims.isEmpty()) { 316 List list = new ArrayList(); 317 list.addAll(requestedClaims); 318 claims = getClaims(list); 319 } 320 } 321 322 if(securityMech.equals(SecurityMechanism.STS_SECURITY_URI)) { 323 String useMetro = SystemConfigurationUtil.getProperty( 324 "com.sun.identity.wss.trustclient.enablemetro", 325 "true"); 326 if(!(Boolean.valueOf(useMetro)).booleanValue()) { 327 return getSTSToken(wspEndPoint, stsEndPoint, stsMexEndPoint, 328 credential, keyTypeURI, tokenType, claims, 329 wstVersion, stsAgentName); 330 } else { 331 return getSTSToken(wspEndPoint,stsEndPoint,stsMexEndPoint, 332 credential,keyTypeURI, tokenType, wstVersion,context); 333 } 334 } else if (securityMech.equals( 335 SecurityMechanism.LIBERTY_DS_SECURITY_URI)) { 336 return getLibertyToken(pc, credential); 337 } else { 338 debug.error("TrustAuthorityClient.getSecurityToken" + 339 "Invalid security mechanism to get token from TA"); 340 return null; 341 } 342 343 } 344 345 /** 346 * Renews the issued security token that was obtained from previous 347 * interactions with Security Token Service (STS). 348 * This method applies only for the STS Tokens. 349 * 350 * In this current OpenSSO 8.0 release, this method implementation is not 351 * supported. 352 * 353 * @param securityToken security token that needs to be renewed. 354 * @param pc provider configuration of the web services client. 355 * @param credential User's credential. The user's credential could be 356 * Single Sign-On Token or a SAML Assertion or any other object. 357 * @return SecurityToken security token for the web services consumer. 358 * @exception FAMSTSException if it's unable to renew security token or 359 * if the trust authority configuration is not of STS. 360 */ 361 public SecurityToken renewIssuedToken(SecurityToken securityToken, 362 ProviderConfig pc, 363 Object credential) throws FAMSTSException { 364 //TODO To be implemented 365 throw new FAMSTSException("unsupported"); 366 367 } 368 369 /** 370 * Cancels the issued security token that was obtained from previous 371 * interactions with Security Token Service (STS). 372 * This method applies only for the STS Tokens. 373 * 374 * In this current OpenSSO 8.0 release, this method implementation is not 375 * supported. 376 * 377 * @param securityToken security token that needs to be canceled. 378 * @param pc provider configuration of the web services client. 379 * @return true if succeed in cancelling the issued token. 380 * @exception FAMSTSException if there is an exception in cancelling 381 * issued security token or if the trust authority configuration 382 * is not of STS. 383 */ 384 public boolean cancelIssuedToken(SecurityToken securityToken, 385 ProviderConfig pc) throws FAMSTSException { 386 // TODO - To be implemented 387 throw new FAMSTSException("unsupported"); 388 } 389 390 /** 391 * Returns security token obtained from Security Token Service. 392 */ 393 private SecurityToken getSTSToken(String wspEndPoint, 394 String stsEndpoint, 395 String stsMexAddress, 396 Object credential, 397 String keyType, 398 String tokenType, 399 String wstVersion, 400 ServletContext context) 401 throws FAMSTSException { 402 403 if(debug.messageEnabled()) { 404 debug.message("TrustAuthorityClient.getSTSToken:: stsEndpoint : " 405 + stsEndpoint); 406 debug.message("TrustAuthorityClient.getSTSToken:: stsMexAddress : " 407 + stsMexAddress); 408 debug.message("TrustAuthorityClient.getSTSToken:: wsp end point : " 409 + wspEndPoint); 410 debug.message("TrustAuthorityClient.getSTSToken:: keyType : " 411 + keyType); 412 } 413 414 ClassLoader oldcc = Thread.currentThread().getContextClassLoader(); 415 try { 416 ClassLoader cls = 417 FAMClassLoader.getFAMClassLoader(context,jars); 418 Thread.currentThread().setContextClassLoader(cls); 419 420 Class _handlerTrustAuthorityClient = cls.loadClass( 421 "com.sun.identity.wss.sts.TrustAuthorityClientImpl"); 422 423 Constructor taClientCon = 424 _handlerTrustAuthorityClient.getConstructor(); 425 426 Object stsClient = taClientCon.newInstance(); 427 428 Class clsa[] = new Class[7]; 429 clsa[0] = Class.forName("java.lang.String"); 430 clsa[1] = Class.forName("java.lang.String"); 431 clsa[2] = Class.forName("java.lang.String"); 432 clsa[3] = Class.forName("java.lang.Object"); 433 clsa[4] = Class.forName("java.lang.String"); 434 clsa[5] = Class.forName("java.lang.String"); 435 clsa[6] = Class.forName("java.lang.String"); 436 437 Method getSTSTokenElement = 438 stsClient.getClass().getDeclaredMethod( 439 "getSTSTokenElement", clsa); 440 441 Object args[] = new Object[7]; 442 args[0] = wspEndPoint; 443 args[1] = stsEndpoint; 444 args[2] = stsMexAddress; 445 args[3] = credential; 446 args[4] = keyType; 447 args[5] = tokenType; 448 args[6] = wstVersion; 449 Element element = (Element)getSTSTokenElement.invoke(stsClient, args); 450 String type = getTokenType(element); 451 452 if(debug.messageEnabled()) { 453 debug.message("TrustAuthorityClient.getSTSToken:: Token " 454 + "type : " + type); 455 debug.message("TrustAuthorityClient.getSTSToken:: Token" 456 + " obtained from STS : " + XMLUtils.print(element)); 457 } 458 459 if (LogUtil.isLogEnabled()) { 460 if (credential != null && (credential 461 instanceof com.iplanet.sso.SSOToken)) { 462 String[] data = {wspEndPoint,stsEndpoint,stsMexAddress, 463 credential.toString(),keyType,tokenType}; 464 LogUtil.access(Level.INFO, 465 LogUtil.SUCCESS_RETRIEVING_TOKEN_FROM_STS, 466 data, 467 credential); 468 } else { 469 String[] data2 = {wspEndPoint,stsEndpoint,stsMexAddress, 470 null,keyType,tokenType}; 471 LogUtil.access(Level.INFO, 472 LogUtil.SUCCESS_RETRIEVING_TOKEN_FROM_STS, 473 data2, 474 null); 475 } 476 } 477 478 if (type != null) { 479 if (type.equals(STSConstants.SAML20_ASSERTION_TOKEN_TYPE)) { 480 return new SAML2Token(element); 481 } else if ( 482 type.equals(STSConstants.SAML11_ASSERTION_TOKEN_TYPE)) { 483 return new AssertionToken(element); 484 } else if (type.equals(SecurityToken.WSS_FAM_SSO_TOKEN)) { 485 return new FAMSecurityToken(element); 486 } else if (type.equals(SecurityToken.WSS_USERNAME_TOKEN)) { 487 return new UserNameToken(element); 488 } else { 489 throw new FAMSTSException ( 490 STSUtils.bundle.getString("unsupportedtokentype")); 491 } 492 } else { 493 throw new FAMSTSException ( 494 STSUtils.bundle.getString("nulltokentype")); 495 } 496 497 } catch (Exception ex) { 498 debug.error("TrustAuthorityClient.getSTSToken:: Failed in" + 499 "obtainining STS Token : ", ex); 500 String[] data = {ex.getLocalizedMessage()}; 501 LogUtil.error(Level.INFO, 502 LogUtil.ERROR_RETRIEVING_TOKEN_FROM_STS, 503 data, 504 null); 505 LogUtil.error(Level.SEVERE, 506 LogUtil.ERROR_RETRIEVING_TOKEN_FROM_STS, 507 data, 508 null); 509 throw new FAMSTSException( 510 STSUtils.bundle.getString("wstrustexception")); 511 } finally { 512 Thread.currentThread().setContextClassLoader(oldcc); 513 } 514 515 } 516 517 /** 518 * Returns Liberty token by quering Liberty discovery service 519 */ 520 private SecurityToken getLibertyToken(ProviderConfig pc, 521 Object ssoToken) throws FAMSTSException { 522 523 // TODO - to be implemented 524 throw new FAMSTSException( 525 STSUtils.bundle.getString("unsupportedoperation")); 526 } 527 528 private String getTokenType (Element element) throws FAMSTSException { 529 String elemName = element.getLocalName(); 530 if (elemName == null) { 531 throw new FAMSTSException( 532 STSUtils.bundle.getString("invalidelementname")); 533 } 534 535 if (elemName.equals(STSConstants.ASSERTION_ELEMENT)) { 536 String attrValue = element.getNamespaceURI(); 537 if ((attrValue != null) && (attrValue.length() != 0) 538 && (attrValue.equals(STSConstants.SAML20_ASSERTION)) ) { 539 return STSConstants.SAML20_ASSERTION_TOKEN_TYPE; 540 } 541 attrValue = element.getNamespaceURI(); 542 if ((attrValue != null) && (attrValue.length() != 0) 543 && (attrValue.equals(STSConstants.SAML10_ASSERTION)) ) { 544 return STSConstants.SAML11_ASSERTION_TOKEN_TYPE; 545 } 546 } else if (elemName.equals(STSConstants.USER_NAME_TOKEN)) { 547 return SecurityToken.WSS_USERNAME_TOKEN; 548 549 } else if(elemName.equals("FAMToken")) { 550 return SecurityToken.WSS_FAM_SSO_TOKEN; 551 } else { 552 // TBD for other token types. 553 return "getTokenType:NOT IMPLEMENTED TOKEN TYPE"; 554 } 555 return null; 556 } 557 558 private SecurityToken getSTSToken(String wspEndPoint, 559 String stsEndPoint, 560 String stsMexEndPoint, 561 Object credential, 562 String keyType, 563 String tokenType, 564 List claims, 565 String wstVersion, 566 String stsAgentName) throws FAMSTSException { 567 try { 568 if(debug.messageEnabled()) { 569 debug.message("TrustAuthorityClient.getSTSToken: WS-Trust" + 570 " Parameters: " + "STSEndpoint = " + stsEndPoint + 571 " keyType = " + keyType + " tokenType = " + tokenType + 572 " wstVersion = " + wstVersion + 573 " STSAgentName = " + stsAgentName); 574 } 575 WSTrustFactory trustFactory = 576 WSTrustFactory.newInstance(wstVersion); 577 RequestSecurityToken rst = 578 trustFactory.createRequestSecurityToken(); 579 rst.setAppliesTo(wspEndPoint); 580 rst.setKeyType(keyType); 581 582 String requestType = STSConstants.WST10_NAMESPACE + "/Issue"; 583 if(STSConstants.WST_VERSION_13.equals(wstVersion)) { 584 requestType = STSConstants.WST13_NAMESPACE + "/Issue"; 585 } 586 rst.setRequestType(requestType); 587 if(credential != null) { 588 rst.setOnBehalfOf(getClientUserToken(credential)); 589 } 590 rst.setTokenType(tokenType); 591 if(claims != null && !claims.isEmpty()) { 592 rst.setClaimTypes(claims); 593 } 594 RequestSecurityTokenResponse rstR = 595 getTrustResponse(rst, stsEndPoint, stsAgentName, 596 wstVersion, credential); 597 RequestedProofToken reqProofToken = rstR.getRequestedProofToken(); 598 if(reqProofToken != null) { 599 Object proofToken = reqProofToken.getProofToken(); 600 if(proofToken instanceof BinarySecret) { 601 BinarySecret binarySecret = 602 (BinarySecret)reqProofToken.getProofToken(); 603 if(binarySecret != null) { 604 secretKey = binarySecret.getSecret(); 605 } 606 }//TODO handle encrypted key case. Not critical for now. 607 608 } 609 Element secTokenE = 610 (Element)rstR.getRequestedSecurityToken().getFirstChild(); 611 return parseSecurityToken(secTokenE); 612 } catch (WSTException wse) { 613 debug.error("TrustAuthorityClient.getSTSToken: Failed in " + 614 " retrieving Token from STS", wse); 615 throw new FAMSTSException(wse.getMessage()); 616 } 617 618 } 619 620 private RequestSecurityTokenResponse getTrustResponse( 621 RequestSecurityToken rst, 622 String url, 623 String stsAgentName, 624 String wstVersion, 625 Object credential) throws FAMSTSException { 626 627 SOAPMessage soapMsg = STSUtils.prepareSOAPMessage(url, wstVersion); 628 if(soapMsg == null) { 629 throw new FAMSTSException("nullElement"); 630 } 631 try { 632 Node rstE = soapMsg.getSOAPPart().importNode( 633 rst.toDOMElement(), true); 634 soapMsg.getSOAPBody().appendChild(rstE); 635 SOAPRequestHandler handler = new SOAPRequestHandler(); 636 Map config = new HashMap(); 637 config.put("providername", stsAgentName); 638 QName serviceQName = new QName(stsAgentName); 639 config.put("javax.xml.ws.wsdl.service", serviceQName); 640 handler.init(config); 641 Subject subject = new Subject(); 642 if(credential != null) { 643 subject.getPrivateCredentials().add(credential); 644 } 645 SOAPMessage secureMsg = handler.secureRequest( 646 soapMsg, subject, config); 647 SOAPMessage response = getSOAPResponse(secureMsg, url); 648 handler.validateResponse(response, config); 649 return getRequestSecurityTokenResponse(response, wstVersion); 650 } catch (SOAPException se) { 651 debug.error("TrustAuthorityClient.getTrustResponse: " + 652 " SOAP Exception", se); 653 throw new FAMSTSException(se.getMessage()); 654 } catch (WSTException we) { 655 debug.error("TrustAuthorityClient.getTrustResponse: " + 656 " WST Exception", we); 657 throw new FAMSTSException(we.getMessage()); 658 } catch (SecurityException sse) { 659 debug.error("TrustAuthorityClient.getTrustResponse: " + 660 " SecurityException", sse); 661 throw new FAMSTSException(sse.getMessage()); 662 } 663 664 } 665 666 private SOAPMessage getSOAPResponse(SOAPMessage soapMsg, String url) 667 throws FAMSTSException { 668 try { 669 SOAPClient soapClient = new SOAPClient(); 670 soapClient.setURL(url); 671 String msg = XMLUtils.print(soapMsg.getSOAPPart(),"UTF-8"); 672 InputStream is = soapClient.call(msg, null, null); 673 return STSUtils.createSOAPMessage(is); 674 } catch (SOAPException se) { 675 debug.error("TrustAutorityClient.getSOAPResponse: " + 676 " soap exception", se); 677 throw new FAMSTSException(se.getMessage()); 678 } catch (Exception ex) { 679 debug.error("TrustAutorityClient.getSOAPResponse: " + 680 " exception", ex); 681 throw new FAMSTSException(ex.getMessage()); 682 } 683 } 684 685 private RequestSecurityTokenResponse getRequestSecurityTokenResponse( 686 SOAPMessage soapMsg, String wstVersion) throws FAMSTSException { 687 try { 688 Element rstRC = (Element)soapMsg.getSOAPBody().getFirstChild(); 689 WSTrustFactory wstFactory = WSTrustFactory.newInstance(wstVersion); 690 if("RequestSecurityTokenResponse".equals(rstRC.getLocalName())) { 691 return wstFactory.createRequestSecurityTokenResponse(rstRC); 692 } 693 RequestSecurityTokenResponseCollection rstRCollection = 694 wstFactory.createRequestSecurityTokenResponseCollection(rstRC); 695 List rstResponses = 696 rstRCollection.getRequestSecurityTokenResponses(); 697 if(rstResponses.size() == 0) { 698 throw new FAMSTSException("nullElements"); 699 } 700 return (RequestSecurityTokenResponse)rstResponses.get(0); 701 702 } catch (SOAPException se) { 703 debug.error("TrustAuthorityClient.getRequestSecurityTokenResponse:" 704 + " soap exception", se); 705 throw new FAMSTSException(se.getMessage()); 706 } catch (WSTException we) { 707 debug.error("TrustAuthorityClient.getRequestSecurityTokenResponse:" 708 + " wst exception", we); 709 throw new FAMSTSException(we.getMessage()); 710 } 711 } 712 713 private SecurityToken parseSecurityToken(Element element) 714 throws FAMSTSException { 715 String type = getTokenType(element); 716 try { 717 if (type != null) { 718 if (type.equals(STSConstants.SAML20_ASSERTION_TOKEN_TYPE)) { 719 return new SAML2Token(element); 720 } else if ( 721 type.equals(STSConstants.SAML11_ASSERTION_TOKEN_TYPE)) { 722 return new AssertionToken(element); 723 } else if (type.equals(SecurityToken.WSS_FAM_SSO_TOKEN)) { 724 return new FAMSecurityToken(element); 725 } else if (type.equals(SecurityToken.WSS_USERNAME_TOKEN)) { 726 return new UserNameToken(element); 727 } else { 728 throw new FAMSTSException ( 729 STSUtils.bundle.getString("unsupportedtokentype")); 730 } 731 } else { 732 throw new FAMSTSException ( 733 STSUtils.bundle.getString("nulltokentype")); 734 } 735 } catch (Exception se) { 736 debug.error("TrustAuthorityClient.parseSecurityToken: " + 737 "Exception :", se); 738 throw new FAMSTSException(se.getMessage()); 739 } 740 741 742 } 743 744 /** 745 * Returns the secret key obtained as a proof token from STS. 746 * This is available only when the requested token type is symmetric. 747 * @return the secret key obtained from STS. 748 */ 749 public Key getSecretKey() { 750 if(secretKey == null) { 751 return null; 752 } 753 return new SecretKeySpec(secretKey, "AES"); 754 } 755 756 private Element getClientUserToken(Object credential) 757 throws FAMSTSException { 758 if (clientTokenClass == null) { 759 String className = SystemConfigurationUtil.getProperty( 760 STSConstants.STS_CLIENT_USER_TOKEN_PLUGIN, 761 "com.sun.identity.wss.sts.STSClientUserToken"); 762 try { 763 clientTokenClass = 764 (Thread.currentThread().getContextClassLoader()). 765 loadClass(className); 766 } catch (Exception ex) { 767 debug.error("TrustAuthorityClientImpl.getClientUserToken:" 768 + "Failed in obtaining class", ex); 769 throw new FAMSTSException( 770 STSUtils.bundle.getString("initializationFailed")); 771 } 772 } 773 774 try { 775 ClientUserToken userToken = 776 (ClientUserToken) clientTokenClass.newInstance(); 777 userToken.init(credential); 778 if(debug.messageEnabled()) { 779 debug.message("TrustAuthorityClientImpl:getClientUserToken: " + 780 "Client User Token : " + userToken); 781 } 782 return (Element)userToken.getTokenValue(); 783 784 } catch (Exception ex) { 785 debug.error("TrustAuthorityClientImpl.getClientUserToken: " + 786 "Failed in initialization", ex); 787 throw new FAMSTSException( 788 STSUtils.bundle.getString("usertokeninitfailed")); 789 } 790 } 791 792 private List<ClaimType> getClaims(List<String> requestedClaims) { 793 List<ClaimType> claimTypes = new ArrayList<ClaimType>(); 794 Iterator<String> iter = requestedClaims.iterator(); 795 while(iter.hasNext()) { 796 String claimName = iter.next(); 797 ClaimType claimType = new ClaimType(ClaimType.IDENTITY_NS); 798 claimType.setName(claimName); 799 claimTypes.add(claimType); 800 } 801 return claimTypes; 802 } 803 804 /** 805 * The list of jar files to be loaded by FAMClassLoader. 806 */ 807 public static String[] jars = new String[]{ 808 "webservices-api.jar", 809 "webservices-rt.jar", 810 "webservices-tools.jar", 811 "webservices-extra-api.jar", 812 "webservices-extra.jar", 813 "openssoclientsdk.jar", 814 "openssowssproviders.jar", 815 "xalan.jar", 816 "xercesImpl.jar" 817 }; 818}