/* Auto-generated C bindings for liter-llm */

#ifndef LITER_LLM_FFI_H
#define LITER_LLM_FFI_H

#pragma once

/* Warning, this file is autogenerated by cbindgen. Don't modify this manually. */

#define LITER_LLM_VERSION_MAJOR 1
#define LITER_LLM_VERSION_MINOR 1
#define LITER_LLM_VERSION_PATCH 0
#define LITER_LLM_VERSION "1.1.0"


#include <stdarg.h>
#include <stdbool.h>
#include <stdint.h>
#include <stdlib.h>
/* Symbol visibility */
#ifndef LITER_LLM_EXPORT
  #if defined(LITER_LLM_STATIC)
    #define LITER_LLM_EXPORT
  #elif defined(_WIN32) || defined(__CYGWIN__)
    #ifdef LITER_LLM_BUILDING
      #define LITER_LLM_EXPORT __declspec(dllexport)
    #else
      #define LITER_LLM_EXPORT __declspec(dllimport)
    #endif
  #elif defined(__GNUC__) || defined(__clang__)
    #define LITER_LLM_EXPORT __attribute__((visibility("default")))
  #else
    #define LITER_LLM_EXPORT
  #endif
#endif

/* Compiler attribute helpers
 *
 * LITER_LLM_WARN_UNUSED  — caller must not discard the return value (e.g. an
 *                         allocated pointer or an error code).
 * LITER_LLM_NONNULL(...) — the listed 1-based argument positions must never be
 *                         NULL.  Callers that pass NULL trigger UB; annotating
 *                         this lets GCC/Clang warn at compile time.
 */
#if defined(__GNUC__) || defined(__clang__)
#  define LITER_LLM_WARN_UNUSED   __attribute__((warn_unused_result))
#  define LITER_LLM_NONNULL(...)  __attribute__((nonnull(__VA_ARGS__)))
#else
#  define LITER_LLM_WARN_UNUSED
#  define LITER_LLM_NONNULL(...)
#endif

/**
 * Opaque handle to a liter-llm client.
 * Create with literllm_client_new(), free with literllm_client_free().
 */
typedef struct LiterLlmClient LiterLlmClient;


/**
 * Callback invoked for each SSE chunk during a streaming chat completion.
 *
 * - `chunk_json`: NUL-terminated JSON string for one `ChatCompletionChunk`.
 *   The pointer is valid only for the duration of the callback invocation.
 *   The callee must **not** free it.
 * - `user_data`: The opaque pointer passed to [`literllm_chat_stream`].
 *
 * This callback returns void; there is no return value.
 */
typedef void (*LiterLlmStreamCallback)(const char *chunk_json, void *user_data);

/**
 * Function pointer struct for lifecycle hook callbacks.
 *
 * All function pointers are optional (may be NULL).  When non-NULL, the
 * corresponding callback is invoked at the appropriate lifecycle point.
 *
 * # Memory ownership
 *
 * - `request_json` passed to callbacks is a NUL-terminated JSON string owned
 *   by the caller (liter-llm).  The hook must **not** free it; it is valid
 *   only for the duration of the callback invocation.
 * - `response_json` and `error_message` follow the same ownership rules.
 * - `user_data` is forwarded as-is to each callback; the caller is
 *   responsible for its lifetime and thread safety.
 */
typedef struct LiterLlmHookCallbacks {
  /**
   * Called before the request is sent.
   *
   * Return `0` to proceed, or non-zero to reject the request (guardrail).
   * When non-zero is returned, `literllm_last_error` will contain the
   * rejection message if set by the hook.
   */
  int32_t (*on_request)(const char *request_json, void *user_data);
  /**
   * Called after a successful response.
   */
  void (*on_response)(const char *request_json, const char *response_json, void *user_data);
  /**
   * Called when the request fails with an error.
   */
  void (*on_error)(const char *request_json, const char *error_message, void *user_data);
  /**
   * Opaque user data pointer forwarded to all callbacks.
   */
  void *user_data;
} LiterLlmHookCallbacks;

