Skip to content
cccskills
FreePublished on GitHubEnglish overview

X

Manage X tasks through the X API v2 and xurl CLI: read and search posts, fetch bookmarks, look up profiles, publish tweets or threads with media, and create X Articles. Bookmark sweeps can turn new finds into idea issues.

OriginalShow the original description

Runs all X (Twitter) operations via X API v2 and the xurl CLI: post tweets and threads with media, publish X Articles, search, fetch bookmarks, sweep new bookmarks into idea-issues with LifeOS Upgrade analysis, look up profiles, read tweets. USE WHEN post to X, tweet, post thread, search X, search Twitter, X bookmarks, fetch bookmarks, pull bookmarks, check bookmarks, twitter bookmarks, what have I bookmarked, bookmarks for upgrades, tb, bookmark sweep, bookmark ideas, read tweet, X article, X profile, Twitter profile, lookup user, who is on X, authorize X. NOT FOR posting the same content to several platforms at once, writing social copy, Instagram/LinkedIn/TikTok data (Apify within each platform’s terms), bulk reads beyond what the X API plan allows (use your own exported data or a data product X licenses).

danielmiessler/LifeOS19,635 stars(GitHub 19,635 + cccskills 0)

Run score Not tested

See how to install

Good for

  • Post a tweet or a thread with media
  • Search X and read a post by its link
  • Fetch bookmarks or review new ones for ideas
  • Look up an X profile or publish an Article

Overview

What it does

This skill handles X tasks through the X API v2 and the xurl CLI. It can read and search posts, look up profiles, and fetch bookmarks. It can also create single posts or threads, including posts with images or video, and draft or publish long-form X Articles. A bookmark sweep can review new bookmarks and turn selected ideas into issues. After publishing a post or Article, the skill reads it back to check the result.

When it helps

Use it when you want to publish on X, find posts about a topic or from an account, review saved bookmarks, or check a profile. It centralizes X operations and authentication across these tasks.

Example requests

  • “Post this text on X.”
  • “Show me my 20 most recent bookmarks.”
  • “Read this X post and check its contents.”

Notes

X API authentication must be configured. Posting and publishing Articles affect the actual account, and the skill asks for confirmation first. It does not support bulk retrieval beyond the X API plan’s limits or operations on Instagram, LinkedIn, or TikTok. X Articles cannot be edited or deleted through the API after publication, so publishing one is irreversible.

This overview was written by AI (OpenAI Codex) from the public SKILL.md. Check the original below for the exact behavior.

Document check

AI checked the SKILL.md for operations that need care and for setup requirements. The score comes only from actually running the skill (hands-on test).

SafetyAre sending data, deleting files, and running commands disclosed?
AGoodConfirmation is required before publishing; published Articles cannot be edited or deleted.
Easy setupDoes it need few tools or API keys, and are they documented?
BPartly lackingSetup.md and credential names are listed, but the full setup procedure is absent here.

Not counted in the score. Rated by AI (OpenAI Codex) as of Oct 28, 2026. Treat it as a guide and read the original before installing.

Disagree? Request a re-evaluation

Tell us which point is wrong and why. No login needed. We will check it against the SKILL.md, redo the evaluation, and show the result here.

This form is protected by reCAPTCHA, and the Google Privacy Policy and Terms of Service apply.

Files included (19)

  • SKILL.md12.8 KB
  • Intents/Bookmarks.md2.1 KB
  • Intents/Post.md3.7 KB
  • Intents/Profile.md827 B
  • Intents/PullBookmarks.md12.2 KB
  • Intents/Read.md1.7 KB
  • Intents/Search.md1.4 KB
  • Setup.md8.0 KB
  • Tools/article.ts28.3 KB
  • Tools/bookmark-issue.ts15.6 KB
  • Tools/bookmarks.ts12.7 KB
  • Tools/delete.ts1.8 KB
  • Tools/media.ts9.0 KB
  • Tools/post.ts12.4 KB
  • Tools/profile.ts2.6 KB
  • Tools/read.ts3.7 KB
  • Tools/search.ts2.8 KB
  • Tools/TwitterText.ts3.0 KB
  • Tools/x-client.ts25.0 KB

SKILL.md (original)

Review the instructions the agent will receive before you install.

X — Unified X (Twitter) API

Contents: Ideal State · Intent Routing · Tools Reference · CLI: xurl · Data & Config · Gotchas · Examples

