Feat/outbound agent#7
Merged
Merged
Conversation
|
You have used all of your free Bugbot PR reviews. To receive reviews on all of your PRs, visit the Cursor dashboard to activate Pro and start your 14-day free trial. |
|
The latest updates on your projects. Learn more about Vercel for GitHub.
|
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
Add this suggestion to a batch that can be applied as a single commit.This suggestion is invalid because no changes were made to the code.Suggestions cannot be applied while the pull request is closed.Suggestions cannot be applied while viewing a subset of changes.Only one suggestion per line can be applied in a batch.Add this suggestion to a batch that can be applied as a single commit.Applying suggestions on deleted lines is not supported.You must change the existing code in this line in order to create a valid suggestion.Outdated suggestions cannot be applied.This suggestion has been applied or marked resolved.Suggestions cannot be applied from pending reviews.Suggestions cannot be applied on multi-line comments.Suggestions cannot be applied while the pull request is queued to merge.Suggestion cannot be applied right now. Please check back later.
What
Adds an outbound engagement agent triggered every 2 hours via
POST /cron/outbound-engagement— it discovers tweets to like, retweet, reply to, and accounts to follow, fully autonomously.Why
The system previously only engaged inbound (mentions/replies via webhook). Growth requires proactive outreach: following relevant accounts, engaging quality content, and joining AI/LLM discussions before they come to us.
How
New layers added (bottom-up):
src/agents/safety.ts— extracted shared pure utilities (sanitizeUntrusted,isReplySafe,AI_DISCLOSURE_PATTERNS) frominbound-engagement.ts. Both agents now share these without duplication.src/db/schema.ts—outbound_actionenum +outbound_engagement_logtable with a unique index on(tweet_id, action)for DB-level dedup.src/db/outbound-engagement.repo.ts— 4 batch-safe functions:getAlreadyActedPairs,getCooledDownAuthorIds,getFollowedAuthorIds,logOutboundAction. All handle empty inputs without querying.src/x/api.ts—SearchedTweettype +searchTweets,followUser,retweetPost,getFollowingHandlesviaxClient(OAuth1, no raw fetch).src/agents/outbound-engagement.ts—generateObjectwithgrok-4-latest. Full safety parity with inbound:<untrusted>wrapping on all tweet content, 280-char retry loop,isReplySafeguard, same voice/non-disclosure rules in system prompt.src/services/outbound-engagement.ts— orchestrates the full pipeline. Two co-located pure functions:meetsSignalThreshold(signal pre-filter) andapplyConstraints(enforces per-run caps + cooldowns without touching I/O). Caps: 10 likes / 5 replies / 3 retweets / 3 follows per run.src/routes/cron.ts—POST /cron/outbound-engagementfollowing the exact fire-and-forget 202 pattern of/cron/daily.Non-obvious decisions:
applyConstraintsis a pure function: agent decides on content quality, service enforces operational limits (caps, 6h account cooldown, follow dedup) as a post-processing step. The agent never knows about rate limits.outbound_engagement_log(zero extra API calls) rather than fetching the full following list on every run.getFollowingHandlesis only called for seed expansion (building the 4th search query from accounts we already follow).errorfield — a failed like never aborts the retweet or reply for that decision.@handlequery), not fetching their follower lists (which would be expensive and paginated).Checklist
bun run typecheckpassesbun run testpasses (85 tests, 0 failures — 17 new tests added)bun run format:checkpassesAGENTS.mdrespected (no cross-layer imports)