@elizaos/plugin-twitter 1.0.14 → 1.2.1
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/README.md +2 -7
- package/dist/index.d.ts +7 -0
- package/dist/index.js +126 -22
- package/dist/index.js.map +1 -1
- package/package.json +1 -1
package/README.md
CHANGED
|
@@ -177,11 +177,6 @@ TWITTER_POST_INTERVAL_VARIANCE=0.2 # Random variance factor for posting interval
|
|
|
177
177
|
|
|
178
178
|
# Interaction Settings
|
|
179
179
|
TWITTER_SEARCH_ENABLE=true # Enable timeline monitoring and interactions
|
|
180
|
-
TWITTER_INTERACTION_INTERVAL_MIN=15 # Minimum interval between interactions (minutes)
|
|
181
|
-
TWITTER_INTERACTION_INTERVAL_MAX=30 # Maximum interval between interactions (minutes)
|
|
182
|
-
TWITTER_INTERACTION_INTERVAL_VARIANCE=0.3 # Random variance for interaction intervals
|
|
183
|
-
TWITTER_AUTO_RESPOND_MENTIONS=true # Automatically respond to mentions
|
|
184
|
-
TWITTER_AUTO_RESPOND_REPLIES=true # Automatically respond to replies
|
|
185
180
|
TWITTER_MAX_INTERACTIONS_PER_RUN=10 # Maximum interactions processed per cycle
|
|
186
181
|
|
|
187
182
|
# Timeline Algorithm Configuration
|
|
@@ -193,8 +188,8 @@ TWITTER_TIMELINE_RELEVANCE_WEIGHT=5 # Weight for relevance scoring
|
|
|
193
188
|
# Advanced Settings
|
|
194
189
|
TWITTER_MAX_TWEET_LENGTH=4000 # Maximum tweet length (for threads)
|
|
195
190
|
TWITTER_DM_ONLY=false # Only interact via direct messages
|
|
196
|
-
TWITTER_ENABLE_ACTION_PROCESSING=false # Enable timeline action processing
|
|
197
|
-
TWITTER_ACTION_INTERVAL=
|
|
191
|
+
TWITTER_ENABLE_ACTION_PROCESSING=false # Enable timeline action processing (likes, retweets, replies)
|
|
192
|
+
TWITTER_ACTION_INTERVAL=30 # Timeline action processing interval in MINUTES (default: 30 minutes)
|
|
198
193
|
```
|
|
199
194
|
|
|
200
195
|
## 🎯 Common Use Cases
|
package/dist/index.d.ts
CHANGED
|
@@ -769,6 +769,7 @@ declare class TwitterInteractionClient {
|
|
|
769
769
|
runtime: IAgentRuntime;
|
|
770
770
|
private isDryRun;
|
|
771
771
|
private state;
|
|
772
|
+
private isRunning;
|
|
772
773
|
/**
|
|
773
774
|
* Constructor for setting up a new instance with the provided client, runtime, and state.
|
|
774
775
|
* @param {ClientBase} client - The client being used for communication.
|
|
@@ -833,6 +834,7 @@ declare class TwitterInteractionClient {
|
|
|
833
834
|
*/
|
|
834
835
|
buildConversationThread(tweet: Tweet$1, maxReplies?: number): Promise<Tweet$1[]>;
|
|
835
836
|
private createMemoryObject;
|
|
837
|
+
stop(): Promise<void>;
|
|
836
838
|
}
|
|
837
839
|
|
|
838
840
|
/**
|
|
@@ -844,6 +846,7 @@ declare class TwitterPostClient {
|
|
|
844
846
|
twitterUsername: string;
|
|
845
847
|
private isDryRun;
|
|
846
848
|
private state;
|
|
849
|
+
private isRunning;
|
|
847
850
|
/**
|
|
848
851
|
* Constructor for initializing a new Twitter client with the provided client, runtime, and state
|
|
849
852
|
* @param {ClientBase} client - The client used for interacting with Twitter API
|
|
@@ -943,6 +946,8 @@ type TwitterProfile = {
|
|
|
943
946
|
declare class RequestQueue {
|
|
944
947
|
private queue;
|
|
945
948
|
private processing;
|
|
949
|
+
private maxRetries;
|
|
950
|
+
private retryAttempts;
|
|
946
951
|
/**
|
|
947
952
|
* Asynchronously adds a request to the queue, then processes the queue.
|
|
948
953
|
*
|
|
@@ -1058,6 +1063,7 @@ declare class TwitterTimelineClient {
|
|
|
1058
1063
|
isDryRun: boolean;
|
|
1059
1064
|
timelineType: TIMELINE_TYPE;
|
|
1060
1065
|
private state;
|
|
1066
|
+
private isRunning;
|
|
1061
1067
|
constructor(client: ClientBase, runtime: IAgentRuntime, state: any);
|
|
1062
1068
|
start(): Promise<void>;
|
|
1063
1069
|
getTimeline(count: number): Promise<Tweet$1[]>;
|
|
@@ -1085,6 +1091,7 @@ declare class TwitterTimelineClient {
|
|
|
1085
1091
|
handleRetweetAction(tweet: Tweet$1): Promise<void>;
|
|
1086
1092
|
handleQuoteAction(tweet: Tweet$1): Promise<void>;
|
|
1087
1093
|
handleReplyAction(tweet: Tweet$1): Promise<void>;
|
|
1094
|
+
stop(): Promise<void>;
|
|
1088
1095
|
}
|
|
1089
1096
|
|
|
1090
1097
|
/**
|
package/dist/index.js
CHANGED
|
@@ -1917,6 +1917,8 @@ var RequestQueue = class {
|
|
|
1917
1917
|
constructor() {
|
|
1918
1918
|
this.queue = [];
|
|
1919
1919
|
this.processing = false;
|
|
1920
|
+
this.maxRetries = 3;
|
|
1921
|
+
this.retryAttempts = /* @__PURE__ */ new Map();
|
|
1920
1922
|
}
|
|
1921
1923
|
/**
|
|
1922
1924
|
* Asynchronously adds a request to the queue, then processes the queue.
|
|
@@ -1952,14 +1954,26 @@ var RequestQueue = class {
|
|
|
1952
1954
|
const request = this.queue.shift();
|
|
1953
1955
|
try {
|
|
1954
1956
|
await request();
|
|
1957
|
+
this.retryAttempts.delete(request);
|
|
1955
1958
|
} catch (error) {
|
|
1956
|
-
|
|
1957
|
-
this.
|
|
1958
|
-
|
|
1959
|
+
logger.error("Error processing request:", error);
|
|
1960
|
+
const retryCount = (this.retryAttempts.get(request) || 0) + 1;
|
|
1961
|
+
if (retryCount < this.maxRetries) {
|
|
1962
|
+
this.retryAttempts.set(request, retryCount);
|
|
1963
|
+
this.queue.unshift(request);
|
|
1964
|
+
await this.exponentialBackoff(retryCount);
|
|
1965
|
+
break;
|
|
1966
|
+
} else {
|
|
1967
|
+
logger.error(`Max retries (${this.maxRetries}) exceeded for request, skipping`);
|
|
1968
|
+
this.retryAttempts.delete(request);
|
|
1969
|
+
}
|
|
1959
1970
|
}
|
|
1960
1971
|
await this.randomDelay();
|
|
1961
1972
|
}
|
|
1962
1973
|
this.processing = false;
|
|
1974
|
+
if (this.queue.length > 0) {
|
|
1975
|
+
this.processQueue();
|
|
1976
|
+
}
|
|
1963
1977
|
}
|
|
1964
1978
|
/**
|
|
1965
1979
|
* Implements an exponential backoff strategy for retrying a task.
|
|
@@ -2006,7 +2020,7 @@ var _ClientBase = class _ClientBase {
|
|
|
2006
2020
|
*/
|
|
2007
2021
|
async cacheTweet(tweet) {
|
|
2008
2022
|
if (!tweet) {
|
|
2009
|
-
|
|
2023
|
+
logger.warn("Tweet is undefined, skipping cache");
|
|
2010
2024
|
return;
|
|
2011
2025
|
}
|
|
2012
2026
|
this.runtime.setCache(`twitter/tweets/${tweet.id}`, tweet);
|
|
@@ -2420,7 +2434,7 @@ var _ClientBase = class _ClientBase {
|
|
|
2420
2434
|
});
|
|
2421
2435
|
return profile;
|
|
2422
2436
|
} catch (error) {
|
|
2423
|
-
|
|
2437
|
+
logger.error("Error fetching Twitter profile:", error);
|
|
2424
2438
|
throw error;
|
|
2425
2439
|
}
|
|
2426
2440
|
}
|
|
@@ -6666,6 +6680,7 @@ var TwitterInteractionClient = class {
|
|
|
6666
6680
|
* @param {any} state - The initial state of the agent.
|
|
6667
6681
|
*/
|
|
6668
6682
|
constructor(client, runtime, state) {
|
|
6683
|
+
this.isRunning = false;
|
|
6669
6684
|
this.client = client;
|
|
6670
6685
|
this.runtime = runtime;
|
|
6671
6686
|
this.state = state;
|
|
@@ -6676,12 +6691,19 @@ var TwitterInteractionClient = class {
|
|
|
6676
6691
|
* Uses an interval based on the 'TWITTER_POLL_INTERVAL' setting, or defaults to 2 minutes if not set.
|
|
6677
6692
|
*/
|
|
6678
6693
|
async start() {
|
|
6694
|
+
this.isRunning = true;
|
|
6679
6695
|
const handleTwitterInteractionsLoop = () => {
|
|
6696
|
+
if (!this.isRunning) {
|
|
6697
|
+
logger4.info("Twitter interaction client stopped, exiting loop");
|
|
6698
|
+
return;
|
|
6699
|
+
}
|
|
6680
6700
|
const interactionInterval = (this.state?.TWITTER_POLL_INTERVAL || this.runtime.getSetting(
|
|
6681
6701
|
"TWITTER_POLL_INTERVAL"
|
|
6682
6702
|
) || 120) * 1e3;
|
|
6683
6703
|
this.handleTwitterInteractions();
|
|
6684
|
-
|
|
6704
|
+
if (this.isRunning) {
|
|
6705
|
+
setTimeout(handleTwitterInteractionsLoop, interactionInterval);
|
|
6706
|
+
}
|
|
6685
6707
|
};
|
|
6686
6708
|
handleTwitterInteractionsLoop();
|
|
6687
6709
|
}
|
|
@@ -6745,7 +6767,12 @@ var TwitterInteractionClient = class {
|
|
|
6745
6767
|
return shouldTarget;
|
|
6746
6768
|
});
|
|
6747
6769
|
}
|
|
6748
|
-
|
|
6770
|
+
const maxInteractionsPerRun = parseInt(
|
|
6771
|
+
this.runtime.getSetting("TWITTER_MAX_INTERACTIONS_PER_RUN") || "10"
|
|
6772
|
+
);
|
|
6773
|
+
const tweetsToProcess = uniqueTweetCandidates.slice(0, maxInteractionsPerRun);
|
|
6774
|
+
logger4.info(`Processing ${tweetsToProcess.length} of ${uniqueTweetCandidates.length} mention tweets (max: ${maxInteractionsPerRun})`);
|
|
6775
|
+
for (const tweet of tweetsToProcess) {
|
|
6749
6776
|
if (!this.client.lastCheckedTweetId || BigInt(tweet.id) > this.client.lastCheckedTweetId) {
|
|
6750
6777
|
const tweetId = createUniqueUuid3(this.runtime, tweet.id);
|
|
6751
6778
|
const existingResponse = await this.runtime.getMemoryById(tweetId);
|
|
@@ -7149,6 +7176,10 @@ var TwitterInteractionClient = class {
|
|
|
7149
7176
|
createdAt: Date.now()
|
|
7150
7177
|
};
|
|
7151
7178
|
}
|
|
7179
|
+
async stop() {
|
|
7180
|
+
logger4.info("Stopping Twitter interaction client...");
|
|
7181
|
+
this.isRunning = false;
|
|
7182
|
+
}
|
|
7152
7183
|
};
|
|
7153
7184
|
|
|
7154
7185
|
// src/post.ts
|
|
@@ -7166,6 +7197,7 @@ var TwitterPostClient = class {
|
|
|
7166
7197
|
* @param {any} state - The state object containing configuration settings
|
|
7167
7198
|
*/
|
|
7168
7199
|
constructor(client, runtime, state) {
|
|
7200
|
+
this.isRunning = false;
|
|
7169
7201
|
this.client = client;
|
|
7170
7202
|
this.state = state;
|
|
7171
7203
|
this.runtime = runtime;
|
|
@@ -7192,13 +7224,20 @@ var TwitterPostClient = class {
|
|
|
7192
7224
|
*/
|
|
7193
7225
|
async start() {
|
|
7194
7226
|
logger5.log("Starting Twitter post client...");
|
|
7227
|
+
this.isRunning = true;
|
|
7195
7228
|
const generateNewTweetLoop = async () => {
|
|
7229
|
+
if (!this.isRunning) {
|
|
7230
|
+
logger5.log("Twitter post client stopped, exiting loop");
|
|
7231
|
+
return;
|
|
7232
|
+
}
|
|
7196
7233
|
const minPostMinutes = this.state?.TWITTER_POST_INTERVAL_MIN || this.runtime.getSetting("TWITTER_POST_INTERVAL_MIN") || 90;
|
|
7197
7234
|
const maxPostMinutes = this.state?.TWITTER_POST_INTERVAL_MAX || this.runtime.getSetting("TWITTER_POST_INTERVAL_MAX") || 180;
|
|
7198
7235
|
const randomMinutes = Math.floor(Math.random() * (maxPostMinutes - minPostMinutes + 1)) + minPostMinutes;
|
|
7199
7236
|
const interval = randomMinutes * 60 * 1e3;
|
|
7200
7237
|
await this.generateNewTweet();
|
|
7201
|
-
|
|
7238
|
+
if (this.isRunning) {
|
|
7239
|
+
setTimeout(generateNewTweetLoop, interval);
|
|
7240
|
+
}
|
|
7202
7241
|
};
|
|
7203
7242
|
setTimeout(generateNewTweetLoop, 60 * 1e3);
|
|
7204
7243
|
const postImmediately = this.state?.TWITTER_POST_IMMEDIATELY ?? this.runtime.getSetting("TWITTER_POST_IMMEDIATELY");
|
|
@@ -7334,6 +7373,8 @@ var TwitterPostClient = class {
|
|
|
7334
7373
|
}
|
|
7335
7374
|
}
|
|
7336
7375
|
async stop() {
|
|
7376
|
+
logger5.log("Stopping Twitter post client...");
|
|
7377
|
+
this.isRunning = false;
|
|
7337
7378
|
}
|
|
7338
7379
|
};
|
|
7339
7380
|
|
|
@@ -7411,19 +7452,31 @@ Your output must ONLY contain the XML block.`;
|
|
|
7411
7452
|
// src/timeline.ts
|
|
7412
7453
|
var TwitterTimelineClient = class {
|
|
7413
7454
|
constructor(client, runtime, state) {
|
|
7455
|
+
this.isRunning = false;
|
|
7414
7456
|
this.client = client;
|
|
7415
7457
|
this.twitterClient = client.twitterClient;
|
|
7416
7458
|
this.runtime = runtime;
|
|
7417
7459
|
this.state = state;
|
|
7418
|
-
|
|
7460
|
+
const dryRunSetting = this.state?.TWITTER_DRY_RUN ?? this.runtime.getSetting("TWITTER_DRY_RUN");
|
|
7461
|
+
this.isDryRun = dryRunSetting === true || dryRunSetting === "true" || typeof dryRunSetting === "string" && dryRunSetting.toLowerCase() === "true";
|
|
7462
|
+
const timelineMode = this.state?.TWITTER_TIMELINE_MODE || this.runtime.getSetting("TWITTER_TIMELINE_MODE") || "foryou";
|
|
7463
|
+
this.timelineType = timelineMode.toLowerCase() === "following" ? "following" /* Following */ : "foryou" /* ForYou */;
|
|
7419
7464
|
}
|
|
7420
7465
|
async start() {
|
|
7466
|
+
logger6.info("Starting Twitter timeline client...");
|
|
7467
|
+
this.isRunning = true;
|
|
7421
7468
|
const handleTwitterTimelineLoop = () => {
|
|
7422
|
-
|
|
7423
|
-
"
|
|
7424
|
-
|
|
7469
|
+
if (!this.isRunning) {
|
|
7470
|
+
logger6.info("Twitter timeline client stopped, exiting loop");
|
|
7471
|
+
return;
|
|
7472
|
+
}
|
|
7473
|
+
const actionIntervalMinutes = this.state?.TWITTER_ACTION_INTERVAL || this.runtime.getSetting("TWITTER_ACTION_INTERVAL") || 240;
|
|
7474
|
+
const actionInterval = actionIntervalMinutes * 60 * 1e3;
|
|
7475
|
+
logger6.info(`Timeline client will check every ${actionIntervalMinutes} minutes`);
|
|
7425
7476
|
this.handleTimeline();
|
|
7426
|
-
|
|
7477
|
+
if (this.isRunning) {
|
|
7478
|
+
setTimeout(handleTwitterTimelineLoop, actionInterval);
|
|
7479
|
+
}
|
|
7427
7480
|
};
|
|
7428
7481
|
handleTwitterTimelineLoop();
|
|
7429
7482
|
}
|
|
@@ -7454,8 +7507,9 @@ var TwitterTimelineClient = class {
|
|
|
7454
7507
|
};
|
|
7455
7508
|
}
|
|
7456
7509
|
async handleTimeline() {
|
|
7457
|
-
|
|
7510
|
+
logger6.info("Starting Twitter timeline processing...");
|
|
7458
7511
|
const tweets = await this.getTimeline(20);
|
|
7512
|
+
logger6.info(`Fetched ${tweets.length} tweets from timeline`);
|
|
7459
7513
|
const maxActionsPerCycle = 20;
|
|
7460
7514
|
const tweetDecisions = [];
|
|
7461
7515
|
for (const tweet of tweets) {
|
|
@@ -7463,7 +7517,7 @@ var TwitterTimelineClient = class {
|
|
|
7463
7517
|
const tweetId = this.createTweetId(this.runtime, tweet);
|
|
7464
7518
|
const memory = await this.runtime.getMemoryById(tweetId);
|
|
7465
7519
|
if (memory) {
|
|
7466
|
-
|
|
7520
|
+
logger6.log(`Already processed tweet ID: ${tweet.id}`);
|
|
7467
7521
|
continue;
|
|
7468
7522
|
}
|
|
7469
7523
|
const roomId = createUniqueUuid5(this.runtime, tweet.conversationId);
|
|
@@ -7516,7 +7570,21 @@ Choose any combination of [LIKE], [RETWEET], [QUOTE], and [REPLY] that are appro
|
|
|
7516
7570
|
});
|
|
7517
7571
|
};
|
|
7518
7572
|
const prioritizedTweets = rankByActionRelevance(tweetDecisions);
|
|
7519
|
-
|
|
7573
|
+
logger6.info(`Processing ${prioritizedTweets.length} tweets with actions`);
|
|
7574
|
+
if (prioritizedTweets.length > 0) {
|
|
7575
|
+
const actionSummary = prioritizedTweets.map((td) => {
|
|
7576
|
+
const actions = [];
|
|
7577
|
+
if (td.actionResponse.like) actions.push("LIKE");
|
|
7578
|
+
if (td.actionResponse.retweet) actions.push("RETWEET");
|
|
7579
|
+
if (td.actionResponse.quote) actions.push("QUOTE");
|
|
7580
|
+
if (td.actionResponse.reply) actions.push("REPLY");
|
|
7581
|
+
return `Tweet ${td.tweet.id}: ${actions.join(", ")}`;
|
|
7582
|
+
});
|
|
7583
|
+
logger6.info(`Actions to execute:
|
|
7584
|
+
${actionSummary.join("\n")}`);
|
|
7585
|
+
}
|
|
7586
|
+
await this.processTimelineActions(prioritizedTweets);
|
|
7587
|
+
logger6.info("Timeline processing complete");
|
|
7520
7588
|
}
|
|
7521
7589
|
async processTimelineActions(tweetDecisions) {
|
|
7522
7590
|
const results = [];
|
|
@@ -7574,6 +7642,10 @@ Choose any combination of [LIKE], [RETWEET], [QUOTE], and [REPLY] that are appro
|
|
|
7574
7642
|
}
|
|
7575
7643
|
async handleLikeAction(tweet) {
|
|
7576
7644
|
try {
|
|
7645
|
+
if (this.isDryRun) {
|
|
7646
|
+
logger6.log(`[DRY RUN] Would have liked tweet ${tweet.id}`);
|
|
7647
|
+
return;
|
|
7648
|
+
}
|
|
7577
7649
|
await this.twitterClient.likeTweet(tweet.id);
|
|
7578
7650
|
logger6.log(`Liked tweet ${tweet.id}`);
|
|
7579
7651
|
} catch (error) {
|
|
@@ -7582,6 +7654,10 @@ Choose any combination of [LIKE], [RETWEET], [QUOTE], and [REPLY] that are appro
|
|
|
7582
7654
|
}
|
|
7583
7655
|
async handleRetweetAction(tweet) {
|
|
7584
7656
|
try {
|
|
7657
|
+
if (this.isDryRun) {
|
|
7658
|
+
logger6.log(`[DRY RUN] Would have retweeted tweet ${tweet.id}`);
|
|
7659
|
+
return;
|
|
7660
|
+
}
|
|
7585
7661
|
await this.twitterClient.retweet(tweet.id);
|
|
7586
7662
|
logger6.log(`Retweeted tweet ${tweet.id}`);
|
|
7587
7663
|
} catch (error) {
|
|
@@ -7603,6 +7679,10 @@ ${tweet.text}`;
|
|
|
7603
7679
|
});
|
|
7604
7680
|
const responseObject = parseKeyValueXml(quoteResponse);
|
|
7605
7681
|
if (responseObject.post) {
|
|
7682
|
+
if (this.isDryRun) {
|
|
7683
|
+
logger6.log(`[DRY RUN] Would have quoted tweet ${tweet.id} with: ${responseObject.post}`);
|
|
7684
|
+
return;
|
|
7685
|
+
}
|
|
7606
7686
|
const result = await this.client.requestQueue.add(
|
|
7607
7687
|
async () => await this.twitterClient.sendQuoteTweet(
|
|
7608
7688
|
responseObject.post,
|
|
@@ -7650,6 +7730,10 @@ ${tweet.text}`;
|
|
|
7650
7730
|
});
|
|
7651
7731
|
const responseObject = parseKeyValueXml(replyResponse);
|
|
7652
7732
|
if (responseObject.post) {
|
|
7733
|
+
if (this.isDryRun) {
|
|
7734
|
+
logger6.log(`[DRY RUN] Would have replied to tweet ${tweet.id} with: ${responseObject.post}`);
|
|
7735
|
+
return;
|
|
7736
|
+
}
|
|
7653
7737
|
const tweetResult = await sendTweet(
|
|
7654
7738
|
this.client,
|
|
7655
7739
|
responseObject.post,
|
|
@@ -7677,6 +7761,10 @@ ${tweet.text}`;
|
|
|
7677
7761
|
logger6.error("Error in quote tweet generation:", error);
|
|
7678
7762
|
}
|
|
7679
7763
|
}
|
|
7764
|
+
async stop() {
|
|
7765
|
+
logger6.info("Stopping Twitter timeline client...");
|
|
7766
|
+
this.isRunning = false;
|
|
7767
|
+
}
|
|
7680
7768
|
};
|
|
7681
7769
|
|
|
7682
7770
|
// src/tests.ts
|
|
@@ -7783,7 +7871,7 @@ var ClientBaseTestSuite = class {
|
|
|
7783
7871
|
};
|
|
7784
7872
|
|
|
7785
7873
|
// src/index.ts
|
|
7786
|
-
|
|
7874
|
+
logger7.info(`Twitter plugin loaded with service name: ${TWITTER_SERVICE_NAME}`);
|
|
7787
7875
|
var TwitterClientInstance = class {
|
|
7788
7876
|
constructor(runtime, state) {
|
|
7789
7877
|
this.client = new ClientBase(runtime, state);
|
|
@@ -7842,13 +7930,13 @@ var _TwitterService = class _TwitterService extends Service {
|
|
|
7842
7930
|
const client = new TwitterClientInstance(runtime, state);
|
|
7843
7931
|
await client.client.init();
|
|
7844
7932
|
if (client.post) {
|
|
7845
|
-
client.post.start();
|
|
7933
|
+
await client.post.start();
|
|
7846
7934
|
}
|
|
7847
7935
|
if (client.interaction) {
|
|
7848
|
-
client.interaction.start();
|
|
7936
|
+
await client.interaction.start();
|
|
7849
7937
|
}
|
|
7850
7938
|
if (client.timeline) {
|
|
7851
|
-
client.timeline.start();
|
|
7939
|
+
await client.timeline.start();
|
|
7852
7940
|
}
|
|
7853
7941
|
this.clients.set(this.getClientKey(clientId, runtime.agentId), client);
|
|
7854
7942
|
await this.emitServerJoinedEvent(runtime, client);
|
|
@@ -7955,7 +8043,15 @@ var _TwitterService = class _TwitterService extends Service {
|
|
|
7955
8043
|
const client = this.clients.get(key);
|
|
7956
8044
|
if (client) {
|
|
7957
8045
|
try {
|
|
7958
|
-
|
|
8046
|
+
if (client.post) {
|
|
8047
|
+
await client.post.stop();
|
|
8048
|
+
}
|
|
8049
|
+
if (client.interaction) {
|
|
8050
|
+
await client.interaction.stop();
|
|
8051
|
+
}
|
|
8052
|
+
if (client.timeline) {
|
|
8053
|
+
await client.timeline.stop();
|
|
8054
|
+
}
|
|
7959
8055
|
this.clients.delete(key);
|
|
7960
8056
|
logger7.info(`Stopped Twitter client for ${clientId}`);
|
|
7961
8057
|
} catch (error) {
|
|
@@ -7995,7 +8091,15 @@ var _TwitterService = class _TwitterService extends Service {
|
|
|
7995
8091
|
async stopAllClients() {
|
|
7996
8092
|
for (const [key, client] of this.clients.entries()) {
|
|
7997
8093
|
try {
|
|
7998
|
-
|
|
8094
|
+
if (client.post) {
|
|
8095
|
+
await client.post.stop();
|
|
8096
|
+
}
|
|
8097
|
+
if (client.interaction) {
|
|
8098
|
+
await client.interaction.stop();
|
|
8099
|
+
}
|
|
8100
|
+
if (client.timeline) {
|
|
8101
|
+
await client.timeline.stop();
|
|
8102
|
+
}
|
|
7999
8103
|
this.clients.delete(key);
|
|
8000
8104
|
} catch (error) {
|
|
8001
8105
|
logger7.error(`Error stopping Twitter client ${key}:`, error);
|