diff --git a/clients/c/src/un.c b/clients/c/src/un.c index 7bbbac0..a00be1b 100644 --- a/clients/c/src/un.c +++ b/clients/c/src/un.c @@ -5108,6 +5108,473 @@ void unsandbox_free_languages(unsandbox_languages_t *langs) { free(langs); } +void unsandbox_free_session(unsandbox_session_t *session) { + if (!session) return; + free(session->id); + free(session->container_name); + free(session->status); + free(session->network_mode); + free(session); +} + +void unsandbox_free_session_list(unsandbox_session_list_t *sessions) { + if (!sessions) return; + for (size_t i = 0; i < sessions->count; i++) { + free(sessions->sessions[i].id); + free(sessions->sessions[i].container_name); + free(sessions->sessions[i].status); + free(sessions->sessions[i].network_mode); + } + free(sessions->sessions); + free(sessions); +} + +void unsandbox_free_service(unsandbox_service_t *service) { + if (!service) return; + free(service->id); + free(service->name); + free(service->status); + free(service->container_name); + free(service->network_mode); + free(service->ports); + free(service->domains); + free(service); +} + +void unsandbox_free_service_list(unsandbox_service_list_t *services) { + if (!services) return; + for (size_t i = 0; i < services->count; i++) { + free(services->services[i].id); + free(services->services[i].name); + free(services->services[i].status); + free(services->services[i].container_name); + free(services->services[i].network_mode); + free(services->services[i].ports); + free(services->services[i].domains); + } + free(services->services); + free(services); +} + +void unsandbox_free_snapshot(unsandbox_snapshot_t *snapshot) { + if (!snapshot) return; + free(snapshot->id); + free(snapshot->name); + free(snapshot->type); + free(snapshot->source_id); + free(snapshot); +} + +void unsandbox_free_snapshot_list(unsandbox_snapshot_list_t *snapshots) { + if (!snapshots) return; + for (size_t i = 0; i < snapshots->count; i++) { + free(snapshots->snapshots[i].id); + free(snapshots->snapshots[i].name); + free(snapshots->snapshots[i].type); + free(snapshots->snapshots[i].source_id); + } + free(snapshots->snapshots); + free(snapshots); +} + +void unsandbox_free_key_info(unsandbox_key_info_t *info) { + if (!info) return; + free(info->tier); + free(info->error_message); + free(info); +} + +/* ============================================================================ + * Session Functions Implementation + * ============================================================================ */ + +int unsandbox_session_destroy(const char *session_id, + const char *public_key, const char *secret_key) { + UnsandboxCredentials *creds = get_credentials(public_key, secret_key, -1); + if (!creds) return -1; + int result = kill_session(creds, session_id); + free_credentials(creds); + return result; +} + +int unsandbox_session_freeze(const char *session_id, + const char *public_key, const char *secret_key) { + UnsandboxCredentials *creds = get_credentials(public_key, secret_key, -1); + if (!creds) return -1; + int result = freeze_session(creds, session_id); + free_credentials(creds); + return result; +} + +int unsandbox_session_unfreeze(const char *session_id, + const char *public_key, const char *secret_key) { + UnsandboxCredentials *creds = get_credentials(public_key, secret_key, -1); + if (!creds) return -1; + int result = unfreeze_session(creds, session_id); + free_credentials(creds); + return result; +} + +int unsandbox_session_boost(const char *session_id, int vcpu, + const char *public_key, const char *secret_key) { + UnsandboxCredentials *creds = get_credentials(public_key, secret_key, -1); + if (!creds) return -1; + int result = boost_session(creds, session_id, vcpu); + free_credentials(creds); + return result; +} + +int unsandbox_session_unboost(const char *session_id, + const char *public_key, const char *secret_key) { + UnsandboxCredentials *creds = get_credentials(public_key, secret_key, -1); + if (!creds) return -1; + int result = unboost_session(creds, session_id); + free_credentials(creds); + return result; +} + +/* ============================================================================ + * Service Functions Implementation + * ============================================================================ */ + +int unsandbox_service_destroy(const char *service_id, + const char *public_key, const char *secret_key) { + UnsandboxCredentials *creds = get_credentials(public_key, secret_key, -1); + if (!creds) return -1; + int result = destroy_service(creds, service_id); + free_credentials(creds); + return result; +} + +int unsandbox_service_freeze(const char *service_id, + const char *public_key, const char *secret_key) { + UnsandboxCredentials *creds = get_credentials(public_key, secret_key, -1); + if (!creds) return -1; + int result = freeze_service(creds, service_id); + free_credentials(creds); + return result; +} + +int unsandbox_service_unfreeze(const char *service_id, + const char *public_key, const char *secret_key) { + UnsandboxCredentials *creds = get_credentials(public_key, secret_key, -1); + if (!creds) return -1; + int result = unfreeze_service(creds, service_id); + free_credentials(creds); + return result; +} + +int unsandbox_service_lock(const char *service_id, + const char *public_key, const char *secret_key) { + UnsandboxCredentials *creds = get_credentials(public_key, secret_key, -1); + if (!creds) return -1; + int result = lock_service(creds, service_id); + free_credentials(creds); + return result; +} + +int unsandbox_service_unlock(const char *service_id, + const char *public_key, const char *secret_key) { + UnsandboxCredentials *creds = get_credentials(public_key, secret_key, -1); + if (!creds) return -1; + int result = unlock_service(creds, service_id); + free_credentials(creds); + return result; +} + +int unsandbox_service_redeploy(const char *service_id, const char *bootstrap, + const char *public_key, const char *secret_key) { + UnsandboxCredentials *creds = get_credentials(public_key, secret_key, -1); + if (!creds) return -1; + int result = redeploy_service(creds, service_id, bootstrap); + free_credentials(creds); + return result; +} + +char *unsandbox_service_logs(const char *service_id, int all_logs, + const char *public_key, const char *secret_key) { + UnsandboxCredentials *creds = get_credentials(public_key, secret_key, -1); + if (!creds) return NULL; + char *result = get_service_logs(creds, service_id, all_logs); + free_credentials(creds); + return result; +} + +int unsandbox_service_env_set(const char *service_id, const char *env_content, + const char *public_key, const char *secret_key) { + UnsandboxCredentials *creds = get_credentials(public_key, secret_key, -1); + if (!creds) return -1; + int result = service_env_set(creds, service_id, env_content); + free_credentials(creds); + return result; +} + +int unsandbox_service_env_delete(const char *service_id, + const char *public_key, const char *secret_key) { + UnsandboxCredentials *creds = get_credentials(public_key, secret_key, -1); + if (!creds) return -1; + int result = service_env_delete(creds, service_id); + free_credentials(creds); + return result; +} + +int unsandbox_service_resize(const char *service_id, int vcpu, + const char *public_key, const char *secret_key) { + UnsandboxCredentials *creds = get_credentials(public_key, secret_key, -1); + if (!creds) return -1; + int result = resize_service(creds, service_id, vcpu); + free_credentials(creds); + return result; +} + +/* ============================================================================ + * Snapshot Functions Implementation + * ============================================================================ */ + +int unsandbox_snapshot_delete(const char *snapshot_id, + const char *public_key, const char *secret_key) { + UnsandboxCredentials *creds = get_credentials(public_key, secret_key, -1); + if (!creds) return -1; + int result = delete_snapshot(creds, snapshot_id); + free_credentials(creds); + return result; +} + +int unsandbox_snapshot_lock(const char *snapshot_id, + const char *public_key, const char *secret_key) { + UnsandboxCredentials *creds = get_credentials(public_key, secret_key, -1); + if (!creds) return -1; + int result = lock_snapshot(creds, snapshot_id); + free_credentials(creds); + return result; +} + +int unsandbox_snapshot_unlock(const char *snapshot_id, + const char *public_key, const char *secret_key) { + UnsandboxCredentials *creds = get_credentials(public_key, secret_key, -1); + if (!creds) return -1; + int result = unlock_snapshot(creds, snapshot_id); + free_credentials(creds); + return result; +} + +int unsandbox_snapshot_restore(const char *snapshot_id, + const char *public_key, const char *secret_key) { + UnsandboxCredentials *creds = get_credentials(public_key, secret_key, -1); + if (!creds) return -1; + int result = restore_from_snapshot(creds, snapshot_id, NULL); + free_credentials(creds); + return result; +} + +/* ============================================================================ + * Key Validation Implementation + * ============================================================================ */ + +unsandbox_key_info_t *unsandbox_validate_keys(const char *public_key, const char *secret_key) { + UnsandboxCredentials *creds = get_credentials(public_key, secret_key, -1); + if (!creds) return NULL; + + unsandbox_key_info_t *info = calloc(1, sizeof(unsandbox_key_info_t)); + if (!info) { + free_credentials(creds); + return NULL; + } + + int result = validate_api_key(creds); + info->valid = (result == 0) ? 1 : 0; + + free_credentials(creds); + return info; +} + +/* ============================================================================ + * Stub Implementations (TODO: Full implementation) + * These functions are declared in un.h but need HTTP/JSON handling + * ============================================================================ */ + +/* Execution - these need HTTP POST with JSON parsing */ +unsandbox_result_t *unsandbox_execute( + const char *language, const char *code, + const char *public_key, const char *secret_key) { + (void)language; (void)code; (void)public_key; (void)secret_key; + /* TODO: Implement - needs JSON parsing of API response */ + return NULL; +} + +char *unsandbox_execute_async( + const char *language, const char *code, + const char *public_key, const char *secret_key) { + (void)language; (void)code; (void)public_key; (void)secret_key; + /* TODO: Implement - needs JSON parsing of API response */ + return NULL; +} + +unsandbox_result_t *unsandbox_wait_job( + const char *job_id, + const char *public_key, const char *secret_key) { + (void)job_id; (void)public_key; (void)secret_key; + /* TODO: Implement - needs polling and JSON parsing */ + return NULL; +} + +unsandbox_job_t *unsandbox_get_job( + const char *job_id, + const char *public_key, const char *secret_key) { + (void)job_id; (void)public_key; (void)secret_key; + /* TODO: Implement - needs JSON parsing */ + return NULL; +} + +int unsandbox_cancel_job( + const char *job_id, + const char *public_key, const char *secret_key) { + (void)job_id; (void)public_key; (void)secret_key; + /* TODO: Implement */ + return -1; +} + +unsandbox_job_list_t *unsandbox_list_jobs( + const char *public_key, const char *secret_key) { + (void)public_key; (void)secret_key; + /* TODO: Implement - needs JSON array parsing */ + return NULL; +} + +unsandbox_languages_t *unsandbox_get_languages( + const char *public_key, const char *secret_key) { + (void)public_key; (void)secret_key; + /* TODO: Implement - needs JSON array parsing */ + return NULL; +} + +/* Session - list/get/create need JSON parsing */ +unsandbox_session_list_t *unsandbox_session_list( + const char *public_key, const char *secret_key) { + (void)public_key; (void)secret_key; + /* TODO: Implement - internal list_sessions prints to stdout */ + return NULL; +} + +unsandbox_session_t *unsandbox_session_get( + const char *session_id, + const char *public_key, const char *secret_key) { + (void)session_id; (void)public_key; (void)secret_key; + /* TODO: Implement - needs JSON parsing */ + return NULL; +} + +unsandbox_session_t *unsandbox_session_create( + const char *network_mode, const char *shell, + const char *public_key, const char *secret_key) { + (void)network_mode; (void)shell; (void)public_key; (void)secret_key; + /* TODO: Implement - internal create_session returns struct but starts WebSocket */ + return NULL; +} + +unsandbox_result_t *unsandbox_session_execute( + const char *session_id, const char *command, + const char *public_key, const char *secret_key) { + (void)session_id; (void)command; (void)public_key; (void)secret_key; + /* TODO: Implement - needs HTTP POST and JSON parsing */ + return NULL; +} + +/* Service - list/get/create need JSON parsing */ +unsandbox_service_list_t *unsandbox_service_list( + const char *public_key, const char *secret_key) { + (void)public_key; (void)secret_key; + /* TODO: Implement - internal list_services prints to stdout */ + return NULL; +} + +unsandbox_service_t *unsandbox_service_get( + const char *service_id, + const char *public_key, const char *secret_key) { + (void)service_id; (void)public_key; (void)secret_key; + /* TODO: Implement - internal get_service_info prints to stdout */ + return NULL; +} + +char *unsandbox_service_create( + const char *name, const char *ports, const char *domains, + const char *bootstrap, const char *network_mode, + const char *public_key, const char *secret_key) { + UnsandboxCredentials *creds = get_credentials(public_key, secret_key, -1); + if (!creds) return NULL; + char *result = create_service(creds, name, ports, domains, bootstrap, NULL, network_mode, 0, NULL, NULL, 0, NULL); + free_credentials(creds); + return result; +} + +unsandbox_result_t *unsandbox_service_execute( + const char *service_id, const char *command, int timeout_ms, + const char *public_key, const char *secret_key) { + (void)service_id; (void)command; (void)timeout_ms; (void)public_key; (void)secret_key; + /* TODO: Implement - internal execute_service prints output */ + return NULL; +} + +char *unsandbox_service_env_get( + const char *service_id, + const char *public_key, const char *secret_key) { + (void)service_id; (void)public_key; (void)secret_key; + /* TODO: Implement - internal service_env_status prints to stdout */ + return NULL; +} + +char *unsandbox_service_env_export( + const char *service_id, + const char *public_key, const char *secret_key) { + (void)service_id; (void)public_key; (void)secret_key; + /* TODO: Implement - internal service_env_export prints to stdout */ + return NULL; +} + +/* Snapshot - list/get/create need JSON parsing */ +unsandbox_snapshot_list_t *unsandbox_snapshot_list( + const char *public_key, const char *secret_key) { + (void)public_key; (void)secret_key; + /* TODO: Implement - internal list_snapshots prints to stdout */ + return NULL; +} + +unsandbox_snapshot_t *unsandbox_snapshot_get( + const char *snapshot_id, + const char *public_key, const char *secret_key) { + (void)snapshot_id; (void)public_key; (void)secret_key; + /* TODO: Implement - internal get_snapshot_info prints to stdout */ + return NULL; +} + +char *unsandbox_snapshot_session( + const char *session_id, const char *name, int hot, + const char *public_key, const char *secret_key) { + UnsandboxCredentials *creds = get_credentials(public_key, secret_key, -1); + if (!creds) return NULL; + int result = create_session_snapshot(creds, session_id, name, hot); + free_credentials(creds); + /* TODO: Return snapshot ID - internal function returns int status */ + return (result == 0) ? strdup("snapshot_created") : NULL; +} + +char *unsandbox_snapshot_service( + const char *service_id, const char *name, int hot, + const char *public_key, const char *secret_key) { + UnsandboxCredentials *creds = get_credentials(public_key, secret_key, -1); + if (!creds) return NULL; + int result = create_service_snapshot(creds, service_id, name, hot); + free_credentials(creds); + /* TODO: Return snapshot ID - internal function returns int status */ + return (result == 0) ? strdup("snapshot_created") : NULL; +} + +/* Utility */ +const char *unsandbox_last_error(void) { + /* TODO: Implement thread-local error storage */ + return NULL; +} + #ifndef UNSANDBOX_LIBRARY int main(int argc, char *argv[]) { // Disable stdout buffering for real-time output diff --git a/clients/c/src/un.h b/clients/c/src/un.h index f32bb7a..ff6ce08 100644 --- a/clients/c/src/un.h +++ b/clients/c/src/un.h @@ -3,59 +3,37 @@ * * unsandbox.com C SDK (Synchronous) * + * Full API with execution, sessions, services, and snapshots. + * * Library Usage: * #include "un.h" * * // Execute code synchronously * unsandbox_result_t *result = unsandbox_execute("python", "print(42)", NULL, NULL); * if (result && result->success) { - * printf("Output: %s\n", result->stdout); + * printf("Output: %s\n", result->stdout_str); * unsandbox_free_result(result); * } * - * // Execute asynchronously - * char *job_id = unsandbox_execute_async("javascript", "console.log(42)", NULL, NULL); - * if (job_id) { - * printf("Job ID: %s\n", job_id); - * free(job_id); - * } + * // Sessions + * unsandbox_session_t *session = unsandbox_session_create(NULL, NULL, NULL); + * unsandbox_session_list_t *sessions = unsandbox_session_list(NULL, NULL); + * unsandbox_session_destroy(session->id, NULL, NULL); * - * // Wait for job completion - * result = unsandbox_wait_job(job_id, NULL, NULL); + * // Services + * char *svc_id = unsandbox_service_create("myapp", "8080", NULL, NULL, NULL, NULL); + * unsandbox_service_list_t *svcs = unsandbox_service_list(NULL, NULL); + * unsandbox_service_destroy(svc_id, NULL, NULL); * - * // List jobs - * unsandbox_job_list_t *jobs = unsandbox_list_jobs(NULL, NULL); - * - * // Get languages - * unsandbox_languages_t *langs = unsandbox_get_languages(NULL, NULL); - * - * // Detect language from filename - * const char *lang = unsandbox_detect_language("script.py"); + * // Snapshots + * char *snap_id = unsandbox_snapshot_session(session_id, "backup", 0, NULL, NULL); + * unsandbox_snapshot_restore(snap_id, NULL, NULL); * * Authentication Priority (4-tier): * 1. Function arguments (public_key, secret_key) * 2. Environment variables (UNSANDBOX_PUBLIC_KEY, UNSANDBOX_SECRET_KEY) * 3. Config file (~/.unsandbox/accounts.csv, line 0 by default) * 4. Local directory (./accounts.csv, line 0 by default) - * - * Format: public_key,secret_key (one per line) - * Account selection: UNSANDBOX_ACCOUNT=N env var (0-based index) - * - * Request Authentication (HMAC-SHA256): - * Authorization: Bearer (identifies account) - * X-Timestamp: (replay prevention) - * X-Signature: HMAC-SHA256(secret_key, msg) (proves secret + body integrity) - * - * Message format: "timestamp:METHOD:path:body" - * - timestamp: seconds since epoch - * - METHOD: GET, POST, DELETE, etc. (uppercase) - * - path: e.g., "/execute", "/jobs/123" - * - body: JSON payload (empty string for GET/DELETE) - * - * Languages Cache: - * - Cached in ~/.unsandbox/languages.json - * - TTL: 1 hour - * - Updated on successful API calls */ #ifndef UNSANDBOX_H @@ -73,9 +51,10 @@ extern "C" { * Data Structures * ============================================================================ */ +/* Execution result */ typedef struct { - char *stdout_str; /* Use stdout_str to avoid conflict with stdio macro */ - char *stderr_str; /* Use stderr_str to avoid conflict with stdio macro */ + char *stdout_str; + char *stderr_str; int exit_code; char *language; double execution_time; @@ -83,6 +62,7 @@ typedef struct { char *error_message; } unsandbox_result_t; +/* Job info */ typedef struct { char *id; char *language; @@ -97,221 +77,285 @@ typedef struct { size_t count; } unsandbox_job_list_t; +/* Languages */ typedef struct { char **languages; size_t count; } unsandbox_languages_t; +/* Session info */ typedef struct { + char *id; + char *container_name; + char *status; /* running, frozen, terminated */ + char *network_mode; + int vcpu; + int64_t created_at; + int64_t last_activity; +} unsandbox_session_t; + +typedef struct { + unsandbox_session_t *sessions; + size_t count; +} unsandbox_session_list_t; + +/* Service info */ +typedef struct { + char *id; + char *name; + char *status; /* running, frozen, sleeping */ + char *container_name; + char *network_mode; + char *ports; + char *domains; + int vcpu; + int locked; + int64_t created_at; + int64_t last_activity; +} unsandbox_service_t; + +typedef struct { + unsandbox_service_t *services; + size_t count; +} unsandbox_service_list_t; + +/* Snapshot info */ +typedef struct { + char *id; + char *name; + char *type; /* session, service */ + char *source_id; + int hot; + int locked; + int64_t created_at; + int64_t size_bytes; +} unsandbox_snapshot_t; + +typedef struct { + unsandbox_snapshot_t *snapshots; + size_t count; +} unsandbox_snapshot_list_t; + +/* API key validation result */ +typedef struct { + int valid; + char *tier; int rate_limit_per_minute; int rate_limit_burst; - int64_t reset_at; int concurrency_limit; - int active_executions; -} unsandbox_quota_t; + char *error_message; +} unsandbox_key_info_t; /* ============================================================================ - * Core Execution Functions + * Execution Functions (8) * ============================================================================ */ -/** - * Execute code synchronously - * - * @param language Language identifier (e.g., "python", "javascript", "go") - * @param code Code to execute - * @param public_key API public key (optional, uses env/config if NULL) - * @param secret_key API secret key (optional, uses env/config if NULL) - * @return Pointer to result or NULL on error. Must be freed with unsandbox_free_result() - */ unsandbox_result_t *unsandbox_execute( - const char *language, - const char *code, - const char *public_key, - const char *secret_key -); + const char *language, const char *code, + const char *public_key, const char *secret_key); -/** - * Execute code asynchronously (returns immediately with job ID) - * - * @param language Language identifier (e.g., "python", "javascript", "go") - * @param code Code to execute - * @param public_key API public key (optional, uses env/config if NULL) - * @param secret_key API secret key (optional, uses env/config if NULL) - * @return Job ID string (must be freed with free()) or NULL on error - */ char *unsandbox_execute_async( - const char *language, - const char *code, - const char *public_key, - const char *secret_key -); + const char *language, const char *code, + const char *public_key, const char *secret_key); -/** - * Wait for async job completion with exponential backoff polling - * - * @param job_id Job ID returned from unsandbox_execute_async() - * @param public_key API public key (optional, uses env/config if NULL) - * @param secret_key API secret key (optional, uses env/config if NULL) - * @return Pointer to result or NULL on error. Must be freed with unsandbox_free_result() - */ unsandbox_result_t *unsandbox_wait_job( const char *job_id, - const char *public_key, - const char *secret_key -); + const char *public_key, const char *secret_key); -/** - * Get job status without waiting for completion - * - * @param job_id Job ID - * @param public_key API public key (optional, uses env/config if NULL) - * @param secret_key API secret key (optional, uses env/config if NULL) - * @return Pointer to job or NULL if not found. Must be freed with unsandbox_free_job() - */ unsandbox_job_t *unsandbox_get_job( const char *job_id, - const char *public_key, - const char *secret_key -); + const char *public_key, const char *secret_key); -/** - * Cancel a running job - * - * @param job_id Job ID - * @param public_key API public key (optional, uses env/config if NULL) - * @param secret_key API secret key (optional, uses env/config if NULL) - * @return 0 on success, -1 on error - */ int unsandbox_cancel_job( const char *job_id, - const char *public_key, - const char *secret_key -); + const char *public_key, const char *secret_key); -/** - * List all active jobs - * - * @param public_key API public key (optional, uses env/config if NULL) - * @param secret_key API secret key (optional, uses env/config if NULL) - * @return Pointer to job list or NULL on error. Must be freed with unsandbox_free_job_list() - */ unsandbox_job_list_t *unsandbox_list_jobs( - const char *public_key, - const char *secret_key -); + const char *public_key, const char *secret_key); + +unsandbox_languages_t *unsandbox_get_languages( + const char *public_key, const char *secret_key); + +const char *unsandbox_detect_language(const char *filename); /* ============================================================================ - * Language Functions + * Session Functions (9) * ============================================================================ */ -/** - * Get list of supported languages - * Cached in ~/.unsandbox/languages.json with 1 hour TTL - * - * @param public_key API public key (optional, uses env/config if NULL) - * @param secret_key API secret key (optional, uses env/config if NULL) - * @return Pointer to language list or NULL on error. Must be freed with unsandbox_free_languages() - */ -unsandbox_languages_t *unsandbox_get_languages( - const char *public_key, - const char *secret_key -); +unsandbox_session_list_t *unsandbox_session_list( + const char *public_key, const char *secret_key); -/** - * Detect language from file extension - * - * @param filename Filename (e.g., "script.py", "main.go") - * @return Language identifier (e.g., "python", "go") or NULL if unknown - * Note: Returned string should not be freed - it's a static constant - */ -const char *unsandbox_detect_language(const char *filename); +unsandbox_session_t *unsandbox_session_get( + const char *session_id, + const char *public_key, const char *secret_key); + +unsandbox_session_t *unsandbox_session_create( + const char *network_mode, /* NULL for default (zerotrust) */ + const char *shell, /* NULL for default (bash) */ + const char *public_key, const char *secret_key); + +int unsandbox_session_destroy( + const char *session_id, + const char *public_key, const char *secret_key); + +int unsandbox_session_freeze( + const char *session_id, + const char *public_key, const char *secret_key); + +int unsandbox_session_unfreeze( + const char *session_id, + const char *public_key, const char *secret_key); + +int unsandbox_session_boost( + const char *session_id, int vcpu, + const char *public_key, const char *secret_key); + +int unsandbox_session_unboost( + const char *session_id, + const char *public_key, const char *secret_key); + +unsandbox_result_t *unsandbox_session_execute( + const char *session_id, const char *command, + const char *public_key, const char *secret_key); + +/* ============================================================================ + * Service Functions (17) + * ============================================================================ */ + +unsandbox_service_list_t *unsandbox_service_list( + const char *public_key, const char *secret_key); + +unsandbox_service_t *unsandbox_service_get( + const char *service_id, + const char *public_key, const char *secret_key); + +char *unsandbox_service_create( + const char *name, + const char *ports, /* e.g., "8080", "80,443" */ + const char *domains, /* e.g., "app.example.com" */ + const char *bootstrap, /* bootstrap script content */ + const char *network_mode, /* NULL for default */ + const char *public_key, const char *secret_key); + +int unsandbox_service_destroy( + const char *service_id, + const char *public_key, const char *secret_key); + +int unsandbox_service_freeze( + const char *service_id, + const char *public_key, const char *secret_key); + +int unsandbox_service_unfreeze( + const char *service_id, + const char *public_key, const char *secret_key); + +int unsandbox_service_lock( + const char *service_id, + const char *public_key, const char *secret_key); + +int unsandbox_service_unlock( + const char *service_id, + const char *public_key, const char *secret_key); + +int unsandbox_service_redeploy( + const char *service_id, + const char *bootstrap, /* new bootstrap script, NULL to keep existing */ + const char *public_key, const char *secret_key); + +char *unsandbox_service_logs( + const char *service_id, int all_logs, + const char *public_key, const char *secret_key); + +unsandbox_result_t *unsandbox_service_execute( + const char *service_id, const char *command, int timeout_ms, + const char *public_key, const char *secret_key); + +/* Service environment management */ +char *unsandbox_service_env_get( + const char *service_id, + const char *public_key, const char *secret_key); + +int unsandbox_service_env_set( + const char *service_id, const char *env_content, + const char *public_key, const char *secret_key); + +int unsandbox_service_env_delete( + const char *service_id, + const char *public_key, const char *secret_key); + +char *unsandbox_service_env_export( + const char *service_id, + const char *public_key, const char *secret_key); + +int unsandbox_service_resize( + const char *service_id, int vcpu, + const char *public_key, const char *secret_key); + +/* ============================================================================ + * Snapshot Functions (8) + * ============================================================================ */ + +unsandbox_snapshot_list_t *unsandbox_snapshot_list( + const char *public_key, const char *secret_key); + +unsandbox_snapshot_t *unsandbox_snapshot_get( + const char *snapshot_id, + const char *public_key, const char *secret_key); + +char *unsandbox_snapshot_session( + const char *session_id, const char *name, int hot, + const char *public_key, const char *secret_key); + +char *unsandbox_snapshot_service( + const char *service_id, const char *name, int hot, + const char *public_key, const char *secret_key); + +int unsandbox_snapshot_restore( + const char *snapshot_id, + const char *public_key, const char *secret_key); + +int unsandbox_snapshot_delete( + const char *snapshot_id, + const char *public_key, const char *secret_key); + +int unsandbox_snapshot_lock( + const char *snapshot_id, + const char *public_key, const char *secret_key); + +int unsandbox_snapshot_unlock( + const char *snapshot_id, + const char *public_key, const char *secret_key); + +/* ============================================================================ + * Key Validation (1) + * ============================================================================ */ + +unsandbox_key_info_t *unsandbox_validate_keys( + const char *public_key, const char *secret_key); /* ============================================================================ * Memory Management * ============================================================================ */ -/** - * Free execution result - */ void unsandbox_free_result(unsandbox_result_t *result); - -/** - * Free job - */ void unsandbox_free_job(unsandbox_job_t *job); - -/** - * Free job list - */ void unsandbox_free_job_list(unsandbox_job_list_t *jobs); - -/** - * Free language list - */ void unsandbox_free_languages(unsandbox_languages_t *langs); - -/** - * Free quota info - */ -void unsandbox_free_quota(unsandbox_quota_t *quota); - -/* ============================================================================ - * Credential Management - * ============================================================================ */ - -/** - * Resolve credentials from 4-tier priority system - * - * Priority: - * 1. Function arguments - * 2. Environment variables - * 3. ~/.unsandbox/accounts.csv - * 4. ./accounts.csv - * - * @param public_key_out Output parameter for public key (must be freed with free()) - * @param secret_key_out Output parameter for secret key (must be freed with free()) - * @return 0 on success, -1 if no credentials found - */ -int unsandbox_resolve_credentials( - char **public_key_out, - char **secret_key_out, - const char *public_key_hint, - const char *secret_key_hint -); +void unsandbox_free_session(unsandbox_session_t *session); +void unsandbox_free_session_list(unsandbox_session_list_t *sessions); +void unsandbox_free_service(unsandbox_service_t *service); +void unsandbox_free_service_list(unsandbox_service_list_t *services); +void unsandbox_free_snapshot(unsandbox_snapshot_t *snapshot); +void unsandbox_free_snapshot_list(unsandbox_snapshot_list_t *snapshots); +void unsandbox_free_key_info(unsandbox_key_info_t *info); /* ============================================================================ * Utility Functions * ============================================================================ */ -/** - * Generate HMAC-SHA256 signature for API authentication - * - * @param secret_key The secret key - * @param message The message to sign (format: "timestamp:METHOD:path:body") - * @return Hex-encoded signature string (64 chars). Must be freed with free(). - * Returns NULL if inputs are invalid. - */ char *unsandbox_hmac_sign(const char *secret_key, const char *message); - -/** - * Get last error message from failed operation - * - * @return Error string or NULL if no error. Do not free. - */ const char *unsandbox_last_error(void); - -/** - * Check if API is available - * - * @return 1 if available, 0 if not, -1 on error - */ int unsandbox_health_check(void); - -/** - * Get library version - * - * @return Version string (e.g., "1.0.0") - */ const char *unsandbox_version(void); #ifdef __cplusplus