/*
 *
 *    Copyright (c) 2020 Project CHIP Authors
 *
 *    Licensed 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.
 */

/**
 *    @file
 *      This file defines the classes corresponding to CHIP Exchange Context Delegate.
 *
 */

#pragma once

#include <lib/support/CHIPMem.h>
#include <messaging/ApplicationExchangeDispatch.h>
#include <messaging/ExchangeMessageDispatch.h>
#include <system/SystemPacketBuffer.h>
#include <transport/SessionManager.h>
#include <transport/raw/MessageHeader.h>

namespace chip {
namespace Messaging {

class ExchangeContext;

/**
 * @brief
 *   This class provides a skeleton for the callback functions. The functions will be
 *   called by ExchangeContext object on specific events. If the user of ExchangeContext
 *   is interested in receiving these callbacks, they can specialize this class and handle
 *   each trigger in their implementation of this class.
 *
 *   For consumers who use an ExchangeContext to send/receive protocol messages, there are specific
 *   expectations around who manages the exchange w.r.t clean-up and destruction:
 *     1. When you allocate an exchange, you own the exchange. Until you send a message successfully, it's on you
 *        to release that ownership by calling Close or Abort on the exchange.
 *
 *     2. If you send a message successfully that doesn't require a response, the ownership transfers to
 *        the ExchangeMgr, and it will close the exchange for you automatically.
 *
 *     3. If you send a message successfully that does require a response and desire to close it before
 *        you get any notifications on that exchange from the ExchangeMgr, you should call Close or Abort on that exchange.
 *
 *     4. On reception of a message on an exchange, the ownership transfers to the OnMessageReceived callee.
 *        If you return from OnMessageReceived and no messages were sent on that exchange, the exchange will transfer back
 *        to the ExchangeMgr and it will automatically close it.
 *
 *     5. If you call WillSendMessage on the exchange in OnMessageReceived indicating a desire to send a message later
 *        on the exchange, then the exchange remains with you, and it's your responsibility to either send a message on it,
 *        or Close/Abort if you no longer wish to have the exchange around.
 *
 *     6. If you get a call to OnExchangeClosing, you should null out your reference to the exchange UNLESS you still
 *        hold ownership of the exchange (i.e due to a prior call to WillSendMessage). In that case, you should call Abort/Close
 *        whenever you're done with using the exchange. Those calls can be made synchronously within the OnExchangeClosing
 *        callback.
 *
 *     7. If you get a call to OnResponseTimeout, you should null out your reference to the exchange since the exchange layer
 *        owns the exchange and will handle releasing the ref later. A call to OnExchangeClosing will follow after.
 *
 */
class DLL_EXPORT ExchangeDelegate
{
public:
    virtual ~ExchangeDelegate() {}

    /**
     * @brief
     *   This function is the protocol callback for handling a received CHIP
     *   message.
     *
     *   After calling this method an exchange will close itself unless one of
     *   two things happens:
     *
     *   1) A call to SendMessage on the exchange with the kExpectResponse flag
     *      set.
     *   2) A call to WillSendMessage on the exchange.
     *
     *   Consumers that don't do one of those things MUST NOT retain a pointer
     *   to the exchange.
     *
     *  @param[in]    ec            A pointer to the ExchangeContext object.
     *  @param[in]    payloadHeader A reference to the PayloadHeader object.
     *  @param[in]    payload       A handle to the PacketBuffer object holding the message payload.
     */
    virtual CHIP_ERROR OnMessageReceived(ExchangeContext * ec, const PayloadHeader & payloadHeader,
                                         System::PacketBufferHandle && payload) = 0;

    /**
     * @brief
     *   This function is the protocol callback to invoke when the timeout for the receipt
     *   of a response message has expired.
     *
     *   After calling this method an exchange will close itself unless one of
     *   two things happens:
     *
     *   1) A call to SendMessage on the exchange with the kExpectResponse flag
     *      set.
     *   2) A call to WillSendMessage on the exchange.
     *
     *   Consumers that don't do one of those things MUST NOT retain a pointer
     *   to the exchange.
     *
     *  @param[in]    ec            A pointer to the ExchangeContext object.
     */
    virtual void OnResponseTimeout(ExchangeContext * ec) = 0;

    /**
     * @brief
     *   This function is the protocol callback to invoke when the associated
     *   exchange context is being closed.
     *
     *   If the exchange was in a state where it was expecting a message to be
     *   sent due to an earlier WillSendMessage call or because the exchange has
     *   just been created as an initiator, the consumer is holding a reference
     *   to the exchange and it's the consumer's responsibility to call
     *   Release() on the exchange at some point.  The usual way this happens is
     *   that the consumer tries to send its message, that fails, and the
     *   consumer calls Close() on the exchange.  Calling Close() after an
     *   OnExchangeClosing() notification is allowed in this situation.
     *
     *  @param[in]    ec            A pointer to the ExchangeContext object.
     */
    virtual void OnExchangeClosing(ExchangeContext * ec) {}

    virtual ExchangeMessageDispatch & GetMessageDispatch() { return ApplicationExchangeDispatch::Instance(); }
};

/**
 * @brief
 *   This class handles unsolicited messages. The implementation can select an exchange delegate to use based on the payload header
 * of the incoming message.
 */
class DLL_EXPORT UnsolicitedMessageHandler
{
public:
    virtual ~UnsolicitedMessageHandler() {}

    /**
     * @brief
     *   This function handles an unsolicited CHIP message.
     *
     *   If the implementation returns CHIP_NO_ERROR, it is expected to set newDelegate to the delegate to use for the exchange
     *   handling the message.  The message layer will handle creating the exchange with this delegate.
     *
     *   If the implementation returns an error, message processing will be aborted for this message.
     *
     *  @param[in]  payloadHeader A reference to the PayloadHeader object for the unsolicited message.  The protocol and message
     *                            type of this header match the UnsolicitedMessageHandler.
     *  @param[out] newDelegate   A new exchange delegate to be used by the new exchange created to handle the message.
     */
    virtual CHIP_ERROR OnUnsolicitedMessageReceived(const PayloadHeader & payloadHeader, ExchangeDelegate *& newDelegate) = 0;

    /**
     * @brief
     *   This function is called when OnUnsolicitedMessageReceived successfully returns a new delegate, but the session manager
     *   fails to assign the delegate to a new exchange.  It can be used to free the delegate as needed.
     *
     *   Once an exchange is created with the delegate, the OnExchangeClosing notification can be used to free the delegate as
     *   needed.
     *
     *  @param[in] delegate   The exchange delegate to be released.
     */
    virtual void OnExchangeCreationFailed(ExchangeDelegate * delegate) {}
};

} // namespace Messaging
} // namespace chip