/**
 * Create a new liter-llm client.
 *
 * # Parameters
 *
 * - `api_key`: NUL-terminated API key string.  Pass an empty string (`""`)
 *   when using a provider that does not require authentication.
 * - `base_url`: NUL-terminated base URL override.  Pass `NULL` to use the
 *   default provider routing based on model-name prefix.
 * - `model_hint`: NUL-terminated model name hint for provider auto-detection
 *   (e.g. `"groq/llama3-70b"`).  Pass `NULL` to default to OpenAI.  Used
 *   only when `base_url` is also `NULL`.
 *
 * # Return value
 *
 * Returns a heap-allocated `LiterLlmClient*` on success, or `NULL` on failure.
 * Check [`literllm_last_error`] for the error message when `NULL` is returned.
 *
 * The returned pointer must be freed with [`literllm_client_free`].
 *
 * # Safety
 *
 * - `api_key` must be a valid, non-null, NUL-terminated C string.
 * - `base_url` may be `NULL` (treated as no override) or a valid NUL-terminated C string.
 * - `model_hint` may be `NULL` (treated as no hint) or a valid NUL-terminated C string.
 * - The caller owns the returned pointer and must call `literllm_client_free` exactly once.
 */
LITER_LLM_EXPORT
LiterLlmClient *literllm_client_new(const char *api_key,
                                    const char *base_url,
                                    const char *model_hint);

/**
 * Free a client created by [`literllm_client_new`].
 *
 * # Safety
 *
 * - `client` must be a valid pointer returned by `literllm_client_new`.
 * - `client` must not be used after this call (use-after-free is UB).
 * - Passing `NULL` is safe and is a no-op.
 */
LITER_LLM_EXPORT void literllm_client_free(LiterLlmClient *client);

/**
 * Send a chat completion request.
 *
 * # Parameters
 *
 * - `client`: A valid client pointer.
 * - `request_json`: NUL-terminated JSON string conforming to the
 *   `ChatCompletionRequest` schema.
 *
 * # Return value
 *
 * Returns a heap-allocated NUL-terminated JSON string containing the
 * `ChatCompletionResponse` on success, or `NULL` on failure.
 * Check [`literllm_last_error`] on failure.
 *
 * The caller must free the returned string with [`literllm_free_string`].
 *
 * # Safety
 *
 * - `client` must be a valid, non-null pointer returned by `literllm_client_new`.
 * - `request_json` must be a valid, non-null, NUL-terminated UTF-8 JSON string.
 */
LITER_LLM_EXPORT char *literllm_chat(const LiterLlmClient *client, const char *request_json);

/**
 * Send a streaming chat completion request, invoking a callback for each chunk.
 *
 * # Parameters
 *
 * - `client`: A valid client pointer.
 * - `request_json`: NUL-terminated JSON string conforming to the
 *   `ChatCompletionRequest` schema.
 * - `callback`: Function called once per SSE chunk with the JSON-serialised
 *   `ChatCompletionChunk`.  The `chunk_json` pointer is valid only for the
 *   duration of each callback invocation and must **not** be freed.
 * - `user_data`: Opaque pointer forwarded unchanged to each `callback` call.
 *   May be `NULL`.
 *
 * # Return value
 *
 * Returns `0` on success (all chunks delivered) or `-1` on failure.
 * Check [`literllm_last_error`] on failure.
 *
 * # Safety
 *
 * - `client` must be a valid, non-null pointer returned by `literllm_client_new`.
 * - `request_json` must be a valid, non-null, NUL-terminated UTF-8 JSON string.
 * - `callback` must be a valid function pointer; it is invoked from the calling
 *   thread with the Tokio runtime blocked.
 * - `user_data` is forwarded as-is; the caller is responsible for its lifetime.
 */
LITER_LLM_EXPORT
int32_t literllm_chat_stream(const LiterLlmClient *client,
                             const char *request_json,
                             LiterLlmStreamCallback callback,
                             void *user_data);

/**
 * Send an embedding request.
 *
 * # Parameters
 *
 * - `client`: A valid client pointer.
 * - `request_json`: NUL-terminated JSON string conforming to the
 *   `EmbeddingRequest` schema.
 *
 * # Return value
 *
 * Returns a heap-allocated NUL-terminated JSON string containing the
 * `EmbeddingResponse` on success, or `NULL` on failure.
 * Check [`literllm_last_error`] on failure.
 *
 * The caller must free the returned string with [`literllm_free_string`].
 *
 * # Safety
 *
 * - `client` must be a valid, non-null pointer returned by `literllm_client_new`.
 * - `request_json` must be a valid, non-null, NUL-terminated UTF-8 JSON string.
 */
