Skip to main content

Endpoint

This endpoint accepts file uploads and creates a secure download link with optional expiration, view limits, and password protection.
POST /api/links/upload

Content Type

Content-Type: multipart/form-data
This endpoint uses multipart/form-data encoding, not JSON. Make sure your client sets the correct Content-Type header or lets the browser/HTTP client handle it automatically.

Form Parameters

file
file
required
The file to upload. This becomes the download target for the secure link.Validation:
  • Required field
  • Must be a valid file upload
  • File is stored on the server filesystem
Storage:
  • Files are stored with unique identifiers
  • Original filename is preserved in metadata
  • File path is used as the link target
expiresAt
string
ISO 8601 timestamp indicating when the download link should expire.Validation:
  • Must be a future date/time
  • Format: YYYY-MM-DDTHH:mm:ss±HH:mm (ISO 8601 with timezone)
  • If not provided, the link will not have time-based expiration
Example: 2026-12-31T23:59:59+00:00
maxViews
integer
Maximum number of times the file can be downloaded before the link becomes invalid.Validation:
  • Must be a positive integer (> 0)
  • If not provided, the link will not have view-based expiration
Example: 10
password
string
Optional password required to download the file. When set, clients must provide this password via the X-Link-Password header when accessing the download link.Security:
  • Stored as a bcrypt hash
  • Required via HTTP header on file download
  • No length restrictions (recommended: 8+ characters)
Example: filePassword123

Response

shortCode
string
Unique identifier for the created download link. This code is used in the access URL.Format: 8-character alphanumeric stringExample: F5gH7jKl
accessUrl
string
The full URL path to download the file.Format: /l/{shortCode}Example: http://localhost:8080/l/F5gH7jKl
expiresAt
string
ISO 8601 timestamp when the download link expires (if expiration was set).Format: YYYY-MM-DDTHH:mm:ss±HH:mmExample: 2026-12-31T23:59:59+00:00
maxViews
integer
Maximum number of downloads allowed (if view limit was set).Example: 10

Status Codes

201
Created
File uploaded successfully and download link created. Response body contains the link details.
400
Bad Request
Request validation failed. Possible causes:
  • Missing or invalid file upload
  • expiresAt is not a future date
  • maxViews is not a positive integer
  • Invalid multipart/form-data format
Error response includes:
  • timestamp: When the error occurred
  • status: HTTP status code (400)
  • error: “Bad Request”
  • message: Specific validation error
  • path: Request path that caused the error
500
Internal Server Error
Unexpected server error occurred (e.g., file storage failure).Error response includes:
  • timestamp: When the error occurred
  • status: HTTP status code (500)
  • error: “Internal Server Error”
  • message: Generic error message with reference ID for troubleshooting
  • path: Request path that caused the error

Examples

Basic File Upload

curl -X POST http://localhost:8080/api/links/upload \
  -F "file=@/path/to/document.pdf"
Response (201 Created):
{
  "shortCode": "F5gH7jKl",
  "accessUrl": "http://localhost:8080/l/F5gH7jKl",
  "expiresAt": null,
  "maxViews": null
}

Upload with Expiration

curl -X POST http://localhost:8080/api/links/upload \
  -F "file=@/path/to/report.xlsx" \
  -F "expiresAt=2026-12-31T23:59:59+00:00"
Response (201 Created):
{
  "shortCode": "M8nOpQrS",
  "accessUrl": "http://localhost:8080/l/M8nOpQrS",
  "expiresAt": "2026-12-31T23:59:59+00:00",
  "maxViews": null
}

Upload with Download Limit

curl -X POST http://localhost:8080/api/links/upload \
  -F "file=@/path/to/presentation.pptx" \
  -F "maxViews=5"
Response (201 Created):
{
  "shortCode": "T3uVwXyZ",
  "accessUrl": "http://localhost:8080/l/T3uVwXyZ",
  "expiresAt": null,
  "maxViews": 5
}

Fully Protected Upload

curl -X POST http://localhost:8080/api/links/upload \
  -F "file=@/path/to/confidential.zip" \
  -F "expiresAt=2026-06-30T12:00:00+00:00" \
  -F "maxViews=3" \
  -F "password=TopSecret2024!"
Response (201 Created):
{
  "shortCode": "A1bC2dEf",
  "accessUrl": "http://localhost:8080/l/A1bC2dEf",
  "expiresAt": "2026-06-30T12:00:00+00:00",
  "maxViews": 3
}
The password is not returned in the response. Users must provide it via the X-Link-Password header when downloading the file.

Accessing the Uploaded File

Once uploaded, users can download the file by accessing the accessUrl (see Resolve Link):
# Without password
curl -O -J http://localhost:8080/l/F5gH7jKl

# With password protection
curl -O -J http://localhost:8080/l/A1bC2dEf \
  -H "X-Link-Password: TopSecret2024!"
The response includes:
  • File download with original filename
  • Content-Disposition: attachment; filename="original-name.pdf"
  • Content-Type: application/octet-stream

Validation Error Example

Request without file:
curl -X POST http://localhost:8080/api/links/upload \
  -F "maxViews=5"
Response (400 Bad Request):
{
  "timestamp": "2026-03-04T14:30:00+00:00",
  "status": 400,
  "error": "Bad Request",
  "message": "file: must not be null",
  "path": "/api/links/upload"
}

Important Notes

File Storage: Uploaded files are stored on the server filesystem. Ensure adequate disk space and implement cleanup strategies for expired or revoked links.
Link Type: Upload links create DOWNLOAD type secure links (as opposed to REDIRECT type). When accessed, they return the file content instead of redirecting.
Original Filename: The original filename is preserved and returned in the Content-Disposition header when the file is downloaded.

Create Link

Create a redirect link to an external URL

Resolve Link

Download a file using its short code

Revoke Link

Permanently disable a download link

Build docs developers (and LLMs) love