postpeer 0.1.0__py3-none-any.whl
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.
- postpeer/__init__.py +40 -0
- postpeer/_generated/pydantic_gen.py +2061 -0
- postpeer/_transport.py +224 -0
- postpeer/_version.py +1 -0
- postpeer/client.py +131 -0
- postpeer/errors.py +125 -0
- postpeer/py.typed +1 -0
- postpeer/resources/__init__.py +3 -0
- postpeer/resources/_generated.py +2107 -0
- postpeer/types.py +3 -0
- postpeer-0.1.0.dist-info/METADATA +213 -0
- postpeer-0.1.0.dist-info/RECORD +14 -0
- postpeer-0.1.0.dist-info/WHEEL +4 -0
- postpeer-0.1.0.dist-info/licenses/LICENSE +17 -0
|
@@ -0,0 +1,2061 @@
|
|
|
1
|
+
# This file is auto-generated by @hey-api/openapi-python
|
|
2
|
+
|
|
3
|
+
from datetime import date, datetime
|
|
4
|
+
from enum import Enum
|
|
5
|
+
from typing import Annotated, Any, Optional, Union
|
|
6
|
+
|
|
7
|
+
from pydantic import AnyUrl, BaseModel, ConfigDict, EmailStr, Field, RootModel
|
|
8
|
+
|
|
9
|
+
|
|
10
|
+
class Platform(str, Enum):
|
|
11
|
+
TWITTER = "twitter"
|
|
12
|
+
INSTAGRAM = "instagram"
|
|
13
|
+
YOUTUBE = "youtube"
|
|
14
|
+
TIKTOK = "tiktok"
|
|
15
|
+
PINTEREST = "pinterest"
|
|
16
|
+
LINKEDIN = "linkedin"
|
|
17
|
+
BLUESKY = "bluesky"
|
|
18
|
+
FACEBOOK = "facebook"
|
|
19
|
+
THREADS = "threads"
|
|
20
|
+
GOOGLEBUSINESS = "googlebusiness"
|
|
21
|
+
|
|
22
|
+
|
|
23
|
+
class Status(str, Enum):
|
|
24
|
+
DRAFT = "draft"
|
|
25
|
+
PENDING = "pending"
|
|
26
|
+
SCHEDULED = "scheduled"
|
|
27
|
+
PUBLISHING = "publishing"
|
|
28
|
+
PUBLISHED = "published"
|
|
29
|
+
FAILED = "failed"
|
|
30
|
+
PARTIAL = "partial"
|
|
31
|
+
|
|
32
|
+
|
|
33
|
+
class SortOrder(str, Enum):
|
|
34
|
+
ASC = "asc"
|
|
35
|
+
DESC = "desc"
|
|
36
|
+
|
|
37
|
+
|
|
38
|
+
class ErrorResponse(BaseModel):
|
|
39
|
+
success: bool
|
|
40
|
+
message: str
|
|
41
|
+
|
|
42
|
+
|
|
43
|
+
class TwitterConfigurationsReplySettings(str, Enum):
|
|
44
|
+
FOLLOWING = "following"
|
|
45
|
+
MENTIONED_USERS = "mentionedUsers"
|
|
46
|
+
SUBSCRIBERS = "subscribers"
|
|
47
|
+
VERIFIED = "verified"
|
|
48
|
+
|
|
49
|
+
|
|
50
|
+
class TwitterConfigurationsThreadItemsMediaItemsType(str, Enum):
|
|
51
|
+
IMAGE = "image"
|
|
52
|
+
VIDEO = "video"
|
|
53
|
+
GIF = "gif"
|
|
54
|
+
DOCUMENT = "document"
|
|
55
|
+
|
|
56
|
+
|
|
57
|
+
class TwitterConfigurationsThreadItemsMediaItems(BaseModel):
|
|
58
|
+
model_config = ConfigDict(extra="forbid")
|
|
59
|
+
type: TwitterConfigurationsThreadItemsMediaItemsType
|
|
60
|
+
url: AnyUrl
|
|
61
|
+
thumbnail: Optional[AnyUrl] = Field(default=None, description="Thumbnail image URL for video items. Supported on YouTube regular videos (not Shorts). JPEG, PNG, or GIF, max 2 MB, min 640 px wide.")
|
|
62
|
+
|
|
63
|
+
|
|
64
|
+
class TwitterConfigurationsThreadItems(BaseModel):
|
|
65
|
+
model_config = ConfigDict(populate_by_name=True, extra="forbid")
|
|
66
|
+
content: str = Field(..., description="Text of this thread tweet (max 280 chars)")
|
|
67
|
+
media_items: Optional[list[TwitterConfigurationsThreadItemsMediaItems]] = Field(default=None, alias="mediaItems")
|
|
68
|
+
|
|
69
|
+
|
|
70
|
+
class TwitterConfigurationsPoll(BaseModel):
|
|
71
|
+
"""Cannot be combined with media or threadItems."""
|
|
72
|
+
|
|
73
|
+
model_config = ConfigDict(populate_by_name=True, extra="forbid")
|
|
74
|
+
options: Annotated[list[str], Field(min_length=2, max_length=4)] = Field(..., description="2–4 poll options.")
|
|
75
|
+
duration_minutes: Annotated[float, Field(ge=5, le=10080)] = Field(..., alias="durationMinutes", description="Poll duration in minutes (5 min – 7 days).")
|
|
76
|
+
|
|
77
|
+
|
|
78
|
+
class TwitterConfigurations(BaseModel):
|
|
79
|
+
"""Pass this object in platformSpecificData when posting to Twitter/X, including Community post options."""
|
|
80
|
+
|
|
81
|
+
model_config = ConfigDict(populate_by_name=True, extra="forbid")
|
|
82
|
+
community_id: Optional[str] = Field(default=None, alias="communityId", description="Community ID to publish this post into.")
|
|
83
|
+
share_with_followers: Optional[bool] = Field(default=None, alias="shareWithFollowers", description="When posting to a Community, also share the post with followers.")
|
|
84
|
+
reply_to_tweet_id: Optional[str] = Field(default=None, alias="replyToTweetId", description="Tweet ID to reply to.")
|
|
85
|
+
reply_settings: Optional[TwitterConfigurationsReplySettings] = Field(default=None, alias="replySettings")
|
|
86
|
+
thread_items: Optional[list[TwitterConfigurationsThreadItems]] = Field(default=None, alias="threadItems", description="Additional tweets to chain as a thread. The root tweet uses post.content.")
|
|
87
|
+
poll: Optional[TwitterConfigurationsPoll] = Field(default=None, description="Cannot be combined with media or threadItems.")
|
|
88
|
+
|
|
89
|
+
|
|
90
|
+
class YouTubeConfigurationsVisibility(str, Enum):
|
|
91
|
+
"""Who can see the video. Defaults to "public". Scheduled posts upload as private and flip to this value at publish time."""
|
|
92
|
+
|
|
93
|
+
PUBLIC = "public"
|
|
94
|
+
PRIVATE = "private"
|
|
95
|
+
UNLISTED = "unlisted"
|
|
96
|
+
|
|
97
|
+
|
|
98
|
+
class YouTubeConfigurations(BaseModel):
|
|
99
|
+
"""Pass this object in platformSpecificData when posting to YouTube."""
|
|
100
|
+
|
|
101
|
+
model_config = ConfigDict(populate_by_name=True, extra="forbid")
|
|
102
|
+
title: Optional[Annotated[str, Field(max_length=100)]] = Field(default=None, description='Video title (max 100 chars, no < or >). Defaults to first 100 chars of content, or "Untitled Video".')
|
|
103
|
+
tags: Optional[list[str]] = Field(default=None, description="Video tags. Total characters across all tags must be ≤500.")
|
|
104
|
+
visibility: Optional[YouTubeConfigurationsVisibility] = Field(default=None, description='Who can see the video. Defaults to "public". Scheduled posts upload as private and flip to this value at publish time.')
|
|
105
|
+
made_for_kids: Optional[bool] = Field(default=None, alias="madeForKids", description="COPPA compliance flag. Setting to true permanently disables comments, notification bell, personalized ads, end screens, and cards on the video. Defaults to false.")
|
|
106
|
+
contains_synthetic_media: Optional[bool] = Field(default=None, alias="containsSyntheticMedia", description="AI-generated content disclosure. YouTube is increasingly enforcing this requirement. Defaults to false.")
|
|
107
|
+
category_id: Optional[str] = Field(default=None, alias="categoryId", description='YouTube category ID. Defaults to "22" (People & Blogs). Common values: "1" Film & Animation, "10" Music, "20" Gaming, "22" People & Blogs, "27" Education, "28" Science & Technology.')
|
|
108
|
+
first_comment: Optional[Annotated[str, Field(max_length=10000)]] = Field(default=None, alias="firstComment", description="Auto-posted comment after the video goes live. Max 10,000 characters. For publishNow posts: posted immediately after upload. For scheduled posts: posted when the video becomes public.")
|
|
109
|
+
|
|
110
|
+
|
|
111
|
+
class TikTokConfigurationsPrivacyLevel(str, Enum):
|
|
112
|
+
"""Who can see this post. Defaults to "PUBLIC_TO_EVERYONE"."""
|
|
113
|
+
|
|
114
|
+
PUBLIC_TO_EVERYONE = "PUBLIC_TO_EVERYONE"
|
|
115
|
+
MUTUAL_FOLLOW_FRIENDS = "MUTUAL_FOLLOW_FRIENDS"
|
|
116
|
+
FOLLOWER_OF_CREATOR = "FOLLOWER_OF_CREATOR"
|
|
117
|
+
SELF_ONLY = "SELF_ONLY"
|
|
118
|
+
|
|
119
|
+
|
|
120
|
+
class TikTokConfigurations(BaseModel):
|
|
121
|
+
"""Pass this object in platformSpecificData when posting to TikTok."""
|
|
122
|
+
|
|
123
|
+
model_config = ConfigDict(populate_by_name=True, extra="forbid")
|
|
124
|
+
privacy_level: Optional[TikTokConfigurationsPrivacyLevel] = Field(default=None, alias="privacyLevel", description='Who can see this post. Defaults to "PUBLIC_TO_EVERYONE".')
|
|
125
|
+
disable_comment: Optional[bool] = Field(default=None, alias="disableComment", description="Disable comments on this post. Defaults to false.")
|
|
126
|
+
disable_duet: Optional[bool] = Field(default=None, alias="disableDuet", description="Disable duet for this video. Videos only. Defaults to false.")
|
|
127
|
+
disable_stitch: Optional[bool] = Field(default=None, alias="disableStitch", description="Disable stitch for this video. Videos only. Defaults to false.")
|
|
128
|
+
brand_content_toggle: Optional[bool] = Field(default=None, alias="brandContentToggle", description="Mark as branded content (paid partnership). Defaults to false.")
|
|
129
|
+
brand_organic_toggle: Optional[bool] = Field(default=None, alias="brandOrganicToggle", description="Mark as organic brand promotion. Defaults to false.")
|
|
130
|
+
is_aigc: Optional[bool] = Field(default=None, alias="isAigc", description="AI-generated content disclosure. Videos only. Defaults to false.")
|
|
131
|
+
video_cover_timestamp_ms: Optional[Annotated[float, Field(ge=0)]] = Field(default=None, alias="videoCoverTimestampMs", description="Timestamp in milliseconds to use as the video cover frame. Videos only.")
|
|
132
|
+
auto_add_music: Optional[bool] = Field(default=None, alias="autoAddMusic", description="Automatically add background music to photo carousels. Photo posts only. Defaults to true.")
|
|
133
|
+
photo_cover_index: Optional[Annotated[float, Field(ge=0)]] = Field(default=None, alias="photoCoverIndex", description="0-indexed position of the cover image in a photo carousel. Photo posts only. Defaults to 0.")
|
|
134
|
+
description: Optional[Annotated[str, Field(max_length=4000)]] = Field(default=None, description="Separate description for a TikTok photo or carousel post. Max 4,000 characters. When omitted, the post content is also used as the description. Photo posts only.")
|
|
135
|
+
draft: Optional[bool] = Field(default=None, description="When true, sends content to the creator's TikTok inbox as a draft. Defaults to false (publishes immediately via DIRECT_POST).")
|
|
136
|
+
|
|
137
|
+
|
|
138
|
+
class PinterestConfigurations(BaseModel):
|
|
139
|
+
"""Pass this object in platformSpecificData when posting to Pinterest."""
|
|
140
|
+
|
|
141
|
+
model_config = ConfigDict(populate_by_name=True, extra="forbid")
|
|
142
|
+
board_id: str = Field(..., alias="boardId", description="Target board ID. Retrieve available boards via GET /v1/pinterest/boards.")
|
|
143
|
+
title: Optional[Annotated[str, Field(max_length=100)]] = Field(default=None, description="Pin title. Max 100 characters. Defaults to first line of content.")
|
|
144
|
+
link: Optional[AnyUrl] = Field(default=None, description="HTTPS destination URL when the pin is clicked. Important for driving traffic.")
|
|
145
|
+
alt_text: Optional[Annotated[str, Field(max_length=500)]] = Field(default=None, alias="altText", description="Accessible image description. Max 500 characters.")
|
|
146
|
+
dominant_color: Optional[str] = Field(default=None, alias="dominantColor", description='Hex color for the loading placeholder (e.g. "#6E7874").')
|
|
147
|
+
cover_image_url: Optional[AnyUrl] = Field(default=None, alias="coverImageUrl", description="Custom cover image URL for video pins.")
|
|
148
|
+
|
|
149
|
+
|
|
150
|
+
class LinkedInConfigurationsVisibility(str, Enum):
|
|
151
|
+
"""Post visibility. "PUBLIC" = visible to everyone, "CONNECTIONS" = visible to connections only. Defaults to "PUBLIC"."""
|
|
152
|
+
|
|
153
|
+
PUBLIC = "PUBLIC"
|
|
154
|
+
CONNECTIONS = "CONNECTIONS"
|
|
155
|
+
|
|
156
|
+
|
|
157
|
+
class LinkedInConfigurations(BaseModel):
|
|
158
|
+
"""Pass this object in platformSpecificData when posting to LinkedIn."""
|
|
159
|
+
|
|
160
|
+
model_config = ConfigDict(populate_by_name=True, extra="forbid")
|
|
161
|
+
visibility: Optional[LinkedInConfigurationsVisibility] = Field(default=None, description='Post visibility. "PUBLIC" = visible to everyone, "CONNECTIONS" = visible to connections only. Defaults to "PUBLIC".')
|
|
162
|
+
article_url: Optional[AnyUrl] = Field(default=None, alias="articleUrl", description="URL for an article/link post. When provided, the post becomes a link share with a preview card.")
|
|
163
|
+
article_title: Optional[Annotated[str, Field(max_length=400)]] = Field(default=None, alias="articleTitle", description="Title for the article preview card. Max 400 characters.")
|
|
164
|
+
article_description: Optional[Annotated[str, Field(max_length=400)]] = Field(default=None, alias="articleDescription", description="Description for the article preview card. Max 400 characters.")
|
|
165
|
+
document_title: Optional[Annotated[str, Field(max_length=200)]] = Field(default=None, alias="documentTitle", description="Title shown on the document card when posting a PDF. Required by LinkedIn when a document media item is included.")
|
|
166
|
+
|
|
167
|
+
|
|
168
|
+
class BlueskyConfigurations(BaseModel):
|
|
169
|
+
"""Pass this object in platformSpecificData when posting to Bluesky."""
|
|
170
|
+
|
|
171
|
+
model_config = ConfigDict(populate_by_name=True, extra="forbid")
|
|
172
|
+
langs: Optional[list[str]] = Field(default=None, description='BCP-47 language tags for the post (e.g. ["en"], ["en-US", "es"]). Defaults to ["en"].')
|
|
173
|
+
alt_text: Optional[list[str]] = Field(default=None, alias="altText", description="Alt text for each image, in the same order as mediaItems. Strongly encouraged for accessibility.")
|
|
174
|
+
|
|
175
|
+
|
|
176
|
+
class FacebookConfigurations(BaseModel):
|
|
177
|
+
"""Pass this object in platformSpecificData when posting to Facebook Pages."""
|
|
178
|
+
|
|
179
|
+
model_config = ConfigDict(populate_by_name=True, extra="forbid")
|
|
180
|
+
link: Optional[AnyUrl] = Field(default=None, description="When provided on a text-only post, Facebook renders a link preview card from this URL's Open Graph tags. Ignored when mediaItems are attached.")
|
|
181
|
+
published: Optional[bool] = Field(default=None, description="When false, the post is created on the Page in unpublished/draft state — useful for staging or scheduling via Facebook's own composer. Defaults to true.")
|
|
182
|
+
video_thumbnail_url: Optional[AnyUrl] = Field(default=None, alias="videoThumbnailUrl", description="Video posts only. Public URL of an image Facebook will use as the video's cover/thumbnail. Applied as a follow-up call after publish — if the upload fails, the post still succeeds (Facebook just auto-picks a frame). Ignored when no video is attached.")
|
|
183
|
+
|
|
184
|
+
|
|
185
|
+
class InstagramConfigurations(BaseModel):
|
|
186
|
+
"""Pass this object in platformSpecificData when posting to Instagram Business accounts. All fields are optional and apply to Reels/video posts; image posts ignore them."""
|
|
187
|
+
|
|
188
|
+
model_config = ConfigDict(populate_by_name=True, extra="forbid")
|
|
189
|
+
share_to_feed: Optional[bool] = Field(default=None, alias="shareToFeed", description="Reels-only. When true (default), the Reel also appears in the account's main feed grid. Set false to publish to Reels only.")
|
|
190
|
+
cover_url: Optional[AnyUrl] = Field(default=None, alias="coverUrl", description="Video-only. Public URL of an image Instagram will use as the cover frame for the Reel/video post. Ignored for image posts.")
|
|
191
|
+
thumb_offset: Optional[Annotated[int, Field(ge=0)]] = Field(default=None, alias="thumbOffset", description="Video-only. Timestamp in milliseconds Instagram extracts as the cover frame. Ignored when coverUrl is set or for image posts.")
|
|
192
|
+
|
|
193
|
+
|
|
194
|
+
class ThreadsConfigurationsReplyControl(str, Enum):
|
|
195
|
+
"""Who can reply to this thread. Defaults to "everyone" when omitted."""
|
|
196
|
+
|
|
197
|
+
EVERYONE = "everyone"
|
|
198
|
+
ACCOUNTS_YOU_FOLLOW = "accounts_you_follow"
|
|
199
|
+
MENTIONED_ONLY = "mentioned_only"
|
|
200
|
+
|
|
201
|
+
|
|
202
|
+
class ThreadsConfigurations(BaseModel):
|
|
203
|
+
"""Pass this object in platformSpecificData when posting to Threads."""
|
|
204
|
+
|
|
205
|
+
model_config = ConfigDict(populate_by_name=True, extra="forbid")
|
|
206
|
+
reply_control: Optional[ThreadsConfigurationsReplyControl] = Field(default=None, alias="replyControl", description='Who can reply to this thread. Defaults to "everyone" when omitted.')
|
|
207
|
+
alt_text: Optional[list[str]] = Field(default=None, alias="altText", description="Alt text for each image, in the same order as mediaItems. Strongly encouraged for accessibility.")
|
|
208
|
+
|
|
209
|
+
|
|
210
|
+
class GoogleBusinessConfigurationsTopicType(str, Enum):
|
|
211
|
+
"""Post type. Defaults to STANDARD. Use EVENT for event posts, OFFER for promotional offer posts."""
|
|
212
|
+
|
|
213
|
+
STANDARD = "STANDARD"
|
|
214
|
+
EVENT = "EVENT"
|
|
215
|
+
OFFER = "OFFER"
|
|
216
|
+
|
|
217
|
+
|
|
218
|
+
class GoogleBusinessConfigurationsCallToActionType(str, Enum):
|
|
219
|
+
"""Call-to-action button shown on the post."""
|
|
220
|
+
|
|
221
|
+
BOOK = "BOOK"
|
|
222
|
+
ORDER = "ORDER"
|
|
223
|
+
SHOP = "SHOP"
|
|
224
|
+
LEARN_MORE = "LEARN_MORE"
|
|
225
|
+
SIGN_UP = "SIGN_UP"
|
|
226
|
+
CALL = "CALL"
|
|
227
|
+
GET_OFFER = "GET_OFFER"
|
|
228
|
+
|
|
229
|
+
|
|
230
|
+
class GoogleBusinessConfigurations(BaseModel):
|
|
231
|
+
"""Pass this object in platformSpecificData when posting to Google Business Profile. Posts appear on Google Search and Maps."""
|
|
232
|
+
|
|
233
|
+
model_config = ConfigDict(populate_by_name=True, extra="forbid")
|
|
234
|
+
topic_type: Optional[GoogleBusinessConfigurationsTopicType] = Field(default=None, alias="topicType", description="Post type. Defaults to STANDARD. Use EVENT for event posts, OFFER for promotional offer posts.")
|
|
235
|
+
call_to_action_type: Optional[GoogleBusinessConfigurationsCallToActionType] = Field(default=None, alias="callToActionType", description="Call-to-action button shown on the post.")
|
|
236
|
+
call_to_action_url: Optional[AnyUrl] = Field(default=None, alias="callToActionUrl", description="URL for the call-to-action. Required for all CTA types except CALL.")
|
|
237
|
+
event_title: Optional[str] = Field(default=None, alias="eventTitle", description="Event title. Required when topicType is EVENT.")
|
|
238
|
+
event_start_date: Optional[str] = Field(default=None, alias="eventStartDate", description="Event start date in YYYY-MM-DD format. Required when topicType is EVENT.")
|
|
239
|
+
event_start_time: Optional[str] = Field(default=None, alias="eventStartTime", description="Event start time in HH:MM (24-hour) format. Required when topicType is EVENT.")
|
|
240
|
+
event_end_date: Optional[str] = Field(default=None, alias="eventEndDate", description="Event end date in YYYY-MM-DD format. Required when topicType is EVENT.")
|
|
241
|
+
event_end_time: Optional[str] = Field(default=None, alias="eventEndTime", description="Event end time in HH:MM (24-hour) format. Required when topicType is EVENT.")
|
|
242
|
+
offer_coupon_code: Optional[str] = Field(default=None, alias="offerCouponCode", description="Coupon code for OFFER posts.")
|
|
243
|
+
offer_redeem_online_url: Optional[AnyUrl] = Field(default=None, alias="offerRedeemOnlineUrl", description="Online redemption URL for OFFER posts.")
|
|
244
|
+
offer_terms_conditions: Optional[str] = Field(default=None, alias="offerTermsConditions", description="Terms and conditions text for OFFER posts.")
|
|
245
|
+
|
|
246
|
+
|
|
247
|
+
class PostPayloadMediaItemsType(str, Enum):
|
|
248
|
+
IMAGE = "image"
|
|
249
|
+
VIDEO = "video"
|
|
250
|
+
GIF = "gif"
|
|
251
|
+
DOCUMENT = "document"
|
|
252
|
+
|
|
253
|
+
|
|
254
|
+
class PostPayloadMediaItems(BaseModel):
|
|
255
|
+
model_config = ConfigDict(extra="forbid")
|
|
256
|
+
type: PostPayloadMediaItemsType
|
|
257
|
+
url: AnyUrl
|
|
258
|
+
thumbnail: Optional[AnyUrl] = Field(default=None, description="Thumbnail image URL for video items. Supported on YouTube regular videos (not Shorts). JPEG, PNG, or GIF, max 2 MB, min 640 px wide.")
|
|
259
|
+
|
|
260
|
+
|
|
261
|
+
class PostPayloadPlatformsPlatform(str, Enum):
|
|
262
|
+
TWITTER = "twitter"
|
|
263
|
+
|
|
264
|
+
|
|
265
|
+
class PostPayloadPlatforms(BaseModel):
|
|
266
|
+
model_config = ConfigDict(populate_by_name=True, extra="forbid")
|
|
267
|
+
platform: PostPayloadPlatformsPlatform
|
|
268
|
+
account_id: str = Field(..., alias="accountId", description="Integration._id — find yours via GET /connect/integrations")
|
|
269
|
+
content: Optional[str] = Field(default=None, description="Optional per-platform text override. Use when you want to change the text for this platform because different platforms talk differently. When omitted, the top-level `content` is used.")
|
|
270
|
+
platform_specific_data: Optional[TwitterConfigurations] = Field(default=None, alias="platformSpecificData")
|
|
271
|
+
|
|
272
|
+
|
|
273
|
+
class PostPayloadPlatformsPlatform_(str, Enum):
|
|
274
|
+
INSTAGRAM = "instagram"
|
|
275
|
+
|
|
276
|
+
|
|
277
|
+
class PostPayloadPlatforms_(BaseModel):
|
|
278
|
+
model_config = ConfigDict(populate_by_name=True, extra="forbid")
|
|
279
|
+
platform: PostPayloadPlatformsPlatform_
|
|
280
|
+
account_id: str = Field(..., alias="accountId", description="Integration._id — find yours via GET /connect/integrations")
|
|
281
|
+
content: Optional[str] = Field(default=None, description="Optional per-platform text override. Use when you want to change the text for this platform because different platforms talk differently. When omitted, the top-level `content` is used.")
|
|
282
|
+
platform_specific_data: Optional[InstagramConfigurations] = Field(default=None, alias="platformSpecificData")
|
|
283
|
+
|
|
284
|
+
|
|
285
|
+
class PostPayloadPlatformsPlatform_2(str, Enum):
|
|
286
|
+
YOUTUBE = "youtube"
|
|
287
|
+
|
|
288
|
+
|
|
289
|
+
class PostPayloadPlatforms_2(BaseModel):
|
|
290
|
+
model_config = ConfigDict(populate_by_name=True, extra="forbid")
|
|
291
|
+
platform: PostPayloadPlatformsPlatform_2
|
|
292
|
+
account_id: str = Field(..., alias="accountId", description="Integration._id — find yours via GET /connect/integrations")
|
|
293
|
+
content: Optional[str] = Field(default=None, description="Optional per-platform text override. Use when you want to change the text for this platform because different platforms talk differently. When omitted, the top-level `content` is used.")
|
|
294
|
+
platform_specific_data: Optional[YouTubeConfigurations] = Field(default=None, alias="platformSpecificData")
|
|
295
|
+
|
|
296
|
+
|
|
297
|
+
class PostPayloadPlatformsPlatform_3(str, Enum):
|
|
298
|
+
TIKTOK = "tiktok"
|
|
299
|
+
|
|
300
|
+
|
|
301
|
+
class PostPayloadPlatforms_3(BaseModel):
|
|
302
|
+
model_config = ConfigDict(populate_by_name=True, extra="forbid")
|
|
303
|
+
platform: PostPayloadPlatformsPlatform_3
|
|
304
|
+
account_id: str = Field(..., alias="accountId", description="Integration._id — find yours via GET /connect/integrations")
|
|
305
|
+
content: Optional[str] = Field(default=None, description="Optional per-platform text override. Use when you want to change the text for this platform because different platforms talk differently. When omitted, the top-level `content` is used.")
|
|
306
|
+
platform_specific_data: Optional[TikTokConfigurations] = Field(default=None, alias="platformSpecificData")
|
|
307
|
+
|
|
308
|
+
|
|
309
|
+
class PostPayloadPlatformsPlatform_4(str, Enum):
|
|
310
|
+
PINTEREST = "pinterest"
|
|
311
|
+
|
|
312
|
+
|
|
313
|
+
class PostPayloadPlatforms_4(BaseModel):
|
|
314
|
+
model_config = ConfigDict(populate_by_name=True, extra="forbid")
|
|
315
|
+
platform: PostPayloadPlatformsPlatform_4
|
|
316
|
+
account_id: str = Field(..., alias="accountId", description="Integration._id — find yours via GET /connect/integrations")
|
|
317
|
+
content: Optional[str] = Field(default=None, description="Optional per-platform text override. Use when you want to change the text for this platform because different platforms talk differently. When omitted, the top-level `content` is used.")
|
|
318
|
+
platform_specific_data: Optional[PinterestConfigurations] = Field(default=None, alias="platformSpecificData")
|
|
319
|
+
|
|
320
|
+
|
|
321
|
+
class PostPayloadPlatformsPlatform_5(str, Enum):
|
|
322
|
+
LINKEDIN = "linkedin"
|
|
323
|
+
|
|
324
|
+
|
|
325
|
+
class PostPayloadPlatforms_5(BaseModel):
|
|
326
|
+
model_config = ConfigDict(populate_by_name=True, extra="forbid")
|
|
327
|
+
platform: PostPayloadPlatformsPlatform_5
|
|
328
|
+
account_id: str = Field(..., alias="accountId", description="Integration._id — find yours via GET /connect/integrations")
|
|
329
|
+
content: Optional[str] = Field(default=None, description="Optional per-platform text override. Use when you want to change the text for this platform because different platforms talk differently. When omitted, the top-level `content` is used.")
|
|
330
|
+
platform_specific_data: Optional[LinkedInConfigurations] = Field(default=None, alias="platformSpecificData")
|
|
331
|
+
|
|
332
|
+
|
|
333
|
+
class PostPayloadPlatformsPlatform_6(str, Enum):
|
|
334
|
+
BLUESKY = "bluesky"
|
|
335
|
+
|
|
336
|
+
|
|
337
|
+
class PostPayloadPlatforms_6(BaseModel):
|
|
338
|
+
model_config = ConfigDict(populate_by_name=True, extra="forbid")
|
|
339
|
+
platform: PostPayloadPlatformsPlatform_6
|
|
340
|
+
account_id: str = Field(..., alias="accountId", description="Integration._id — find yours via GET /connect/integrations")
|
|
341
|
+
content: Optional[str] = Field(default=None, description="Optional per-platform text override. Use when you want to change the text for this platform because different platforms talk differently. When omitted, the top-level `content` is used.")
|
|
342
|
+
platform_specific_data: Optional[BlueskyConfigurations] = Field(default=None, alias="platformSpecificData")
|
|
343
|
+
|
|
344
|
+
|
|
345
|
+
class PostPayloadPlatformsPlatform_7(str, Enum):
|
|
346
|
+
FACEBOOK = "facebook"
|
|
347
|
+
|
|
348
|
+
|
|
349
|
+
class PostPayloadPlatforms_7(BaseModel):
|
|
350
|
+
model_config = ConfigDict(populate_by_name=True, extra="forbid")
|
|
351
|
+
platform: PostPayloadPlatformsPlatform_7
|
|
352
|
+
account_id: str = Field(..., alias="accountId", description="Integration._id — find yours via GET /connect/integrations")
|
|
353
|
+
content: Optional[str] = Field(default=None, description="Optional per-platform text override. Use when you want to change the text for this platform because different platforms talk differently. When omitted, the top-level `content` is used.")
|
|
354
|
+
platform_specific_data: Optional[FacebookConfigurations] = Field(default=None, alias="platformSpecificData")
|
|
355
|
+
|
|
356
|
+
|
|
357
|
+
class PostPayloadPlatformsPlatform_8(str, Enum):
|
|
358
|
+
THREADS = "threads"
|
|
359
|
+
|
|
360
|
+
|
|
361
|
+
class PostPayloadPlatforms_8(BaseModel):
|
|
362
|
+
model_config = ConfigDict(populate_by_name=True, extra="forbid")
|
|
363
|
+
platform: PostPayloadPlatformsPlatform_8
|
|
364
|
+
account_id: str = Field(..., alias="accountId", description="Integration._id — find yours via GET /connect/integrations")
|
|
365
|
+
content: Optional[str] = Field(default=None, description="Optional per-platform text override. Use when you want to change the text for this platform because different platforms talk differently. When omitted, the top-level `content` is used.")
|
|
366
|
+
platform_specific_data: Optional[ThreadsConfigurations] = Field(default=None, alias="platformSpecificData")
|
|
367
|
+
|
|
368
|
+
|
|
369
|
+
class PostPayloadPlatformsPlatform_9(str, Enum):
|
|
370
|
+
GOOGLEBUSINESS = "googlebusiness"
|
|
371
|
+
|
|
372
|
+
|
|
373
|
+
class PostPayloadPlatforms_9(BaseModel):
|
|
374
|
+
model_config = ConfigDict(populate_by_name=True, extra="forbid")
|
|
375
|
+
platform: PostPayloadPlatformsPlatform_9
|
|
376
|
+
account_id: str = Field(..., alias="accountId", description="Integration._id — find yours via GET /connect/integrations")
|
|
377
|
+
content: Optional[str] = Field(default=None, description="Optional per-platform text override. Use when you want to change the text for this platform because different platforms talk differently. When omitted, the top-level `content` is used.")
|
|
378
|
+
platform_specific_data: Optional[GoogleBusinessConfigurations] = Field(default=None, alias="platformSpecificData")
|
|
379
|
+
|
|
380
|
+
|
|
381
|
+
class PostPayload(BaseModel):
|
|
382
|
+
model_config = ConfigDict(populate_by_name=True, extra="forbid")
|
|
383
|
+
content: str = Field(..., description="Post text body")
|
|
384
|
+
media_items: Optional[list[PostPayloadMediaItems]] = Field(default=None, alias="mediaItems", description="Media attachments (images, videos, GIFs)")
|
|
385
|
+
platforms: Annotated[list[Union[PostPayloadPlatforms, PostPayloadPlatforms_, PostPayloadPlatforms_2, PostPayloadPlatforms_3, PostPayloadPlatforms_4, PostPayloadPlatforms_5, PostPayloadPlatforms_6, PostPayloadPlatforms_7, PostPayloadPlatforms_8, PostPayloadPlatforms_9]], Field(min_length=1)] = Field(..., description="Target platform accounts to publish to")
|
|
386
|
+
publish_now: Optional[bool] = Field(default=None, alias="publishNow", description="Publish immediately. Required when scheduledFor is omitted.")
|
|
387
|
+
scheduled_for: Optional[datetime] = Field(default=None, alias="scheduledFor", description="ISO 8601 datetime to schedule the post for future publishing")
|
|
388
|
+
timezone: Optional[str] = Field(default=None, description="IANA timezone for the scheduled time (e.g. America/New_York). Defaults to UTC.")
|
|
389
|
+
|
|
390
|
+
|
|
391
|
+
class HealthCheckResponse(BaseModel):
|
|
392
|
+
"""Default Response"""
|
|
393
|
+
|
|
394
|
+
ok: bool
|
|
395
|
+
|
|
396
|
+
|
|
397
|
+
class HealthCheckAuthResponse(BaseModel):
|
|
398
|
+
"""Default Response"""
|
|
399
|
+
|
|
400
|
+
ok: bool
|
|
401
|
+
|
|
402
|
+
|
|
403
|
+
class GetLinkedInSelectionPath(BaseModel):
|
|
404
|
+
token: Annotated[str, Field(min_length=1)]
|
|
405
|
+
|
|
406
|
+
|
|
407
|
+
class GetLinkedInSelectionPlatform(str, Enum):
|
|
408
|
+
LINKEDIN = "linkedin"
|
|
409
|
+
|
|
410
|
+
|
|
411
|
+
class GetLinkedInSelectionAccountsType(str, Enum):
|
|
412
|
+
PERSON = "person"
|
|
413
|
+
|
|
414
|
+
|
|
415
|
+
class GetLinkedInSelectionAccountsType_(str, Enum):
|
|
416
|
+
ORGANIZATION = "organization"
|
|
417
|
+
|
|
418
|
+
|
|
419
|
+
class GetLinkedInSelectionAccounts(BaseModel):
|
|
420
|
+
id: str
|
|
421
|
+
type: Union[GetLinkedInSelectionAccountsType, GetLinkedInSelectionAccountsType_]
|
|
422
|
+
platform_user_id: str = Field(..., alias="platformUserId")
|
|
423
|
+
display_name: Optional[str] = Field(default=None, alias="displayName")
|
|
424
|
+
username: Optional[str] = None
|
|
425
|
+
image_url: Optional[AnyUrl] = Field(default=None, alias="imageUrl")
|
|
426
|
+
|
|
427
|
+
|
|
428
|
+
class GetLinkedInSelectionResponse(BaseModel):
|
|
429
|
+
"""Default Response"""
|
|
430
|
+
|
|
431
|
+
success: bool
|
|
432
|
+
platform: GetLinkedInSelectionPlatform
|
|
433
|
+
expires_in_seconds: float = Field(..., alias="expiresInSeconds")
|
|
434
|
+
accounts: list[GetLinkedInSelectionAccounts]
|
|
435
|
+
|
|
436
|
+
|
|
437
|
+
class SubmitLinkedInSelectionBody(BaseModel):
|
|
438
|
+
model_config = ConfigDict(populate_by_name=True, extra="forbid")
|
|
439
|
+
selected_account_ids: Annotated[list[str], Field(min_length=1)] = Field(..., alias="selectedAccountIds")
|
|
440
|
+
|
|
441
|
+
|
|
442
|
+
class SubmitLinkedInSelectionPath(BaseModel):
|
|
443
|
+
token: Annotated[str, Field(min_length=1)]
|
|
444
|
+
|
|
445
|
+
|
|
446
|
+
class SubmitLinkedInSelectionPlatform(str, Enum):
|
|
447
|
+
LINKEDIN = "linkedin"
|
|
448
|
+
|
|
449
|
+
|
|
450
|
+
class SubmitLinkedInSelectionIntegrationsPlatform(str, Enum):
|
|
451
|
+
TWITTER = "twitter"
|
|
452
|
+
INSTAGRAM = "instagram"
|
|
453
|
+
YOUTUBE = "youtube"
|
|
454
|
+
TIKTOK = "tiktok"
|
|
455
|
+
PINTEREST = "pinterest"
|
|
456
|
+
LINKEDIN = "linkedin"
|
|
457
|
+
BLUESKY = "bluesky"
|
|
458
|
+
FACEBOOK = "facebook"
|
|
459
|
+
THREADS = "threads"
|
|
460
|
+
GOOGLEBUSINESS = "googlebusiness"
|
|
461
|
+
|
|
462
|
+
|
|
463
|
+
class SubmitLinkedInSelectionIntegrationsApp(BaseModel):
|
|
464
|
+
id: Optional[str] = None
|
|
465
|
+
name: Optional[str] = None
|
|
466
|
+
image_url: Optional[str] = Field(default=None, alias="imageUrl")
|
|
467
|
+
|
|
468
|
+
|
|
469
|
+
class SubmitLinkedInSelectionIntegrations(BaseModel):
|
|
470
|
+
id: str = Field(..., description="Use this as accountId when creating posts")
|
|
471
|
+
platform: SubmitLinkedInSelectionIntegrationsPlatform
|
|
472
|
+
platform_user_id: Optional[str] = Field(default=None, alias="platformUserId", description="The user ID on the platform, or null if not yet retrieved")
|
|
473
|
+
username: Optional[str] = Field(default=None, description="The public username or handle, including @ for handle-based platforms")
|
|
474
|
+
display_name: Optional[str] = Field(default=None, alias="displayName", description="Human-readable display name of the connected account")
|
|
475
|
+
profile_url: Optional[AnyUrl] = Field(default=None, alias="profileUrl", description="Public profile/page URL for the connected account, when it can be derived")
|
|
476
|
+
image_url: Optional[AnyUrl] = Field(default=None, alias="imageUrl", description="Profile image URL for the connected account, or null if unavailable")
|
|
477
|
+
platform_metadata: Optional[dict[str, Any]] = Field(default=None, alias="platformMetadata", description="Provider-specific public metadata for this connected account.")
|
|
478
|
+
profile_id: Optional[str] = Field(default=None, alias="profileId", description="Profile this integration belongs to, or null if it was connected without a profile")
|
|
479
|
+
app_id: Optional[str] = Field(default=None, alias="appId", description="The OAuth app (customer's own OAuth app) this integration was connected under, or null if postpeer's system app was used.")
|
|
480
|
+
app: Optional[SubmitLinkedInSelectionIntegrationsApp] = Field(default=None, description="The OAuth app metadata for BYOK integrations, or null when postpeer system app was used.")
|
|
481
|
+
byok: bool = Field(..., description="True when this integration was connected under the customer's own OAuth app (Bring Your Own Keys), i.e. appId is set. False when postpeer's system app is used.")
|
|
482
|
+
created_at: datetime = Field(..., alias="createdAt")
|
|
483
|
+
|
|
484
|
+
|
|
485
|
+
class SubmitLinkedInSelectionResponse(BaseModel):
|
|
486
|
+
"""Default Response"""
|
|
487
|
+
|
|
488
|
+
success: bool
|
|
489
|
+
platform: SubmitLinkedInSelectionPlatform
|
|
490
|
+
message: str
|
|
491
|
+
redirect_uri: Optional[str] = Field(default=None, alias="redirectUri")
|
|
492
|
+
integrations: list[SubmitLinkedInSelectionIntegrations]
|
|
493
|
+
|
|
494
|
+
|
|
495
|
+
class GetOAuthUrlPlatform(str, Enum):
|
|
496
|
+
TWITTER = "twitter"
|
|
497
|
+
INSTAGRAM = "instagram"
|
|
498
|
+
YOUTUBE = "youtube"
|
|
499
|
+
TIKTOK = "tiktok"
|
|
500
|
+
PINTEREST = "pinterest"
|
|
501
|
+
LINKEDIN = "linkedin"
|
|
502
|
+
BLUESKY = "bluesky"
|
|
503
|
+
FACEBOOK = "facebook"
|
|
504
|
+
THREADS = "threads"
|
|
505
|
+
GOOGLEBUSINESS = "googlebusiness"
|
|
506
|
+
|
|
507
|
+
|
|
508
|
+
class GetOAuthUrlPath(BaseModel):
|
|
509
|
+
platform: GetOAuthUrlPlatform
|
|
510
|
+
|
|
511
|
+
|
|
512
|
+
class GetOAuthUrlQuery(BaseModel):
|
|
513
|
+
redirect_uri: Optional[AnyUrl] = Field(default=None, alias="redirectUri", description="Final URL to redirect to after the connection completes. In headless mode, this URL also receives selection status query parameters when customer-owned account selection is required.")
|
|
514
|
+
cancel_redirect_uri: Optional[AnyUrl] = Field(default=None, alias="cancelRedirectUri", description="URL to redirect to when the user cancels or denies the OAuth prompt. Falls back to redirectUri when omitted.")
|
|
515
|
+
headless: Optional[bool] = Field(default=False, description="When true, platforms that require account selection redirect back to redirectUri with a short-lived selectionToken so you can build your own selection UI. When false, PostPeer hosts the selection UI.")
|
|
516
|
+
profile_id: Optional[str] = Field(default=None, alias="profileId", description="Profile to associate the resulting integration with. Must belong to the same project. Omit to connect without a profile.")
|
|
517
|
+
app_id: Optional[str] = Field(default=None, alias="appId", description="Connect under your own OAuth app (Bring Your Own Keys). Pass the id of an OAuth app created via /v1/apps for this same platform. Omit to use postpeer's system app.")
|
|
518
|
+
|
|
519
|
+
|
|
520
|
+
class GetOAuthUrlResponse(BaseModel):
|
|
521
|
+
"""Default Response"""
|
|
522
|
+
|
|
523
|
+
url: str
|
|
524
|
+
|
|
525
|
+
|
|
526
|
+
class ConnectBlueskyBody(BaseModel):
|
|
527
|
+
model_config = ConfigDict(extra="forbid")
|
|
528
|
+
identifier: str = Field(..., description='Bluesky handle (e.g. "alice.bsky.social") or DID (e.g. "did:plc:abc123").')
|
|
529
|
+
password: str = Field(..., description="An app password generated at https://bsky.app/settings/app-passwords. Do NOT use the account password.")
|
|
530
|
+
|
|
531
|
+
|
|
532
|
+
class ConnectBlueskyQuery(BaseModel):
|
|
533
|
+
redirect_uri: Optional[AnyUrl] = Field(default=None, alias="redirectUri", description="Final URL to redirect to after the connection completes. In headless mode, this URL also receives selection status query parameters when customer-owned account selection is required.")
|
|
534
|
+
cancel_redirect_uri: Optional[AnyUrl] = Field(default=None, alias="cancelRedirectUri", description="URL to redirect to when the user cancels or denies the OAuth prompt. Falls back to redirectUri when omitted.")
|
|
535
|
+
headless: Optional[bool] = Field(default=False, description="When true, platforms that require account selection redirect back to redirectUri with a short-lived selectionToken so you can build your own selection UI. When false, PostPeer hosts the selection UI.")
|
|
536
|
+
profile_id: Optional[str] = Field(default=None, alias="profileId", description="Profile to associate the resulting integration with. Must belong to the same project. Omit to connect without a profile.")
|
|
537
|
+
app_id: Optional[str] = Field(default=None, alias="appId", description="Connect under your own OAuth app (Bring Your Own Keys). Pass the id of an OAuth app created via /v1/apps for this same platform. Omit to use postpeer's system app.")
|
|
538
|
+
|
|
539
|
+
|
|
540
|
+
class ListIntegrationsPlatform(str, Enum):
|
|
541
|
+
TWITTER = "twitter"
|
|
542
|
+
INSTAGRAM = "instagram"
|
|
543
|
+
YOUTUBE = "youtube"
|
|
544
|
+
TIKTOK = "tiktok"
|
|
545
|
+
PINTEREST = "pinterest"
|
|
546
|
+
LINKEDIN = "linkedin"
|
|
547
|
+
BLUESKY = "bluesky"
|
|
548
|
+
FACEBOOK = "facebook"
|
|
549
|
+
THREADS = "threads"
|
|
550
|
+
GOOGLEBUSINESS = "googlebusiness"
|
|
551
|
+
|
|
552
|
+
|
|
553
|
+
class ListIntegrationsQuery(BaseModel):
|
|
554
|
+
platform: Optional[ListIntegrationsPlatform] = None
|
|
555
|
+
profile_id: Optional[str] = Field(default=None, alias="profileId", description='Filter to integrations belonging to this profile. Pass "null" (literal string) to filter to integrations with no profile.')
|
|
556
|
+
q: Optional[str] = Field(default=None, description="Case-insensitive search across the connected account name (displayName), username, and platform user ID.")
|
|
557
|
+
limit: Optional[Annotated[int, Field(ge=1, le=100)]] = Field(default=20, description="Page size (max 100)")
|
|
558
|
+
offset: Optional[Annotated[int, Field(ge=0)]] = Field(default=0, description="Number of integrations to skip")
|
|
559
|
+
sort: Optional[SortOrder] = None
|
|
560
|
+
|
|
561
|
+
|
|
562
|
+
class ListIntegrationsIntegrationsPlatform(str, Enum):
|
|
563
|
+
TWITTER = "twitter"
|
|
564
|
+
INSTAGRAM = "instagram"
|
|
565
|
+
YOUTUBE = "youtube"
|
|
566
|
+
TIKTOK = "tiktok"
|
|
567
|
+
PINTEREST = "pinterest"
|
|
568
|
+
LINKEDIN = "linkedin"
|
|
569
|
+
BLUESKY = "bluesky"
|
|
570
|
+
FACEBOOK = "facebook"
|
|
571
|
+
THREADS = "threads"
|
|
572
|
+
GOOGLEBUSINESS = "googlebusiness"
|
|
573
|
+
|
|
574
|
+
|
|
575
|
+
class ListIntegrationsIntegrationsApp(BaseModel):
|
|
576
|
+
id: Optional[str] = None
|
|
577
|
+
name: Optional[str] = None
|
|
578
|
+
image_url: Optional[str] = Field(default=None, alias="imageUrl")
|
|
579
|
+
|
|
580
|
+
|
|
581
|
+
class ListIntegrationsIntegrations(BaseModel):
|
|
582
|
+
id: str = Field(..., description="Use this as accountId when creating posts")
|
|
583
|
+
platform: ListIntegrationsIntegrationsPlatform
|
|
584
|
+
platform_user_id: Optional[str] = Field(default=None, alias="platformUserId", description="The user ID on the platform, or null if not yet retrieved")
|
|
585
|
+
username: Optional[str] = Field(default=None, description="The public username or handle, including @ for handle-based platforms")
|
|
586
|
+
display_name: Optional[str] = Field(default=None, alias="displayName", description="Human-readable display name of the connected account")
|
|
587
|
+
profile_url: Optional[AnyUrl] = Field(default=None, alias="profileUrl", description="Public profile/page URL for the connected account, when it can be derived")
|
|
588
|
+
image_url: Optional[AnyUrl] = Field(default=None, alias="imageUrl", description="Profile image URL for the connected account, or null if unavailable")
|
|
589
|
+
platform_metadata: Optional[dict[str, Any]] = Field(default=None, alias="platformMetadata", description="Provider-specific public metadata for this connected account.")
|
|
590
|
+
profile_id: Optional[str] = Field(default=None, alias="profileId", description="Profile this integration belongs to, or null if it was connected without a profile")
|
|
591
|
+
app_id: Optional[str] = Field(default=None, alias="appId", description="The OAuth app (customer's own OAuth app) this integration was connected under, or null if postpeer's system app was used.")
|
|
592
|
+
app: Optional[ListIntegrationsIntegrationsApp] = Field(default=None, description="The OAuth app metadata for BYOK integrations, or null when postpeer system app was used.")
|
|
593
|
+
byok: bool = Field(..., description="True when this integration was connected under the customer's own OAuth app (Bring Your Own Keys), i.e. appId is set. False when postpeer's system app is used.")
|
|
594
|
+
created_at: datetime = Field(..., alias="createdAt")
|
|
595
|
+
|
|
596
|
+
|
|
597
|
+
class ListIntegrationsResponse(BaseModel):
|
|
598
|
+
"""Default Response"""
|
|
599
|
+
|
|
600
|
+
success: bool
|
|
601
|
+
total: Annotated[int, Field(ge=0)] = Field(..., description="Total matched integrations across all pages")
|
|
602
|
+
integrations: list[ListIntegrationsIntegrations]
|
|
603
|
+
|
|
604
|
+
|
|
605
|
+
class DisconnectIntegrationPath(BaseModel):
|
|
606
|
+
id: str = Field(..., description="Integration ID to disconnect")
|
|
607
|
+
|
|
608
|
+
|
|
609
|
+
class DisconnectIntegrationResponse(BaseModel):
|
|
610
|
+
"""Default Response"""
|
|
611
|
+
|
|
612
|
+
success: bool
|
|
613
|
+
message: str
|
|
614
|
+
|
|
615
|
+
|
|
616
|
+
class ListProfilesQuery(BaseModel):
|
|
617
|
+
page: Optional[Annotated[int, Field(ge=1)]] = 1
|
|
618
|
+
limit: Optional[Annotated[int, Field(ge=1, le=100)]] = 50
|
|
619
|
+
name: Optional[Annotated[str, Field(min_length=1, max_length=200)]] = Field(default=None, description="Case-insensitive substring match on profile name")
|
|
620
|
+
|
|
621
|
+
|
|
622
|
+
class ListProfilesProfiles(BaseModel):
|
|
623
|
+
id: str
|
|
624
|
+
name: str
|
|
625
|
+
description: Optional[str] = None
|
|
626
|
+
integration_count: Annotated[int, Field(ge=0)] = Field(..., alias="integrationCount", description="Number of active integrations bound to this profile")
|
|
627
|
+
created_at: datetime = Field(..., alias="createdAt")
|
|
628
|
+
updated_at: datetime = Field(..., alias="updatedAt")
|
|
629
|
+
|
|
630
|
+
|
|
631
|
+
class ListProfilesResponse(BaseModel):
|
|
632
|
+
"""Default Response"""
|
|
633
|
+
|
|
634
|
+
success: bool
|
|
635
|
+
total: Annotated[int, Field(ge=0)]
|
|
636
|
+
page: Annotated[int, Field(ge=1)]
|
|
637
|
+
limit: Annotated[int, Field(ge=1)]
|
|
638
|
+
profiles: list[ListProfilesProfiles]
|
|
639
|
+
|
|
640
|
+
|
|
641
|
+
class CreateProfileBody(BaseModel):
|
|
642
|
+
name: Annotated[str, Field(min_length=1, max_length=200)] = Field(..., description='Profile name (e.g. "Acme Co", "Personal Brand")')
|
|
643
|
+
description: Optional[Annotated[str, Field(max_length=1000)]] = Field(default=None, description="Optional description of what this profile is for")
|
|
644
|
+
|
|
645
|
+
|
|
646
|
+
class CreateProfileProfile(BaseModel):
|
|
647
|
+
id: str
|
|
648
|
+
name: str
|
|
649
|
+
description: Optional[str] = None
|
|
650
|
+
integration_count: Annotated[int, Field(ge=0)] = Field(..., alias="integrationCount", description="Number of active integrations bound to this profile")
|
|
651
|
+
created_at: datetime = Field(..., alias="createdAt")
|
|
652
|
+
updated_at: datetime = Field(..., alias="updatedAt")
|
|
653
|
+
|
|
654
|
+
|
|
655
|
+
class CreateProfileResponse(BaseModel):
|
|
656
|
+
"""Default Response"""
|
|
657
|
+
|
|
658
|
+
success: bool
|
|
659
|
+
profile: CreateProfileProfile
|
|
660
|
+
|
|
661
|
+
|
|
662
|
+
class DeleteProfilePath(BaseModel):
|
|
663
|
+
id: str = Field(..., description="Profile ID")
|
|
664
|
+
|
|
665
|
+
|
|
666
|
+
class DeleteProfileResponse(BaseModel):
|
|
667
|
+
"""Default Response"""
|
|
668
|
+
|
|
669
|
+
success: bool
|
|
670
|
+
message: str
|
|
671
|
+
|
|
672
|
+
|
|
673
|
+
class GetProfilePath(BaseModel):
|
|
674
|
+
id: str = Field(..., description="Profile ID")
|
|
675
|
+
|
|
676
|
+
|
|
677
|
+
class GetProfileProfile(BaseModel):
|
|
678
|
+
id: str
|
|
679
|
+
name: str
|
|
680
|
+
description: Optional[str] = None
|
|
681
|
+
integration_count: Annotated[int, Field(ge=0)] = Field(..., alias="integrationCount", description="Number of active integrations bound to this profile")
|
|
682
|
+
created_at: datetime = Field(..., alias="createdAt")
|
|
683
|
+
updated_at: datetime = Field(..., alias="updatedAt")
|
|
684
|
+
|
|
685
|
+
|
|
686
|
+
class GetProfileResponse(BaseModel):
|
|
687
|
+
"""Default Response"""
|
|
688
|
+
|
|
689
|
+
success: bool
|
|
690
|
+
profile: GetProfileProfile
|
|
691
|
+
|
|
692
|
+
|
|
693
|
+
class UpdateProfileBody(BaseModel):
|
|
694
|
+
name: Optional[Annotated[str, Field(min_length=1, max_length=200)]] = None
|
|
695
|
+
description: Optional[Annotated[str, Field(max_length=1000)]] = None
|
|
696
|
+
|
|
697
|
+
|
|
698
|
+
class UpdateProfilePath(BaseModel):
|
|
699
|
+
id: str = Field(..., description="Profile ID")
|
|
700
|
+
|
|
701
|
+
|
|
702
|
+
class UpdateProfileProfile(BaseModel):
|
|
703
|
+
id: str
|
|
704
|
+
name: str
|
|
705
|
+
description: Optional[str] = None
|
|
706
|
+
integration_count: Annotated[int, Field(ge=0)] = Field(..., alias="integrationCount", description="Number of active integrations bound to this profile")
|
|
707
|
+
created_at: datetime = Field(..., alias="createdAt")
|
|
708
|
+
updated_at: datetime = Field(..., alias="updatedAt")
|
|
709
|
+
|
|
710
|
+
|
|
711
|
+
class UpdateProfileResponse(BaseModel):
|
|
712
|
+
"""Default Response"""
|
|
713
|
+
|
|
714
|
+
success: bool
|
|
715
|
+
profile: UpdateProfileProfile
|
|
716
|
+
|
|
717
|
+
|
|
718
|
+
class ListAppsPlatform(str, Enum):
|
|
719
|
+
TWITTER = "twitter"
|
|
720
|
+
INSTAGRAM = "instagram"
|
|
721
|
+
YOUTUBE = "youtube"
|
|
722
|
+
TIKTOK = "tiktok"
|
|
723
|
+
PINTEREST = "pinterest"
|
|
724
|
+
LINKEDIN = "linkedin"
|
|
725
|
+
BLUESKY = "bluesky"
|
|
726
|
+
FACEBOOK = "facebook"
|
|
727
|
+
THREADS = "threads"
|
|
728
|
+
GOOGLEBUSINESS = "googlebusiness"
|
|
729
|
+
|
|
730
|
+
|
|
731
|
+
class ListAppsQuery(BaseModel):
|
|
732
|
+
platform: Optional[ListAppsPlatform] = None
|
|
733
|
+
page: Optional[Annotated[int, Field(ge=1)]] = 1
|
|
734
|
+
limit: Optional[Annotated[int, Field(ge=1, le=100)]] = 50
|
|
735
|
+
name: Optional[Annotated[str, Field(min_length=1, max_length=200)]] = Field(default=None, description="Case-insensitive substring match on app name")
|
|
736
|
+
|
|
737
|
+
|
|
738
|
+
class ListAppsAppsPlatform(str, Enum):
|
|
739
|
+
TWITTER = "twitter"
|
|
740
|
+
INSTAGRAM = "instagram"
|
|
741
|
+
YOUTUBE = "youtube"
|
|
742
|
+
TIKTOK = "tiktok"
|
|
743
|
+
PINTEREST = "pinterest"
|
|
744
|
+
LINKEDIN = "linkedin"
|
|
745
|
+
BLUESKY = "bluesky"
|
|
746
|
+
FACEBOOK = "facebook"
|
|
747
|
+
THREADS = "threads"
|
|
748
|
+
GOOGLEBUSINESS = "googlebusiness"
|
|
749
|
+
|
|
750
|
+
|
|
751
|
+
class ListAppsApps(BaseModel):
|
|
752
|
+
id: str = Field(..., description="Pass this as appId when connecting")
|
|
753
|
+
platform: ListAppsAppsPlatform
|
|
754
|
+
name: str
|
|
755
|
+
image_url: Optional[str] = Field(default=None, alias="imageUrl")
|
|
756
|
+
client_id: str = Field(..., alias="clientId", description="The OAuth app client id. The client secret is never returned.")
|
|
757
|
+
integration_count: Annotated[int, Field(ge=0)] = Field(..., alias="integrationCount", description="Number of active integrations connected under this app")
|
|
758
|
+
created_at: datetime = Field(..., alias="createdAt")
|
|
759
|
+
updated_at: datetime = Field(..., alias="updatedAt")
|
|
760
|
+
|
|
761
|
+
|
|
762
|
+
class ListAppsResponse(BaseModel):
|
|
763
|
+
"""Default Response"""
|
|
764
|
+
|
|
765
|
+
success: bool
|
|
766
|
+
total: Annotated[int, Field(ge=0)]
|
|
767
|
+
page: Annotated[int, Field(ge=1)]
|
|
768
|
+
limit: Annotated[int, Field(ge=1)]
|
|
769
|
+
apps: list[ListAppsApps]
|
|
770
|
+
|
|
771
|
+
|
|
772
|
+
class CreateAppPlatform(str, Enum):
|
|
773
|
+
TWITTER = "twitter"
|
|
774
|
+
INSTAGRAM = "instagram"
|
|
775
|
+
YOUTUBE = "youtube"
|
|
776
|
+
TIKTOK = "tiktok"
|
|
777
|
+
PINTEREST = "pinterest"
|
|
778
|
+
LINKEDIN = "linkedin"
|
|
779
|
+
BLUESKY = "bluesky"
|
|
780
|
+
FACEBOOK = "facebook"
|
|
781
|
+
THREADS = "threads"
|
|
782
|
+
GOOGLEBUSINESS = "googlebusiness"
|
|
783
|
+
|
|
784
|
+
|
|
785
|
+
class CreateAppBody(BaseModel):
|
|
786
|
+
platform: CreateAppPlatform
|
|
787
|
+
name: Annotated[str, Field(min_length=1, max_length=200)] = Field(..., description='A label for this app (e.g. "Acme Twitter OAuth App")')
|
|
788
|
+
client_id: Annotated[str, Field(min_length=1)] = Field(..., alias="clientId", description="The client id of your OAuth app for this platform")
|
|
789
|
+
client_secret: Annotated[str, Field(min_length=1)] = Field(..., alias="clientSecret", description="The client secret of your OAuth app. Stored encrypted.")
|
|
790
|
+
image_url: Optional[AnyUrl] = Field(default=None, alias="imageUrl", description="Optional icon URL for the app")
|
|
791
|
+
|
|
792
|
+
|
|
793
|
+
class CreateAppAppPlatform(str, Enum):
|
|
794
|
+
TWITTER = "twitter"
|
|
795
|
+
INSTAGRAM = "instagram"
|
|
796
|
+
YOUTUBE = "youtube"
|
|
797
|
+
TIKTOK = "tiktok"
|
|
798
|
+
PINTEREST = "pinterest"
|
|
799
|
+
LINKEDIN = "linkedin"
|
|
800
|
+
BLUESKY = "bluesky"
|
|
801
|
+
FACEBOOK = "facebook"
|
|
802
|
+
THREADS = "threads"
|
|
803
|
+
GOOGLEBUSINESS = "googlebusiness"
|
|
804
|
+
|
|
805
|
+
|
|
806
|
+
class CreateAppApp(BaseModel):
|
|
807
|
+
id: str = Field(..., description="Pass this as appId when connecting")
|
|
808
|
+
platform: CreateAppAppPlatform
|
|
809
|
+
name: str
|
|
810
|
+
image_url: Optional[str] = Field(default=None, alias="imageUrl")
|
|
811
|
+
client_id: str = Field(..., alias="clientId", description="The OAuth app client id. The client secret is never returned.")
|
|
812
|
+
integration_count: Annotated[int, Field(ge=0)] = Field(..., alias="integrationCount", description="Number of active integrations connected under this app")
|
|
813
|
+
created_at: datetime = Field(..., alias="createdAt")
|
|
814
|
+
updated_at: datetime = Field(..., alias="updatedAt")
|
|
815
|
+
|
|
816
|
+
|
|
817
|
+
class CreateAppResponse(BaseModel):
|
|
818
|
+
"""Default Response"""
|
|
819
|
+
|
|
820
|
+
success: bool
|
|
821
|
+
app: CreateAppApp
|
|
822
|
+
|
|
823
|
+
|
|
824
|
+
class DeleteAppPath(BaseModel):
|
|
825
|
+
id: str = Field(..., description="OAuth app ID")
|
|
826
|
+
|
|
827
|
+
|
|
828
|
+
class DeleteAppResponse(BaseModel):
|
|
829
|
+
"""Default Response"""
|
|
830
|
+
|
|
831
|
+
success: bool
|
|
832
|
+
message: str
|
|
833
|
+
|
|
834
|
+
|
|
835
|
+
class GetAppPath(BaseModel):
|
|
836
|
+
id: str = Field(..., description="OAuth app ID")
|
|
837
|
+
|
|
838
|
+
|
|
839
|
+
class GetAppAppPlatform(str, Enum):
|
|
840
|
+
TWITTER = "twitter"
|
|
841
|
+
INSTAGRAM = "instagram"
|
|
842
|
+
YOUTUBE = "youtube"
|
|
843
|
+
TIKTOK = "tiktok"
|
|
844
|
+
PINTEREST = "pinterest"
|
|
845
|
+
LINKEDIN = "linkedin"
|
|
846
|
+
BLUESKY = "bluesky"
|
|
847
|
+
FACEBOOK = "facebook"
|
|
848
|
+
THREADS = "threads"
|
|
849
|
+
GOOGLEBUSINESS = "googlebusiness"
|
|
850
|
+
|
|
851
|
+
|
|
852
|
+
class GetAppApp(BaseModel):
|
|
853
|
+
id: str = Field(..., description="Pass this as appId when connecting")
|
|
854
|
+
platform: GetAppAppPlatform
|
|
855
|
+
name: str
|
|
856
|
+
image_url: Optional[str] = Field(default=None, alias="imageUrl")
|
|
857
|
+
client_id: str = Field(..., alias="clientId", description="The OAuth app client id. The client secret is never returned.")
|
|
858
|
+
integration_count: Annotated[int, Field(ge=0)] = Field(..., alias="integrationCount", description="Number of active integrations connected under this app")
|
|
859
|
+
created_at: datetime = Field(..., alias="createdAt")
|
|
860
|
+
updated_at: datetime = Field(..., alias="updatedAt")
|
|
861
|
+
|
|
862
|
+
|
|
863
|
+
class GetAppResponse(BaseModel):
|
|
864
|
+
"""Default Response"""
|
|
865
|
+
|
|
866
|
+
success: bool
|
|
867
|
+
app: GetAppApp
|
|
868
|
+
|
|
869
|
+
|
|
870
|
+
class UpdateAppBody(BaseModel):
|
|
871
|
+
model_config = ConfigDict(populate_by_name=True, extra="forbid")
|
|
872
|
+
name: Optional[Annotated[str, Field(min_length=1, max_length=200)]] = None
|
|
873
|
+
image_url: Optional[str] = Field(default=None, alias="imageUrl")
|
|
874
|
+
client_secret: Optional[Annotated[str, Field(min_length=1)]] = Field(default=None, alias="clientSecret", description="Rotate the stored client secret. The clientId stays the same so existing tokens keep working — to switch to a different app, create a new OAuth app and reconnect.")
|
|
875
|
+
|
|
876
|
+
|
|
877
|
+
class UpdateAppPath(BaseModel):
|
|
878
|
+
id: str = Field(..., description="OAuth app ID")
|
|
879
|
+
|
|
880
|
+
|
|
881
|
+
class UpdateAppAppPlatform(str, Enum):
|
|
882
|
+
TWITTER = "twitter"
|
|
883
|
+
INSTAGRAM = "instagram"
|
|
884
|
+
YOUTUBE = "youtube"
|
|
885
|
+
TIKTOK = "tiktok"
|
|
886
|
+
PINTEREST = "pinterest"
|
|
887
|
+
LINKEDIN = "linkedin"
|
|
888
|
+
BLUESKY = "bluesky"
|
|
889
|
+
FACEBOOK = "facebook"
|
|
890
|
+
THREADS = "threads"
|
|
891
|
+
GOOGLEBUSINESS = "googlebusiness"
|
|
892
|
+
|
|
893
|
+
|
|
894
|
+
class UpdateAppApp(BaseModel):
|
|
895
|
+
id: str = Field(..., description="Pass this as appId when connecting")
|
|
896
|
+
platform: UpdateAppAppPlatform
|
|
897
|
+
name: str
|
|
898
|
+
image_url: Optional[str] = Field(default=None, alias="imageUrl")
|
|
899
|
+
client_id: str = Field(..., alias="clientId", description="The OAuth app client id. The client secret is never returned.")
|
|
900
|
+
integration_count: Annotated[int, Field(ge=0)] = Field(..., alias="integrationCount", description="Number of active integrations connected under this app")
|
|
901
|
+
created_at: datetime = Field(..., alias="createdAt")
|
|
902
|
+
updated_at: datetime = Field(..., alias="updatedAt")
|
|
903
|
+
|
|
904
|
+
|
|
905
|
+
class UpdateAppResponse(BaseModel):
|
|
906
|
+
"""Default Response"""
|
|
907
|
+
|
|
908
|
+
success: bool
|
|
909
|
+
app: UpdateAppApp
|
|
910
|
+
|
|
911
|
+
|
|
912
|
+
class TestNotificationChannel(str, Enum):
|
|
913
|
+
WEBHOOK = "webhook"
|
|
914
|
+
EMAIL = "email"
|
|
915
|
+
|
|
916
|
+
|
|
917
|
+
class TestNotificationWebhook(BaseModel):
|
|
918
|
+
model_config = ConfigDict(extra="forbid")
|
|
919
|
+
url: AnyUrl = Field(..., description="HTTPS endpoint that receives PostPeer JSON payloads")
|
|
920
|
+
|
|
921
|
+
|
|
922
|
+
class TestNotificationEmail(BaseModel):
|
|
923
|
+
model_config = ConfigDict(extra="forbid")
|
|
924
|
+
recipients: Annotated[list[EmailStr], Field(min_length=1, max_length=10)]
|
|
925
|
+
|
|
926
|
+
|
|
927
|
+
class TestNotificationBody(BaseModel):
|
|
928
|
+
model_config = ConfigDict(populate_by_name=True, extra="forbid")
|
|
929
|
+
channel: TestNotificationChannel
|
|
930
|
+
profile_id: Optional[str] = Field(default=None, alias="profileId")
|
|
931
|
+
webhook: Optional[TestNotificationWebhook] = None
|
|
932
|
+
email: Optional[TestNotificationEmail] = None
|
|
933
|
+
|
|
934
|
+
|
|
935
|
+
class TestNotificationResponse(BaseModel):
|
|
936
|
+
"""Default Response"""
|
|
937
|
+
|
|
938
|
+
success: bool
|
|
939
|
+
message: str
|
|
940
|
+
|
|
941
|
+
|
|
942
|
+
class ListNotificationsNotificationsChannel(str, Enum):
|
|
943
|
+
WEBHOOK = "webhook"
|
|
944
|
+
EMAIL = "email"
|
|
945
|
+
|
|
946
|
+
|
|
947
|
+
class ListNotificationsNotificationsEventTypes(str, Enum):
|
|
948
|
+
POST_SCHEDULED = "post.scheduled"
|
|
949
|
+
POST_PUBLISHED = "post.published"
|
|
950
|
+
POST_PARTIAL = "post.partial"
|
|
951
|
+
POST_FAILED = "post.failed"
|
|
952
|
+
|
|
953
|
+
|
|
954
|
+
class ListNotificationsNotificationsWebhook(BaseModel):
|
|
955
|
+
model_config = ConfigDict(extra="forbid")
|
|
956
|
+
url: AnyUrl
|
|
957
|
+
secret: str = Field(..., description="Webhook signing secret (masked in list responses)")
|
|
958
|
+
|
|
959
|
+
|
|
960
|
+
class ListNotificationsNotificationsEmail(BaseModel):
|
|
961
|
+
model_config = ConfigDict(extra="forbid")
|
|
962
|
+
recipients: Annotated[list[EmailStr], Field(min_length=1, max_length=10)]
|
|
963
|
+
|
|
964
|
+
|
|
965
|
+
class ListNotificationsNotifications(BaseModel):
|
|
966
|
+
model_config = ConfigDict(populate_by_name=True, extra="forbid")
|
|
967
|
+
id: str
|
|
968
|
+
channel: ListNotificationsNotificationsChannel
|
|
969
|
+
profile_id: Optional[str] = Field(default=None, alias="profileId")
|
|
970
|
+
event_types: list[ListNotificationsNotificationsEventTypes] = Field(..., alias="eventTypes")
|
|
971
|
+
only_scheduled_posts: bool = Field(..., alias="onlyScheduledPosts")
|
|
972
|
+
enabled: bool
|
|
973
|
+
webhook: Optional[ListNotificationsNotificationsWebhook] = None
|
|
974
|
+
email: Optional[ListNotificationsNotificationsEmail] = None
|
|
975
|
+
last_test_at: Optional[datetime] = Field(default=None, alias="lastTestAt")
|
|
976
|
+
last_test_status: Optional[str] = Field(default=None, alias="lastTestStatus")
|
|
977
|
+
created_at: datetime = Field(..., alias="createdAt")
|
|
978
|
+
updated_at: datetime = Field(..., alias="updatedAt")
|
|
979
|
+
|
|
980
|
+
|
|
981
|
+
class ListNotificationsResponse(BaseModel):
|
|
982
|
+
"""Default Response"""
|
|
983
|
+
|
|
984
|
+
success: bool
|
|
985
|
+
notifications: list[ListNotificationsNotifications]
|
|
986
|
+
|
|
987
|
+
|
|
988
|
+
class CreateNotificationChannel(str, Enum):
|
|
989
|
+
WEBHOOK = "webhook"
|
|
990
|
+
EMAIL = "email"
|
|
991
|
+
|
|
992
|
+
|
|
993
|
+
class CreateNotificationEventTypes(str, Enum):
|
|
994
|
+
POST_SCHEDULED = "post.scheduled"
|
|
995
|
+
POST_PUBLISHED = "post.published"
|
|
996
|
+
POST_PARTIAL = "post.partial"
|
|
997
|
+
POST_FAILED = "post.failed"
|
|
998
|
+
|
|
999
|
+
|
|
1000
|
+
class CreateNotificationWebhook(BaseModel):
|
|
1001
|
+
model_config = ConfigDict(extra="forbid")
|
|
1002
|
+
url: AnyUrl = Field(..., description="HTTPS endpoint that receives PostPeer JSON payloads")
|
|
1003
|
+
|
|
1004
|
+
|
|
1005
|
+
class CreateNotificationEmail(BaseModel):
|
|
1006
|
+
model_config = ConfigDict(extra="forbid")
|
|
1007
|
+
recipients: Annotated[list[EmailStr], Field(min_length=1, max_length=10)]
|
|
1008
|
+
|
|
1009
|
+
|
|
1010
|
+
class CreateNotificationBody(BaseModel):
|
|
1011
|
+
model_config = ConfigDict(populate_by_name=True, extra="forbid")
|
|
1012
|
+
channel: CreateNotificationChannel
|
|
1013
|
+
profile_id: Optional[str] = Field(default=None, alias="profileId")
|
|
1014
|
+
event_types: Annotated[list[CreateNotificationEventTypes], Field(min_length=1)] = Field(..., alias="eventTypes")
|
|
1015
|
+
only_scheduled_posts: Optional[bool] = Field(default=False, alias="onlyScheduledPosts", description="When true, deliver matching notifications only for posts that were scheduled.")
|
|
1016
|
+
enabled: Optional[bool] = True
|
|
1017
|
+
webhook: Optional[CreateNotificationWebhook] = None
|
|
1018
|
+
email: Optional[CreateNotificationEmail] = None
|
|
1019
|
+
|
|
1020
|
+
|
|
1021
|
+
class CreateNotificationNotificationChannel(str, Enum):
|
|
1022
|
+
WEBHOOK = "webhook"
|
|
1023
|
+
EMAIL = "email"
|
|
1024
|
+
|
|
1025
|
+
|
|
1026
|
+
class CreateNotificationNotificationEventTypes(str, Enum):
|
|
1027
|
+
POST_SCHEDULED = "post.scheduled"
|
|
1028
|
+
POST_PUBLISHED = "post.published"
|
|
1029
|
+
POST_PARTIAL = "post.partial"
|
|
1030
|
+
POST_FAILED = "post.failed"
|
|
1031
|
+
|
|
1032
|
+
|
|
1033
|
+
class CreateNotificationNotificationWebhook(BaseModel):
|
|
1034
|
+
model_config = ConfigDict(extra="forbid")
|
|
1035
|
+
url: AnyUrl
|
|
1036
|
+
secret: str = Field(..., description="Webhook signing secret (masked in list responses)")
|
|
1037
|
+
|
|
1038
|
+
|
|
1039
|
+
class CreateNotificationNotificationEmail(BaseModel):
|
|
1040
|
+
model_config = ConfigDict(extra="forbid")
|
|
1041
|
+
recipients: Annotated[list[EmailStr], Field(min_length=1, max_length=10)]
|
|
1042
|
+
|
|
1043
|
+
|
|
1044
|
+
class CreateNotificationNotification(BaseModel):
|
|
1045
|
+
model_config = ConfigDict(populate_by_name=True, extra="forbid")
|
|
1046
|
+
id: str
|
|
1047
|
+
channel: CreateNotificationNotificationChannel
|
|
1048
|
+
profile_id: Optional[str] = Field(default=None, alias="profileId")
|
|
1049
|
+
event_types: list[CreateNotificationNotificationEventTypes] = Field(..., alias="eventTypes")
|
|
1050
|
+
only_scheduled_posts: bool = Field(..., alias="onlyScheduledPosts")
|
|
1051
|
+
enabled: bool
|
|
1052
|
+
webhook: Optional[CreateNotificationNotificationWebhook] = None
|
|
1053
|
+
email: Optional[CreateNotificationNotificationEmail] = None
|
|
1054
|
+
last_test_at: Optional[datetime] = Field(default=None, alias="lastTestAt")
|
|
1055
|
+
last_test_status: Optional[str] = Field(default=None, alias="lastTestStatus")
|
|
1056
|
+
created_at: datetime = Field(..., alias="createdAt")
|
|
1057
|
+
updated_at: datetime = Field(..., alias="updatedAt")
|
|
1058
|
+
|
|
1059
|
+
|
|
1060
|
+
class CreateNotificationResponse(BaseModel):
|
|
1061
|
+
"""Default Response"""
|
|
1062
|
+
|
|
1063
|
+
success: bool
|
|
1064
|
+
notification: CreateNotificationNotification
|
|
1065
|
+
|
|
1066
|
+
|
|
1067
|
+
class DeleteNotificationPath(BaseModel):
|
|
1068
|
+
id: str = Field(..., description="Notification subscription ID")
|
|
1069
|
+
|
|
1070
|
+
|
|
1071
|
+
class DeleteNotificationResponse(BaseModel):
|
|
1072
|
+
"""Default Response"""
|
|
1073
|
+
|
|
1074
|
+
success: bool
|
|
1075
|
+
message: str
|
|
1076
|
+
|
|
1077
|
+
|
|
1078
|
+
class GetNotificationPath(BaseModel):
|
|
1079
|
+
id: str = Field(..., description="Notification subscription ID")
|
|
1080
|
+
|
|
1081
|
+
|
|
1082
|
+
class GetNotificationNotificationChannel(str, Enum):
|
|
1083
|
+
WEBHOOK = "webhook"
|
|
1084
|
+
EMAIL = "email"
|
|
1085
|
+
|
|
1086
|
+
|
|
1087
|
+
class GetNotificationNotificationEventTypes(str, Enum):
|
|
1088
|
+
POST_SCHEDULED = "post.scheduled"
|
|
1089
|
+
POST_PUBLISHED = "post.published"
|
|
1090
|
+
POST_PARTIAL = "post.partial"
|
|
1091
|
+
POST_FAILED = "post.failed"
|
|
1092
|
+
|
|
1093
|
+
|
|
1094
|
+
class GetNotificationNotificationWebhook(BaseModel):
|
|
1095
|
+
model_config = ConfigDict(extra="forbid")
|
|
1096
|
+
url: AnyUrl
|
|
1097
|
+
secret: str = Field(..., description="Webhook signing secret (masked in list responses)")
|
|
1098
|
+
|
|
1099
|
+
|
|
1100
|
+
class GetNotificationNotificationEmail(BaseModel):
|
|
1101
|
+
model_config = ConfigDict(extra="forbid")
|
|
1102
|
+
recipients: Annotated[list[EmailStr], Field(min_length=1, max_length=10)]
|
|
1103
|
+
|
|
1104
|
+
|
|
1105
|
+
class GetNotificationNotification(BaseModel):
|
|
1106
|
+
model_config = ConfigDict(populate_by_name=True, extra="forbid")
|
|
1107
|
+
id: str
|
|
1108
|
+
channel: GetNotificationNotificationChannel
|
|
1109
|
+
profile_id: Optional[str] = Field(default=None, alias="profileId")
|
|
1110
|
+
event_types: list[GetNotificationNotificationEventTypes] = Field(..., alias="eventTypes")
|
|
1111
|
+
only_scheduled_posts: bool = Field(..., alias="onlyScheduledPosts")
|
|
1112
|
+
enabled: bool
|
|
1113
|
+
webhook: Optional[GetNotificationNotificationWebhook] = None
|
|
1114
|
+
email: Optional[GetNotificationNotificationEmail] = None
|
|
1115
|
+
last_test_at: Optional[datetime] = Field(default=None, alias="lastTestAt")
|
|
1116
|
+
last_test_status: Optional[str] = Field(default=None, alias="lastTestStatus")
|
|
1117
|
+
created_at: datetime = Field(..., alias="createdAt")
|
|
1118
|
+
updated_at: datetime = Field(..., alias="updatedAt")
|
|
1119
|
+
|
|
1120
|
+
|
|
1121
|
+
class GetNotificationResponse(BaseModel):
|
|
1122
|
+
"""Default Response"""
|
|
1123
|
+
|
|
1124
|
+
success: bool
|
|
1125
|
+
notification: GetNotificationNotification
|
|
1126
|
+
|
|
1127
|
+
|
|
1128
|
+
class UpdateNotificationEventTypes(str, Enum):
|
|
1129
|
+
POST_SCHEDULED = "post.scheduled"
|
|
1130
|
+
POST_PUBLISHED = "post.published"
|
|
1131
|
+
POST_PARTIAL = "post.partial"
|
|
1132
|
+
POST_FAILED = "post.failed"
|
|
1133
|
+
|
|
1134
|
+
|
|
1135
|
+
class UpdateNotificationWebhook(BaseModel):
|
|
1136
|
+
model_config = ConfigDict(extra="forbid")
|
|
1137
|
+
url: AnyUrl = Field(..., description="HTTPS endpoint that receives PostPeer JSON payloads")
|
|
1138
|
+
|
|
1139
|
+
|
|
1140
|
+
class UpdateNotificationEmail(BaseModel):
|
|
1141
|
+
model_config = ConfigDict(extra="forbid")
|
|
1142
|
+
recipients: Annotated[list[EmailStr], Field(min_length=1, max_length=10)]
|
|
1143
|
+
|
|
1144
|
+
|
|
1145
|
+
class UpdateNotificationBody(BaseModel):
|
|
1146
|
+
model_config = ConfigDict(populate_by_name=True, extra="forbid")
|
|
1147
|
+
profile_id: Optional[str] = Field(default=None, alias="profileId")
|
|
1148
|
+
event_types: Optional[Annotated[list[UpdateNotificationEventTypes], Field(min_length=1)]] = Field(default=None, alias="eventTypes")
|
|
1149
|
+
only_scheduled_posts: Optional[bool] = Field(default=None, alias="onlyScheduledPosts", description="When true, deliver matching notifications only for posts that were scheduled.")
|
|
1150
|
+
enabled: Optional[bool] = None
|
|
1151
|
+
webhook: Optional[UpdateNotificationWebhook] = None
|
|
1152
|
+
email: Optional[UpdateNotificationEmail] = None
|
|
1153
|
+
|
|
1154
|
+
|
|
1155
|
+
class UpdateNotificationPath(BaseModel):
|
|
1156
|
+
id: str = Field(..., description="Notification subscription ID")
|
|
1157
|
+
|
|
1158
|
+
|
|
1159
|
+
class UpdateNotificationNotificationChannel(str, Enum):
|
|
1160
|
+
WEBHOOK = "webhook"
|
|
1161
|
+
EMAIL = "email"
|
|
1162
|
+
|
|
1163
|
+
|
|
1164
|
+
class UpdateNotificationNotificationEventTypes(str, Enum):
|
|
1165
|
+
POST_SCHEDULED = "post.scheduled"
|
|
1166
|
+
POST_PUBLISHED = "post.published"
|
|
1167
|
+
POST_PARTIAL = "post.partial"
|
|
1168
|
+
POST_FAILED = "post.failed"
|
|
1169
|
+
|
|
1170
|
+
|
|
1171
|
+
class UpdateNotificationNotificationWebhook(BaseModel):
|
|
1172
|
+
model_config = ConfigDict(extra="forbid")
|
|
1173
|
+
url: AnyUrl
|
|
1174
|
+
secret: str = Field(..., description="Webhook signing secret (masked in list responses)")
|
|
1175
|
+
|
|
1176
|
+
|
|
1177
|
+
class UpdateNotificationNotificationEmail(BaseModel):
|
|
1178
|
+
model_config = ConfigDict(extra="forbid")
|
|
1179
|
+
recipients: Annotated[list[EmailStr], Field(min_length=1, max_length=10)]
|
|
1180
|
+
|
|
1181
|
+
|
|
1182
|
+
class UpdateNotificationNotification(BaseModel):
|
|
1183
|
+
model_config = ConfigDict(populate_by_name=True, extra="forbid")
|
|
1184
|
+
id: str
|
|
1185
|
+
channel: UpdateNotificationNotificationChannel
|
|
1186
|
+
profile_id: Optional[str] = Field(default=None, alias="profileId")
|
|
1187
|
+
event_types: list[UpdateNotificationNotificationEventTypes] = Field(..., alias="eventTypes")
|
|
1188
|
+
only_scheduled_posts: bool = Field(..., alias="onlyScheduledPosts")
|
|
1189
|
+
enabled: bool
|
|
1190
|
+
webhook: Optional[UpdateNotificationNotificationWebhook] = None
|
|
1191
|
+
email: Optional[UpdateNotificationNotificationEmail] = None
|
|
1192
|
+
last_test_at: Optional[datetime] = Field(default=None, alias="lastTestAt")
|
|
1193
|
+
last_test_status: Optional[str] = Field(default=None, alias="lastTestStatus")
|
|
1194
|
+
created_at: datetime = Field(..., alias="createdAt")
|
|
1195
|
+
updated_at: datetime = Field(..., alias="updatedAt")
|
|
1196
|
+
|
|
1197
|
+
|
|
1198
|
+
class UpdateNotificationResponse(BaseModel):
|
|
1199
|
+
"""Default Response"""
|
|
1200
|
+
|
|
1201
|
+
success: bool
|
|
1202
|
+
notification: UpdateNotificationNotification
|
|
1203
|
+
|
|
1204
|
+
|
|
1205
|
+
class ListPlatformsPlatformsName(str, Enum):
|
|
1206
|
+
TWITTER = "twitter"
|
|
1207
|
+
INSTAGRAM = "instagram"
|
|
1208
|
+
YOUTUBE = "youtube"
|
|
1209
|
+
TIKTOK = "tiktok"
|
|
1210
|
+
PINTEREST = "pinterest"
|
|
1211
|
+
LINKEDIN = "linkedin"
|
|
1212
|
+
BLUESKY = "bluesky"
|
|
1213
|
+
FACEBOOK = "facebook"
|
|
1214
|
+
THREADS = "threads"
|
|
1215
|
+
GOOGLEBUSINESS = "googlebusiness"
|
|
1216
|
+
|
|
1217
|
+
|
|
1218
|
+
class ListPlatformsPlatformsStatus(str, Enum):
|
|
1219
|
+
PROD = "prod"
|
|
1220
|
+
BETA = "beta"
|
|
1221
|
+
DEV = "dev"
|
|
1222
|
+
|
|
1223
|
+
|
|
1224
|
+
class ListPlatformsPlatforms(BaseModel):
|
|
1225
|
+
name: ListPlatformsPlatformsName
|
|
1226
|
+
status: ListPlatformsPlatformsStatus
|
|
1227
|
+
|
|
1228
|
+
|
|
1229
|
+
class ListPlatformsResponse(BaseModel):
|
|
1230
|
+
"""Default Response"""
|
|
1231
|
+
|
|
1232
|
+
platforms: list[ListPlatformsPlatforms]
|
|
1233
|
+
|
|
1234
|
+
|
|
1235
|
+
class ListPostsStatus(str, Enum):
|
|
1236
|
+
DRAFT = "draft"
|
|
1237
|
+
PENDING = "pending"
|
|
1238
|
+
SCHEDULED = "scheduled"
|
|
1239
|
+
PUBLISHING = "publishing"
|
|
1240
|
+
PUBLISHED = "published"
|
|
1241
|
+
FAILED = "failed"
|
|
1242
|
+
PARTIAL = "partial"
|
|
1243
|
+
|
|
1244
|
+
|
|
1245
|
+
class ListPostsPlatform(str, Enum):
|
|
1246
|
+
TWITTER = "twitter"
|
|
1247
|
+
INSTAGRAM = "instagram"
|
|
1248
|
+
YOUTUBE = "youtube"
|
|
1249
|
+
TIKTOK = "tiktok"
|
|
1250
|
+
PINTEREST = "pinterest"
|
|
1251
|
+
LINKEDIN = "linkedin"
|
|
1252
|
+
BLUESKY = "bluesky"
|
|
1253
|
+
FACEBOOK = "facebook"
|
|
1254
|
+
THREADS = "threads"
|
|
1255
|
+
GOOGLEBUSINESS = "googlebusiness"
|
|
1256
|
+
|
|
1257
|
+
|
|
1258
|
+
class ListPostsQuery(BaseModel):
|
|
1259
|
+
status: Optional[ListPostsStatus] = None
|
|
1260
|
+
platform: Optional[list[ListPostsPlatform]] = Field(default=None, description="Filter by platform (repeatable — OR logic)")
|
|
1261
|
+
profile_id: Optional[str] = Field(default=None, alias="profileId", description='Filter to posts targeting an integration bound to this profile. Pass "null" (literal string) to filter to posts whose integrations have no profile.')
|
|
1262
|
+
created_after: Optional[datetime] = Field(default=None, alias="createdAfter", description="ISO 8601 lower bound on createdAt")
|
|
1263
|
+
created_before: Optional[datetime] = Field(default=None, alias="createdBefore", description="ISO 8601 upper bound on createdAt")
|
|
1264
|
+
scheduled_after: Optional[datetime] = Field(default=None, alias="scheduledAfter", description="ISO 8601 lower bound on scheduledFor")
|
|
1265
|
+
scheduled_before: Optional[datetime] = Field(default=None, alias="scheduledBefore", description="ISO 8601 upper bound on scheduledFor")
|
|
1266
|
+
limit: Optional[Annotated[int, Field(ge=1, le=100)]] = Field(default=20, description="Page size (max 100)")
|
|
1267
|
+
offset: Optional[Annotated[int, Field(ge=0)]] = Field(default=0, description="Number of posts to skip")
|
|
1268
|
+
sort: Optional[SortOrder] = None
|
|
1269
|
+
|
|
1270
|
+
|
|
1271
|
+
class ListPostsPostsStatus(str, Enum):
|
|
1272
|
+
DRAFT = "draft"
|
|
1273
|
+
PENDING = "pending"
|
|
1274
|
+
SCHEDULED = "scheduled"
|
|
1275
|
+
PUBLISHING = "publishing"
|
|
1276
|
+
PUBLISHED = "published"
|
|
1277
|
+
FAILED = "failed"
|
|
1278
|
+
PARTIAL = "partial"
|
|
1279
|
+
|
|
1280
|
+
|
|
1281
|
+
class ListPostsPostsMediaItemsType(str, Enum):
|
|
1282
|
+
IMAGE = "image"
|
|
1283
|
+
VIDEO = "video"
|
|
1284
|
+
GIF = "gif"
|
|
1285
|
+
|
|
1286
|
+
|
|
1287
|
+
class ListPostsPostsMediaItems(BaseModel):
|
|
1288
|
+
type: ListPostsPostsMediaItemsType
|
|
1289
|
+
url: str
|
|
1290
|
+
filename: str
|
|
1291
|
+
size: float
|
|
1292
|
+
mime_type: str = Field(..., alias="mimeType")
|
|
1293
|
+
|
|
1294
|
+
|
|
1295
|
+
class ListPostsPostsPlatformsPlatform(str, Enum):
|
|
1296
|
+
TWITTER = "twitter"
|
|
1297
|
+
INSTAGRAM = "instagram"
|
|
1298
|
+
YOUTUBE = "youtube"
|
|
1299
|
+
TIKTOK = "tiktok"
|
|
1300
|
+
PINTEREST = "pinterest"
|
|
1301
|
+
LINKEDIN = "linkedin"
|
|
1302
|
+
BLUESKY = "bluesky"
|
|
1303
|
+
FACEBOOK = "facebook"
|
|
1304
|
+
THREADS = "threads"
|
|
1305
|
+
GOOGLEBUSINESS = "googlebusiness"
|
|
1306
|
+
|
|
1307
|
+
|
|
1308
|
+
class ListPostsPostsPlatformsStatus(str, Enum):
|
|
1309
|
+
DRAFT = "draft"
|
|
1310
|
+
PENDING = "pending"
|
|
1311
|
+
SCHEDULED = "scheduled"
|
|
1312
|
+
PUBLISHING = "publishing"
|
|
1313
|
+
PUBLISHED = "published"
|
|
1314
|
+
FAILED = "failed"
|
|
1315
|
+
PARTIAL = "partial"
|
|
1316
|
+
|
|
1317
|
+
|
|
1318
|
+
class ListPostsPostsPlatforms(BaseModel):
|
|
1319
|
+
platform: ListPostsPostsPlatformsPlatform
|
|
1320
|
+
status: ListPostsPostsPlatformsStatus
|
|
1321
|
+
content: Optional[str] = Field(default=None, description="Per-platform text override that was used for this platform. Null when the top-level `content` was used.")
|
|
1322
|
+
platform_post_id: Optional[str] = Field(default=None, alias="platformPostId")
|
|
1323
|
+
platform_post_url: Optional[str] = Field(default=None, alias="platformPostUrl", description="Direct URL to the published post")
|
|
1324
|
+
published_at: Optional[datetime] = Field(default=None, alias="publishedAt")
|
|
1325
|
+
error_message: Optional[str] = Field(default=None, alias="errorMessage")
|
|
1326
|
+
warning_message: Optional[str] = Field(default=None, alias="warningMessage")
|
|
1327
|
+
|
|
1328
|
+
|
|
1329
|
+
class ListPostsPosts(BaseModel):
|
|
1330
|
+
post_id: str = Field(..., alias="postId", description="MongoDB ObjectId of the Post document")
|
|
1331
|
+
content: str
|
|
1332
|
+
status: ListPostsPostsStatus
|
|
1333
|
+
scheduled_for: Optional[datetime] = Field(default=None, alias="scheduledFor", description="ISO 8601 scheduled datetime")
|
|
1334
|
+
timezone: str
|
|
1335
|
+
media_items: list[ListPostsPostsMediaItems] = Field(..., alias="mediaItems")
|
|
1336
|
+
platforms: list[ListPostsPostsPlatforms]
|
|
1337
|
+
crossposting_enabled: bool = Field(..., alias="crosspostingEnabled")
|
|
1338
|
+
raw_request_body: dict[str, Any] = Field(..., alias="rawRequestBody")
|
|
1339
|
+
created_at: datetime = Field(..., alias="createdAt")
|
|
1340
|
+
updated_at: datetime = Field(..., alias="updatedAt")
|
|
1341
|
+
|
|
1342
|
+
|
|
1343
|
+
class ListPostsResponse(BaseModel):
|
|
1344
|
+
"""Default Response"""
|
|
1345
|
+
|
|
1346
|
+
success: bool
|
|
1347
|
+
total: Annotated[int, Field(ge=0)] = Field(..., description="Total matched posts across all pages")
|
|
1348
|
+
posts: list[ListPostsPosts]
|
|
1349
|
+
|
|
1350
|
+
|
|
1351
|
+
class CreatePostMediaItemsType(str, Enum):
|
|
1352
|
+
IMAGE = "image"
|
|
1353
|
+
VIDEO = "video"
|
|
1354
|
+
GIF = "gif"
|
|
1355
|
+
DOCUMENT = "document"
|
|
1356
|
+
|
|
1357
|
+
|
|
1358
|
+
class CreatePostMediaItems(BaseModel):
|
|
1359
|
+
model_config = ConfigDict(extra="forbid")
|
|
1360
|
+
type: CreatePostMediaItemsType
|
|
1361
|
+
url: AnyUrl
|
|
1362
|
+
thumbnail: Optional[AnyUrl] = Field(default=None, description="Thumbnail image URL for video items. Supported on YouTube regular videos (not Shorts). JPEG, PNG, or GIF, max 2 MB, min 640 px wide.")
|
|
1363
|
+
|
|
1364
|
+
|
|
1365
|
+
class CreatePostPlatformsPlatform(str, Enum):
|
|
1366
|
+
TWITTER = "twitter"
|
|
1367
|
+
|
|
1368
|
+
|
|
1369
|
+
class CreatePostPlatforms(BaseModel):
|
|
1370
|
+
model_config = ConfigDict(populate_by_name=True, extra="forbid")
|
|
1371
|
+
platform: CreatePostPlatformsPlatform
|
|
1372
|
+
account_id: str = Field(..., alias="accountId", description="Integration._id — find yours via GET /connect/integrations")
|
|
1373
|
+
content: Optional[str] = Field(default=None, description="Optional per-platform text override. Use when you want to change the text for this platform because different platforms talk differently. When omitted, the top-level `content` is used.")
|
|
1374
|
+
platform_specific_data: Optional[TwitterConfigurations] = Field(default=None, alias="platformSpecificData")
|
|
1375
|
+
|
|
1376
|
+
|
|
1377
|
+
class CreatePostPlatformsPlatform_(str, Enum):
|
|
1378
|
+
INSTAGRAM = "instagram"
|
|
1379
|
+
|
|
1380
|
+
|
|
1381
|
+
class CreatePostPlatforms_(BaseModel):
|
|
1382
|
+
model_config = ConfigDict(populate_by_name=True, extra="forbid")
|
|
1383
|
+
platform: CreatePostPlatformsPlatform_
|
|
1384
|
+
account_id: str = Field(..., alias="accountId", description="Integration._id — find yours via GET /connect/integrations")
|
|
1385
|
+
content: Optional[str] = Field(default=None, description="Optional per-platform text override. Use when you want to change the text for this platform because different platforms talk differently. When omitted, the top-level `content` is used.")
|
|
1386
|
+
platform_specific_data: Optional[InstagramConfigurations] = Field(default=None, alias="platformSpecificData")
|
|
1387
|
+
|
|
1388
|
+
|
|
1389
|
+
class CreatePostPlatformsPlatform_2(str, Enum):
|
|
1390
|
+
YOUTUBE = "youtube"
|
|
1391
|
+
|
|
1392
|
+
|
|
1393
|
+
class CreatePostPlatforms_2(BaseModel):
|
|
1394
|
+
model_config = ConfigDict(populate_by_name=True, extra="forbid")
|
|
1395
|
+
platform: CreatePostPlatformsPlatform_2
|
|
1396
|
+
account_id: str = Field(..., alias="accountId", description="Integration._id — find yours via GET /connect/integrations")
|
|
1397
|
+
content: Optional[str] = Field(default=None, description="Optional per-platform text override. Use when you want to change the text for this platform because different platforms talk differently. When omitted, the top-level `content` is used.")
|
|
1398
|
+
platform_specific_data: Optional[YouTubeConfigurations] = Field(default=None, alias="platformSpecificData")
|
|
1399
|
+
|
|
1400
|
+
|
|
1401
|
+
class CreatePostPlatformsPlatform_3(str, Enum):
|
|
1402
|
+
TIKTOK = "tiktok"
|
|
1403
|
+
|
|
1404
|
+
|
|
1405
|
+
class CreatePostPlatforms_3(BaseModel):
|
|
1406
|
+
model_config = ConfigDict(populate_by_name=True, extra="forbid")
|
|
1407
|
+
platform: CreatePostPlatformsPlatform_3
|
|
1408
|
+
account_id: str = Field(..., alias="accountId", description="Integration._id — find yours via GET /connect/integrations")
|
|
1409
|
+
content: Optional[str] = Field(default=None, description="Optional per-platform text override. Use when you want to change the text for this platform because different platforms talk differently. When omitted, the top-level `content` is used.")
|
|
1410
|
+
platform_specific_data: Optional[TikTokConfigurations] = Field(default=None, alias="platformSpecificData")
|
|
1411
|
+
|
|
1412
|
+
|
|
1413
|
+
class CreatePostPlatformsPlatform_4(str, Enum):
|
|
1414
|
+
PINTEREST = "pinterest"
|
|
1415
|
+
|
|
1416
|
+
|
|
1417
|
+
class CreatePostPlatforms_4(BaseModel):
|
|
1418
|
+
model_config = ConfigDict(populate_by_name=True, extra="forbid")
|
|
1419
|
+
platform: CreatePostPlatformsPlatform_4
|
|
1420
|
+
account_id: str = Field(..., alias="accountId", description="Integration._id — find yours via GET /connect/integrations")
|
|
1421
|
+
content: Optional[str] = Field(default=None, description="Optional per-platform text override. Use when you want to change the text for this platform because different platforms talk differently. When omitted, the top-level `content` is used.")
|
|
1422
|
+
platform_specific_data: Optional[PinterestConfigurations] = Field(default=None, alias="platformSpecificData")
|
|
1423
|
+
|
|
1424
|
+
|
|
1425
|
+
class CreatePostPlatformsPlatform_5(str, Enum):
|
|
1426
|
+
LINKEDIN = "linkedin"
|
|
1427
|
+
|
|
1428
|
+
|
|
1429
|
+
class CreatePostPlatforms_5(BaseModel):
|
|
1430
|
+
model_config = ConfigDict(populate_by_name=True, extra="forbid")
|
|
1431
|
+
platform: CreatePostPlatformsPlatform_5
|
|
1432
|
+
account_id: str = Field(..., alias="accountId", description="Integration._id — find yours via GET /connect/integrations")
|
|
1433
|
+
content: Optional[str] = Field(default=None, description="Optional per-platform text override. Use when you want to change the text for this platform because different platforms talk differently. When omitted, the top-level `content` is used.")
|
|
1434
|
+
platform_specific_data: Optional[LinkedInConfigurations] = Field(default=None, alias="platformSpecificData")
|
|
1435
|
+
|
|
1436
|
+
|
|
1437
|
+
class CreatePostPlatformsPlatform_6(str, Enum):
|
|
1438
|
+
BLUESKY = "bluesky"
|
|
1439
|
+
|
|
1440
|
+
|
|
1441
|
+
class CreatePostPlatforms_6(BaseModel):
|
|
1442
|
+
model_config = ConfigDict(populate_by_name=True, extra="forbid")
|
|
1443
|
+
platform: CreatePostPlatformsPlatform_6
|
|
1444
|
+
account_id: str = Field(..., alias="accountId", description="Integration._id — find yours via GET /connect/integrations")
|
|
1445
|
+
content: Optional[str] = Field(default=None, description="Optional per-platform text override. Use when you want to change the text for this platform because different platforms talk differently. When omitted, the top-level `content` is used.")
|
|
1446
|
+
platform_specific_data: Optional[BlueskyConfigurations] = Field(default=None, alias="platformSpecificData")
|
|
1447
|
+
|
|
1448
|
+
|
|
1449
|
+
class CreatePostPlatformsPlatform_7(str, Enum):
|
|
1450
|
+
FACEBOOK = "facebook"
|
|
1451
|
+
|
|
1452
|
+
|
|
1453
|
+
class CreatePostPlatforms_7(BaseModel):
|
|
1454
|
+
model_config = ConfigDict(populate_by_name=True, extra="forbid")
|
|
1455
|
+
platform: CreatePostPlatformsPlatform_7
|
|
1456
|
+
account_id: str = Field(..., alias="accountId", description="Integration._id — find yours via GET /connect/integrations")
|
|
1457
|
+
content: Optional[str] = Field(default=None, description="Optional per-platform text override. Use when you want to change the text for this platform because different platforms talk differently. When omitted, the top-level `content` is used.")
|
|
1458
|
+
platform_specific_data: Optional[FacebookConfigurations] = Field(default=None, alias="platformSpecificData")
|
|
1459
|
+
|
|
1460
|
+
|
|
1461
|
+
class CreatePostPlatformsPlatform_8(str, Enum):
|
|
1462
|
+
THREADS = "threads"
|
|
1463
|
+
|
|
1464
|
+
|
|
1465
|
+
class CreatePostPlatforms_8(BaseModel):
|
|
1466
|
+
model_config = ConfigDict(populate_by_name=True, extra="forbid")
|
|
1467
|
+
platform: CreatePostPlatformsPlatform_8
|
|
1468
|
+
account_id: str = Field(..., alias="accountId", description="Integration._id — find yours via GET /connect/integrations")
|
|
1469
|
+
content: Optional[str] = Field(default=None, description="Optional per-platform text override. Use when you want to change the text for this platform because different platforms talk differently. When omitted, the top-level `content` is used.")
|
|
1470
|
+
platform_specific_data: Optional[ThreadsConfigurations] = Field(default=None, alias="platformSpecificData")
|
|
1471
|
+
|
|
1472
|
+
|
|
1473
|
+
class CreatePostPlatformsPlatform_9(str, Enum):
|
|
1474
|
+
GOOGLEBUSINESS = "googlebusiness"
|
|
1475
|
+
|
|
1476
|
+
|
|
1477
|
+
class CreatePostPlatforms_9(BaseModel):
|
|
1478
|
+
model_config = ConfigDict(populate_by_name=True, extra="forbid")
|
|
1479
|
+
platform: CreatePostPlatformsPlatform_9
|
|
1480
|
+
account_id: str = Field(..., alias="accountId", description="Integration._id — find yours via GET /connect/integrations")
|
|
1481
|
+
content: Optional[str] = Field(default=None, description="Optional per-platform text override. Use when you want to change the text for this platform because different platforms talk differently. When omitted, the top-level `content` is used.")
|
|
1482
|
+
platform_specific_data: Optional[GoogleBusinessConfigurations] = Field(default=None, alias="platformSpecificData")
|
|
1483
|
+
|
|
1484
|
+
|
|
1485
|
+
class CreatePostBody(BaseModel):
|
|
1486
|
+
model_config = ConfigDict(populate_by_name=True, extra="forbid")
|
|
1487
|
+
content: str = Field(..., description="Post text body")
|
|
1488
|
+
media_items: Optional[list[CreatePostMediaItems]] = Field(default=None, alias="mediaItems", description="Media attachments (images, videos, GIFs)")
|
|
1489
|
+
platforms: Annotated[list[Union[CreatePostPlatforms, CreatePostPlatforms_, CreatePostPlatforms_2, CreatePostPlatforms_3, CreatePostPlatforms_4, CreatePostPlatforms_5, CreatePostPlatforms_6, CreatePostPlatforms_7, CreatePostPlatforms_8, CreatePostPlatforms_9]], Field(min_length=1)] = Field(..., description="Target platform accounts to publish to")
|
|
1490
|
+
publish_now: Optional[bool] = Field(default=None, alias="publishNow", description="Publish immediately. Required when scheduledFor is omitted.")
|
|
1491
|
+
scheduled_for: Optional[datetime] = Field(default=None, alias="scheduledFor", description="ISO 8601 datetime to schedule the post for future publishing")
|
|
1492
|
+
timezone: Optional[str] = Field(default=None, description="IANA timezone for the scheduled time (e.g. America/New_York). Defaults to UTC.")
|
|
1493
|
+
|
|
1494
|
+
|
|
1495
|
+
class CreatePostStatus(str, Enum):
|
|
1496
|
+
DRAFT = "draft"
|
|
1497
|
+
PENDING = "pending"
|
|
1498
|
+
SCHEDULED = "scheduled"
|
|
1499
|
+
PUBLISHING = "publishing"
|
|
1500
|
+
PUBLISHED = "published"
|
|
1501
|
+
FAILED = "failed"
|
|
1502
|
+
PARTIAL = "partial"
|
|
1503
|
+
|
|
1504
|
+
|
|
1505
|
+
class CreatePostPlatformsPlatform_10(str, Enum):
|
|
1506
|
+
TWITTER = "twitter"
|
|
1507
|
+
INSTAGRAM = "instagram"
|
|
1508
|
+
YOUTUBE = "youtube"
|
|
1509
|
+
TIKTOK = "tiktok"
|
|
1510
|
+
PINTEREST = "pinterest"
|
|
1511
|
+
LINKEDIN = "linkedin"
|
|
1512
|
+
BLUESKY = "bluesky"
|
|
1513
|
+
FACEBOOK = "facebook"
|
|
1514
|
+
THREADS = "threads"
|
|
1515
|
+
GOOGLEBUSINESS = "googlebusiness"
|
|
1516
|
+
|
|
1517
|
+
|
|
1518
|
+
class CreatePostPlatforms_10(BaseModel):
|
|
1519
|
+
platform: CreatePostPlatformsPlatform_10
|
|
1520
|
+
success: bool = Field(..., description="For publish-now timeout fallback, true means the platform target was accepted and final status is still pending.")
|
|
1521
|
+
platform_post_url: Optional[str] = Field(default=None, alias="platformPostUrl", description="Direct URL to the published post")
|
|
1522
|
+
error: Optional[str] = Field(default=None, description="Error message when success is false")
|
|
1523
|
+
warning_message: Optional[str] = Field(default=None, alias="warningMessage", description="Warning message when the post published but a non-critical follow-up action failed")
|
|
1524
|
+
|
|
1525
|
+
|
|
1526
|
+
class CreatePostResponse(BaseModel):
|
|
1527
|
+
"""Default Response"""
|
|
1528
|
+
|
|
1529
|
+
success: bool = Field(..., description="false only when every platform failed")
|
|
1530
|
+
status: CreatePostStatus
|
|
1531
|
+
scheduled_for: Optional[datetime] = Field(default=None, alias="scheduledFor", description="ISO 8601 datetime the post is scheduled for (only present for scheduled posts)")
|
|
1532
|
+
post_id: str = Field(..., alias="postId", description="id of the saved Post document")
|
|
1533
|
+
platforms: list[CreatePostPlatforms_10]
|
|
1534
|
+
|
|
1535
|
+
|
|
1536
|
+
class DeletePostPath(BaseModel):
|
|
1537
|
+
post_id: str = Field(..., alias="postId", description="Post identifier")
|
|
1538
|
+
|
|
1539
|
+
|
|
1540
|
+
class DeletePostQuery(BaseModel):
|
|
1541
|
+
delete_from_platforms: Optional[bool] = Field(default=False, alias="deleteFromPlatforms", description="When true, also delete supported published platform posts. Costs 1 credit per successful platform deletion.")
|
|
1542
|
+
|
|
1543
|
+
|
|
1544
|
+
class DeletePostPlatforms(BaseModel):
|
|
1545
|
+
platform: str
|
|
1546
|
+
integration_id: str = Field(..., alias="integrationId")
|
|
1547
|
+
platform_post_id: Optional[str] = Field(default=None, alias="platformPostId")
|
|
1548
|
+
status: str
|
|
1549
|
+
success: bool
|
|
1550
|
+
message: Optional[str] = None
|
|
1551
|
+
error_message: Optional[str] = Field(default=None, alias="errorMessage")
|
|
1552
|
+
|
|
1553
|
+
|
|
1554
|
+
class DeletePostResponse(BaseModel):
|
|
1555
|
+
"""Default Response"""
|
|
1556
|
+
|
|
1557
|
+
model_config = ConfigDict(populate_by_name=True, extra="forbid")
|
|
1558
|
+
success: bool
|
|
1559
|
+
credits_charged: Optional[Annotated[int, Field(ge=0)]] = Field(default=None, alias="creditsCharged")
|
|
1560
|
+
platforms: Optional[list[DeletePostPlatforms]] = None
|
|
1561
|
+
|
|
1562
|
+
|
|
1563
|
+
class GetPostPath(BaseModel):
|
|
1564
|
+
post_id: str = Field(..., alias="postId", description="Post identifier")
|
|
1565
|
+
|
|
1566
|
+
|
|
1567
|
+
class GetPostPostStatus(str, Enum):
|
|
1568
|
+
DRAFT = "draft"
|
|
1569
|
+
PENDING = "pending"
|
|
1570
|
+
SCHEDULED = "scheduled"
|
|
1571
|
+
PUBLISHING = "publishing"
|
|
1572
|
+
PUBLISHED = "published"
|
|
1573
|
+
FAILED = "failed"
|
|
1574
|
+
PARTIAL = "partial"
|
|
1575
|
+
|
|
1576
|
+
|
|
1577
|
+
class GetPostPostMediaItemsType(str, Enum):
|
|
1578
|
+
IMAGE = "image"
|
|
1579
|
+
VIDEO = "video"
|
|
1580
|
+
GIF = "gif"
|
|
1581
|
+
|
|
1582
|
+
|
|
1583
|
+
class GetPostPostMediaItems(BaseModel):
|
|
1584
|
+
type: GetPostPostMediaItemsType
|
|
1585
|
+
url: str
|
|
1586
|
+
filename: str
|
|
1587
|
+
size: float
|
|
1588
|
+
mime_type: str = Field(..., alias="mimeType")
|
|
1589
|
+
|
|
1590
|
+
|
|
1591
|
+
class GetPostPostPlatformsPlatform(str, Enum):
|
|
1592
|
+
TWITTER = "twitter"
|
|
1593
|
+
INSTAGRAM = "instagram"
|
|
1594
|
+
YOUTUBE = "youtube"
|
|
1595
|
+
TIKTOK = "tiktok"
|
|
1596
|
+
PINTEREST = "pinterest"
|
|
1597
|
+
LINKEDIN = "linkedin"
|
|
1598
|
+
BLUESKY = "bluesky"
|
|
1599
|
+
FACEBOOK = "facebook"
|
|
1600
|
+
THREADS = "threads"
|
|
1601
|
+
GOOGLEBUSINESS = "googlebusiness"
|
|
1602
|
+
|
|
1603
|
+
|
|
1604
|
+
class GetPostPostPlatformsStatus(str, Enum):
|
|
1605
|
+
DRAFT = "draft"
|
|
1606
|
+
PENDING = "pending"
|
|
1607
|
+
SCHEDULED = "scheduled"
|
|
1608
|
+
PUBLISHING = "publishing"
|
|
1609
|
+
PUBLISHED = "published"
|
|
1610
|
+
FAILED = "failed"
|
|
1611
|
+
PARTIAL = "partial"
|
|
1612
|
+
|
|
1613
|
+
|
|
1614
|
+
class GetPostPostPlatforms(BaseModel):
|
|
1615
|
+
platform: GetPostPostPlatformsPlatform
|
|
1616
|
+
status: GetPostPostPlatformsStatus
|
|
1617
|
+
content: Optional[str] = Field(default=None, description="Per-platform text override that was used for this platform. Null when the top-level `content` was used.")
|
|
1618
|
+
platform_post_id: Optional[str] = Field(default=None, alias="platformPostId")
|
|
1619
|
+
platform_post_url: Optional[str] = Field(default=None, alias="platformPostUrl", description="Direct URL to the published post")
|
|
1620
|
+
published_at: Optional[datetime] = Field(default=None, alias="publishedAt")
|
|
1621
|
+
error_message: Optional[str] = Field(default=None, alias="errorMessage")
|
|
1622
|
+
warning_message: Optional[str] = Field(default=None, alias="warningMessage")
|
|
1623
|
+
|
|
1624
|
+
|
|
1625
|
+
class GetPostPost(BaseModel):
|
|
1626
|
+
post_id: str = Field(..., alias="postId", description="MongoDB ObjectId of the Post document")
|
|
1627
|
+
content: str
|
|
1628
|
+
status: GetPostPostStatus
|
|
1629
|
+
scheduled_for: Optional[datetime] = Field(default=None, alias="scheduledFor", description="ISO 8601 scheduled datetime")
|
|
1630
|
+
timezone: str
|
|
1631
|
+
media_items: list[GetPostPostMediaItems] = Field(..., alias="mediaItems")
|
|
1632
|
+
platforms: list[GetPostPostPlatforms]
|
|
1633
|
+
crossposting_enabled: bool = Field(..., alias="crosspostingEnabled")
|
|
1634
|
+
raw_request_body: dict[str, Any] = Field(..., alias="rawRequestBody")
|
|
1635
|
+
created_at: datetime = Field(..., alias="createdAt")
|
|
1636
|
+
updated_at: datetime = Field(..., alias="updatedAt")
|
|
1637
|
+
|
|
1638
|
+
|
|
1639
|
+
class GetPostResponse(BaseModel):
|
|
1640
|
+
"""Default Response"""
|
|
1641
|
+
|
|
1642
|
+
success: bool
|
|
1643
|
+
post: GetPostPost
|
|
1644
|
+
|
|
1645
|
+
|
|
1646
|
+
class ListScheduledPostsQuery(BaseModel):
|
|
1647
|
+
limit: Optional[Annotated[int, Field(ge=1, le=100)]] = Field(default=20, description="Page size (max 100)")
|
|
1648
|
+
offset: Optional[Annotated[int, Field(ge=0)]] = Field(default=0, description="Number of scheduled posts to skip")
|
|
1649
|
+
sort: Optional[SortOrder] = None
|
|
1650
|
+
|
|
1651
|
+
|
|
1652
|
+
class ListScheduledPostsPostsMediaItemsType(str, Enum):
|
|
1653
|
+
IMAGE = "image"
|
|
1654
|
+
VIDEO = "video"
|
|
1655
|
+
GIF = "gif"
|
|
1656
|
+
DOCUMENT = "document"
|
|
1657
|
+
|
|
1658
|
+
|
|
1659
|
+
class ListScheduledPostsPostsMediaItems(BaseModel):
|
|
1660
|
+
model_config = ConfigDict(extra="forbid")
|
|
1661
|
+
type: ListScheduledPostsPostsMediaItemsType
|
|
1662
|
+
url: AnyUrl
|
|
1663
|
+
thumbnail: Optional[AnyUrl] = Field(default=None, description="Thumbnail image URL for video items. Supported on YouTube regular videos (not Shorts). JPEG, PNG, or GIF, max 2 MB, min 640 px wide.")
|
|
1664
|
+
|
|
1665
|
+
|
|
1666
|
+
class ListScheduledPostsPostsPlatformsPlatform(str, Enum):
|
|
1667
|
+
TWITTER = "twitter"
|
|
1668
|
+
INSTAGRAM = "instagram"
|
|
1669
|
+
YOUTUBE = "youtube"
|
|
1670
|
+
TIKTOK = "tiktok"
|
|
1671
|
+
PINTEREST = "pinterest"
|
|
1672
|
+
LINKEDIN = "linkedin"
|
|
1673
|
+
BLUESKY = "bluesky"
|
|
1674
|
+
FACEBOOK = "facebook"
|
|
1675
|
+
THREADS = "threads"
|
|
1676
|
+
GOOGLEBUSINESS = "googlebusiness"
|
|
1677
|
+
|
|
1678
|
+
|
|
1679
|
+
class ListScheduledPostsPostsPlatformsStatus(str, Enum):
|
|
1680
|
+
DRAFT = "draft"
|
|
1681
|
+
PENDING = "pending"
|
|
1682
|
+
SCHEDULED = "scheduled"
|
|
1683
|
+
PUBLISHING = "publishing"
|
|
1684
|
+
PUBLISHED = "published"
|
|
1685
|
+
FAILED = "failed"
|
|
1686
|
+
PARTIAL = "partial"
|
|
1687
|
+
|
|
1688
|
+
|
|
1689
|
+
class ListScheduledPostsPostsPlatforms(BaseModel):
|
|
1690
|
+
platform: ListScheduledPostsPostsPlatformsPlatform
|
|
1691
|
+
status: ListScheduledPostsPostsPlatformsStatus
|
|
1692
|
+
|
|
1693
|
+
|
|
1694
|
+
class ListScheduledPostsPosts(BaseModel):
|
|
1695
|
+
post_id: str = Field(..., alias="postId", description="MongoDB ObjectId of the Post document")
|
|
1696
|
+
content: str = Field(..., description="Post text body")
|
|
1697
|
+
scheduled_for: Optional[datetime] = Field(default=None, alias="scheduledFor", description="ISO 8601 scheduled datetime")
|
|
1698
|
+
timezone: str = Field(..., description="IANA timezone for the scheduled time")
|
|
1699
|
+
media_items: Optional[list[ListScheduledPostsPostsMediaItems]] = Field(default=None, alias="mediaItems", description="Media attachments")
|
|
1700
|
+
platforms: list[ListScheduledPostsPostsPlatforms]
|
|
1701
|
+
created_at: datetime = Field(..., alias="createdAt")
|
|
1702
|
+
|
|
1703
|
+
|
|
1704
|
+
class ListScheduledPostsResponse(BaseModel):
|
|
1705
|
+
"""Default Response"""
|
|
1706
|
+
|
|
1707
|
+
success: bool
|
|
1708
|
+
total: Annotated[int, Field(ge=0)] = Field(..., description="Total matched scheduled posts across all pages")
|
|
1709
|
+
posts: list[ListScheduledPostsPosts]
|
|
1710
|
+
|
|
1711
|
+
|
|
1712
|
+
class CancelScheduledPostPath(BaseModel):
|
|
1713
|
+
post_id: str = Field(..., alias="postId")
|
|
1714
|
+
|
|
1715
|
+
|
|
1716
|
+
class CancelScheduledPostResponse(BaseModel):
|
|
1717
|
+
"""Default Response"""
|
|
1718
|
+
|
|
1719
|
+
success: bool
|
|
1720
|
+
message: str
|
|
1721
|
+
|
|
1722
|
+
|
|
1723
|
+
class ReschedulePostBody(BaseModel):
|
|
1724
|
+
scheduled_for: datetime = Field(..., alias="scheduledFor", description="New ISO 8601 datetime to schedule the post")
|
|
1725
|
+
timezone: Optional[str] = Field(default=None, description="IANA timezone")
|
|
1726
|
+
|
|
1727
|
+
|
|
1728
|
+
class ReschedulePostPath(BaseModel):
|
|
1729
|
+
post_id: str = Field(..., alias="postId")
|
|
1730
|
+
|
|
1731
|
+
|
|
1732
|
+
class ReschedulePostResponse(BaseModel):
|
|
1733
|
+
"""Default Response"""
|
|
1734
|
+
|
|
1735
|
+
success: bool
|
|
1736
|
+
message: str
|
|
1737
|
+
scheduled_for: str = Field(..., alias="scheduledFor")
|
|
1738
|
+
|
|
1739
|
+
|
|
1740
|
+
class CreateMediaUploadBody(BaseModel):
|
|
1741
|
+
model_config = ConfigDict(populate_by_name=True, extra="forbid")
|
|
1742
|
+
filename: Annotated[str, Field(min_length=1)]
|
|
1743
|
+
mime_type: Annotated[str, Field(min_length=1)] = Field(..., alias="mimeType")
|
|
1744
|
+
|
|
1745
|
+
|
|
1746
|
+
class CreateMediaUploadData(BaseModel):
|
|
1747
|
+
upload_url: str = Field(..., alias="uploadUrl")
|
|
1748
|
+
public_url: str = Field(..., alias="publicUrl")
|
|
1749
|
+
|
|
1750
|
+
|
|
1751
|
+
class CreateMediaUploadResponse(BaseModel):
|
|
1752
|
+
"""Default Response"""
|
|
1753
|
+
|
|
1754
|
+
success: bool
|
|
1755
|
+
data: CreateMediaUploadData
|
|
1756
|
+
|
|
1757
|
+
|
|
1758
|
+
class GetAnalyticsSource(str, Enum):
|
|
1759
|
+
"""Where the result came from. "postpeer" = posts published via PostPeer (stored in our DB). "platform" = fetched directly from the connected platform account."""
|
|
1760
|
+
|
|
1761
|
+
POSTPEER = "postpeer"
|
|
1762
|
+
PLATFORM = "platform"
|
|
1763
|
+
|
|
1764
|
+
|
|
1765
|
+
class GetAnalyticsSortBy(str, Enum):
|
|
1766
|
+
"""Sort results by this metric"""
|
|
1767
|
+
|
|
1768
|
+
DATE = "date"
|
|
1769
|
+
LIKES = "likes"
|
|
1770
|
+
COMMENTS = "comments"
|
|
1771
|
+
IMPRESSIONS = "impressions"
|
|
1772
|
+
VIEWS = "views"
|
|
1773
|
+
SHARES = "shares"
|
|
1774
|
+
SAVES = "saves"
|
|
1775
|
+
CLICKS = "clicks"
|
|
1776
|
+
ENGAGEMENT = "engagement"
|
|
1777
|
+
|
|
1778
|
+
|
|
1779
|
+
class GetAnalyticsQuery(BaseModel):
|
|
1780
|
+
post_id: Optional[str] = Field(default=None, alias="postId", description="PostPeer post ID or external platform post ID (auto-resolved). When omitted, returns a paginated list of all published posts with analytics.")
|
|
1781
|
+
platform: Optional[Platform] = None
|
|
1782
|
+
account_id: Optional[str] = Field(default=None, alias="accountId", description="Integration ID. Required for external ID lookups and source=platform.")
|
|
1783
|
+
source: Optional[GetAnalyticsSource] = Field(default=None, description='Where the result came from. "postpeer" = posts published via PostPeer (stored in our DB). "platform" = fetched directly from the connected platform account.')
|
|
1784
|
+
from_date: Optional[date] = Field(default=None, alias="fromDate", description="Inclusive start date (YYYY-MM-DD). Defaults to 90 days ago.")
|
|
1785
|
+
to_date: Optional[date] = Field(default=None, alias="toDate", description="Inclusive end date (YYYY-MM-DD). Defaults to today.")
|
|
1786
|
+
sort_by: Optional[GetAnalyticsSortBy] = Field(default=None, alias="sortBy", description="Sort results by this metric")
|
|
1787
|
+
order: Optional[SortOrder] = None
|
|
1788
|
+
limit: Optional[Annotated[int, Field(ge=1, le=100)]] = Field(default=50, description="Page size (1-100)")
|
|
1789
|
+
page: Optional[Annotated[int, Field(ge=1)]] = Field(default=1, description="Page number")
|
|
1790
|
+
|
|
1791
|
+
|
|
1792
|
+
class GetAnalyticsPostSource(str, Enum):
|
|
1793
|
+
"""Where the result came from. "postpeer" = posts published via PostPeer (stored in our DB). "platform" = fetched directly from the connected platform account."""
|
|
1794
|
+
|
|
1795
|
+
POSTPEER = "postpeer"
|
|
1796
|
+
PLATFORM = "platform"
|
|
1797
|
+
|
|
1798
|
+
|
|
1799
|
+
class GetAnalyticsPostAggregated(BaseModel):
|
|
1800
|
+
impressions: Optional[float] = None
|
|
1801
|
+
reach: Optional[float] = None
|
|
1802
|
+
likes: Optional[float] = None
|
|
1803
|
+
comments: Optional[float] = None
|
|
1804
|
+
shares: Optional[float] = None
|
|
1805
|
+
saves: Optional[float] = None
|
|
1806
|
+
clicks: Optional[float] = None
|
|
1807
|
+
views: Optional[float] = None
|
|
1808
|
+
engagement_rate: Optional[float] = Field(default=None, alias="engagementRate", description="Engagement rate (0-1). null when the platform does not report engagement.")
|
|
1809
|
+
|
|
1810
|
+
|
|
1811
|
+
class GetAnalyticsPostPlatformsMetrics(BaseModel):
|
|
1812
|
+
impressions: Optional[float] = None
|
|
1813
|
+
reach: Optional[float] = None
|
|
1814
|
+
likes: Optional[float] = None
|
|
1815
|
+
comments: Optional[float] = None
|
|
1816
|
+
shares: Optional[float] = None
|
|
1817
|
+
saves: Optional[float] = None
|
|
1818
|
+
clicks: Optional[float] = None
|
|
1819
|
+
views: Optional[float] = None
|
|
1820
|
+
engagement_rate: Optional[float] = Field(default=None, alias="engagementRate", description="Engagement rate (0-1). null when the platform does not report engagement.")
|
|
1821
|
+
|
|
1822
|
+
|
|
1823
|
+
class GetAnalyticsPostPlatforms(BaseModel):
|
|
1824
|
+
platform: Platform
|
|
1825
|
+
platform_post_id: str = Field(..., alias="platformPostId", description="Native post ID on the platform")
|
|
1826
|
+
platform_post_url: Optional[str] = Field(default=None, alias="platformPostUrl", description="Direct URL to the published post, if known")
|
|
1827
|
+
metrics: GetAnalyticsPostPlatformsMetrics
|
|
1828
|
+
|
|
1829
|
+
|
|
1830
|
+
class GetAnalyticsPost(BaseModel):
|
|
1831
|
+
source: GetAnalyticsPostSource = Field(..., description='Where the result came from. "postpeer" = posts published via PostPeer (stored in our DB). "platform" = fetched directly from the connected platform account.')
|
|
1832
|
+
post_id: Optional[str] = Field(default=None, alias="postId", description="PostPeer post ID. null when source=platform (post fetched directly from the platform).")
|
|
1833
|
+
content: Optional[str] = None
|
|
1834
|
+
published_at: Optional[datetime] = Field(default=None, alias="publishedAt")
|
|
1835
|
+
aggregated: GetAnalyticsPostAggregated
|
|
1836
|
+
platforms: list[GetAnalyticsPostPlatforms]
|
|
1837
|
+
|
|
1838
|
+
|
|
1839
|
+
class GetAnalytics(BaseModel):
|
|
1840
|
+
success: bool
|
|
1841
|
+
post: GetAnalyticsPost
|
|
1842
|
+
|
|
1843
|
+
|
|
1844
|
+
class GetAnalyticsPostsSource(str, Enum):
|
|
1845
|
+
"""Where the result came from. "postpeer" = posts published via PostPeer (stored in our DB). "platform" = fetched directly from the connected platform account."""
|
|
1846
|
+
|
|
1847
|
+
POSTPEER = "postpeer"
|
|
1848
|
+
PLATFORM = "platform"
|
|
1849
|
+
|
|
1850
|
+
|
|
1851
|
+
class GetAnalyticsPostsAggregated(BaseModel):
|
|
1852
|
+
impressions: Optional[float] = None
|
|
1853
|
+
reach: Optional[float] = None
|
|
1854
|
+
likes: Optional[float] = None
|
|
1855
|
+
comments: Optional[float] = None
|
|
1856
|
+
shares: Optional[float] = None
|
|
1857
|
+
saves: Optional[float] = None
|
|
1858
|
+
clicks: Optional[float] = None
|
|
1859
|
+
views: Optional[float] = None
|
|
1860
|
+
engagement_rate: Optional[float] = Field(default=None, alias="engagementRate", description="Engagement rate (0-1). null when the platform does not report engagement.")
|
|
1861
|
+
|
|
1862
|
+
|
|
1863
|
+
class GetAnalyticsPostsPlatformsMetrics(BaseModel):
|
|
1864
|
+
impressions: Optional[float] = None
|
|
1865
|
+
reach: Optional[float] = None
|
|
1866
|
+
likes: Optional[float] = None
|
|
1867
|
+
comments: Optional[float] = None
|
|
1868
|
+
shares: Optional[float] = None
|
|
1869
|
+
saves: Optional[float] = None
|
|
1870
|
+
clicks: Optional[float] = None
|
|
1871
|
+
views: Optional[float] = None
|
|
1872
|
+
engagement_rate: Optional[float] = Field(default=None, alias="engagementRate", description="Engagement rate (0-1). null when the platform does not report engagement.")
|
|
1873
|
+
|
|
1874
|
+
|
|
1875
|
+
class GetAnalyticsPostsPlatforms(BaseModel):
|
|
1876
|
+
platform: Platform
|
|
1877
|
+
platform_post_id: str = Field(..., alias="platformPostId", description="Native post ID on the platform")
|
|
1878
|
+
platform_post_url: Optional[str] = Field(default=None, alias="platformPostUrl", description="Direct URL to the published post, if known")
|
|
1879
|
+
metrics: GetAnalyticsPostsPlatformsMetrics
|
|
1880
|
+
|
|
1881
|
+
|
|
1882
|
+
class GetAnalyticsPosts(BaseModel):
|
|
1883
|
+
source: GetAnalyticsPostsSource = Field(..., description='Where the result came from. "postpeer" = posts published via PostPeer (stored in our DB). "platform" = fetched directly from the connected platform account.')
|
|
1884
|
+
post_id: Optional[str] = Field(default=None, alias="postId", description="PostPeer post ID. null when source=platform (post fetched directly from the platform).")
|
|
1885
|
+
content: Optional[str] = None
|
|
1886
|
+
published_at: Optional[datetime] = Field(default=None, alias="publishedAt")
|
|
1887
|
+
aggregated: GetAnalyticsPostsAggregated
|
|
1888
|
+
platforms: list[GetAnalyticsPostsPlatforms]
|
|
1889
|
+
|
|
1890
|
+
|
|
1891
|
+
class GetAnalytics_(BaseModel):
|
|
1892
|
+
success: bool
|
|
1893
|
+
total: Annotated[int, Field(ge=0)] = Field(..., description="Total matched posts across all pages")
|
|
1894
|
+
page: Annotated[int, Field(ge=1)]
|
|
1895
|
+
limit: Annotated[int, Field(ge=1)]
|
|
1896
|
+
posts: list[GetAnalyticsPosts]
|
|
1897
|
+
|
|
1898
|
+
|
|
1899
|
+
class GetAnalyticsResponse(RootModel[Union[GetAnalytics, GetAnalytics_]]):
|
|
1900
|
+
"""Single-post response (when postId is supplied) or paginated list response."""
|
|
1901
|
+
|
|
1902
|
+
root: Union[GetAnalytics, GetAnalytics_] = Field(..., description="Single-post response (when postId is supplied) or paginated list response.")
|
|
1903
|
+
|
|
1904
|
+
|
|
1905
|
+
class GetUsageQuery(BaseModel):
|
|
1906
|
+
profile_id: Optional[str] = Field(default=None, alias="profileId", description="Return usage for this profile only. Mutually exclusive with integrationId.")
|
|
1907
|
+
integration_id: Optional[str] = Field(default=None, alias="integrationId", description="Return usage for this integration only. Mutually exclusive with profileId.")
|
|
1908
|
+
from_: Optional[Annotated[str, Field(pattern=r"^\d{4}-(0[1-9]|1[0-2])$")]] = Field(default=None, alias="from", description="Inclusive start month (YYYY-MM). Filters the usage history array.")
|
|
1909
|
+
to: Optional[Annotated[str, Field(pattern=r"^\d{4}-(0[1-9]|1[0-2])$")]] = Field(default=None, description="Inclusive end month (YYYY-MM). Filters the usage history array.")
|
|
1910
|
+
|
|
1911
|
+
|
|
1912
|
+
class GetUsageUsage(BaseModel):
|
|
1913
|
+
year: int = Field(..., description="Calendar year")
|
|
1914
|
+
month: Annotated[int, Field(ge=1, le=12)] = Field(..., description="Calendar month (1–12)")
|
|
1915
|
+
count: Annotated[int, Field(ge=0)] = Field(..., description="Credits used this month")
|
|
1916
|
+
platform: dict[str, int] = Field(..., description="Credits broken down by platform name")
|
|
1917
|
+
|
|
1918
|
+
|
|
1919
|
+
class GetUsageBalanceMonthly(BaseModel):
|
|
1920
|
+
limit: int = Field(..., description="Total monthly credits included in your plan")
|
|
1921
|
+
used: int = Field(..., description="Monthly credits used so far this billing cycle")
|
|
1922
|
+
remaining: int = Field(..., description="Monthly credits still available this cycle")
|
|
1923
|
+
cycle_start: datetime = Field(..., alias="cycleStart", description="Start of the current billing cycle")
|
|
1924
|
+
cycle_end: datetime = Field(..., alias="cycleEnd", description="End of the current billing cycle — resets here")
|
|
1925
|
+
|
|
1926
|
+
|
|
1927
|
+
class GetUsageBalancePurchased(BaseModel):
|
|
1928
|
+
total: int = Field(..., description="Total one-time credits purchased (never expire)")
|
|
1929
|
+
used: int = Field(..., description="One-time credits consumed so far")
|
|
1930
|
+
remaining: int = Field(..., description="One-time credits still available")
|
|
1931
|
+
|
|
1932
|
+
|
|
1933
|
+
class GetUsageBalance(BaseModel):
|
|
1934
|
+
"""Current credit balance. Only present on project-level requests (no profileId or integrationId filter)."""
|
|
1935
|
+
|
|
1936
|
+
monthly: GetUsageBalanceMonthly
|
|
1937
|
+
purchased: GetUsageBalancePurchased
|
|
1938
|
+
|
|
1939
|
+
|
|
1940
|
+
class GetUsageResponse(BaseModel):
|
|
1941
|
+
"""Default Response"""
|
|
1942
|
+
|
|
1943
|
+
success: bool
|
|
1944
|
+
total_usage: Annotated[int, Field(ge=0)] = Field(..., alias="totalUsage", description="All-time credits used")
|
|
1945
|
+
usage: list[GetUsageUsage] = Field(..., description="Monthly credit history, oldest first")
|
|
1946
|
+
balance: Optional[GetUsageBalance] = Field(default=None, description="Current credit balance. Only present on project-level requests (no profileId or integrationId filter).")
|
|
1947
|
+
|
|
1948
|
+
|
|
1949
|
+
class GetPinterestBoardsQuery(BaseModel):
|
|
1950
|
+
account_id: Optional[str] = Field(default=None, alias="accountId", description="Integration ID of the Pinterest account. If omitted, uses the first connected Pinterest account.")
|
|
1951
|
+
|
|
1952
|
+
|
|
1953
|
+
class GetPinterestBoardsBoards(BaseModel):
|
|
1954
|
+
id: str
|
|
1955
|
+
name: str
|
|
1956
|
+
description: Optional[str] = None
|
|
1957
|
+
privacy: str
|
|
1958
|
+
|
|
1959
|
+
|
|
1960
|
+
class GetPinterestBoardsResponse(BaseModel):
|
|
1961
|
+
"""Default Response"""
|
|
1962
|
+
|
|
1963
|
+
success: bool
|
|
1964
|
+
boards: list[GetPinterestBoardsBoards]
|
|
1965
|
+
|
|
1966
|
+
|
|
1967
|
+
class GetTikTokCreatorInfoQuery(BaseModel):
|
|
1968
|
+
account_id: Optional[str] = Field(default=None, alias="accountId", description="Integration ID of the TikTok account. If omitted, uses the first connected TikTok account.")
|
|
1969
|
+
|
|
1970
|
+
|
|
1971
|
+
class GetTikTokCreatorInfoDataPrivacyLevelOptions(str, Enum):
|
|
1972
|
+
PUBLIC_TO_EVERYONE = "PUBLIC_TO_EVERYONE"
|
|
1973
|
+
MUTUAL_FOLLOW_FRIENDS = "MUTUAL_FOLLOW_FRIENDS"
|
|
1974
|
+
FOLLOWER_OF_CREATOR = "FOLLOWER_OF_CREATOR"
|
|
1975
|
+
SELF_ONLY = "SELF_ONLY"
|
|
1976
|
+
|
|
1977
|
+
|
|
1978
|
+
class GetTikTokCreatorInfoData(BaseModel):
|
|
1979
|
+
creator_avatar_url: Union[str, Any] = Field(..., alias="creatorAvatarUrl", description="Profile avatar URL returned by TikTok.")
|
|
1980
|
+
creator_username: Union[str, Any] = Field(..., alias="creatorUsername", description="Username (@handle) of the creator.")
|
|
1981
|
+
creator_nickname: Union[str, Any] = Field(..., alias="creatorNickname", description="Display name of the creator.")
|
|
1982
|
+
privacy_level_options: list[GetTikTokCreatorInfoDataPrivacyLevelOptions] = Field(..., alias="privacyLevelOptions", description="Privacy levels available to this creator. Your UX must restrict the privacy dropdown to these values.")
|
|
1983
|
+
comment_disabled: bool = Field(..., alias="commentDisabled", description="If true, the creator has disabled comments in their app settings — grey out the Allow Comment toggle.")
|
|
1984
|
+
duet_disabled: bool = Field(..., alias="duetDisabled", description="If true, the creator has disabled duet in their app settings — grey out the Allow Duet toggle.")
|
|
1985
|
+
stitch_disabled: bool = Field(..., alias="stitchDisabled", description="If true, the creator has disabled stitch in their app settings — grey out the Allow Stitch toggle.")
|
|
1986
|
+
max_video_post_duration_sec: float = Field(..., alias="maxVideoPostDurationSec", description="Maximum video duration (in seconds) this creator may post. Reject videos longer than this before upload.")
|
|
1987
|
+
|
|
1988
|
+
|
|
1989
|
+
class GetTikTokCreatorInfoResponse(BaseModel):
|
|
1990
|
+
"""Default Response"""
|
|
1991
|
+
|
|
1992
|
+
success: bool
|
|
1993
|
+
data: Optional[GetTikTokCreatorInfoData] = None
|
|
1994
|
+
error: Optional[str] = None
|
|
1995
|
+
|
|
1996
|
+
|
|
1997
|
+
class AiWriteContentPlatforms(str, Enum):
|
|
1998
|
+
TWITTER = "twitter"
|
|
1999
|
+
INSTAGRAM = "instagram"
|
|
2000
|
+
YOUTUBE = "youtube"
|
|
2001
|
+
TIKTOK = "tiktok"
|
|
2002
|
+
PINTEREST = "pinterest"
|
|
2003
|
+
LINKEDIN = "linkedin"
|
|
2004
|
+
BLUESKY = "bluesky"
|
|
2005
|
+
FACEBOOK = "facebook"
|
|
2006
|
+
THREADS = "threads"
|
|
2007
|
+
GOOGLEBUSINESS = "googlebusiness"
|
|
2008
|
+
|
|
2009
|
+
|
|
2010
|
+
class AiWriteContentBody(BaseModel):
|
|
2011
|
+
description: Annotated[str, Field(min_length=3, max_length=1500)] = Field(..., description="Free-form description of what the post should be about, in the creator's own words.")
|
|
2012
|
+
platforms: Optional[list[AiWriteContentPlatforms]] = Field(default=None, description="Platforms this post will target. Used to fit the strictest character limit.")
|
|
2013
|
+
existing_content: Optional[str] = Field(default=None, alias="existingContent", description="Optional existing draft to rewrite/improve rather than start from scratch.")
|
|
2014
|
+
|
|
2015
|
+
|
|
2016
|
+
class AiWriteContentResponse(BaseModel):
|
|
2017
|
+
"""Default Response"""
|
|
2018
|
+
|
|
2019
|
+
success: bool
|
|
2020
|
+
content: str
|
|
2021
|
+
credits_charged: float = Field(..., alias="creditsCharged")
|
|
2022
|
+
|
|
2023
|
+
|
|
2024
|
+
class AiGenerateImageAspectRatio(str, Enum):
|
|
2025
|
+
"""Output aspect ratio. Defaults to square when omitted."""
|
|
2026
|
+
|
|
2027
|
+
SQUARE = "square"
|
|
2028
|
+
VERTICAL = "vertical"
|
|
2029
|
+
LANDSCAPE = "landscape"
|
|
2030
|
+
|
|
2031
|
+
|
|
2032
|
+
class AiGenerateImageStyle(str, Enum):
|
|
2033
|
+
"""Visual style preset. Adds style guidance to the prompt. Omit for the model to pick whatever fits the brief."""
|
|
2034
|
+
|
|
2035
|
+
PHOTO = "photo"
|
|
2036
|
+
ILLUSTRATION = "illustration"
|
|
2037
|
+
MINIMAL = "minimal"
|
|
2038
|
+
VIBRANT = "vibrant"
|
|
2039
|
+
CINEMATIC = "cinematic"
|
|
2040
|
+
_3D_RENDER = "3d-render"
|
|
2041
|
+
RETRO = "retro"
|
|
2042
|
+
HAND_DRAWN = "hand-drawn"
|
|
2043
|
+
|
|
2044
|
+
|
|
2045
|
+
class AiGenerateImageBody(BaseModel):
|
|
2046
|
+
model_config = ConfigDict(populate_by_name=True, extra="forbid")
|
|
2047
|
+
description: Annotated[str, Field(min_length=3, max_length=1500)]
|
|
2048
|
+
aspect_ratio: Optional[AiGenerateImageAspectRatio] = Field(default=None, alias="aspectRatio", description="Output aspect ratio. Defaults to square when omitted.")
|
|
2049
|
+
style: Optional[AiGenerateImageStyle] = Field(default=None, description="Visual style preset. Adds style guidance to the prompt. Omit for the model to pick whatever fits the brief.")
|
|
2050
|
+
reference_image_urls: Optional[Annotated[list[AnyUrl], Field(max_length=4)]] = Field(default=None, alias="referenceImageUrls", description='Reference images. Used as style/vibe inspiration ONLY. The model will not copy them. Useful for "match my brand look" or "same composition as this".')
|
|
2051
|
+
asset_image_urls: Optional[Annotated[list[AnyUrl], Field(max_length=4)]] = Field(default=None, alias="assetImageUrls", description="Asset images that MUST appear in the generated image (e.g. a brand logo, a specific product photo). The model will place them faithfully according to the brief, without redrawing them.")
|
|
2052
|
+
reference_image_url: Optional[AnyUrl] = Field(default=None, alias="referenceImageUrl", description="DEPRECATED: use referenceImageUrls instead. Still accepted for backwards compatibility.")
|
|
2053
|
+
|
|
2054
|
+
|
|
2055
|
+
class AiGenerateImageResponse(BaseModel):
|
|
2056
|
+
"""Default Response"""
|
|
2057
|
+
|
|
2058
|
+
success: bool
|
|
2059
|
+
url: AnyUrl
|
|
2060
|
+
mime_type: str = Field(..., alias="mimeType")
|
|
2061
|
+
credits_charged: float = Field(..., alias="creditsCharged")
|