/**************************************************************************/
/*  aethex_cloud_save.cpp                                                 */
/**************************************************************************/
/*                       AeThex Engine                                    */
/*                    https://aethex.dev                                  */
/**************************************************************************/

#include "aethex_cloud_save.h"
#include "aethex_cloud.h"
#include "core/io/http_client.h"

void AethexCloudSave::_bind_methods() {
    ClassDB::bind_method(D_METHOD("list_saves", "game_id"), &AethexCloudSave::list_saves, DEFVAL(""));
    ClassDB::bind_method(D_METHOD("get_save", "save_id"), &AethexCloudSave::get_save);
    ClassDB::bind_method(D_METHOD("create_save", "game_id", "name", "data"), &AethexCloudSave::create_save);
    ClassDB::bind_method(D_METHOD("update_save", "save_id", "data"), &AethexCloudSave::update_save);
    ClassDB::bind_method(D_METHOD("delete_save", "save_id"), &AethexCloudSave::delete_save);
    ClassDB::bind_method(D_METHOD("sync_project", "project_path"), &AethexCloudSave::sync_project);

    ClassDB::bind_method(D_METHOD("list_saves_async", "game_id", "callback"), &AethexCloudSave::list_saves_async);
    ClassDB::bind_method(D_METHOD("save_async", "game_id", "name", "data", "callback"), &AethexCloudSave::save_async);

    ADD_SIGNAL(MethodInfo("save_completed", PropertyInfo(Variant::DICTIONARY, "result")));
    ADD_SIGNAL(MethodInfo("save_failed", PropertyInfo(Variant::STRING, "error")));
    ADD_SIGNAL(MethodInfo("sync_completed", PropertyInfo(Variant::DICTIONARY, "result")));
}

AethexCloudSave::AethexCloudSave() {
}

AethexCloudSave::~AethexCloudSave() {
}

void AethexCloudSave::set_cloud(AethexCloud *p_cloud) {
    cloud = p_cloud;
}

Dictionary AethexCloudSave::list_saves(const String &p_game_id) {
    if (!cloud) {
        Dictionary result;
        result["success"] = false;
        result["error"] = "Cloud not initialized";
        return result;
    }

    String endpoint = "/api/cloud/saves";
    if (!p_game_id.is_empty()) {
        endpoint += "?gameId=" + p_game_id.uri_encode();
    }

    return cloud->make_request(endpoint, HTTPClient::METHOD_GET);
}

Dictionary AethexCloudSave::get_save(const String &p_save_id) {
    if (!cloud) {
        Dictionary result;
        result["success"] = false;
        result["error"] = "Cloud not initialized";
        return result;
    }

    return cloud->make_request("/api/cloud/saves/" + p_save_id, HTTPClient::METHOD_GET);
}

Dictionary AethexCloudSave::create_save(const String &p_game_id, const String &p_name, const Dictionary &p_data) {
    if (!cloud) {
        Dictionary result;
        result["success"] = false;
        result["error"] = "Cloud not initialized";
        return result;
    }

    Dictionary data;
    data["gameId"] = p_game_id;
    data["name"] = p_name;
    data["data"] = p_data;

    Dictionary result = cloud->make_request("/api/cloud/saves", HTTPClient::METHOD_POST, data);
    
    if (result.get("success", false)) {
        emit_signal("save_completed", result);
    } else {
        emit_signal("save_failed", result.get("error", "Save failed"));
    }

    return result;
}

Dictionary AethexCloudSave::update_save(const String &p_save_id, const Dictionary &p_data) {
    if (!cloud) {
        Dictionary result;
        result["success"] = false;
        result["error"] = "Cloud not initialized";
        return result;
    }

    Dictionary data;
    data["data"] = p_data;

    return cloud->make_request("/api/cloud/saves/" + p_save_id, HTTPClient::METHOD_PUT, data);
}

Dictionary AethexCloudSave::delete_save(const String &p_save_id) {
    if (!cloud) {
        Dictionary result;
        result["success"] = false;
        result["error"] = "Cloud not initialized";
        return result;
    }

    return cloud->make_request("/api/cloud/saves/" + p_save_id, HTTPClient::METHOD_DELETE);
}

Dictionary AethexCloudSave::sync_project(const String &p_project_path) {
    if (!cloud) {
        Dictionary result;
        result["success"] = false;
        result["error"] = "Cloud not initialized";
        return result;
    }

    Dictionary data;
    data["projectPath"] = p_project_path;
    // TODO: Read and package project files

    Dictionary result = cloud->make_request("/api/cloud/projects/sync", HTTPClient::METHOD_POST, data);
    
    if (result.get("success", false)) {
        emit_signal("sync_completed", result);
    }

    return result;
}

void AethexCloudSave::list_saves_async(const String &p_game_id, const Callable &p_callback) {
    Dictionary result = list_saves(p_game_id);
    if (p_callback.is_valid()) {
        p_callback.call(result);
    }
}

void AethexCloudSave::save_async(const String &p_game_id, const String &p_name, const Dictionary &p_data, const Callable &p_callback) {
    Dictionary result = create_save(p_game_id, p_name, p_data);
    if (p_callback.is_valid()) {
        p_callback.call(result);
    }
}
