feat:Amazon Ads - Add DAILY option for Reports streams & Auto-update start_date if past lookback(retention) period (#55217)
Co-authored-by: Octavia Squidington III <octavia-squidington-iii@users.noreply.github.com>
This commit is contained in:
@@ -65,6 +65,32 @@ acceptance_tests:
|
||||
bypass_reason: "can't populate stream because it requires real ad campaign"
|
||||
- name: sponsored_product_ad_group_bid_recommendations
|
||||
bypass_reason: "data is updated frequently"
|
||||
- name: sponsored_display_campaigns_report_stream_daily
|
||||
bypass_reason: "can't populate stream because it requires real ad campaign"
|
||||
- name: sponsored_products_keywords_report_stream_daily
|
||||
bypass_reason: "can't populate stream because it requires real ad campaign"
|
||||
- name: sponsored_display_productads_report_stream_daily
|
||||
bypass_reason: "can't populate stream because it requires real ad campaign"
|
||||
- name: sponsored_products_campaigns_report_stream_daily
|
||||
bypass_reason: "can't populate stream because it requires real ad campaign"
|
||||
- name: sponsored_products_asins_keywords_report_stream_daily
|
||||
bypass_reason: "can't populate stream because it requires real ad campaign"
|
||||
- name: sponsored_display_targets_report_stream_daily
|
||||
bypass_reason: "can't populate stream because it requires real ad campaign"
|
||||
- name: sponsored_products_productads_report_stream_daily
|
||||
bypass_reason: "can't populate stream because it requires real ad campaign"
|
||||
- name: sponsored_display_asins_report_stream_daily
|
||||
bypass_reason: "can't populate stream because it requires real ad campaign"
|
||||
- name: sponsored_brands_v3_report_stream_daily
|
||||
bypass_reason: "can't populate stream because it requires real ad campaign"
|
||||
- name: sponsored_products_asins_targets_report_stream_daily
|
||||
bypass_reason: "can't populate stream because it requires real ad campaign"
|
||||
- name: sponsored_products_adgroups_report_stream_daily
|
||||
bypass_reason: "can't populate stream because it requires real ad campaign"
|
||||
- name: sponsored_display_adgroups_report_stream_daily
|
||||
bypass_reason: "can't populate stream because it requires real ad campaign"
|
||||
- name: sponsored_products_targets_report_stream_daily
|
||||
bypass_reason: "can't populate stream because it requires real ad campaign"
|
||||
timeout_seconds: 2400
|
||||
expect_records:
|
||||
path: integration_tests/expected_records.jsonl
|
||||
|
||||
@@ -31,6 +31,38 @@
|
||||
"cursor_field": ["reportDate"],
|
||||
"sync_mode": "incremental",
|
||||
"destination_sync_mode": "overwrite"
|
||||
},
|
||||
{
|
||||
"stream": {
|
||||
"name": "sponsored_products_report_stream_daily",
|
||||
"json_schema": {},
|
||||
"supported_sync_modes": ["full_refresh", "incremental"],
|
||||
"source_defined_primary_key": [
|
||||
["profileId"],
|
||||
["recordType"],
|
||||
["reportDate"],
|
||||
["recordId"]
|
||||
]
|
||||
},
|
||||
"cursor_field": ["reportDate"],
|
||||
"sync_mode": "incremental",
|
||||
"destination_sync_mode": "overwrite"
|
||||
},
|
||||
{
|
||||
"stream": {
|
||||
"name": "sponsored_brands_v3_report_stream_daily",
|
||||
"json_schema": {},
|
||||
"supported_sync_modes": ["full_refresh", "incremental"],
|
||||
"source_defined_primary_key": [
|
||||
["profileId"],
|
||||
["recordType"],
|
||||
["reportDate"],
|
||||
["recordId"]
|
||||
]
|
||||
},
|
||||
"cursor_field": ["reportDate"],
|
||||
"sync_mode": "incremental",
|
||||
"destination_sync_mode": "overwrite"
|
||||
}
|
||||
]
|
||||
}
|
||||
|
||||
@@ -13,7 +13,7 @@ data:
|
||||
connectorSubtype: api
|
||||
connectorType: source
|
||||
definitionId: c6b0a29e-1da9-4512-9002-7bfd0cba2246
|
||||
dockerImageTag: 7.1.7
|
||||
dockerImageTag: 7.2.0-rc.1
|
||||
dockerRepository: airbyte/source-amazon-ads
|
||||
documentationUrl: https://docs.airbyte.com/integrations/sources/amazon-ads
|
||||
githubIssueLabel: source-amazon-ads
|
||||
@@ -34,6 +34,8 @@ data:
|
||||
enabled: true
|
||||
releaseStage: generally_available
|
||||
releases:
|
||||
rolloutConfiguration:
|
||||
enableProgressiveRollout: true
|
||||
breakingChanges:
|
||||
7.0.0:
|
||||
message:
|
||||
|
||||
@@ -3,7 +3,7 @@ requires = [ "poetry-core>=1.0.0",]
|
||||
build-backend = "poetry.core.masonry.api"
|
||||
|
||||
[tool.poetry]
|
||||
version = "7.1.7"
|
||||
version = "7.2.0-rc.1"
|
||||
name = "source-amazon-ads"
|
||||
description = "Source implementation for Amazon Ads."
|
||||
authors = [ "Airbyte <contact@airbyte.io>",]
|
||||
|
||||
@@ -1235,7 +1235,6 @@ definitions:
|
||||
$ref: "#/definitions/incremental_sync_report_datetime_cursor"
|
||||
transformations:
|
||||
$ref: "#/definitions/transformation_report_add_fields"
|
||||
|
||||
retriever:
|
||||
$ref: "#/definitions/basic_async_retriever"
|
||||
creation_requester:
|
||||
@@ -1248,28 +1247,67 @@ definitions:
|
||||
adProduct: SPONSORED_BRANDS
|
||||
groupBy: ["purchasedAsin"]
|
||||
columns:
|
||||
[
|
||||
"campaignBudgetCurrencyCode",
|
||||
"campaignName",
|
||||
"adGroupName",
|
||||
"attributionType",
|
||||
"purchasedAsin",
|
||||
"productName",
|
||||
"productCategory",
|
||||
"sales14d",
|
||||
"orders14d",
|
||||
"unitsSold14d",
|
||||
"newToBrandSales14d",
|
||||
"newToBrandPurchases14d",
|
||||
"newToBrandUnitsSold14d",
|
||||
"newToBrandSalesPercentage14d",
|
||||
"newToBrandPurchasesPercentage14d",
|
||||
"newToBrandUnitsSoldPercentage14d",
|
||||
]
|
||||
- "campaignBudgetCurrencyCode"
|
||||
- "campaignName"
|
||||
- "adGroupName"
|
||||
- "attributionType"
|
||||
- "purchasedAsin"
|
||||
- "productName"
|
||||
- "productCategory"
|
||||
- "sales14d"
|
||||
- "orders14d"
|
||||
- "unitsSold14d"
|
||||
- "newToBrandSales14d"
|
||||
- "newToBrandPurchases14d"
|
||||
- "newToBrandUnitsSold14d"
|
||||
- "newToBrandSalesPercentage14d"
|
||||
- "newToBrandPurchasesPercentage14d"
|
||||
- "newToBrandUnitsSoldPercentage14d"
|
||||
reportTypeId: sbPurchasedProduct
|
||||
filters: []
|
||||
timeUnit: SUMMARY
|
||||
format: GZIP_JSON
|
||||
sponsored_brands_v3_report_stream_daily:
|
||||
type: DeclarativeStream
|
||||
name: sponsored_brands_v3_report_stream_daily
|
||||
primary_key: ["profileId", "reportDate", "adGroupName", "purchasedAsin"]
|
||||
incremental_sync:
|
||||
$ref: "#/definitions/incremental_sync_report_datetime_cursor"
|
||||
transformations:
|
||||
$ref: "#/definitions/transformation_report_add_fields"
|
||||
retriever:
|
||||
$ref: "#/definitions/basic_async_retriever"
|
||||
creation_requester:
|
||||
$ref: "#/definitions/basic_async_retriever/creation_requester"
|
||||
request_body_json:
|
||||
name: "purchasedAsin report daily {{ stream_interval.start_time }}"
|
||||
startDate: "{{ stream_interval.start_time }}"
|
||||
endDate: "{{ stream_interval.end_time }}"
|
||||
configuration:
|
||||
adProduct: SPONSORED_BRANDS
|
||||
groupBy: ["purchasedAsin"]
|
||||
columns:
|
||||
- "date"
|
||||
- "campaignBudgetCurrencyCode"
|
||||
- "campaignName"
|
||||
- "adGroupName"
|
||||
- "attributionType"
|
||||
- "purchasedAsin"
|
||||
- "productName"
|
||||
- "productCategory"
|
||||
- "sales14d"
|
||||
- "orders14d"
|
||||
- "unitsSold14d"
|
||||
- "newToBrandSales14d"
|
||||
- "newToBrandPurchases14d"
|
||||
- "newToBrandUnitsSold14d"
|
||||
- "newToBrandSalesPercentage14d"
|
||||
- "newToBrandPurchasesPercentage14d"
|
||||
- "newToBrandUnitsSoldPercentage14d"
|
||||
reportTypeId: sbPurchasedProduct
|
||||
filters: []
|
||||
timeUnit: DAILY
|
||||
format: GZIP_JSON
|
||||
|
||||
sponsored_display_campaigns_report_stream:
|
||||
type: DeclarativeStream
|
||||
@@ -1361,6 +1399,93 @@ definitions:
|
||||
filters: []
|
||||
timeUnit: SUMMARY
|
||||
format: GZIP_JSON
|
||||
sponsored_display_campaigns_report_stream_daily:
|
||||
type: DeclarativeStream
|
||||
name: sponsored_display_campaigns_report_stream_daily
|
||||
primary_key: ["profileId", "reportDate", "campaignId"]
|
||||
incremental_sync:
|
||||
$ref: "#/definitions/incremental_sync_report_datetime_cursor"
|
||||
transformations:
|
||||
$ref: "#/definitions/transformation_report_add_fields"
|
||||
retriever:
|
||||
$ref: "#/definitions/basic_async_retriever"
|
||||
creation_requester:
|
||||
$ref: "#/definitions/basic_async_retriever/creation_requester"
|
||||
request_body_json:
|
||||
name: "campaigns report daily {{ stream_interval.start_time }}"
|
||||
startDate: "{{ stream_interval.start_time }}"
|
||||
endDate: "{{ stream_interval.end_time }}"
|
||||
configuration:
|
||||
adProduct: SPONSORED_DISPLAY
|
||||
groupBy: ["campaign"]
|
||||
columns:
|
||||
- "date"
|
||||
- "addToCart"
|
||||
- "addToCartClicks"
|
||||
- "addToCartRate"
|
||||
- "addToCartViews"
|
||||
- "addToList"
|
||||
- "addToListFromClicks"
|
||||
- "addToListFromViews"
|
||||
- "qualifiedBorrows"
|
||||
- "qualifiedBorrowsFromClicks"
|
||||
- "qualifiedBorrowsFromViews"
|
||||
- "royaltyQualifiedBorrows"
|
||||
- "royaltyQualifiedBorrowsFromClicks"
|
||||
- "royaltyQualifiedBorrowsFromViews"
|
||||
- "brandedSearches"
|
||||
- "brandedSearchesClicks"
|
||||
- "brandedSearchesViews"
|
||||
- "brandedSearchRate"
|
||||
- "campaignBudgetCurrencyCode"
|
||||
- "campaignId"
|
||||
- "campaignName"
|
||||
- "clicks"
|
||||
- "cost"
|
||||
- "detailPageViews"
|
||||
- "detailPageViewsClicks"
|
||||
- "eCPAddToCart"
|
||||
- "eCPBrandSearch"
|
||||
- "impressions"
|
||||
- "impressionsViews"
|
||||
- "leadFormOpens"
|
||||
- "leads"
|
||||
- "linkOuts"
|
||||
- "newToBrandPurchases"
|
||||
- "newToBrandPurchasesClicks"
|
||||
- "newToBrandSalesClicks"
|
||||
- "newToBrandUnitsSold"
|
||||
- "newToBrandUnitsSoldClicks"
|
||||
- "purchases"
|
||||
- "purchasesClicks"
|
||||
- "purchasesPromotedClicks"
|
||||
- "sales"
|
||||
- "salesClicks"
|
||||
- "salesPromotedClicks"
|
||||
- "unitsSold"
|
||||
- "unitsSoldClicks"
|
||||
- "videoCompleteViews"
|
||||
- "videoFirstQuartileViews"
|
||||
- "videoMidpointViews"
|
||||
- "videoThirdQuartileViews"
|
||||
- "videoUnmutes"
|
||||
- "viewabilityRate"
|
||||
- "viewClickThroughRate"
|
||||
- "campaignBudgetAmount"
|
||||
- "campaignStatus"
|
||||
- "costType"
|
||||
- "cumulativeReach"
|
||||
- "impressionsFrequencyAverage"
|
||||
- "newToBrandDetailPageViewClicks"
|
||||
- "newToBrandDetailPageViewRate"
|
||||
- "newToBrandDetailPageViews"
|
||||
- "newToBrandDetailPageViewViews"
|
||||
- "newToBrandECPDetailPageView"
|
||||
- "newToBrandSales"
|
||||
reportTypeId: sdCampaigns
|
||||
filters: []
|
||||
timeUnit: DAILY
|
||||
format: GZIP_JSON
|
||||
sponsored_display_adgroups_report_stream:
|
||||
type: DeclarativeStream
|
||||
name: sponsored_display_adgroups_report_stream
|
||||
@@ -1451,6 +1576,93 @@ definitions:
|
||||
filters: []
|
||||
timeUnit: SUMMARY
|
||||
format: GZIP_JSON
|
||||
sponsored_display_adgroups_report_stream_daily:
|
||||
type: DeclarativeStream
|
||||
name: sponsored_display_adgroups_report_stream_daily
|
||||
primary_key: ["profileId", "reportDate", "adGroupName", "adGroupId"]
|
||||
incremental_sync:
|
||||
$ref: "#/definitions/incremental_sync_report_datetime_cursor"
|
||||
transformations:
|
||||
$ref: "#/definitions/transformation_report_add_fields"
|
||||
retriever:
|
||||
$ref: "#/definitions/basic_async_retriever"
|
||||
creation_requester:
|
||||
$ref: "#/definitions/basic_async_retriever/creation_requester"
|
||||
request_body_json:
|
||||
name: "adGroups report daily {{ stream_interval.start_time }}"
|
||||
startDate: "{{ stream_interval.start_time }}"
|
||||
endDate: "{{ stream_interval.end_time }}"
|
||||
configuration:
|
||||
adProduct: SPONSORED_DISPLAY
|
||||
groupBy: ["adGroup"]
|
||||
columns:
|
||||
- "date"
|
||||
- "addToCart"
|
||||
- "addToCartClicks"
|
||||
- "addToCartRate"
|
||||
- "addToCartViews"
|
||||
- "adGroupId"
|
||||
- "adGroupName"
|
||||
- "addToList"
|
||||
- "addToListFromClicks"
|
||||
- "addToListFromViews"
|
||||
- "qualifiedBorrows"
|
||||
- "qualifiedBorrowsFromClicks"
|
||||
- "qualifiedBorrowsFromViews"
|
||||
- "royaltyQualifiedBorrows"
|
||||
- "royaltyQualifiedBorrowsFromClicks"
|
||||
- "royaltyQualifiedBorrowsFromViews"
|
||||
- "bidOptimization"
|
||||
- "brandedSearches"
|
||||
- "brandedSearchesClicks"
|
||||
- "brandedSearchesViews"
|
||||
- "brandedSearchRate"
|
||||
- "campaignBudgetCurrencyCode"
|
||||
- "campaignId"
|
||||
- "campaignName"
|
||||
- "clicks"
|
||||
- "cost"
|
||||
- "detailPageViews"
|
||||
- "detailPageViewsClicks"
|
||||
- "eCPAddToCart"
|
||||
- "eCPBrandSearch"
|
||||
- "impressions"
|
||||
- "impressionsViews"
|
||||
- "leadFormOpens"
|
||||
- "leads"
|
||||
- "linkOuts"
|
||||
- "newToBrandPurchases"
|
||||
- "newToBrandPurchasesClicks"
|
||||
- "newToBrandSales"
|
||||
- "newToBrandSalesClicks"
|
||||
- "newToBrandUnitsSold"
|
||||
- "newToBrandUnitsSoldClicks"
|
||||
- "purchases"
|
||||
- "purchasesClicks"
|
||||
- "purchasesPromotedClicks"
|
||||
- "sales"
|
||||
- "salesClicks"
|
||||
- "salesPromotedClicks"
|
||||
- "unitsSold"
|
||||
- "unitsSoldClicks"
|
||||
- "videoCompleteViews"
|
||||
- "videoFirstQuartileViews"
|
||||
- "videoMidpointViews"
|
||||
- "videoThirdQuartileViews"
|
||||
- "videoUnmutes"
|
||||
- "viewabilityRate"
|
||||
- "viewClickThroughRate"
|
||||
- "cumulativeReach"
|
||||
- "impressionsFrequencyAverage"
|
||||
- "newToBrandDetailPageViewClicks"
|
||||
- "newToBrandDetailPageViewRate"
|
||||
- "newToBrandDetailPageViews"
|
||||
- "newToBrandDetailPageViewViews"
|
||||
- "newToBrandECPDetailPageView"
|
||||
reportTypeId: sdAdGroup
|
||||
filters: []
|
||||
timeUnit: DAILY
|
||||
format: GZIP_JSON
|
||||
sponsored_display_productads_report_stream:
|
||||
type: DeclarativeStream
|
||||
name: sponsored_display_productads_report_stream
|
||||
@@ -1544,6 +1756,96 @@ definitions:
|
||||
filters: []
|
||||
timeUnit: SUMMARY
|
||||
format: GZIP_JSON
|
||||
sponsored_display_productads_report_stream_daily:
|
||||
type: DeclarativeStream
|
||||
name: sponsored_display_productads_report_stream_daily
|
||||
primary_key: ["profileId", "reportDate", "adGroupName", "adId"]
|
||||
incremental_sync:
|
||||
$ref: "#/definitions/incremental_sync_report_datetime_cursor"
|
||||
transformations:
|
||||
$ref: "#/definitions/transformation_report_add_fields"
|
||||
retriever:
|
||||
$ref: "#/definitions/basic_async_retriever"
|
||||
creation_requester:
|
||||
$ref: "#/definitions/basic_async_retriever/creation_requester"
|
||||
request_body_json:
|
||||
name: "productAds report daily {{ stream_interval.start_time }}"
|
||||
startDate: "{{ stream_interval.start_time }}"
|
||||
endDate: "{{ stream_interval.end_time }}"
|
||||
configuration:
|
||||
adProduct: SPONSORED_DISPLAY
|
||||
groupBy: ["advertiser"]
|
||||
columns:
|
||||
- "date"
|
||||
- "addToCart"
|
||||
- "addToCartRate"
|
||||
- "addToCartViews"
|
||||
- "addToCartClicks"
|
||||
- "adGroupId"
|
||||
- "adGroupName"
|
||||
- "adId"
|
||||
- "addToList"
|
||||
- "addToListFromClicks"
|
||||
- "qualifiedBorrows"
|
||||
- "royaltyQualifiedBorrows"
|
||||
- "addToListFromViews"
|
||||
- "qualifiedBorrowsFromClicks"
|
||||
- "qualifiedBorrowsFromViews"
|
||||
- "royaltyQualifiedBorrowsFromClicks"
|
||||
- "royaltyQualifiedBorrowsFromViews"
|
||||
- "bidOptimization"
|
||||
- "brandedSearches"
|
||||
- "brandedSearchesClicks"
|
||||
- "brandedSearchesViews"
|
||||
- "brandedSearchRate"
|
||||
- "campaignBudgetCurrencyCode"
|
||||
- "campaignId"
|
||||
- "campaignName"
|
||||
- "clicks"
|
||||
- "cost"
|
||||
- "cumulativeReach"
|
||||
- "detailPageViews"
|
||||
- "detailPageViewsClicks"
|
||||
- "eCPAddToCart"
|
||||
- "eCPBrandSearch"
|
||||
- "impressions"
|
||||
- "impressionsFrequencyAverage"
|
||||
- "impressionsViews"
|
||||
- "leadFormOpens"
|
||||
- "leads"
|
||||
- "linkOuts"
|
||||
- "newToBrandDetailPageViewClicks"
|
||||
- "newToBrandDetailPageViewRate"
|
||||
- "newToBrandDetailPageViews"
|
||||
- "newToBrandDetailPageViewViews"
|
||||
- "newToBrandECPDetailPageView"
|
||||
- "newToBrandPurchases"
|
||||
- "newToBrandPurchasesClicks"
|
||||
- "newToBrandSales"
|
||||
- "newToBrandSalesClicks"
|
||||
- "newToBrandUnitsSold"
|
||||
- "newToBrandUnitsSoldClicks"
|
||||
- "promotedAsin"
|
||||
- "promotedSku"
|
||||
- "purchases"
|
||||
- "purchasesClicks"
|
||||
- "purchasesPromotedClicks"
|
||||
- "sales"
|
||||
- "salesClicks"
|
||||
- "salesPromotedClicks"
|
||||
- "unitsSold"
|
||||
- "unitsSoldClicks"
|
||||
- "videoCompleteViews"
|
||||
- "videoFirstQuartileViews"
|
||||
- "videoMidpointViews"
|
||||
- "videoThirdQuartileViews"
|
||||
- "videoUnmutes"
|
||||
- "viewabilityRate"
|
||||
- "viewClickThroughRate"
|
||||
reportTypeId: sdAdvertisedProduct
|
||||
filters: []
|
||||
timeUnit: DAILY
|
||||
format: GZIP_JSON
|
||||
sponsored_display_targets_report_stream:
|
||||
type: DeclarativeStream
|
||||
name: sponsored_display_targets_report_stream
|
||||
@@ -1629,6 +1931,88 @@ definitions:
|
||||
filters: []
|
||||
timeUnit: SUMMARY
|
||||
format: GZIP_JSON
|
||||
sponsored_display_targets_report_stream_daily:
|
||||
type: DeclarativeStream
|
||||
name: sponsored_display_targets_report_stream_daily
|
||||
primary_key: ["profileId", "reportDate", "adGroupName", "targetingId"]
|
||||
incremental_sync:
|
||||
$ref: "#/definitions/incremental_sync_report_datetime_cursor"
|
||||
transformations:
|
||||
$ref: "#/definitions/transformation_report_add_fields"
|
||||
retriever:
|
||||
$ref: "#/definitions/basic_async_retriever"
|
||||
creation_requester:
|
||||
$ref: "#/definitions/basic_async_retriever/creation_requester"
|
||||
request_body_json:
|
||||
name: "targets report daily {{ stream_interval.start_time }}"
|
||||
startDate: "{{ stream_interval.start_time }}"
|
||||
endDate: "{{ stream_interval.end_time }}"
|
||||
configuration:
|
||||
adProduct: SPONSORED_DISPLAY
|
||||
groupBy: ["targeting"]
|
||||
columns:
|
||||
- "date"
|
||||
- "addToCart"
|
||||
- "addToCartClicks"
|
||||
- "addToCartRate"
|
||||
- "addToCartViews"
|
||||
- "adGroupId"
|
||||
- "adGroupName"
|
||||
- "addToList"
|
||||
- "addToListFromClicks"
|
||||
- "addToListFromViews"
|
||||
- "qualifiedBorrows"
|
||||
- "qualifiedBorrowsFromClicks"
|
||||
- "qualifiedBorrowsFromViews"
|
||||
- "royaltyQualifiedBorrows"
|
||||
- "royaltyQualifiedBorrowsFromClicks"
|
||||
- "royaltyQualifiedBorrowsFromViews"
|
||||
- "brandedSearches"
|
||||
- "brandedSearchesClicks"
|
||||
- "brandedSearchesViews"
|
||||
- "brandedSearchRate"
|
||||
- "campaignBudgetCurrencyCode"
|
||||
- "campaignId"
|
||||
- "campaignName"
|
||||
- "clicks"
|
||||
- "cost"
|
||||
- "detailPageViews"
|
||||
- "detailPageViewsClicks"
|
||||
- "eCPAddToCart"
|
||||
- "eCPBrandSearch"
|
||||
- "impressions"
|
||||
- "impressionsViews"
|
||||
- "leadFormOpens"
|
||||
- "leads"
|
||||
- "linkOuts"
|
||||
- "newToBrandPurchases"
|
||||
- "newToBrandPurchasesClicks"
|
||||
- "newToBrandSales"
|
||||
- "newToBrandSalesClicks"
|
||||
- "newToBrandUnitsSold"
|
||||
- "newToBrandUnitsSoldClicks"
|
||||
- "purchases"
|
||||
- "purchasesClicks"
|
||||
- "purchasesPromotedClicks"
|
||||
- "sales"
|
||||
- "salesClicks"
|
||||
- "salesPromotedClicks"
|
||||
- "targetingExpression"
|
||||
- "targetingId"
|
||||
- "targetingText"
|
||||
- "unitsSold"
|
||||
- "unitsSoldClicks"
|
||||
- "videoCompleteViews"
|
||||
- "videoFirstQuartileViews"
|
||||
- "videoMidpointViews"
|
||||
- "videoThirdQuartileViews"
|
||||
- "videoUnmutes"
|
||||
- "viewabilityRate"
|
||||
- "viewClickThroughRate"
|
||||
reportTypeId: sdTargeting
|
||||
filters: []
|
||||
timeUnit: DAILY
|
||||
format: GZIP_JSON
|
||||
sponsored_display_asins_report_stream:
|
||||
type: DeclarativeStream
|
||||
name: sponsored_display_asins_report_stream
|
||||
@@ -1680,6 +2064,54 @@ definitions:
|
||||
filters: []
|
||||
timeUnit: SUMMARY
|
||||
format: GZIP_JSON
|
||||
sponsored_display_asins_report_stream_daily:
|
||||
type: DeclarativeStream
|
||||
name: sponsored_display_asins_report_stream_daily
|
||||
primary_key: ["profileId", "reportDate", "adGroupName", "promotedAsin"]
|
||||
incremental_sync:
|
||||
$ref: "#/definitions/incremental_sync_report_datetime_cursor"
|
||||
transformations:
|
||||
$ref: "#/definitions/transformation_report_add_fields"
|
||||
retriever:
|
||||
$ref: "#/definitions/basic_async_retriever"
|
||||
creation_requester:
|
||||
$ref: "#/definitions/basic_async_retriever/creation_requester"
|
||||
request_body_json:
|
||||
name: "asins report daily {{ stream_interval.start_time }}"
|
||||
startDate: "{{ stream_interval.start_time }}"
|
||||
endDate: "{{ stream_interval.end_time }}"
|
||||
configuration:
|
||||
adProduct: SPONSORED_DISPLAY
|
||||
groupBy: ["asin"]
|
||||
columns:
|
||||
- "date"
|
||||
- "adGroupId"
|
||||
- "adGroupName"
|
||||
- "asinBrandHalo"
|
||||
- "addToList"
|
||||
- "addToListFromClicks"
|
||||
- "qualifiedBorrowsFromClicks"
|
||||
- "royaltyQualifiedBorrowsFromClicks"
|
||||
- "addToListFromViews"
|
||||
- "qualifiedBorrows"
|
||||
- "qualifiedBorrowsFromViews"
|
||||
- "royaltyQualifiedBorrows"
|
||||
- "royaltyQualifiedBorrowsFromViews"
|
||||
- "campaignBudgetCurrencyCode"
|
||||
- "campaignId"
|
||||
- "campaignName"
|
||||
- "conversionsBrandHalo"
|
||||
- "conversionsBrandHaloClicks"
|
||||
- "promotedAsin"
|
||||
- "promotedSku"
|
||||
- "salesBrandHalo"
|
||||
- "salesBrandHaloClicks"
|
||||
- "unitsSoldBrandHalo"
|
||||
- "unitsSoldBrandHaloClicks"
|
||||
reportTypeId: sdPurchasedProduct
|
||||
filters: []
|
||||
timeUnit: DAILY
|
||||
format: GZIP_JSON
|
||||
|
||||
sponsored_products_campaigns_report_stream:
|
||||
type: DeclarativeStream
|
||||
@@ -1741,6 +2173,65 @@ definitions:
|
||||
filters: []
|
||||
timeUnit: SUMMARY
|
||||
format: GZIP_JSON
|
||||
sponsored_products_campaigns_report_stream_daily:
|
||||
type: DeclarativeStream
|
||||
name: sponsored_products_campaigns_report_stream_daily
|
||||
primary_key: ["profileId", "reportDate", "campaignId"]
|
||||
incremental_sync:
|
||||
$ref: "#/definitions/incremental_sync_report_datetime_cursor"
|
||||
transformations:
|
||||
$ref: "#/definitions/transformation_report_add_fields"
|
||||
retriever:
|
||||
$ref: "#/definitions/basic_async_retriever"
|
||||
creation_requester:
|
||||
$ref: "#/definitions/basic_async_retriever/creation_requester"
|
||||
request_body_json:
|
||||
name: "campaigns report daily {{ stream_interval.start_time }}"
|
||||
startDate: "{{ stream_interval.start_time }}"
|
||||
endDate: "{{ stream_interval.end_time }}"
|
||||
configuration:
|
||||
adProduct: SPONSORED_PRODUCTS
|
||||
groupBy: ["campaign"]
|
||||
columns:
|
||||
- "date"
|
||||
- "campaignName"
|
||||
- "campaignId"
|
||||
- "campaignStatus"
|
||||
- "campaignBudgetAmount"
|
||||
- "campaignRuleBasedBudgetAmount"
|
||||
- "campaignApplicableBudgetRuleId"
|
||||
- "campaignApplicableBudgetRuleName"
|
||||
- "impressions"
|
||||
- "clicks"
|
||||
- "cost"
|
||||
- "purchases1d"
|
||||
- "purchases7d"
|
||||
- "purchases14d"
|
||||
- "purchases30d"
|
||||
- "purchasesSameSku1d"
|
||||
- "purchasesSameSku7d"
|
||||
- "purchasesSameSku14d"
|
||||
- "purchasesSameSku30d"
|
||||
- "unitsSoldClicks1d"
|
||||
- "unitsSoldClicks7d"
|
||||
- "unitsSoldClicks14d"
|
||||
- "unitsSoldClicks30d"
|
||||
- "sales1d"
|
||||
- "sales7d"
|
||||
- "sales14d"
|
||||
- "sales30d"
|
||||
- "attributedSalesSameSku1d"
|
||||
- "attributedSalesSameSku7d"
|
||||
- "attributedSalesSameSku14d"
|
||||
- "attributedSalesSameSku30d"
|
||||
- "unitsSoldSameSku1d"
|
||||
- "unitsSoldSameSku7d"
|
||||
- "unitsSoldSameSku14d"
|
||||
- "unitsSoldSameSku30d"
|
||||
reportTypeId: spCampaigns
|
||||
filters: []
|
||||
timeUnit: DAILY
|
||||
format: GZIP_JSON
|
||||
sponsored_products_adgroups_report_stream:
|
||||
type: DeclarativeStream
|
||||
name: sponsored_products_adgroups_report_stream
|
||||
@@ -1798,6 +2289,62 @@ definitions:
|
||||
filters: []
|
||||
timeUnit: SUMMARY
|
||||
format: GZIP_JSON
|
||||
sponsored_products_adgroups_report_stream_daily:
|
||||
type: DeclarativeStream
|
||||
name: sponsored_products_adgroups_report_stream_daily
|
||||
primary_key: ["profileId", "reportDate", "adGroupName", "adGroupId"]
|
||||
incremental_sync:
|
||||
$ref: "#/definitions/incremental_sync_report_datetime_cursor"
|
||||
transformations:
|
||||
$ref: "#/definitions/transformation_report_add_fields"
|
||||
retriever:
|
||||
$ref: "#/definitions/basic_async_retriever"
|
||||
creation_requester:
|
||||
$ref: "#/definitions/basic_async_retriever/creation_requester"
|
||||
request_body_json:
|
||||
name: "adGroups report daily {{ stream_interval.start_time }}"
|
||||
startDate: "{{ stream_interval.start_time }}"
|
||||
endDate: "{{ stream_interval.end_time }}"
|
||||
configuration:
|
||||
adProduct: SPONSORED_PRODUCTS
|
||||
groupBy: ["campaign", "adGroup"]
|
||||
columns:
|
||||
- "date"
|
||||
- "campaignName"
|
||||
- "campaignId"
|
||||
- "adGroupName"
|
||||
- "adGroupId"
|
||||
- "impressions"
|
||||
- "clicks"
|
||||
- "cost"
|
||||
- "purchases1d"
|
||||
- "purchases7d"
|
||||
- "purchases14d"
|
||||
- "purchases30d"
|
||||
- "purchasesSameSku1d"
|
||||
- "purchasesSameSku7d"
|
||||
- "purchasesSameSku14d"
|
||||
- "purchasesSameSku30d"
|
||||
- "unitsSoldClicks1d"
|
||||
- "unitsSoldClicks7d"
|
||||
- "unitsSoldClicks14d"
|
||||
- "unitsSoldClicks30d"
|
||||
- "sales1d"
|
||||
- "sales7d"
|
||||
- "sales14d"
|
||||
- "sales30d"
|
||||
- "attributedSalesSameSku1d"
|
||||
- "attributedSalesSameSku7d"
|
||||
- "attributedSalesSameSku14d"
|
||||
- "attributedSalesSameSku30d"
|
||||
- "unitsSoldSameSku1d"
|
||||
- "unitsSoldSameSku7d"
|
||||
- "unitsSoldSameSku14d"
|
||||
- "unitsSoldSameSku30d"
|
||||
reportTypeId: spCampaigns
|
||||
filters: []
|
||||
timeUnit: DAILY
|
||||
format: GZIP_JSON
|
||||
sponsored_products_keywords_report_stream:
|
||||
type: DeclarativeStream
|
||||
name: sponsored_products_keywords_report_stream
|
||||
@@ -1864,6 +2411,67 @@ definitions:
|
||||
]
|
||||
timeUnit: SUMMARY
|
||||
format: GZIP_JSON
|
||||
sponsored_products_keywords_report_stream_daily:
|
||||
type: DeclarativeStream
|
||||
name: sponsored_products_keywords_report_stream_daily
|
||||
primary_key: ["profileId", "reportDate", "adGroupName", "keywordId"]
|
||||
incremental_sync:
|
||||
$ref: "#/definitions/incremental_sync_report_datetime_cursor"
|
||||
transformations:
|
||||
$ref: "#/definitions/transformation_report_add_fields"
|
||||
retriever:
|
||||
$ref: "#/definitions/basic_async_retriever"
|
||||
creation_requester:
|
||||
$ref: "#/definitions/basic_async_retriever/creation_requester"
|
||||
request_body_json:
|
||||
name: "keywords report daily {{ stream_interval.start_time }}"
|
||||
startDate: "{{ stream_interval.start_time }}"
|
||||
endDate: "{{ stream_interval.end_time }}"
|
||||
configuration:
|
||||
adProduct: SPONSORED_PRODUCTS
|
||||
groupBy: ["targeting"]
|
||||
columns:
|
||||
- "date"
|
||||
- "campaignName"
|
||||
- "campaignId"
|
||||
- "adGroupName"
|
||||
- "adGroupId"
|
||||
- "keywordId"
|
||||
- "keyword"
|
||||
- "matchType"
|
||||
- "impressions"
|
||||
- "clicks"
|
||||
- "cost"
|
||||
- "purchases1d"
|
||||
- "purchases7d"
|
||||
- "purchases14d"
|
||||
- "purchases30d"
|
||||
- "purchasesSameSku1d"
|
||||
- "purchasesSameSku7d"
|
||||
- "purchasesSameSku14d"
|
||||
- "purchasesSameSku30d"
|
||||
- "unitsSoldClicks1d"
|
||||
- "unitsSoldClicks7d"
|
||||
- "unitsSoldClicks14d"
|
||||
- "unitsSoldClicks30d"
|
||||
- "sales1d"
|
||||
- "sales7d"
|
||||
- "sales14d"
|
||||
- "sales30d"
|
||||
- "attributedSalesSameSku1d"
|
||||
- "attributedSalesSameSku7d"
|
||||
- "attributedSalesSameSku14d"
|
||||
- "attributedSalesSameSku30d"
|
||||
- "unitsSoldSameSku1d"
|
||||
- "unitsSoldSameSku7d"
|
||||
- "unitsSoldSameSku14d"
|
||||
- "unitsSoldSameSku30d"
|
||||
reportTypeId: spTargeting
|
||||
filters:
|
||||
- field: "keywordType"
|
||||
values: ["BROAD", "PHRASE", "EXACT"]
|
||||
timeUnit: DAILY
|
||||
format: GZIP_JSON
|
||||
sponsored_products_targets_report_stream:
|
||||
type: DeclarativeStream
|
||||
name: sponsored_products_targets_report_stream
|
||||
@@ -1935,6 +2543,70 @@ definitions:
|
||||
]
|
||||
timeUnit: SUMMARY
|
||||
format: GZIP_JSON
|
||||
sponsored_products_targets_report_stream_daily:
|
||||
type: DeclarativeStream
|
||||
name: sponsored_products_targets_report_stream_daily
|
||||
primary_key: ["profileId", "reportDate", "adGroupName", "keywordId"]
|
||||
incremental_sync:
|
||||
$ref: "#/definitions/incremental_sync_report_datetime_cursor"
|
||||
transformations:
|
||||
$ref: "#/definitions/transformation_report_add_fields"
|
||||
retriever:
|
||||
$ref: "#/definitions/basic_async_retriever"
|
||||
creation_requester:
|
||||
$ref: "#/definitions/basic_async_retriever/creation_requester"
|
||||
request_body_json:
|
||||
name: "targets report daily {{ stream_interval.start_time }}"
|
||||
startDate: "{{ stream_interval.start_time }}"
|
||||
endDate: "{{ stream_interval.end_time }}"
|
||||
configuration:
|
||||
adProduct: SPONSORED_PRODUCTS
|
||||
groupBy: ["targeting"]
|
||||
columns:
|
||||
- "date"
|
||||
- "campaignName"
|
||||
- "campaignId"
|
||||
- "adGroupName"
|
||||
- "adGroupId"
|
||||
- "keywordId"
|
||||
- "keyword"
|
||||
- "targeting"
|
||||
- "keywordType"
|
||||
- "impressions"
|
||||
- "clicks"
|
||||
- "cost"
|
||||
- "purchases1d"
|
||||
- "purchases7d"
|
||||
- "purchases14d"
|
||||
- "purchases30d"
|
||||
- "purchasesSameSku1d"
|
||||
- "purchasesSameSku7d"
|
||||
- "purchasesSameSku14d"
|
||||
- "purchasesSameSku30d"
|
||||
- "unitsSoldClicks1d"
|
||||
- "unitsSoldClicks7d"
|
||||
- "unitsSoldClicks14d"
|
||||
- "unitsSoldClicks30d"
|
||||
- "sales1d"
|
||||
- "sales7d"
|
||||
- "sales14d"
|
||||
- "sales30d"
|
||||
- "attributedSalesSameSku1d"
|
||||
- "attributedSalesSameSku7d"
|
||||
- "attributedSalesSameSku14d"
|
||||
- "attributedSalesSameSku30d"
|
||||
- "unitsSoldSameSku1d"
|
||||
- "unitsSoldSameSku7d"
|
||||
- "unitsSoldSameSku14d"
|
||||
- "unitsSoldSameSku30d"
|
||||
reportTypeId: spTargeting
|
||||
filters:
|
||||
- field: "keywordType"
|
||||
values:
|
||||
- "TARGETING_EXPRESSION"
|
||||
- "TARGETING_EXPRESSION_PREDEFINED"
|
||||
timeUnit: DAILY
|
||||
format: GZIP_JSON
|
||||
sponsored_products_productads_report_stream:
|
||||
type: DeclarativeStream
|
||||
name: sponsored_products_productads_report_stream
|
||||
@@ -1995,6 +2667,65 @@ definitions:
|
||||
filters: []
|
||||
timeUnit: SUMMARY
|
||||
format: GZIP_JSON
|
||||
sponsored_products_productads_report_stream_daily:
|
||||
type: DeclarativeStream
|
||||
name: sponsored_products_productads_report_stream_daily
|
||||
primary_key: ["profileId", "reportDate", "adGroupName", "adId"]
|
||||
incremental_sync:
|
||||
$ref: "#/definitions/incremental_sync_report_datetime_cursor"
|
||||
transformations:
|
||||
$ref: "#/definitions/transformation_report_add_fields"
|
||||
retriever:
|
||||
$ref: "#/definitions/basic_async_retriever"
|
||||
creation_requester:
|
||||
$ref: "#/definitions/basic_async_retriever/creation_requester"
|
||||
request_body_json:
|
||||
name: "productAds report daily {{ stream_interval.start_time }}"
|
||||
startDate: "{{ stream_interval.start_time }}"
|
||||
endDate: "{{ stream_interval.end_time }}"
|
||||
configuration:
|
||||
adProduct: SPONSORED_PRODUCTS
|
||||
groupBy: ["advertiser"]
|
||||
columns:
|
||||
- "date"
|
||||
- "campaignName"
|
||||
- "campaignId"
|
||||
- "adGroupName"
|
||||
- "adGroupId"
|
||||
- "adId"
|
||||
- "impressions"
|
||||
- "clicks"
|
||||
- "cost"
|
||||
- "campaignBudgetCurrencyCode"
|
||||
- "advertisedAsin"
|
||||
- "purchases1d"
|
||||
- "purchases7d"
|
||||
- "purchases14d"
|
||||
- "purchases30d"
|
||||
- "purchasesSameSku1d"
|
||||
- "purchasesSameSku7d"
|
||||
- "purchasesSameSku14d"
|
||||
- "purchasesSameSku30d"
|
||||
- "unitsSoldClicks1d"
|
||||
- "unitsSoldClicks7d"
|
||||
- "unitsSoldClicks14d"
|
||||
- "unitsSoldClicks30d"
|
||||
- "sales1d"
|
||||
- "sales7d"
|
||||
- "sales14d"
|
||||
- "sales30d"
|
||||
- "attributedSalesSameSku1d"
|
||||
- "attributedSalesSameSku7d"
|
||||
- "attributedSalesSameSku14d"
|
||||
- "attributedSalesSameSku30d"
|
||||
- "unitsSoldSameSku1d"
|
||||
- "unitsSoldSameSku7d"
|
||||
- "unitsSoldSameSku14d"
|
||||
- "unitsSoldSameSku30d"
|
||||
reportTypeId: spAdvertisedProduct
|
||||
filters: []
|
||||
timeUnit: DAILY
|
||||
format: GZIP_JSON
|
||||
sponsored_products_asins_keywords_report_stream:
|
||||
type: DeclarativeStream
|
||||
name: sponsored_products_asins_keywords_report_stream
|
||||
@@ -2044,6 +2775,54 @@ definitions:
|
||||
filters: []
|
||||
timeUnit: SUMMARY
|
||||
format: GZIP_JSON
|
||||
sponsored_products_asins_keywords_report_stream_daily:
|
||||
type: DeclarativeStream
|
||||
name: sponsored_products_asins_keywords_report_stream_daily
|
||||
primary_key: ["profileId", "reportDate", "adGroupName", "advertisedAsin"]
|
||||
incremental_sync:
|
||||
$ref: "#/definitions/incremental_sync_report_datetime_cursor"
|
||||
transformations:
|
||||
$ref: "#/definitions/transformation_report_add_fields"
|
||||
retriever:
|
||||
$ref: "#/definitions/basic_async_retriever"
|
||||
creation_requester:
|
||||
$ref: "#/definitions/basic_async_retriever/creation_requester"
|
||||
request_body_json:
|
||||
name: "asins_keywords report daily {{ stream_interval.start_time }}"
|
||||
startDate: "{{ stream_interval.start_time }}"
|
||||
endDate: "{{ stream_interval.end_time }}"
|
||||
configuration:
|
||||
adProduct: SPONSORED_PRODUCTS
|
||||
groupBy: ["asin"]
|
||||
columns:
|
||||
- "date"
|
||||
- "campaignName"
|
||||
- "campaignId"
|
||||
- "adGroupName"
|
||||
- "adGroupId"
|
||||
- "keywordId"
|
||||
- "keyword"
|
||||
- "advertisedAsin"
|
||||
- "purchasedAsin"
|
||||
- "advertisedSku"
|
||||
- "campaignBudgetCurrencyCode"
|
||||
- "matchType"
|
||||
- "unitsSoldClicks1d"
|
||||
- "unitsSoldClicks7d"
|
||||
- "unitsSoldClicks14d"
|
||||
- "unitsSoldClicks30d"
|
||||
- "unitsSoldOtherSku1d"
|
||||
- "unitsSoldOtherSku7d"
|
||||
- "unitsSoldOtherSku14d"
|
||||
- "unitsSoldOtherSku30d"
|
||||
- "salesOtherSku1d"
|
||||
- "salesOtherSku7d"
|
||||
- "salesOtherSku14d"
|
||||
- "salesOtherSku30d"
|
||||
reportTypeId: spPurchasedProduct
|
||||
filters: []
|
||||
timeUnit: DAILY
|
||||
format: GZIP_JSON
|
||||
sponsored_products_asins_targets_report_stream:
|
||||
type: DeclarativeStream
|
||||
name: sponsored_products_asins_targets_report_stream
|
||||
@@ -2094,6 +2873,55 @@ definitions:
|
||||
filters: []
|
||||
timeUnit: SUMMARY
|
||||
format: GZIP_JSON
|
||||
sponsored_products_asins_targets_report_stream_daily:
|
||||
type: DeclarativeStream
|
||||
name: sponsored_products_asins_targets_report_stream_daily
|
||||
primary_key: ["profileId", "reportDate", "adGroupName", "advertisedAsin"]
|
||||
incremental_sync:
|
||||
$ref: "#/definitions/incremental_sync_report_datetime_cursor"
|
||||
transformations:
|
||||
$ref: "#/definitions/transformation_report_add_fields"
|
||||
retriever:
|
||||
$ref: "#/definitions/basic_async_retriever"
|
||||
creation_requester:
|
||||
$ref: "#/definitions/basic_async_retriever/creation_requester"
|
||||
request_body_json:
|
||||
name: "asins_targets report daily {{ stream_interval.start_time }}"
|
||||
startDate: "{{ stream_interval.start_time }}"
|
||||
endDate: "{{ stream_interval.end_time }}"
|
||||
configuration:
|
||||
adProduct: SPONSORED_PRODUCTS
|
||||
groupBy: ["asin"]
|
||||
columns:
|
||||
- "date"
|
||||
- "campaignName"
|
||||
- "campaignId"
|
||||
- "adGroupName"
|
||||
- "adGroupId"
|
||||
- "advertisedAsin"
|
||||
- "purchasedAsin"
|
||||
- "advertisedSku"
|
||||
- "campaignBudgetCurrencyCode"
|
||||
- "matchType"
|
||||
- "unitsSoldClicks1d"
|
||||
- "unitsSoldClicks7d"
|
||||
- "unitsSoldClicks14d"
|
||||
- "unitsSoldClicks30d"
|
||||
- "unitsSoldOtherSku1d"
|
||||
- "unitsSoldOtherSku7d"
|
||||
- "unitsSoldOtherSku14d"
|
||||
- "unitsSoldOtherSku30d"
|
||||
- "salesOtherSku1d"
|
||||
- "salesOtherSku7d"
|
||||
- "salesOtherSku14d"
|
||||
- "salesOtherSku30d"
|
||||
- "keywordId"
|
||||
- "targeting"
|
||||
- "keywordType"
|
||||
reportTypeId: spPurchasedProduct
|
||||
filters: []
|
||||
timeUnit: DAILY
|
||||
format: GZIP_JSON
|
||||
|
||||
incremental_sync_report_datetime_cursor:
|
||||
type: DatetimeBasedCursor
|
||||
@@ -2104,7 +2932,11 @@ definitions:
|
||||
lookback_window: P{{ config.get('look_back_window', 3) }}D
|
||||
start_datetime:
|
||||
type: MinMaxDatetime
|
||||
datetime: "{{ config.get('start_date', today_utc().strftime('%Y-%m-%d') ) }}"
|
||||
datetime: >-
|
||||
{%- set today = today_utc() - duration('P1D') -%}
|
||||
{%- set user_start_date = config.get('start_date', today.strftime('%Y-%m-%d')) -%}
|
||||
{%- set ninety_days_ago = today - duration('P90D') -%}
|
||||
"{{ max(user_start_date, ninety_days_ago.strftime('%Y-%m-%d')) }}"
|
||||
datetime_format: "%Y-%m-%d"
|
||||
end_datetime:
|
||||
datetime: "{{ today_utc() }}"
|
||||
@@ -2178,7 +3010,12 @@ definitions:
|
||||
Amazon-Advertising-API-ClientId: '{{ config["client_id"] }}'
|
||||
request_body_json:
|
||||
name: "purchasedAsin report {{ stream_interval.start_time }}"
|
||||
startDate: "{{ stream_interval.start_time }}"
|
||||
startDate: >
|
||||
{% if stream_interval.start_time < config['start_date'] %}
|
||||
{{ config['start_date'] }}
|
||||
{% else %}
|
||||
{{ stream_interval.start_time }}
|
||||
{% endif %}
|
||||
endDate: "{{ stream_interval.end_time }}"
|
||||
configuration:
|
||||
adProduct: OVERRIDDEN_REPORT_TYPE # Placeholder value. Each report stream overrides the adProduct value to the respective report name
|
||||
@@ -2271,6 +3108,20 @@ streams:
|
||||
- $ref: "#/definitions/streams/sponsored_products_asins_keywords_report_stream"
|
||||
- $ref: "#/definitions/streams/sponsored_products_asins_targets_report_stream"
|
||||
|
||||
- $ref: "#/definitions/streams/sponsored_brands_v3_report_stream_daily"
|
||||
- $ref: "#/definitions/streams/sponsored_display_campaigns_report_stream_daily"
|
||||
- $ref: "#/definitions/streams/sponsored_display_adgroups_report_stream_daily"
|
||||
- $ref: "#/definitions/streams/sponsored_display_productads_report_stream_daily"
|
||||
- $ref: "#/definitions/streams/sponsored_display_targets_report_stream_daily"
|
||||
- $ref: "#/definitions/streams/sponsored_display_asins_report_stream_daily"
|
||||
- $ref: "#/definitions/streams/sponsored_products_campaigns_report_stream_daily"
|
||||
- $ref: "#/definitions/streams/sponsored_products_adgroups_report_stream_daily"
|
||||
- $ref: "#/definitions/streams/sponsored_products_keywords_report_stream_daily"
|
||||
- $ref: "#/definitions/streams/sponsored_products_targets_report_stream_daily"
|
||||
- $ref: "#/definitions/streams/sponsored_products_productads_report_stream_daily"
|
||||
- $ref: "#/definitions/streams/sponsored_products_asins_keywords_report_stream_daily"
|
||||
- $ref: "#/definitions/streams/sponsored_products_asins_targets_report_stream_daily"
|
||||
|
||||
concurrency_level:
|
||||
type: ConcurrencyLevel
|
||||
default_concurrency: 10
|
||||
|
||||
@@ -0,0 +1,26 @@
|
||||
{
|
||||
"$schema": "http://json-schema.org/draft-07/schema#",
|
||||
"properties": {
|
||||
"date": { "type": ["null", "string"] },
|
||||
"profileId": { "type": ["null", "integer"] },
|
||||
"reportDate": { "type": ["null", "string"] },
|
||||
"attributionType": { "type": ["null", "string"] },
|
||||
"campaignName": { "type": ["null", "string"] },
|
||||
"newToBrandSales14d": { "type": ["null", "number"] },
|
||||
"orders14d": { "type": ["null", "integer"] },
|
||||
"productName": { "type": ["null", "string"] },
|
||||
"sales14d": { "type": ["null", "number"] },
|
||||
"newToBrandPurchasesPercentage14d": { "type": ["null", "number"] },
|
||||
"purchasedAsin": { "type": ["null", "string"] },
|
||||
"newToBrandSalesPercentage14d": { "type": ["null", "number"] },
|
||||
"productCategory": { "type": ["null", "string"] },
|
||||
"newToBrandPurchases14d": { "type": ["null", "integer"] },
|
||||
"newToBrandUnitsSoldPercentage14d": { "type": ["null", "number"] },
|
||||
"unitsSold14d": { "type": ["null", "integer"] },
|
||||
"adGroupName": { "type": ["null", "string"] },
|
||||
"newToBrandUnitsSold14d": { "type": ["null", "integer"] },
|
||||
"campaignBudgetCurrencyCode": { "type": ["null", "string"] }
|
||||
},
|
||||
"title": "sponsored_brands_v3_report_stream_daily",
|
||||
"type": ["null", "object"]
|
||||
}
|
||||
@@ -0,0 +1,202 @@
|
||||
{
|
||||
"$schema": "http://json-schema.org/draft-07/schema#",
|
||||
"properties": {
|
||||
"date": {
|
||||
"type": ["null", "string"]
|
||||
},
|
||||
"profileId": {
|
||||
"type": ["null", "integer"]
|
||||
},
|
||||
"reportDate": {
|
||||
"type": ["null", "string"]
|
||||
},
|
||||
"adGroupId": {
|
||||
"type": ["null", "integer"]
|
||||
},
|
||||
"addToCart": {
|
||||
"type": ["null", "integer"]
|
||||
},
|
||||
"addToCartClicks": {
|
||||
"type": ["null", "integer"]
|
||||
},
|
||||
"addToCartRate": {
|
||||
"type": ["null", "number"]
|
||||
},
|
||||
"addToCartViews": {
|
||||
"type": ["null", "integer"]
|
||||
},
|
||||
"adGroupName": {
|
||||
"type": ["null", "string"]
|
||||
},
|
||||
"addToList": {
|
||||
"type": ["null", "integer"]
|
||||
},
|
||||
"addToListFromClicks": {
|
||||
"type": ["null", "integer"]
|
||||
},
|
||||
"addToListFromViews": {
|
||||
"type": ["null", "integer"]
|
||||
},
|
||||
"qualifiedBorrows": {
|
||||
"type": ["null", "integer"]
|
||||
},
|
||||
"qualifiedBorrowsFromClicks": {
|
||||
"type": ["null", "integer"]
|
||||
},
|
||||
"qualifiedBorrowsFromViews": {
|
||||
"type": ["null", "integer"]
|
||||
},
|
||||
"royaltyQualifiedBorrows": {
|
||||
"type": ["null", "integer"]
|
||||
},
|
||||
"royaltyQualifiedBorrowsFromClicks": {
|
||||
"type": ["null", "integer"]
|
||||
},
|
||||
"royaltyQualifiedBorrowsFromViews": {
|
||||
"type": ["null", "integer"]
|
||||
},
|
||||
"bidOptimization": {
|
||||
"type": ["null", "string"]
|
||||
},
|
||||
"brandedSearches": {
|
||||
"type": ["null", "integer"]
|
||||
},
|
||||
"brandedSearchesClicks": {
|
||||
"type": ["null", "integer"]
|
||||
},
|
||||
"brandedSearchesViews": {
|
||||
"type": ["null", "integer"]
|
||||
},
|
||||
"brandedSearchRate": {
|
||||
"type": ["null", "number"]
|
||||
},
|
||||
"campaignBudgetCurrencyCode": {
|
||||
"type": ["null", "string"]
|
||||
},
|
||||
"campaignId": {
|
||||
"type": ["null", "integer"]
|
||||
},
|
||||
"campaignName": {
|
||||
"type": ["null", "string"]
|
||||
},
|
||||
"clicks": {
|
||||
"type": ["null", "integer"]
|
||||
},
|
||||
"cost": {
|
||||
"type": ["null", "number"]
|
||||
},
|
||||
"detailPageViews": {
|
||||
"type": ["null", "integer"]
|
||||
},
|
||||
"detailPageViewsClicks": {
|
||||
"type": ["null", "integer"]
|
||||
},
|
||||
"eCPAddToCart": {
|
||||
"type": ["null", "number"]
|
||||
},
|
||||
"eCPBrandSearch": {
|
||||
"type": ["null", "number"]
|
||||
},
|
||||
"impressions": {
|
||||
"type": ["null", "integer"]
|
||||
},
|
||||
"impressionsViews": {
|
||||
"type": ["null", "integer"]
|
||||
},
|
||||
"leadFormOpens": {
|
||||
"type": ["null", "integer"]
|
||||
},
|
||||
"leads": {
|
||||
"type": ["null", "integer"]
|
||||
},
|
||||
"linkOuts": {
|
||||
"type": ["null", "integer"]
|
||||
},
|
||||
"newToBrandPurchases": {
|
||||
"type": ["null", "integer"]
|
||||
},
|
||||
"newToBrandPurchasesClicks": {
|
||||
"type": ["null", "integer"]
|
||||
},
|
||||
"newToBrandSales": {
|
||||
"type": ["null", "number"]
|
||||
},
|
||||
"newToBrandSalesClicks": {
|
||||
"type": ["null", "number"]
|
||||
},
|
||||
"newToBrandUnitsSold": {
|
||||
"type": ["null", "integer"]
|
||||
},
|
||||
"newToBrandUnitsSoldClicks": {
|
||||
"type": ["null", "integer"]
|
||||
},
|
||||
"purchases": {
|
||||
"type": ["null", "integer"]
|
||||
},
|
||||
"purchasesClicks": {
|
||||
"type": ["null", "integer"]
|
||||
},
|
||||
"purchasesPromotedClicks": {
|
||||
"type": ["null", "integer"]
|
||||
},
|
||||
"sales": {
|
||||
"type": ["null", "number"]
|
||||
},
|
||||
"salesClicks": {
|
||||
"type": ["null", "number"]
|
||||
},
|
||||
"salesPromotedClicks": {
|
||||
"type": ["null", "number"]
|
||||
},
|
||||
"unitsSold": {
|
||||
"type": ["null", "integer"]
|
||||
},
|
||||
"unitsSoldClicks": {
|
||||
"type": ["null", "integer"]
|
||||
},
|
||||
"videoCompleteViews": {
|
||||
"type": ["null", "integer"]
|
||||
},
|
||||
"videoFirstQuartileViews": {
|
||||
"type": ["null", "integer"]
|
||||
},
|
||||
"videoMidpointViews": {
|
||||
"type": ["null", "integer"]
|
||||
},
|
||||
"videoThirdQuartileViews": {
|
||||
"type": ["null", "integer"]
|
||||
},
|
||||
"videoUnmutes": {
|
||||
"type": ["null", "integer"]
|
||||
},
|
||||
"viewabilityRate": {
|
||||
"type": ["null", "number"]
|
||||
},
|
||||
"viewClickThroughRate": {
|
||||
"type": ["null", "number"]
|
||||
},
|
||||
"cumulativeReach": {
|
||||
"type": ["null", "string"]
|
||||
},
|
||||
"impressionsFrequencyAverage": {
|
||||
"type": ["null", "number"]
|
||||
},
|
||||
"newToBrandDetailPageViewClicks": {
|
||||
"type": ["null", "integer"]
|
||||
},
|
||||
"newToBrandDetailPageViewRate": {
|
||||
"type": ["null", "number"]
|
||||
},
|
||||
"newToBrandDetailPageViews": {
|
||||
"type": ["null", "integer"]
|
||||
},
|
||||
"newToBrandDetailPageViewViews": {
|
||||
"type": ["null", "integer"]
|
||||
},
|
||||
"newToBrandECPDetailPageView": {
|
||||
"type": ["null", "number"]
|
||||
}
|
||||
},
|
||||
"title": "sponsored_display_adgroups_report_stream_daily",
|
||||
"type": ["null", "object"]
|
||||
}
|
||||
@@ -0,0 +1,86 @@
|
||||
{
|
||||
"$schema": "http://json-schema.org/draft-07/schema#",
|
||||
"properties": {
|
||||
"date": {
|
||||
"type": ["null", "string"]
|
||||
},
|
||||
"profileId": {
|
||||
"type": ["null", "integer"]
|
||||
},
|
||||
"reportDate": {
|
||||
"type": ["null", "string"]
|
||||
},
|
||||
"promotedAsin": {
|
||||
"type": ["null", "string"]
|
||||
},
|
||||
"adGroupId": {
|
||||
"type": ["null", "integer"]
|
||||
},
|
||||
"adGroupName": {
|
||||
"type": ["null", "string"]
|
||||
},
|
||||
"asinBrandHalo": {
|
||||
"type": ["null", "string"]
|
||||
},
|
||||
"addToList": {
|
||||
"type": ["null", "integer"]
|
||||
},
|
||||
"addToListFromClicks": {
|
||||
"type": ["null", "integer"]
|
||||
},
|
||||
"qualifiedBorrowsFromClicks": {
|
||||
"type": ["null", "integer"]
|
||||
},
|
||||
"royaltyQualifiedBorrowsFromClicks": {
|
||||
"type": ["null", "integer"]
|
||||
},
|
||||
"addToListFromViews": {
|
||||
"type": ["null", "integer"]
|
||||
},
|
||||
"qualifiedBorrows": {
|
||||
"type": ["null", "integer"]
|
||||
},
|
||||
"qualifiedBorrowsFromViews": {
|
||||
"type": ["null", "integer"]
|
||||
},
|
||||
"royaltyQualifiedBorrows": {
|
||||
"type": ["null", "integer"]
|
||||
},
|
||||
"royaltyQualifiedBorrowsFromViews": {
|
||||
"type": ["null", "integer"]
|
||||
},
|
||||
"campaignBudgetCurrencyCode": {
|
||||
"type": ["null", "string"]
|
||||
},
|
||||
"campaignId": {
|
||||
"type": ["null", "integer"]
|
||||
},
|
||||
"campaignName": {
|
||||
"type": ["null", "string"]
|
||||
},
|
||||
"conversionsBrandHalo": {
|
||||
"type": ["null", "integer"]
|
||||
},
|
||||
"conversionsBrandHaloClicks": {
|
||||
"type": ["null", "integer"]
|
||||
},
|
||||
"promotedSku": {
|
||||
"type": ["null", "string"]
|
||||
},
|
||||
"salesBrandHalo": {
|
||||
"type": ["null", "integer"]
|
||||
},
|
||||
"salesBrandHaloClicks": {
|
||||
"type": ["null", "integer"]
|
||||
},
|
||||
|
||||
"unitsSoldBrandHalo": {
|
||||
"type": ["null", "integer"]
|
||||
},
|
||||
"unitsSoldBrandHaloClicks": {
|
||||
"type": ["null", "integer"]
|
||||
}
|
||||
},
|
||||
"title": "sponsored_display_asins_report_stream_daily",
|
||||
"type": ["null", "object"]
|
||||
}
|
||||
@@ -0,0 +1,202 @@
|
||||
{
|
||||
"$schema": "http://json-schema.org/draft-07/schema#",
|
||||
"properties": {
|
||||
"date": {
|
||||
"type": ["null", "string"]
|
||||
},
|
||||
"profileId": {
|
||||
"type": ["null", "integer"]
|
||||
},
|
||||
"reportDate": {
|
||||
"type": ["null", "string"]
|
||||
},
|
||||
"campaignId": {
|
||||
"type": ["null", "integer"]
|
||||
},
|
||||
"addToCart": {
|
||||
"type": ["null", "integer"]
|
||||
},
|
||||
"addToCartClicks": {
|
||||
"type": ["null", "integer"]
|
||||
},
|
||||
"addToCartRate": {
|
||||
"type": ["null", "number"]
|
||||
},
|
||||
"addToCartViews": {
|
||||
"type": ["null", "integer"]
|
||||
},
|
||||
"addToList": {
|
||||
"type": ["null", "integer"]
|
||||
},
|
||||
"addToListFromClicks": {
|
||||
"type": ["null", "integer"]
|
||||
},
|
||||
"addToListFromViews": {
|
||||
"type": ["null", "integer"]
|
||||
},
|
||||
"qualifiedBorrows": {
|
||||
"type": ["null", "integer"]
|
||||
},
|
||||
"qualifiedBorrowsFromClicks": {
|
||||
"type": ["null", "integer"]
|
||||
},
|
||||
"qualifiedBorrowsFromViews": {
|
||||
"type": ["null", "integer"]
|
||||
},
|
||||
"royaltyQualifiedBorrows": {
|
||||
"type": ["null", "integer"]
|
||||
},
|
||||
"royaltyQualifiedBorrowsFromClicks": {
|
||||
"type": ["null", "integer"]
|
||||
},
|
||||
"royaltyQualifiedBorrowsFromViews": {
|
||||
"type": ["null", "integer"]
|
||||
},
|
||||
"brandedSearches": {
|
||||
"type": ["null", "integer"]
|
||||
},
|
||||
"brandedSearchesClicks": {
|
||||
"type": ["null", "integer"]
|
||||
},
|
||||
"brandedSearchesViews": {
|
||||
"type": ["null", "integer"]
|
||||
},
|
||||
"brandedSearchRate": {
|
||||
"type": ["null", "number"]
|
||||
},
|
||||
"campaignBudgetCurrencyCode": {
|
||||
"type": ["null", "string"]
|
||||
},
|
||||
"campaignName": {
|
||||
"type": ["null", "string"]
|
||||
},
|
||||
"clicks": {
|
||||
"type": ["null", "integer"]
|
||||
},
|
||||
"cost": {
|
||||
"type": ["null", "number"]
|
||||
},
|
||||
"detailPageViews": {
|
||||
"type": ["null", "integer"]
|
||||
},
|
||||
"detailPageViewsClicks": {
|
||||
"type": ["null", "integer"]
|
||||
},
|
||||
"eCPAddToCart": {
|
||||
"type": ["null", "number"]
|
||||
},
|
||||
"eCPBrandSearch": {
|
||||
"type": ["null", "number"]
|
||||
},
|
||||
"impressions": {
|
||||
"type": ["null", "integer"]
|
||||
},
|
||||
"impressionsViews": {
|
||||
"type": ["null", "integer"]
|
||||
},
|
||||
"leadFormOpens": {
|
||||
"type": ["null", "integer"]
|
||||
},
|
||||
"leads": {
|
||||
"type": ["null", "integer"]
|
||||
},
|
||||
"linkOuts": {
|
||||
"type": ["null", "integer"]
|
||||
},
|
||||
"newToBrandPurchases": {
|
||||
"type": ["null", "integer"]
|
||||
},
|
||||
"newToBrandPurchasesClicks": {
|
||||
"type": ["null", "integer"]
|
||||
},
|
||||
"newToBrandSalesClicks": {
|
||||
"type": ["null", "number"]
|
||||
},
|
||||
"newToBrandUnitsSold": {
|
||||
"type": ["null", "integer"]
|
||||
},
|
||||
"newToBrandUnitsSoldClicks": {
|
||||
"type": ["null", "integer"]
|
||||
},
|
||||
"purchases": {
|
||||
"type": ["null", "integer"]
|
||||
},
|
||||
"purchasesClicks": {
|
||||
"type": ["null", "integer"]
|
||||
},
|
||||
"purchasesPromotedClicks": {
|
||||
"type": ["null", "integer"]
|
||||
},
|
||||
"sales": {
|
||||
"type": ["null", "number"]
|
||||
},
|
||||
"salesClicks": {
|
||||
"type": ["null", "number"]
|
||||
},
|
||||
"salesPromotedClicks": {
|
||||
"type": ["null", "number"]
|
||||
},
|
||||
"unitsSold": {
|
||||
"type": ["null", "integer"]
|
||||
},
|
||||
"unitsSoldClicks": {
|
||||
"type": ["null", "integer"]
|
||||
},
|
||||
"videoCompleteViews": {
|
||||
"type": ["null", "integer"]
|
||||
},
|
||||
"videoFirstQuartileViews": {
|
||||
"type": ["null", "integer"]
|
||||
},
|
||||
"videoMidpointViews": {
|
||||
"type": ["null", "integer"]
|
||||
},
|
||||
"videoThirdQuartileViews": {
|
||||
"type": ["null", "integer"]
|
||||
},
|
||||
"videoUnmutes": {
|
||||
"type": ["null", "integer"]
|
||||
},
|
||||
"viewabilityRate": {
|
||||
"type": ["null", "number"]
|
||||
},
|
||||
"viewClickThroughRate": {
|
||||
"type": ["null", "number"]
|
||||
},
|
||||
"campaignBudgetAmount": {
|
||||
"type": ["null", "number"]
|
||||
},
|
||||
"campaignStatus": {
|
||||
"type": ["null", "string"]
|
||||
},
|
||||
"costType": {
|
||||
"type": ["null", "string"]
|
||||
},
|
||||
"cumulativeReach": {
|
||||
"type": ["null", "string"]
|
||||
},
|
||||
"impressionsFrequencyAverage": {
|
||||
"type": ["null", "number"]
|
||||
},
|
||||
"newToBrandDetailPageViewClicks": {
|
||||
"type": ["null", "integer"]
|
||||
},
|
||||
"newToBrandDetailPageViewRate": {
|
||||
"type": ["null", "number"]
|
||||
},
|
||||
"newToBrandDetailPageViews": {
|
||||
"type": ["null", "integer"]
|
||||
},
|
||||
"newToBrandDetailPageViewViews": {
|
||||
"type": ["null", "integer"]
|
||||
},
|
||||
"newToBrandECPDetailPageView": {
|
||||
"type": ["null", "number"]
|
||||
},
|
||||
"newToBrandSales": {
|
||||
"type": ["null", "number"]
|
||||
}
|
||||
},
|
||||
"title": "sponsored_display_campaigns_report_stream_daily",
|
||||
"type": ["null", "object"]
|
||||
}
|
||||
@@ -0,0 +1,212 @@
|
||||
{
|
||||
"$schema": "http://json-schema.org/draft-07/schema#",
|
||||
"properties": {
|
||||
"date": {
|
||||
"type": ["null", "string"]
|
||||
},
|
||||
"profileId": {
|
||||
"type": ["null", "integer"]
|
||||
},
|
||||
"reportDate": {
|
||||
"type": ["null", "string"]
|
||||
},
|
||||
"adId": {
|
||||
"type": ["null", "integer"]
|
||||
},
|
||||
|
||||
"addToCart": {
|
||||
"type": ["null", "integer"]
|
||||
},
|
||||
"addToCartRate": {
|
||||
"type": ["null", "number"]
|
||||
},
|
||||
"addToCartViews": {
|
||||
"type": ["null", "integer"]
|
||||
},
|
||||
"addToCartClicks": {
|
||||
"type": ["null", "integer"]
|
||||
},
|
||||
"adGroupId": {
|
||||
"type": ["null", "integer"]
|
||||
},
|
||||
"adGroupName": {
|
||||
"type": ["null", "string"]
|
||||
},
|
||||
"addToList": {
|
||||
"type": ["null", "integer"]
|
||||
},
|
||||
"addToListFromClicks": {
|
||||
"type": ["null", "integer"]
|
||||
},
|
||||
"qualifiedBorrows": {
|
||||
"type": ["null", "integer"]
|
||||
},
|
||||
"royaltyQualifiedBorrows": {
|
||||
"type": ["null", "integer"]
|
||||
},
|
||||
"addToListFromViews": {
|
||||
"type": ["null", "integer"]
|
||||
},
|
||||
"qualifiedBorrowsFromClicks": {
|
||||
"type": ["null", "integer"]
|
||||
},
|
||||
"qualifiedBorrowsFromViews": {
|
||||
"type": ["null", "integer"]
|
||||
},
|
||||
"royaltyQualifiedBorrowsFromClicks": {
|
||||
"type": ["null", "integer"]
|
||||
},
|
||||
"royaltyQualifiedBorrowsFromViews": {
|
||||
"type": ["null", "integer"]
|
||||
},
|
||||
"bidOptimization": {
|
||||
"type": ["null", "string"]
|
||||
},
|
||||
"brandedSearches": {
|
||||
"type": ["null", "integer"]
|
||||
},
|
||||
"brandedSearchesClicks": {
|
||||
"type": ["null", "integer"]
|
||||
},
|
||||
"brandedSearchesViews": {
|
||||
"type": ["null", "integer"]
|
||||
},
|
||||
"brandedSearchRate": {
|
||||
"type": ["null", "number"]
|
||||
},
|
||||
"campaignBudgetCurrencyCode": {
|
||||
"type": ["null", "string"]
|
||||
},
|
||||
"campaignId": {
|
||||
"type": ["null", "integer"]
|
||||
},
|
||||
"campaignName": {
|
||||
"type": ["null", "string"]
|
||||
},
|
||||
"clicks": {
|
||||
"type": ["null", "integer"]
|
||||
},
|
||||
"cost": {
|
||||
"type": ["null", "number"]
|
||||
},
|
||||
"cumulativeReach": {
|
||||
"type": ["null", "string"]
|
||||
},
|
||||
"detailPageViews": {
|
||||
"type": ["null", "integer"]
|
||||
},
|
||||
"detailPageViewsClicks": {
|
||||
"type": ["null", "integer"]
|
||||
},
|
||||
"eCPAddToCart": {
|
||||
"type": ["null", "number"]
|
||||
},
|
||||
"eCPBrandSearch": {
|
||||
"type": ["null", "number"]
|
||||
},
|
||||
"impressions": {
|
||||
"type": ["null", "integer"]
|
||||
},
|
||||
"impressionsFrequencyAverage": {
|
||||
"type": ["null", "number"]
|
||||
},
|
||||
"impressionsViews": {
|
||||
"type": ["null", "integer"]
|
||||
},
|
||||
"leadFormOpens": {
|
||||
"type": ["null", "integer"]
|
||||
},
|
||||
"leads": {
|
||||
"type": ["null", "integer"]
|
||||
},
|
||||
"linkOuts": {
|
||||
"type": ["null", "integer"]
|
||||
},
|
||||
"newToBrandDetailPageViewClicks": {
|
||||
"type": ["null", "integer"]
|
||||
},
|
||||
"newToBrandDetailPageViewRate": {
|
||||
"type": ["null", "number"]
|
||||
},
|
||||
"newToBrandDetailPageViews": {
|
||||
"type": ["null", "integer"]
|
||||
},
|
||||
"newToBrandDetailPageViewViews": {
|
||||
"type": ["null", "integer"]
|
||||
},
|
||||
"newToBrandECPDetailPageView": {
|
||||
"type": ["null", "number"]
|
||||
},
|
||||
"newToBrandPurchases": {
|
||||
"type": ["null", "integer"]
|
||||
},
|
||||
"newToBrandPurchasesClicks": {
|
||||
"type": ["null", "integer"]
|
||||
},
|
||||
"newToBrandSales": {
|
||||
"type": ["null", "number"]
|
||||
},
|
||||
"newToBrandSalesClicks": {
|
||||
"type": ["null", "number"]
|
||||
},
|
||||
"newToBrandUnitsSold": {
|
||||
"type": ["null", "integer"]
|
||||
},
|
||||
"newToBrandUnitsSoldClicks": {
|
||||
"type": ["null", "integer"]
|
||||
},
|
||||
"promotedAsin": {
|
||||
"type": ["null", "string"]
|
||||
},
|
||||
"promotedSku": {
|
||||
"type": ["null", "string"]
|
||||
},
|
||||
"purchases": {
|
||||
"type": ["null", "integer"]
|
||||
},
|
||||
"purchasesClicks": {
|
||||
"type": ["null", "integer"]
|
||||
},
|
||||
"purchasesPromotedClicks": {
|
||||
"type": ["null", "integer"]
|
||||
},
|
||||
"sales": {
|
||||
"type": ["null", "number"]
|
||||
},
|
||||
"salesClicks": {
|
||||
"type": ["null", "number"]
|
||||
},
|
||||
"salesPromotedClicks": {
|
||||
"type": ["null", "number"]
|
||||
},
|
||||
"unitsSold": {
|
||||
"type": ["null", "integer"]
|
||||
},
|
||||
"unitsSoldClicks": {
|
||||
"type": ["null", "integer"]
|
||||
},
|
||||
"videoCompleteViews": {
|
||||
"type": ["null", "integer"]
|
||||
},
|
||||
"videoFirstQuartileViews": {
|
||||
"type": ["null", "integer"]
|
||||
},
|
||||
"videoMidpointViews": {
|
||||
"type": ["null", "integer"]
|
||||
},
|
||||
"videoThirdQuartileViews": {
|
||||
"type": ["null", "integer"]
|
||||
},
|
||||
"videoUnmutes": {
|
||||
"type": ["null", "integer"]
|
||||
},
|
||||
"viewabilityRate": {
|
||||
"type": ["null", "number"]
|
||||
},
|
||||
"viewClickThroughRate": {
|
||||
"type": ["null", "number"]
|
||||
}
|
||||
},
|
||||
"title": "sponsored_display_productads_report_stream_daily",
|
||||
"type": ["null", "object"]
|
||||
}
|
||||
@@ -0,0 +1,187 @@
|
||||
{
|
||||
"$schema": "http://json-schema.org/draft-07/schema#",
|
||||
"date": {
|
||||
"type": ["null", "string"]
|
||||
},
|
||||
"properties": {
|
||||
"profileId": {
|
||||
"type": ["null", "integer"]
|
||||
},
|
||||
"reportDate": {
|
||||
"type": ["null", "string"]
|
||||
},
|
||||
"targetingId": {
|
||||
"type": ["null", "integer"]
|
||||
},
|
||||
"addToCart": {
|
||||
"type": ["null", "integer"]
|
||||
},
|
||||
"addToCartClicks": {
|
||||
"type": ["null", "integer"]
|
||||
},
|
||||
"addToCartRate": {
|
||||
"type": ["null", "number"]
|
||||
},
|
||||
"addToCartViews": {
|
||||
"type": ["null", "integer"]
|
||||
},
|
||||
"adGroupId": {
|
||||
"type": ["null", "integer"]
|
||||
},
|
||||
"adGroupName": {
|
||||
"type": ["null", "string"]
|
||||
},
|
||||
"addToList": {
|
||||
"type": ["null", "integer"]
|
||||
},
|
||||
"addToListFromClicks": {
|
||||
"type": ["null", "integer"]
|
||||
},
|
||||
"addToListFromViews": {
|
||||
"type": ["null", "integer"]
|
||||
},
|
||||
"qualifiedBorrows": {
|
||||
"type": ["null", "integer"]
|
||||
},
|
||||
"qualifiedBorrowsFromClicks": {
|
||||
"type": ["null", "integer"]
|
||||
},
|
||||
"qualifiedBorrowsFromViews": {
|
||||
"type": ["null", "integer"]
|
||||
},
|
||||
"royaltyQualifiedBorrows": {
|
||||
"type": ["null", "integer"]
|
||||
},
|
||||
"royaltyQualifiedBorrowsFromClicks": {
|
||||
"type": ["null", "integer"]
|
||||
},
|
||||
"royaltyQualifiedBorrowsFromViews": {
|
||||
"type": ["null", "integer"]
|
||||
},
|
||||
"brandedSearches": {
|
||||
"type": ["null", "integer"]
|
||||
},
|
||||
"brandedSearchesClicks": {
|
||||
"type": ["null", "integer"]
|
||||
},
|
||||
"brandedSearchesViews": {
|
||||
"type": ["null", "integer"]
|
||||
},
|
||||
"brandedSearchRate": {
|
||||
"type": ["null", "number"]
|
||||
},
|
||||
"campaignBudgetCurrencyCode": {
|
||||
"type": ["null", "string"]
|
||||
},
|
||||
"campaignId": {
|
||||
"type": ["null", "integer"]
|
||||
},
|
||||
"campaignName": {
|
||||
"type": ["null", "string"]
|
||||
},
|
||||
"clicks": {
|
||||
"type": ["null", "integer"]
|
||||
},
|
||||
"cost": {
|
||||
"type": ["null", "number"]
|
||||
},
|
||||
"detailPageViews": {
|
||||
"type": ["null", "integer"]
|
||||
},
|
||||
"detailPageViewsClicks": {
|
||||
"type": ["null", "integer"]
|
||||
},
|
||||
"eCPAddToCart": {
|
||||
"type": ["null", "number"]
|
||||
},
|
||||
"eCPBrandSearch": {
|
||||
"type": ["null", "number"]
|
||||
},
|
||||
"impressions": {
|
||||
"type": ["null", "integer"]
|
||||
},
|
||||
"impressionsViews": {
|
||||
"type": ["null", "integer"]
|
||||
},
|
||||
"leadFormOpens": {
|
||||
"type": ["null", "integer"]
|
||||
},
|
||||
"leads": {
|
||||
"type": ["null", "integer"]
|
||||
},
|
||||
"linkOuts": {
|
||||
"type": ["null", "integer"]
|
||||
},
|
||||
"newToBrandPurchases": {
|
||||
"type": ["null", "integer"]
|
||||
},
|
||||
"newToBrandPurchasesClicks": {
|
||||
"type": ["null", "integer"]
|
||||
},
|
||||
"newToBrandSales": {
|
||||
"type": ["null", "number"]
|
||||
},
|
||||
"newToBrandSalesClicks": {
|
||||
"type": ["null", "number"]
|
||||
},
|
||||
"newToBrandUnitsSold": {
|
||||
"type": ["null", "integer"]
|
||||
},
|
||||
"newToBrandUnitsSoldClicks": {
|
||||
"type": ["null", "integer"]
|
||||
},
|
||||
"purchases": {
|
||||
"type": ["null", "integer"]
|
||||
},
|
||||
"purchasesClicks": {
|
||||
"type": ["null", "integer"]
|
||||
},
|
||||
"purchasesPromotedClicks": {
|
||||
"type": ["null", "integer"]
|
||||
},
|
||||
"sales": {
|
||||
"type": ["null", "number"]
|
||||
},
|
||||
"salesClicks": {
|
||||
"type": ["null", "number"]
|
||||
},
|
||||
"salesPromotedClicks": {
|
||||
"type": ["null", "number"]
|
||||
},
|
||||
"targetingExpression": {
|
||||
"type": ["null", "string"]
|
||||
},
|
||||
"targetingText": {
|
||||
"type": ["null", "string"]
|
||||
},
|
||||
"unitsSold": {
|
||||
"type": ["null", "integer"]
|
||||
},
|
||||
"unitsSoldClicks": {
|
||||
"type": ["null", "integer"]
|
||||
},
|
||||
"videoCompleteViews": {
|
||||
"type": ["null", "integer"]
|
||||
},
|
||||
"videoFirstQuartileViews": {
|
||||
"type": ["null", "integer"]
|
||||
},
|
||||
"videoMidpointViews": {
|
||||
"type": ["null", "integer"]
|
||||
},
|
||||
"videoThirdQuartileViews": {
|
||||
"type": ["null", "integer"]
|
||||
},
|
||||
"videoUnmutes": {
|
||||
"type": ["null", "integer"]
|
||||
},
|
||||
"viewabilityRate": {
|
||||
"type": ["null", "number"]
|
||||
},
|
||||
"viewClickThroughRate": {
|
||||
"type": ["null", "number"]
|
||||
}
|
||||
},
|
||||
"title": "sponsored_display_targets_report_stream_daily",
|
||||
"type": ["null", "object"]
|
||||
}
|
||||
@@ -0,0 +1,107 @@
|
||||
{
|
||||
"$schema": "http://json-schema.org/draft-07/schema#",
|
||||
"properties": {
|
||||
"date": { "type": ["null", "string"] },
|
||||
"profileId": {
|
||||
"type": ["null", "integer"]
|
||||
},
|
||||
"reportDate": {
|
||||
"type": ["null", "string"]
|
||||
},
|
||||
"adGroupId": {
|
||||
"type": ["null", "integer"]
|
||||
},
|
||||
"campaignName": {
|
||||
"type": ["null", "string"]
|
||||
},
|
||||
"campaignId": {
|
||||
"type": ["null", "integer"]
|
||||
},
|
||||
"adGroupName": {
|
||||
"type": ["null", "string"]
|
||||
},
|
||||
"impressions": {
|
||||
"type": ["null", "integer"]
|
||||
},
|
||||
"clicks": {
|
||||
"type": ["null", "integer"]
|
||||
},
|
||||
"cost": {
|
||||
"type": ["null", "number"]
|
||||
},
|
||||
"purchases1d": {
|
||||
"type": ["null", "integer"]
|
||||
},
|
||||
"purchases7d": {
|
||||
"type": ["null", "integer"]
|
||||
},
|
||||
"purchases14d": {
|
||||
"type": ["null", "integer"]
|
||||
},
|
||||
"purchases30d": {
|
||||
"type": ["null", "integer"]
|
||||
},
|
||||
"purchasesSameSku1d": {
|
||||
"type": ["null", "integer"]
|
||||
},
|
||||
"purchasesSameSku7d": {
|
||||
"type": ["null", "integer"]
|
||||
},
|
||||
"purchasesSameSku14d": {
|
||||
"type": ["null", "integer"]
|
||||
},
|
||||
"purchasesSameSku30d": {
|
||||
"type": ["null", "integer"]
|
||||
},
|
||||
"unitsSoldClicks1d": {
|
||||
"type": ["null", "integer"]
|
||||
},
|
||||
"unitsSoldClicks7d": {
|
||||
"type": ["null", "integer"]
|
||||
},
|
||||
"unitsSoldClicks14d": {
|
||||
"type": ["null", "integer"]
|
||||
},
|
||||
"unitsSoldClicks30d": {
|
||||
"type": ["null", "integer"]
|
||||
},
|
||||
"sales1d": {
|
||||
"type": ["null", "number"]
|
||||
},
|
||||
"sales7d": {
|
||||
"type": ["null", "number"]
|
||||
},
|
||||
"sales14d": {
|
||||
"type": ["null", "number"]
|
||||
},
|
||||
"sales30d": {
|
||||
"type": ["null", "number"]
|
||||
},
|
||||
"attributedSalesSameSku1d": {
|
||||
"type": ["null", "number"]
|
||||
},
|
||||
"attributedSalesSameSku7d": {
|
||||
"type": ["null", "number"]
|
||||
},
|
||||
"attributedSalesSameSku14d": {
|
||||
"type": ["null", "number"]
|
||||
},
|
||||
"attributedSalesSameSku30d": {
|
||||
"type": ["null", "number"]
|
||||
},
|
||||
"unitsSoldSameSku1d": {
|
||||
"type": ["null", "integer"]
|
||||
},
|
||||
"unitsSoldSameSku7d": {
|
||||
"type": ["null", "integer"]
|
||||
},
|
||||
"unitsSoldSameSku14d": {
|
||||
"type": ["null", "integer"]
|
||||
},
|
||||
"unitsSoldSameSku30d": {
|
||||
"type": ["null", "integer"]
|
||||
}
|
||||
},
|
||||
"title": "sponsored_products_adgroups_report_stream_daily",
|
||||
"type": ["null", "object"]
|
||||
}
|
||||
@@ -0,0 +1,83 @@
|
||||
{
|
||||
"$schema": "http://json-schema.org/draft-07/schema#",
|
||||
"properties": {
|
||||
"date": { "type": ["null", "string"] },
|
||||
"profileId": {
|
||||
"type": ["null", "integer"]
|
||||
},
|
||||
"reportDate": {
|
||||
"type": ["null", "string"]
|
||||
},
|
||||
"advertisedAsin": {
|
||||
"type": ["null", "string"]
|
||||
},
|
||||
"campaignName": {
|
||||
"type": ["null", "string"]
|
||||
},
|
||||
"campaignId": {
|
||||
"type": ["null", "integer"]
|
||||
},
|
||||
"adGroupName": {
|
||||
"type": ["null", "string"]
|
||||
},
|
||||
"adGroupId": {
|
||||
"type": ["null", "integer"]
|
||||
},
|
||||
"keywordId": {
|
||||
"type": ["null", "integer"]
|
||||
},
|
||||
"keyword": {
|
||||
"type": ["null", "string"]
|
||||
},
|
||||
"purchasedAsin": {
|
||||
"type": ["null", "string"]
|
||||
},
|
||||
"advertisedSku": {
|
||||
"type": ["null", "string"]
|
||||
},
|
||||
"campaignBudgetCurrencyCode": {
|
||||
"type": ["null", "string"]
|
||||
},
|
||||
"matchType": {
|
||||
"type": ["null", "string"]
|
||||
},
|
||||
"unitsSoldClicks1d": {
|
||||
"type": ["null", "integer"]
|
||||
},
|
||||
"unitsSoldClicks7d": {
|
||||
"type": ["null", "integer"]
|
||||
},
|
||||
"unitsSoldClicks14d": {
|
||||
"type": ["null", "integer"]
|
||||
},
|
||||
"unitsSoldClicks30d": {
|
||||
"type": ["null", "integer"]
|
||||
},
|
||||
"unitsSoldOtherSku1d": {
|
||||
"type": ["null", "integer"]
|
||||
},
|
||||
"unitsSoldOtherSku7d": {
|
||||
"type": ["null", "integer"]
|
||||
},
|
||||
"unitsSoldOtherSku14d": {
|
||||
"type": ["null", "integer"]
|
||||
},
|
||||
"unitsSoldOtherSku30d": {
|
||||
"type": ["null", "integer"]
|
||||
},
|
||||
"salesOtherSku1d": {
|
||||
"type": ["null", "number"]
|
||||
},
|
||||
"salesOtherSku7d": {
|
||||
"type": ["null", "number"]
|
||||
},
|
||||
"salesOtherSku14d": {
|
||||
"type": ["null", "number"]
|
||||
},
|
||||
"salesOtherSku30d": {
|
||||
"type": ["null", "number"]
|
||||
}
|
||||
},
|
||||
"title": "sponsored_products_asins_keywords_report_stream_daily",
|
||||
"type": ["null", "object"]
|
||||
}
|
||||
@@ -0,0 +1,87 @@
|
||||
{
|
||||
"$schema": "http://json-schema.org/draft-07/schema#",
|
||||
"properties": {
|
||||
"date": { "type": ["null", "string"] },
|
||||
"profileId": {
|
||||
"type": ["null", "integer"]
|
||||
},
|
||||
"reportDate": {
|
||||
"type": ["null", "string"]
|
||||
},
|
||||
"advertisedAsin": {
|
||||
"type": ["null", "string"]
|
||||
},
|
||||
|
||||
"campaignName": {
|
||||
"type": ["null", "string"]
|
||||
},
|
||||
"campaignId": {
|
||||
"type": ["null", "integer"]
|
||||
},
|
||||
"adGroupName": {
|
||||
"type": ["null", "string"]
|
||||
},
|
||||
"adGroupId": {
|
||||
"type": ["null", "integer"]
|
||||
},
|
||||
"purchasedAsin": {
|
||||
"type": ["null", "string"]
|
||||
},
|
||||
"advertisedSku": {
|
||||
"type": ["null", "string"]
|
||||
},
|
||||
"campaignBudgetCurrencyCode": {
|
||||
"type": ["null", "string"]
|
||||
},
|
||||
"matchType": {
|
||||
"type": ["null", "string"]
|
||||
},
|
||||
"unitsSoldClicks1d": {
|
||||
"type": ["null", "integer"]
|
||||
},
|
||||
"unitsSoldClicks7d": {
|
||||
"type": ["null", "integer"]
|
||||
},
|
||||
"unitsSoldClicks14d": {
|
||||
"type": ["null", "integer"]
|
||||
},
|
||||
"unitsSoldClicks30d": {
|
||||
"type": ["null", "integer"]
|
||||
},
|
||||
"unitsSoldOtherSku1d": {
|
||||
"type": ["null", "integer"]
|
||||
},
|
||||
"unitsSoldOtherSku7d": {
|
||||
"type": ["null", "integer"]
|
||||
},
|
||||
"unitsSoldOtherSku14d": {
|
||||
"type": ["null", "integer"]
|
||||
},
|
||||
"unitsSoldOtherSku30d": {
|
||||
"type": ["null", "integer"]
|
||||
},
|
||||
"salesOtherSku1d": {
|
||||
"type": ["null", "number"]
|
||||
},
|
||||
"salesOtherSku7d": {
|
||||
"type": ["null", "number"]
|
||||
},
|
||||
"salesOtherSku14d": {
|
||||
"type": ["null", "number"]
|
||||
},
|
||||
"salesOtherSku30d": {
|
||||
"type": ["null", "number"]
|
||||
},
|
||||
"keywordId": {
|
||||
"type": ["null", "integer"]
|
||||
},
|
||||
"targeting": {
|
||||
"type": ["null", "string"]
|
||||
},
|
||||
"keywordType": {
|
||||
"type": ["null", "string"]
|
||||
}
|
||||
},
|
||||
"title": "sponsored_products_asins_targets_report_stream_daily",
|
||||
"type": ["null", "object"]
|
||||
}
|
||||
@@ -0,0 +1,116 @@
|
||||
{
|
||||
"$schema": "http://json-schema.org/draft-07/schema#",
|
||||
"properties": {
|
||||
"date": { "type": ["null", "string"] },
|
||||
"profileId": {
|
||||
"type": ["null", "integer"]
|
||||
},
|
||||
"reportDate": {
|
||||
"type": ["null", "string"]
|
||||
},
|
||||
"campaignId": {
|
||||
"type": ["null", "integer"]
|
||||
},
|
||||
"campaignName": {
|
||||
"type": ["null", "string"]
|
||||
},
|
||||
"campaignStatus": {
|
||||
"type": ["null", "string"]
|
||||
},
|
||||
"campaignBudgetAmount": {
|
||||
"type": ["null", "number"]
|
||||
},
|
||||
"campaignRuleBasedBudgetAmount": {
|
||||
"type": ["null", "number"]
|
||||
},
|
||||
"campaignApplicableBudgetRuleId": {
|
||||
"type": ["null", "string"]
|
||||
},
|
||||
"campaignApplicableBudgetRuleName": {
|
||||
"type": ["null", "string"]
|
||||
},
|
||||
"impressions": {
|
||||
"type": ["null", "integer"]
|
||||
},
|
||||
"clicks": {
|
||||
"type": ["null", "integer"]
|
||||
},
|
||||
"cost": {
|
||||
"type": ["null", "number"]
|
||||
},
|
||||
"purchases1d": {
|
||||
"type": ["null", "integer"]
|
||||
},
|
||||
"purchases7d": {
|
||||
"type": ["null", "integer"]
|
||||
},
|
||||
"purchases14d": {
|
||||
"type": ["null", "integer"]
|
||||
},
|
||||
"purchases30d": {
|
||||
"type": ["null", "integer"]
|
||||
},
|
||||
"purchasesSameSku1d": {
|
||||
"type": ["null", "integer"]
|
||||
},
|
||||
"purchasesSameSku7d": {
|
||||
"type": ["null", "integer"]
|
||||
},
|
||||
"purchasesSameSku14d": {
|
||||
"type": ["null", "integer"]
|
||||
},
|
||||
"purchasesSameSku30d": {
|
||||
"type": ["null", "integer"]
|
||||
},
|
||||
"unitsSoldClicks1d": {
|
||||
"type": ["null", "integer"]
|
||||
},
|
||||
"unitsSoldClicks7d": {
|
||||
"type": ["null", "integer"]
|
||||
},
|
||||
"unitsSoldClicks14d": {
|
||||
"type": ["null", "integer"]
|
||||
},
|
||||
"unitsSoldClicks30d": {
|
||||
"type": ["null", "integer"]
|
||||
},
|
||||
"sales1d": {
|
||||
"type": ["null", "number"]
|
||||
},
|
||||
"sales7d": {
|
||||
"type": ["null", "number"]
|
||||
},
|
||||
"sales14d": {
|
||||
"type": ["null", "number"]
|
||||
},
|
||||
"sales30d": {
|
||||
"type": ["null", "number"]
|
||||
},
|
||||
"attributedSalesSameSku1d": {
|
||||
"type": ["null", "number"]
|
||||
},
|
||||
"attributedSalesSameSku7d": {
|
||||
"type": ["null", "number"]
|
||||
},
|
||||
"attributedSalesSameSku14d": {
|
||||
"type": ["null", "number"]
|
||||
},
|
||||
"attributedSalesSameSku30d": {
|
||||
"type": ["null", "number"]
|
||||
},
|
||||
"unitsSoldSameSku1d": {
|
||||
"type": ["null", "integer"]
|
||||
},
|
||||
"unitsSoldSameSku7d": {
|
||||
"type": ["null", "integer"]
|
||||
},
|
||||
"unitsSoldSameSku14d": {
|
||||
"type": ["null", "integer"]
|
||||
},
|
||||
"unitsSoldSameSku30d": {
|
||||
"type": ["null", "integer"]
|
||||
}
|
||||
},
|
||||
"title": "sponsored_products_campaigns_report_stream_daily",
|
||||
"type": ["null", "object"]
|
||||
}
|
||||
@@ -0,0 +1,116 @@
|
||||
{
|
||||
"$schema": "http://json-schema.org/draft-07/schema#",
|
||||
"properties": {
|
||||
"date": { "type": ["null", "string"] },
|
||||
"profileId": {
|
||||
"type": ["null", "integer"]
|
||||
},
|
||||
"reportDate": {
|
||||
"type": ["null", "string"]
|
||||
},
|
||||
"keywordId": {
|
||||
"type": ["null", "integer"]
|
||||
},
|
||||
"campaignName": {
|
||||
"type": ["null", "string"]
|
||||
},
|
||||
"campaignId": {
|
||||
"type": ["null", "integer"]
|
||||
},
|
||||
"adGroupName": {
|
||||
"type": ["null", "string"]
|
||||
},
|
||||
"adGroupId": {
|
||||
"type": ["null", "integer"]
|
||||
},
|
||||
"keyword": {
|
||||
"type": ["null", "string"]
|
||||
},
|
||||
"matchType": {
|
||||
"type": ["null", "string"]
|
||||
},
|
||||
"impressions": {
|
||||
"type": ["null", "integer"]
|
||||
},
|
||||
"clicks": {
|
||||
"type": ["null", "integer"]
|
||||
},
|
||||
"cost": {
|
||||
"type": ["null", "number"]
|
||||
},
|
||||
"purchases1d": {
|
||||
"type": ["null", "integer"]
|
||||
},
|
||||
"purchases7d": {
|
||||
"type": ["null", "integer"]
|
||||
},
|
||||
"purchases14d": {
|
||||
"type": ["null", "integer"]
|
||||
},
|
||||
"purchases30d": {
|
||||
"type": ["null", "integer"]
|
||||
},
|
||||
"purchasesSameSku1d": {
|
||||
"type": ["null", "integer"]
|
||||
},
|
||||
"purchasesSameSku7d": {
|
||||
"type": ["null", "integer"]
|
||||
},
|
||||
"purchasesSameSku14d": {
|
||||
"type": ["null", "integer"]
|
||||
},
|
||||
"purchasesSameSku30d": {
|
||||
"type": ["null", "integer"]
|
||||
},
|
||||
"unitsSoldClicks1d": {
|
||||
"type": ["null", "integer"]
|
||||
},
|
||||
"unitsSoldClicks7d": {
|
||||
"type": ["null", "integer"]
|
||||
},
|
||||
"unitsSoldClicks14d": {
|
||||
"type": ["null", "integer"]
|
||||
},
|
||||
"unitsSoldClicks30d": {
|
||||
"type": ["null", "integer"]
|
||||
},
|
||||
"sales1d": {
|
||||
"type": ["null", "number"]
|
||||
},
|
||||
"sales7d": {
|
||||
"type": ["null", "number"]
|
||||
},
|
||||
"sales14d": {
|
||||
"type": ["null", "number"]
|
||||
},
|
||||
"sales30d": {
|
||||
"type": ["null", "number"]
|
||||
},
|
||||
"attributedSalesSameSku1d": {
|
||||
"type": ["null", "number"]
|
||||
},
|
||||
"attributedSalesSameSku7d": {
|
||||
"type": ["null", "number"]
|
||||
},
|
||||
"attributedSalesSameSku14d": {
|
||||
"type": ["null", "number"]
|
||||
},
|
||||
"attributedSalesSameSku30d": {
|
||||
"type": ["null", "number"]
|
||||
},
|
||||
"unitsSoldSameSku1d": {
|
||||
"type": ["null", "integer"]
|
||||
},
|
||||
"unitsSoldSameSku7d": {
|
||||
"type": ["null", "integer"]
|
||||
},
|
||||
"unitsSoldSameSku14d": {
|
||||
"type": ["null", "integer"]
|
||||
},
|
||||
"unitsSoldSameSku30d": {
|
||||
"type": ["null", "integer"]
|
||||
}
|
||||
},
|
||||
"title": "sponsored_products_keywords_report_stream_daily",
|
||||
"type": ["null", "object"]
|
||||
}
|
||||
@@ -0,0 +1,117 @@
|
||||
{
|
||||
"$schema": "http://json-schema.org/draft-07/schema#",
|
||||
"properties": {
|
||||
"date": { "type": ["null", "string"] },
|
||||
"profileId": {
|
||||
"type": ["null", "integer"]
|
||||
},
|
||||
"reportDate": {
|
||||
"type": ["null", "string"]
|
||||
},
|
||||
"adId": {
|
||||
"type": ["null", "integer"]
|
||||
},
|
||||
|
||||
"campaignName": {
|
||||
"type": ["null", "string"]
|
||||
},
|
||||
"campaignId": {
|
||||
"type": ["null", "integer"]
|
||||
},
|
||||
"adGroupName": {
|
||||
"type": ["null", "string"]
|
||||
},
|
||||
"adGroupId": {
|
||||
"type": ["null", "integer"]
|
||||
},
|
||||
"impressions": {
|
||||
"type": ["null", "integer"]
|
||||
},
|
||||
"clicks": {
|
||||
"type": ["null", "integer"]
|
||||
},
|
||||
"cost": {
|
||||
"type": ["null", "number"]
|
||||
},
|
||||
"campaignBudgetCurrencyCode": {
|
||||
"type": ["null", "string"]
|
||||
},
|
||||
"advertisedAsin": {
|
||||
"type": ["null", "string"]
|
||||
},
|
||||
"purchases1d": {
|
||||
"type": ["null", "integer"]
|
||||
},
|
||||
"purchases7d": {
|
||||
"type": ["null", "integer"]
|
||||
},
|
||||
"purchases14d": {
|
||||
"type": ["null", "integer"]
|
||||
},
|
||||
"purchases30d": {
|
||||
"type": ["null", "integer"]
|
||||
},
|
||||
"purchasesSameSku1d": {
|
||||
"type": ["null", "integer"]
|
||||
},
|
||||
"purchasesSameSku7d": {
|
||||
"type": ["null", "integer"]
|
||||
},
|
||||
"purchasesSameSku14d": {
|
||||
"type": ["null", "integer"]
|
||||
},
|
||||
"purchasesSameSku30d": {
|
||||
"type": ["null", "integer"]
|
||||
},
|
||||
"unitsSoldClicks1d": {
|
||||
"type": ["null", "integer"]
|
||||
},
|
||||
"unitsSoldClicks7d": {
|
||||
"type": ["null", "integer"]
|
||||
},
|
||||
"unitsSoldClicks14d": {
|
||||
"type": ["null", "integer"]
|
||||
},
|
||||
"unitsSoldClicks30d": {
|
||||
"type": ["null", "integer"]
|
||||
},
|
||||
"sales1d": {
|
||||
"type": ["null", "number"]
|
||||
},
|
||||
"sales7d": {
|
||||
"type": ["null", "number"]
|
||||
},
|
||||
"sales14d": {
|
||||
"type": ["null", "number"]
|
||||
},
|
||||
"sales30d": {
|
||||
"type": ["null", "number"]
|
||||
},
|
||||
"attributedSalesSameSku1d": {
|
||||
"type": ["null", "number"]
|
||||
},
|
||||
"attributedSalesSameSku7d": {
|
||||
"type": ["null", "number"]
|
||||
},
|
||||
"attributedSalesSameSku14d": {
|
||||
"type": ["null", "number"]
|
||||
},
|
||||
"attributedSalesSameSku30d": {
|
||||
"type": ["null", "number"]
|
||||
},
|
||||
"unitsSoldSameSku1d": {
|
||||
"type": ["null", "integer"]
|
||||
},
|
||||
"unitsSoldSameSku7d": {
|
||||
"type": ["null", "integer"]
|
||||
},
|
||||
"unitsSoldSameSku14d": {
|
||||
"type": ["null", "integer"]
|
||||
},
|
||||
"unitsSoldSameSku30d": {
|
||||
"type": ["null", "integer"]
|
||||
}
|
||||
},
|
||||
"title": "sponsored_products_productads_report_stream_daily",
|
||||
"type": ["null", "object"]
|
||||
}
|
||||
@@ -0,0 +1,120 @@
|
||||
{
|
||||
"$schema": "http://json-schema.org/draft-07/schema#",
|
||||
"properties": {
|
||||
"date": { "type": ["null", "string"] },
|
||||
"profileId": {
|
||||
"type": ["null", "integer"]
|
||||
},
|
||||
"reportDate": {
|
||||
"type": ["null", "string"]
|
||||
},
|
||||
"keywordId": {
|
||||
"type": ["null", "integer"]
|
||||
},
|
||||
|
||||
"campaignName": {
|
||||
"type": ["null", "string"]
|
||||
},
|
||||
"campaignId": {
|
||||
"type": ["null", "integer"]
|
||||
},
|
||||
"adGroupName": {
|
||||
"type": ["null", "string"]
|
||||
},
|
||||
"adGroupId": {
|
||||
"type": ["null", "integer"]
|
||||
},
|
||||
"keyword": {
|
||||
"type": ["null", "string"]
|
||||
},
|
||||
"targeting": {
|
||||
"type": ["null", "string"]
|
||||
},
|
||||
"keywordType": {
|
||||
"type": ["null", "string"]
|
||||
},
|
||||
"impressions": {
|
||||
"type": ["null", "integer"]
|
||||
},
|
||||
"clicks": {
|
||||
"type": ["null", "integer"]
|
||||
},
|
||||
"cost": {
|
||||
"type": ["null", "number"]
|
||||
},
|
||||
"purchases1d": {
|
||||
"type": ["null", "integer"]
|
||||
},
|
||||
"purchases7d": {
|
||||
"type": ["null", "integer"]
|
||||
},
|
||||
"purchases14d": {
|
||||
"type": ["null", "integer"]
|
||||
},
|
||||
"purchases30d": {
|
||||
"type": ["null", "integer"]
|
||||
},
|
||||
"purchasesSameSku1d": {
|
||||
"type": ["null", "integer"]
|
||||
},
|
||||
"purchasesSameSku7d": {
|
||||
"type": ["null", "integer"]
|
||||
},
|
||||
"purchasesSameSku14d": {
|
||||
"type": ["null", "integer"]
|
||||
},
|
||||
"purchasesSameSku30d": {
|
||||
"type": ["null", "integer"]
|
||||
},
|
||||
"unitsSoldClicks1d": {
|
||||
"type": ["null", "integer"]
|
||||
},
|
||||
"unitsSoldClicks7d": {
|
||||
"type": ["null", "integer"]
|
||||
},
|
||||
"unitsSoldClicks14d": {
|
||||
"type": ["null", "integer"]
|
||||
},
|
||||
"unitsSoldClicks30d": {
|
||||
"type": ["null", "integer"]
|
||||
},
|
||||
"sales1d": {
|
||||
"type": ["null", "number"]
|
||||
},
|
||||
"sales7d": {
|
||||
"type": ["null", "number"]
|
||||
},
|
||||
"sales14d": {
|
||||
"type": ["null", "number"]
|
||||
},
|
||||
"sales30d": {
|
||||
"type": ["null", "number"]
|
||||
},
|
||||
"attributedSalesSameSku1d": {
|
||||
"type": ["null", "number"]
|
||||
},
|
||||
"attributedSalesSameSku7d": {
|
||||
"type": ["null", "number"]
|
||||
},
|
||||
"attributedSalesSameSku14d": {
|
||||
"type": ["null", "number"]
|
||||
},
|
||||
"attributedSalesSameSku30d": {
|
||||
"type": ["null", "number"]
|
||||
},
|
||||
"unitsSoldSameSku1d": {
|
||||
"type": ["null", "integer"]
|
||||
},
|
||||
"unitsSoldSameSku7d": {
|
||||
"type": ["null", "integer"]
|
||||
},
|
||||
"unitsSoldSameSku14d": {
|
||||
"type": ["null", "integer"]
|
||||
},
|
||||
"unitsSoldSameSku30d": {
|
||||
"type": ["null", "integer"]
|
||||
}
|
||||
},
|
||||
"title": "sponsored_products_targets_report_stream_daily",
|
||||
"type": ["null", "object"]
|
||||
}
|
||||
@@ -1,114 +1,117 @@
|
||||
# Copyright (c) 2023 Airbyte, Inc., all rights reserved.
|
||||
# Copyright (c) 2025 Airbyte, Inc., all rights reserved.
|
||||
|
||||
|
||||
import uuid
|
||||
from unittest import TestCase
|
||||
import gzip
|
||||
from typing import Any, Mapping
|
||||
|
||||
import pendulum
|
||||
import pytest
|
||||
import requests_mock
|
||||
from source_amazon_ads import SourceAmazonAds
|
||||
|
||||
from airbyte_cdk.models import Level as LogLevel
|
||||
from airbyte_cdk.models import SyncMode
|
||||
from airbyte_cdk.test.mock_http import HttpMocker, HttpRequestMatcher
|
||||
|
||||
from .ad_requests import (
|
||||
OAuthRequestBuilder,
|
||||
ProfilesRequestBuilder,
|
||||
ReportCheckStatusRequestBuilder,
|
||||
ReportDownloadRequestBuilder,
|
||||
SponsoredBrandsV3ReportRequestBuilder,
|
||||
SponsoredDisplayReportRequestBuilder,
|
||||
SponsoredProductsReportRequestBuilder,
|
||||
)
|
||||
from .ad_responses import (
|
||||
ErrorResponseBuilder,
|
||||
OAuthResponseBuilder,
|
||||
ProfilesResponseBuilder,
|
||||
ReportCheckStatusResponseBuilder,
|
||||
ReportDownloadResponseBuilder,
|
||||
ReportInitResponseBuilder,
|
||||
)
|
||||
from .ad_responses.records import (
|
||||
ErrorRecordBuilder,
|
||||
ProfilesRecordBuilder,
|
||||
ReportCheckStatusRecordBuilder,
|
||||
ReportFileRecordBuilder,
|
||||
ReportInitResponseRecordBuilder,
|
||||
)
|
||||
from .config import ConfigBuilder
|
||||
from .metrics_map import BRANDS_METRICS_MAP_V3, DISPLAY_REPORT_METRICS_MAP, PRODUCTS_REPORT_METRICS_MAP
|
||||
from .utils import get_log_messages_by_log_level, read_stream
|
||||
from airbyte_cdk.test.catalog_builder import CatalogBuilder
|
||||
from airbyte_cdk.test.entrypoint_wrapper import EntrypointOutput, read
|
||||
from airbyte_cdk.test.state_builder import StateBuilder
|
||||
|
||||
|
||||
class TestDisplayReportStreams(TestCase):
|
||||
@property
|
||||
def _config(self):
|
||||
return ConfigBuilder().build()
|
||||
# Fixture for the configuration with a valid region value
|
||||
@pytest.fixture(name="config")
|
||||
def config_fixture() -> Mapping[str, Any]:
|
||||
return {
|
||||
"client_id": "amzn.app-oa2-client.test",
|
||||
"client_secret": "test-secret",
|
||||
"refresh_token": "test-refresh-token",
|
||||
"region": "NA",
|
||||
"report_wait_timeout": 3600,
|
||||
"report_generation_max_retry": 5,
|
||||
}
|
||||
|
||||
def _given_oauth_and_profiles(self, http_mocker: HttpMocker, config: dict) -> None:
|
||||
|
||||
# Fixture to mock OAuth token endpoint
|
||||
@pytest.fixture(name="mock_oauth")
|
||||
def mock_oauth_fixture(requests_mock: requests_mock.Mocker) -> None:
|
||||
requests_mock.post(
|
||||
"https://api.amazon.com/auth/o2/token",
|
||||
json={"access_token": "test-access-token", "token_type": "bearer", "expires_in": 3600},
|
||||
status_code=200,
|
||||
)
|
||||
|
||||
|
||||
# Fixture to mock profiles endpoint
|
||||
@pytest.fixture(name="mock_profiles")
|
||||
def mock_profiles_fixture(requests_mock: requests_mock.Mocker) -> None:
|
||||
requests_mock.get(
|
||||
"https://advertising-api.amazon.com/v2/profiles?profileTypeFilter=seller,vendor",
|
||||
json=[{"profileId": 1, "timezone": "UTC"}],
|
||||
status_code=200,
|
||||
request_headers={"Authorization": "Bearer test-access-token"},
|
||||
)
|
||||
|
||||
|
||||
def get_log_messages_by_log_level(logs, level: LogLevel) -> list:
|
||||
"""Utility to extract log messages by log level."""
|
||||
return [log.log.message for log in logs if log.type == "LOG" and log.log.level == level]
|
||||
|
||||
|
||||
class TestDisplayReportStreams:
|
||||
@staticmethod
|
||||
def _read(config: Mapping[str, Any], stream_name: str, sync_mode: SyncMode = SyncMode.full_refresh) -> EntrypointOutput:
|
||||
catalog = CatalogBuilder().with_stream(stream_name, sync_mode).build()
|
||||
state = StateBuilder().build()
|
||||
source = SourceAmazonAds(catalog, config, state)
|
||||
return read(source, config, catalog, state)
|
||||
|
||||
def test_given_file_when_read_brands_v3_report_then_return_records(
|
||||
self, requests_mock: requests_mock.Mocker, config: Mapping[str, Any], mock_oauth, mock_profiles
|
||||
):
|
||||
"""
|
||||
Authenticate and get profiles
|
||||
"""
|
||||
http_mocker.post(
|
||||
OAuthRequestBuilder.oauth_endpoint(
|
||||
client_id=config["client_id"], client_secred=config["client_secret"], refresh_token=config["refresh_token"]
|
||||
).build(),
|
||||
OAuthResponseBuilder.token_response().build(),
|
||||
)
|
||||
http_mocker.get(
|
||||
ProfilesRequestBuilder.profiles_endpoint(client_id=config["client_id"], client_access_token=config["access_token"]).build(),
|
||||
ProfilesResponseBuilder.profiles_response().with_record(ProfilesRecordBuilder.profiles_record()).build(),
|
||||
)
|
||||
|
||||
@HttpMocker()
|
||||
def test_given_file_when_read_display_report_then_return_records(self, http_mocker):
|
||||
"""
|
||||
Check display report stream: normal stream read flow
|
||||
In this test we prepare http mocker to handle all report types and tactics as well as workaround to handle gzipped file content
|
||||
Check Sponsored Brands V3 report stream: normal stream read flow
|
||||
In this test, we prepare HTTP mocks to handle report initiation, status checks, and file downloads.
|
||||
Request structure:
|
||||
1. Request report for start processing
|
||||
2. Check status and get a download link
|
||||
3. Download report file using the link
|
||||
1. POST request to initiate report processing.
|
||||
2. GET request to check report status and retrieve the download URL.
|
||||
3. GET request to download the gzipped report file.
|
||||
"""
|
||||
self._given_oauth_and_profiles(http_mocker, self._config)
|
||||
|
||||
profile_timezone = ProfilesRecordBuilder.profiles_record().build().get("timezone")
|
||||
start_date = pendulum.today(tz=profile_timezone).date()
|
||||
|
||||
for report_type, metrics in DISPLAY_REPORT_METRICS_MAP.items():
|
||||
report_id = str(uuid.uuid4())
|
||||
http_mocker.post(
|
||||
SponsoredDisplayReportRequestBuilder._init_report_endpoint(
|
||||
self._config["client_id"], self._config["access_token"], self._config["profiles"][0], report_type, metrics, start_date
|
||||
).build(),
|
||||
ReportInitResponseBuilder.report_init_response()
|
||||
.with_record(ReportInitResponseRecordBuilder.init_response_record().with_status("PENDING").with_id(report_id))
|
||||
.with_status_code(200)
|
||||
.build(),
|
||||
)
|
||||
download_request_builder = ReportDownloadRequestBuilder.download_endpoint(report_id)
|
||||
http_mocker.get(
|
||||
ReportCheckStatusRequestBuilder.check_sponsored_display_report_status_endpoint(
|
||||
self._config["client_id"], self._config["access_token"], self._config["profiles"][0], report_id
|
||||
).build(),
|
||||
ReportCheckStatusResponseBuilder.check_status_response()
|
||||
.with_record(ReportCheckStatusRecordBuilder.status_record().with_status("COMPLETED").with_url(download_request_builder.url))
|
||||
.build(),
|
||||
)
|
||||
|
||||
# a workaround to pass compressed document to the mocked response
|
||||
gzip_file_report_response = (
|
||||
ReportDownloadResponseBuilder.download_report().with_record(ReportFileRecordBuilder.report_file_record()).build()
|
||||
)
|
||||
request_matcher = HttpRequestMatcher(download_request_builder.build(), minimum_number_of_expected_match=1)
|
||||
http_mocker._matchers.append(request_matcher)
|
||||
|
||||
http_mocker._mocker.get(
|
||||
requests_mock.ANY,
|
||||
additional_matcher=http_mocker._matches_wrapper(request_matcher),
|
||||
response_list=[{"content": gzip_file_report_response.body, "status_code": gzip_file_report_response.status_code}],
|
||||
)
|
||||
report_id = "report-id-brands-v3"
|
||||
download_url = f"https://advertising-api.amazon.com/reporting/reports/{report_id}/download"
|
||||
requests_mock.post(
|
||||
"https://advertising-api.amazon.com/reporting/reports",
|
||||
json={"reportId": report_id, "status": "PENDING"},
|
||||
status_code=202,
|
||||
request_headers={"Authorization": "Bearer test-access-token"},
|
||||
)
|
||||
requests_mock.get(
|
||||
f"https://advertising-api.amazon.com/reporting/reports/{report_id}",
|
||||
json={"status": "COMPLETED", "url": download_url},
|
||||
status_code=200,
|
||||
request_headers={"Authorization": "Bearer test-access-token"},
|
||||
)
|
||||
report_data = gzip.compress(b'[{"record": "data"}]')
|
||||
requests_mock.get(
|
||||
download_url,
|
||||
content=report_data,
|
||||
status_code=200,
|
||||
)
|
||||
output = self._read(config, "sponsored_brands_v3_report_stream", SyncMode.incremental)
|
||||
start_date = pendulum.today(tz="UTC").date()
|
||||
assert output.most_recent_state.stream_state.states == [
|
||||
{"cursor": {"reportDate": start_date.format("YYYY-MM-DD")}, "partition": {"parent_slice": {}, "profileId": 1}}
|
||||
]
|
||||
assert len(output.records) == 1
|
||||
|
||||
def test_given_file_when_read_display_report_then_return_records(
|
||||
self, requests_mock: requests_mock.Mocker, config: Mapping[str, Any], mock_oauth, mock_profiles
|
||||
):
|
||||
"""
|
||||
Check display report streams: normal stream read flow for multiple streams
|
||||
This test iterates over several Sponsored Display report streams, mocking the API responses for each.
|
||||
It ensures that each stream can successfully initiate, check status, and download a report.
|
||||
Request structure:
|
||||
1. POST request to initiate report processing for each stream.
|
||||
2. GET request to check report status and retrieve the download URL for each stream.
|
||||
3. GET request to download the gzipped report file for each stream.
|
||||
"""
|
||||
number_of_records = 0
|
||||
for stream_name in (
|
||||
"sponsored_display_campaigns_report_stream",
|
||||
@@ -117,59 +120,42 @@ class TestDisplayReportStreams(TestCase):
|
||||
"sponsored_display_targets_report_stream",
|
||||
"sponsored_display_asins_report_stream",
|
||||
):
|
||||
output = read_stream(stream_name, SyncMode.full_refresh, self._config)
|
||||
report_id = f"report-id-display-{stream_name}"
|
||||
download_url = f"https://advertising-api.amazon.com/reporting/reports/{report_id}/download"
|
||||
requests_mock.post(
|
||||
"https://advertising-api.amazon.com/reporting/reports",
|
||||
json={"reportId": report_id, "status": "PENDING"},
|
||||
status_code=202,
|
||||
request_headers={"Authorization": "Bearer test-access-token"},
|
||||
)
|
||||
requests_mock.get(
|
||||
f"https://advertising-api.amazon.com/reporting/reports/{report_id}",
|
||||
json={"status": "COMPLETED", "url": download_url},
|
||||
status_code=200,
|
||||
request_headers={"Authorization": "Bearer test-access-token"},
|
||||
)
|
||||
report_data = gzip.compress(b'[{"record": "data"}]')
|
||||
requests_mock.get(
|
||||
download_url,
|
||||
content=report_data,
|
||||
status_code=200,
|
||||
)
|
||||
output = self._read(config, stream_name)
|
||||
number_of_records += len(output.records)
|
||||
assert number_of_records == 5
|
||||
|
||||
@HttpMocker()
|
||||
def test_given_file_when_read_products_report_then_return_records(self, http_mocker):
|
||||
def test_given_file_when_read_products_report_then_return_records(
|
||||
self, requests_mock: requests_mock.Mocker, config: Mapping[str, Any], mock_oauth, mock_profiles
|
||||
):
|
||||
"""
|
||||
Check products report stream: normal stream read flow.
|
||||
In this test we prepare http mocker to handle all report types based on metrics defined for the report stream
|
||||
as well as workaround to handle gzipped file content.
|
||||
Check Sponsored Products report streams: normal stream read flow for multiple streams
|
||||
This test iterates over several Sponsored Products report streams, mocking the API responses for each.
|
||||
It ensures that each stream can successfully initiate, check status, and download a report.
|
||||
Request structure:
|
||||
1. Request report for start processing
|
||||
2. Check status and get a download link
|
||||
3. Download report file using the link
|
||||
1. POST request to initiate report processing for each stream.
|
||||
2. GET request to check report status and retrieve the download URL for each stream.
|
||||
3. GET request to download the gzipped report file for each stream.
|
||||
"""
|
||||
self._given_oauth_and_profiles(http_mocker, self._config)
|
||||
|
||||
profile_timezone = ProfilesRecordBuilder.profiles_record().build().get("timezone")
|
||||
start_date = pendulum.today(tz=profile_timezone).date()
|
||||
|
||||
for report_type, metrics in PRODUCTS_REPORT_METRICS_MAP.items():
|
||||
report_id = str(uuid.uuid4())
|
||||
http_mocker.post(
|
||||
SponsoredProductsReportRequestBuilder._init_report_endpoint(
|
||||
self._config["client_id"], self._config["access_token"], self._config["profiles"][0], report_type, metrics, start_date
|
||||
).build(),
|
||||
ReportInitResponseBuilder.report_init_response()
|
||||
.with_record(ReportInitResponseRecordBuilder.init_response_record().with_status("PENDING").with_id(report_id))
|
||||
.with_status_code(200)
|
||||
.build(),
|
||||
)
|
||||
download_request_builder = ReportDownloadRequestBuilder.download_endpoint(report_id)
|
||||
http_mocker.get(
|
||||
ReportCheckStatusRequestBuilder.check_sponsored_products_report_status_endpoint(
|
||||
self._config["client_id"], self._config["access_token"], self._config["profiles"][0], report_id
|
||||
).build(),
|
||||
ReportCheckStatusResponseBuilder.check_status_response()
|
||||
.with_record(ReportCheckStatusRecordBuilder.status_record().with_status("COMPLETED").with_url(download_request_builder.url))
|
||||
.build(),
|
||||
)
|
||||
|
||||
# a workaround to pass compressed document to the mocked response
|
||||
gzip_file_report_response = (
|
||||
ReportDownloadResponseBuilder.download_report().with_record(ReportFileRecordBuilder.report_file_record()).build()
|
||||
)
|
||||
request_matcher = HttpRequestMatcher(download_request_builder.build(), minimum_number_of_expected_match=1)
|
||||
http_mocker._matchers.append(request_matcher)
|
||||
|
||||
http_mocker._mocker.get(
|
||||
requests_mock.ANY,
|
||||
additional_matcher=http_mocker._matches_wrapper(request_matcher),
|
||||
response_list=[{"content": gzip_file_report_response.body, "status_code": gzip_file_report_response.status_code}],
|
||||
)
|
||||
number_of_records = 0
|
||||
for stream_name in (
|
||||
"sponsored_products_campaigns_report_stream",
|
||||
@@ -180,165 +166,171 @@ class TestDisplayReportStreams(TestCase):
|
||||
"sponsored_products_asins_keywords_report_stream",
|
||||
"sponsored_products_asins_targets_report_stream",
|
||||
):
|
||||
output = read_stream(stream_name, SyncMode.full_refresh, self._config)
|
||||
report_id = f"report-id-products-{stream_name}"
|
||||
download_url = f"https://advertising-api.amazon.com/reporting/reports/{report_id}/download"
|
||||
requests_mock.post(
|
||||
"https://advertising-api.amazon.com/reporting/reports",
|
||||
json={"reportId": report_id, "status": "PENDING"},
|
||||
status_code=202,
|
||||
request_headers={"Authorization": "Bearer test-access-token"},
|
||||
)
|
||||
requests_mock.get(
|
||||
f"https://advertising-api.amazon.com/reporting/reports/{report_id}",
|
||||
json={"status": "COMPLETED", "url": download_url},
|
||||
status_code=200,
|
||||
request_headers={"Authorization": "Bearer test-access-token"},
|
||||
)
|
||||
report_data = gzip.compress(b'[{"record": "data"}]')
|
||||
requests_mock.get(
|
||||
download_url,
|
||||
content=report_data,
|
||||
status_code=200,
|
||||
)
|
||||
output = self._read(config, stream_name)
|
||||
number_of_records += len(output.records)
|
||||
assert number_of_records == 7
|
||||
|
||||
@HttpMocker()
|
||||
def test_given_file_when_read_brands_v3_report_then_return_records(self, http_mocker):
|
||||
def test_given_known_error_when_read_brands_v3_report_then_skip_report(
|
||||
self, requests_mock: requests_mock.Mocker, config: Mapping[str, Any], mock_oauth, mock_profiles
|
||||
):
|
||||
"""
|
||||
Check brands v3 report stream: normal stream read flow.
|
||||
In this test we prepare http mocker to handle all report types based on metrics defined for the report stream
|
||||
as well as workaround to handle gzipped file content.
|
||||
Check error handling for Sponsored Brands V3 report stream
|
||||
This test simulates known errors (400, 401, 406) by mocking API responses to return empty reports.
|
||||
It verifies that the stream skips the report gracefully without logging warnings.
|
||||
Request structure:
|
||||
1. Request report for start processing
|
||||
2. Check status and get a download link
|
||||
3. Download report file using the link
|
||||
1. POST request to initiate report processing.
|
||||
2. GET request to check report status and retrieve the download URL.
|
||||
3. GET request to download the gzipped empty report file.
|
||||
"""
|
||||
self._given_oauth_and_profiles(http_mocker, self._config)
|
||||
|
||||
profile_timezone = ProfilesRecordBuilder.profiles_record().build().get("timezone")
|
||||
start_date = pendulum.today(tz=profile_timezone).date()
|
||||
for report_type, metrics in BRANDS_METRICS_MAP_V3.items():
|
||||
report_id = str(uuid.uuid4())
|
||||
http_mocker.post(
|
||||
SponsoredBrandsV3ReportRequestBuilder._init_report_endpoint(
|
||||
self._config["client_id"], self._config["access_token"], self._config["profiles"][0], report_type, metrics, start_date
|
||||
).build(),
|
||||
ReportInitResponseBuilder.report_init_response()
|
||||
.with_record(ReportInitResponseRecordBuilder.init_response_record().with_status("PENDING").with_id(report_id))
|
||||
.with_status_code(200)
|
||||
.build(),
|
||||
)
|
||||
download_request_builder = ReportDownloadRequestBuilder.download_endpoint(report_id)
|
||||
http_mocker.get(
|
||||
ReportCheckStatusRequestBuilder.check_sponsored_brands_v3_report_status_endpoint(
|
||||
self._config["client_id"], self._config["access_token"], self._config["profiles"][0], report_id
|
||||
).build(),
|
||||
ReportCheckStatusResponseBuilder.check_status_response()
|
||||
.with_record(ReportCheckStatusRecordBuilder.status_record().with_status("COMPLETED").with_url(download_request_builder.url))
|
||||
.build(),
|
||||
)
|
||||
|
||||
# a workaround to pass compressed document to the mocked response
|
||||
gzip_file_report_response = (
|
||||
ReportDownloadResponseBuilder.download_report().with_record(ReportFileRecordBuilder.report_file_record()).build()
|
||||
)
|
||||
request_matcher = HttpRequestMatcher(download_request_builder.build(), minimum_number_of_expected_match=1)
|
||||
http_mocker._matchers.append(request_matcher)
|
||||
|
||||
http_mocker._mocker.get(
|
||||
requests_mock.ANY,
|
||||
additional_matcher=http_mocker._matches_wrapper(request_matcher),
|
||||
response_list=[{"content": gzip_file_report_response.body, "status_code": gzip_file_report_response.status_code}],
|
||||
)
|
||||
|
||||
output = read_stream("sponsored_brands_v3_report_stream", SyncMode.incremental, self._config)
|
||||
# OLd format
|
||||
# assert output.most_recent_state.stream_state == AirbyteStateBlob({"1": {"reportDate": start_date.format("YYYY-MM-DD")}})
|
||||
assert output.most_recent_state.stream_state.states == [
|
||||
{"cursor": {"reportDate": start_date.format("YYYY-MM-DD")}, "partition": {"parent_slice": {}, "profileId": 1}}
|
||||
]
|
||||
assert len(output.records) == 1
|
||||
|
||||
@HttpMocker()
|
||||
def test_given_known_error_when_read_brands_v3_report_then_skip_report(self, http_mocker):
|
||||
"""
|
||||
Check brands v3 stream: non-breaking errors are ignored.
|
||||
When error of this kind happen, we warn and then keep syncing another reports if possible.
|
||||
In this test all report init requests are failed with known error and skipped
|
||||
"""
|
||||
|
||||
ERRORS = [
|
||||
(400, "KDP authors do not have access to Sponsored Brands functionality"),
|
||||
(401, "Not authorized to access scope 0001"),
|
||||
(406, "Report date is too far in the past."),
|
||||
]
|
||||
|
||||
for status_code, msg in ERRORS:
|
||||
self._given_oauth_and_profiles(http_mocker, self._config)
|
||||
profile_timezone = ProfilesRecordBuilder.profiles_record().build().get("timezone")
|
||||
start_date = pendulum.today(tz=profile_timezone).date()
|
||||
non_breaking_error = ErrorRecordBuilder.non_breaking_error().with_error_message(msg)
|
||||
|
||||
for report_type, metrics in BRANDS_METRICS_MAP_V3.items():
|
||||
http_mocker.post(
|
||||
SponsoredBrandsV3ReportRequestBuilder._init_report_endpoint(
|
||||
self._config["client_id"],
|
||||
self._config["access_token"],
|
||||
self._config["profiles"][0],
|
||||
report_type,
|
||||
metrics,
|
||||
start_date,
|
||||
).build(),
|
||||
ErrorResponseBuilder.non_breaking_error_response()
|
||||
.with_record(non_breaking_error)
|
||||
.with_status_code(status_code)
|
||||
.build(),
|
||||
)
|
||||
|
||||
output = read_stream("sponsored_brands_v3_report_stream", SyncMode.full_refresh, self._config)
|
||||
report_id = f"report-id-brands-v3-{status_code}"
|
||||
download_url = f"https://advertising-api.amazon.com/reporting/reports/{report_id}/download"
|
||||
requests_mock.post(
|
||||
"https://advertising-api.amazon.com/reporting/reports",
|
||||
json={"reportId": report_id, "status": "PENDING"},
|
||||
status_code=202,
|
||||
request_headers={"Authorization": "Bearer test-access-token"},
|
||||
)
|
||||
requests_mock.get(
|
||||
f"https://advertising-api.amazon.com/reporting/reports/{report_id}",
|
||||
json={"status": "COMPLETED", "url": download_url},
|
||||
status_code=200,
|
||||
request_headers={"Authorization": "Bearer test-access-token"},
|
||||
)
|
||||
report_data = gzip.compress(b"[]")
|
||||
requests_mock.get(
|
||||
download_url,
|
||||
content=report_data,
|
||||
status_code=200,
|
||||
)
|
||||
output = self._read(config, "sponsored_brands_v3_report_stream")
|
||||
assert len(output.records) == 0
|
||||
|
||||
warning_logs = get_log_messages_by_log_level(output.logs, LogLevel.WARN)
|
||||
expected_warning_log = f"Exception has occurred during job creation: {msg}"
|
||||
assert any([expected_warning_log in warn for warn in warning_logs])
|
||||
http_mocker.clear_all_matchers()
|
||||
assert len(warning_logs) == 0
|
||||
requests_mock.reset()
|
||||
|
||||
@HttpMocker()
|
||||
def test_given_known_error_when_read_display_report_then_partially_skip_records(self, http_mocker):
|
||||
def test_given_known_error_when_read_display_report_then_partially_skip_records(
|
||||
self, requests_mock: requests_mock.Mocker, config: Mapping[str, Any], mock_oauth, mock_profiles
|
||||
):
|
||||
"""
|
||||
Check display v3 stream: non-breaking errors are ignored.
|
||||
When error of this kind happen, we warn and then keep syncing another reports if possible.
|
||||
In this test half of report init requests are failed with known error and skipped while another half of reports successfully processed
|
||||
Check partial error handling for Sponsored Display report streams
|
||||
This test simulates errors for some streams by mocking empty reports for odd-indexed streams.
|
||||
It ensures that the source skips failed streams gracefully while processing successful ones.
|
||||
Request structure:
|
||||
1. POST request to initiate report processing for each stream.
|
||||
2. GET request to check report status and retrieve the download URL for each stream.
|
||||
3. GET request to download the gzipped report file (data for even-indexed, empty for odd-indexed).
|
||||
"""
|
||||
self._given_oauth_and_profiles(http_mocker, self._config)
|
||||
|
||||
profile_timezone = ProfilesRecordBuilder.profiles_record().build().get("timezone")
|
||||
start_date = pendulum.today(tz=profile_timezone).date()
|
||||
|
||||
for report_type, metrics in DISPLAY_REPORT_METRICS_MAP.items():
|
||||
report_id = str(uuid.uuid4())
|
||||
http_mocker.post(
|
||||
SponsoredDisplayReportRequestBuilder._init_report_endpoint(
|
||||
self._config["client_id"], self._config["access_token"], self._config["profiles"][0], report_type, metrics, start_date
|
||||
).build(),
|
||||
ReportInitResponseBuilder.report_init_response()
|
||||
.with_record(ReportInitResponseRecordBuilder.init_response_record().with_status("PENDING").with_id(report_id))
|
||||
.with_status_code(200)
|
||||
.build(),
|
||||
)
|
||||
download_request_builder = ReportDownloadRequestBuilder.download_endpoint(report_id)
|
||||
http_mocker.get(
|
||||
ReportCheckStatusRequestBuilder.check_sponsored_display_report_status_endpoint(
|
||||
self._config["client_id"], self._config["access_token"], self._config["profiles"][0], report_id
|
||||
).build(),
|
||||
ReportCheckStatusResponseBuilder.check_status_response()
|
||||
.with_record(ReportCheckStatusRecordBuilder.status_record().with_status("COMPLETED").with_url(download_request_builder.url))
|
||||
.build(),
|
||||
)
|
||||
|
||||
# a workaround to pass compressed document to the mocked response
|
||||
gzip_file_report_response = (
|
||||
ReportDownloadResponseBuilder.download_report().with_record(ReportFileRecordBuilder.report_file_record()).build()
|
||||
)
|
||||
request_matcher = HttpRequestMatcher(download_request_builder.build(), minimum_number_of_expected_match=1)
|
||||
http_mocker._matchers.append(request_matcher)
|
||||
|
||||
http_mocker._mocker.get(
|
||||
requests_mock.ANY,
|
||||
additional_matcher=http_mocker._matches_wrapper(request_matcher),
|
||||
response_list=[{"content": gzip_file_report_response.body, "status_code": gzip_file_report_response.status_code}],
|
||||
)
|
||||
|
||||
number_of_records = 0
|
||||
for stream_name in (
|
||||
streams = (
|
||||
"sponsored_display_campaigns_report_stream",
|
||||
"sponsored_display_adgroups_report_stream",
|
||||
"sponsored_display_productads_report_stream",
|
||||
"sponsored_display_targets_report_stream",
|
||||
"sponsored_display_asins_report_stream",
|
||||
):
|
||||
output = read_stream(stream_name, SyncMode.full_refresh, self._config)
|
||||
)
|
||||
number_of_records = 0
|
||||
for i, stream_name in enumerate(streams):
|
||||
report_id = f"report-id-display-{stream_name}"
|
||||
download_url = f"https://advertising-api.amazon.com/reporting/reports/{report_id}/download"
|
||||
requests_mock.post(
|
||||
"https://advertising-api.amazon.com/reporting/reports",
|
||||
json={"reportId": report_id, "status": "PENDING"},
|
||||
status_code=202,
|
||||
request_headers={"Authorization": "Bearer test-access-token"},
|
||||
)
|
||||
requests_mock.get(
|
||||
f"https://advertising-api.amazon.com/reporting/reports/{report_id}",
|
||||
json={"status": "COMPLETED", "url": download_url},
|
||||
status_code=200,
|
||||
request_headers={"Authorization": "Bearer test-access-token"},
|
||||
)
|
||||
report_data = gzip.compress(b'[{"record": "data"}]') if i % 2 == 0 else gzip.compress(b"[]")
|
||||
requests_mock.get(
|
||||
download_url,
|
||||
content=report_data,
|
||||
status_code=200,
|
||||
)
|
||||
output = self._read(config, stream_name)
|
||||
number_of_records += len(output.records)
|
||||
assert number_of_records == 5
|
||||
if i % 2 == 1:
|
||||
warning_logs = get_log_messages_by_log_level(output.logs, LogLevel.WARN)
|
||||
assert len(warning_logs) == 0
|
||||
assert number_of_records == 3
|
||||
|
||||
@pytest.mark.parametrize(
|
||||
"stream_name",
|
||||
[
|
||||
"sponsored_brands_v3_report_stream_daily",
|
||||
"sponsored_display_campaigns_report_stream_daily",
|
||||
"sponsored_display_adgroups_report_stream_daily",
|
||||
"sponsored_display_productads_report_stream_daily",
|
||||
"sponsored_display_targets_report_stream_daily",
|
||||
"sponsored_display_asins_report_stream_daily",
|
||||
"sponsored_products_campaigns_report_stream_daily",
|
||||
"sponsored_products_adgroups_report_stream_daily",
|
||||
"sponsored_products_keywords_report_stream_daily",
|
||||
"sponsored_products_targets_report_stream_daily",
|
||||
"sponsored_products_productads_report_stream_daily",
|
||||
"sponsored_products_asins_keywords_report_stream_daily",
|
||||
"sponsored_products_asins_targets_report_stream_daily",
|
||||
],
|
||||
)
|
||||
def test_daily_stream(self, requests_mock, config, mock_oauth, mock_profiles, stream_name):
|
||||
"""
|
||||
Check daily report streams: parameterized test for all daily streams
|
||||
This test verifies that each daily stream can fetch and process records with the 'date' field.
|
||||
It uses HTTP mocks to simulate report initiation, status checks, and downloading gzipped daily data.
|
||||
Request structure:
|
||||
1. POST request to initiate report processing for the specified stream.
|
||||
2. GET request to check report status and retrieve the download URL.
|
||||
3. GET request to download the gzipped report file containing daily data.
|
||||
"""
|
||||
report_id = f"report-id-{stream_name}"
|
||||
download_url = f"https://advertising-api.amazon.com/reporting/reports/{report_id}/download"
|
||||
requests_mock.post(
|
||||
"https://advertising-api.amazon.com/reporting/reports",
|
||||
json={"reportId": report_id, "status": "PENDING"},
|
||||
status_code=202,
|
||||
request_headers={"Authorization": "Bearer test-access-token"},
|
||||
)
|
||||
requests_mock.get(
|
||||
f"https://advertising-api.amazon.com/reporting/reports/{report_id}",
|
||||
json={"status": "COMPLETED", "url": download_url},
|
||||
status_code=200,
|
||||
request_headers={"Authorization": "Bearer test-access-token"},
|
||||
)
|
||||
report_data = gzip.compress(b'[{"date": "2023-01-01", "record": "data1"}, {"date": "2023-01-02", "record": "data2"}]')
|
||||
requests_mock.get(
|
||||
download_url,
|
||||
content=report_data,
|
||||
status_code=200,
|
||||
)
|
||||
output = self._read(config, stream_name)
|
||||
assert len(output.records) == 2
|
||||
assert all("date" in record.record.data for record in output.records)
|
||||
assert [record.record.data["date"] for record in output.records] == ["2023-01-01", "2023-01-02"]
|
||||
|
||||
@@ -42,7 +42,7 @@ To use the [Amazon Ads API](https://advertising.amazon.com/API/docs/en-us), you
|
||||
5. Click **Authenticate your Amazon Ads account**.
|
||||
6. Log in and Authorize to the Amazon account.
|
||||
7. Select **Region** to pull data from **North America (NA)**, **Europe (EU)**, **Far East (FE)**. See [docs](https://advertising.amazon.com/API/docs/en-us/info/api-overview#api-endpoints) for more details.
|
||||
8. **Start Date (Optional)** is used for generating reports starting from the specified start date. This should be in YYYY-MM-DD format and not more than 60 days in the past. If a date is not specified, today's date is used. The date is treated in the timezone of the processed profile.
|
||||
8. **Start Date (Optional)** is used for generating reports starting from the specified start date. This should be in YYYY-MM-DD format and not more than 90 days in the past. If a date is not specified, today's date is used. The date is treated in the timezone of the processed profile.
|
||||
9. **Profile IDs (Optional)** you want to fetch data for. The Amazon Ads source connector supports only profiles with seller and vendor type, profiles with agency type will be ignored. See [docs](https://advertising.amazon.com/API/docs/en-us/concepts/authorization/profiles) for more details.
|
||||
10. **Marketplace IDs (Optional)** you want to fetch data for. _Note: If Profile IDs are also selected, profiles will be selected if they match the Profile ID **OR** the Marketplace ID._
|
||||
11. Click **Set up source**.
|
||||
@@ -58,7 +58,7 @@ To use the [Amazon Ads API](https://advertising.amazon.com/API/docs/en-us), you
|
||||
4. **Client Secret** of your Amazon Ads developer application. See [onboarding process](https://advertising.amazon.com/API/docs/en-us/setting-up/overview) for more details.
|
||||
5. **Refresh Token**. See [onboarding process](https://advertising.amazon.com/API/docs/en-us/setting-up/overview) for more details.
|
||||
6. Select **Region** to pull data from **North America (NA)**, **Europe (EU)**, **Far East (FE)**. See [docs](https://advertising.amazon.com/API/docs/en-us/info/api-overview#api-endpoints) for more details.
|
||||
7. **Start Date (Optional)** is used for generating reports starting from the specified start date. This should be in YYYY-MM-DD format and not more than 60 days in the past. If a date is not specified, today's date is used. The date is treated in the timezone of the processed profile.
|
||||
7. **Start Date (Optional)** is used for generating reports starting from the specified start date. This should be in YYYY-MM-DD format and not more than 90 days in the past. If a date is not specified, yesterday's date is used. The date is treated in the timezone of the processed profile.
|
||||
8. **Profile IDs (Optional)** you want to fetch data for. The Amazon Ads source connector supports only profiles with seller and vendor type, profiles with agency type will be ignored. See [docs](https://advertising.amazon.com/API/docs/en-us/concepts/authorization/profiles) for more details.
|
||||
9. **Marketplace IDs (Optional)** you want to fetch data for. _Note: If Profile IDs are also selected, profiles will be selected if they match the Profile ID **OR** the Marketplace ID._
|
||||
10. Click **Set up source**.
|
||||
@@ -72,7 +72,7 @@ To use the [Amazon Ads API](https://advertising.amazon.com/API/docs/en-us), you
|
||||
2. **Client Secret** of your Amazon Ads developer application. See [onboarding process](https://advertising.amazon.com/API/docs/en-us/setting-up/overview) for more details.
|
||||
3. **Refresh Token**. See [onboarding process](https://advertising.amazon.com/API/docs/en-us/setting-up/overview) for more details.
|
||||
4. Select **Region** to pull data from **North America (NA)**, **Europe (EU)**, **Far East (FE)**. See [docs](https://advertising.amazon.com/API/docs/en-us/info/api-overview#api-endpoints) for more details.
|
||||
5. **Start Date (Optional)** is used for generating reports starting from the specified start date. This should be in YYYY-MM-DD format and not more than 60 days in the past. If a date is not specified, today's date is used. The date is treated in the timezone of the processed profile.
|
||||
5. **Start Date (Optional)** is used for generating reports starting from the specified start date. This should be in YYYY-MM-DD format and not more than 90 days in the past. If a date is not specified, today's date is used. The date is treated in the timezone of the processed profile.
|
||||
6. **Profile IDs (Optional)** you want to fetch data for. The Amazon Ads source connector supports only profiles with seller and vendor type, profiles with agency type will be ignored. See [docs](https://advertising.amazon.com/API/docs/en-us/concepts/authorization/profiles) for more details.
|
||||
7. **Marketplace IDs (Optional)** you want to fetch data for. _Note: If Profile IDs are also selected, profiles will be selected if they match the Profile ID **OR** the Marketplace ID._
|
||||
<!-- /env:oss -->
|
||||
@@ -129,8 +129,12 @@ All the reports are generated relative to the target profile's timezone.
|
||||
|
||||
Campaign reports may sometimes have no data or may not be presenting in records. This can occur when there are no clicks or views associated with the campaigns on the requested day - [details](https://advertising.amazon.com/API/docs/en-us/guides/reporting/v2/faq#why-is-my-report-empty).
|
||||
|
||||
Report data synchronization only covers the last 60 days - [details](https://advertising.amazon.com/API/docs/en-us/reference/1/reports#parameters).
|
||||
Report data synchronization only covers the last 90 days - [details](https://advertising.amazon.com/API/docs/en-us/reference/1/reports#parameters).
|
||||
|
||||
:::note
|
||||
The 'Reports' stream(s) by default will have `timeUnit` set to `SUMMARY`. If you would like more granularity, use the `_daily` versions of the report streams, which have
|
||||
`timeUnit` set to `DAILY`. More info about this can be found [here](https://advertising.amazon.com/API/docs/en-us/guides/reporting/v3/get-started#timeunit-and-supported-columns).
|
||||
:::
|
||||
## Performance considerations
|
||||
|
||||
Information about expected report generation waiting time can be found [here](https://advertising.amazon.com/API/docs/en-us/get-started/developer-notes).
|
||||
@@ -153,6 +157,7 @@ Information about expected report generation waiting time can be found [here](ht
|
||||
|
||||
| Version | Date | Pull Request | Subject |
|
||||
|:--------|:-----------|:---------------------------------------------------------|:-----------------------------------------------------------------------------------------------------------------------------------------------------------------------|
|
||||
| 7.2.0-rc.1 | 2025-04-22 | [55217](https://github.com/airbytehq/airbyte/pull/55217) | Add `daily` versions of `reports` streams & Auto-update start_date if past lookback window|
|
||||
| 7.1.7 | 2025-04-12 | [57591](https://github.com/airbytehq/airbyte/pull/57591) | Update dependencies |
|
||||
| 7.1.6 | 2025-04-05 | [57138](https://github.com/airbytehq/airbyte/pull/57138) | Update dependencies |
|
||||
| 7.1.5 | 2025-03-29 | [56554](https://github.com/airbytehq/airbyte/pull/56554) | Update dependencies |
|
||||
|
||||
Reference in New Issue
Block a user