/**
 *
 *    Copyright (c) 2021 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.
 */

#include "MediaPlaybackManager.h"
#include "TvApp-JNI.h"
#include <app-common/zap-generated/attributes/Accessors.h>
#include <app-common/zap-generated/ids/Clusters.h>
#include <app/util/config.h>
#include <cstdint>
#include <jni.h>
#include <lib/support/CHIPJNIError.h>
#include <lib/support/JniReferences.h>
#include <lib/support/JniTypeWrappers.h>

#include "MediaPlaybackManager.h"

#include <string>

using namespace chip;
using namespace chip::app;
using namespace chip::app::DataModel;
using namespace chip::app::Clusters::MediaPlayback;
using namespace chip::Uint8;
using chip::CharSpan;

/** @brief Media PlayBack Cluster Init
 *
 * This function is called when a specific cluster is initialized. It gives the
 * application an opportunity to take care of cluster initialization procedures.
 * It is called exactly once for each endpoint where cluster is present.
 *
 * @param endpoint   Ver.: always
 *
 */
void emberAfMediaPlaybackClusterInitCallback(chip::EndpointId endpoint)
{
    ChipLogProgress(Zcl, "TV Android App: MediaPlayback::PostClusterInit");
    TvAppJNIMgr().PostClusterInit(chip::app::Clusters::MediaPlayback::Id, endpoint);
}

void MediaPlaybackManager::NewManager(jint endpoint, jobject manager)
{
    ChipLogProgress(Zcl, "TV Android App: MediaPlayback::SetDefaultDelegate");
    MediaPlaybackManager * mgr = new MediaPlaybackManager();
    mgr->InitializeWithObjects(manager);
    chip::app::Clusters::MediaPlayback::SetDefaultDelegate(static_cast<EndpointId>(endpoint), mgr);
}

PlaybackStateEnum MediaPlaybackManager::HandleGetCurrentState()
{
    uint64_t ret = HandleMediaRequestGetAttribute(MEDIA_PLAYBACK_ATTRIBUTE_PLAYBACK_STATE);
    return static_cast<PlaybackStateEnum>(ret);
}

uint64_t MediaPlaybackManager::HandleGetStartTime()
{
    return HandleMediaRequestGetAttribute(MEDIA_PLAYBACK_ATTRIBUTE_START_TIME);
}

uint64_t MediaPlaybackManager::HandleGetDuration()
{
    return HandleMediaRequestGetAttribute(MEDIA_PLAYBACK_ATTRIBUTE_DURATION);
}

float MediaPlaybackManager::HandleGetPlaybackSpeed()
{
    long ret = HandleMediaRequestGetLongAttribute(MEDIA_PLAYBACK_ATTRIBUTE_SPEED);
    return static_cast<float>(ret);
}

uint64_t MediaPlaybackManager::HandleGetSeekRangeStart()
{
    return HandleMediaRequestGetAttribute(MEDIA_PLAYBACK_ATTRIBUTE_SEEK_RANGE_START);
}

uint64_t MediaPlaybackManager::HandleGetSeekRangeEnd()
{
    return HandleMediaRequestGetAttribute(MEDIA_PLAYBACK_ATTRIBUTE_SEEK_RANGE_END);
}

CHIP_ERROR MediaPlaybackManager::HandleGetActiveAudioTrack(AttributeValueEncoder & aEncoder)
{
    return HandleGetActiveTrack(true, aEncoder);
}

