#include <Arduino.h>
#include <stdarg.h>
#include "debug_log.h"

static const uint8_t NB_LIGNES = 80;
static const uint8_t TAILLE_LIGNE = 160;

static char lignes[NB_LIGNES][TAILLE_LIGNE];
static uint32_t horodatage[NB_LIGNES];
static uint8_t prochaineLigne = 0;
static uint8_t nbLignes = 0;
static uint32_t compteur = 0;

static void appendJsonString(String &out, const char *s) {
    out += '"';
    while (*s) {
        char c = *s++;
        switch (c) {
            case '\\': out += "\\\\"; break;
            case '"':  out += "\\\""; break;
            case '\n': out += "\\n"; break;
            case '\r': break;
            case '\t': out += "\\t"; break;
            default:
                if ((uint8_t)c < 0x20) out += ' ';
                else out += c;
                break;
        }
    }
    out += '"';
}

void debugLogLine(const char *message) {
    if (!message) return;

    snprintf(lignes[prochaineLigne], TAILLE_LIGNE, "%s", message);
    horodatage[prochaineLigne] = millis();
    prochaineLigne = (prochaineLigne + 1) % NB_LIGNES;
    if (nbLignes < NB_LIGNES) nbLignes++;
    compteur++;
}

void debugLogf(const char *format, ...) {
    char buffer[TAILLE_LIGNE];

    va_list args;
    va_start(args, format);
    vsnprintf(buffer, sizeof(buffer), format, args);
    va_end(args);

    Serial.println(buffer);
    debugLogLine(buffer);
}

void getDebugLogJson(String &out) {
    out.reserve(NB_LIGNES * 96);
    out = "{\"count\":";
    out += compteur;
    out += ",\"lines\":[";

    for (uint8_t i = 0; i < nbLignes; i++) {
        uint8_t idx = (prochaineLigne + NB_LIGNES - nbLignes + i) % NB_LIGNES;
        if (i) out += ',';
        out += "{\"t\":";
        out += horodatage[idx];
        out += ",\"m\":";
        appendJsonString(out, lignes[idx]);
        out += '}';
    }

    out += "]}";
}

void clearDebugLog() {
    prochaineLigne = 0;
    nbLignes = 0;
    compteur = 0;
    debugLogf("[DEBUG] Journal vidé");
}