LITER_LLM_EXPORT char *literllm_embed(const LiterLlmClient *client, const char *request_json);

/**
 * List available models.
 *
 * # Parameters
 *
 * - `client`: A valid client pointer.
 *
 * # Return value
 *
 * Returns a heap-allocated NUL-terminated JSON string containing the
 * `ModelsListResponse` on success, or `NULL` on failure.
 * Check [`literllm_last_error`] on failure.
 *
 * The caller must free the returned string with [`literllm_free_string`].
 *
 * # Safety
 *
 * - `client` must be a valid, non-null pointer returned by `literllm_client_new`.
 */
LITER_LLM_EXPORT char *literllm_list_models(const LiterLlmClient *client);

/**
 * Generate an image from a text prompt.
 *
 * # Parameters
 *
 * - `client`: A valid client pointer.
 * - `request_json`: NUL-terminated JSON string conforming to the
 *   `CreateImageRequest` schema.
 *
 * # Return value
 *
 * Returns a heap-allocated NUL-terminated JSON string containing the
 * `ImagesResponse` on success, or `NULL` on failure.
 * The caller must free the returned string with [`literllm_free_string`].
 *
 * # Safety
 *
 * - `client` must be a valid, non-null pointer returned by `literllm_client_new`.
 * - `request_json` must be a valid, non-null, NUL-terminated UTF-8 JSON string.
 */
LITER_LLM_EXPORT
char *literllm_image_generate(const LiterLlmClient *client,
                              const char *request_json);

/**
 * Generate speech audio from text.
 *
 * # Parameters
 *
 * - `client`: A valid client pointer.
 * - `request_json`: NUL-terminated JSON string conforming to the
 *   `CreateSpeechRequest` schema.
 *
 * # Return value
 *
 * Returns a heap-allocated NUL-terminated base64-encoded string of the audio
 * bytes on success, or `NULL` on failure.
 * The caller must free the returned string with [`literllm_free_string`].
 *
 * # Safety
 *
 * - `client` must be a valid, non-null pointer returned by `literllm_client_new`.
 * - `request_json` must be a valid, non-null, NUL-terminated UTF-8 JSON string.
 */
LITER_LLM_EXPORT char *literllm_speech(const LiterLlmClient *client, const char *request_json);

/**
 * Transcribe audio to text.
 *
 * # Parameters
 *
 * - `client`: A valid client pointer.
 * - `request_json`: NUL-terminated JSON string conforming to the
 *   `CreateTranscriptionRequest` schema.
 *
 * # Return value
 *
 * Returns a heap-allocated NUL-terminated JSON string containing the
 * `TranscriptionResponse` on success, or `NULL` on failure.
 * The caller must free the returned string with [`literllm_free_string`].
 *
 * # Safety
 *
 * - `client` must be a valid, non-null pointer returned by `literllm_client_new`.
 * - `request_json` must be a valid, non-null, NUL-terminated UTF-8 JSON string.
 */
LITER_LLM_EXPORT char *literllm_transcribe(const LiterLlmClient *client, const char *request_json);

/**
 * Check content against moderation policies.
 *
 * # Parameters
 *
 * - `client`: A valid client pointer.
 * - `request_json`: NUL-terminated JSON string conforming to the
 *   `ModerationRequest` schema.
 *
 * # Return value
 *
 * Returns a heap-allocated NUL-terminated JSON string containing the
 * `ModerationResponse` on success, or `NULL` on failure.
 * The caller must free the returned string with [`literllm_free_string`].
 *
 * # Safety
 *
 * - `client` must be a valid, non-null pointer returned by `literllm_client_new`.
 * - `request_json` must be a valid, non-null, NUL-terminated UTF-8 JSON string.
 */
LITER_LLM_EXPORT char *literllm_moderate(const LiterLlmClient *client, const char *request_json);

