001/*
002 * ====================================================================
003 * Licensed to the Apache Software Foundation (ASF) under one
004 * or more contributor license agreements.  See the NOTICE file
005 * distributed with this work for additional information
006 * regarding copyright ownership.  The ASF licenses this file
007 * to you under the Apache License, Version 2.0 (the
008 * "License"); you may not use this file except in compliance
009 * with the License.  You may obtain a copy of the License at
010 *
011 *   http://www.apache.org/licenses/LICENSE-2.0
012 *
013 * Unless required by applicable law or agreed to in writing,
014 * software distributed under the License is distributed on an
015 * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
016 * KIND, either express or implied.  See the License for the
017 * specific language governing permissions and limitations
018 * under the License.
019 * ====================================================================
020 *
021 * This software consists of voluntary contributions made by many
022 * individuals on behalf of the Apache Software Foundation.  For more
023 * information on the Apache Software Foundation, please see
024 * <http://www.apache.org/>.
025 *
026 */
027
028package org.apache.http.impl.nio;
029
030import java.io.IOException;
031
032import javax.net.ssl.SSLContext;
033
034import org.apache.http.annotation.Contract;
035import org.apache.http.annotation.ThreadingBehavior;
036import org.apache.http.config.ConnectionConfig;
037import org.apache.http.impl.nio.reactor.AbstractIODispatch;
038import org.apache.http.nio.NHttpConnectionFactory;
039import org.apache.http.nio.NHttpServerEventHandler;
040import org.apache.http.nio.reactor.IOSession;
041import org.apache.http.nio.reactor.ssl.SSLSetupHandler;
042import org.apache.http.params.HttpParams;
043import org.apache.http.util.Args;
044
045/**
046 * Default {@link org.apache.http.nio.reactor.IOEventDispatch} implementation
047 * that supports both plain (non-encrypted) and SSL encrypted server side HTTP
048 * connections.
049 *
050 * @since 4.2
051 */
052@SuppressWarnings("deprecation")
053@Contract(threading = ThreadingBehavior.IMMUTABLE_CONDITIONAL)
054public class DefaultHttpServerIODispatch
055                    extends AbstractIODispatch<DefaultNHttpServerConnection> {
056
057    /**
058     * Creates a new instance of this class to be used for dispatching I/O event
059     * notifications to the given protocol handler.
060     *
061     * @param handler the client protocol handler.
062     * @param sslContext an SSLContext or null (for a plain text connection.)
063     * @param config a connection configuration
064     * @return a new instance
065     * @since 4.4.7
066     */
067    public static DefaultHttpServerIODispatch create(final NHttpServerEventHandler handler,
068            final SSLContext sslContext,
069            final ConnectionConfig config) {
070        return sslContext == null ? new DefaultHttpServerIODispatch(handler, config)
071                : new DefaultHttpServerIODispatch(handler, sslContext, config);
072    }
073
074    /**
075     * Creates a new instance of this class to be used for dispatching I/O event
076     * notifications to the given protocol handler.
077     *
078     * @param handler the client protocol handler.
079     * @param sslContext an SSLContext or null (for a plain text connection.)
080     * @param sslHandler customizes various aspects of the TLS/SSL protocol.
081     * @param config a connection configuration
082     * @return a new instance
083     * @since 4.4.7
084     */
085    public static DefaultHttpServerIODispatch create(final NHttpServerEventHandler handler,
086            final SSLContext sslContext,
087            final SSLSetupHandler sslHandler,
088            final ConnectionConfig config) {
089        return sslContext == null ? new DefaultHttpServerIODispatch(handler, config)
090                : new DefaultHttpServerIODispatch(handler, sslContext, sslHandler, config);
091    }
092
093    private final NHttpServerEventHandler handler;
094    private final NHttpConnectionFactory<? extends DefaultNHttpServerConnection> connFactory;
095
096    public DefaultHttpServerIODispatch(
097            final NHttpServerEventHandler handler,
098            final NHttpConnectionFactory<? extends DefaultNHttpServerConnection> connFactory) {
099        super();
100        this.handler = Args.notNull(handler, "HTTP client handler");
101        this.connFactory = Args.notNull(connFactory, "HTTP server connection factory");
102    }
103
104    /**
105     * @deprecated (4.3) use {@link DefaultHttpServerIODispatch#DefaultHttpServerIODispatch(
106     *   NHttpServerEventHandler, ConnectionConfig)}
107     */
108    @Deprecated
109    public DefaultHttpServerIODispatch(
110            final NHttpServerEventHandler handler,
111            final HttpParams params) {
112        this(handler, new DefaultNHttpServerConnectionFactory(params));
113    }
114
115    /**
116     * @deprecated (4.3) use {@link DefaultHttpServerIODispatch#DefaultHttpServerIODispatch(
117     *   NHttpServerEventHandler, SSLContext, SSLSetupHandler, ConnectionConfig)}
118     */
119    @Deprecated
120    public DefaultHttpServerIODispatch(
121            final NHttpServerEventHandler handler,
122            final SSLContext sslContext,
123            final SSLSetupHandler sslHandler,
124            final HttpParams params) {
125        this(handler, new SSLNHttpServerConnectionFactory(sslContext, sslHandler, params));
126    }
127
128    /**
129     * @deprecated (4.3) use {@link DefaultHttpServerIODispatch#DefaultHttpServerIODispatch(
130     *   NHttpServerEventHandler, SSLContext, ConnectionConfig)}
131     */
132    @Deprecated
133    public DefaultHttpServerIODispatch(
134            final NHttpServerEventHandler handler,
135            final SSLContext sslContext,
136            final HttpParams params) {
137        this(handler, sslContext, null, params);
138    }
139
140    /**
141     * @since 4.3
142     */
143    public DefaultHttpServerIODispatch(final NHttpServerEventHandler handler, final ConnectionConfig config) {
144        this(handler, new DefaultNHttpServerConnectionFactory(config));
145    }
146
147    /**
148     * @since 4.3
149     */
150    public DefaultHttpServerIODispatch(
151            final NHttpServerEventHandler handler,
152            final SSLContext sslContext,
153            final SSLSetupHandler sslHandler,
154            final ConnectionConfig config) {
155        this(handler, new SSLNHttpServerConnectionFactory(sslContext, sslHandler, config));
156    }
157
158    /**
159     * @since 4.3
160     */
161    public DefaultHttpServerIODispatch(
162            final NHttpServerEventHandler handler,
163            final SSLContext sslContext,
164            final ConnectionConfig config) {
165        this(handler, new SSLNHttpServerConnectionFactory(sslContext, null, config));
166    }
167
168    @Override
169    protected DefaultNHttpServerConnection createConnection(final IOSession session) {
170        return this.connFactory.createConnection(session);
171    }
172
173    @Override
174    protected void onConnected(final DefaultNHttpServerConnection conn) {
175        try {
176            this.handler.connected(conn);
177        } catch (final Exception ex) {
178            this.handler.exception(conn, ex);
179        }
180    }
181
182    @Override
183    protected void onClosed(final DefaultNHttpServerConnection conn) {
184        this.handler.closed(conn);
185    }
186
187    @Override
188    protected void onException(final DefaultNHttpServerConnection conn, final IOException ex) {
189        this.handler.exception(conn, ex);
190    }
191
192    @Override
193    protected void onInputReady(final DefaultNHttpServerConnection conn) {
194        conn.consumeInput(this.handler);
195    }
196
197    @Override
198    protected void onOutputReady(final DefaultNHttpServerConnection conn) {
199        conn.produceOutput(this.handler);
200    }
201
202    @Override
203    protected void onTimeout(final DefaultNHttpServerConnection conn) {
204        try {
205            this.handler.timeout(conn);
206        } catch (final Exception ex) {
207            this.handler.exception(conn, ex);
208        }
209    }
210
211}