#include "ssid_manager_c.h"
#include <string.h>
#include <esp_log.h>
#include <nvs_flash.h>
#include <stdlib.h>

#define TAG "SsidManager"
#define NVS_NAMESPACE "wifi"
#define MAX_WIFI_SSID_COUNT 10
#define MAX_SSID_LEN 32
#define MAX_PASS_LEN 64

// 内部结构体定义
typedef struct {
    char ssid[MAX_SSID_LEN + 1];
    char password[MAX_PASS_LEN + 1];
} SsidEntry;

struct SsidManager {
    SsidEntry entries[MAX_WIFI_SSID_COUNT];
    int count;
};

// 函数实现
SsidManager* ssid_manager_create() {
    SsidManager* manager = (SsidManager*)malloc(sizeof(SsidManager));
    if (manager) {
        manager->count = 0;
        ssid_manager_load_from_nvs(manager);
    }
    return manager;
}

void ssid_manager_destroy(SsidManager* manager) {
    if (manager) {
        free(manager);
    }
}

void ssid_manager_clear(SsidManager* manager) {
    manager->count = 0;
    ssid_manager_save_to_nvs(manager);
}

void ssid_manager_load_from_nvs(SsidManager* manager) {
    manager->count = 0;
    
    nvs_handle_t nvs_handle;
    esp_err_t ret = nvs_open(NVS_NAMESPACE, NVS_READONLY, &nvs_handle);
    if (ret != ESP_OK) {
        ESP_LOGW(TAG, "NVS namespace %s doesn't exist", NVS_NAMESPACE);
        return;
    }

    for (int i = 0; i < MAX_WIFI_SSID_COUNT; i++) {
        char ssid_key[12];
        char password_key[12];
        
        // 安全生成键名
        if (i == 0) {
            strncpy(ssid_key, "ssid", sizeof(ssid_key));
            strncpy(password_key, "password", sizeof(password_key));
        } else {
            // 使用更安全的格式化方式
            int written = snprintf(ssid_key, sizeof(ssid_key), "ssid%d", i);
            if (written < 0 || written >= sizeof(ssid_key)) {
                ESP_LOGE(TAG, "ssid_key truncation for index %d", i);
                continue;
            }
            
            written = snprintf(password_key, sizeof(password_key), "password%d", i);
            if (written < 0 || written >= sizeof(password_key)) {
                ESP_LOGE(TAG, "password_key truncation for index %d", i);
                continue;
            }
        }

        char ssid[MAX_SSID_LEN + 1] = {0};
        char password[MAX_PASS_LEN + 1] = {0};
        size_t len = sizeof(ssid);
        
        // 获取SSID
        if (nvs_get_str(nvs_handle, ssid_key, ssid, &len) != ESP_OK) {
            continue;
        }
        
        // 获取密码
        len = sizeof(password);
        if (nvs_get_str(nvs_handle, password_key, password, &len) != ESP_OK) {
            continue;
        }

        // 添加到管理器
        if (manager->count < MAX_WIFI_SSID_COUNT) {
            strncpy(manager->entries[manager->count].ssid, ssid, MAX_SSID_LEN);
            manager->entries[manager->count].ssid[MAX_SSID_LEN] = '\0'; // 确保空终止
            
            strncpy(manager->entries[manager->count].password, password, MAX_PASS_LEN);
            manager->entries[manager->count].password[MAX_PASS_LEN] = '\0'; // 确保空终止
            
            manager->count++;
        }
    }
    nvs_close(nvs_handle);
}