/**
 * Rerank documents by relevance to a query.
 *
 * # Parameters
 *
 * - `client`: A valid client pointer.
 * - `request_json`: NUL-terminated JSON string conforming to the
 *   `RerankRequest` schema.
 *
 * # Return value
 *
 * Returns a heap-allocated NUL-terminated JSON string containing the
 * `RerankResponse` on success, or `NULL` on failure.
 * The caller must free the returned string with [`literllm_free_string`].
 *
 * # Safety
 *
 * - `client` must be a valid, non-null pointer returned by `literllm_client_new`.
 * - `request_json` must be a valid, non-null, NUL-terminated UTF-8 JSON string.
 */
LITER_LLM_EXPORT char *literllm_rerank(const LiterLlmClient *client, const char *request_json);

/**
 * Perform a web/document search.
 *
 * # Parameters
 *
 * - `client`: A valid client pointer.
 * - `request_json`: NUL-terminated JSON string conforming to the
 *   `SearchRequest` schema.
 *
 * # Return value
 *
 * Returns a heap-allocated NUL-terminated JSON string containing the
 * `SearchResponse` on success, or `NULL` on failure.
 * The caller must free the returned string with [`literllm_free_string`].
 *
 * # Safety
 *
 * - `client` must be a valid, non-null pointer returned by `literllm_client_new`.
 * - `request_json` must be a valid, non-null, NUL-terminated UTF-8 JSON string.
 */
LITER_LLM_EXPORT char *literllm_search(const LiterLlmClient *client, const char *request_json);

/**
 * Extract text from a document via OCR.
 *
 * # Parameters
 *
 * - `client`: A valid client pointer.
 * - `request_json`: NUL-terminated JSON string conforming to the
 *   `OcrRequest` schema.
 *
 * # Return value
 *
 * Returns a heap-allocated NUL-terminated JSON string containing the
 * `OcrResponse` on success, or `NULL` on failure.
 * The caller must free the returned string with [`literllm_free_string`].
 *
 * # Safety
 *
 * - `client` must be a valid, non-null pointer returned by `literllm_client_new`.
 * - `request_json` must be a valid, non-null, NUL-terminated UTF-8 JSON string.
 */
LITER_LLM_EXPORT char *literllm_ocr(const LiterLlmClient *client, const char *request_json);

/**
 * Upload a file.
 *
 * # Parameters
 *
 * - `client`: A valid client pointer.
 * - `request_json`: NUL-terminated JSON string conforming to the
 *   `CreateFileRequest` schema.  The `file` field must be base64-encoded.
 *
 * # Return value
 *
 * Returns a heap-allocated NUL-terminated JSON string containing the
 * `FileObject` on success, or `NULL` on failure.
 * The caller must free the returned string with [`literllm_free_string`].
 *
 * # Safety
 *
 * - `client` must be a valid, non-null pointer returned by `literllm_client_new`.
 * - `request_json` must be a valid, non-null, NUL-terminated UTF-8 JSON string.
 */
LITER_LLM_EXPORT char *literllm_create_file(const LiterLlmClient *client, const char *request_json);

/**
 * Retrieve metadata for a file by ID.
 *
 * # Parameters
 *
 * - `client`: A valid client pointer.
 * - `file_id`: NUL-terminated file ID string.
 *
 * # Return value
 *
 * Returns a heap-allocated NUL-terminated JSON string containing the
 * `FileObject` on success, or `NULL` on failure.
 * The caller must free the returned string with [`literllm_free_string`].
 *
 * # Safety
 *
 * - `client` must be a valid, non-null pointer returned by `literllm_client_new`.
 * - `file_id` must be a valid, non-null, NUL-terminated UTF-8 string.
 */
LITER_LLM_EXPORT char *literllm_retrieve_file(const LiterLlmClient *client, const char *file_id);

/**
 * Delete a file by ID.
 *
 * # Parameters
 *
 * - `client`: A valid client pointer.
 * - `file_id`: NUL-terminated file ID string.
 *
 * # Return value
 *
 * Returns a heap-allocated NUL-terminated JSON string containing the
 * `DeleteResponse` on success, or `NULL` on failure.
 * The caller must free the returned string with [`literllm_free_string`].
 *
 * # Safety
 *
 * - `client` must be a valid, non-null pointer returned by `literllm_client_new`.
 * - `file_id` must be a valid, non-null, NUL-terminated UTF-8 string.
 */
LITER_LLM_EXPORT char *literllm_delete_file(const LiterLlmClient *client, const char *file_id);