CHIP_ERROR MediaPlaybackManager::HandleGetActiveTrack(bool audio, AttributeValueEncoder & aEncoder)
{
    DeviceLayer::StackUnlock unlock;
    Structs::TrackStruct::Type response;
    Structs::TrackAttributesStruct::Type trackAttributes;
    response.trackAttributes = Nullable<Structs::TrackAttributesStruct::Type>(trackAttributes);

    jobject trackObj;
    CHIP_ERROR err = CHIP_NO_ERROR;
    JNIEnv * env   = JniReferences::GetInstance().GetEnvForCurrentThread();
    VerifyOrReturnError(env != nullptr, CHIP_JNI_ERROR_NULL_OBJECT, ChipLogError(Zcl, "Could not get JNIEnv for current thread"));
    JniLocalReferenceScope scope(env);

    ChipLogProgress(Zcl, "MediaPlaybackManager::HandleGetActiveAudioTrack");
    VerifyOrExit(mMediaPlaybackManagerObject.HasValidObjectRef(), err = CHIP_ERROR_INCORRECT_STATE);
    VerifyOrExit(mGetActiveTrackMethod != nullptr, err = CHIP_ERROR_INCORRECT_STATE);

    env->ExceptionClear();
    trackObj = env->CallObjectMethod(mMediaPlaybackManagerObject.ObjectRef(), mGetActiveTrackMethod, static_cast<jboolean>(audio));
    if (env->ExceptionCheck())
    {
        ChipLogError(AppServer, "Java exception in MediaPlaybackManager::HandleGetActiveAudioTrack");
        env->ExceptionDescribe();
        env->ExceptionClear();
        goto exit;
    }

    if (trackObj != nullptr)
    {
        jclass trackClass   = env->GetObjectClass(trackObj);
        jfieldID getIdField = env->GetFieldID(trackClass, "id", "Ljava/lang/String;");
        jstring jid         = static_cast<jstring>(env->GetObjectField(trackObj, getIdField));
        JniUtfString id(env, jid);
        if (jid != nullptr)
        {
            response.id = id.charSpan();
        }

        jfieldID getLanguageCodeField = env->GetFieldID(trackClass, "languageCode", "Ljava/lang/String;");
        jstring jlanguagecode         = static_cast<jstring>(env->GetObjectField(trackObj, getLanguageCodeField));
        JniUtfString languageCode(env, jlanguagecode);
        if (jlanguagecode != nullptr)
        {
            trackAttributes.languageCode = languageCode.charSpan();
        }

        jfieldID getDisplayNameField = env->GetFieldID(trackClass, "displayName", "Ljava/lang/String;");
        jstring jdisplayname         = static_cast<jstring>(env->GetObjectField(trackObj, getDisplayNameField));
        JniUtfString displayName(env, jdisplayname);
        if (jdisplayname != nullptr)
        {
            trackAttributes.displayName = Optional<chip::app::DataModel::Nullable<chip::Span<const char>>>(
                Nullable<chip::Span<const char>>(displayName.charSpan()));
        }
    }
    else
    {
        return aEncoder.EncodeNull();
    }

exit:
    if (err != CHIP_NO_ERROR)
    {
        ChipLogError(Zcl, "MediaPlaybackManager::HandleGetActiveAudioTrack status error: %s", err.AsString());
    }

    return aEncoder.Encode(response);
}

CHIP_ERROR MediaPlaybackManager::HandleGetAvailableAudioTracks(AttributeValueEncoder & aEncoder)
{
    return HandleGetAvailableTracks(true, aEncoder);
}

