Quickstart

From zero to a published post: create an API key, a team, connect an account, upload media and publish, using plain HTTP.

The Free plan is enough for everything on this page: it includes 20 posts, 200 uploads and 3 teams a month. Examples use curl; every request is also available through the SDK.

1. Get an API key

Sign up, then open API Keys in the dashboard and create a key. It starts with sk_live_ and is shown once. Keep it on your server.

export SIAR_API_KEY=sk_live_...

Check that it works:

curl "https://api.siaran.my/api/v1/team" -H "x-api-key: $SIAR_API_KEY"

An empty list is a success: { "items": [], "total": 0 }.

2. Create a team

A team is a group of at most one connected account per network. Use one per customer, brand or location.

curl -X POST "https://api.siaran.my/api/v1/team" \
  -H "x-api-key: $SIAR_API_KEY" \
  -H "content-type: application/json" \
  -d '{ "name": "Acme Bakery" }'
# → { "id": "TEAM_ID", "name": "Acme Bakery", ... }

3. Connect an account

Ask for an authorization URL, open it in a browser and sign in with the network. Afterwards the account belongs to the team.

curl -X POST "https://api.siaran.my/api/v1/social-account/connect" \
  -H "x-api-key: $SIAR_API_KEY" \
  -H "content-type: application/json" \
  -d '{
    "type": "LINKEDIN",
    "teamId": "TEAM_ID",
    "redirectUrl": "https://yourapp.example/connected"
  }'
# → { "url": "https://www.linkedin.com/oauth/v2/authorization?..." }
# Send your user to that URL. After consent they land back on redirectUrl.

To let your own users do this, send them a hosted connect link instead.

4. Upload media (optional)

# Small files: multipart form upload
curl -X POST "https://api.siaran.my/api/v1/upload" \
  -H "x-api-key: $SIAR_API_KEY" \
  -F "teamId=TEAM_ID" \
  -F "file=@./launch.jpg"

# Or let Siar fetch it from a public URL
curl -X POST "https://api.siaran.my/api/v1/upload/from-url" \
  -H "x-api-key: $SIAR_API_KEY" \
  -H "content-type: application/json" \
  -d '{ "teamId": "TEAM_ID", "url": "https://cdn.example.com/launch.mp4" }'
# → { "id": "UPLOAD_ID", "type": "video", "mime": "video/mp4", ... }

The response contains the upload id. Reference it from any post in uploadIds.

5. Publish

curl -X POST "https://api.siaran.my/api/v1/post" \
  -H "x-api-key: $SIAR_API_KEY" \
  -H "content-type: application/json" \
  -d '{
    "teamId": "TEAM_ID",
    "title": "Launch day",
    "postDate": "2026-11-02T09:00:00.000Z",
    "status": "SCHEDULED",
    "socialAccountTypes": [
      "INSTAGRAM",
      "LINKEDIN",
      "BLUESKY"
    ],
    "data": {
      "INSTAGRAM": {
        "type": "POST",
        "text": "We shipped. Details in the comments.",
        "uploadIds": [
          "UPLOAD_ID"
        ]
      },
      "LINKEDIN": {
        "text": "We shipped today. Here is what changed and why.",
        "uploadIds": [
          "UPLOAD_ID"
        ]
      },
      "BLUESKY": {
        "text": "We shipped today.",
        "uploadIds": [
          "UPLOAD_ID"
        ]
      }
    },
    "firstComment": {
      "INSTAGRAM": "Changelog: example.com/changelog"
    }
  }'

With status: "SCHEDULED" and a future postDate the post publishes at that time. Use DRAFT to store it without publishing.

6. Check the result

curl "https://api.siaran.my/api/v1/post/POST_ID" -H "x-api-key: $SIAR_API_KEY"

The status moves from SCHEDULED through PROCESSING to POSTED or ERROR. For production, listen for the post.published webhook instead of polling.

Next