fa95894ef7b15eac2b5e0e1b294be6dbfd973e11
[java-idp.git] / tests / edu / internet2 / middleware / shibboleth / runner / MockHTTPBindingProvider.java
1 /*
2  * External class so it can be configured by String name to SAML.
3  * 
4  * Look for:
5  *     samlConfig = SAMLConfig.instance();
6  *     samlConfig.setDefaultBindingProvider(SAMLBinding.SOAP,"edu.internet2.middleware.shibboleth.runner.MockHTTPBindingProvider" );
7  * in ShibbolethRunner constructor.
8  */
9
10 /*
11  * Copyright [2005] [University Corporation for Advanced Internet Development, Inc.]
12  *
13  * Licensed under the Apache License, Version 2.0 (the "License");
14  * you may not use this file except in compliance with the License.
15  * You may obtain a copy of the License at
16  *
17  * http://www.apache.org/licenses/LICENSE-2.0
18  *
19  * Unless required by applicable law or agreed to in writing, software
20  * distributed under the License is distributed on an "AS IS" BASIS,
21  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
22  * See the License for the specific language governing permissions and
23  * limitations under the License.
24  */
25
26 package edu.internet2.middleware.shibboleth.runner;
27
28 import java.io.BufferedReader;
29 import java.io.StringReader;
30 import java.net.MalformedURLException;
31
32 import org.apache.xml.security.c14n.CanonicalizationException;
33 import org.apache.xml.security.c14n.Canonicalizer;
34 import org.apache.xml.security.c14n.InvalidCanonicalizerException;
35 import org.opensaml.BindingException;
36 import org.opensaml.SAMLBinding;
37 import org.opensaml.SAMLConfig;
38 import org.opensaml.SAMLException;
39 import org.opensaml.SAMLRequest;
40 import org.opensaml.SAMLResponse;
41 import org.opensaml.XML;
42 import org.opensaml.provider.SOAPHTTPBindingProvider;
43 import org.w3c.dom.Element;
44 import org.xml.sax.InputSource;
45 import org.xml.sax.SAXException;
46
47 import edu.internet2.middleware.shibboleth.runner.ShibbolethRunner.IdpTestContext;
48
49
50 /**
51  *  This is a replacement for SOAPHTTPBindingProvider in OpenSAML. While that
52  *  module builds a URL and URLConnection to send a request to a Web Server
53  *  hosting the IdP, this code generates a direct call to the AA or Artifact
54  *  Resolver through the IdP Servlet.
55  *  
56  *  <p>The ShibbolethRunner constructor sets this class name as the SAML 
57  *  default BindingProvider.</p>
58  */
59 public class MockHTTPBindingProvider 
60     extends SOAPHTTPBindingProvider {
61     
62     
63     /** OpenSAML will construct this object. */
64     public MockHTTPBindingProvider(String binding, Element e) throws SAMLException {
65         super(binding, e);
66     }
67
68     /**
69      * Based on the Http version of this code, this method replaces the URL and
70      * URLConnection with operations on the Mock HttpRequest.
71      */
72     public SAMLResponse send(String endpoint, SAMLRequest request, Object callCtx)
73         throws SAMLException
74     {
75         try {
76             Element envelope = sendRequest(request, callCtx);
77             
78             IdpTestContext idp = ShibbolethRunner.idp;
79             
80             /*
81              * Prepare the Idp Mockrunner blocks for the Query
82              */
83             idp.request.setLocalPort(8443);
84             idp.request.setRequestURI(endpoint);
85             idp.request.setRequestURL(endpoint);
86             if (endpoint.endsWith("/AA")) {
87                 idp.request.setServletPath("/shibboleth.idp/AA");
88             } else {
89                 idp.request.setServletPath("/shibboleth.idp/Artifact");
90             }
91
92             idp.request.setContentType("text/xml; charset=UTF-8");
93             idp.request.setHeader("SOAPAction","http://www.oasis-open.org/committees/security");
94         
95              
96             
97             Canonicalizer c = Canonicalizer.getInstance(Canonicalizer.ALGO_ID_C14N_OMIT_COMMENTS);
98             byte[] bs = c.canonicalizeSubtree(envelope);
99             idp.request.setBodyContent(bs);
100
101             idp.testModule.doPost();
102             
103             String content_type=idp.response.getContentType();
104             
105             if (content_type == null || !content_type.startsWith("text/xml")) {
106                 String outputStreamContent = idp.response.getOutputStreamContent();
107                 StringReader outputreader = new StringReader(outputStreamContent);
108                 BufferedReader reader=new BufferedReader(outputreader);
109                 throw new BindingException(
110                     "MockHTTPBindingProvider.send() detected an invalid content type ("
111                         + (content_type!=null ? content_type : "none")
112                         + ") in the response.");
113             }
114             
115             envelope=XML.parserPool.parse(
116                     new InputSource(new StringReader(idp.response.getOutputStreamContent())),
117                     (request.getMinorVersion()>0) ? XML.parserPool.getSchemaSAML11() : XML.parserPool.getSchemaSAML10()
118                     ).getDocumentElement();
119             
120             SAMLResponse ret = recvResponse(envelope, callCtx);
121            
122             if (!ret.getInResponseTo().equals(request.getId())) {
123                 throw new BindingException("MockHTTPBindingProvider.send() unable to match SAML InResponseTo value to request");
124             }
125             return ret;
126         }
127         catch (MalformedURLException ex) {
128             throw new SAMLException("SAMLSOAPBinding.send() detected a malformed URL in the binding provided", ex);
129         }
130         catch (SAXException ex) {
131             throw new SAMLException("SAMLSOAPBinding.send() caught an XML exception while parsing the response", ex);
132         }
133         catch (InvalidCanonicalizerException ex) {
134             throw new SAMLException("SAMLSOAPBinding.send() caught a C14N exception while serializing the request", ex);
135         }
136         catch (CanonicalizationException ex) {
137             throw new SAMLException("SAMLSOAPBinding.send() caught a C14N exception while serializing the request", ex);
138         }
139         catch (java.io.IOException ex) {
140             throw new SAMLException("SAMLSOAPBinding.send() caught an I/O exception", ex);
141         }
142         finally {
143         }
144     }
145 }
146