CHIP_ERROR MediaPlaybackManager::HandleGetAvailableTracks(bool audio, AttributeValueEncoder & aEncoder)
{
    DeviceLayer::StackUnlock unlock;
    CHIP_ERROR err = CHIP_NO_ERROR;
    JNIEnv * env   = JniReferences::GetInstance().GetEnvForCurrentThread();
    VerifyOrReturnError(env != nullptr, CHIP_JNI_ERROR_NULL_OBJECT, ChipLogError(Zcl, "Could not get JNIEnv for current thread"));
    JniLocalReferenceScope scope(env);

    ChipLogProgress(Zcl, "MediaPlaybackManager::HandleGetAvailableAudioTracks");
    VerifyOrExit(mMediaPlaybackManagerObject.HasValidObjectRef(), err = CHIP_ERROR_INCORRECT_STATE);
    VerifyOrExit(mGetAvailableTracksMethod != nullptr, err = CHIP_ERROR_INCORRECT_STATE);

    env->ExceptionClear();

    return aEncoder.EncodeList([this, env, audio](const auto & encoder) -> CHIP_ERROR {
        jobjectArray trackList = (jobjectArray) env->CallObjectMethod(mMediaPlaybackManagerObject.ObjectRef(),
                                                                      mGetAvailableTracksMethod, static_cast<jboolean>(audio));
        if (env->ExceptionCheck())
        {
            ChipLogError(Zcl, "Java exception in MediaPlaybackManager::HandleGetAvailableAudioTracks");
            env->ExceptionDescribe();
            env->ExceptionClear();
            return CHIP_ERROR_INCORRECT_STATE;
        }

        jint length = env->GetArrayLength(trackList);

        for (jint i = 0; i < length; i++)
        {
            Structs::TrackStruct::Type track;
            Structs::TrackAttributesStruct::Type trackAttributes;
            track.trackAttributes = Nullable<Structs::TrackAttributesStruct::Type>(trackAttributes);

            jobject trackObject = env->GetObjectArrayElement(trackList, i);
            jclass trackClass   = env->GetObjectClass(trackObject);

            jfieldID getIdField = env->GetFieldID(trackClass, "id", "Ljava/lang/String;");
            jstring jid         = static_cast<jstring>(env->GetObjectField(trackObject, getIdField));
            JniUtfString id(env, jid);
            if (jid != nullptr)
            {
                track.id = id.charSpan();
            }

            jfieldID getLanguageCodeField = env->GetFieldID(trackClass, "languageCode", "Ljava/lang/String;");
            jstring jlanguagecode         = static_cast<jstring>(env->GetObjectField(trackObject, getLanguageCodeField));
            JniUtfString languageCode(env, jlanguagecode);
            if (jlanguagecode != nullptr)
            {
                trackAttributes.languageCode = languageCode.charSpan();
            }

            jfieldID getDisplayNameField = env->GetFieldID(trackClass, "displayName", "Ljava/lang/String;");
            jstring jdisplayname         = static_cast<jstring>(env->GetObjectField(trackObject, getDisplayNameField));
            JniUtfString displayName(env, jdisplayname);
            if (jdisplayname != nullptr)
            {
                trackAttributes.displayName = Optional<chip::app::DataModel::Nullable<chip::Span<const char>>>(
                    Nullable<chip::Span<const char>>(displayName.charSpan()));
            }

            ReturnErrorOnFailure(encoder.Encode(track));
        }
        return CHIP_NO_ERROR;
    });

exit:
    if (err != CHIP_NO_ERROR)
    {
        ChipLogError(Zcl, "MediaPlaybackManager::HandleGetAvailableAudioTracks status error: %s", err.AsString());
    }

    return err;
}

CHIP_ERROR MediaPlaybackManager::HandleGetActiveTextTrack(AttributeValueEncoder & aEncoder)
{
    return HandleGetActiveTrack(false, aEncoder);
}

CHIP_ERROR MediaPlaybackManager::HandleGetAvailableTextTracks(AttributeValueEncoder & aEncoder)
{
    return HandleGetAvailableTracks(false, aEncoder);
}

void MediaPlaybackManager::HandlePlay(CommandResponseHelper<Commands::PlaybackResponse::Type> & helper)
{
    helper.Success(HandleMediaRequest(MEDIA_PLAYBACK_REQUEST_PLAY, 0));
}

void MediaPlaybackManager::HandlePause(CommandResponseHelper<Commands::PlaybackResponse::Type> & helper)
{
    helper.Success(HandleMediaRequest(MEDIA_PLAYBACK_REQUEST_PAUSE, 0));
}

void MediaPlaybackManager::HandleStop(CommandResponseHelper<Commands::PlaybackResponse::Type> & helper)
{
    helper.Success(HandleMediaRequest(MEDIA_PLAYBACK_REQUEST_STOP, 0));
}

void MediaPlaybackManager::HandleFastForward(CommandResponseHelper<Commands::PlaybackResponse::Type> & helper,
                                             const chip::Optional<bool> & audioAdvanceUnmuted)
{
    helper.Success(HandleMediaRequest(MEDIA_PLAYBACK_REQUEST_FAST_FORWARD, 0));
}

void MediaPlaybackManager::HandlePrevious(CommandResponseHelper<Commands::PlaybackResponse::Type> & helper)
{
    helper.Success(HandleMediaRequest(MEDIA_PLAYBACK_REQUEST_PREVIOUS, 0));
}

void MediaPlaybackManager::HandleRewind(CommandResponseHelper<Commands::PlaybackResponse::Type> & helper,
                                        const chip::Optional<bool> & audioAdvanceUnmuted)
{
    helper.Success(HandleMediaRequest(MEDIA_PLAYBACK_REQUEST_REWIND, 0));
}