void ssid_manager_save_to_nvs(SsidManager* manager) {
    nvs_handle_t nvs_handle;
    ESP_ERROR_CHECK(nvs_open(NVS_NAMESPACE, NVS_READWRITE, &nvs_handle));
    
    // 安全清除所有旧键值
    for (int i = 0; i < MAX_WIFI_SSID_COUNT; i++) {
        char ssid_key[12];
        char password_key[12];
        
        // 安全生成键名
        if (i == 0) {
            strncpy(ssid_key, "ssid", sizeof(ssid_key));
            strncpy(password_key, "password", sizeof(password_key));
        } else {
            // 使用更安全的格式化方式
            int written = snprintf(ssid_key, sizeof(ssid_key), "ssid%d", i);
            if (written < 0 || written >= sizeof(ssid_key)) {
                ESP_LOGE(TAG, "ssid_key truncation for index %d", i);
                continue;
            }
            
            written = snprintf(password_key, sizeof(password_key), "password%d", i);
            if (written < 0 || written >= sizeof(password_key)) {
                ESP_LOGE(TAG, "password_key truncation for index %d", i);
                continue;
            }
        }
        
        // 清除键值
        nvs_erase_key(nvs_handle, ssid_key);
        nvs_erase_key(nvs_handle, password_key);
    }
    
    // 安全保存新数据
    for (int i = 0; i < manager->count; i++) {
        char ssid_key[12];
        char password_key[12];
        
        // 安全生成键名
        if (i == 0) {
            strncpy(ssid_key, "ssid", sizeof(ssid_key));
            strncpy(password_key, "password", sizeof(password_key));
        } else {
            // 使用更安全的格式化方式
            int written = snprintf(ssid_key, sizeof(ssid_key), "ssid%d", i);
            if (written < 0 || written >= sizeof(ssid_key)) {
                ESP_LOGE(TAG, "ssid_key truncation for index %d", i);
                continue;
            }
            
            written = snprintf(password_key, sizeof(password_key), "password%d", i);
            if (written < 0 || written >= sizeof(password_key)) {
                ESP_LOGE(TAG, "password_key truncation for index %d", i);
                continue;
            }
        }
        
        // 设置键值
        nvs_set_str(nvs_handle, ssid_key, manager->entries[i].ssid);
        nvs_set_str(nvs_handle, password_key, manager->entries[i].password);
    }
    
    nvs_commit(nvs_handle);
    nvs_close(nvs_handle);
}

void ssid_manager_add_ssid(SsidManager* manager, const char* ssid, const char* password) {
    // 检查是否已存在
    for (int i = 0; i < manager->count; i++) {
        if (strcmp(manager->entries[i].ssid, ssid) == 0) {
            ESP_LOGW(TAG, "SSID %s already exists, overwrite it", ssid);
            strncpy(manager->entries[i].password, password, MAX_PASS_LEN);
            manager->entries[i].password[MAX_PASS_LEN] = '\0'; // 确保空终止
            ssid_manager_save_to_nvs(manager);
            return;
        }
    }
    
    // 处理列表已满的情况
    if (manager->count >= MAX_WIFI_SSID_COUNT) {
        ESP_LOGW(TAG, "SSID list is full, removing last entry");
        manager->count--;
    }
    
    // 移动现有条目（为新条目腾出空间）
    for (int i = manager->count; i > 0; i--) {
        memcpy(&manager->entries[i], &manager->entries[i-1], sizeof(SsidEntry));
    }
    
    // 添加新条目到开头
    strncpy(manager->entries[0].ssid, ssid, MAX_SSID_LEN);
    manager->entries[0].ssid[MAX_SSID_LEN] = '\0'; // 确保空终止
    
    strncpy(manager->entries[0].password, password, MAX_PASS_LEN);
    manager->entries[0].password[MAX_PASS_LEN] = '\0'; // 确保空终止
    
    manager->count++;
    
    ssid_manager_save_to_nvs(manager);
}

void ssid_manager_remove_ssid(SsidManager* manager, int index) {
    if (index < 0 || index >= manager->count) {
        ESP_LOGW(TAG, "Invalid index %d", index);
        return;
    }
    
    // 移动后续条目覆盖要删除的条目
    for (int i = index; i < manager->count - 1; i++) {
        memcpy(&manager->entries[i], &manager->entries[i+1], sizeof(SsidEntry));
    }
    
    manager->count--;
    ssid_manager_save_to_nvs(manager);
}

void ssid_manager_set_default_ssid(SsidManager* manager, int index) {
    if (index < 0 || index >= manager->count) {
        ESP_LOGW(TAG, "Invalid index %d", index);
        return;
    }
    
    if (index == 0) {
        return; // 已经是默认
    }
    
    // 保存目标条目
    SsidEntry target;
    memcpy(&target, &manager->entries[index], sizeof(SsidEntry));
    
    // 移动前面的条目
    for (int i = index; i > 0; i--) {
        memcpy(&manager->entries[i], &manager->entries[i-1], sizeof(SsidEntry));
    }
    
    // 将目标条目放在开头
    memcpy(&manager->entries[0], &target, sizeof(SsidEntry));
    ssid_manager_save_to_nvs(manager);
}

// 辅助函数
int ssid_manager_get_count(SsidManager* manager) {
    return manager->count;
}

const char* ssid_manager_get_ssid(SsidManager* manager, int index) {
    if (index < 0 || index >= manager->count) return NULL;
    return manager->entries[index].ssid;
}

const char* ssid_manager_get_password(SsidManager* manager, int index) {
    if (index < 0 || index >= manager->count) return NULL;
    return manager->entries[index].password;
}