postproxy-mcp 1.0.2 → 1.2.0
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/dist/api/client.d.ts +27 -1
- package/dist/api/client.d.ts.map +1 -1
- package/dist/api/client.js +99 -0
- package/dist/api/client.js.map +1 -1
- package/dist/server.d.ts +192 -6
- package/dist/server.d.ts.map +1 -1
- package/dist/server.js +197 -6
- package/dist/server.js.map +1 -1
- package/dist/tools/history.d.ts.map +1 -1
- package/dist/tools/history.js +6 -2
- package/dist/tools/history.js.map +1 -1
- package/dist/tools/post.d.ts +6 -0
- package/dist/tools/post.d.ts.map +1 -1
- package/dist/tools/post.js +22 -8
- package/dist/tools/post.js.map +1 -1
- package/dist/tools/queue.d.ts +73 -0
- package/dist/tools/queue.d.ts.map +1 -0
- package/dist/tools/queue.js +167 -0
- package/dist/tools/queue.js.map +1 -0
- package/dist/types/index.d.ts +91 -3
- package/dist/types/index.d.ts.map +1 -1
- package/dist/utils/validation.d.ts +63 -2
- package/dist/utils/validation.d.ts.map +1 -1
- package/dist/utils/validation.js +12 -0
- package/dist/utils/validation.js.map +1 -1
- package/package.json +1 -1
- package/src/api/client.ts +112 -0
- package/src/server.ts +204 -6
- package/src/tools/history.ts +5 -2
- package/src/tools/post.ts +29 -14
- package/src/tools/queue.ts +230 -0
- package/src/types/index.ts +84 -11
- package/src/utils/validation.ts +13 -0
- package/worker/index.ts +366 -19
package/worker/index.ts
CHANGED
|
@@ -36,15 +36,26 @@ interface PlatformOutcome {
|
|
|
36
36
|
insights?: any;
|
|
37
37
|
}
|
|
38
38
|
|
|
39
|
+
interface MediaAttachment {
|
|
40
|
+
id: string;
|
|
41
|
+
status: "pending" | "processed" | "failed";
|
|
42
|
+
error_message: string | null;
|
|
43
|
+
content_type: string;
|
|
44
|
+
source_url: string | null;
|
|
45
|
+
url: string | null;
|
|
46
|
+
}
|
|
47
|
+
|
|
39
48
|
interface Post {
|
|
40
49
|
id: string;
|
|
41
50
|
body?: string;
|
|
42
51
|
content?: string;
|
|
43
|
-
status: "draft" | "pending" | "processing" | "processed" | "scheduled";
|
|
52
|
+
status: "draft" | "pending" | "processing" | "processed" | "scheduled" | "media_processing_failed";
|
|
44
53
|
draft: boolean;
|
|
45
54
|
scheduled_at: string | null;
|
|
46
55
|
created_at: string;
|
|
56
|
+
media?: MediaAttachment[];
|
|
47
57
|
platforms: PlatformOutcome[];
|
|
58
|
+
thread?: Array<{ id: string; body: string; media?: MediaAttachment[] }>;
|
|
48
59
|
}
|
|
49
60
|
|
|
50
61
|
export default class PostProxyMCP extends WorkerEntrypoint<Env> {
|
|
@@ -177,7 +188,8 @@ export default class PostProxyMCP extends WorkerEntrypoint<Env> {
|
|
|
177
188
|
schedule?: string,
|
|
178
189
|
draft?: boolean,
|
|
179
190
|
platformParams?: Record<string, Record<string, any>>,
|
|
180
|
-
idempotencyKey?: string
|
|
191
|
+
idempotencyKey?: string,
|
|
192
|
+
threadChildren?: Array<{ body: string; media?: string[] }>
|
|
181
193
|
): Promise<any> {
|
|
182
194
|
const baseUrl = this.env.POSTPROXY_BASE_URL.replace(/\/$/, "");
|
|
183
195
|
const url = `${baseUrl}/posts`;
|
|
@@ -224,6 +236,11 @@ export default class PostProxyMCP extends WorkerEntrypoint<Env> {
|
|
|
224
236
|
formData.append("platforms", JSON.stringify(platformParams));
|
|
225
237
|
}
|
|
226
238
|
|
|
239
|
+
// Add thread children
|
|
240
|
+
if (threadChildren && threadChildren.length > 0) {
|
|
241
|
+
formData.append("thread", JSON.stringify(threadChildren));
|
|
242
|
+
}
|
|
243
|
+
|
|
227
244
|
// Build headers
|
|
228
245
|
const headers: Record<string, string> = {
|
|
229
246
|
Authorization: `Bearer ${this.getApiKey()}`,
|
|
@@ -290,7 +307,10 @@ export default class PostProxyMCP extends WorkerEntrypoint<Env> {
|
|
|
290
307
|
*/
|
|
291
308
|
private determineOverallStatus(
|
|
292
309
|
post: Post
|
|
293
|
-
): "pending" | "processing" | "complete" | "failed" | "draft" {
|
|
310
|
+
): "pending" | "processing" | "complete" | "failed" | "draft" | "media_processing_failed" {
|
|
311
|
+
if (post.status === "media_processing_failed") {
|
|
312
|
+
return "media_processing_failed";
|
|
313
|
+
}
|
|
294
314
|
if (post.status === "draft" || post.draft === true) {
|
|
295
315
|
return "draft";
|
|
296
316
|
}
|
|
@@ -382,6 +402,9 @@ export default class PostProxyMCP extends WorkerEntrypoint<Env> {
|
|
|
382
402
|
* @param draft {boolean} If true, creates a draft post that won't publish automatically
|
|
383
403
|
* @param platforms {string} Optional JSON string of platform-specific parameters
|
|
384
404
|
* @param media_files {string} Optional JSON array of file objects with {filename, data (base64), content_type?}
|
|
405
|
+
* @param thread {string} Optional JSON array of thread child posts [{body, media?}]. Supported on X and Threads only.
|
|
406
|
+
* @param queue_id {string} Optional queue ID to add the post to
|
|
407
|
+
* @param queue_priority {string} Optional priority when adding to a queue (high, medium, low)
|
|
385
408
|
* @return {Promise<string>} Post creation result as JSON
|
|
386
409
|
*/
|
|
387
410
|
async postPublish(
|
|
@@ -393,7 +416,10 @@ export default class PostProxyMCP extends WorkerEntrypoint<Env> {
|
|
|
393
416
|
require_confirmation?: boolean,
|
|
394
417
|
draft?: boolean,
|
|
395
418
|
platforms?: string,
|
|
396
|
-
media_files?: string
|
|
419
|
+
media_files?: string,
|
|
420
|
+
thread?: string,
|
|
421
|
+
queue_id?: string,
|
|
422
|
+
queue_priority?: string
|
|
397
423
|
): Promise<string> {
|
|
398
424
|
this.getApiKey(); // Validate API key is present
|
|
399
425
|
|
|
@@ -432,6 +458,27 @@ export default class PostProxyMCP extends WorkerEntrypoint<Env> {
|
|
|
432
458
|
}
|
|
433
459
|
}
|
|
434
460
|
|
|
461
|
+
// Parse thread JSON if provided
|
|
462
|
+
let threadChildren: Array<{ body: string; media?: string[] }> | undefined;
|
|
463
|
+
if (thread) {
|
|
464
|
+
try {
|
|
465
|
+
threadChildren = JSON.parse(thread);
|
|
466
|
+
if (!Array.isArray(threadChildren)) {
|
|
467
|
+
throw new Error("thread must be an array");
|
|
468
|
+
}
|
|
469
|
+
for (const child of threadChildren) {
|
|
470
|
+
if (!child.body) {
|
|
471
|
+
throw new Error("Each thread child must have a 'body' property");
|
|
472
|
+
}
|
|
473
|
+
}
|
|
474
|
+
} catch (e: any) {
|
|
475
|
+
if (e.message.includes("thread")) {
|
|
476
|
+
throw e;
|
|
477
|
+
}
|
|
478
|
+
throw new Error("Invalid thread parameter: must be valid JSON array");
|
|
479
|
+
}
|
|
480
|
+
}
|
|
481
|
+
|
|
435
482
|
// Validate input
|
|
436
483
|
if (!content || content.trim() === "") {
|
|
437
484
|
throw new Error("Content cannot be empty");
|
|
@@ -452,6 +499,7 @@ export default class PostProxyMCP extends WorkerEntrypoint<Env> {
|
|
|
452
499
|
schedule_time: schedule,
|
|
453
500
|
draft: draft || false,
|
|
454
501
|
platforms: platformParams || {},
|
|
502
|
+
thread: threadChildren || [],
|
|
455
503
|
},
|
|
456
504
|
},
|
|
457
505
|
null,
|
|
@@ -503,7 +551,8 @@ export default class PostProxyMCP extends WorkerEntrypoint<Env> {
|
|
|
503
551
|
schedule,
|
|
504
552
|
draft,
|
|
505
553
|
platformParams,
|
|
506
|
-
finalIdempotencyKey
|
|
554
|
+
finalIdempotencyKey,
|
|
555
|
+
threadChildren
|
|
507
556
|
);
|
|
508
557
|
} else {
|
|
509
558
|
// Create post with JSON (URLs only)
|
|
@@ -527,6 +576,17 @@ export default class PostProxyMCP extends WorkerEntrypoint<Env> {
|
|
|
527
576
|
apiPayload.platforms = platformParams;
|
|
528
577
|
}
|
|
529
578
|
|
|
579
|
+
if (threadChildren && threadChildren.length > 0) {
|
|
580
|
+
apiPayload.thread = threadChildren;
|
|
581
|
+
}
|
|
582
|
+
|
|
583
|
+
if (queue_id) {
|
|
584
|
+
apiPayload.queue_id = queue_id;
|
|
585
|
+
if (queue_priority) {
|
|
586
|
+
apiPayload.queue_priority = queue_priority;
|
|
587
|
+
}
|
|
588
|
+
}
|
|
589
|
+
|
|
530
590
|
const extraHeaders: Record<string, string> = {
|
|
531
591
|
"Idempotency-Key": finalIdempotencyKey,
|
|
532
592
|
};
|
|
@@ -579,17 +639,23 @@ export default class PostProxyMCP extends WorkerEntrypoint<Env> {
|
|
|
579
639
|
|
|
580
640
|
const overallStatus = this.determineOverallStatus(postDetails);
|
|
581
641
|
|
|
582
|
-
|
|
583
|
-
|
|
584
|
-
|
|
585
|
-
|
|
586
|
-
|
|
587
|
-
|
|
588
|
-
|
|
589
|
-
|
|
590
|
-
|
|
591
|
-
|
|
592
|
-
|
|
642
|
+
const result: any = {
|
|
643
|
+
job_id: job_id,
|
|
644
|
+
overall_status: overallStatus,
|
|
645
|
+
draft: postDetails.draft || false,
|
|
646
|
+
status: postDetails.status,
|
|
647
|
+
platforms,
|
|
648
|
+
};
|
|
649
|
+
|
|
650
|
+
if (postDetails.media && postDetails.media.length > 0) {
|
|
651
|
+
result.media = postDetails.media;
|
|
652
|
+
}
|
|
653
|
+
|
|
654
|
+
if (postDetails.thread && postDetails.thread.length > 0) {
|
|
655
|
+
result.thread = postDetails.thread;
|
|
656
|
+
}
|
|
657
|
+
|
|
658
|
+
return JSON.stringify(result, null, 2);
|
|
593
659
|
}
|
|
594
660
|
|
|
595
661
|
/**
|
|
@@ -731,6 +797,171 @@ export default class PostProxyMCP extends WorkerEntrypoint<Env> {
|
|
|
731
797
|
return JSON.stringify({ placements }, null, 2);
|
|
732
798
|
}
|
|
733
799
|
|
|
800
|
+
/**
|
|
801
|
+
* List all queues
|
|
802
|
+
* @param profile_group_id {string} Optional profile group ID to filter queues
|
|
803
|
+
* @return {Promise<string>} List of queues as JSON
|
|
804
|
+
*/
|
|
805
|
+
async queuesList(profile_group_id?: string): Promise<string> {
|
|
806
|
+
this.getApiKey();
|
|
807
|
+
|
|
808
|
+
const path = profile_group_id
|
|
809
|
+
? `/post_queues?profile_group_id=${profile_group_id}`
|
|
810
|
+
: "/post_queues";
|
|
811
|
+
const response = await this.apiRequest<any>("GET", path);
|
|
812
|
+
const queues = this.extractArray<any>(response);
|
|
813
|
+
|
|
814
|
+
return JSON.stringify({ queues }, null, 2);
|
|
815
|
+
}
|
|
816
|
+
|
|
817
|
+
/**
|
|
818
|
+
* Get a single queue by ID
|
|
819
|
+
* @param queue_id {string} Queue ID
|
|
820
|
+
* @return {Promise<string>} Queue details as JSON
|
|
821
|
+
*/
|
|
822
|
+
async queuesGet(queue_id: string): Promise<string> {
|
|
823
|
+
if (!queue_id) {
|
|
824
|
+
throw new Error("queue_id is required");
|
|
825
|
+
}
|
|
826
|
+
|
|
827
|
+
const queue = await this.apiRequest<any>("GET", `/post_queues/${queue_id}`);
|
|
828
|
+
return JSON.stringify(queue, null, 2);
|
|
829
|
+
}
|
|
830
|
+
|
|
831
|
+
/**
|
|
832
|
+
* Create a new posting queue
|
|
833
|
+
* @param profile_group_id {string} Profile group ID to connect the queue to
|
|
834
|
+
* @param name {string} Queue name
|
|
835
|
+
* @param description {string} Optional description
|
|
836
|
+
* @param timezone {string} Optional IANA timezone (default: UTC)
|
|
837
|
+
* @param jitter {number} Optional random offset in minutes (0-60)
|
|
838
|
+
* @param timeslots {string} Optional JSON array of timeslots [{day, time}]
|
|
839
|
+
* @return {Promise<string>} Created queue as JSON
|
|
840
|
+
*/
|
|
841
|
+
async queuesCreate(
|
|
842
|
+
profile_group_id: string,
|
|
843
|
+
name: string,
|
|
844
|
+
description?: string,
|
|
845
|
+
timezone?: string,
|
|
846
|
+
jitter?: number,
|
|
847
|
+
timeslots?: string
|
|
848
|
+
): Promise<string> {
|
|
849
|
+
this.getApiKey();
|
|
850
|
+
|
|
851
|
+
if (!profile_group_id) {
|
|
852
|
+
throw new Error("profile_group_id is required");
|
|
853
|
+
}
|
|
854
|
+
if (!name) {
|
|
855
|
+
throw new Error("name is required");
|
|
856
|
+
}
|
|
857
|
+
|
|
858
|
+
const apiPayload: any = {
|
|
859
|
+
profile_group_id,
|
|
860
|
+
post_queue: { name },
|
|
861
|
+
};
|
|
862
|
+
if (description !== undefined) {
|
|
863
|
+
apiPayload.post_queue.description = description;
|
|
864
|
+
}
|
|
865
|
+
if (timezone) {
|
|
866
|
+
apiPayload.post_queue.timezone = timezone;
|
|
867
|
+
}
|
|
868
|
+
if (jitter !== undefined) {
|
|
869
|
+
apiPayload.post_queue.jitter = jitter;
|
|
870
|
+
}
|
|
871
|
+
if (timeslots) {
|
|
872
|
+
try {
|
|
873
|
+
const parsed = JSON.parse(timeslots);
|
|
874
|
+
if (Array.isArray(parsed)) {
|
|
875
|
+
apiPayload.post_queue.queue_timeslots_attributes = parsed;
|
|
876
|
+
}
|
|
877
|
+
} catch {
|
|
878
|
+
throw new Error("Invalid timeslots parameter: must be valid JSON array");
|
|
879
|
+
}
|
|
880
|
+
}
|
|
881
|
+
|
|
882
|
+
const queue = await this.apiRequest<any>("POST", "/post_queues", apiPayload);
|
|
883
|
+
return JSON.stringify({ ...queue, message: "Queue created successfully" }, null, 2);
|
|
884
|
+
}
|
|
885
|
+
|
|
886
|
+
/**
|
|
887
|
+
* Update a queue's settings
|
|
888
|
+
* @param queue_id {string} Queue ID to update
|
|
889
|
+
* @param name {string} Optional new name
|
|
890
|
+
* @param description {string} Optional new description
|
|
891
|
+
* @param timezone {string} Optional IANA timezone
|
|
892
|
+
* @param enabled {boolean} Optional pause/unpause
|
|
893
|
+
* @param jitter {number} Optional random offset in minutes (0-60)
|
|
894
|
+
* @param timeslots {string} Optional JSON array of timeslots to add/remove
|
|
895
|
+
* @return {Promise<string>} Updated queue as JSON
|
|
896
|
+
*/
|
|
897
|
+
async queuesUpdate(
|
|
898
|
+
queue_id: string,
|
|
899
|
+
name?: string,
|
|
900
|
+
description?: string,
|
|
901
|
+
timezone?: string,
|
|
902
|
+
enabled?: boolean,
|
|
903
|
+
jitter?: number,
|
|
904
|
+
timeslots?: string
|
|
905
|
+
): Promise<string> {
|
|
906
|
+
this.getApiKey();
|
|
907
|
+
|
|
908
|
+
if (!queue_id) {
|
|
909
|
+
throw new Error("queue_id is required");
|
|
910
|
+
}
|
|
911
|
+
|
|
912
|
+
const apiPayload: any = { post_queue: {} };
|
|
913
|
+
if (name !== undefined) apiPayload.post_queue.name = name;
|
|
914
|
+
if (description !== undefined) apiPayload.post_queue.description = description;
|
|
915
|
+
if (timezone !== undefined) apiPayload.post_queue.timezone = timezone;
|
|
916
|
+
if (enabled !== undefined) apiPayload.post_queue.enabled = enabled;
|
|
917
|
+
if (jitter !== undefined) apiPayload.post_queue.jitter = jitter;
|
|
918
|
+
if (timeslots) {
|
|
919
|
+
try {
|
|
920
|
+
const parsed = JSON.parse(timeslots);
|
|
921
|
+
if (Array.isArray(parsed)) {
|
|
922
|
+
apiPayload.post_queue.queue_timeslots_attributes = parsed;
|
|
923
|
+
}
|
|
924
|
+
} catch {
|
|
925
|
+
throw new Error("Invalid timeslots parameter: must be valid JSON array");
|
|
926
|
+
}
|
|
927
|
+
}
|
|
928
|
+
|
|
929
|
+
const queue = await this.apiRequest<any>("PATCH", `/post_queues/${queue_id}`, apiPayload);
|
|
930
|
+
return JSON.stringify({ ...queue, message: "Queue updated successfully" }, null, 2);
|
|
931
|
+
}
|
|
932
|
+
|
|
933
|
+
/**
|
|
934
|
+
* Delete a posting queue
|
|
935
|
+
* @param queue_id {string} Queue ID to delete
|
|
936
|
+
* @return {Promise<string>} Deletion confirmation as JSON
|
|
937
|
+
*/
|
|
938
|
+
async queuesDelete(queue_id: string): Promise<string> {
|
|
939
|
+
this.getApiKey();
|
|
940
|
+
|
|
941
|
+
if (!queue_id) {
|
|
942
|
+
throw new Error("queue_id is required");
|
|
943
|
+
}
|
|
944
|
+
|
|
945
|
+
await this.apiRequest<void>("DELETE", `/post_queues/${queue_id}`);
|
|
946
|
+
return JSON.stringify({ queue_id, deleted: true }, null, 2);
|
|
947
|
+
}
|
|
948
|
+
|
|
949
|
+
/**
|
|
950
|
+
* Get the next available timeslot for a queue
|
|
951
|
+
* @param queue_id {string} Queue ID
|
|
952
|
+
* @return {Promise<string>} Next slot as JSON
|
|
953
|
+
*/
|
|
954
|
+
async queuesNextSlot(queue_id: string): Promise<string> {
|
|
955
|
+
this.getApiKey();
|
|
956
|
+
|
|
957
|
+
if (!queue_id) {
|
|
958
|
+
throw new Error("queue_id is required");
|
|
959
|
+
}
|
|
960
|
+
|
|
961
|
+
const result = await this.apiRequest<any>("GET", `/post_queues/${queue_id}/next_slot`);
|
|
962
|
+
return JSON.stringify(result, null, 2);
|
|
963
|
+
}
|
|
964
|
+
|
|
734
965
|
/**
|
|
735
966
|
* MCP tool definitions
|
|
736
967
|
*/
|
|
@@ -748,7 +979,7 @@ export default class PostProxyMCP extends WorkerEntrypoint<Env> {
|
|
|
748
979
|
},
|
|
749
980
|
{
|
|
750
981
|
name: "postPublish",
|
|
751
|
-
description: "Publish a post to specified targets",
|
|
982
|
+
description: "Publish a post to specified targets. Supports threads (X and Threads only).",
|
|
752
983
|
inputSchema: {
|
|
753
984
|
type: "object",
|
|
754
985
|
properties: {
|
|
@@ -759,8 +990,11 @@ export default class PostProxyMCP extends WorkerEntrypoint<Env> {
|
|
|
759
990
|
idempotency_key: { type: "string", description: "Optional idempotency key for deduplication" },
|
|
760
991
|
require_confirmation: { type: "boolean", description: "If true, return summary without publishing" },
|
|
761
992
|
draft: { type: "boolean", description: "If true, creates a draft post" },
|
|
762
|
-
platforms: { type: "string", description: "Optional JSON string of platform-specific parameters" },
|
|
993
|
+
platforms: { type: "string", description: "Optional JSON string of platform-specific parameters. YouTube supports: title, privacy_status, cover_url, made_for_kids. TikTok supports: format (video|image), privacy_status, and more." },
|
|
763
994
|
media_files: { type: "string", description: "Optional JSON array of file objects for direct upload. Each object must have 'filename' and 'data' (base64-encoded file content), optionally 'content_type'. Example: [{\"filename\":\"photo.jpg\",\"data\":\"base64...\"}]" },
|
|
995
|
+
thread: { type: "string", description: "Optional JSON array of thread child posts. Supported on X and Threads only. Each object must have 'body' (string), optionally 'media' (array of URLs). Example: [{\"body\":\"Reply 1\"},{\"body\":\"Reply 2\",\"media\":[\"https://...\"]}]" },
|
|
996
|
+
queue_id: { type: "string", description: "Optional queue ID to add the post to. The queue will automatically assign a timeslot. Do not use together with 'schedule'." },
|
|
997
|
+
queue_priority: { type: "string", description: "Optional priority when adding to a queue: high, medium (default), or low" },
|
|
764
998
|
},
|
|
765
999
|
required: ["content", "targets"],
|
|
766
1000
|
},
|
|
@@ -834,6 +1068,83 @@ export default class PostProxyMCP extends WorkerEntrypoint<Env> {
|
|
|
834
1068
|
required: ["profile_id"],
|
|
835
1069
|
},
|
|
836
1070
|
},
|
|
1071
|
+
{
|
|
1072
|
+
name: "queuesList",
|
|
1073
|
+
description: "List all posting queues. Queues automatically schedule posts into recurring weekly timeslots.",
|
|
1074
|
+
inputSchema: {
|
|
1075
|
+
type: "object",
|
|
1076
|
+
properties: {
|
|
1077
|
+
profile_group_id: { type: "string", description: "Optional profile group ID to filter queues" },
|
|
1078
|
+
},
|
|
1079
|
+
required: [],
|
|
1080
|
+
},
|
|
1081
|
+
},
|
|
1082
|
+
{
|
|
1083
|
+
name: "queuesGet",
|
|
1084
|
+
description: "Get details of a single posting queue including its timeslots and post count",
|
|
1085
|
+
inputSchema: {
|
|
1086
|
+
type: "object",
|
|
1087
|
+
properties: {
|
|
1088
|
+
queue_id: { type: "string", description: "Queue ID" },
|
|
1089
|
+
},
|
|
1090
|
+
required: ["queue_id"],
|
|
1091
|
+
},
|
|
1092
|
+
},
|
|
1093
|
+
{
|
|
1094
|
+
name: "queuesCreate",
|
|
1095
|
+
description: "Create a new posting queue with weekly timeslots",
|
|
1096
|
+
inputSchema: {
|
|
1097
|
+
type: "object",
|
|
1098
|
+
properties: {
|
|
1099
|
+
profile_group_id: { type: "string", description: "Profile group ID to connect the queue to" },
|
|
1100
|
+
name: { type: "string", description: "Queue name" },
|
|
1101
|
+
description: { type: "string", description: "Optional description" },
|
|
1102
|
+
timezone: { type: "string", description: "IANA timezone name (default: UTC)" },
|
|
1103
|
+
jitter: { type: "number", description: "Random offset in minutes (0-60, default: 0)" },
|
|
1104
|
+
timeslots: { type: "string", description: "Optional JSON array of timeslots [{\"day\":1,\"time\":\"09:00\"}]. Day: 0=Sun..6=Sat" },
|
|
1105
|
+
},
|
|
1106
|
+
required: ["profile_group_id", "name"],
|
|
1107
|
+
},
|
|
1108
|
+
},
|
|
1109
|
+
{
|
|
1110
|
+
name: "queuesUpdate",
|
|
1111
|
+
description: "Update a queue's settings, timeslots, or pause/unpause it",
|
|
1112
|
+
inputSchema: {
|
|
1113
|
+
type: "object",
|
|
1114
|
+
properties: {
|
|
1115
|
+
queue_id: { type: "string", description: "Queue ID to update" },
|
|
1116
|
+
name: { type: "string", description: "New queue name" },
|
|
1117
|
+
description: { type: "string", description: "New description" },
|
|
1118
|
+
timezone: { type: "string", description: "IANA timezone name" },
|
|
1119
|
+
enabled: { type: "boolean", description: "Set false to pause, true to unpause" },
|
|
1120
|
+
jitter: { type: "number", description: "Random offset in minutes (0-60)" },
|
|
1121
|
+
timeslots: { type: "string", description: "JSON array of timeslots to add [{\"day\":1,\"time\":\"09:00\"}] or remove [{\"id\":42,\"_destroy\":true}]" },
|
|
1122
|
+
},
|
|
1123
|
+
required: ["queue_id"],
|
|
1124
|
+
},
|
|
1125
|
+
},
|
|
1126
|
+
{
|
|
1127
|
+
name: "queuesDelete",
|
|
1128
|
+
description: "Delete a posting queue. Posts in the queue will not be deleted.",
|
|
1129
|
+
inputSchema: {
|
|
1130
|
+
type: "object",
|
|
1131
|
+
properties: {
|
|
1132
|
+
queue_id: { type: "string", description: "Queue ID to delete" },
|
|
1133
|
+
},
|
|
1134
|
+
required: ["queue_id"],
|
|
1135
|
+
},
|
|
1136
|
+
},
|
|
1137
|
+
{
|
|
1138
|
+
name: "queuesNextSlot",
|
|
1139
|
+
description: "Get the next available timeslot for a queue",
|
|
1140
|
+
inputSchema: {
|
|
1141
|
+
type: "object",
|
|
1142
|
+
properties: {
|
|
1143
|
+
queue_id: { type: "string", description: "Queue ID" },
|
|
1144
|
+
},
|
|
1145
|
+
required: ["queue_id"],
|
|
1146
|
+
},
|
|
1147
|
+
},
|
|
837
1148
|
];
|
|
838
1149
|
}
|
|
839
1150
|
|
|
@@ -890,7 +1201,10 @@ export default class PostProxyMCP extends WorkerEntrypoint<Env> {
|
|
|
890
1201
|
args.require_confirmation,
|
|
891
1202
|
args.draft,
|
|
892
1203
|
args.platforms,
|
|
893
|
-
args.media_files
|
|
1204
|
+
args.media_files,
|
|
1205
|
+
args.thread,
|
|
1206
|
+
args.queue_id,
|
|
1207
|
+
args.queue_priority
|
|
894
1208
|
);
|
|
895
1209
|
break;
|
|
896
1210
|
case "postStatus":
|
|
@@ -911,6 +1225,39 @@ export default class PostProxyMCP extends WorkerEntrypoint<Env> {
|
|
|
911
1225
|
case "profilesPlacements":
|
|
912
1226
|
result = await this.profilesPlacements(args.profile_id);
|
|
913
1227
|
break;
|
|
1228
|
+
case "queuesList":
|
|
1229
|
+
result = await this.queuesList(args?.profile_group_id);
|
|
1230
|
+
break;
|
|
1231
|
+
case "queuesGet":
|
|
1232
|
+
result = await this.queuesGet(args.queue_id);
|
|
1233
|
+
break;
|
|
1234
|
+
case "queuesCreate":
|
|
1235
|
+
result = await this.queuesCreate(
|
|
1236
|
+
args.profile_group_id,
|
|
1237
|
+
args.name,
|
|
1238
|
+
args.description,
|
|
1239
|
+
args.timezone,
|
|
1240
|
+
args.jitter,
|
|
1241
|
+
args.timeslots
|
|
1242
|
+
);
|
|
1243
|
+
break;
|
|
1244
|
+
case "queuesUpdate":
|
|
1245
|
+
result = await this.queuesUpdate(
|
|
1246
|
+
args.queue_id,
|
|
1247
|
+
args.name,
|
|
1248
|
+
args.description,
|
|
1249
|
+
args.timezone,
|
|
1250
|
+
args.enabled,
|
|
1251
|
+
args.jitter,
|
|
1252
|
+
args.timeslots
|
|
1253
|
+
);
|
|
1254
|
+
break;
|
|
1255
|
+
case "queuesDelete":
|
|
1256
|
+
result = await this.queuesDelete(args.queue_id);
|
|
1257
|
+
break;
|
|
1258
|
+
case "queuesNextSlot":
|
|
1259
|
+
result = await this.queuesNextSlot(args.queue_id);
|
|
1260
|
+
break;
|
|
914
1261
|
default:
|
|
915
1262
|
return {
|
|
916
1263
|
jsonrpc: "2.0",
|