{"swagger": "2.0", "info": {"title": "vBase API", "description": "<a target='_blank' href='https://docs.vbase.com/'>vBase Documentation</a>", "version": "v1"}, "host": "app.vbase.com", "schemes": ["https"], "basePath": "/api/v1", "consumes": ["application/json"], "produces": ["application/json"], "securityDefinitions": {"Bearer": {"type": "apiKey", "name": "Authorization", "in": "header", "description": "Bearer token"}}, "security": [{"Bearer": []}], "paths": {"/collections": {"get": {"operationId": "collections_list", "description": "Get user collections with optional filtering", "parameters": [{"name": "user_address", "in": "query", "description": "Filter by user address", "required": false, "type": "string"}, {"name": "is_pinned", "in": "query", "description": "Filter by pinned status", "required": false, "type": "boolean"}], "responses": {"200": {"description": "Collections retrieved successfully", "schema": {"type": "array", "items": {"$ref": "#/definitions/Collection"}}}, "400": {"description": "Bad request - invalid query parameters", "schema": {"$ref": "#/definitions/Error"}}, "404": {"description": "User not found", "schema": {"$ref": "#/definitions/Error"}}}, "tags": ["Collections"]}, "post": {"operationId": "collections_create", "description": "Create a new user collection", "parameters": [{"name": "data", "in": "body", "required": true, "schema": {"required": ["name"], "type": "object", "properties": {"name": {"description": "Collection name", "type": "string"}, "cid": {"description": "Collection CID", "type": "string"}, "description": {"description": "Collection description", "type": "string"}, "is_pinned": {"description": "Whether the collection is pinned", "type": "boolean"}}}}], "responses": {"201": {"description": "Collection created successfully", "schema": {"$ref": "#/definitions/Collection"}}, "400": {"description": "Bad request - validation error", "schema": {"$ref": "#/definitions/Error"}}, "409": {"description": "Conflict - collection already exists", "schema": {"$ref": "#/definitions/Error"}}}, "tags": ["Collections"]}, "parameters": []}, "/collections/verify": {"post": {"operationId": "collections_verify_create", "summary": "Verify a user collection against the blockchain", "description": "\nVerify a collection of stamped objects against the blockchain.\n\nUse the request `Content-Type` to choose the payload format:\n\n**Raw JSON body**\n```json\n{\n  \"collection_name\": \"my-collection\",\n  \"user_address\": \"0x123...\",\n  \"objects\": [\n    {\n      \"cid\": \"cid1\",\n      \"timestamp\": \"2024-01-01T00:00:00+00:00\"\n    }\n  ]\n}\n```\n\n**Raw CSV body**\nSend the CSV string directly with `Content-Type: text/csv`, for example:\n\n```csv\ncollection_name,user_address,collection_timezone\nvb-test,0x4A281DdC750359d5C0D2D51A890cefA43485EF2d,\nt,c,f\n2025-07-23 11:42:15+00:00,0x6f3328cba0ffde8429e66008708419751921bf41737e32a0fcd173849e325561,application-logs2025-07-15T19_46_13.098Z-2025-07-16T19_46_13.098Z_2025-07-23_11-42-15+0000.json\n2025-07-23 20:34:58+00:00,0xaeda4cf7d65f9d67b128bf795b5f237183550a814c9d4aa83c7e84f027d4aeec,attribcache140_2025-07-23_20-34-58+0000.bin\n```\n\n`collection_name` and `user_address` are optional in JSON requests. When\nomitted, the backend will try to infer metadata from the payload.\n\nFor CSV requests, the leading metadata section\n`collection_name,user_address,collection_timezone` is optional.\n\n**Multipart/form-data (legacy)**\nUpload a `.csv` or `.json` file in the `file` field. The payload is normalized\nto the same validated API model as raw JSON and raw CSV requests.\n\n`Accept` controls the response type. This endpoint currently returns JSON.\n", "parameters": [{"name": "data", "in": "body", "required": true, "schema": {"description": "For application/json requests, send the raw verify-user-collection request payload with optional collection_name, user_address, context, and file_name fields. For CSV, send the raw request body with Content-Type: text/csv. Legacy multipart/form-data file uploads are also supported.", "type": "object"}}, {"name": "Accept", "in": "header", "description": "Preferred response media type. Use application/json.", "type": "string", "default": "application/json"}], "responses": {"200": {"description": "Verification result", "schema": {"$ref": "#/definitions/VerifyCollectionResponse"}, "examples": {"application/json": {"display_timezone": "UTC", "collections": [{"name": "my-collection", "cid": "0x329c036f2bcedbb9c44521c22a84d82ae328fef03e942c42b447d4ae67bbd800", "user_address": "0x4A281DdC750359d5C0D2D51A890cefA43485EF2d", "matched_receipts": [{"transaction_hash": "0xbe3f57e7ad7b00e79f88b3f9ffc9fdee84d3251cfc2d121386d8fe793b0d782a", "user_address": "0x4A281DdC750359d5C0D2D51A890cefA43485EF2d", "set_cid": "0x329c036f2bcedbb9c44521c22a84d82ae328fef03e942c42b447d4ae67bbd800", "object_cid": "0x6f3328cba0ffde8429e66008708419751921bf41737e32a0fcd173849e325561", "timestamp": "2025-07-23T11:42:15+00:00", "chain_id": 8453}], "unmatched_objects": [{"cid": "0xaeda4cf7d65f9d67b128bf795b5f237183550a814c9d4aa83c7e84f027d4aeec", "timestamp": "2025-07-23T20:34:58+00:00"}], "unmatched_receipts": []}]}}}, "400": {"description": "Invalid input data", "schema": {"$ref": "#/definitions/Error"}}}, "tags": ["Collections"], "security": [{"Bearer": []}]}, "parameters": []}, "/stamp/": {"post": {"operationId": "stamp_create", "summary": "[DEPRECATED] Stamp a file, inline data, or CID", "description": "\n**DEPRECATED**: This endpoint is deprecated. Please use `/api/v1/stamps` instead.\n\nThis endpoint allows users to stamp a file, inline data, or an existing CID.\nAccepts file, inline data, or CID and returns a stamp record with metadata.\nAt least one of 'file', 'data', or 'data_cid' must be provided.\n\nCollection can be specified using either:\n- collection_cid: Direct CID of the collection\n- collection_name: Name of the collection (case-insensitive, will be converted to CID)\n\nOnly one collection parameter can be specified.\n\nFor 'data' parameter, you can optionally specify 'file_name' to customize the file name\ninstead of using the auto-generated name based on CID.\n", "parameters": [{"name": "file", "in": "formData", "description": "Binary file to be stamped", "required": false, "type": "file"}, {"name": "data", "in": "formData", "description": "Inline text or JSON data", "required": false, "type": "string", "default": "{\"hello\": \"world\"}"}, {"name": "file_name", "in": "formData", "description": "Custom file name for data (only used when 'data' is provided)", "required": false, "type": "string"}, {"name": "data_cid", "in": "formData", "description": "Existing CID to stamp", "required": false, "type": "string"}, {"name": "collection_cid", "in": "formData", "description": "Optional CID of collection to group stamped object", "required": false, "type": "string"}, {"name": "collection_name", "in": "formData", "description": "Optional name of collection to group stamped object (case-insensitive)", "required": false, "type": "string"}, {"name": "store_stamped_file", "in": "formData", "description": "Whether to store the stamped file", "required": false, "type": "boolean", "default": true}, {"name": "idempotent", "in": "formData", "description": "Enable idempotency", "required": false, "type": "boolean", "default": true}, {"name": "idempotency_window", "in": "formData", "description": "Idempotency window in seconds", "required": false, "type": "integer", "default": 3600}], "responses": {"200": {"description": "Idempotent request - returning previous stamp.", "schema": {"$ref": "#/definitions/IdempotentStampResponse"}}, "201": {"description": "Stamp created successfully", "schema": {"$ref": "#/definitions/StampCreatedResponse"}}, "400": {"description": "Bad request - invalid input or idempotent conflict", "schema": {"$ref": "#/definitions/Error"}}, "500": {"description": "Internal server error", "schema": {"$ref": "#/definitions/Error"}}}, "consumes": ["multipart/form-data", "application/x-www-form-urlencoded"], "tags": ["Stamps"], "security": [{"Bearer": []}], "deprecated": true}, "parameters": []}, "/stamps": {"post": {"operationId": "stamps_create", "summary": "Stamp a file, inline data, or CID", "description": "\nThis endpoint allows users to stamp a file, inline data, or an existing CID.\nAccepts file, inline data, or CID and returns a stamp record with metadata.\nAt least one of 'file', 'data', or 'data_cid' must be provided.\n\nCollection can be specified using either:\n- collection_cid: Direct CID of the collection\n- collection_name: Name of the collection (case-insensitive, will be converted to CID)\n\nOnly one collection parameter can be specified.\n\nFor 'data' parameter, you can optionally specify 'file_name' to customize the file name\ninstead of using the auto-generated name based on CID.\n", "parameters": [{"name": "file", "in": "formData", "description": "Binary file to be stamped", "required": false, "type": "file"}, {"name": "data", "in": "formData", "description": "Inline text or JSON data", "required": false, "type": "string", "default": "{\"hello\": \"world\"}"}, {"name": "file_name", "in": "formData", "description": "Custom file name for data (only used when 'data' is provided)", "required": false, "type": "string"}, {"name": "data_cid", "in": "formData", "description": "Existing CID to stamp", "required": false, "type": "string"}, {"name": "collection_cid", "in": "formData", "description": "Optional CID of collection to group stamped object", "required": false, "type": "string"}, {"name": "collection_name", "in": "formData", "description": "Optional name of collection to group stamped object (case-insensitive)", "required": false, "type": "string"}, {"name": "store_stamped_file", "in": "formData", "description": "Whether to store the stamped file", "required": false, "type": "boolean", "default": true}, {"name": "idempotent", "in": "formData", "description": "Enable idempotency", "required": false, "type": "boolean", "default": true}, {"name": "idempotency_window", "in": "formData", "description": "Idempotency window in seconds", "required": false, "type": "integer", "default": 3600}], "responses": {"200": {"description": "Idempotent request - returning previous stamp.", "schema": {"$ref": "#/definitions/IdempotentStampResponse"}}, "201": {"description": "Stamp created successfully", "schema": {"$ref": "#/definitions/StampCreatedResponse"}}, "400": {"description": "Bad request - invalid input or idempotent conflict", "schema": {"$ref": "#/definitions/Error"}}, "500": {"description": "Internal server error", "schema": {"$ref": "#/definitions/Error"}}}, "consumes": ["multipart/form-data", "application/x-www-form-urlencoded"], "tags": ["Stamps"], "security": [{"Bearer": []}]}, "parameters": []}, "/stamps/upload-stamped-file": {"post": {"operationId": "stamps_upload-stamped-file_create", "summary": "Upload a stamped file", "description": "\nThis endpoint allows users to upload a file that has been previously stamped.\nIt validates that the file exists in the blockchain for the authenticated user and specified collection.\n\nThe collection can be specified using either:\n- collection_name: Name of the collection (case-insensitive)\n- collection_cid: CID of the collection\n\nAt least one of 'collection_name' or 'collection_cid' must be provided.\nIf both are provided, the stored CID for the named collection must match the provided collection_cid.\n\nThe endpoint performs the following validations:\n- Ensures at least one collection identifier is provided.\n- Finds the collection for the authenticated user.\n- Extracts the object CID from the uploaded file.\n- Verifies that the file exists in blockchain records for the user's address and collection.\n- Uploads a separate copy of the file for each matching record.\n\nNote: User address is automatically determined from the authenticated user's profile.\n\nReturns structured error responses with appropriate HTTP status codes:\n- 400: Invalid input or validation failed, or collection_cid does not match collection_name\n- 404: Collection not found or no blockchain records found\n- 409: Multiple blockchain records found (conflict)\n- 500: File processing, blockchain, or upload errors\n", "parameters": [{"name": "collection_name", "in": "formData", "description": "Collection name for blockchain verification (case-insensitive)", "required": false, "type": "string"}, {"name": "collection_cid", "in": "formData", "description": "Collection CID for blockchain verification", "required": false, "type": "string"}, {"name": "file", "in": "formData", "description": "Previously stamped file to be uploaded", "required": false, "type": "file"}, {"name": "data", "in": "formData", "description": "Inline text or JSON data (alternative to file)", "required": false, "type": "string"}, {"name": "file_name", "in": "formData", "description": "Custom file name for data (only used when 'data' is provided)", "required": false, "type": "string"}], "responses": {"200": {"description": "File was already uploaded. Returns the existing file object.", "schema": {"$ref": "#/definitions/StampCreatedResponse"}}, "201": {"description": "File uploaded successfully", "schema": {"$ref": "#/definitions/StampCreatedResponse"}}, "400": {"description": "Invalid input or validation failed", "schema": {"$ref": "#/definitions/Error"}}, "404": {"description": "Collection not found or no blockchain records found", "schema": {"$ref": "#/definitions/Error"}}, "409": {"description": "Multiple blockchain records found for same user/collection", "schema": {"$ref": "#/definitions/Error"}}}, "consumes": ["multipart/form-data", "application/x-www-form-urlencoded"], "tags": ["Stamps"], "security": [{"Bearer": []}]}, "parameters": []}, "/stamps/verify": {"post": {"operationId": "stamps_verify_create", "summary": "Verify one or more Content IDs (CIDs)", "description": "\nThis endpoint checks whether Content IDs (SHA3 hash) have previously been\nstamped on the blockchain using vBase. If a match is found, the api returns the full stamp details,\nincluding the timestamp, blockchain address, and other stamp details.\n", "parameters": [{"name": "data", "in": "body", "required": true, "schema": {"required": ["cids"], "type": "object", "properties": {"cids": {"description": "Array of CIDs to verify", "type": "array", "items": {"type": "string"}, "example": ["0xbd...1"]}, "filter_by_user": {"description": "When true, only return results owned by the current user", "type": "boolean", "example": false}}}}], "responses": {"200": {"description": "OK", "schema": {"$ref": "#/definitions/VerificationResult"}}, "400": {"description": "Invalid input data", "schema": {"$ref": "#/definitions/Error"}}}, "tags": ["Stamps"], "security": [{"Bearer": []}]}, "parameters": []}, "/users/me": {"get": {"operationId": "users_me_list", "description": "Handle GET request to retrieve user account settings.", "parameters": [], "responses": {"200": {"description": "Account settings retrieved successfully", "schema": {"$ref": "#/definitions/AccountSettings"}}, "404": {"description": "User not found", "schema": {"$ref": "#/definitions/Error"}}}, "tags": ["Users"]}, "parameters": []}, "/users/{user_address}": {"get": {"operationId": "users_read", "description": "Handle GET request to retrieve user account settings.", "parameters": [], "responses": {"200": {"description": "Account settings retrieved successfully", "schema": {"$ref": "#/definitions/AccountSettings"}}, "404": {"description": "User not found", "schema": {"$ref": "#/definitions/Error"}}}, "tags": ["Users"]}, "parameters": [{"name": "user_address", "in": "path", "required": true, "type": "string"}]}}, "definitions": {"Collection": {"type": "object", "properties": {"id": {"title": "Id", "type": "integer"}, "name": {"title": "Name", "type": "string", "minLength": 1}, "cid": {"title": "Cid", "type": "string", "minLength": 1}, "is_pinned": {"title": "Is pinned", "type": "boolean"}, "is_portfolio": {"title": "Is portfolio", "type": "boolean"}, "is_portfolio_collection": {"title": "Is portfolio collection", "type": "boolean"}, "is_public": {"title": "Is public", "type": "boolean"}, "created_at": {"title": "Created at", "type": "string", "format": "date-time"}, "description": {"title": "Description", "type": "string", "minLength": 1}}}, "Error": {"type": "object", "properties": {"error": {"title": "Error", "type": "string", "minLength": 1}, "details": {"title": "Details", "type": "string", "minLength": 1}}}, "CommitmentReceipt": {"type": "object", "properties": {"transaction_hash": {"title": "Transaction hash", "type": "string", "minLength": 1}, "user_address": {"title": "User address", "type": "string", "minLength": 1}, "set_cid": {"title": "Set cid", "type": "string", "minLength": 1}, "object_cid": {"title": "Object cid", "type": "string", "minLength": 1}, "timestamp": {"title": "Timestamp", "type": "string", "minLength": 1}, "chain_id": {"title": "Chain id", "type": "integer"}}}, "UnmatchedObject": {"required": ["cid", "timestamp"], "type": "object", "properties": {"cid": {"title": "Cid", "type": "string", "minLength": 1}, "timestamp": {"title": "Timestamp", "type": "string", "minLength": 1}}}, "VerifyCollection": {"type": "object", "properties": {"name": {"title": "Name", "type": "string", "minLength": 1, "x-nullable": true}, "cid": {"title": "Cid", "type": "string", "minLength": 1, "x-nullable": true}, "user_address": {"title": "User address", "type": "string", "minLength": 1, "x-nullable": true}, "matched_receipts": {"type": "array", "items": {"$ref": "#/definitions/CommitmentReceipt"}}, "unmatched_objects": {"type": "array", "items": {"$ref": "#/definitions/UnmatchedObject"}}, "unmatched_receipts": {"type": "array", "items": {"$ref": "#/definitions/CommitmentReceipt"}}}}, "VerifyCollectionResponse": {"type": "object", "properties": {"display_timezone": {"title": "Display timezone", "type": "string", "minLength": 1}, "collections": {"type": "array", "items": {"$ref": "#/definitions/VerifyCollection"}}}}, "IdempotentStampResponse": {"type": "object", "properties": {"commitment_receipt": {"$ref": "#/definitions/CommitmentReceipt"}}}, "FileObject": {"type": "object", "properties": {"file_name": {"title": "File name", "type": "string", "minLength": 1}, "file_path": {"title": "File path", "type": "string", "minLength": 1}}}, "StampCreatedResponse": {"type": "object", "properties": {"commitment_receipt": {"$ref": "#/definitions/CommitmentReceipt"}, "file_object": {"$ref": "#/definitions/FileObject"}}}, "VerificationResult": {"type": "object", "properties": {"display_timezone": {"title": "Display timezone", "type": "string", "minLength": 1}, "stamp_list": {"type": "array", "items": {"$ref": "#/definitions/CommitmentReceipt"}}}}, "AccountSettings": {"type": "object", "properties": {"name": {"title": "Name", "type": "string", "minLength": 1}, "email": {"title": "Email", "type": "string", "format": "email", "minLength": 1}, "persistent_id": {"title": "Persistent id", "type": "string", "minLength": 1}, "description": {"title": "Description", "type": "string", "minLength": 1}, "display_timezone": {"title": "Display timezone", "type": "string", "minLength": 1}, "date_joined": {"title": "Date joined", "type": "string", "format": "date-time"}, "last_address": {"title": "Last address", "type": "string", "minLength": 1}, "last_name": {"title": "Last name", "type": "string", "minLength": 1}, "last_is_verified": {"title": "Last is verified", "type": "boolean"}, "storage_type": {"title": "Storage type", "type": "string", "minLength": 1}}}}}