/**
 * List files, optionally filtered by query parameters.
 *
 * # Parameters
 *
 * - `client`: A valid client pointer.
 * - `query_json`: NUL-terminated JSON string conforming to the
 *   `FileListQuery` schema.  May be `NULL` to list all files.
 *
 * # Return value
 *
 * Returns a heap-allocated NUL-terminated JSON string containing the
 * `FileListResponse` on success, or `NULL` on failure.
 * The caller must free the returned string with [`literllm_free_string`].
 *
 * # Safety
 *
 * - `client` must be a valid, non-null pointer returned by `literllm_client_new`.
 * - `query_json` may be `NULL` or a valid NUL-terminated UTF-8 JSON string.
 */
LITER_LLM_EXPORT char *literllm_list_files(const LiterLlmClient *client, const char *query_json);

/**
 * Retrieve the raw content of a file (returned as base64-encoded string).
 *
 * # Parameters
 *
 * - `client`: A valid client pointer.
 * - `file_id`: NUL-terminated file ID string.
 *
 * # Return value
 *
 * Returns a heap-allocated NUL-terminated base64-encoded string of the file
 * content on success, or `NULL` on failure.
 * The caller must free the returned string with [`literllm_free_string`].
 *
 * # Safety
 *
 * - `client` must be a valid, non-null pointer returned by `literllm_client_new`.
 * - `file_id` must be a valid, non-null, NUL-terminated UTF-8 string.
 */
LITER_LLM_EXPORT char *literllm_file_content(const LiterLlmClient *client, const char *file_id);

/**
 * Create a new batch job.
 *
 * # Parameters
 *
 * - `client`: A valid client pointer.
 * - `request_json`: NUL-terminated JSON string conforming to the
 *   `CreateBatchRequest` schema.
 *
 * # Return value
 *
 * Returns a heap-allocated NUL-terminated JSON string containing the
 * `BatchObject` on success, or `NULL` on failure.
 * The caller must free the returned string with [`literllm_free_string`].
 *
 * # Safety
 *
 * - `client` must be a valid, non-null pointer returned by `literllm_client_new`.
 * - `request_json` must be a valid, non-null, NUL-terminated UTF-8 JSON string.
 */
LITER_LLM_EXPORT
char *literllm_create_batch(const LiterLlmClient *client,
                            const char *request_json);

/**
 * Retrieve a batch by ID.
 *
 * # Parameters
 *
 * - `client`: A valid client pointer.
 * - `batch_id`: NUL-terminated batch ID string.
 *
 * # Return value
 *
 * Returns a heap-allocated NUL-terminated JSON string containing the
 * `BatchObject` on success, or `NULL` on failure.
 * The caller must free the returned string with [`literllm_free_string`].
 *
 * # Safety
 *
 * - `client` must be a valid, non-null pointer returned by `literllm_client_new`.
 * - `batch_id` must be a valid, non-null, NUL-terminated UTF-8 string.
 */
LITER_LLM_EXPORT char *literllm_retrieve_batch(const LiterLlmClient *client, const char *batch_id);

/**
 * List batches, optionally filtered by query parameters.
 *
 * # Parameters
 *
 * - `client`: A valid client pointer.
 * - `query_json`: NUL-terminated JSON string conforming to the
 *   `BatchListQuery` schema.  May be `NULL` to list all batches.
 *
 * # Return value
 *
 * Returns a heap-allocated NUL-terminated JSON string containing the
 * `BatchListResponse` on success, or `NULL` on failure.
 * The caller must free the returned string with [`literllm_free_string`].
 *
 * # Safety
 *
 * - `client` must be a valid, non-null pointer returned by `literllm_client_new`.
 * - `query_json` may be `NULL` or a valid NUL-terminated UTF-8 JSON string.
 */
LITER_LLM_EXPORT char *literllm_list_batches(const LiterLlmClient *client, const char *query_json);

/**
 * Cancel an in-progress batch.
 *
 * # Parameters
 *
 * - `client`: A valid client pointer.
 * - `batch_id`: NUL-terminated batch ID string.
 *
 * # Return value
 *
 * Returns a heap-allocated NUL-terminated JSON string containing the
 * `BatchObject` on success, or `NULL` on failure.
 * The caller must free the returned string with [`literllm_free_string`].
 *
 * # Safety
 *
 * - `client` must be a valid, non-null pointer returned by `literllm_client_new`.
 * - `batch_id` must be a valid, non-null, NUL-terminated UTF-8 string.
 */
