差分

このページの2つのバージョン間の差分を表示します。

この比較画面へのリンク

両方とも前のリビジョン前のリビジョン
次のリビジョン
前のリビジョン
study:java:sharepointonline:implement3 [2021/07/19 08:55] – [Mainコード] bananastudy:java:sharepointonline:implement3 [2025/02/03 09:17] (現在) banana
行 1: 行 1:
 ====== Binary token取得の実装 ====== ====== Binary token取得の実装 ======
 本稿では、[[study:java:sharepointonline:implement1|SAML Security token 取得の実装]]に続き、Binary token取得処理の実装について、紹介します。\\ 本稿では、[[study:java:sharepointonline:implement1|SAML Security token 取得の実装]]に続き、Binary token取得処理の実装について、紹介します。\\
 +動作環境については、上記ページに紹介してありますので、割愛します。
  
-===== Mainコード =====+{{keywords>Get Binary token Sharepoint online}} 
 + 
 +====== Mainコード ======
 実装コードのメインとなる部分を以下に示します。 実装コードのメインとなる部分を以下に示します。
 <code java> <code java>
行 21: 行 24:
  .post(new URI(CUSTOM_STS_ENDPOINT))  .post(new URI(CUSTOM_STS_ENDPOINT))
  .header("content-type", "application/soap+xml; charset=utf-8")  .header("content-type", "application/soap+xml; charset=utf-8")
- .body(buildBinaryTokenRequestEnvelope(samlAssertion));+ .body(buildBinaryTokenRequestEnvelope(samlAssertion));  ★ポイント1
  
     RestTemplate _restTemplate = new RestTemplate();     RestTemplate _restTemplate = new RestTemplate();
-    _restTemplate.setRequestFactory(buildProxyClientHttpRequestFactory());+    _restTemplate.setRequestFactory(buildProxyClientHttpRequestFactory());   ★ポイント2
  
     ResponseEntity<String> _responseEntity = _restTemplate.exchange(_requestEntity, String.class);     ResponseEntity<String> _responseEntity = _restTemplate.exchange(_requestEntity, String.class);
行 33: 行 36:
  
     Document _definitionDocument = (Document) _result.getNode();     Document _definitionDocument = (Document) _result.getNode();
-    final String XPATH_EXPRESSION = "//wsse:BinarySecurityToken";+    final String XPATH_EXPRESSION = "//wsse:BinarySecurityToken";    ★ポイント3
     _token = getXPathExpression(XPATH_EXPRESSION).evaluateAsString(_definitionDocument);     _token = getXPathExpression(XPATH_EXPRESSION).evaluateAsString(_definitionDocument);
  
