EmberlyEmberly Docs

Account API

Read and update your profile, and manage API keys, your upload token, sessions and your data.

All endpoints need authentication.

MethodEndpointDescription
GET PUT/api/profileRead or update your profile and settings
POST/api/profile/avatarUpload an avatar
POST DELETE/api/profile/bannerUpload or remove a profile banner
GET POST/api/profile/api-keysList or create API keys
DELETE/api/profile/api-keys/{id}Revoke an API key
GET POST/api/profile/upload-tokenRead or reset your upload token
GET DELETE/api/profile/sessionsRecent sign-ins, or sign out everywhere
GET PATCH DELETE/api/notificationsYour notifications: list, mark read, clear
GET/api/profile/devicesDevices signed in to your account
PATCH DELETE/api/profile/devices/{id}Rename a device, or sign it out
POST GET/api/profile/exportRequest a copy of your data, and check on it
DELETE/api/profileDelete your account

Profile

GET /api/profile

{
  "success": true,
  "data": {
    "id": "clx1a2b...",
    "name": "codemeapixel",
    "email": "[email protected]",
    "image": "/api/avatars/clx1a2b.png?v=3",
    "randomizeFileUrls": false,
    "enableRichEmbeds": true,
    "theme": "default-dark",
    "emailNotificationsEnabled": true,
    "discordNotificationsEnabled": false
  }
}

PUT /api/profile

Send only the fields you want to change.

FieldDescription
nameUsername. At least 2 characters, no spaces.
fullNameDisplay name, up to 100 characters.
emailNew email address.
currentPassword, newPasswordChange your password. newPassword needs at least 8 characters.
randomizeFileUrlsUse random names in file links instead of the original file name.
enableRichEmbedsShow a branded card in link previews. When off, previews show just the file.
defaultFileExpirationDefault expiry for new uploads: HOUR, DAY, WEEK or MONTH.
defaultFileExpirationActionWhat expiry does: DELETE or SET_PRIVATE.
emailNotificationsEnabled, emailPreferencesEmail notifications.
discordWebhookUrl, discordNotificationsEnabled, discordPreferencesSend notifications to a Discord webhook. The URL must be a Discord webhook URL; send "" or null to remove it.
bio, website, twitter, github, discordPublic profile details.
isProfilePublic, showLinkedAccountsWho can see your public profile.
theme, customColorsYour dashboard theme.
curl -X PUT https://embrly.ca/api/profile \
  -H "Authorization: Bearer ebk_..." \
  -H "Content-Type: application/json" \
  -d '{"enableRichEmbeds": false}'

Avatar and Banner

POST /api/profile/avatar and POST /api/profile/banner take multipart/form-data with a file field. DELETE /api/profile/banner removes the banner.


API Keys

You can have up to 10 API keys. Each acts as your whole account.

GET /api/profile/api-keys

{
  "success": true,
  "data": {
    "keys": [
      {
        "id": "clx7k...",
        "name": "Backup script",
        "prefix": "ebk_3fA9",
        "lastUsedAt": "2026-10-24T08:01:00.000Z",
        "createdAt": "2026-09-02T12:00:00.000Z"
      }
    ]
  }
}

POST /api/profile/api-keys

{ "name": "Backup script" }

Returns 201 with the new key. The full key is only shown once, so store it straight away:

{
  "success": true,
  "data": { "key": "ebk_3fA9...", "prefix": "ebk_3fA9", "name": "Backup script" }
}

Returns 422 once you have 10 keys.

DELETE /api/profile/api-keys/{id}

Revokes the key immediately.


Upload Token

The upload token is what ShareX and other upload tools use. These two endpoints return it without the success/data wrapper.

GET /api/profile/upload-token

{ "uploadToken": "4f6c1e2a-..." }

POST /api/profile/upload-token

Creates a new token and returns it in the same format. The old token stops working, so update your upload tools afterwards.


Sessions

GET /api/profile/sessions

Your recent sign-ins (?limit=, default 20) and details of the last one, without the success/data wrapper.

DELETE /api/profile/sessions

Signs you out on every device, including this one. API keys and the upload token keep working.


Notifications

GET /api/notifications

QueryDescription
limitUp to 50. Defaults to 20.
cursornextCursor from the previous page.
unreadtrue for unread only.
categorysecurity, account, billing, productUpdates or marketing.
{
  "success": true,
  "data": {
    "items": [
      {
        "id": "clxn0t...",
        "category": "security",
        "title": "New sign-in from Chrome on Windows",
        "body": "Calgary, Alberta, Canada · Oct 24, 2026, 6:46 AM MDT",
        "link": "/me?tab=security",
        "readAt": null,
        "createdAt": "2026-10-24T12:46:00.000Z"
      }
    ],
    "nextCursor": null,
    "unread": 1
  }
}

PATCH /api/notifications

Marks notifications read. Send { "ids": ["..."] }, or {} to mark all of them.

DELETE /api/notifications

Deletes notifications. Send { "ids": ["..."] }, or {} to delete all of them.

Notifications older than 90 days are removed automatically.


Devices

Each browser that signs in to your account is recorded as a device. You get an email when a new one signs in.

GET /api/profile/devices

{
  "success": true,
  "data": {
    "devices": [
      {
        "id": "clxd3v...",
        "name": "Chrome on Windows",
        "lastLocation": "Calgary, Alberta, Canada",
        "firstSeenAt": "2026-10-01T12:00:00.000Z",
        "lastSeenAt": "2026-10-24T09:00:00.000Z",
        "current": true
      }
    ]
  }
}

PATCH /api/profile/devices/{id}

Rename a device: { "name": "Work laptop" }.

DELETE /api/profile/devices/{id}

Signs the device out within about 30 seconds. It has to sign in again, and counts as a new device when it does.


Your Data

POST /api/profile/export

Starts preparing a ZIP of your files and account data in the background. We email you a download link when it's ready. Starting a new export replaces your previous one, and you can start one an hour after the last. Returns 429 if one is still being prepared or was made less than an hour ago.

GET /api/profile/export

Returns your latest export:

{
  "success": true,
  "data": {
    "export": {
      "id": "clx9a...",
      "status": "ready",
      "size": 48213004,
      "createdAt": "2026-10-24T10:00:00.000Z",
      "completedAt": "2026-10-24T10:03:12.000Z",
      "expiresAt": "2026-10-31T10:03:12.000Z"
    }
  }
}

status is pending, ready, failed or expired. export is null if you've never exported.

GET /api/profile/export/{id}

Downloads a ready export as a ZIP. It contains your files under files/, sorted by upload date, and account.json with your profile, settings, short links, domains and devices. Links last 7 days, and only work for the account that requested them.

DELETE /api/profile

Deletes your account, files, short links and everything else, permanently. Confirm it with your password:

{ "password": "your-account-password" }

Returns 403 if the password is missing or wrong, so a leaked API key can't delete your account on its own.


In the Browser Only

Two-factor authentication, linked GitHub and Discord accounts, and recovery codes are managed from Profile → Security and Profile → Connections. Their endpoints are meant for the dashboard and need a browser session.