LITER_LLM_EXPORT char *literllm_cancel_batch(const LiterLlmClient *client, const char *batch_id);

/**
 * Create a new response.
 *
 * # Parameters
 *
 * - `client`: A valid client pointer.
 * - `request_json`: NUL-terminated JSON string conforming to the
 *   `CreateResponseRequest` schema.
 *
 * # Return value
 *
 * Returns a heap-allocated NUL-terminated JSON string containing the
 * `ResponseObject` on success, or `NULL` on failure.
 * The caller must free the returned string with [`literllm_free_string`].
 *
 * # Safety
 *
 * - `client` must be a valid, non-null pointer returned by `literllm_client_new`.
 * - `request_json` must be a valid, non-null, NUL-terminated UTF-8 JSON string.
 */
LITER_LLM_EXPORT
char *literllm_create_response(const LiterLlmClient *client,
                               const char *request_json);

/**
 * Retrieve a response by ID.
 *
 * # Parameters
 *
 * - `client`: A valid client pointer.
 * - `response_id`: NUL-terminated response ID string.
 *
 * # Return value
 *
 * Returns a heap-allocated NUL-terminated JSON string containing the
 * `ResponseObject` on success, or `NULL` on failure.
 * The caller must free the returned string with [`literllm_free_string`].
 *
 * # Safety
 *
 * - `client` must be a valid, non-null pointer returned by `literllm_client_new`.
 * - `response_id` must be a valid, non-null, NUL-terminated UTF-8 string.
 */
LITER_LLM_EXPORT
char *literllm_retrieve_response(const LiterLlmClient *client,
                                 const char *response_id);

/**
 * Cancel an in-progress response.
 *
 * # Parameters
 *
 * - `client`: A valid client pointer.
 * - `response_id`: NUL-terminated response ID string.
 *
 * # Return value
 *
 * Returns a heap-allocated NUL-terminated JSON string containing the
 * `ResponseObject` on success, or `NULL` on failure.
 * The caller must free the returned string with [`literllm_free_string`].
 *
 * # Safety
 *
 * - `client` must be a valid, non-null pointer returned by `literllm_client_new`.
 * - `response_id` must be a valid, non-null, NUL-terminated UTF-8 string.
 */
LITER_LLM_EXPORT
char *literllm_cancel_response(const LiterLlmClient *client,
                               const char *response_id);

/**
 * Read the cumulative global spend tracked by the budget layer.
 *
 * Returns the spend in USD.  If no budget is configured on the client,
 * returns `0.0`.
 *
 * # Safety
 *
 * - `client` must be a valid, non-null pointer returned by
 *   `literllm_client_new` or `literllm_client_new_with_config`.
 */
LITER_LLM_EXPORT double literllm_budget_usage(const LiterLlmClient *client);

/**
 * Retrieve the last error message for the current thread.
 *
 * Returns a `const char*` pointer to the NUL-terminated error string, or
 * `NULL` if no error has occurred since the last successful call.
 *
 * The returned pointer is valid only until the **next** liter-llm function
 * call on the **same thread**.  The caller must **not** free this pointer.
 *
 * # Safety
 *
 * Always safe to call.  No preconditions.
 */
LITER_LLM_EXPORT const char *literllm_last_error(void);

/**
 * Free a string returned by [`literllm_chat`], [`literllm_embed`], or
 * [`literllm_list_models`].
 *
 * # Safety
 *
 * - `s` must be a pointer returned by one of the functions listed above.
 * - `s` must not be used after this call (use-after-free is UB).
 * - Passing `NULL` is safe and is a no-op.
 * - Do **not** pass the pointer returned by [`literllm_last_error`]; that
 *   pointer must not be freed.
 */
LITER_LLM_EXPORT void literllm_free_string(char *s);

/**
 * Returns the version string of the liter-llm library.
 *
 * The returned pointer is valid for the lifetime of the program and must
 * **not** be freed.
 *
 * # Safety
 *
 * Always safe to call.
 */
LITER_LLM_EXPORT const char *literllm_version(void);

