late-sdk 0.0.894 → 0.0.896

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.
Files changed (109) hide show
  1. checksums.yaml +4 -4
  2. data/README.md +26 -3
  3. data/docs/AdAccountsApi.md +446 -0
  4. data/docs/AdAnalyticsResponse.md +1 -1
  5. data/docs/AdAnalyticsResponseAnalytics.md +22 -0
  6. data/docs/AdCampaign.md +1 -1
  7. data/docs/AdCampaignBudget.md +11 -3
  8. data/docs/AdCampaignsApi.md +149 -3
  9. data/docs/AdInsightsApi.md +1 -1
  10. data/docs/AdNegativeKeywordList.md +26 -0
  11. data/docs/AdNegativeKeywordListKeyword.md +22 -0
  12. data/docs/BoostPostRequest.md +6 -4
  13. data/docs/CampaignAnalyticsResponseAnalytics.md +3 -1
  14. data/docs/CampaignAnalyticsResponseAnalyticsImpressionShareCache.md +20 -0
  15. data/docs/CampaignAnalyticsResponseAnalyticsSummary.md +96 -0
  16. data/docs/CampaignAnalyticsResponseCampaign.md +2 -0
  17. data/docs/CreateAdNegativeKeywordList201Response.md +24 -0
  18. data/docs/CreateAdNegativeKeywordListRequest.md +26 -0
  19. data/docs/CreateCallAdRequest.md +8 -2
  20. data/docs/CreateMessagingAdRequest.md +8 -2
  21. data/docs/CtwaAdRequestBody.md +8 -2
  22. data/docs/CtwaAdRequestBodyCreativesInner.md +7 -3
  23. data/docs/DeleteAdNegativeKeywordList200Response.md +20 -0
  24. data/docs/GetAdAnalytics202Response.md +1 -1
  25. data/docs/GetAdNegativeKeywordList200Response.md +24 -0
  26. data/docs/GetAdNegativeKeywordList200ResponseList.md +28 -0
  27. data/docs/ListAdNegativeKeywordLists200Response.md +24 -0
  28. data/docs/MediaItem.md +1 -1
  29. data/docs/MessagingAdsApi.md +10 -10
  30. data/docs/ReplaceAdNegativeKeywordListKeywords200Response.md +22 -0
  31. data/docs/ReplaceAdNegativeKeywordListKeywordsRequest.md +24 -0
  32. data/docs/ReplaceCampaignNegativeKeywordListsRequest.md +20 -0
  33. data/docs/UpdateAdCampaign200Response.md +1 -1
  34. data/docs/UpdateAdCampaignRequest.md +2 -0
  35. data/docs/UpdateAdNegativeKeywordList200Response.md +20 -0
  36. data/docs/UpdateAdNegativeKeywordListRequest.md +24 -0
  37. data/lib/zernio-sdk/api/ad_accounts_api.rb +500 -0
  38. data/lib/zernio-sdk/api/ad_campaigns_api.rb +160 -6
  39. data/lib/zernio-sdk/api/ad_insights_api.rb +2 -2
  40. data/lib/zernio-sdk/api/messaging_ads_api.rb +8 -8
  41. data/lib/zernio-sdk/models/ad_analytics_response.rb +1 -1
  42. data/lib/zernio-sdk/models/ad_analytics_response_analytics.rb +169 -0
  43. data/lib/zernio-sdk/models/ad_campaign.rb +3 -1
  44. data/lib/zernio-sdk/models/ad_campaign_budget.rb +99 -5
  45. data/lib/zernio-sdk/models/ad_negative_keyword_list.rb +209 -0
  46. data/lib/zernio-sdk/models/ad_negative_keyword_list_keyword.rb +222 -0
  47. data/lib/zernio-sdk/models/boost_post_request.rb +38 -7
  48. data/lib/zernio-sdk/models/campaign_analytics_response_analytics.rb +11 -2
  49. data/lib/zernio-sdk/models/campaign_analytics_response_analytics_impression_share_cache.rb +158 -0
  50. data/lib/zernio-sdk/models/campaign_analytics_response_analytics_summary.rb +550 -0
  51. data/lib/zernio-sdk/models/campaign_analytics_response_campaign.rb +11 -1
  52. data/lib/zernio-sdk/models/create_ad_negative_keyword_list201_response.rb +220 -0
  53. data/lib/zernio-sdk/models/create_ad_negative_keyword_list_request.rb +327 -0
  54. data/lib/zernio-sdk/models/create_call_ad_request.rb +94 -3
  55. data/lib/zernio-sdk/models/create_messaging_ad_request.rb +94 -3
  56. data/lib/zernio-sdk/models/ctwa_ad_request_body.rb +95 -4
  57. data/lib/zernio-sdk/models/ctwa_ad_request_body_creatives_inner.rb +67 -21
  58. data/lib/zernio-sdk/models/ctwa_ad_request_body_creatives_inner_video.rb +1 -1
  59. data/lib/zernio-sdk/models/ctwa_ad_request_body_video.rb +1 -1
  60. data/lib/zernio-sdk/models/{ad_campaign_campaign_budget.rb → delete_ad_negative_keyword_list200_response.rb} +35 -48
  61. data/lib/zernio-sdk/models/get_ad_analytics202_response.rb +1 -1
  62. data/lib/zernio-sdk/models/get_ad_negative_keyword_list200_response.rb +199 -0
  63. data/lib/zernio-sdk/models/get_ad_negative_keyword_list200_response_list.rb +227 -0
  64. data/lib/zernio-sdk/models/list_ad_negative_keyword_lists200_response.rb +201 -0
  65. data/lib/zernio-sdk/models/media_item.rb +1 -0
  66. data/lib/zernio-sdk/models/replace_ad_negative_keyword_list_keywords200_response.rb +189 -0
  67. data/lib/zernio-sdk/models/replace_ad_negative_keyword_list_keywords_request.rb +289 -0
  68. data/lib/zernio-sdk/models/replace_campaign_negative_keyword_lists_request.rb +219 -0
  69. data/lib/zernio-sdk/models/update_ad_campaign200_response.rb +1 -1
  70. data/lib/zernio-sdk/models/update_ad_campaign_request.rb +13 -1
  71. data/lib/zernio-sdk/models/update_ad_campaign_request_budget.rb +1 -1
  72. data/lib/zernio-sdk/models/update_ad_negative_keyword_list200_response.rb +178 -0
  73. data/lib/zernio-sdk/models/update_ad_negative_keyword_list_request.rb +296 -0
  74. data/lib/zernio-sdk/version.rb +1 -1
  75. data/lib/zernio-sdk.rb +16 -1
  76. data/openapi.yaml +981 -43
  77. data/spec/api/ad_accounts_api_spec.rb +82 -0
  78. data/spec/api/ad_campaigns_api_spec.rb +29 -3
  79. data/spec/api/ad_insights_api_spec.rb +1 -1
  80. data/spec/api/messaging_ads_api_spec.rb +4 -4
  81. data/spec/models/ad_analytics_response_analytics_spec.rb +48 -0
  82. data/spec/models/ad_campaign_budget_spec.rb +24 -0
  83. data/spec/models/ad_negative_keyword_list_keyword_spec.rb +52 -0
  84. data/spec/models/ad_negative_keyword_list_spec.rb +60 -0
  85. data/spec/models/boost_post_request_spec.rb +7 -1
  86. data/spec/models/campaign_analytics_response_analytics_impression_share_cache_spec.rb +42 -0
  87. data/spec/models/campaign_analytics_response_analytics_spec.rb +6 -0
  88. data/spec/models/campaign_analytics_response_analytics_summary_spec.rb +270 -0
  89. data/spec/models/campaign_analytics_response_campaign_spec.rb +6 -0
  90. data/spec/models/create_ad_negative_keyword_list201_response_spec.rb +54 -0
  91. data/spec/models/create_ad_negative_keyword_list_request_spec.rb +64 -0
  92. data/spec/models/create_call_ad_request_spec.rb +18 -0
  93. data/spec/models/create_messaging_ad_request_spec.rb +18 -0
  94. data/spec/models/ctwa_ad_request_body_creatives_inner_spec.rb +12 -0
  95. data/spec/models/ctwa_ad_request_body_spec.rb +18 -0
  96. data/spec/models/delete_ad_negative_keyword_list200_response_spec.rb +42 -0
  97. data/spec/models/get_ad_negative_keyword_list200_response_list_spec.rb +66 -0
  98. data/spec/models/get_ad_negative_keyword_list200_response_spec.rb +54 -0
  99. data/spec/models/list_ad_negative_keyword_lists200_response_spec.rb +54 -0
  100. data/spec/models/replace_ad_negative_keyword_list_keywords200_response_spec.rb +48 -0
  101. data/spec/models/replace_ad_negative_keyword_list_keywords_request_spec.rb +58 -0
  102. data/spec/models/{ad_campaign_campaign_budget_spec.rb → replace_campaign_negative_keyword_lists_request_spec.rb} +12 -12
  103. data/spec/models/update_ad_campaign_request_spec.rb +6 -0
  104. data/spec/models/update_ad_negative_keyword_list200_response_spec.rb +42 -0
  105. data/spec/models/update_ad_negative_keyword_list_request_spec.rb +58 -0
  106. data/zernio-sdk-0.0.896.gem +0 -0
  107. metadata +66 -6
  108. data/docs/AdCampaignCampaignBudget.md +0 -20
  109. data/zernio-sdk-0.0.894.gem +0 -0