void MediaPlaybackManager::HandleSkipBackward(CommandResponseHelper<Commands::PlaybackResponse::Type> & helper,
                                              const uint64_t & deltaPositionMilliseconds)
{
    helper.Success(HandleMediaRequest(MEDIA_PLAYBACK_REQUEST_SKIP_BACKWARD, deltaPositionMilliseconds));
}

void MediaPlaybackManager::HandleSkipForward(CommandResponseHelper<Commands::PlaybackResponse::Type> & helper,
                                             const uint64_t & deltaPositionMilliseconds)
{
    helper.Success(HandleMediaRequest(MEDIA_PLAYBACK_REQUEST_SKIP_FORWARD, deltaPositionMilliseconds));
}

void MediaPlaybackManager::HandleSeek(CommandResponseHelper<Commands::PlaybackResponse::Type> & helper,
                                      const uint64_t & positionMilliseconds)
{
    helper.Success(HandleMediaRequest(MEDIA_PLAYBACK_REQUEST_SEEK, positionMilliseconds));
}

void MediaPlaybackManager::HandleNext(CommandResponseHelper<Commands::PlaybackResponse::Type> & helper)
{
    helper.Success(HandleMediaRequest(MEDIA_PLAYBACK_REQUEST_NEXT, 0));
}

void MediaPlaybackManager::HandleStartOver(CommandResponseHelper<Commands::PlaybackResponse::Type> & helper)
{
    helper.Success(HandleMediaRequest(MEDIA_PLAYBACK_REQUEST_START_OVER, 0));
}

bool MediaPlaybackManager::HandleActivateAudioTrack(const chip::CharSpan & trackId, const uint8_t & audioOutputIndex)
{
    return HandleActivateTrack(true, trackId);
}

bool MediaPlaybackManager::HandleActivateTrack(bool audio, const chip::CharSpan & trackId)
{
    DeviceLayer::StackUnlock unlock;
    std::string id(trackId.data(), trackId.size());

    jint ret       = -1;
    CHIP_ERROR err = CHIP_NO_ERROR;
    JNIEnv * env   = JniReferences::GetInstance().GetEnvForCurrentThread();
    VerifyOrReturnValue(env != nullptr, false, ChipLogError(Zcl, "Could not get JNIEnv for current thread"));
    JniLocalReferenceScope scope(env);

    ChipLogProgress(Zcl, "MediaPlaybackManager::HandleActivateAudioTrack");
    VerifyOrExit(mMediaPlaybackManagerObject.HasValidObjectRef(), err = CHIP_ERROR_INCORRECT_STATE);
    VerifyOrExit(mActivateTrackMethod != nullptr, err = CHIP_ERROR_INCORRECT_STATE);

    env->ExceptionClear();

    {
        UtfString jniid(env, id.c_str());
        ret = env->CallIntMethod(mMediaPlaybackManagerObject.ObjectRef(), mActivateTrackMethod, static_cast<jboolean>(audio),
                                 jniid.jniValue());
        if (env->ExceptionCheck())
        {
            ChipLogError(AppServer, "Java exception in MediaPlaybackManager::HandleActivateTrack %s", id.c_str());
            env->ExceptionDescribe();
            env->ExceptionClear();
        }
    }
exit:
    return static_cast<int>(ret) == 0;
}

bool MediaPlaybackManager::HandleActivateTextTrack(const chip::CharSpan & trackId)
{
    return HandleActivateTrack(false, trackId);
}

bool MediaPlaybackManager::HandleDeactivateTextTrack()
{
    DeviceLayer::StackUnlock unlock;
    jint ret       = -1;
    CHIP_ERROR err = CHIP_NO_ERROR;
    JNIEnv * env   = JniReferences::GetInstance().GetEnvForCurrentThread();
    VerifyOrReturnValue(env != nullptr, false, ChipLogError(Zcl, "Could not get JNIEnv for current thread"));
    JniLocalReferenceScope scope(env);

    ChipLogProgress(Zcl, "MediaPlaybackManager::HandleDeactivateTextTrack");
    VerifyOrExit(mMediaPlaybackManagerObject.HasValidObjectRef(), err = CHIP_ERROR_INCORRECT_STATE);
    VerifyOrExit(mDeactivateTextTrackMethod != nullptr, err = CHIP_ERROR_INCORRECT_STATE);

    env->ExceptionClear();
    ret = env->CallIntMethod(mMediaPlaybackManagerObject.ObjectRef(), mDeactivateTextTrackMethod);
    if (env->ExceptionCheck())
    {
        ChipLogError(AppServer, "Java exception in MediaPlaybackManager::HandleDeactivateTextTrack");
        env->ExceptionDescribe();
        env->ExceptionClear();
    }
exit:
    return static_cast<int>(ret) == 0;
}

