From 7040334eec79f02ad9e972b24bc35f3ca69ae79c Mon Sep 17 00:00:00 2001 From: smolkik-code Date: Wed, 17 Jun 2026 12:55:43 +0700 Subject: [PATCH] fix: use reels_media endpoint for stories (returns actual items) - /feed/user/{id}/story/ only returns reel metadata, not items - /feed/reels_media/ with POST returns actual story media - Batch user IDs (20 per request) for efficiency - Fallback: reels_tray -> reels_media batch --- instagram_monitor.py | 48 +++++++++++++++++++++++++++++++------------- 1 file changed, 34 insertions(+), 14 deletions(-) diff --git a/instagram_monitor.py b/instagram_monitor.py index 868c0df..df26a7a 100644 --- a/instagram_monitor.py +++ b/instagram_monitor.py @@ -194,10 +194,12 @@ class InstagramMonitor: return followees def _get_user_stories(self, user_pk: int) -> list[dict]: + """Fetch stories via reels_media endpoint (returns actual items).""" try: - resp = self.session.get( - f"{API_BASE}/feed/user/{user_pk}/story/", - params={"user_id": user_pk}, + resp = self.session.post( + f"{API_BASE}/feed/reels_media/", + json={"user_ids": [user_pk]}, + headers={**IG_HEADERS, "Content-Type": "application/x-www-form-urlencoded"}, timeout=30, ) if resp.status_code != 200: @@ -206,9 +208,7 @@ class InstagramMonitor: data = resp.json() items = data.get("items", []) - logger.debug(f"Stories {user_pk}: {len(items)} items, keys={list(data.keys())}") if not items: - logger.debug(f"Stories {user_pk} raw: {resp.text[:400]}") return [] stories = [] @@ -364,16 +364,36 @@ class InstagramMonitor: all_stories = self._get_all_stories() total_stories = sum(len(s) for s in all_stories.values()) - # Method 2: per-user stories for known active users (fallback) + # Method 2: per-user stories via reels_media (fallback) if total_stories == 0: - logger.info("reels_tray empty, trying per-user story fetch for followees...") - for user in followees[:10]: - user_pk = user["pk"] - stories = self._get_user_stories(user_pk) - if stories: - all_stories[user_pk] = stories - total_stories += len(stories) - logger.info(f"@{user['username']}: {len(stories)} stories via per-user endpoint") + logger.info("reels_tray empty, trying reels_media for followees...") + # Batch user IDs for reels_media + user_pks = [u["pk"] for u in followees] + for batch_start in range(0, len(user_pks), 20): + batch = user_pks[batch_start:batch_start + 20] + try: + resp = self.session.post( + f"{API_BASE}/feed/reels_media/", + json={"user_ids": batch}, + headers={**IG_HEADERS, "Content-Type": "application/x-www-form-urlencoded"}, + timeout=30, + ) + if resp.status_code == 200: + data = resp.json() + items = data.get("items", []) + for item in items: + user_info = item.get("user", {}) + user_pk = user_info.get("pk", item.get("user_pk", 0)) + media_id = str(item.get("pk", item.get("id", ""))) + if self.db.is_downloaded(media_id): + continue + if user_pk not in all_stories: + all_stories[user_pk] = [] + all_stories[user_pk].append(item) + total_stories += 1 + logger.info(f"reels_media batch: {len(items)} stories from {len(data.get('statuses', []))} users") + except Exception as e: + logger.error(f"reels_media batch error: {e}") logger.info(f"Total stories found: {total_stories}")