@@ -24,20 +24,29 @@ module Zernio
24
24
  # Ad display name. Used to derive campaign / ad set names. On the multi-creative shape, each ad's Meta name gets a \" #N\" suffix (1-indexed) so Ads Manager shows them as a numbered batch.
25
25
  attr_accessor :name
26
26
 
27
+ # Messaging and CTWA only. Platform post or reel ID, resolved like boost platformPostId. Facebook IDs become object_story_id; Instagram IDs become source_instagram_media_id using the connected Instagram identity. Mutually exclusive with objectStoryId and fresh creative fields.
28
+ attr_accessor :existing_post_id
29
+
30
+ # Messaging and CTWA only. Raw Facebook pageId_postId reference, used as object_story_id even with an Instagram account. Mutually exclusive with existingPostId and fresh creative fields.
31
+ attr_accessor :object_story_id
32
+
33
+ # WhatsApp only. Optional E.164 number already paired with the Facebook Page. Omit to let Meta select the paired number. Sent to the creative CTA and, when creating a new ad set, its promoted_object. Attach requests do not change the existing ad set.
34
+ attr_accessor :whatsapp_phone_number
35
+
27
36
  # Single-creative shape only. Mutually exclusive with `creatives[]`.
28
37
  attr_accessor :headline
29
38
 
