Skip to content

[17.0][ADD] social_media_x_sync - #6

Merged
edescalona merged 3 commits into
17.0from
17.0-add-social_media_x_sync
Oct 10, 2026
Merged

edescalona merged 3 commits into
17.0from
17.0-add-social_media_x_sync

Conversation

@edescalona

Copy link
Copy Markdown
Owner

@BinhexTeam

T25184

Adds social_media_x_sync, the X half of social_media_sync. Auto-installed when social_media_sync and social_media_x are both present. It declares no Python dependency of its own and relies on the tweepy dependency of the connector.

Why a separate module

The split from social_media_x is a cost line, not a feature line. The connector spends a fixed number of calls per account however much that account has published: link it, refresh its card, publish, delete, read the figures of the publications of the last 30 days, read the single publication being opened.

Everything whose cost grows with the history of the account lives here: the timeline, one download per media not stored yet, and up to five calls per publication whose comments are read. On top of that, one page of the latest likes of the account is read on every import and when the comments dialog opens. It is one call, but X charges every post it answers, up to 100. An Odoo that only publishes on X installs social_media_x alone and pays for none of it.

What it adds

  • Timeline import with user posts, up to the 100 publications the endpoint answers in one request (next_token is not followed). Retweets, replies and quotes are discarded. Photos are downloaded once from their address. Videos and animated GIFs are downloaded from their mp4 variant with the highest bit rate. All of them are stored as attachments, the videos through _store_remote_videos of social_media_sync, and the t.co links X appends for those media are stripped from the text. The system parameter social_media_sync.download_videos set to False leaves the videos and animated GIFs on X while the photos keep coming; the publication keeps its video mark and the next import downloads what is missing once the parameter is back on.
  • Account statistics as the sum of every publication stored for the account, with no window and no ceiling. Engagement is derived from impressions and interactions, since X reports no rate of its own. A publication deleted on X is marked Deleted and keeps the figures of its last read.
  • Comments with recent search, which only covers the last 7 days. The conversation is walked a hundred replies at a time, up to five pages. When it is read to the end, the reply count of each comment is computed in Odoo; when the ceiling cuts it short, no number is stated. Replies may carry images, and a video shows its cover.
  • Recommend on a publication and on a comment, through POST /2/users/:id/likes and DELETE /2/users/:id/likes/:tweet_id, with the user context of the account. Whether the account already liked a post is read from one page of its latest 100 likes, so an older like is not seen.
  • Delete on the comments the account wrote, with the same DELETE /2/tweets/:id already used for publications. A comment already gone on X counts as deleted.
  • Enable since / Post since, so an account does not have its whole history read again on every import.
  • With Reposts / With Quotes filters on the dashboard search panel, and Reposts / Quotes as optional columns on the list of publications.
  • Rate-limit windows per endpoint, kept on the account by social_media_x, are respected for the timeline, the recent search, the reply, the likes and the delete. While a window lasts:
    • reading the conversation shows a notice instead of an empty thread;
    • publishing a comment, recommending or deleting reports the limit instead of a result X never gave.

Scheduled actions

The passes of social_media_sync plus two of social_media_base:

Action Schedule On X
Checking social media updates 2 h imports the timeline; the only endpoint that knows whether anything moved is the import itself
Initial sync of the new accounts monthly (and on linking) first import of the timeline
Full resync weekly same read as the ordinary import, so it notices no remote deletion
Refresh statistics of recent publications daily call of social_media_x, not of this module

The bihourly check skips any account whose first import has not run yet, because that check and the initial import write the same row from two threads.

Not implemented

  • Pagination of the timeline beyond the first page, and conversations longer than 500 replies.
  • No migration script: last_post_ref, enable_since and post_since_id move from social_media_x to this module, so an existing database needs ir_model_fields updated before uninstalling the connector, or a recreation.

Requirements

A paid X API plan, the same one the connector needs: the user timeline, the recent search and the likes are API v2 endpoints and answer 403 outside a Project.

Tests

social_media_x_sync/tests/:

  • test_sync_account_x.py, test_sync_post_account_x.py and test_sync_utils_x.py;
  • test_card_footer_x.py, test_comment_dialog_x.py and test_post_reaction_x.py, which drive the tours social_card_footer_x, social_comment_dialog_x and social_post_reaction_x.

The notice of the Update button comes from social_media_sync, which words it from the accounts the import read, so this module adds no notice of its own.

Every HTTP call is patched; no network access.

Depends on

All of them are installed by the CI from test-requirements.txt, in a [DON'T MERGE] commit.

… conversation of each post

Bridge between social_media_sync and social_media_x, auto-installed with both.
It holds everything whose cost against the X API grows with the history of the
account, so an installation that only publishes on X pays a fixed number of
calls per account.

- Timeline import, one page of up to 100 original publications; photos, videos
  and animated GIFs are downloaded once as attachments, the videos through
  _store_remote_videos of social_media_sync, so the system parameter
  social_media_sync.download_videos leaves them out.
- Account statistics as the sum of every stored publication.
- Comments through the recent search endpoint, up to five pages of a hundred.
- Recommend on publications and comments, and Delete on the account's own
  comments.
- Import checkpoint (enable_since, post_since_id, last_post_ref), moved here
  from social_media_x.
- Reposts and quotes filters and optional list columns.

The bihourly check imports on X instead of flagging the account, since reading
the timeline is already the import.
@edescalona edescalona closed this Oct 10, 2026
@edescalona edescalona reopened this Oct 10, 2026
@edescalona
edescalona merged commit 462be8a into 17.0 Oct 10, 2026
4 of 6 checks passed
@edescalona
edescalona deleted the 17.0-add-social_media_x_sync branch October 10, 2026 18:20
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

1 participant