#pragma once

#ifdef __cplusplus
extern "C" {
#endif

#include <stddef.h>
#include <stdint.h>

#include "session/export.h"
#include "session/network/session_network_types.h"
#include "session/platform.h"

typedef struct file_server_parsed_download_url {
    char scheme[8];              // "http" or "https" + null
    char host[254];              // 253 max valid DNS length + null
    uint16_t port;               // 0 if the url stated none, meaning the scheme's default
    char file_id[65];            // id + null terminator
    char custom_pubkey_hex[65];  // 64 hex chars + null terminator, empty string if not present
    bool wants_stream_decryption;
} file_server_parsed_download_url;

/// API: session_file_server/session_file_server_parse_download_url
///
/// Parses a url to extract the information required to download the file.
///
/// Inputs:
/// - `url` -- [in] url to check.
/// - `out` -- [out] parsed download url.
///
/// Outputs:
/// - returns true if url was successfully parsed, false otherwise.
LIBSESSION_EXPORT bool session_file_server_parse_download_url(
        const char* url, file_server_parsed_download_url* out);

/// API: session_file_server/session_file_server_generate_download_url
///
/// Determines whether a given download url requires deterministic decryption.
///
/// Inputs:
/// - `file_id` -- [in] id for the file generated by uploading to the file server.
/// - `scheme` -- [in] the scheme for the target file server, uses the default file server scheme if
/// null.
/// - `host` -- [in] the host for the target file server, uses the default file server host if null.
/// - `port` -- [in] the port for the target file server, uses the default file server port if 0.
/// Only written into the url when the scheme does not already imply it.
/// - `pubkey_hex` -- [in] the pubkey for the target file server (in hex), uses the default file
/// server pubkey if null.
/// - `use_stream_encryption` -- [in] flag indicating whether the file should use stream encryption.
/// - `out_url` -- [out] generated download url.
/// - `out_url_len` -- [in] size of the url buffer provided.
///
/// Outputs:
/// - returns true if url was successfully generated and copied into the buffer, false if otherwise
/// (including if the buffer was too small).
LIBSESSION_EXPORT bool session_file_server_generate_download_url(
        const char* file_id,
        const char* scheme,
        const char* host,
        uint16_t port,
        const char* pubkey_hex,
        bool use_stream_encryption,
        char* out_url,
        size_t out_url_len);

/// API: session_file_server/session_file_server_get_client_version
///
/// Constructs a request to retrieve the version information for the given platform.
///
/// Inputs:
/// - `platform` -- [in] the platform to retrieve the client version for.
/// - `ed25519_secret` -- [in] the users ed25519 secret key (used for blinded auth - 64 bytes).
/// - `request_timeout_ms` -- [in] timeout in milliseconds to use for the request.  This won't take
/// the path build into account so if the path build takes forever then this request will never
/// timeout.
/// - `request_and_path_build_timeout_ms` -- [in] timeout in milliseconds to use for the request and
/// path build (if required).  This value takes presedence over `request_timeout_ms` if provided,
/// the request itself will be given a timeout of this value subtracting however long it took to
/// build the path.  A value of `0` will be ignored and `request_timeout_ms` will be used instead.
/// - `callback` -- [in] callback to be called with the result of the request.
/// - `ctx` -- [in, optional] Pointer to an optional context to pass through to the callback.  Set
/// to NULL if unused.
LIBSESSION_EXPORT session_request_params* session_file_server_get_client_version(
        CLIENT_PLATFORM platform,
        const unsigned char* ed25519_secret, /* 64 bytes */
        int64_t request_timeout_ms,
        int64_t overall_timeout_ms);

#ifdef __cplusplus
}
#endif