30
39
  # Primary text shown above the image / video. Single-creative shape only. Mutually exclusive with `creatives[]`.
31
40
  attr_accessor :body
32
41
 
33
- # Image asset for single-creative shape. Mutually exclusive with `video` and with `creatives[]`. Required on the single-creative shape if `video` is not supplied.
42
+ # Image asset for single-creative shape. Mutually exclusive with `video` and with `creatives[]`. Required on the single-creative shape if neither `video` nor an existing post reference is supplied.
34
43
  attr_accessor :image_url
35
44
 
36
45
  attr_accessor :video
37
46
 
38
47
  attr_accessor :welcome_message
39
48
 
40
- # Multi-creative shape: N CTWA ads under one campaign + one ad set, sharing budget and targeting. Mutually exclusive with the top-level single-creative fields (`headline` / `body` / `imageUrl` / `video`): setting both is a 400, unlike `POST /v1/ads/create` where the top-level fields are silently ignored in multi-creative mode. Each entry must supply its own headline, body, and exactly one of `imageUrl` / `video`.
49
+ # Multi-creative shape: N CTWA ads under one campaign + one ad set, sharing budget and targeting. Mutually exclusive with the top-level single-creative fields (`headline` / `body` / `imageUrl` / `video`): setting both is a 400, unlike `POST /v1/ads/create` where the top-level fields are silently ignored in multi-creative mode. Each entry supplies headline, body, and image/video, or an existingPostId or objectStoryId reference. Fresh and existing creatives can be mixed.
41
50
  attr_accessor :creatives
42
51
 
43
52
  # Attach the creatives to this EXISTING messaging ad set instead of building a campaign, so the ad set keeps its learning phase. It then owns budget, targeting and schedule, so `budgetAmount`, `budgetType`, `endDate`, `objective`, `countries`, `interests`, `audienceId` and `campaignStatus` are rejected with a 400 alongside it. Its `destination_type` must match the ad's destination.
@@ -151,6 +160,9 @@ module Zernio
151
160
  :'account_id' => :'accountId',
152
161
  :'ad_account_id' => :'adAccountId',
153
162
  :'name' => :'name',
163
+ :'existing_post_id' => :'existingPostId',
164
+ :'object_story_id' => :'objectStoryId',
165
+ :'whatsapp_phone_number' => :'whatsappPhoneNumber',
154
166
  :'headline' => :'headline',
155
167
  :'body' => :'body',
156
168
  :'image_url' => :'imageUrl',
@@ -205,6 +217,9 @@ module Zernio
205
217
  :'account_id' => :'String',
206
218
  :'ad_account_id' => :'String',
207
219
  :'name' => :'String',
220
+ :'existing_post_id' => :'String',
221
+ :'object_story_id' => :'String',
222
+ :'whatsapp_phone_number' => :'String',
208
223
  :'headline' => :'String',
209
224
  :'body' => :'String',
210
225
  :'image_url' => :'String',
@@ -290,6 +305,18 @@ module Zernio
290
305
  self.name = nil
291
306
  end
292
307
 
308
+ if attributes.key?(:'existing_post_id')
309
+ self.existing_post_id = attributes[:'existing_post_id']
310
+ end
311
+
312
+ if attributes.key?(:'object_story_id')
313
+ self.object_story_id = attributes[:'object_story_id']
314
+ end
315
+
316
+ if attributes.key?(:'whatsapp_phone_number')
317
+ self.whatsapp_phone_number = attributes[:'whatsapp_phone_number']
318
+ end
319
+
293
320
  if attributes.key?(:'headline')
294
321
  self.headline = attributes[:'headline']
295
322
  end
@@ -484,6 +511,20 @@ module Zernio
484
511
  invalid_properties.push('invalid value for "name", the character length must be greater than or equal to 1.')
485
512
  end
486
513
 
514
+ if !@existing_post_id.nil? && @existing_post_id.to_s.length < 1
515
+ invalid_properties.push('invalid value for "existing_post_id", the character length must be greater than or equal to 1.')
516
+ end
517
+
518
+ pattern = Regexp.new(/^\d+_\d+$/)
519
+ if !@object_story_id.nil? && @object_story_id !~ pattern
520
+ invalid_properties.push("invalid value for \"object_story_id\", must conform to the pattern #{pattern}.")
521
+ end
522
+
523
+ pattern = Regexp.new(/^\+[1-9]\d{6,14}$/)
524
+ if !@whatsapp_phone_number.nil? && @whatsapp_phone_number !~ pattern
525
+ invalid_properties.push("invalid value for \"whatsapp_phone_number\", must conform to the pattern #{pattern}.")
526
+ end
527
+
487
528
  if !@headline.nil? && @headline.to_s.length > 255
488
529
  invalid_properties.push('invalid value for "headline", the character length must be smaller than or equal to 255.')
489
530
  end
@@ -553,6 +594,9 @@ module Zernio
553
594
  return false if @ad_account_id.to_s.length < 1
554
595
  return false if @name.nil?
555
596
  return false if @name.to_s.length < 1
597
+ return false if !@existing_post_id.nil? && @existing_post_id.to_s.length < 1
598
+ return false if !@object_story_id.nil? && @object_story_id !~ Regexp.new(/^\d+_\d+$/)
599
+ return false if !@whatsapp_phone_number.nil? && @whatsapp_phone_number !~ Regexp.new(/^\+[1-9]\d{6,14}$/)
556
600
  return false if !@headline.nil? && @headline.to_s.length > 255
