#pragma once

// HTTP request / response types + llhttp glue, and send_json/send_binary.
// Modeled after the Node.js src/http.js.

#include <cstdint>
#include <functional>
#include <string>
#include <unordered_map>
#include <vector>

#include <uv.h>
#include <nlohmann/json.hpp>

// Forward-declared; defined in tls_server.
struct tls_session;

using json = nlohmann::json;

// ---------------------------------------------------------------------------
// Parsed HTTP request
// ---------------------------------------------------------------------------

struct HttpRequest {
    std::string method;          // "GET", "POST", ...
    std::string path;            // "/v1/client?authCode=..."
    std::string version;         // "1.1"
    std::unordered_map<std::string, std::string> headers;
    std::vector<uint8_t> body;

    // Parsed query string
    std::string query_string;    // "authCode=xxx&name=yyy"

    std::string get_query_param(const std::string& key, const std::string& def = "") const;
};

// ---------------------------------------------------------------------------
// Response writer (wraps a tls_session*)
// ---------------------------------------------------------------------------

struct HttpResponse {
    tls_session* session = nullptr;
    int status_code = 200;
    bool headers_sent = false;
    std::string body_for_log;  // captured for request logging

    void send_json(int code, const json& body);
    void send_binary(int code, const std::vector<uint8_t>& data, const std::string& content_type);
    void send_empty(int code);

    // After response is fully written, close the connection.
    void finish();
};

// ---------------------------------------------------------------------------
// Route handler signature
// ---------------------------------------------------------------------------

struct RouteContext {
    std::string query_path;  // path without query string
    std::string full_url;    // raw path + query
    class PairingStore* pairing_store = nullptr;
    json config;
};

using RouteHandler = std::function<void(HttpRequest&, HttpResponse&, RouteContext&)>;

// ---------------------------------------------------------------------------
// Helpers
// ---------------------------------------------------------------------------

// Normalize /api/v1/... -> /v1/...  (matches src/http.js normalizePath)
std::string normalize_path(const std::string& pathname);

// Format "YYYY-MM-DD HH:MM:SS" from current time (matches serverTimestamp)
std::string server_timestamp();
