325N/A/*
325N/A * Copyright (c) 1997, 2010, Oracle and/or its affiliates. All rights reserved.
325N/A * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
325N/A *
325N/A * This code is free software; you can redistribute it and/or modify it
325N/A * under the terms of the GNU General Public License version 2 only, as
325N/A * published by the Free Software Foundation. Oracle designates this
325N/A * particular file as subject to the "Classpath" exception as provided
325N/A * by Oracle in the LICENSE file that accompanied this code.
325N/A *
325N/A * This code is distributed in the hope that it will be useful, but WITHOUT
325N/A * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
325N/A * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
325N/A * version 2 for more details (a copy is included in the LICENSE file that
325N/A * accompanied this code).
325N/A *
325N/A * You should have received a copy of the GNU General Public License version
325N/A * 2 along with this work; if not, write to the Free Software Foundation,
325N/A * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
325N/A *
325N/A * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
325N/A * or visit www.oracle.com if you need additional information or have any
325N/A * questions.
325N/A */
325N/A
325N/Apackage com.sun.xml.internal.ws.api.server;
325N/A
325N/Aimport com.sun.istack.internal.NotNull;
325N/Aimport com.sun.istack.internal.Nullable;
325N/Aimport com.sun.xml.internal.ws.api.PropertySet;
325N/Aimport com.sun.xml.internal.ws.api.message.Message;
325N/Aimport com.sun.xml.internal.ws.api.message.Packet;
325N/Aimport com.sun.xml.internal.ws.api.pipe.Codec;
325N/Aimport com.sun.xml.internal.ws.api.pipe.Fiber;
325N/Aimport com.sun.xml.internal.ws.util.Pool;
325N/A
325N/Aimport java.io.IOException;
325N/A
325N/A/**
325N/A * Partial server side async transport implementation. It manages pooling of
325N/A * {@link Codec} and other details.
325N/A *
325N/A * @author Jitendra Kotamraju
325N/A */
325N/Apublic abstract class AbstractServerAsyncTransport<T> {
325N/A
325N/A private final WSEndpoint endpoint;
325N/A private final CodecPool codecPool;
325N/A
325N/A /**
325N/A * {@link WSEndpoint#setExecutor} should be called before creating the
325N/A * transport
325N/A *
325N/A * @param endpoint webservices requests are directed towards this endpoint
325N/A */
325N/A public AbstractServerAsyncTransport(WSEndpoint endpoint) {
325N/A this.endpoint = endpoint;
325N/A codecPool = new CodecPool(endpoint);
325N/A }
325N/A
325N/A /**
325N/A * decodes the transport data to Packet
325N/A *
325N/A * @param connection that carries the web service request
325N/A * @param codec for encoding/decoding {@link Message}
325N/A * @return decoded {@link Packet}
325N/A * @throws IOException if an i/o error happens while encoding/decoding
325N/A */
325N/A protected Packet decodePacket(T connection, @NotNull Codec codec) throws IOException {
325N/A Packet packet = new Packet();
325N/A packet.acceptableMimeTypes = getAcceptableMimeTypes(connection);
325N/A packet.addSatellite(getPropertySet(connection));
325N/A packet.transportBackChannel = getTransportBackChannel(connection);
325N/A return packet;
325N/A }
325N/A
325N/A /**
325N/A * Encodes the {@link Packet} to infoset and writes on the connection.
325N/A *
325N/A * @param connection that carries the web service request
325N/A * @param packet that needs to encoded to infoset
325N/A * @param codec that does the encoding of Packet
325N/A * @throws IOException if an i/o error happens while encoding/decoding
325N/A */
325N/A protected abstract void encodePacket(T connection, @NotNull Packet packet, @NotNull Codec codec) throws IOException;
325N/A
325N/A /**
325N/A * If the request has Accept header, return that value
325N/A *
325N/A * @param connection that carries the web service request
325N/A * @return Accept MIME types
325N/A */
325N/A protected abstract @Nullable String getAcceptableMimeTypes(T connection);
325N/A
325N/A /**
325N/A * {@link TransportBackChannel} used by jax-ws runtime to close the connection
325N/A * while the processing of the request is still continuing. In oneway HTTP case, a
325N/A * response code needs to be sent before invoking the endpoint.
325N/A *
325N/A * @param connection that carries the web service request
325N/A * @return TransportBackChannel instance using the connection
325N/A */
325N/A protected abstract @Nullable TransportBackChannel getTransportBackChannel(T connection);
325N/A
325N/A /**
325N/A * If there are any properties associated with the connection, those will
325N/A * be added to {@link Packet}
325N/A *
325N/A * @param connection that carries the web service request
325N/A * @return {@link PropertySet} for the connection
325N/A */
325N/A protected abstract @NotNull PropertySet getPropertySet(T connection);
325N/A
325N/A /**
325N/A * Return a {@link WebServiceContextDelegate} using the underlying connection.
325N/A *
325N/A * @param connection that carries the web service request
325N/A * @return non-null WebServiceContextDelegate instance
325N/A */
325N/A protected abstract @NotNull WebServiceContextDelegate getWebServiceContextDelegate(T connection);
325N/A
325N/A /**
325N/A * Reads and decodes infoset from the connection and invokes the endpoints. The
325N/A * response is encoded and written to the connection. The response could be
325N/A * written using a different thread.
325N/A *
325N/A * @param connection that carries the web service request
325N/A * @throws IOException if an i/o error happens while encoding/decoding
325N/A */
325N/A protected void handle(final T connection) throws IOException {
325N/A final Codec codec = codecPool.take();
325N/A Packet request = decodePacket(connection, codec);
325N/A if (!request.getMessage().isFault()) {
325N/A endpoint.schedule(request, new WSEndpoint.CompletionCallback() {
325N/A public void onCompletion(@NotNull Packet response) {
325N/A try {
325N/A encodePacket(connection, response, codec);
325N/A } catch(IOException ioe) {
325N/A ioe.printStackTrace();
325N/A }
325N/A codecPool.recycle(codec);
325N/A }
325N/A });
325N/A }
325N/A }
325N/A
325N/A private static final class CodecPool extends Pool<Codec> {
325N/A WSEndpoint endpoint;
325N/A
325N/A CodecPool(WSEndpoint endpoint) {
325N/A this. endpoint = endpoint;
325N/A }
325N/A
325N/A protected Codec create() {
325N/A return endpoint.createCodec();
325N/A }
325N/A }
325N/A
325N/A}