void MediaPlaybackManager::InitializeWithObjects(jobject managerObject)
{
    JNIEnv * env = JniReferences::GetInstance().GetEnvForCurrentThread();
    VerifyOrReturn(env != nullptr, ChipLogError(Zcl, "Failed to GetEnvForCurrentThread for MediaPlaybackManager"));

    VerifyOrReturn(mMediaPlaybackManagerObject.Init(managerObject) == CHIP_NO_ERROR,
                   ChipLogError(Zcl, "Failed to init mMediaPlaybackManagerObject"));

    jclass mMediaPlaybackManagerClass = env->GetObjectClass(managerObject);
    VerifyOrReturn(mMediaPlaybackManagerClass != nullptr, ChipLogError(Zcl, "Failed to get MediaPlaybackManager Java class"));

    mGetAttributeMethod = env->GetMethodID(mMediaPlaybackManagerClass, "getAttributes", "(I)J");
    if (mGetAttributeMethod == nullptr)
    {
        ChipLogError(Zcl, "Failed to access MediaPlaybackManager 'getAttributes' method");
        env->ExceptionClear();
    }

    mRequestMethod = env->GetMethodID(mMediaPlaybackManagerClass, "request", "(IJ)I");
    if (mRequestMethod == nullptr)
    {
        ChipLogError(Zcl, "Failed to access MediaPlaybackManager 'request' method");
        env->ExceptionClear();
    }

    mGetPositionMethod =
        env->GetMethodID(mMediaPlaybackManagerClass, "getPosition", "()Lcom/matter/tv/server/tvapp/MediaPlaybackPosition;");
    if (mGetPositionMethod == nullptr)
    {
        ChipLogError(Zcl, "Failed to access MediaPlaybackManager 'getPosition' method");
        env->ExceptionClear();
    }

    mGetAvailableTracksMethod =
        env->GetMethodID(mMediaPlaybackManagerClass, "getAvailableTracks", "(Z)[Lcom/matter/tv/server/tvapp/MediaTrack;"); // TODO
    if (mGetAvailableTracksMethod == nullptr)
    {
        ChipLogError(Zcl, "Failed to access MediaPlaybackManager 'getAvailableTracks' method");
        env->ExceptionClear();
    }

    mActivateTrackMethod = env->GetMethodID(mMediaPlaybackManagerClass, "activateTrack", "(ZLjava/lang/String;)I");
    if (mActivateTrackMethod == nullptr)
    {
        ChipLogError(Zcl, "Failed to access MediaPlaybackManager 'activateTrack' method");
        env->ExceptionClear();
    }

    mDeactivateTextTrackMethod = env->GetMethodID(mMediaPlaybackManagerClass, "deactivateTextTrack", "()I");
    if (mDeactivateTextTrackMethod == nullptr)
    {
        ChipLogError(Zcl, "Failed to access MediaPlaybackManager 'deactivateTextTrack' method");
        env->ExceptionClear();
    }

    mGetActiveTrackMethod =
        env->GetMethodID(mMediaPlaybackManagerClass, "getActiveTrack", "(Z)Lcom/matter/tv/server/tvapp/MediaTrack;");
    if (mGetActiveTrackMethod == nullptr)
    {
        ChipLogError(Zcl, "Failed to access MediaPlaybackManager 'getActiveTrack' method");
        env->ExceptionClear();
    }
}

