- Migrate user profile fields from `legacy{}` to `core{}` / `avatar{}` / `location{}` (with legacy fallback for older response shapes). Affects `user`, `whoami`, `status`, `followers`, `following`.
- Fix `user-posts` empty results: add missing `includePromotedContent` variable and update `instructions` path from `timeline_v2` to `timeline`.
- Switch `followers` / `following` to POST (Twitter changed the requirement).
- Refresh 16 stale `FALLBACK_QUERY_IDS` from fa0311/twitter-openapi.
- Drop `legacy{}` early-return in `parse_user_result`; key existence on `rest_id` so followers/following keep working when Twitter fully drops legacy.
- Add unit tests for the new core/avatar/location fallback chain and rest_id/typename guards.
- Early return when no entityRanges (skip unnecessary processing)
- Escape [ and ] in link labels to prevent nested bracket issues
- Encode ) in URLs as %29 to prevent malformed markdown links (e.g. Wikipedia)
- Add 3 new test cases for the above edge cases
Twitter migrated SearchTimeline from GET to POST; update fetch_search
to route through _graphql_post via a new use_post flag on _fetch_timeline,
avoiding duplicating the pagination logic (closes#39, refs #40, #42).
Also guard against get_ondemand_file_url returning None so the error
message is clear instead of crashing on NoneType.split (closes #43-adjacent).
Refresh all FALLBACK_QUERY_IDS from live JS bundles — 18 operations updated.
Extract visibility metadata from TweetWithVisibilityResults wrapper
before unwrapping. Adds is_subscriber_only field to Tweet model,
with full serialization roundtrip and test coverage.
Co-authored-by: Claude Opus 4.6 <noreply@anthropic.com>
- Fix auth.py subprocess script Windows Edge cookie path inconsistency
- Add timeutil.py for UTC→local time and relative time conversion
- Integrate time localization into formatter.py and serialization.py
- Add --output/-o option to show command for saving tweet detail as JSON
- Remove constants.py legacy aliases (USER_AGENT, SEC_CH_UA)
- Remove client.py backward-compat delegation methods and re-exports
- Update test imports to use parser module directly
- Add upload_media() method to TwitterClient (INIT/APPEND/FINALIZE flow
via upload.twitter.com, supports JPEG/PNG/GIF/WebP up to 5MB)
- Extend create_tweet() and quote_tweet() with optional media_ids param
- Add --image/-i option to post, reply, and quote CLI commands (max 4)
- Add MediaUploadError exception for upload-specific error handling
- Add 6 unit tests covering upload flow, validation, and media_ids
Co-Authored-By: Catafal <67582323+Catafal@users.noreply.github.com>
- Create exceptions.py with 7 exception types: TwitterError, AuthenticationError,
RateLimitError, NotFoundError, NetworkError, QueryIdError, TwitterAPIError
- Remove inline TwitterAPIError from client.py, import from exceptions module
- Replace RuntimeError('Cannot resolve queryId') with QueryIdError
- Replace RuntimeError('User not found') with NotFoundError
- Update test assertion for new TwitterAPIError message format