The same API, but every request is cancelled when signal aborts (the call then rejects with the
browser's AbortError, never with NetworkError).
const ctl = new AbortController();
const page = await unet.api.withSignal(ctl.signal).feed();
A feed as this user sees it: type is "global" (default, everyone), "following" or "foryou" (personalised;
ApiError 403 not_allowed when the account has privacy mode on). Pass nextCursor back as cursor.
Older servers ignore type and always answer with the global feed.
One post, by numeric id or by hashId (the id in post links). Public posts can also be read without signing in (no viewer state, at most the public fields).
Comments a user wrote (the profile "Replies" tab), newest first, each with the post it answers. Empty if hidden from you.
Posts a user reposted (the profile "Reposts" tab), newest repost first. Empty if hidden from you.
Songs on a user's profile (the "Music" tab), in the owner's order, and how many a profile may hold.
Find songs to put on your profile (30-second previews). Needs profile:write.
Add a song (itunesId from searchMusic) to the end of your profile playlist. ApiError 409 already_exists / playlist_full. Needs profile:write.
The new order of your songs: every track id, once. Returns the playlist in that order.
Remove one of your songs; returns what is left.
People, posts, hashtags and topics. from / after / before narrow the posts; offset pages them (nextPostsOffset).
Accounts to follow (the apps' “Follow suggestions”; people you already follow are left out). Needs content:read.
Your notifications (likes, replies, mentions, follows). Needs notifications:read.
Mark one notification (or all, when id is omitted) as read. Returns the new unread count.
Optionalid: numberPublish a post as the user (text, images, voice/video, audio, GIF, schedule...). Needs posts:write.
Places to attach to a post: pass one as createPost({ place }) (id, name, lat, lon). Needs posts:write.
The file behind post.video.url, post.audioUrl or a sticker url as a Blob (content:read). Those URLs need a UNET session
token, which a <video src> / <audio src> cannot send, so the SDK downloads the file with your access token
(same visibility rules as the post). Play it with a blob URL:
const blob = await unet.api.media(post.video!.url);
video.src = URL.createObjectURL(blob); // URL.revokeObjectURL(video.src) when done
Not for images: those URLs are public, use them in <img src> directly. No download timeout; pass a
signal (api.withSignal) to cancel.
A link a <video src> can stream from directly (content:read): playback starts at once and seeking works, with no full
download. Pass post.video.url. The link is signed for you and valid for about 30 minutes (expiresAt); ask again when it
runs out. Same visibility rules as the post. Prefer this to media() for video.
const { url } = await unet.api.mediaLink(post.video!.url);
video.src = url;
Full text of a long post (content:read). Short content is only the lead.
People who liked your post, newest first (since = when). As in the apps only the author sees this: ApiError
403 not_allowed for anyone else's post. Fediverse accounts are not listed. Needs content:read.
People who reposted your post, same rules and shape as postLikes.
People who liked your comment, newest first (since = when): the "View activity" of a comment. Only the comment's
author sees this: ApiError 404 not_found, 403 not_allowed for anyone else. Needs content:read.
People who reposted your comment, same rules and shape as commentLikes.
A post (text and long-form body) translated into targetLang (default: the user's translation language). Results are
cached per language. ApiError codes: 403 translation_not_allowed (the author did not allow it, or a private
account) / translation_unavailable; 400 same_language / invalid_language / nothing_to_translate; 429
RateLimited (the daily quota or the hourly cap; retryAfter says when). Needs content:read.
OptionaltargetLang: stringPosts tagged with a place, newest first (post.place.id; pass its lat / lon too so posts of the same spot saved
under another id are found). The user's own rules apply (blocks, private accounts, NSFW). Needs content:read.
Follow. Private accounts return { following: false, pending: true } until they approve. Idempotent.
Unfollow, or cancel a pending request. Idempotent.
Remove someone from your followers.
Save a post to your collection. Idempotent.
Your saved posts, newest first.
Posts you liked, newest like first.
Block someone (also removes follows between you). Idempotent.
People whose posts you hide from your feeds.
Report a user, post or comment to UNET moderators.
Change display name, bio and links. Returns the updated profile.
Change the profile picture (JPEG, PNG, WebP, GIF or HEIC, up to 10 MB). The server scans and resizes it like the apps do.
ApiError 400 invalid_file, 413 payload_too_large, 451 content_policy, 503 scan_unavailable. Needs profile:write.
Change the profile banner (same rules as uploadAvatar). Needs profile:write.
Remove the profile banner. Needs profile:write.
Privacy, notification, content (translation, link previews, view counts) and “For you” feed settings, as in the apps'
Settings. Never includes password, two-factor, sessions or other security settings. Needs settings:read.
Change settings; send only what changes. Everything is validated before anything is saved (ApiError 400
invalid_request, the message names the field). privacy.isNsfwProfile changes once a day (RateLimited),
privacy.dmRequestsRequirePlus needs Plus (ApiError 403 not_allowed). Returns all settings. Needs settings:write.
Hide posts containing keyword from “For you” (lower-cased, up to 100 characters). Returns the list. Needs settings:write.
Stop hiding keyword. Returns the list. Needs settings:write.
Whether you can use the Fediverse and whether it is on, plus your handle there. Needs settings:read.
Switch the Fediverse on or off. Turning it on sends your profile and public posts in plaintext to other servers, which may keep
copies, so acceptedPlaintextDisclosure: true is required (ApiError 400 disclosure_required; 403 not_available). Needs settings:write.
Posts of the Fediverse accounts you follow, newest first; enabled: false and no items while it is off. Needs content:read.
Look up Fediverse accounts, posts and hashtags (q: a handle like [email protected], an address, or words). Needs search:read; the Fediverse must be on.
Posts of the Fediverse that use a hashtag (tag without the #). Needs content:read.
An account on another server, with what you are to each other. Needs content:read.
An account by its handle ([email protected], with or without the leading @): found on its own server when this one has
not seen it yet, so a profile can be opened from a plain mention. ApiError 404 not_found when there is no such account. Needs content:read.
Their posts, newest first. reposts: true: what they boosted. replies: false: only posts of their own, replies: true:
only their replies (see FediverseItem.inReplyTo); left out: both together. Needs content:read.
The people an account follows or is followed by, as the account's own server publishes them (available: false: it keeps the
list private). Page with nextCursor. Needs content:read.
Follow an account by handle (name@host) or address; a locked account gets a request (viewer.follow: "pending"). Needs follows:write.
Stop following an account on another server. Needs follows:write.
Block / unblock an account on another server. Needs safety:manage.
Fediverse accounts you blocked. Needs safety:manage.
One Fediverse post by its address (uri), with what you did to it. Needs content:read.
The replies under a Fediverse post, oldest first. What this server has seen: other servers may hold more. Needs content:read.
Like / unlike a Fediverse post. Idempotent. Needs posts:interact.
Boost (repost) / take back a boost of a Fediverse post. Idempotent. Needs posts:interact.
Reply to a Fediverse post, or to one of its replies (uri is the address of what you answer; text, up to 5000 characters). Delivered to other servers in the background (deliveryState). Needs posts:interact.
Change your reply. Needs posts:manage.
Delete your reply. Needs posts:manage.
Vote in a Fediverse poll (choices: option numbers from 0). Needs posts:interact.
Posts with a hashtag (tag without the #), newest first. ApiError 404 not_found for a tag nobody used. Needs content:read.
Posts of a topic (id is post.topic.id). ApiError 404 not_found for an unknown topic. Needs content:read.
The bell on a profile: be notified about this author's new posts. Only for people you follow (ApiError 403 not_following). Needs follows:write.
Stop those notifications. Needs follows:write.
People you follow who follow username (Profile.mutual has a preview). Needs content:read.
Whether you watch this post (be notified about new comment activity under it). Needs content:read.
Watch a post: batched notifications about new comments under it (the bell on the post page). ApiError 400 invalid_request for your own post, 403 comments_disabled where comments are off, 404 for a post you cannot see. Idempotent. Needs posts:interact.
Stop watching it. Idempotent. Needs posts:interact.
Pin one of your posts to your profile (pinned posts come first; Post.isPinned). ApiError 403 not_allowed for someone else's, 409 pin_limit_reached at the limit (3; pinning a pinned post moves it to the top). Needs posts:manage.
Unpin it. Needs posts:manage.
Tell the feed to show less like this post (its author, topic, hashtags and language). Needs posts:interact.
What you told the feed to show less of. Needs settings:read.
Take one of them back. Needs settings:write.
Like a post. Idempotent: liking twice leaves it liked.
Repost a post (not your own). Idempotent.
Comments of a post (content:read).
Replies to a comment (content:read).
Comment on a post, or reply to a comment with parentId. Text and/or a GIF (gifUrl from api.gifs), or a sticker
(stickerId from api.stickerPacks(); not together with a GIF), or up to 3 pictures (images: files, uploaded for you; or
imageKeys from uploadCommentImage(); not together with a GIF or a sticker).
The post's "who can comment" setting, blocks and privacy are enforced (ApiError 403 not_allowed).
Sends an Idempotency-Key, so a retry cannot double-comment.
Upload one picture for a comment (JPEG, PNG, WebP, GIF or HEIC, up to 10 MB; scanned and resized like in the apps). Pass the
returned imageKey (up to 3) as imageKeys of comment(). ApiError 400 invalid_file, 413 payload_too_large,
451 content_policy, 503 scan_unavailable. Needs posts:interact.
Delete one of your own comments (posts:manage).
One comment (e.g. the comment a post quotes: post.quoteCommentId). Needs content:read.
Repost a comment (not your own). Idempotent. Quote it with createPost({ quoteCommentId }).
Edit the text of your own comment. Only within 30 minutes of posting (ApiError 403 edit_window_closed after that). Needs posts:manage.
The post's author pins one comment under the post (replaces the pinned one); unpinComment removes it. Needs posts:manage.
Sticker packs for a picker: the ones you installed (default) or the public catalogue (q searches).
Your scheduled, not-yet-published posts. Needs posts:write.
Edit one of your posts (also posts made in other apps). Needs posts:manage.
Delete a post of yours, or cancel it if it is still scheduled. Needs posts:manage.
Move a scheduled post to a new future time. Needs posts:manage.
Live hints from the server (new notifications, changes on posts you show, new posts in a feed): see Realtime. The
stream opens at once and reconnects by itself; call close() when you stop needing it. Needs notifications:read for
notifications and content:read for posts / feeds.
ReadonlygifsGIF picker backend (needs posts:write). Pick one, then createPost({ gifUrl: gif.gifUrl }).
const { gifs } = await unet.api.gifs.search("cat");
await unet.api.createPost({ content: "meow", gifUrl: gifs[0].gifUrl });
UNET REST API (
/open/v1), acting as the signed-in user: read (feed, posts, profiles, search, comments, notifications), write (posts, comments, likes, follows, library, safety, profile). Each method names the permission (scope) it needs; the app must be granted it in the Developers Console. Every method returns plain JSON-typed data; 404 is thrown asApiError(404).