行 47: 行 50:
 }//receiveBinarySecurityToken }//receiveBinarySecurityToken
  
 +//build Binary token request envelope
 private String buildBinaryTokenRequestEnvelope(String samlAssertion) { private String buildBinaryTokenRequestEnvelope(String samlAssertion) {
   //SAML Assertion mapping   //SAML Assertion mapping
   Map<String, String> _mapRequest = new HashMap<String, String>();   Map<String, String> _mapRequest = new HashMap<String, String>();
   _mapRequest.put("samltoken", samlAssertion);   _mapRequest.put("samltoken", samlAssertion);
 +  _mapRequest.put("siteurl", RSC.getString("site.url"));
   //replace placeHolder   //replace placeHolder
   StringSubstitutor _substitutor = new StringSubstitutor(_mapRequest, "%(", ")");   StringSubstitutor _substitutor = new StringSubstitutor(_mapRequest, "%(", ")");
行 58: 行 63:
 }//buildBinaryTokenRequestEnvelope }//buildBinaryTokenRequestEnvelope
  
 +//build HttpComponentsClientHttpRequestFactory for PROXY connection
 private HttpComponentsClientHttpRequestFactory buildProxyClientHttpRequestFactory() throws Exception { private HttpComponentsClientHttpRequestFactory buildProxyClientHttpRequestFactory() throws Exception {
   return ProxyClientHttpRequestFactoryBuilder.build());   return ProxyClientHttpRequestFactoryBuilder.build());
 } }
  
 +//create XPathExpression
 private XPathExpression getXPathExpression(String expression) { private XPathExpression getXPathExpression(String expression) {
   XPathExpression _xPathExpressioin = XPathExpressionFactory.createXPathExpression(expression, namespacePrefixes);   XPathExpression _xPathExpressioin = XPathExpressionFactory.createXPathExpression(expression, namespacePrefixes);
行 68: 行 75:
  
 </code> </code>
 +
 +★ポイント1\\
 +SOAPリクエストメッセージを作成する部分です。\\
 +%(samltoken)部分をSAML security token(SAML Assertion)に置換します。\\
 +%(siteurl)部分は、SharepointサイトURLに置換します。\\
 +appliction.propertiesの一部分を以下に示します。
 +<code>
 +site.url=SharepointサイトURL
 +soap.binary.token.request=<s:Envelope xmlns:s="http://www.w3.org/2003/05/soap-envelope" xmlns:a="http://www.w3.org/2005/08/addressing" xmlns:u="http://docs.oasis-open.org/wss/2004/01/oasis-200401-wss-wssecurity-utility-1.0.xsd"><s:Header><a:Action s:mustUnderstand="1">http://schemas.xmlsoap.org/ws/2005/02/trust/RST/Issue</a:Action><a:ReplyTo><a:Address>http://www.w3.org/2005/08/addressing/anonymous</a:Address></a:ReplyTo><o:Security s:mustUnderstand="1" xmlns:o="http://docs.oasis-open.org/wss/2004/01/oasis-200401-wss-wssecurity-secext-1.0.xsd">%(samltoken)</o:Security></s:Header><s:Body><t:RequestSecurityToken xmlns:t="http://schemas.xmlsoap.org/ws/2005/02/trust"><wsp:AppliesTo xmlns:wsp="http://schemas.xmlsoap.org/ws/2004/09/policy"><a:EndpointReference><a:Address>%(siteurl)</a:Address></a:EndpointReference></wsp:AppliesTo><t:KeyType>http://schemas.xmlsoap.org/ws/2005/05/identity/NoProofKey</t:KeyType><t:RequestType>http://schemas.xmlsoap.org/ws/2005/02/trust/Issue</t:RequestType><t:TokenType>urn:oasis:names:tc:SAML:1.0:assertion</t:TokenType></t:RequestSecurityToken></s:Body></s:Envelope>
 +</code>
 +
 +★ポイント2\\
 +ここからの処理は外部サイトにアクセスするので、Proxy環境にある場合はProxy設定と、Https通信設定が必要です。\\
 +詳細は次節を参照してください。
 +
 +★ポイント3\\
 +レスポンスXMLから、XPathを利用してBinary tokenを抽出します。\\
 +wsse:BinarySecurityToken項目がnamespaceのものなので、XPathExpression生成時namespaceを渡す必要があります。
 +
 +====== ProxyClientHttpRequestFactoryBuilderクラス ======
 +ProxyClientHttpRequestFactoryBuilderクラスのコードを以下に示します。
 +<code java>
 +public class ProxyClientHttpRequestFactoryBuilder {
 +  private static final String PROXY_HOST = "proxy.sample.com";
 +  private static final int PROXY_PORT = 8080;
 +
 +  public static HttpComponentsClientHttpRequestFactory build() throws Exception {
 +    HttpHost _proxy = new HttpHost(PROXY_HOST, PROXY_PORT );
 +
 +    final int TIMEOUT = 5;
 +
 +    //request configuration
 +    RequestConfig _reqConfig = RequestConfig.custom()
 + .setConnectTimeout(TIMEOUT * 1000)
 +        .setSocketTimeout(TIMEOUT * 1000)
 + .setConnectionRequestTimeout(TIMEOUT * 1000)
 + .setProxy(_proxy)   ★ポイント1
 + .build();
 +
 +    BouncyCastleFipsProviderHelper.setUpProvider();   ★ポイント2
 +
 +    //setup SSLContext(BouncyCastle provider)
 +    SSLContext _sslContext = SSLContexts.custom()
 + .setProvider(new BouncyCastleJsseProvider(true))   ★ポイント3
 + .build();
 +
 +    SSLConnectionSocketFactory _sslSocketFactory = new SSLConnectionSocketFactory(_sslContext,
 + new String[]{"TLSv1.2"},
 + new String[]{"SSL_ECDHE_RSA_WITH_AES_128_CBC_SHA", "TLS_ECDHE_RSA_WITH_AES_128_GCM_SHA256",    ★ポイント4
 + "TLS_DHE_RSA_WITH_AES_128_GCM_SHA256"}, //key length=128制限があるため
 + new DefaultHostnameVerifier());
 +
 +    Registry<ConnectionSocketFactory> _socketFactoryRegistry = RegistryBuilder.<ConnectionSocketFactory>create()
 + .register("http", PlainConnectionSocketFactory.getSocketFactory())
 + .register("https", _sslSocketFactory)
 + .build();
 +
 +    PoolingHttpClientConnectionManager _cm = new PoolingHttpClientConnectionManager(_socketFactoryRegistry);
 + _cm.setMaxTotal(200);
 + _cm.setDefaultMaxPerRoute(100);
 +
 +    //create HttpClient
 +    HttpClient _client = HttpClientBuilder.create()
 + .setUserAgent("NONISV|Nskcom|Sharepoint-demo/1.0") //NONISV|CompanyName|AppName/Version
 + .setConnectionManager(_cm)
 + .disableRedirectHandling()
 + .setDefaultRequestConfig(_reqConfig)
 + .build();
 +
 +    HttpComponentsClientHttpRequestFactory _factory = new HttpComponentsClientHttpRequestFactory(_client);
 +
 +    return _factory;
 +  }//build
 +
 +}
 +</code>
 +
 +★ポイント1
 +HTTP Proxyを設定する部分です。ID/Password認証は必要ありません。
 +
 +★ポイント2
 +Bouncy CastleプロバイダーをSecurity Providerとして登録する部分です。\\
 +詳細については、[[study:java:sharepointonline:implement2|3rd Party Security Providerの導入について]]を参照してください。
 +
 +★ポイント3
 +FIPSモードとしてBouncy castleプロバイダーを設定します。
 +
 +★ポイント4
 +Cipher Suiteを指定します。 Java 7環境では、key size制限(128)があるため、Sharepointサイト要求のCipher Suiteから128lengthのみを選択します。\\
 +この指定がないと、「java.security.InvalidKeyException: Illegal key size」エラーが発生します。
 +
 +~~DISCUSSION~~

QR Code
QR Code study:java:sharepointonline:implement3 (generated for current page)