Source Code Cross Referenced for HeaderList.java in  » 6.0-JDK-Modules » jax-ws-runtime » com » sun » xml » ws » api » message » Java Source Code / Java DocumentationJava Source Code and Java Documentation

Java Source Code / Java Documentation
1. 6.0 JDK Core
2. 6.0 JDK Modules
3. 6.0 JDK Modules com.sun
4. 6.0 JDK Modules com.sun.java
5. 6.0 JDK Modules sun
6. 6.0 JDK Platform
7. Ajax
8. Apache Harmony Java SE
9. Aspect oriented
10. Authentication Authorization
11. Blogger System
12. Build
13. Byte Code
14. Cache
15. Chart
16. Chat
17. Code Analyzer
18. Collaboration
19. Content Management System
20. Database Client
21. Database DBMS
22. Database JDBC Connection Pool
23. Database ORM
24. Development
25. EJB Server geronimo
26. EJB Server GlassFish
27. EJB Server JBoss 4.2.1
28. EJB Server resin 3.1.5
29. ERP CRM Financial
30. ESB
31. Forum
32. GIS
33. Graphic Library
34. Groupware
35. HTML Parser
36. IDE
37. IDE Eclipse
38. IDE Netbeans
39. Installer
40. Internationalization Localization
41. Inversion of Control
42. Issue Tracking
43. J2EE
44. JBoss
45. JMS
46. JMX
47. Library
48. Mail Clients
49. Net
50. Parser
51. PDF
52. Portal
53. Profiler
54. Project Management
55. Report
56. RSS RDF
57. Rule Engine
58. Science
59. Scripting
60. Search Engine
61. Security
62. Sevlet Container
63. Source Control
64. Swing Library
65. Template Engine
66. Test Coverage
67. Testing
68. UML
69. Web Crawler
70. Web Framework
71. Web Mail
72. Web Server
73. Web Services
74. Web Services apache cxf 2.0.1
75. Web Services AXIS2
76. Wiki Engine
77. Workflow Engines
78. XML
79. XML UI
Java
Java Tutorial
Java Open Source
Jar File Download
Java Articles
Java Products
Java by API
Photoshop Tutorials
Maya Tutorials
Flash Tutorials
3ds-Max Tutorials
Illustrator Tutorials
GIMP Tutorials
C# / C Sharp
C# / CSharp Tutorial
C# / CSharp Open Source
ASP.Net
ASP.NET Tutorial
JavaScript DHTML
JavaScript Tutorial
JavaScript Reference
HTML / CSS
HTML CSS Reference
C / ANSI-C
C Tutorial
C++
C++ Tutorial
Ruby
PHP
Python
Python Tutorial
Python Open Source
SQL Server / T-SQL
SQL Server / T-SQL Tutorial
Oracle PL / SQL
Oracle PL/SQL Tutorial
PostgreSQL
SQL / MySQL
MySQL Tutorial
VB.Net
VB.Net Tutorial
Flash / Flex / ActionScript
VBA / Excel / Access / Word
XML
XML Tutorial
Microsoft Office PowerPoint 2007 Tutorial
Microsoft Office Excel 2007 Tutorial
Microsoft Office Word 2007 Tutorial
Java Source Code / Java Documentation » 6.0 JDK Modules » jax ws runtime » com.sun.xml.ws.api.message 
Source Cross Referenced  Class Diagram Java Document (Java Doc) 


