/*
 *   Copyright (c) 2026 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 <atomic>
#include <future>
#include <memory>
#include <mutex>
#include <string>
#include <thread>
#include <vector>

#include <inet/IPAddress.h>
#include <inet/InetInterface.h>
#include <lib/core/CHIPError.h>
#include <lib/dnssd/Types.h>
#include <lib/dnssd/wire/Parser.h>
#include <lib/dnssd/wire/RecordData.h>
#include <lib/support/SetupDiscriminator.h>
#include <lib/support/ThreadDiscoveryCode.h>
#include <lib/support/ThreadOperationalDataset.h>
#include <transport/raw/PeerAddress.h>

#include <commissioner/commissioner.hpp>

namespace chip {
namespace Controller {
/**
 * CommissionProxy acts as a bridge between the OpenThread Commissioner and Matter commissioning.
 * It handles Thread-specific commissioning (MeshCoP) and proxies mDNS discovery data
 * to facilitate the transition into Matter's operational commissioning flow.
 */
class ThreadMeshcopCommissionProxy : public ot::commissioner::CommissionerHandler,
                                     public chip::Dnssd::ParserDelegate,
                                     public chip::Dnssd::TxtRecordDelegate
{
public:
    enum class State
    {
        kConnecting,    // Establishing connection to Thread Border Agent
        kDiscovering,   // Waiting for mDNS announcements from the joiner
        kDiscovered,    // Discovered a matching joiner
        kCommissioning, // Proxying packets between local socket and joiner
        kAborted,       // Error or user cancellation
    };

    ThreadMeshcopCommissionProxy();
    ~ThreadMeshcopCommissionProxy() override;

    /**
     * Entry point to start the Thread commissioning and discover the device.
     * TODO: this function is synchronous, we need to make it asynchronous
     */
    CHIP_ERROR Discover(ByteSpan & pskc, const Transport::PeerAddress & peerAddr, const Thread::DiscoveryCode code,
                        chip::SetupDiscriminator expectedDiscriminator, Dnssd::DiscoveredNodeData & nodeData, uint16_t timeout);
    std::string GetLastDiscoveryDiagnosticJson();

    // ot::commissioner::CommissionerHandler
    void OnJoinerMessage(const std::vector<uint8_t> & joinerIdBytes, uint16_t joinerPort,
                         const std::vector<uint8_t> & payload) override;

    // chip::Dnssd::ParserDelegate
    void OnHeader(chip::Dnssd::ConstHeaderRef & header) override;
    void OnQuery(const chip::Dnssd::QueryData & data) override;
    void OnResource(chip::Dnssd::ResourceType section, const chip::Dnssd::ResourceData & data) override;

    // chip::Dnssd::TxtRecordDelegate
    void OnRecord(const chip::Dnssd::BytesRange & name, const chip::Dnssd::BytesRange & value) override;

private:
    // Internal Helper Methods
    CHIP_ERROR InitializeCommissioner(ByteSpan & pskc);
    CHIP_ERROR CreateProxySocket(Dnssd::CommissionNodeData & commissionData);
    void ProcessAnnouncement(const std::vector<uint8_t> & joinerIdBytes, uint16_t joinerPort, const std::vector<uint8_t> & payload);
    void ResetCommissionerForDiscovery();
    void SetState(State state);

    ot::commissioner::CommissionerDataset MakeCommissionerDataset(Thread::DiscoveryCode code);

    struct DiscoveryDiagnostic
    {
        bool valid                 = false;
        bool requestedShort        = false;
        uint16_t requestedValue    = 0;
        uint16_t expectedLongValue = 0;
        uint64_t discoveryCode     = 0;
        uint64_t joinerId          = 0;
        uint16_t joinerUdpPort     = 0;
        uint16_t matterUdpPort     = 0;
        std::vector<uint8_t> steeringData;
        Dnssd::CommissionNodeData commissionData{};
    };

    // Member Variables
    chip::Dnssd::DiscoveredNodeData mNodeData;
    chip::Dnssd::BytesRange mDnsPacket;

    int mProxyFd          = -1;
    uint16_t mServicePort = 0;
    std::atomic<State> mState;
    chip::SetupDiscriminator mExpectedDiscriminator;

    uint64_t mJoinerId = 0;

    std::recursive_mutex mMutex;
    bool mPromiseFulfilled = false;
    std::promise<Dnssd::DiscoveredNodeData> mDiscoveredNodePromise;

    std::shared_ptr<ot::commissioner::Commissioner> mCommissioner;
    std::thread mProxyThread;
    DiscoveryDiagnostic mLastDiscoveryDiagnostic;
};

} // namespace Controller
} // namespace chip