/**
 * Register a custom LLM provider at runtime.
 *
 * # Parameters
 *
 * - `config_json`: NUL-terminated JSON string conforming to the
 *   [`CustomProviderConfig`](liter_llm::CustomProviderConfig) schema.
 *
 * # Return value
 *
 * Returns `0` on success, `-1` on failure.
 * Check [`literllm_last_error`] for the error message when `-1` is returned.
 *
 * # Safety
 *
 * - `config_json` must be a valid, non-null, NUL-terminated UTF-8 JSON string.
 */
LITER_LLM_EXPORT int32_t literllm_register_provider(const char *config_json);

/**
 * Unregister a previously registered custom provider by name.
 *
 * # Parameters
 *
 * - `name`: NUL-terminated provider name string.
 *
 * # Return value
 *
 * Returns `0` if the provider was found and removed, `1` if no provider with
 * that name existed, or `-1` on failure.
 * Check [`literllm_last_error`] for the error message when `-1` is returned.
 *
 * # Safety
 *
 * - `name` must be a valid, non-null, NUL-terminated UTF-8 string.
 */
LITER_LLM_EXPORT int32_t literllm_unregister_provider(const char *name);

/**
 * Create a new liter-llm client from a full JSON configuration object.
 *
 * This is an extended version of [`literllm_client_new`] that accepts a
 * single JSON string containing all configuration options, including
 * cache, budget, extra headers, and model hint.
 *
 * # JSON Schema
 *
 * ```json
 * {
 *   "api_key": "sk-...",
 *   "base_url": "https://...",          // optional
 *   "model_hint": "groq/llama3-70b",    // optional
 *   "max_retries": 3,                    // optional, default 3
 *   "timeout_secs": 60,                  // optional, default 60
 *   "extra_headers": {"X-Custom": "v"},  // optional
 *   "cache": {                           // optional
 *     "max_entries": 256,
 *     "ttl_secs": 300
 *   },
 *   "budget": {                          // optional
 *     "global_limit": 10.0,
 *     "model_limits": {"gpt-4": 5.0},
 *     "enforcement": "hard"
 *   }
 * }
 * ```
 *
 * # Return value
 *
 * Returns a heap-allocated `LiterLlmClient*` on success, or `NULL` on
 * failure.  Check [`literllm_last_error`] for the error message when
 * `NULL` is returned.
 *
 * The returned pointer must be freed with [`literllm_client_free`].
 *
 * # Safety
 *
 * - `config_json` must be a valid, non-null, NUL-terminated UTF-8 JSON string.
 * - The caller owns the returned pointer and must call `literllm_client_free`
 *   exactly once.
 */
LITER_LLM_EXPORT LiterLlmClient *literllm_client_new_with_config(const char *config_json);

/**
 * Register lifecycle hook callbacks for a client.
 *
 * The callbacks are stored for the lifetime of the client and invoked
 * around each API call (chat, embed, etc.).
 *
 * **Note:** In the current implementation, hooks are advisory metadata
 * stored on the client handle.  Full Tower-integrated hook invocation
 * requires the client to be wrapped in a `HooksLayer` service stack,
 * which is an internal architecture detail.  C FFI callers should use
 * these callbacks as a notification mechanism; the Rust core handles
 * the actual request lifecycle.
 *
 * # Parameters
 *
 * - `client`: A valid client pointer.
 * - `callbacks`: Pointer to a `LiterLlmHookCallbacks` struct.  The struct
 *   is copied; the caller may free it after this call returns.
 *
 * # Return value
 *
 * Returns `0` on success, `-1` on failure.
 *
 * # Safety
 *
 * - `client` must be a valid, non-null pointer returned by
 *   `literllm_client_new` or `literllm_client_new_with_config`.
 * - `callbacks` must be a valid, non-null pointer to a
 *   `LiterLlmHookCallbacks` struct.
 * - Function pointers in `callbacks` must remain valid for the lifetime
 *   of the client.
 * - `user_data` must be valid for the lifetime of the client if non-NULL.
 */
LITER_LLM_EXPORT
int32_t literllm_set_hooks(LiterLlmClient *client,
                           const struct LiterLlmHookCallbacks *callbacks);

#endif  /* LITER_LLM_FFI_H */