557
601
  return false if !@headline.nil? && @headline.to_s.length < 1
558
602
  return false if !@body.nil? && @body.to_s.length < 1
@@ -624,6 +668,50 @@ module Zernio
624
668
  @name = name
625
669
  end
626
670
 
671
+ # Custom attribute writer method with validation
672
+ # @param [Object] existing_post_id Value to be assigned
673
+ def existing_post_id=(existing_post_id)
674
+ if existing_post_id.nil?
675
+ fail ArgumentError, 'existing_post_id cannot be nil'
676
+ end
677
+
678
+ if existing_post_id.to_s.length < 1
679
+ fail ArgumentError, 'invalid value for "existing_post_id", the character length must be greater than or equal to 1.'
680
+ end
681
+
682
+ @existing_post_id = existing_post_id
683
+ end
684
+
685
+ # Custom attribute writer method with validation
686
+ # @param [Object] object_story_id Value to be assigned
687
+ def object_story_id=(object_story_id)
688
+ if object_story_id.nil?
689
+ fail ArgumentError, 'object_story_id cannot be nil'
690
+ end
691
+
692
+ pattern = Regexp.new(/^\d+_\d+$/)
693
+ if object_story_id !~ pattern
694
+ fail ArgumentError, "invalid value for \"object_story_id\", must conform to the pattern #{pattern}."
695
+ end
696
+
697
+ @object_story_id = object_story_id
698
+ end
699
+
700
+ # Custom attribute writer method with validation
701
+ # @param [Object] whatsapp_phone_number Value to be assigned
702
+ def whatsapp_phone_number=(whatsapp_phone_number)
703
+ if whatsapp_phone_number.nil?
704
+ fail ArgumentError, 'whatsapp_phone_number cannot be nil'
705
+ end
706
+
707
+ pattern = Regexp.new(/^\+[1-9]\d{6,14}$/)
708
+ if whatsapp_phone_number !~ pattern
709
+ fail ArgumentError, "invalid value for \"whatsapp_phone_number\", must conform to the pattern #{pattern}."
710
+ end
711
+
712
+ @whatsapp_phone_number = whatsapp_phone_number
713
+ end
714
+
627
715
  # Custom attribute writer method with validation
628
716
  # @param [Object] headline Value to be assigned
629
717
  def headline=(headline)
@@ -840,6 +928,9 @@ module Zernio
840
928
  account_id == o.account_id &&
841
929
  ad_account_id == o.ad_account_id &&
842
930
  name == o.name &&
931
+ existing_post_id == o.existing_post_id &&
932
+ object_story_id == o.object_story_id &&
933
+ whatsapp_phone_number == o.whatsapp_phone_number &&
843
934
  headline == o.headline &&
844
935
  body == o.body &&
845
936
  image_url == o.image_url &&
@@ -886,7 +977,7 @@ module Zernio
886
977
  # Calculates hash code according to all attributes.
887
978
  # @return [Integer] Hash code
888
979
  def hash
889
- [account_id, ad_account_id, name, headline, body, image_url, video, welcome_message, creatives, ad_set_id, budget_amount, budget_type, currency, end_date, countries, cities, regions, zips, metros, custom_locations, age_min, age_max, interests, audience_id, placements, advantage_audience, objective, status, campaign_status, bid_strategy, bid_amount, roas_average_floor, dsa_beneficiary, dsa_payor, regional_regulated_categories, regional_regulation_identities, phone_number, link_url].hash
980
+ [account_id, ad_account_id, name, existing_post_id, object_story_id, whatsapp_phone_number, headline, body, image_url, video, welcome_message, creatives, ad_set_id, budget_amount, budget_type, currency, end_date, countries, cities, regions, zips, metros, custom_locations, age_min, age_max, interests, audience_id, placements, advantage_audience, objective, status, campaign_status, bid_strategy, bid_amount, roas_average_floor, dsa_beneficiary, dsa_payor, regional_regulated_categories, regional_regulation_identities, phone_number, link_url].hash
890
981
  end
891
982
 
892
983
  # Builds the object from hash
@@ -24,20 +24,29 @@ module Zernio
24
24
  # Ad display name. Used to derive campaign / ad set names. On the multi-creative shape, each ad's Meta name gets a \" #N\" suffix (1-indexed) so Ads Manager shows them as a numbered batch.
25
25
  attr_accessor :name
26
26
 
27
+ # Messaging and CTWA only. Platform post or reel ID, resolved like boost platformPostId. Facebook IDs become object_story_id; Instagram IDs become source_instagram_media_id using the connected Instagram identity. Mutually exclusive with objectStoryId and fresh creative fields.
28
+ attr_accessor :existing_post_id
29
+
30
+ # Messaging and CTWA only. Raw Facebook pageId_postId reference, used as object_story_id even with an Instagram account. Mutually exclusive with existingPostId and fresh creative fields.
31
+ attr_accessor :object_story_id
32
+
33
+ # WhatsApp only. Optional E.164 number already paired with the Facebook Page. Omit to let Meta select the paired number. Sent to the creative CTA and, when creating a new ad set, its promoted_object. Attach requests do not change the existing ad set.
34
+ attr_accessor :whatsapp_phone_number
35
+
27
36
  # Single-creative shape only. Mutually exclusive with `creatives[]`.
28
37
  attr_accessor :headline