uint64_t MediaPlaybackManager::HandleMediaRequestGetAttribute(MediaPlaybackRequestAttribute attribute)
{
    DeviceLayer::StackUnlock unlock;
    uint64_t ret          = std::numeric_limits<uint64_t>::max();
    jlong jAttributeValue = -1;
    CHIP_ERROR err        = CHIP_NO_ERROR;
    JNIEnv * env          = JniReferences::GetInstance().GetEnvForCurrentThread();
    VerifyOrReturnValue(env != nullptr, ret, ChipLogError(Zcl, "Could not get JNIEnv for current thread"));
    JniLocalReferenceScope scope(env);

    ChipLogProgress(Zcl, "Received MediaPlaybackManager::HandleMediaRequestGetAttribute:%d", attribute);
    VerifyOrExit(mMediaPlaybackManagerObject.HasValidObjectRef(), err = CHIP_ERROR_INCORRECT_STATE);
    VerifyOrExit(mGetAttributeMethod != nullptr, err = CHIP_ERROR_INCORRECT_STATE);

    env->ExceptionClear();

    jAttributeValue =
        env->CallLongMethod(mMediaPlaybackManagerObject.ObjectRef(), mGetAttributeMethod, static_cast<jint>(attribute));
    if (env->ExceptionCheck())
    {
        ChipLogError(AppServer, "Java exception in MediaPlaybackManager::GetAttribute");
        env->ExceptionDescribe();
        env->ExceptionClear();
        goto exit;
    }

    if (jAttributeValue >= 0)
    {
        ret = static_cast<uint64_t>(jAttributeValue);
    }
    else
    {
        err = CHIP_ERROR_INCORRECT_STATE;
    }

exit:
    if (err != CHIP_NO_ERROR)
    {
        ChipLogError(Zcl, "MediaPlaybackManager::GetAttribute status error: %s", err.AsString());
    }

    return ret;
}

long MediaPlaybackManager::HandleMediaRequestGetLongAttribute(MediaPlaybackRequestAttribute attribute)
{
    DeviceLayer::StackUnlock unlock;
    long ret              = 0;
    jlong jAttributeValue = -1;
    CHIP_ERROR err        = CHIP_NO_ERROR;
    JNIEnv * env          = JniReferences::GetInstance().GetEnvForCurrentThread();
    VerifyOrReturnValue(env != nullptr, false, ChipLogError(Zcl, "Could not get JNIEnv for current thread"));
    JniLocalReferenceScope scope(env);

    ChipLogProgress(Zcl, "Received MediaPlaybackManager::HandleMediaRequestGetLongAttribute:%d", attribute);
    VerifyOrExit(mMediaPlaybackManagerObject.HasValidObjectRef(), err = CHIP_ERROR_INCORRECT_STATE);
    VerifyOrExit(mGetAttributeMethod != nullptr, err = CHIP_ERROR_INCORRECT_STATE);

    env->ExceptionClear();

    jAttributeValue =
        env->CallLongMethod(mMediaPlaybackManagerObject.ObjectRef(), mGetAttributeMethod, static_cast<jint>(attribute));
    if (env->ExceptionCheck())
    {
        ChipLogError(AppServer, "Java exception in MediaPlaybackManager::GetAttribute");
        env->ExceptionDescribe();
        env->ExceptionClear();
        goto exit;
    }

    ret = static_cast<long>(jAttributeValue);

exit:
    if (err != CHIP_NO_ERROR)
    {
        ChipLogError(Zcl, "MediaPlaybackManager::GetAttribute status error: %s", err.AsString());
    }

    return ret;
}

Commands::PlaybackResponse::Type MediaPlaybackManager::HandleMediaRequest(MediaPlaybackRequest mediaPlaybackRequest,
                                                                          uint64_t deltaPositionMilliseconds)