001:        /*
002:         * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS HEADER.
003:         * 
004:         * Copyright 1997-2007 Sun Microsystems, Inc. All rights reserved.
005:         * 
006:         * The contents of this file are subject to the terms of either the GNU
007:         * General Public License Version 2 only ("GPL") or the Common Development
008:         * and Distribution License("CDDL") (collectively, the "License").  You
009:         * may not use this file except in compliance with the License. You can obtain
010:         * a copy of the License at https://glassfish.dev.java.net/public/CDDL+GPL.html
011:         * or glassfish/bootstrap/legal/LICENSE.txt.  See the License for the specific
012:         * language governing permissions and limitations under the License.
013:         * 
014:         * When distributing the software, include this License Header Notice in each
015:         * file and include the License file at glassfish/bootstrap/legal/LICENSE.txt.
016:         * Sun designates this particular file as subject to the "Classpath" exception
017:         * as provided by Sun in the GPL Version 2 section of the License file that
018:         * accompanied this code.  If applicable, add the following below the License
019:         * Header, with the fields enclosed by brackets [] replaced by your own
020:         * identifying information: "Portions Copyrighted [year]
021:         * [name of copyright owner]"
022:         * 
023:         * Contributor(s):
024:         * 
025:         * If you wish your version of this file to be governed by only the CDDL or
026:         * only the GPL Version 2, indicate your decision by adding "[Contributor]
027:         * elects to include this software in this distribution under the [CDDL or GPL
028:         * Version 2] license."  If you don't indicate a single choice of license, a
029:         * recipient has the option to distribute your version of this file under
030:         * either the CDDL, the GPL Version 2 or to extend the choice of license to
031:         * its licensees as provided above.  However, if you add GPL Version 2 code
032:         * and therefore, elected the GPL Version 2 license, then the option applies
033:         * only if the new code is made subject to such option by the copyright
034:         * holder.
035:         */
036:        package com.sun.xml.ws.api.message;
037:
038:        import com.sun.istack.NotNull;
039:        import com.sun.istack.Nullable;
040:        import com.sun.xml.ws.addressing.WsaTubeHelper;
041:        import com.sun.xml.ws.api.SOAPVersion;
042:        import com.sun.xml.ws.api.WSBinding;
043:        import com.sun.xml.ws.api.addressing.AddressingVersion;
044:        import com.sun.xml.ws.api.addressing.OneWayFeature;
045:        import com.sun.xml.ws.api.addressing.WSEndpointReference;
046:        import com.sun.xml.ws.api.model.wsdl.WSDLBoundOperation;
047:        import com.sun.xml.ws.api.model.wsdl.WSDLPort;
048:        import com.sun.xml.ws.api.pipe.Pipe;
049:        import com.sun.xml.ws.api.pipe.Codec;
050:        import com.sun.xml.ws.message.RelatesToHeader;
051:        import com.sun.xml.ws.message.StringHeader;
052:        import com.sun.xml.ws.protocol.soap.ClientMUTube;
053:        import com.sun.xml.ws.protocol.soap.ServerMUTube;
054:        import com.sun.xml.ws.resources.AddressingMessages;
055:        import com.sun.xml.ws.resources.ClientMessages;
056:
057:        import javax.xml.namespace.QName;
058:        import javax.xml.stream.XMLStreamException;
059:        import javax.xml.ws.WebServiceException;
060:        import java.util.ArrayList;
061:        import java.util.BitSet;
062:        import java.util.Collection;
063:        import java.util.Iterator;
064:        import java.util.NoSuchElementException;
065:        import java.util.Set;
066:
067:        /**
068:         * A list of {@link Header}s on a {@link Message}.
069:         *
070:         * <p>
071:         * This list can be modified to add headers
072:         * from outside a {@link Message}, this is necessary
073:         * since intermediate processing layers often need to
074:         * put additional headers.
075:         *
076:         * <p>
077:         * Following the SOAP convention, the order among headers
078:         * are not significant. However, {@link Codec}s are
079:         * expected to preserve the order of headers in the input
080:         * message as much as possible.
081:         *
082:         *
083:         * <a name="MU"></a>
084:         * <h3>MustUnderstand Processing</h3>
085:         * <p>
086:         * To perform SOAP mustUnderstang processing correctly, we need to keep
087:         * track of headers that are understood and headers that are not.
088:         * This is a collaborative process among {@link Pipe}s, thus it's something
089:         * a {@link Pipe} author needs to keep in mind.
090:         *
091:         * <p>
092:         * Specifically, when a {@link Pipe} sees a header and processes it
093:         * (that is, if it did enough computing with the header to claim that
094:         * the header is understood), then it should mark the corresponding
095:         * header as "understood". For example, when a pipe that handles JAX-WSA
096:         * examins the &lt;wsa:To> header, it can claim that it understood the header.
097:         * But for example, if a pipe that does the signature verification checks
098:         * &lt;wsa:To> for a signature, that would not be considered as "understood".
099:         *
100:         * <p>
101:         * There are two ways to mark a header as understood:
102:         *
103:         * <ol>
104:         *  <li>Use one of the <tt>getXXX</tt> methods that take a
105:         *      boolean <tt>markAsUnderstood</tt> parameter.
106:         *      Most often, a {@link Pipe} knows it's going to understand a header
107:         *      as long as it's present, so this is the easiest and thus the preferred way.
108:         *
109:         *      For example, if JAX-WSA looks for &lt;wsa:To>, then it can set
110:         *      <tt>markAsUnderstand</tt> to true, to do the obtaining of a header
111:         *      and marking at the same time.
112:         *
113:         *  <li>Call {@link #understood(int)}.
114:         *      If under a rare circumstance, a pipe cannot determine whether
115:         *      it can understand it or not when you are fetching a header, then
116:         *      you can use this method afterward to mark it as understood.
117:         * </ol>
118:         *
119:         * <p>
120:         * Intuitively speaking, at the end of the day, if a header is not
121:         * understood but {@link Header#isIgnorable(SOAPVersion, Set)} is false, a bad thing
122:         * will happen. The actual implementation of the checking is more complicated,
123:         * for that see {@link ClientMUTube}/{@link ServerMUTube}.
124:         *
125:         * @see Message#getHeaders()
126:         */
127:        public final class HeaderList extends ArrayList<Header> {
128:
129:            /**
130:             * Bit set to keep track of which headers are understood.
131:             * <p>
132:             * The first 32 headers use this field, and the rest will use
133:             * {@link #moreUnderstoodBits}. The expectation is that
134:             * most of the time a SOAP message will only have up to 32 headers,
135:             * so we can avoid allocating separate objects for {@link BitSet}.
136:             */
137:            private int understoodBits;
138:            /**
139:             * If there are more than 32 headers, we use this {@link BitSet}
140:             * to keep track of whether those headers are understood.
141:             * Lazily allocated.
142:             */
143:            private BitSet moreUnderstoodBits = null;
144:
145:            private String to = null;
146:            private String action = null;
147:            private WSEndpointReference replyTo = null;
148:            private WSEndpointReference faultTo = null;
149:            private String messageId;
150:
151:            /**
152:             * Creates an empty {@link HeaderList}.
153:             */
154:            public HeaderList() {
155:            }
156:
157:            /**
158:             * Copy constructor.
159:             */
160:            public HeaderList(HeaderList that) {
161:                super (that);
162:                this .understoodBits = that.understoodBits;
163:                if (that.moreUnderstoodBits != null)
164:                    this .moreUnderstoodBits = (BitSet) that.moreUnderstoodBits
165:                            .clone();
166:                this .to = that.to;
167:                this .action = that.action;
168:                this .replyTo = that.replyTo;
169:                this .faultTo = that.faultTo;
170:                this .messageId = that.messageId;
171:            }
172:
173:            /**
174:             * The number of total headers.
175:             */
176:            public int size() {
177:                return super .size();
178:            }
179:
180:            /**
181:             * Adds all the headers.
182:             */
183:            public void addAll(Header... headers) {
184:                for (Header header : headers)
185:                    add(header);
186:            }
187:
188:            /**
189:             * Gets the {@link Header} at the specified index.
190:             *
191:             * <p>
192:             * This method does not mark the returned {@link Header} as understood.
193:             *
194:             * @see #understood(int)
195:             */
196:            public Header get(int index) {
197:                return super .get(index);
198:            }
199:
200:            /**
201:             * Marks the {@link Header} at the specified index as
202:             * <a href="#MU">"understood"</a>.
203:             */
204:            public void understood(int index) {
205:                assert index < size(); // check that index is in range
206:                if (index < 32)
207:                    understoodBits |= 1 << index;
208:                else {
209:                    if (moreUnderstoodBits == null)
210:                        moreUnderstoodBits = new BitSet();
211:                    moreUnderstoodBits.set(index - 32);
212:                }
213:            }
214:
215:            /**
216:             * Returns true if a {@link Header} at the given index
217:             * was <a href="#MU">"understood"</a>.
218:             */
219:            public boolean isUnderstood(int index) {
220:                assert index < size(); // check that index is in range
221:                if (index < 32)
222:                    return understoodBits == (understoodBits | (1 << index));
223:                else {
224:                    if (moreUnderstoodBits == null)
225:                        return false;
226:                    return moreUnderstoodBits.get(index - 32);
227:                }
228:            }
229:
230:            /**
231:             * Marks the specified {@link Header} as <a href="#MU">"understood"</a>.
232:             *
233:             * @deprecated
234:             * By the deifnition of {@link ArrayList}, this operation requires
235:             * O(n) search of the array, and thus inherently inefficient.
236:             *
237:             * Because of this, if you are developing a {@link Pipe} for
238:             * a performance sensitive environment, do not use this method.
239:             *
240:             * @throws IllegalArgumentException
241:             *      if the given header is not {@link #contains(Object) contained}
242:             *      in this header.
243:             */
244:            public void understood(@NotNull
245:            Header header) {
246:                int sz = size();
247:                for (int i = 0; i < sz; i++) {
248:                    if (get(i) == header) {
249:                        understood(i);
250:                        return;
251:                    }
252:                }
253:                throw new IllegalArgumentException();
254:            }
255:
256:            /**
257:             * Gets the first {@link Header} of the specified name.
258:             *
259:             * @param markAsUnderstood
260:             *      If this parameter is true, the returned header will
261:             *      be marked as <a href="#MU">"understood"</a>.
262:             * @return null if not found.
263:             */
264:            public @Nullable
265:            Header get(@NotNull
266:            String nsUri, @NotNull
267:            String localName, boolean markAsUnderstood) {
268:                int len = size();
269:                for (int i = 0; i < len; i++) {
270:                    Header h = get(i);
271:                    if (h.getLocalPart().equals(localName)
272:                            && h.getNamespaceURI().equals(nsUri)) {
273:                        if (markAsUnderstood)
274:                            understood(i);
275:                        return h;
276:                    }
277:                }
278:                return null;
279:            }
280:
281:            /**
282:             * @deprecated
283:             *      Use {@link #get(String, String, boolean)}
284:             */
285:            public Header get(String nsUri, String localName) {
286:                return get(nsUri, localName, true);
287:            }
288:
289:            /**
290:             * Gets the first {@link Header} of the specified name.
291:             *
292:             * @param markAsUnderstood
293:             *      If this parameter is true, the returned header will
294:             *      be marked as <a href="#MU">"understood"</a>.
295:             * @return null
296:             *      if not found.
297:             */
298:            public @Nullable
299:            Header get(@NotNull
300:            QName name, boolean markAsUnderstood) {
301:                return get(name.getNamespaceURI(), name.getLocalPart(),
302:                        markAsUnderstood);
303:            }
304:
305:            /**
306:             * @deprecated
307:             *      Use {@link #get(QName)}
308:             */
309:            public @Nullable
310:            Header get(@NotNull
311:            QName name) {
312:                return get(name, true);
313:            }
314:
315:            /**
316:             * @deprecated
317:             *      Use {@link #getHeaders(String, String, boolean)}
318:             */
319:            public Iterator<Header> getHeaders(final String nsUri,
320:                    final String localName) {
321:                return getHeaders(nsUri, localName, true);
322:            }
323:
324:            /**
325:             * Gets all the {@link Header}s of the specified name,
326:             * including duplicates (if any.)
327:             *
328:             * @param markAsUnderstood
329:             *      If this parameter is true, the returned headers will
330:             *      be marked as <a href="#MU">"understood"</a> when they are returned
331:             *      from {@link Iterator#next()}.
332:             * @return empty iterator if not found.
333:             */
334:            public @NotNull
335:            Iterator<Header> getHeaders(@NotNull
336:            final String nsUri, @NotNull
337:            final String localName, final boolean markAsUnderstood) {
338:                return new Iterator<Header>() {
339:                    int idx = 0;
340:                    Header next;
341:
342:                    public boolean hasNext() {
343:                        if (next == null)
344:                            fetch();
345:                        return next != null;
346:                    }
347:
348:                    public Header next() {
349:                        if (next == null) {
350:                            fetch();
351:                            if (next == null)
352:                                throw new NoSuchElementException();
353:                        }
354:
355:                        if (markAsUnderstood) {
356:                            assert get(idx - 1) == next;
357:                            understood(idx - 1);
358:                        }
359:
360:                        Header r = next;
361:                        next = null;
362:                        return r;
363:                    }
364:
365:                    private void fetch() {
366:                        while (idx < size()) {
367:                            Header h = get(idx++);
368:                            if (h.getLocalPart().equals(localName)
369:                                    && h.getNamespaceURI().equals(nsUri)) {
370:                                next = h;
371:                                break;
372:                            }
373:                        }
374:                    }
375:
376:                    public void remove() {
377:                        throw new UnsupportedOperationException();
378:                    }
379:                };
380:            }
381:
382:            /**
383:             * @see #getHeaders(String, String, boolean)
384:             */
385:            public @NotNull
386:            Iterator<Header> getHeaders(@NotNull
387:            QName headerName, final boolean markAsUnderstood) {
388:                return getHeaders(headerName.getNamespaceURI(), headerName
389:                        .getLocalPart(), markAsUnderstood);
390:            }
391:
392:            /**
393:             * @deprecated
394:             *      use {@link #getHeaders(String, boolean)}.
395:             */
396:            public @NotNull
397:            Iterator<Header> getHeaders(@NotNull
398:            final String nsUri) {
399:                return getHeaders(nsUri, true);
400:            }
401:
402:            /**
403:             * Gets an iteration of headers {@link Header} in the specified namespace,
404:             * including duplicates (if any.)
405:             *
406:             * @param markAsUnderstood
407:             *      If this parameter is true, the returned headers will
408:             *      be marked as <a href="#MU">"understood"</a> when they are returned
409:             *      from {@link Iterator#next()}.
410:             * @return
411:             *      empty iterator if not found.
412:             */
413:            public @NotNull
414:            Iterator<Header> getHeaders(@NotNull
415:            final String nsUri, final boolean markAsUnderstood) {
416:                return new Iterator<Header>() {
417:                    int idx = 0;
418:                    Header next;
419:
420:                    public boolean hasNext() {
421:                        if (next == null)
422:                            fetch();
423:                        return next != null;
424:                    }
425:
426:                    public Header next() {
427:                        if (next == null) {
428:                            fetch();
429:                            if (next == null)
430:                                throw new NoSuchElementException();
431:                        }
432:
433:                        if (markAsUnderstood) {
434:                            assert get(idx - 1) == next;
435:                            understood(idx - 1);
436:                        }
437:
438:                        Header r = next;
439:                        next = null;
440:                        return r;
441:                    }
442:
443:                    private void fetch() {
444:                        while (idx < size()) {
445:                            Header h = get(idx++);
446:                            if (h.getNamespaceURI().equals(nsUri)) {
447:                                next = h;
448:                                break;
449:                            }
450:                        }
451:                    }
452:
453:                    public void remove() {
454:                        throw new UnsupportedOperationException();
455:                    }
456:                };
457:            }
458:
459:            /**
460:             * Gets the first {@link Header} of the specified name targeted at the
461:             * current implicit role.
462:             *
463:             * @param name name of the header
464:             * @param markUnderstood
465:             *      If this parameter is true, the returned headers will
466:             *      be marked as <a href="#MU">"understood"</a> when they are returned
467:             *      from {@link Iterator#next()}.
468:             * @return null if header not found
469:             */
470:            private Header getFirstHeader(QName name, boolean markUnderstood,
471:                    SOAPVersion sv) {
472:                if (sv == null)
473:                    throw new IllegalArgumentException(AddressingMessages
474:                            .NULL_SOAP_VERSION());
475:
476:                Iterator<Header> iter = getHeaders(name.getNamespaceURI(), name
477:                        .getLocalPart(), markUnderstood);
478:                while (iter.hasNext()) {
479:                    Header h = iter.next();
480:                    if (h.getRole(sv).equals(sv.implicitRole))
481:                        return h;
482:                }
483:
484:                return null;
485:            }
486:
487:            /**
488:             * Returns the value of WS-Addressing <code>To</code> header. The <code>version</code>
489:             * identifies the WS-Addressing version and the header returned is targeted at
490:             * the current implicit role. Caches the value for subsequent invocation.
491:             * Duplicate <code>To</code> headers are detected earlier.
492:             *
493:             * @param av WS-Addressing version
494:             * @param sv SOAP version
495:             * @throws IllegalArgumentException if either <code>av</code> or <code>sv</code> is null.
496:             * @return Value of WS-Addressing To header, anonymous URI if no header is present
497:             */
498:            public String getTo(AddressingVersion av, SOAPVersion sv) {
499:                if (to != null)
500:                    return to;
501:                if (av == null)
502:                    throw new IllegalArgumentException(AddressingMessages
503:                            .NULL_ADDRESSING_VERSION());
504:
505:                Header h = getFirstHeader(av.toTag, true, sv);
506:                if (h != null) {
507:                    to = h.getStringContent();
508:                } else {
509:                    to = av.anonymousUri;
510:                }
511:
512:                return to;
513:            }
514:
515:            /**
516:             * Returns the value of WS-Addressing <code>Action</code> header. The <code>version</code>
517:             * identifies the WS-Addressing version and the header returned is targeted at
518:             * the current implicit role. Caches the value for subsequent invocation.
519:             * Duplicate <code>Action</code> headers are detected earlier.
520:             *
521:             * @param av WS-Addressing version
522:             * @param sv SOAP version
523:             * @throws IllegalArgumentException if either <code>av</code> or <code>sv</code> is null.
524:             * @return Value of WS-Addressing Action header, null if no header is present
525:             */
526:            public String getAction(@NotNull
527:            AddressingVersion av, @NotNull
528:            SOAPVersion sv) {
529:                if (action != null)
530:                    return action;
531:                if (av == null)
532:                    throw new IllegalArgumentException(AddressingMessages
533:                            .NULL_ADDRESSING_VERSION());
534:
535:                Header h = getFirstHeader(av.actionTag, true, sv);
536:                if (h != null) {
537:                    action = h.getStringContent();
538:                }
539:
540:                return action;
541:            }
542:
543:            /**
544:             * Returns the value of WS-Addressing <code>ReplyTo</code> header. The <code>version</code>
545:             * identifies the WS-Addressing version and the header returned is targeted at
546:             * the current implicit role. Caches the value for subsequent invocation.
547:             * Duplicate <code>ReplyTo</code> headers are detected earlier.
548:             *
549:             * @param av WS-Addressing version
550:             * @param sv SOAP version
551:             * @throws IllegalArgumentException if either <code>av</code> or <code>sv</code> is null.
552:             * @return Value of WS-Addressing ReplyTo header, null if no header is present
553:             */
554:            public WSEndpointReference getReplyTo(@NotNull
555:            AddressingVersion av, @NotNull
556:            SOAPVersion sv) {
557:                if (replyTo != null)
558:                    return replyTo;
559:                if (av == null)
560:                    throw new IllegalArgumentException(AddressingMessages
561:                            .NULL_ADDRESSING_VERSION());
562:
563:                Header h = getFirstHeader(av.replyToTag, true, sv);
564:                if (h != null) {
565:                    try {
566:                        replyTo = h.readAsEPR(av);
567:                    } catch (XMLStreamException e) {
568:                        throw new WebServiceException(AddressingMessages
569:                                .REPLY_TO_CANNOT_PARSE(), e);
570:                    }
571:                } else {
572:                    replyTo = av.anonymousEpr;
573:                }
574:
575:                return replyTo;
576:            }
577:
578:            /**
579:             * Returns the value of WS-Addressing <code>FaultTo</code> header. The <code>version</code>
580:             * identifies the WS-Addressing version and the header returned is targeted at
581:             * the current implicit role. Caches the value for subsequent invocation.
582:             * Duplicate <code>FaultTo</code> headers are detected earlier.
583:             *
584:             * @param av WS-Addressing version
585:             * @param sv SOAP version
586:             * @throws IllegalArgumentException if either <code>av</code> or <code>sv</code> is null.
587:             * @return Value of WS-Addressing FaultTo header, null if no header is present
588:             */
589:            public WSEndpointReference getFaultTo(@NotNull
590:            AddressingVersion av, @NotNull
591:            SOAPVersion sv) {
592:                if (faultTo != null)
593:                    return faultTo;
594:
595:                if (av == null)
596:                    throw new IllegalArgumentException(AddressingMessages
597:                            .NULL_ADDRESSING_VERSION());
598:
599:                Header h = getFirstHeader(av.faultToTag, true, sv);
600:                if (h != null) {
601:                    try {
602:                        faultTo = h.readAsEPR(av);
603:                    } catch (XMLStreamException e) {
604:                        throw new WebServiceException(AddressingMessages
605:                                .FAULT_TO_CANNOT_PARSE(), e);
606:                    }
607:                }
608:
609:                return faultTo;
610:            }
611:
612:            /**
613:             * Returns the value of WS-Addressing <code>MessageID</code> header. The <code>version</code>
614:             * identifies the WS-Addressing version and the header returned is targeted at
615:             * the current implicit role. Caches the value for subsequent invocation.
616:             * Duplicate <code>MessageID</code> headers are detected earlier.
617:             *
618:             * @param av WS-Addressing version
619:             * @param sv SOAP version
620:             * @throws WebServiceException if either <code>av</code> or <code>sv</code> is null.
621:             * @return Value of WS-Addressing MessageID header, null if no header is present
622:             */
623:            public String getMessageID(@NotNull
624:            AddressingVersion av, @NotNull
625:            SOAPVersion sv) {
626:                if (messageId != null)
627:                    return messageId;
628:
629:                if (av == null)
630:                    throw new IllegalArgumentException(AddressingMessages
631:                            .NULL_ADDRESSING_VERSION());
632:
633:                Header h = getFirstHeader(av.messageIDTag, true, sv);
634:                if (h != null) {
635:                    messageId = h.getStringContent();
636:                }
637:
638:                return messageId;
639:            }
640:
641:            /**
642:             * Creates a set of outbound WS-Addressing headers on the client with the
643:             * specified Action Message Addressing Property value.
644:             * <p><p>
645:             * This method needs to be invoked right after such a Message is
646:             * created which is error prone but so far only MEX, RM and JAX-WS
647:             * creates a request so this ugliness is acceptable. This method is also used
648:             * to create protocol messages that are not associated with any {@link WSBinding}
649:             * and {@link WSDLPort}.
650:             *
651:             * @param packet request packet
652:             * @param av WS-Addressing version
653:             * @param sv SOAP version
654:             * @param oneway Indicates if the message exchange pattern is oneway
655:             * @param action Action Message Addressing Property value
656:             */
657:            public void fillRequestAddressingHeaders(Packet packet,
658:                    AddressingVersion av, SOAPVersion sv, boolean oneway,
659:                    String action) {
660:                fillCommonAddressingHeaders(packet, av, sv, action);
661:
662:                // wsa:ReplyTo
663:                // null or "true" is equivalent to request/response MEP
664:                if (!oneway) {
665:                    WSEndpointReference epr = av.anonymousEpr;
666:                    add(epr.createHeader(av.replyToTag));
667:
668:                    // wsa:MessageID
669:                    Header h = new StringHeader(av.messageIDTag, packet
670:                            .getMessage().getID(av, sv));
671:                    add(h);
672:                }
673:            }
674:
675:            /**
676:             * Creates a set of outbound WS-Addressing headers on the client with the
677:             * default Action Message Addressing Property value.
678:             * <p><p>
679:             * This method needs to be invoked right after such a Message is
680:             * created which is error prone but so far only MEX, RM and JAX-WS
681:             * creates a request so this ugliness is acceptable. If more components
682:             * are identified using this, then we may revisit this.
683:             * <p><p>
684:             * This method is used if default Action Message Addressing Property is to
685:             * be used. See
686:             * {@link #fillRequestAddressingHeaders(Packet, com.sun.xml.ws.api.addressing.AddressingVersion, com.sun.xml.ws.api.SOAPVersion, boolean, String)}
687:             * if non-default Action is to be used, for example when creating a protocol message not
688:             * associated with {@link WSBinding} and {@link WSDLPort}.
689:             * This method uses SOAPAction as the Action unless set expplicitly in the wsdl.
690:             * @param wsdlPort request WSDL port
691:             * @param binding request WSBinding
692:             * @param packet request packet
693:             */
694:            public void fillRequestAddressingHeaders(WSDLPort wsdlPort,
695:                    @NotNull
696:                    WSBinding binding, Packet packet) {
697:                if (binding == null)
698:                    throw new IllegalArgumentException(AddressingMessages
699:                            .NULL_BINDING());
700:
701:                AddressingVersion addressingVersion = binding
702:                        .getAddressingVersion();
703:                //seiModel is passed as null as it is not needed.
704:                WsaTubeHelper wsaHelper = addressingVersion.getWsaHelper(
705:                        wsdlPort, null, binding);
706:
707:                // wsa:Action
708:                String action = wsaHelper.getEffectiveInputAction(packet);
709:                if (action == null || action.equals("")) {
710:                    throw new WebServiceException(ClientMessages
711:                            .INVALID_SOAP_ACTION());
712:                }
713:                boolean oneway = !packet.expectReply;
714:                if (wsdlPort != null) {
715:                    // if WSDL has <wsaw:Anonymous>prohibited</wsaw:Anonymous>, then throw an error
716:                    // as anonymous ReplyTo MUST NOT be added in that case. BindingProvider need to
717:                    // disable AddressingFeature and MemberSubmissionAddressingFeature and hand-craft
718:                    // the SOAP message with non-anonymous ReplyTo/FaultTo.
719:                    if (!oneway
720:                            && packet.getMessage() != null
721:                            && packet.getMessage().getOperation(wsdlPort) != null
722:                            && packet.getMessage().getOperation(wsdlPort)
723:                                    .getAnonymous() == WSDLBoundOperation.ANONYMOUS.prohibited) {
724:                        throw new WebServiceException(AddressingMessages
725:                                .WSAW_ANONYMOUS_PROHIBITED());
726:                    }
727:                }
728:                if (!binding.isFeatureEnabled(OneWayFeature.class)) {
729:                    // standard oneway
730:                    fillRequestAddressingHeaders(packet, addressingVersion,
731:                            binding.getSOAPVersion(), oneway, action);
732:                } else {
733:                    // custom oneway
734:                    fillRequestAddressingHeaders(packet, addressingVersion,
735:                            binding.getSOAPVersion(), binding
736:                                    .getFeature(OneWayFeature.class), action);
737:                }
738:            }
739:
740:            private void fillRequestAddressingHeaders(@NotNull
741:            Packet packet, @NotNull
742:            AddressingVersion av, @NotNull
743:            SOAPVersion sv, @NotNull
744:            OneWayFeature of, @NotNull
745:            String action) {
746:                fillCommonAddressingHeaders(packet, av, sv, action);
747:
748:                // wsa:ReplyTo
749:                if (of.getReplyTo() != null) {
750:                    add(of.getReplyTo().createHeader(av.replyToTag));
751:
752:                    // add wsa:MessageID only for non-null ReplyTo
753:                    Header h = new StringHeader(av.messageIDTag, packet
754:                            .getMessage().getID(av, sv));
755:                    add(h);
756:                }
757:
758:                // wsa:From
759:                if (of.getFrom() != null) {
760:                    add(of.getFrom().createHeader(av.fromTag));
761:                }
762:
763:                // wsa:RelatesTo
764:                if (of.getRelatesToID() != null) {
765:                    add(new RelatesToHeader(av.relatesToTag, of
766:                            .getRelatesToID()));
767:                }
768:            }
769:
770:            /**
771:             * Creates wsa:To, wsa:Action and wsa:MessageID header on the client
772:             *
773:             * @param packet request packet
774:             * @param av WS-Addressing version
775:             * @param sv SOAP version
776:             * @param action Action Message Addressing Property value
777:             * @throws IllegalArgumentException if any of the parameters is null.
778:             */
779:            private void fillCommonAddressingHeaders(Packet packet, @NotNull
780:            AddressingVersion av, @NotNull
781:            SOAPVersion sv, @NotNull
782:            String action) {
783:                if (packet == null)
784:                    throw new IllegalArgumentException(AddressingMessages
785:                            .NULL_PACKET());
786:
787:                if (av == null)
788:                    throw new IllegalArgumentException(AddressingMessages
789:                            .NULL_ADDRESSING_VERSION());
790:
791:                if (sv == null)
792:                    throw new IllegalArgumentException(AddressingMessages
793:                            .NULL_SOAP_VERSION());
794:
795:                if (action == null)
796:                    throw new IllegalArgumentException(AddressingMessages
797:                            .NULL_ACTION());
798:
799:                // wsa:To
800:                StringHeader h = new StringHeader(av.toTag,
801:                        packet.endpointAddress.toString());
802:                add(h);
803:
804:                // wsa:Action
805:                packet.soapAction = action;
806:                h = new StringHeader(av.actionTag, action);
807:                add(h);
808:            }
809:
810:            /**
811:             * Adds a new {@link Header}.
812:             *
813:             * <p>
814:             * Order doesn't matter in headers, so this method
815:             * does not make any guarantee as to where the new header
816:             * is inserted.
817:             *
818:             * @return
819:             *      always true. Don't use the return value.      
820:             */
821:            public boolean add(Header header) {
822:                return super .add(header);
823:            }
824:
825:            /**
826:             * @deprecated
827:             *      {@link HeaderList} is monotonic and you can't remove anything.
828:             */
829:            // to allow this, we need to implement the resizing of understoodBits
830:            public Header remove(int index) {
831:                throw new UnsupportedOperationException();
832:            }
833:
834:            /**
835:             * @deprecated
836:             *      {@link HeaderList} is monotonic and you can't remove anything.
837:             */
838:            public boolean remove(Object o) {
839:                throw new UnsupportedOperationException();
840:            }
841:
842:            /**
843:             * @deprecated
844:             *      {@link HeaderList} is monotonic and you can't remove anything.
845:             */
846:            public boolean removeAll(Collection<?> c) {
847:                throw new UnsupportedOperationException();
848:            }
849:
850:            /**
851:             * @deprecated
852:             *      {@link HeaderList} is monotonic and you can't remove anything.
853:             */
854:            public boolean retainAll(Collection<?> c) {
855:                throw new UnsupportedOperationException();
856:            }
857:
858:            /**
859:             * Creates a copy.
860:             *
861:             * This handles null {@link HeaderList} correctly.
862:             *
863:             * @param original
864:             *      Can be null, in which case null will be returned.
865:             */
866:            public static HeaderList copy(HeaderList original) {
867:                if (original == null)
868:                    return null;
869:                else
870:                    return new HeaderList(original);
871:            }
872:
873:            public void readResponseAddressingHeaders(WSDLPort wsdlPort,
874:                    WSBinding binding) {
875:                // read Action
876:                String action = getAction(binding.getAddressingVersion(),
877:                        binding.getSOAPVersion());
878:                // TODO: validate client-inbound Action
879:            }
880:        }
www.java2java.com | Contact Us
Copyright 2009 - 12 Demo Source and Support. All rights reserved.
All other trademarks are property of their respective owners.