29
38
 
30
39
  # Primary text shown above the image / video. Single-creative shape only. Mutually exclusive with `creatives[]`.
31
40
  attr_accessor :body
32
41
 
33
- # Image asset for single-creative shape. Mutually exclusive with `video` and with `creatives[]`. Required on the single-creative shape if `video` is not supplied.
42
+ # Image asset for single-creative shape. Mutually exclusive with `video` and with `creatives[]`. Required on the single-creative shape if neither `video` nor an existing post reference is supplied.
34
43
  attr_accessor :image_url
35
44
 
36
45
  attr_accessor :video
37
46
 
38
47
  attr_accessor :welcome_message
39
48
 
40
- # Multi-creative shape: N CTWA ads under one campaign + one ad set, sharing budget and targeting. Mutually exclusive with the top-level single-creative fields (`headline` / `body` / `imageUrl` / `video`): setting both is a 400, unlike `POST /v1/ads/create` where the top-level fields are silently ignored in multi-creative mode. Each entry must supply its own headline, body, and exactly one of `imageUrl` / `video`.
49
+ # Multi-creative shape: N CTWA ads under one campaign + one ad set, sharing budget and targeting. Mutually exclusive with the top-level single-creative fields (`headline` / `body` / `imageUrl` / `video`): setting both is a 400, unlike `POST /v1/ads/create` where the top-level fields are silently ignored in multi-creative mode. Each entry supplies headline, body, and image/video, or an existingPostId or objectStoryId reference. Fresh and existing creatives can be mixed.
41
50
  attr_accessor :creatives
42
51
 
43
52
  # Attach the creatives to this EXISTING messaging ad set instead of building a campaign, so the ad set keeps its learning phase. It then owns budget, targeting and schedule, so `budgetAmount`, `budgetType`, `endDate`, `objective`, `countries`, `interests`, `audienceId` and `campaignStatus` are rejected with a 400 alongside it. Its `destination_type` must match the ad's destination.
@@ -148,6 +157,9 @@ module Zernio
148
157
  :'account_id' => :'accountId',
149
158
  :'ad_account_id' => :'adAccountId',
150
159
  :'name' => :'name',
160
+ :'existing_post_id' => :'existingPostId',
161
+ :'object_story_id' => :'objectStoryId',
162
+ :'whatsapp_phone_number' => :'whatsappPhoneNumber',
151
163
  :'headline' => :'headline',
152
164
  :'body' => :'body',
153
165
  :'image_url' => :'imageUrl',
@@ -201,6 +213,9 @@ module Zernio
201
213
  :'account_id' => :'String',
202
214
  :'ad_account_id' => :'String',
203
215
  :'name' => :'String',
216
+ :'existing_post_id' => :'String',
217
+ :'object_story_id' => :'String',
218
+ :'whatsapp_phone_number' => :'String',
204
219
  :'headline' => :'String',
205
220
  :'body' => :'String',
206
221
  :'image_url' => :'String',
@@ -285,6 +300,18 @@ module Zernio
285
300
  self.name = nil
286
301
  end
287
302
 
303
+ if attributes.key?(:'existing_post_id')
304
+ self.existing_post_id = attributes[:'existing_post_id']
305
+ end
306
+
307
+ if attributes.key?(:'object_story_id')
308
+ self.object_story_id = attributes[:'object_story_id']
309
+ end
310
+
311
+ if attributes.key?(:'whatsapp_phone_number')
312
+ self.whatsapp_phone_number = attributes[:'whatsapp_phone_number']
313
+ end
314
+
288
315
  if attributes.key?(:'headline')
289
316
  self.headline = attributes[:'headline']
290
317
  end
@@ -473,6 +500,20 @@ module Zernio
473
500
  invalid_properties.push('invalid value for "name", the character length must be greater than or equal to 1.')
474
501
  end
475
502
 
503
+ if !@existing_post_id.nil? && @existing_post_id.to_s.length < 1
504
+ invalid_properties.push('invalid value for "existing_post_id", the character length must be greater than or equal to 1.')
505
+ end
506
+
507
+ pattern = Regexp.new(/^\d+_\d+$/)
508
+ if !@object_story_id.nil? && @object_story_id !~ pattern
509
+ invalid_properties.push("invalid value for \"object_story_id\", must conform to the pattern #{pattern}.")
510
+ end
511
+
512
+ pattern = Regexp.new(/^\+[1-9]\d{6,14}$/)
513
+ if !@whatsapp_phone_number.nil? && @whatsapp_phone_number !~ pattern
514
+ invalid_properties.push("invalid value for \"whatsapp_phone_number\", must conform to the pattern #{pattern}.")
515
+ end
516
+
476
517
  if !@headline.nil? && @headline.to_s.length > 255
477
518
  invalid_properties.push('invalid value for "headline", the character length must be smaller than or equal to 255.')
478
519
  end
@@ -538,6 +579,9 @@ module Zernio
538
579
  return false if @ad_account_id.to_s.length < 1
539
580
  return false if @name.nil?
540
581
  return false if @name.to_s.length < 1
582
+ return false if !@existing_post_id.nil? && @existing_post_id.to_s.length < 1
583
+ return false if !@object_story_id.nil? && @object_story_id !~ Regexp.new(/^\d+_\d+$/)
584
+ return false if !@whatsapp_phone_number.nil? && @whatsapp_phone_number !~ Regexp.new(/^\+[1-9]\d{6,14}$/)
541
585
  return false if !@headline.nil? && @headline.to_s.length > 255