{
    DeviceLayer::StackUnlock unlock;
    Commands::PlaybackResponse::Type response;

    jint ret       = -1;
    CHIP_ERROR err = CHIP_NO_ERROR;
    JNIEnv * env   = JniReferences::GetInstance().GetEnvForCurrentThread();
    VerifyOrReturnValue(env != nullptr, response, ChipLogError(Zcl, "Could not get JNIEnv for current thread"));
    JniLocalReferenceScope scope(env);

    ChipLogProgress(Zcl, "MediaPlaybackManager::Request %d-%ld", mediaPlaybackRequest,
                    static_cast<long>(deltaPositionMilliseconds));
    VerifyOrExit(mMediaPlaybackManagerObject.HasValidObjectRef(), err = CHIP_ERROR_INCORRECT_STATE);
    VerifyOrExit(mRequestMethod != nullptr, err = CHIP_ERROR_INCORRECT_STATE);

    env->ExceptionClear();
    ret = env->CallIntMethod(mMediaPlaybackManagerObject.ObjectRef(), mRequestMethod, static_cast<jint>(mediaPlaybackRequest),
                             static_cast<jlong>(deltaPositionMilliseconds));
    if (env->ExceptionCheck())
    {
        ChipLogError(AppServer, "Java exception in MediaPlaybackManager::Request %d", mediaPlaybackRequest);
        env->ExceptionDescribe();
        env->ExceptionClear();
        response.status = StatusEnum::kInvalidStateForCommand;
    }
    response.status = static_cast<StatusEnum>(ret);

exit:
    if (err != CHIP_NO_ERROR)
    {
        response.status = StatusEnum::kInvalidStateForCommand;
        ChipLogError(Zcl, "MediaPlaybackManager::HandleMediaRequest status error: %s", err.AsString());
    }

    return response;
}

CHIP_ERROR MediaPlaybackManager::HandleGetSampledPosition(AttributeValueEncoder & aEncoder)
{
    DeviceLayer::StackUnlock unlock;
    Structs::PlaybackPositionStruct::Type response;
    response.updatedAt = 0;
    response.position  = Nullable<uint64_t>(0);

    jobject positionObj;
    CHIP_ERROR err = CHIP_NO_ERROR;
    JNIEnv * env   = JniReferences::GetInstance().GetEnvForCurrentThread();
    VerifyOrReturnError(env != nullptr, CHIP_JNI_ERROR_NULL_OBJECT, ChipLogError(Zcl, "Could not get JNIEnv for current thread"));
    JniLocalReferenceScope scope(env);

    ChipLogProgress(Zcl, "MediaPlaybackManager::HandleGetSampledPosition");
    VerifyOrExit(mMediaPlaybackManagerObject.HasValidObjectRef(), err = CHIP_ERROR_INCORRECT_STATE);
    VerifyOrExit(mGetPositionMethod != nullptr, err = CHIP_ERROR_INCORRECT_STATE);

    env->ExceptionClear();
    positionObj = env->CallObjectMethod(mMediaPlaybackManagerObject.ObjectRef(), mGetPositionMethod);
    if (env->ExceptionCheck())
    {
        ChipLogError(AppServer, "Java exception in MediaPlaybackManager::HandleGetSampledPosition");
        env->ExceptionDescribe();
        env->ExceptionClear();
        goto exit;
    }

    {
        jclass inputClass    = env->GetObjectClass(positionObj);
        jfieldID positionId  = env->GetFieldID(inputClass, "position", "J");
        jfieldID updatedAtId = env->GetFieldID(inputClass, "updatedAt", "J");
        response.position    = Nullable<uint64_t>(static_cast<uint64_t>(env->GetLongField(positionObj, positionId)));
        response.updatedAt   = static_cast<uint64_t>(env->GetLongField(positionObj, updatedAtId));
    }

exit:
    if (err != CHIP_NO_ERROR)
    {
        ChipLogError(Zcl, "MediaPlaybackManager::GetAttribute status error: %" CHIP_ERROR_FORMAT, err.Format());
    }

    return aEncoder.Encode(response);
}

uint32_t MediaPlaybackManager::GetFeatureMap(chip::EndpointId endpoint)
{
    if (endpoint >= MATTER_DM_CONTENT_LAUNCHER_CLUSTER_SERVER_ENDPOINT_COUNT)
    {
        return kEndpointFeatureMap;
    }

    uint32_t featureMap = 0;
    Attributes::FeatureMap::Get(endpoint, &featureMap);
    return featureMap;
}

uint16_t MediaPlaybackManager::GetClusterRevision(chip::EndpointId endpoint)
{
    if (endpoint >= MATTER_DM_CONTENT_LAUNCHER_CLUSTER_SERVER_ENDPOINT_COUNT)
    {
        return kClusterRevision;
    }

    uint16_t clusterRevision = 0;
    bool success =
        (Attributes::ClusterRevision::Get(endpoint, &clusterRevision) == chip::Protocols::InteractionModel::Status::Success);
    if (!success)
    {
        ChipLogError(Zcl, "MediaPlaybackManager::GetClusterRevision error reading cluster revision");
    }
    return clusterRevision;
}
