storage-p

Documentación de la API

La misma API REST sobre la que corre el cliente web. Cada elemento se cifra en tu navegador antes de salir del dispositivo — el servidor solo ve texto cifrado y no puede leerlo. Úsala para construir tus propios clientes o para dar a una integración acceso acotado y confirmable a unos pocos elementos. Base URL: https://storage-p.com

Especificación OpenAPI (legible por máquina, para integraciones) /openapi.yaml

Guías

Recorridos completos de lo que storage-p hace de verdad — basados en el conjunto real de funciones, sin inventar nada.

Auto-alojarlo en tu propio servidor

Ejecuta storage-p como contenedor Docker tras Caddy en tu dominio. Caddy sirve el cliente estático y hace de proxy de /api hacia el backend; la base de datos SQLite está cifrada en reposo con SQLCipher. Lo operas de extremo a extremo — nadie más tiene las claves.

Guardar y generar claves SSH / TLS

Genera claves SSH Ed25519 (formato OpenSSH) y certificados TLS autofirmados en la pestaña Generadores, o sube archivos de clave/certificado existentes (hasta 1 MB). El material privado se cifra en el navegador antes de subirlo, así nunca existe en claro en el servidor.

Enlaces de un solo uso (burn-after-read)

Comparte un elemento o una carpeta entera con un enlace cuya clave de descifrado vive solo en el fragmento de la URL (#…) — la parte que el navegador nunca envía al servidor. Define un TTL y un límite de vistas; tras la última vista, los datos ya no se pueden abrir.

Tokens de API limitados con confirmación

Crea un token que solo pueda leer los elementos o proyectos que autorices. Activa la confirmación por lectura y cada acceso se detiene hasta que lo apruebes desde la campana de la app o un mensaje de Telegram; añade un límite de peticiones y una caducidad. La integración recibe el elemento aún cifrado más una clave de acceso de un solo uso para descifrarlo en local.

Proyectos y acceso del equipo

Convierte una carpeta en un proyecto con su propia clave. Da a otro usuario acceso de lectura o escritura y la clave del proyecto se sella con su clave pública (X25519), de modo que trabaja con los elementos más recientes sin que el servidor vea nunca una copia legible. Revoca cualquier acceso cuando quieras.

TOTP / 2FA integrado

Guarda el secreto TOTP de un inicio de sesión junto a él y lee el código rotativo en vivo en el mismo sitio — storage-p también hace de autenticador. También puedes proteger tu propia cuenta con doble factor TOTP.

Importar desde otro gestor

Trae un JSON de Bitwarden, un CSV de KeePass o cualquier CSV con columnas name/username/password/url/notes. El análisis y el cifrado se ejecutan en tu dispositivo, así las entradas se vuelven a cifrar con tu clave y nunca se suben en claro.

Documentación de la API · API

Autenticación

Obtén un token de acceso vía register/login y envíalo como Bearer. Los tokens de acceso son de corta duración (15 min); renueva con el refresh token.

Authorization: Bearer <access_token>

Auth

Registro, inicio de sesión y mantenimiento de la sesión. La contraseña maestra no sale del navegador — solo se envía un auth-hash Argon2id.

POST /api/v1/auth/register
Crear una cuenta. El cliente elige los parámetros KDF y sube su clave privada ya cifrada.
Cuerpo{ email, master_password, kdf_salt_b64, kdf_memory_kib, kdf_iters, kdf_parallelism, pubkey_b64, privkey_enc_b64 }
Respuesta{ access_token, refresh_token, user_id, kdf_* }
POST /api/v1/auth/login
Iniciar sesión. Devuelve los tokens y la sal KDF que el cliente necesita para derivar la clave de bóveda.
Cuerpo{ email, master_password, totp_code? }
Respuesta{ access_token, refresh_token, user_id, kdf_*, totp_required }
POST /api/v1/auth/refresh
Cambiar un refresh token por un access token nuevo de corta duración.
Cuerpo{ refresh_token }
Respuesta{ access_token, refresh_token }
POST /api/v1/auth/logout Bearer
Revocar el refresh token actual.
Respuesta{ ok }
POST /api/v1/auth/totp/setup Bearer
Activar el doble factor TOTP para la cuenta.
Cuerpo{ secret_b32, current_code }
Respuesta{ ok }

Vault

CRUD sobre tus elementos. Todo entra y sale ya cifrado; el servidor solo guarda y devuelve texto cifrado.

GET /api/v1/vault Bearer
Listar todos los elementos (texto cifrado) de la bóveda.
Respuesta[ { id, meta_enc_b64, body_enc_b64, version, created_at, updated_at } ]
POST /api/v1/vault Bearer
Añadir un elemento. meta/body ya están cifrados en el cliente antes de subirse.
Cuerpo{ meta_enc_b64, body_enc_b64, blind_index_b64? }
Respuesta{ id, ... }
GET /api/v1/vault/:id Bearer
Obtener un elemento por id.
PUT /api/v1/vault/:id Bearer
Actualizar un elemento; expected_version evita sobrescribir un cambio más reciente.
Cuerpo{ meta_enc_b64?, body_enc_b64?, expected_version }
DELETE /api/v1/vault/:id Bearer
Mover un elemento a la papelera (borrado lógico, reversible).
GET /api/v1/vault/trash Bearer
Listar los elementos en la papelera.
POST /api/v1/vault/:id/restore Bearer
Restaurar un elemento de la papelera.
DELETE /api/v1/vault/:id/purge Bearer
Eliminar un elemento de forma permanente — no se puede deshacer.

Sharing

Dos formas de pasar un secreto: un enlace de un solo uso (burn-after-read) o una entrega end-to-end a otro usuario vía sealed-box.

POST /api/v1/share Bearer
Crear un enlace de un solo uso. La clave de descifrado vive en el fragmento de la URL y nunca llega al servidor.
Cuerpo{ payload_b64, nonce_b64, ttl_secs, max_views }
Respuesta{ id, expires_at }
GET /api/v1/share/:id
Abrir un enlace de un solo uso. Se destruye tras el número de vistas permitido.
Respuesta{ payload_b64, nonce_b64 }
GET /api/v1/users/lookup?email= Bearer
Encontrar la clave pública de un usuario por email para compartir end-to-end.
Respuesta{ user_id, pubkey_b64 }
POST /api/v1/shares/user Bearer
Enviar un elemento a otro usuario, sellado con su clave pública — solo él puede abrirlo.
Cuerpo{ to_email, payload_b64 }
GET /api/v1/shares/incoming Bearer
Listar los elementos que otros usuarios han compartido contigo.
DELETE /api/v1/shares/:id Bearer
Eliminar un recurso compartido entrante o saliente.

Tokens & confirmations

Los tokens acotados permiten a una integración leer elementos seleccionados, opcionalmente con tu confirmación en la app o Telegram.

GET /api/v1/tokens Bearer
Listar tus tokens de API.
POST /api/v1/tokens Bearer
Crear un token acotado para una integración — elegir qué elementos puede leer y si cada lectura requiere confirmación.
Cuerpo{ name, item_ids[], require_confirmation, rate_limit_per_hour, ttl_secs }
Respuesta{ id, token, expires_at }
DELETE /api/v1/tokens/:id Bearer
Revocar un token de inmediato.
GET /api/v1/confirmations/pending Bearer
Listar solicitudes de acceso pendientes de tu aprobación.
POST /api/v1/confirmations/:id/resolve Bearer
Aprobar o denegar una solicitud pendiente.
Cuerpo{ decision: "approve"|"deny" }
GET /api/v1/api/vault/:id Bearer (scoped token)
Cómo una integración lee un elemento acotado. Si requiere confirmación, la primera llamada devuelve un confirmation_id para sondear hasta que apruebes.

Tokens API limitados (para integraciones)

Crea un token limitado en la UI (Tokens API). Solo puede leer elementos permitidos, y las lecturas pueden requerir confirmación. Flujo: el primer GET devuelve un confirmation_id con estado pending_confirmation; el propietario aprueba en la app o vía Telegram; repite el GET con ?confirmation_id= para recibir el elemento (aún cifrado en el cliente).

Notas

meta_enc / body_enc son nonce(24)‖ciphertext, cifrados con la clave de bóveda derivada de la contraseña maestra. El servidor no puede descifrarlos.