542
586
  return false if !@headline.nil? && @headline.to_s.length < 1
543
587
  return false if !@body.nil? && @body.to_s.length < 1
@@ -610,6 +654,50 @@ module Zernio
610
654
  @name = name
611
655
  end
612
656
 
657
+ # Custom attribute writer method with validation
658
+ # @param [Object] existing_post_id Value to be assigned
659
+ def existing_post_id=(existing_post_id)
660
+ if existing_post_id.nil?
661
+ fail ArgumentError, 'existing_post_id cannot be nil'
662
+ end
663
+
664
+ if existing_post_id.to_s.length < 1
665
+ fail ArgumentError, 'invalid value for "existing_post_id", the character length must be greater than or equal to 1.'
666
+ end
667
+
668
+ @existing_post_id = existing_post_id
669
+ end
670
+
671
+ # Custom attribute writer method with validation
672
+ # @param [Object] object_story_id Value to be assigned
673
+ def object_story_id=(object_story_id)
674
+ if object_story_id.nil?
675
+ fail ArgumentError, 'object_story_id cannot be nil'
676
+ end
677
+
678
+ pattern = Regexp.new(/^\d+_\d+$/)
679
+ if object_story_id !~ pattern
680
+ fail ArgumentError, "invalid value for \"object_story_id\", must conform to the pattern #{pattern}."
681
+ end
682
+
683
+ @object_story_id = object_story_id
684
+ end
685
+
686
+ # Custom attribute writer method with validation
687
+ # @param [Object] whatsapp_phone_number Value to be assigned
688
+ def whatsapp_phone_number=(whatsapp_phone_number)
689
+ if whatsapp_phone_number.nil?
690
+ fail ArgumentError, 'whatsapp_phone_number cannot be nil'
691
+ end
692
+
693
+ pattern = Regexp.new(/^\+[1-9]\d{6,14}$/)
694
+ if whatsapp_phone_number !~ pattern
695
+ fail ArgumentError, "invalid value for \"whatsapp_phone_number\", must conform to the pattern #{pattern}."
696
+ end
697
+
698
+ @whatsapp_phone_number = whatsapp_phone_number
699
+ end
700
+
613
701
  # Custom attribute writer method with validation
614
702
  # @param [Object] headline Value to be assigned
615
703
  def headline=(headline)
@@ -816,6 +904,9 @@ module Zernio
816
904
  account_id == o.account_id &&
817
905
  ad_account_id == o.ad_account_id &&
818
906
  name == o.name &&
907
+ existing_post_id == o.existing_post_id &&
908
+ object_story_id == o.object_story_id &&
909
+ whatsapp_phone_number == o.whatsapp_phone_number &&
819
910
  headline == o.headline &&
820
911
  body == o.body &&
821
912
  image_url == o.image_url &&
@@ -861,7 +952,7 @@ module Zernio
861
952
  # Calculates hash code according to all attributes.
862
953
  # @return [Integer] Hash code
863
954
  def hash
864
- [account_id, ad_account_id, name, headline, body, image_url, video, welcome_message, creatives, ad_set_id, budget_amount, budget_type, currency, end_date, countries, cities, regions, zips, metros, custom_locations, age_min, age_max, interests, audience_id, placements, advantage_audience, objective, status, campaign_status, bid_strategy, bid_amount, roas_average_floor, dsa_beneficiary, dsa_payor, regional_regulated_categories, regional_regulation_identities, destination].hash
955
+ [account_id, ad_account_id, name, existing_post_id, object_story_id, whatsapp_phone_number, headline, body, image_url, video, welcome_message, creatives, ad_set_id, budget_amount, budget_type, currency, end_date, countries, cities, regions, zips, metros, custom_locations, age_min, age_max, interests, audience_id, placements, advantage_audience, objective, status, campaign_status, bid_strategy, bid_amount, roas_average_floor, dsa_beneficiary, dsa_payor, regional_regulated_categories, regional_regulation_identities, destination].hash
865
956
  end
866
957
 
867
958
  # Builds the object from hash
@@ -14,7 +14,7 @@ require 'date'
14
14
  require 'time'
15
15
 
16
16
  module Zernio
17
- # In addition to the `required` list, the request must use EXACTLY ONE of the two shapes: - Single-creative: `headline`, `body`, and one of `imageUrl` / `video` (mutually exclusive). - Multi-creative: a non-empty `creatives[]` array. Top-level `headline` / `body` / `imageUrl` / `video` must NOT be set on this shape. The route enforces this at the Zod boundary; OpenAPI's `required` cannot express the OR cleanly.
17
+ # In addition to the `required` list, the request must use EXACTLY ONE of the two shapes: - Single-creative: `headline`, `body`, and one of `imageUrl` / `video`, OR `existingPostId` / `objectStoryId` to reuse an organic post. - Multi-creative: a non-empty `creatives[]` array. Top-level creative fields must NOT be set on this shape. Existing post references work on messaging and CTWA only (not call ads). They cannot be combined with each other or with headline, body, imageUrl, video, or welcomeMessage. No media is uploaded and the organic post is retained. Fresh creatives still require headline, body, and image or video. The route enforces this at the Zod boundary; OpenAPI's `required` cannot express the OR cleanly.
18
18
  class CtwaAdRequestBody < ApiModelBase
19
19
  # Facebook or Instagram SocialAccount ID.