Handles every X (Twitter) operation through the X API v2 (direct fetch()) and the xurl CLI: post single tweets, threads and media, publish long-form Articles, search recent tweets, fetch bookmarks, look up user profiles, and read tweets by ID or URL. Other skills delegate their X work here, so the credentials, the auth handling and the OAuth 2.0 token store live in one place; if each skill wired up its own, the secrets would sprawl and the refresh chain would break.

Not for posting the same content to several platforms (Broadcast), writing social copy (a copywriting skill), or bulk collection beyond what the X API allows. X reads use the official API or the principal’s own exported data; when X refuses a read, the intent stops and reports it.

Ideal State

  • Every X operation runs through this skill's tools or xurl on the auth mode it needs, and every X read goes through Tools/read.ts, never a web fetch or browser.
  • Nothing reaches the account (a tweet, thread, media post or published Article) without the principal's confirmation, and a post is reported done only after reading it back.
  • Posted text and URLs go out exactly as given, measured by X's weighted count; over-limit text is rejected, never cut.
  • The OAuth 2.0 grant survives every run: one refresher per grant, and a missing scope or revoked grant ends in a surfaced re-authorization URL, never a guess.

Intent Routing

IntentTriggerFile
Post"post to X", "tweet", "post tweet", "send tweet", "thread"Intents/Post.md
Search"search X", "search twitter", "find tweets"Intents/Search.md
Bookmarks"X bookmarks", "fetch bookmarks", "re-authorize bookmarks", "authorize X", "bookmark token expired"Intents/Bookmarks.md
PullBookmarks"pull bookmarks", "check bookmarks", "bookmark sweep", "bookmarks for upgrades", "tb", "quick bookmark check"Intents/PullBookmarks.md
Profile"X profile", "twitter profile", "lookup user", "who is @user"Intents/Profile.md
Read"read tweet", "get tweet", "fetch tweet"Intents/Read.md
Article"X article", "Twitter article", "long-form on X", "publish an article to X"Tools/article.ts: create --file piece.md drafts (the default), --publish publishes, then read the post back with Tools/read.ts. Publishing is irreversible through the API.
FileRead when
Setup.mdfirst-time setup: the token-store Config.md, the X app and its secrets, and the first-run proof

Tools Reference

