/*
 * ====================================================================
 * Licensed to the Apache Software Foundation (ASF) under one
 * or more contributor license agreements.  See the NOTICE file
 * distributed with this work for additional information
 * regarding copyright ownership.  The ASF licenses this file
 * to you under the Apache License, Version 2.0 (the
 * "License"); you may not use this file except in compliance
 * with the License.  You may obtain a copy of the License at
 *
 *   http://www.apache.org/licenses/LICENSE-2.0
 *
 * Unless required by applicable law or agreed to in writing,
 * software distributed under the License is distributed on an
 * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
 * KIND, either express or implied.  See the License for the
 * specific language governing permissions and limitations
 * under the License.
 * ====================================================================
 *
 * This software consists of voluntary contributions made by many
 * individuals on behalf of the Apache Software Foundation.  For more
 * information on the Apache Software Foundation, please see
 * <http://www.apache.org/>.
 *
 */
package org.apache.hc.core5.http2.nio.pool;

import java.net.InetSocketAddress;
import java.util.concurrent.Future;

import org.apache.hc.core5.annotation.Contract;
import org.apache.hc.core5.annotation.ThreadingBehavior;
import org.apache.hc.core5.concurrent.CallbackContribution;
import org.apache.hc.core5.concurrent.FutureCallback;
import org.apache.hc.core5.function.Callback;
import org.apache.hc.core5.function.Resolver;
import org.apache.hc.core5.http.HttpHost;
import org.apache.hc.core5.http.URIScheme;
import org.apache.hc.core5.http.impl.DefaultAddressResolver;
import org.apache.hc.core5.http.nio.command.ShutdownCommand;
import org.apache.hc.core5.http.nio.ssl.TlsStrategy;
import org.apache.hc.core5.http2.nio.command.PingCommand;
import org.apache.hc.core5.http2.nio.support.BasicPingHandler;
import org.apache.hc.core5.io.CloseMode;
import org.apache.hc.core5.reactor.AbstractIOSessionPool;
import org.apache.hc.core5.reactor.Command;
import org.apache.hc.core5.reactor.ConnectionInitiator;
import org.apache.hc.core5.reactor.IOSession;
import org.apache.hc.core5.reactor.ssl.TransportSecurityLayer;
import org.apache.hc.core5.util.Args;
import org.apache.hc.core5.util.TimeValue;
import org.apache.hc.core5.util.Timeout;

/**
 * Pool of HTTP/2 message multiplexing capable connections.
 *
 * @since 5.0
 */
@Contract(threading = ThreadingBehavior.SAFE)
public final class H2ConnPool extends AbstractIOSessionPool<HttpHost> {

    private final ConnectionInitiator connectionInitiator;
    private final Resolver<HttpHost, InetSocketAddress> addressResolver;
    private final TlsStrategy tlsStrategy;

    private volatile TimeValue validateAfterInactivity = TimeValue.NEG_ONE_MILLISECOND;

    public H2ConnPool(
            final ConnectionInitiator connectionInitiator,
            final Resolver<HttpHost, InetSocketAddress> addressResolver,
            final TlsStrategy tlsStrategy) {
        super();
        this.connectionInitiator = Args.notNull(connectionInitiator, "Connection initiator");
        this.addressResolver = addressResolver != null ? addressResolver : DefaultAddressResolver.INSTANCE;
        this.tlsStrategy = tlsStrategy;
    }

    public TimeValue getValidateAfterInactivity() {
        return validateAfterInactivity;
    }

    public void setValidateAfterInactivity(final TimeValue timeValue) {
        this.validateAfterInactivity = timeValue;
    }

    @Override
    protected void closeSession(
            final IOSession ioSession,
            final CloseMode closeMode) {
        if (closeMode == CloseMode.GRACEFUL) {
            ioSession.enqueue(ShutdownCommand.GRACEFUL, Command.Priority.NORMAL);
        } else {
            ioSession.close(closeMode);
        }
    }

    @Override
    protected Future<IOSession> connectSession(
            final HttpHost namedEndpoint,
            final Timeout connectTimeout,
            final FutureCallback<IOSession> callback) {
        final InetSocketAddress remoteAddress = addressResolver.resolve(namedEndpoint);
        return connectionInitiator.connect(
                namedEndpoint,
                remoteAddress,
                null,
                connectTimeout,
                null,
                new CallbackContribution<IOSession>(callback) {

                    @Override
                    public void completed(final IOSession ioSession) {
                        if (tlsStrategy != null
                                && URIScheme.HTTPS.same(namedEndpoint.getSchemeName())
                                && ioSession instanceof TransportSecurityLayer) {
                            tlsStrategy.upgrade(
                                    (TransportSecurityLayer) ioSession,
                                    namedEndpoint,
                                    ioSession.getLocalAddress(),
                                    ioSession.getRemoteAddress(),
                                    null,
                                    connectTimeout);
                            ioSession.setSocketTimeout(connectTimeout);
                        }
                        callback.completed(ioSession);
                    }

                });
    }

    @Override
    protected void validateSession(
            final IOSession ioSession,
            final Callback<Boolean> callback) {
        final TimeValue timeValue = validateAfterInactivity;
        if (TimeValue.isNonNegative(timeValue)) {
            final long lastAccessTime = Math.min(ioSession.getLastReadTime(), ioSession.getLastWriteTime());
            final long deadline = lastAccessTime + timeValue.toMilliseconds();
            if (deadline <= System.currentTimeMillis()) {
                final Timeout socketTimeoutMillis = ioSession.getSocketTimeout();
                ioSession.enqueue(new PingCommand(new BasicPingHandler(result -> {
                    ioSession.setSocketTimeout(socketTimeoutMillis);
                    callback.execute(result);
                })), Command.Priority.NORMAL);
                return;
            }
        }
        callback.execute(true);
    }

}