20
20
  attr_accessor :account_id
@@ -25,20 +25,29 @@ module Zernio
25
25
  # Ad display name. Used to derive campaign / ad set names. On the multi-creative shape, each ad's Meta name gets a \" #N\" suffix (1-indexed) so Ads Manager shows them as a numbered batch.
26
26
  attr_accessor :name
27
27
 
28
+ # Messaging and CTWA only. Platform post or reel ID, resolved like boost platformPostId. Facebook IDs become object_story_id; Instagram IDs become source_instagram_media_id using the connected Instagram identity. Mutually exclusive with objectStoryId and fresh creative fields.
29
+ attr_accessor :existing_post_id
30
+
31
+ # Messaging and CTWA only. Raw Facebook pageId_postId reference, used as object_story_id even with an Instagram account. Mutually exclusive with existingPostId and fresh creative fields.
32
+ attr_accessor :object_story_id
33
+
34
+ # WhatsApp only. Optional E.164 number already paired with the Facebook Page. Omit to let Meta select the paired number. Sent to the creative CTA and, when creating a new ad set, its promoted_object. Attach requests do not change the existing ad set.
35
+ attr_accessor :whatsapp_phone_number
36
+
28
37
  # Single-creative shape only. Mutually exclusive with `creatives[]`.
29
38
  attr_accessor :headline
30
39
 
31
40
  # Primary text shown above the image / video. Single-creative shape only. Mutually exclusive with `creatives[]`.
32
41
  attr_accessor :body
33
42
 
34
- # Image asset for single-creative shape. Mutually exclusive with `video` and with `creatives[]`. Required on the single-creative shape if `video` is not supplied.
43
+ # Image asset for single-creative shape. Mutually exclusive with `video` and with `creatives[]`. Required on the single-creative shape if neither `video` nor an existing post reference is supplied.
35
44
  attr_accessor :image_url
36
45
 
37
46
  attr_accessor :video
38
47
 
39
48
  attr_accessor :welcome_message
40
49
 
41
- # Multi-creative shape: N CTWA ads under one campaign + one ad set, sharing budget and targeting. Mutually exclusive with the top-level single-creative fields (`headline` / `body` / `imageUrl` / `video`): setting both is a 400, unlike `POST /v1/ads/create` where the top-level fields are silently ignored in multi-creative mode. Each entry must supply its own headline, body, and exactly one of `imageUrl` / `video`.
50
+ # Multi-creative shape: N CTWA ads under one campaign + one ad set, sharing budget and targeting. Mutually exclusive with the top-level single-creative fields (`headline` / `body` / `imageUrl` / `video`): setting both is a 400, unlike `POST /v1/ads/create` where the top-level fields are silently ignored in multi-creative mode. Each entry supplies headline, body, and image/video, or an existingPostId or objectStoryId reference. Fresh and existing creatives can be mixed.
42
51
  attr_accessor :creatives
43
52
 
44
53
  # Attach the creatives to this EXISTING messaging ad set instead of building a campaign, so the ad set keeps its learning phase. It then owns budget, targeting and schedule, so `budgetAmount`, `budgetType`, `endDate`, `objective`, `countries`, `interests`, `audienceId` and `campaignStatus` are rejected with a 400 alongside it. Its `destination_type` must match the ad's destination.
@@ -146,6 +155,9 @@ module Zernio
146
155
  :'account_id' => :'accountId',
147
156
  :'ad_account_id' => :'adAccountId',
148
157
  :'name' => :'name',
158
+ :'existing_post_id' => :'existingPostId',
159
+ :'object_story_id' => :'objectStoryId',
160
+ :'whatsapp_phone_number' => :'whatsappPhoneNumber',
149
161
  :'headline' => :'headline',
150
162
  :'body' => :'body',
151
163
  :'image_url' => :'imageUrl',
@@ -198,6 +210,9 @@ module Zernio
198
210
  :'account_id' => :'String',
199
211
  :'ad_account_id' => :'String',
200
212
  :'name' => :'String',
213
+ :'existing_post_id' => :'String',
214
+ :'object_story_id' => :'String',
215
+ :'whatsapp_phone_number' => :'String',
201
216
  :'headline' => :'String',
202
217
  :'body' => :'String',
203
218
  :'image_url' => :'String',
@@ -274,6 +289,18 @@ module Zernio
274
289
  self.name = nil
275
290
  end
276
291
 
292
+ if attributes.key?(:'existing_post_id')
293
+ self.existing_post_id = attributes[:'existing_post_id']
294
+ end
295
+
296
+ if attributes.key?(:'object_story_id')
297
+ self.object_story_id = attributes[:'object_story_id']
298
+ end
299
+
300
+ if attributes.key?(:'whatsapp_phone_number')
301
+ self.whatsapp_phone_number = attributes[:'whatsapp_phone_number']
302
+ end
303
+
277
304
  if attributes.key?(:'headline')
278
305
  self.headline = attributes[:'headline']
279
306
  end
@@ -456,6 +483,20 @@ module Zernio
456
483
  invalid_properties.push('invalid value for "name", the character length must be greater than or equal to 1.')
457
484
  end
458
485
 
