/*
 *
 *    Copyright (c) 2021 Project CHIP Authors
 *    All rights reserved.
 *
 *    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.
 */

#pragma once

#include <app/AppBuildConfig.h>
#include <app/AttributePathParams.h>
#include <app/InteractionModelEngine.h>
#include <app/ReadPrepareParams.h>
#include <controller/TypedReadCallback.h>

#if CHIP_CONFIG_ENABLE_READ_CLIENT
namespace chip {
namespace Controller {
namespace detail {

using SubscriptionOnDoneCallback = std::function<void(void)>;

template <typename DecodableAttributeType>
struct ReportAttributeParams : public app::ReadPrepareParams
{
    ReportAttributeParams(const SessionHandle & sessionHandle) : app::ReadPrepareParams(sessionHandle)
    {
        mKeepSubscriptions = false;
    }
    typename TypedReadAttributeCallback<DecodableAttributeType>::OnSuccessCallbackType mOnReportCb;
    typename TypedReadAttributeCallback<DecodableAttributeType>::OnErrorCallbackType mOnErrorCb;
    typename TypedReadAttributeCallback<DecodableAttributeType>::OnSubscriptionEstablishedCallbackType
        mOnSubscriptionEstablishedCb = nullptr;
    typename TypedReadAttributeCallback<DecodableAttributeType>::OnResubscriptionAttemptCallbackType mOnResubscriptionAttemptCb =
        nullptr;
    SubscriptionOnDoneCallback mOnDoneCb         = nullptr;
    app::ReadClient::InteractionType mReportType = app::ReadClient::InteractionType::Read;
};

template <typename DecodableAttributeType>
CHIP_ERROR ReportAttribute(Messaging::ExchangeManager * exchangeMgr, EndpointId endpointId, ClusterId clusterId,
                           AttributeId attributeId, ReportAttributeParams<DecodableAttributeType> && readParams,
                           const Optional<DataVersion> & aDataVersion = NullOptional)
{
    app::InteractionModelEngine * engine = app::InteractionModelEngine::GetInstance();
    CHIP_ERROR err                       = CHIP_NO_ERROR;

    auto readPaths = Platform::MakeUnique<app::AttributePathParams>(endpointId, clusterId, attributeId);
    VerifyOrReturnError(readPaths != nullptr, CHIP_ERROR_NO_MEMORY);
    readParams.mpAttributePathParamsList    = readPaths.get();
    readParams.mAttributePathParamsListSize = 1;
    chip::Platform::UniquePtr<chip::app::DataVersionFilter> dataVersionFilters;
    if (aDataVersion.HasValue())
    {
        dataVersionFilters = Platform::MakeUnique<app::DataVersionFilter>(endpointId, clusterId, aDataVersion.Value());
        VerifyOrReturnError(dataVersionFilters != nullptr, CHIP_ERROR_NO_MEMORY);
        readParams.mpDataVersionFilterList    = dataVersionFilters.get();
        readParams.mDataVersionFilterListSize = 1;
    }
    auto onDoneCb = readParams.mOnDoneCb;
    auto onDone   = [onDoneCb](TypedReadAttributeCallback<DecodableAttributeType> * callback) {
        if (onDoneCb)
        {
            onDoneCb();
        }
        chip::Platform::Delete(callback);
    };

    auto callback = chip::Platform::MakeUnique<TypedReadAttributeCallback<DecodableAttributeType>>(
        clusterId, attributeId, readParams.mOnReportCb, readParams.mOnErrorCb, onDone, readParams.mOnSubscriptionEstablishedCb,
        readParams.mOnResubscriptionAttemptCb);
    VerifyOrReturnError(callback != nullptr, CHIP_ERROR_NO_MEMORY);

    auto readClient =
        chip::Platform::MakeUnique<app::ReadClient>(engine, exchangeMgr, callback->GetBufferedCallback(), readParams.mReportType);
    VerifyOrReturnError(readClient != nullptr, CHIP_ERROR_NO_MEMORY);

    if (readClient->IsSubscriptionType())
    {
        readPaths.release();
        dataVersionFilters.release();

        err = readClient->SendAutoResubscribeRequest(std::move(readParams));
        ReturnErrorOnFailure(err);
    }
    else
    {
        err = readClient->SendRequest(readParams);
        ReturnErrorOnFailure(err);
    }

    //
    // At this point, we'll get a callback through the OnDone callback above regardless of success or failure
    // of the read operation to permit us to free up the callback object. So, release ownership of the callback
    // object now to prevent it from being reclaimed at the end of this scoped block.
    //
    callback->AdoptReadClient(std::move(readClient));
    callback.release();

    return err;
}

} // namespace detail

/**
 * To avoid instantiating all the complicated read code on a per-attribute
 * basis, we have a helper that's just templated on the type.
 */
template <typename DecodableAttributeType>
CHIP_ERROR ReadAttribute(Messaging::ExchangeManager * exchangeMgr, const SessionHandle & sessionHandle, EndpointId endpointId,
                         ClusterId clusterId, AttributeId attributeId,
                         typename TypedReadAttributeCallback<DecodableAttributeType>::OnSuccessCallbackType onSuccessCb,
                         typename TypedReadAttributeCallback<DecodableAttributeType>::OnErrorCallbackType onErrorCb,
                         bool fabricFiltered = true)
{
    detail::ReportAttributeParams<DecodableAttributeType> params(sessionHandle);
    params.mOnReportCb       = onSuccessCb;
    params.mOnErrorCb        = onErrorCb;
    params.mIsFabricFiltered = fabricFiltered;
    return detail::ReportAttribute(exchangeMgr, endpointId, clusterId, attributeId, std::move(params), NullOptional);
}

/*
 * A typed read attribute function that takes as input a template parameter that encapsulates the type information
 * for a given attribute as well as callbacks for success and failure and either returns a decoded cluster-object representation
 * of the requested attribute through the provided success callback or calls the provided failure callback.
 *
 * The AttributeTypeInfo is generally expected to be a ClusterName::Attributes::AttributeName::TypeInfo struct, but any
 * object that contains type information exposed through a 'DecodableType' type declaration as well as GetClusterId() and
 * GetAttributeId() methods is expected to work.
 */
template <typename AttributeTypeInfo>
CHIP_ERROR
ReadAttribute(Messaging::ExchangeManager * exchangeMgr, const SessionHandle & sessionHandle, EndpointId endpointId,
              typename TypedReadAttributeCallback<typename AttributeTypeInfo::DecodableType>::OnSuccessCallbackType onSuccessCb,
              typename TypedReadAttributeCallback<typename AttributeTypeInfo::DecodableType>::OnErrorCallbackType onErrorCb,
              bool fabricFiltered = true)
{
    return ReadAttribute<typename AttributeTypeInfo::DecodableType>(
        exchangeMgr, sessionHandle, endpointId, AttributeTypeInfo::GetClusterId(), AttributeTypeInfo::GetAttributeId(), onSuccessCb,
        onErrorCb, fabricFiltered);
}

// Helper for SubscribeAttribute to reduce the amount of code generated.
template <typename DecodableAttributeType>
CHIP_ERROR SubscribeAttribute(
    Messaging::ExchangeManager * exchangeMgr, const SessionHandle & sessionHandle, EndpointId endpointId, ClusterId clusterId,
    AttributeId attributeId, typename TypedReadAttributeCallback<DecodableAttributeType>::OnSuccessCallbackType onReportCb,
    typename TypedReadAttributeCallback<DecodableAttributeType>::OnErrorCallbackType onErrorCb, uint16_t minIntervalFloorSeconds,
    uint16_t maxIntervalCeilingSeconds,
    typename TypedReadAttributeCallback<DecodableAttributeType>::OnSubscriptionEstablishedCallbackType onSubscriptionEstablishedCb =
        nullptr,
    typename TypedReadAttributeCallback<DecodableAttributeType>::OnResubscriptionAttemptCallbackType onResubscriptionAttemptCb =
        nullptr,
    bool fabricFiltered = true, bool keepPreviousSubscriptions = false, const Optional<DataVersion> & aDataVersion = NullOptional,
    typename detail::SubscriptionOnDoneCallback onDoneCb = nullptr)
{
    detail::ReportAttributeParams<DecodableAttributeType> params(sessionHandle);
    params.mOnReportCb                  = onReportCb;
    params.mOnErrorCb                   = onErrorCb;
    params.mOnSubscriptionEstablishedCb = onSubscriptionEstablishedCb;
    params.mOnResubscriptionAttemptCb   = onResubscriptionAttemptCb;
    params.mOnDoneCb                    = onDoneCb;
    params.mMinIntervalFloorSeconds     = minIntervalFloorSeconds;
    params.mMaxIntervalCeilingSeconds   = maxIntervalCeilingSeconds;
    params.mKeepSubscriptions           = keepPreviousSubscriptions;
    params.mReportType                  = app::ReadClient::InteractionType::Subscribe;
    params.mIsFabricFiltered            = fabricFiltered;
    return detail::ReportAttribute(exchangeMgr, endpointId, clusterId, attributeId, std::move(params), aDataVersion);
}

/*
 * A typed way to subscribe to the value of a single attribute.  See
 * documentation for ReadAttribute above for details on how AttributeTypeInfo
 * works.
 *
 * A const view-only reference to the underlying ReadClient is passed in through the OnSubscriptionEstablishedCallbackType
 * argument. This reference is valid until the error callback is invoked at which point, this reference is no longer valid
 * and should not be used any more.
 */
template <typename AttributeTypeInfo>
CHIP_ERROR SubscribeAttribute(
    Messaging::ExchangeManager * exchangeMgr, const SessionHandle & sessionHandle, EndpointId endpointId,
    typename TypedReadAttributeCallback<typename AttributeTypeInfo::DecodableType>::OnSuccessCallbackType onReportCb,
    typename TypedReadAttributeCallback<typename AttributeTypeInfo::DecodableType>::OnErrorCallbackType onErrorCb,
    uint16_t aMinIntervalFloorSeconds, uint16_t aMaxIntervalCeilingSeconds,
    typename TypedReadAttributeCallback<typename AttributeTypeInfo::DecodableType>::OnSubscriptionEstablishedCallbackType
        onSubscriptionEstablishedCb = nullptr,
    typename TypedReadAttributeCallback<typename AttributeTypeInfo::DecodableType>::OnResubscriptionAttemptCallbackType
        onResubscriptionAttemptCb = nullptr,
    bool fabricFiltered = true, bool keepPreviousSubscriptions = false, const Optional<DataVersion> & aDataVersion = NullOptional,
    typename detail::SubscriptionOnDoneCallback onDoneCb = nullptr)
{
    return SubscribeAttribute<typename AttributeTypeInfo::DecodableType>(
        exchangeMgr, sessionHandle, endpointId, AttributeTypeInfo::GetClusterId(), AttributeTypeInfo::GetAttributeId(), onReportCb,
        onErrorCb, aMinIntervalFloorSeconds, aMaxIntervalCeilingSeconds, onSubscriptionEstablishedCb, onResubscriptionAttemptCb,
        fabricFiltered, keepPreviousSubscriptions, aDataVersion, onDoneCb);
}

namespace detail {

template <typename DecodableEventType>
struct ReportEventParams : public app::ReadPrepareParams
{
    ReportEventParams(const SessionHandle & sessionHandle) : app::ReadPrepareParams(sessionHandle) {}
    typename TypedReadEventCallback<DecodableEventType>::OnSuccessCallbackType mOnReportCb;
    typename TypedReadEventCallback<DecodableEventType>::OnErrorCallbackType mOnErrorCb;
    typename TypedReadEventCallback<DecodableEventType>::OnDoneCallbackType mOnDoneCb;
    typename TypedReadEventCallback<DecodableEventType>::OnSubscriptionEstablishedCallbackType mOnSubscriptionEstablishedCb =
        nullptr;
    typename TypedReadEventCallback<DecodableEventType>::OnResubscriptionAttemptCallbackType mOnResubscriptionAttemptCb = nullptr;
    app::ReadClient::InteractionType mReportType = app::ReadClient::InteractionType::Read;
};

template <typename DecodableEventType>
CHIP_ERROR ReportEvent(Messaging::ExchangeManager * apExchangeMgr, EndpointId endpointId,
                       ReportEventParams<DecodableEventType> && readParams, bool aIsUrgentEvent)
{
    ClusterId clusterId                  = DecodableEventType::GetClusterId();
    EventId eventId                      = DecodableEventType::GetEventId();
    app::InteractionModelEngine * engine = app::InteractionModelEngine::GetInstance();
    CHIP_ERROR err                       = CHIP_NO_ERROR;

    auto readPaths = Platform::MakeUnique<app::EventPathParams>(endpointId, clusterId, eventId, aIsUrgentEvent);
    VerifyOrReturnError(readPaths != nullptr, CHIP_ERROR_NO_MEMORY);

    readParams.mpEventPathParamsList = readPaths.get();

    readParams.mEventPathParamsListSize = 1;

    auto callback = chip::Platform::MakeUnique<TypedReadEventCallback<DecodableEventType>>(
        readParams.mOnReportCb, readParams.mOnErrorCb, readParams.mOnDoneCb, readParams.mOnSubscriptionEstablishedCb,
        readParams.mOnResubscriptionAttemptCb);

    VerifyOrReturnError(callback != nullptr, CHIP_ERROR_NO_MEMORY);

    auto readClient = chip::Platform::MakeUnique<app::ReadClient>(engine, apExchangeMgr, *callback.get(), readParams.mReportType);
    VerifyOrReturnError(readClient != nullptr, CHIP_ERROR_NO_MEMORY);

    if (readClient->IsSubscriptionType())
    {
        readPaths.release();
        err = readClient->SendAutoResubscribeRequest(std::move(readParams));
        ReturnErrorOnFailure(err);
    }
    else
    {
        err = readClient->SendRequest(readParams);
        ReturnErrorOnFailure(err);
    }

    //
    // At this point, we'll get a callback through the OnDone callback above regardless of success or failure
    // of the read operation to permit us to free up the callback object. So, release ownership of the callback
    // object now to prevent it from being reclaimed at the end of this scoped block.
    //
    callback->AdoptReadClient(std::move(readClient));
    callback.release();

    return err;
}

} // namespace detail

/*
 * A typed read event function that takes as input a template parameter that encapsulates the type information
 * for a given attribute as well as callbacks for success and failure and either returns a decoded cluster-object representation
 * of the requested attribute through the provided success callback or calls the provided failure callback.
 *
 * The DecodableEventType is generally expected to be a ClusterName::Events::EventName::DecodableEventType struct, but any
 * object that contains type information exposed through a 'DecodableType' type declaration as well as GetClusterId() and
 * GetEventId() methods is expected to work.
 *
 * @param[in] onSuccessCb Used to deliver event data received through the Read interactions
 * @param[in] onErrorCb failureCb will be called when an error occurs *after* a successful call to ReadEvent.
 * @param[in] onDoneCb    OnDone will be called when ReadClient has finished all work for event retrieval, it is possible that there
 * is no event.
 */
template <typename DecodableEventType>
CHIP_ERROR ReadEvent(Messaging::ExchangeManager * exchangeMgr, const SessionHandle & sessionHandle, EndpointId endpointId,
                     typename TypedReadEventCallback<DecodableEventType>::OnSuccessCallbackType onSuccessCb,
                     typename TypedReadEventCallback<DecodableEventType>::OnErrorCallbackType onErrorCb,
                     typename TypedReadEventCallback<DecodableEventType>::OnDoneCallbackType onDoneCb)
{
    detail::ReportEventParams<DecodableEventType> params(sessionHandle);
    params.mOnReportCb = onSuccessCb;
    params.mOnErrorCb  = onErrorCb;
    params.mOnDoneCb   = onDoneCb;
    return detail::ReportEvent(exchangeMgr, endpointId, std::move(params), false /*aIsUrgentEvent*/);
}

/**
 * A functon that allows subscribing to one particular event.  This works
 * similarly to ReadEvent but keeps reporting events as they are emitted.
 */
template <typename DecodableEventType>
CHIP_ERROR SubscribeEvent(
    Messaging::ExchangeManager * exchangeMgr, const SessionHandle & sessionHandle, EndpointId endpointId,
    typename TypedReadEventCallback<DecodableEventType>::OnSuccessCallbackType onReportCb,
    typename TypedReadEventCallback<DecodableEventType>::OnErrorCallbackType onErrorCb, uint16_t minIntervalFloorSeconds,
    uint16_t maxIntervalCeilingSeconds,
    typename TypedReadEventCallback<DecodableEventType>::OnSubscriptionEstablishedCallbackType onSubscriptionEstablishedCb =
        nullptr,
    typename TypedReadEventCallback<DecodableEventType>::OnResubscriptionAttemptCallbackType onResubscriptionAttemptCb = nullptr,
    bool keepPreviousSubscriptions = false, bool aIsUrgentEvent = false)
{
    detail::ReportEventParams<DecodableEventType> params(sessionHandle);
    params.mOnReportCb                  = onReportCb;
    params.mOnErrorCb                   = onErrorCb;
    params.mOnDoneCb                    = nullptr;
    params.mOnSubscriptionEstablishedCb = onSubscriptionEstablishedCb;
    params.mOnResubscriptionAttemptCb   = onResubscriptionAttemptCb;
    params.mMinIntervalFloorSeconds     = minIntervalFloorSeconds;
    params.mMaxIntervalCeilingSeconds   = maxIntervalCeilingSeconds;
    params.mKeepSubscriptions           = keepPreviousSubscriptions;
    params.mReportType                  = app::ReadClient::InteractionType::Subscribe;
    return detail::ReportEvent(exchangeMgr, endpointId, std::move(params), aIsUrgentEvent);
}

} // namespace Controller
} // namespace chip
#endif // CHIP_CONFIG_ENABLE_READ_CLIENT
