Tue, 06 Mar 2012 16:09:35 -0800
7150322: Stop using drop source bundles in jaxws
Reviewed-by: darcy, ohrstrom
1 /*
2 * Copyright (c) 1997, 2010, Oracle and/or its affiliates. All rights reserved.
3 * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
4 *
5 * This code is free software; you can redistribute it and/or modify it
6 * under the terms of the GNU General Public License version 2 only, as
7 * published by the Free Software Foundation. Oracle designates this
8 * particular file as subject to the "Classpath" exception as provided
9 * by Oracle in the LICENSE file that accompanied this code.
10 *
11 * This code is distributed in the hope that it will be useful, but WITHOUT
12 * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
13 * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
14 * version 2 for more details (a copy is included in the LICENSE file that
15 * accompanied this code).
16 *
17 * You should have received a copy of the GNU General Public License version
18 * 2 along with this work; if not, write to the Free Software Foundation,
19 * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
20 *
21 * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
22 * or visit www.oracle.com if you need additional information or have any
23 * questions.
24 */
26 package com.sun.xml.internal.ws.wsdl;
28 import com.sun.istack.internal.NotNull;
29 import com.sun.istack.internal.Nullable;
30 import com.sun.xml.internal.ws.api.WSBinding;
31 import com.sun.xml.internal.ws.api.model.SEIModel;
32 import com.sun.xml.internal.ws.api.model.wsdl.WSDLPort;
33 import com.sun.xml.internal.ws.api.model.wsdl.WSDLBoundOperation;
34 import com.sun.xml.internal.ws.api.addressing.AddressingVersion;
35 import com.sun.xml.internal.ws.api.message.HeaderList;
36 import com.sun.xml.internal.ws.api.message.Message;
37 import com.sun.xml.internal.ws.api.message.Messages;
38 import com.sun.xml.internal.ws.api.message.Packet;
39 import com.sun.xml.internal.ws.model.AbstractSEIModelImpl;
40 import com.sun.xml.internal.ws.model.JavaMethodImpl;
41 import static com.sun.xml.internal.ws.wsdl.PayloadQNameBasedOperationFinder.*;
42 import com.sun.xml.internal.ws.resources.AddressingMessages;
44 import javax.xml.namespace.QName;
45 import java.util.HashMap;
46 import java.util.Map;
47 import java.util.logging.Logger;
49 /**
50 * An {@link WSDLOperationFinder} implementation that uses
51 * WS-Addressing Action Message Addressing Property, <code>wsa:Action</code> and SOAP Payload QName,
52 * as the key for dispatching.
53 * <p/>
54 * This should be used only when AddressingFeature is enabled.
55 * A map of all {@link ActionBasedOperationSignature}s in the port and the corresponding and the WSDL Operation QNames
56 * is maintained.
57 * <p/>
58 *
59 * @author Rama Pulavarthi
60 */
61 final class ActionBasedOperationFinder extends WSDLOperationFinder {
63 private static final Logger LOGGER = Logger.getLogger(ActionBasedOperationFinder.class.getName());
64 private final Map<ActionBasedOperationSignature, QName> uniqueOpSignatureMap;
65 private final Map<String, QName> actionMap;
67 private final @NotNull AddressingVersion av;
69 public ActionBasedOperationFinder(WSDLPort wsdlModel, WSBinding binding, @Nullable SEIModel seiModel) {
70 super(wsdlModel, binding, seiModel);
72 assert binding.getAddressingVersion() != null; // this dispatcher can be only used when addressing is on.
73 av = binding.getAddressingVersion();
74 uniqueOpSignatureMap = new HashMap<ActionBasedOperationSignature, QName>();
75 actionMap = new HashMap<String,QName>();
77 if (seiModel != null) {
78 for (JavaMethodImpl m : ((AbstractSEIModelImpl) seiModel).getJavaMethods()) {
79 if(m.getMEP().isAsync)
80 continue;
82 String action = m.getInputAction();
83 QName payloadName = m.getRequestPayloadName();
84 if (payloadName == null)
85 payloadName = EMPTY_PAYLOAD;
86 //first look at annotations and then in wsdlmodel
87 if (action == null || action.equals("")) {
88 if (m.getOperation() != null) action = m.getOperation().getOperation().getInput().getAction();
89 // action = m.getInputAction();
90 }
91 if (action != null) {
92 ActionBasedOperationSignature opSignature = new ActionBasedOperationSignature(action, payloadName);
93 if(uniqueOpSignatureMap.get(opSignature) != null) {
94 LOGGER.warning(AddressingMessages.NON_UNIQUE_OPERATION_SIGNATURE(
95 uniqueOpSignatureMap.get(opSignature),m.getOperationQName(),action,payloadName));
96 }
97 uniqueOpSignatureMap.put(opSignature, m.getOperationQName());
98 actionMap.put(action,m.getOperationQName());
99 }
100 }
101 } else {
102 for (WSDLBoundOperation wsdlOp : wsdlModel.getBinding().getBindingOperations()) {
103 QName payloadName = wsdlOp.getReqPayloadName();
104 if (payloadName == null)
105 payloadName = EMPTY_PAYLOAD;
106 String action = wsdlOp.getOperation().getInput().getAction();
107 ActionBasedOperationSignature opSignature = new ActionBasedOperationSignature(
108 action, payloadName);
109 if(uniqueOpSignatureMap.get(opSignature) != null) {
110 LOGGER.warning(AddressingMessages.NON_UNIQUE_OPERATION_SIGNATURE(
111 uniqueOpSignatureMap.get(opSignature),wsdlOp.getName(),action,payloadName));
113 }
114 uniqueOpSignatureMap.put(opSignature, wsdlOp.getName());
115 actionMap.put(action,wsdlOp.getName());
116 }
117 }
118 }
120 /**
121 *
122 * @param request Request Packet that is used to find the associated WSDLOperation
123 * @return WSDL operation Qname.
124 * return null if WS-Addressing is not engaged.
125 * @throws DispatchException with WSA defined fault message when it cannot find an associated WSDL operation.
126 *
127 */
128 @Override
129 public QName getWSDLOperationQName(Packet request) throws DispatchException {
130 HeaderList hl = request.getMessage().getHeaders();
131 String action = hl.getAction(av, binding.getSOAPVersion());
133 if (action == null)
134 // Addressing is not enagaged, return null to use other ways to dispatch.
135 return null;
137 Message message = request.getMessage();
138 QName payloadName;
139 String localPart = message.getPayloadLocalPart();
140 if (localPart == null) {
141 payloadName = EMPTY_PAYLOAD;
142 } else {
143 String nsUri = message.getPayloadNamespaceURI();
144 if (nsUri == null)
145 nsUri = EMPTY_PAYLOAD_NSURI;
146 payloadName = new QName(nsUri, localPart);
147 }
149 QName opName = uniqueOpSignatureMap.get(new ActionBasedOperationSignature(action, payloadName));
150 if (opName != null)
151 return opName;
153 //Seems like in Wstrust STS wsdls, the payload does not match what is specified in the wsdl leading to incorrect
154 // wsdl operation resolution. Use just wsa:Action to dispatch as a last resort.
155 //try just with wsa:Action
156 opName = actionMap.get(action);
157 if (opName != null)
158 return opName;
160 // invalid action header
161 Message result = Messages.create(action, av, binding.getSOAPVersion());
163 throw new DispatchException(result);
165 }
168 }