All tools are in ~/.claude/skills/X/Tools/ and run with bun. Each intent carries the command for its own tool (post.ts, search.ts, profile.ts, read.ts, bookmarks.ts, and bookmark-issue.ts for the sweep's check, create, skip and audit); this table holds only the tools no intent owns. Which auth mode each path uses is in Gotchas.

ToolPurposeUsage
x-client.tsCredential loader, token store, auth helpersImported by the other tools
media.tsChunked media upload (video/image/GIF)bun run media.ts upload clip.mp4
article.tsLong-form X Articles: markdown to content_state, draft, publishbun run article.ts create --file piece.md --publish
delete.tsDelete tweets by idbun run delete.ts <id> [<id> ...]
send gate, video PII gateWhat stops a post and how each block is reportedPost intent § Tool contract (Intents/Post.md)

CLI: xurl

xurl is the official X CLI. Use for quick API calls not covered by tools:

# Quick lookups
xurl /2/users/me
xurl /2/tweets/1234567890

# Search
xurl "/2/tweets/search/recent?query=from:<username>&max_results=10"

# Post (use Tools/post.ts instead for threads)
xurl -X POST /2/tweets -d '{"text":"Hello"}'

Data & Config

Config: LIFEOS/USER/CUSTOMIZATIONS/SKILLS/X/Config.md (a fenced yaml block choosing the OAuth 2.0 token store: local, a 0600 file on this machine that x-client.ts refreshes, or cloudflare-kv, a KV namespace that another process such as a scheduled Worker refreshes). Setup, field table and first-run proof: Setup.md. Without it, reads still work on the bearer token, posting falls back to OAuth 1.0a text-only, and every OAuth 2.0 path (media, Articles, bookmarks, delete) stops with an error naming Setup.md.

The bookmark sweep (PullBookmarks) reads three more things from the same directory and the work-tracking config: the bookmark_sweep mapping in that yaml block (issue labels, property label prefix), PREFERENCES.md (relevance profile and what counts as an idea), and the repo for idea-issues (bookmark_sweep.repo, default the repo in LIFEOS/USER/WORK/work_repo.json). Its state lives outside the skill tree in LIFEOS/MEMORY/STATE/X/ (bookmarks-state.json, bookmark-issues.json). The caller outside the skill is Pulse's Synapse module, which reads bookmark-issues.json; the former scheduled sweep that shelled out to Tools/bookmark-issue.ts is retired.

Secrets, all from ~/.claude/.env, loaded by Tools/x-client.ts and never hardcoded (names only):

VarPurpose
TWITTER_CLIENT_IDOAuth 2.0 client ID (authorize + local refresh)
TWITTER_CLIENT_SECRETOAuth 2.0 client secret
X_BEARER_TOKENApp-only bearer token (reads)
TWITTER_API_KEY, TWITTER_API_KEY_SECRET, X_ACCESS_TOKEN, X_ACCESS_TOKEN_SECRETOptional OAuth 1.0a text-only posting fallback
CLOUDFLARE_ACCOUNT_ID, CLOUDFLARE_API_TOKEN, X_TOKENS_KV_NAMESPACEOnly for token_store: cloudflare-kv

Gotchas

  • A published X Article cannot be deleted or edited through the API. X documents POST /2/articles/draft and POST /2/articles/{id}/publish and nothing else — no GET, no PATCH, no DELETE. Drafts are free to create and invisible until published, so iterate on drafts and treat --publish as one-way. article.ts defaults to draft-only for exactly this reason. The X web UI does offer Edit and Delete on a published Article, so a bad publish is recoverable by hand in the browser, not in code.
  • Article content_state is DraftJS in snake_case, not the camelCase DraftJS raw state every online example shows: inline_style_ranges, entity_ranges, and a flat entities array of {key, value} rather than an entityMap object. Offsets index the stripped text (markers removed). Images, embedded posts, code and dividers are atomic blocks whose single-space text is covered entirely by one entity range — a zero-length atomic block is rejected.
  • X's 280-character limit is weighted, not JavaScript text.length. HTTP(S) URLs count as exactly 23 characters and emoji/Unicode follow X weighting in Tools/TwitterText.ts. Tools/post.ts sends the exact caller input or rejects it (Post intent).
  • read.ts returns article and long-tweet text in one call. It requests tweet.fields=article,note_tweet, while X answers WebFetch with 402 and automation browsers are usually logged out, so any other route first only burns time.
  • One refresh chain per grant, ever. X rotates the refresh token on every refresh and treats reuse of a consumed one as theft, revoking the whole grant until a human re-authorizes. With token_store: local, x-client.ts is the only refresher: refreshes run behind <token_file>.lock, waiters re-read the file instead of replaying a consumed token, and writes are tmp+rename. With cloudflare-kv, the external owner refreshes and this client never does. Never call the token endpoint directly with a stored refresh token — always go through getValidTokens() — and never point two installs' local stores at the same grant.
  • Three auth modes, not one. Posting, media, Articles and delete = OAuth 2.0 user context (OAuth 1.0a text-only fallback when no OAuth 2.0 store is configured), reads (search, profiles, tweets) = app-only bearer token, bookmarks = OAuth 2.0 PKCE. A 401 on one path says nothing about the other two.
  • Prefer the OAuth 2.0 store for posting. OAuth 1.0a portal keys can be revoked or regenerated without notice and then 401 on every post; post.ts uses the OAuth 2.0 store whenever one is configured and falls back to OAuth 1.0a only without one. If posting 403s, read the body first: type: …/spend-cap-reached means the account's Billing Cycle Cap in the X developer console is hit (every endpoint 403s until the cap is raised or the cycle resets). Otherwise the grant lacks tweet.write: re-run bookmarks.ts authorize. The consent click is a human's, so surface the URL; if the app grant is still active on the account, authorize completes with no click.
  • Media upload needs its own scope: media.write. Without it POST /2/media/upload returns a bare 403 while /2/tweets keeps working, which reads as "video posting is broken" rather than "the grant is short a scope". SCOPES in bookmarks.ts carries it; a grant authorized without it must be re-authorized once.
  • The v2 media endpoints are sub-paths, not command= parameters, and X's own chunked-upload doc still describes the retired v1.1 shape. The working contract is: POST /2/media/upload/initialize (JSON body: media_type, total_bytes, media_category) → POST /2/media/upload/{id}/append (multipart: segment_index, media, segments ≤5MB) → POST /2/media/upload/{id}/finalize. Sending command=INIT to the base path returns 400 "Missing media field in JSON" — the parameter is ignored and the call is read as a simple upload, so the error names the wrong problem. Images ≤5MB skip all of it: one multipart POST /2/media/upload with a media field.
  • Status is the one call that still speaks the old dialect: GET /2/media/upload?media_id=<id>&command=STATUS. It rejects media_ids (the plural that every other v2 endpoint takes) and has no sub-path form. Video/GIF process asynchronously — poll to succeeded before attaching, because an unprocessed media_id publishes a tweet with no video and no error. All of this is encoded in Tools/media.ts.

Examples

Example 1: Read a tweet link

User: "read this: https://x.com/<user>/status/<id>"
→ bun run Tools/read.ts <url> (immediately — no browser attempts)
→ Returns the tweet, plus the full article plain_text when the post carries an X Article

read.ts takes a status URL or a numeric tweet ID. A bare x.com/i/article/<id> link is an article ID, not a tweet ID, and the API has no read-by-article-ID call; use the status URL of the post that carries the article.

Example 2: Fetch recent bookmarks

User: "show my last 20 X bookmarks"
→ Bookmarks intent: bun run Tools/bookmarks.ts fetch 20
→ Author, text and links per bookmark

Example 3: Bookmark sweep

User: "tb"  (or "just check bookmarks" for quick mode: last 30, MEDIUM skipped)
→ PullBookmarks intent: fetch 50 --json, filter seenIds
→ each new bookmark created-or-skipped inline via bookmark-issue.ts, audit passes, Upgrade report with prior-work tags

Reviews

No reviews yet. Tell others what you thought.

Comments

No login needed. Share how it worked for you, ask a question, or note where it did not run.

No comments yet. Be the first to write one.

Comments are published right away. Do not include personal information such as email addresses or phone numbers. Up to 2 URLs.

0 / 1,000 characters

This form is protected by reCAPTCHA, and the Google Privacy Policy and Terms of Service apply.

More skills from this repository

AnnualReports

FreeSummary

Find and fetch vendor cybersecurity reports, then compare their findings on topics such as ransomware, breaches, cloud security, and AI. Analyses identify the reports consulted and cite each figure by vendor, year, and report, including where sources disagree.

  • Find reports in a cybersecurity topic area
  • Fetch a specific vendor report
  • Compare ransomware findings across reports
danielmiessler/LifeOS19.6KUpdated Oct 28, 2026

Compare a component's own design needs with the goals of the larger system through three structured passes. The result identifies conflicts, recommends an appropriate scope, and assesses whether the proposed design fits the whole.

  • Choosing between a service, a library, and inline code
  • Comparing feature requests with product goals
  • Checking how new components fit an existing system
danielmiessler/LifeOS19.6KUpdated Oct 28, 2026

Aphorisms

FreeSummary

Find quotes that fit a text’s themes, with attribution and a short reason for each suggestion. Add sourced quotes, research thinkers, and organize a quote collection by theme and usage history to avoid repetition.

  • Finding a fitting quote for a newsletter
  • Saving sourced quotes without duplicates
  • Researching a thinker’s quotes by theme
danielmiessler/LifeOS19.6KUpdated Oct 28, 2026

Art

FreeSummary

Create blog illustrations, technical diagrams, comparisons, comics, and icons through workflows tailored to each format. The skill guides composition, color, and model selection, then stages generated images for review before they are used in a project.

  • Creating blog header illustrations
  • Explaining a system with a technical diagram
  • Visualizing comparisons and timelines
danielmiessler/LifeOS19.6KUpdated Oct 28, 2026

ArtDirection

FreeSummary

Assess the visual quality of images, films, slides, and site captures against a brief and craft criteria. Two vision judges score the work and rank defects, guiding bounded revision; delivery is gated on a passing critique, with human calibration labels recorded separately.

  • Reviewing a render and listing the most important visual defects
  • Iterating on a film or slide deck until it meets a defined bar
  • Checking whether an image reads as professional
danielmiessler/LifeOS19.6KUpdated Oct 28, 2026

ArXiv

FreeSummary

Find arXiv papers by topic, research category, or paper ID. Retrieve titles, authors, abstracts, and links, check new submissions, and add AlphaXiv's AI-generated overviews when available to help decide which papers to read.

  • Checking new AI and machine learning papers
  • Finding papers on a specific research topic
  • Looking up a paper by its ID or arXiv URL
danielmiessler/LifeOS19.6KUpdated Oct 28, 2026

See all skills by danielmiessler

Report a problem with this skill