486
+ if !@existing_post_id.nil? && @existing_post_id.to_s.length < 1
487
+ invalid_properties.push('invalid value for "existing_post_id", the character length must be greater than or equal to 1.')
488
+ end
489
+
490
+ pattern = Regexp.new(/^\d+_\d+$/)
491
+ if !@object_story_id.nil? && @object_story_id !~ pattern
492
+ invalid_properties.push("invalid value for \"object_story_id\", must conform to the pattern #{pattern}.")
493
+ end
494
+
495
+ pattern = Regexp.new(/^\+[1-9]\d{6,14}$/)
496
+ if !@whatsapp_phone_number.nil? && @whatsapp_phone_number !~ pattern
497
+ invalid_properties.push("invalid value for \"whatsapp_phone_number\", must conform to the pattern #{pattern}.")
498
+ end
499
+
459
500
  if !@headline.nil? && @headline.to_s.length > 255
460
501
  invalid_properties.push('invalid value for "headline", the character length must be smaller than or equal to 255.')
461
502
  end
@@ -517,6 +558,9 @@ module Zernio
517
558
  return false if @ad_account_id.to_s.length < 1
518
559
  return false if @name.nil?
519
560
  return false if @name.to_s.length < 1
561
+ return false if !@existing_post_id.nil? && @existing_post_id.to_s.length < 1
562
+ return false if !@object_story_id.nil? && @object_story_id !~ Regexp.new(/^\d+_\d+$/)
563
+ return false if !@whatsapp_phone_number.nil? && @whatsapp_phone_number !~ Regexp.new(/^\+[1-9]\d{6,14}$/)
520
564
  return false if !@headline.nil? && @headline.to_s.length > 255
521
565
  return false if !@headline.nil? && @headline.to_s.length < 1
522
566
  return false if !@body.nil? && @body.to_s.length < 1
@@ -586,6 +630,50 @@ module Zernio
586
630
  @name = name
587
631
  end
588
632
 
633
+ # Custom attribute writer method with validation
634
+ # @param [Object] existing_post_id Value to be assigned
635
+ def existing_post_id=(existing_post_id)
636
+ if existing_post_id.nil?
637
+ fail ArgumentError, 'existing_post_id cannot be nil'
638
+ end
639
+
640
+ if existing_post_id.to_s.length < 1
641
+ fail ArgumentError, 'invalid value for "existing_post_id", the character length must be greater than or equal to 1.'
642
+ end
643
+
644
+ @existing_post_id = existing_post_id
645
+ end
646
+
647
+ # Custom attribute writer method with validation
648
+ # @param [Object] object_story_id Value to be assigned
649
+ def object_story_id=(object_story_id)
650
+ if object_story_id.nil?
651
+ fail ArgumentError, 'object_story_id cannot be nil'
652
+ end
653
+
654
+ pattern = Regexp.new(/^\d+_\d+$/)
655
+ if object_story_id !~ pattern
656
+ fail ArgumentError, "invalid value for \"object_story_id\", must conform to the pattern #{pattern}."
657
+ end
658
+
659
+ @object_story_id = object_story_id
660
+ end
661
+
662
+ # Custom attribute writer method with validation
663
+ # @param [Object] whatsapp_phone_number Value to be assigned
664
+ def whatsapp_phone_number=(whatsapp_phone_number)
665
+ if whatsapp_phone_number.nil?
666
+ fail ArgumentError, 'whatsapp_phone_number cannot be nil'
667
+ end
668
+
669
+ pattern = Regexp.new(/^\+[1-9]\d{6,14}$/)
670
+ if whatsapp_phone_number !~ pattern
671
+ fail ArgumentError, "invalid value for \"whatsapp_phone_number\", must conform to the pattern #{pattern}."
672
+ end
673
+
674
+ @whatsapp_phone_number = whatsapp_phone_number
675
+ end
676
+
589
677
  # Custom attribute writer method with validation
590
678
  # @param [Object] headline Value to be assigned
591
679
  def headline=(headline)
@@ -782,6 +870,9 @@ module Zernio
782
870
  account_id == o.account_id &&
783
871
  ad_account_id == o.ad_account_id &&
784
872
  name == o.name &&
873
+ existing_post_id == o.existing_post_id &&
874
+ object_story_id == o.object_story_id &&
875
+ whatsapp_phone_number == o.whatsapp_phone_number &&
785
876
  headline == o.headline &&
786
877
  body == o.body &&
787
878
  image_url == o.image_url &&
@@ -826,7 +917,7 @@ module Zernio
826
917
  # Calculates hash code according to all attributes.
827
918
  # @return [Integer] Hash code
828
919
  def hash
829
- [account_id, ad_account_id, name, headline, body, image_url, video, welcome_message, creatives, ad_set_id, budget_amount, budget_type, currency, end_date, countries, cities, regions, zips, metros, custom_locations, age_min, age_max, interests, audience_id, placements, advantage_audience, objective, status, campaign_status, bid_strategy, bid_amount, roas_average_floor, dsa_beneficiary, dsa_payor, regional_regulated_categories, regional_regulation_identities].hash
920
+ [account_id, ad_account_id, name, existing_post_id, object_story_id, whatsapp_phone_number, headline, body, image_url, video, welcome_message, creatives, ad_set_id, budget_amount, budget_type, currency, end_date, countries, cities, regions, zips, metros, custom_locations, age_min, age_max, interests, audience_id, placements, advantage_audience, objective, status, campaign_status, bid_strategy, bid_amount, roas_average_floor, dsa_beneficiary, dsa_payor, regional_regulated_categories, regional_regulation_identities].hash
830
921
  end
831
922
 
832
923
  # Builds the object from hash