adapty 0.8.4-beta.1 → 0.8.5

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (107) hide show
  1. package/README.md +133 -3
  2. package/bin/dev.js +2 -2
  3. package/bin/run.js +2 -2
  4. package/dist/commands/access-levels/create.js +1 -1
  5. package/dist/commands/access-levels/list.d.ts +1 -1
  6. package/dist/commands/apps/create.js +9 -6
  7. package/dist/commands/apps/list.d.ts +1 -1
  8. package/dist/commands/apps/update.js +7 -4
  9. package/dist/commands/asa/ad-groups/create.js +9 -7
  10. package/dist/commands/asa/ad-groups/get.js +3 -2
  11. package/dist/commands/asa/ad-groups/list.d.ts +1 -1
  12. package/dist/commands/asa/ad-groups/list.js +1 -1
  13. package/dist/commands/asa/ad-groups/update.js +22 -12
  14. package/dist/commands/asa/ads/create.js +7 -5
  15. package/dist/commands/asa/ads/get.js +3 -2
  16. package/dist/commands/asa/ads/list.d.ts +1 -1
  17. package/dist/commands/asa/ads/list.js +1 -1
  18. package/dist/commands/asa/ads/update.js +9 -5
  19. package/dist/commands/asa/apps/list.d.ts +1 -1
  20. package/dist/commands/asa/apps/list.js +1 -1
  21. package/dist/commands/asa/automations/create.d.ts +9 -0
  22. package/dist/commands/asa/automations/create.js +26 -7
  23. package/dist/commands/asa/automations/get.js +3 -2
  24. package/dist/commands/asa/automations/list.d.ts +1 -1
  25. package/dist/commands/asa/automations/list.js +1 -1
  26. package/dist/commands/asa/automations/run.js +5 -3
  27. package/dist/commands/asa/automations/runs.d.ts +1 -1
  28. package/dist/commands/asa/automations/runs.js +4 -4
  29. package/dist/commands/asa/automations/update.d.ts +9 -0
  30. package/dist/commands/asa/automations/update.js +36 -12
  31. package/dist/commands/asa/campaigns/bulk-create.js +31 -18
  32. package/dist/commands/asa/campaigns/bulk-list.js +7 -5
  33. package/dist/commands/asa/campaigns/bulk-status.js +3 -2
  34. package/dist/commands/asa/campaigns/create.js +10 -8
  35. package/dist/commands/asa/campaigns/get.js +3 -2
  36. package/dist/commands/asa/campaigns/list.d.ts +1 -1
  37. package/dist/commands/asa/campaigns/list.js +1 -1
  38. package/dist/commands/asa/campaigns/update.js +25 -15
  39. package/dist/commands/asa/competitors/summary.js +5 -5
  40. package/dist/commands/asa/connect.js +5 -3
  41. package/dist/commands/asa/creatives/list.d.ts +1 -1
  42. package/dist/commands/asa/creatives/list.js +1 -1
  43. package/dist/commands/asa/keywords/add.js +13 -10
  44. package/dist/commands/asa/keywords/list.d.ts +1 -1
  45. package/dist/commands/asa/keywords/list.js +1 -1
  46. package/dist/commands/asa/keywords/update.js +15 -10
  47. package/dist/commands/asa/metrics/index.d.ts +6 -3
  48. package/dist/commands/asa/metrics/index.js +38 -14
  49. package/dist/commands/asa/metrics/overview.js +3 -3
  50. package/dist/commands/asa/negative-keywords/add.js +10 -7
  51. package/dist/commands/asa/negative-keywords/list.d.ts +1 -1
  52. package/dist/commands/asa/negative-keywords/list.js +1 -1
  53. package/dist/commands/asa/orgs/list.d.ts +1 -1
  54. package/dist/commands/asa/orgs/list.js +1 -1
  55. package/dist/commands/asa/product-pages/list.d.ts +1 -1
  56. package/dist/commands/asa/product-pages/list.js +1 -1
  57. package/dist/commands/asa/product-pages/sync.js +1 -1
  58. package/dist/commands/asa/search-terms/list.d.ts +1 -1
  59. package/dist/commands/asa/search-terms/list.js +1 -1
  60. package/dist/commands/asa/whoami.js +7 -2
  61. package/dist/commands/auth/login.js +3 -1
  62. package/dist/commands/flows/config/get.js +2 -2
  63. package/dist/commands/flows/config/preview.d.ts +2 -2
  64. package/dist/commands/flows/config/preview.js +6 -4
  65. package/dist/commands/flows/config/update.js +5 -3
  66. package/dist/commands/flows/config/validate.js +5 -3
  67. package/dist/commands/flows/list.d.ts +1 -1
  68. package/dist/commands/flows/media/upload.js +1 -1
  69. package/dist/commands/flows/publish.js +5 -5
  70. package/dist/commands/paywalls/create.js +1 -1
  71. package/dist/commands/paywalls/list.d.ts +1 -1
  72. package/dist/commands/paywalls/placements.d.ts +2 -2
  73. package/dist/commands/paywalls/update.js +1 -1
  74. package/dist/commands/placements/create.js +17 -12
  75. package/dist/commands/placements/list.d.ts +1 -1
  76. package/dist/commands/placements/update.js +20 -15
  77. package/dist/commands/products/create.js +20 -13
  78. package/dist/commands/products/list.d.ts +1 -1
  79. package/dist/commands/products/update.js +1 -1
  80. package/dist/commands/segments/list.d.ts +1 -1
  81. package/dist/lib/api-client.d.ts +10 -6
  82. package/dist/lib/api-client.js +56 -35
  83. package/dist/lib/api-schemas.d.ts +56 -56
  84. package/dist/lib/app-url.js +2 -1
  85. package/dist/lib/asa-client.d.ts +13 -8
  86. package/dist/lib/asa-client.js +9 -4
  87. package/dist/lib/asa-flags.d.ts +37 -13
  88. package/dist/lib/asa-flags.js +87 -20
  89. package/dist/lib/asa-keyword-action.d.ts +18 -0
  90. package/dist/lib/asa-keyword-action.js +175 -0
  91. package/dist/lib/asa-schemas.d.ts +100 -80
  92. package/dist/lib/auth.js +2 -1
  93. package/dist/lib/client-from-config.d.ts +1 -1
  94. package/dist/lib/client-from-config.js +2 -1
  95. package/dist/lib/config.d.ts +2 -2
  96. package/dist/lib/confirm.d.ts +4 -4
  97. package/dist/lib/confirm.js +12 -7
  98. package/dist/lib/errors.d.ts +18 -18
  99. package/dist/lib/errors.js +14 -10
  100. package/dist/lib/flags.d.ts +3 -3
  101. package/dist/lib/flags.js +2 -1
  102. package/dist/lib/flow-help.js +11 -6
  103. package/dist/lib/output.js +23 -12
  104. package/dist/lib/preview.d.ts +5 -5
  105. package/dist/lib/preview.js +2 -1
  106. package/oclif.manifest.json +372 -200
  107. package/package.json +10 -8
@@ -0,0 +1,175 @@
1
+ import { isValidUuid } from './flags.js';
2
+ export const ADD_AS_KEYWORD_ACTION = 'add-as-keyword-to';
3
+ export const CPT_BID_TYPES = ['ad_group_default_bid', 'keyword_current_bid', 'search_term_current_cpt', 'set_to'];
4
+ export const KEYWORD_MATCH_TYPES = ['BROAD', 'EXACT'];
5
+ export const NEGATE_TYPES = ['ad-group', 'campaign'];
6
+ const SEARCH_TERM = 'search-term';
7
+ const TARGETING_KEYWORD = 'targeting-keyword';
8
+ const BID_TYPE_IGNORING_VALUE = 'ad_group_default_bid';
9
+ const BID_TYPES_READING_MARKUP = new Set(['keyword_current_bid', 'search_term_current_cpt']);
10
+ // KeywordMatchType also carries AUTO. --match-type never offers it — an automation creates a
11
+ // keyword, and AUTO is not something a keyword can be — but a rule that already stores AUTO keeps
12
+ // it rather than being pushed onto another match type by an edit that never mentioned match types.
13
+ const STORED_MATCH_TYPES = new Set(['AUTO', ...KEYWORD_MATCH_TYPES]);
14
+ const SHARED_FLAGS = ['target-ad-group', 'match-type', 'cpt-bid-type', 'cpt-bid'];
15
+ const SEARCH_TERM_FLAGS = ['negate', 'no-negate', 'skip-enable-duplicates'];
16
+ const TARGETING_KEYWORD_FLAGS = ['pause-original'];
17
+ const ALL_FLAGS = [...SHARED_FLAGS, ...SEARCH_TERM_FLAGS, ...TARGETING_KEYWORD_FLAGS];
18
+ const MISSING_REASONS = {
19
+ 'cpt-bid': 'the bid to set, required by --cpt-bid-type set_to',
20
+ 'cpt-bid-type': 'where the bid of the new keyword comes from; the API has no default',
21
+ 'match-type': 'BROAD or EXACT; the API has no default',
22
+ 'target-ad-group': 'the ad groups the keyword is added to; a rule with none does nothing',
23
+ };
24
+ function dashed(name) {
25
+ return `--${name}`;
26
+ }
27
+ function asRecord(value) {
28
+ return typeof value === 'object' && value !== null && !Array.isArray(value) ? value : {};
29
+ }
30
+ function isFlagSet(flags, name) {
31
+ const value = flags[name];
32
+ if (value === undefined) {
33
+ return false;
34
+ }
35
+ if (Array.isArray(value)) {
36
+ return value.length > 0;
37
+ }
38
+ // --no-negate has no negated form of its own, so only a true means it was passed.
39
+ return name === 'no-negate' ? value === true : true;
40
+ }
41
+ export function hasAddKeywordActionFlags(flags) {
42
+ return ALL_FLAGS.some(name => isFlagSet(flags, name));
43
+ }
44
+ // Params are rebuilt, not patched: a rule may store the add-as-negative-keyword shape
45
+ // ({target_type, ids}) under an add-as-keyword-to action, and the API picks the params variant by
46
+ // shape without a discriminator — so every stray key silently changes which action gets run.
47
+ // Only what fits the expected shape is carried over; the rest has to come from the flags.
48
+ function storedInternalIds(params) {
49
+ const ids = asRecord(params.targets).internal_ids;
50
+ return Array.isArray(ids) ? ids.filter((id) => typeof id === 'string' && isValidUuid(id)) : [];
51
+ }
52
+ function storedMatchType(params) {
53
+ const matchType = params.match_type;
54
+ return typeof matchType === 'string' && STORED_MATCH_TYPES.has(matchType) ? matchType : undefined;
55
+ }
56
+ function storedCptBidType(params) {
57
+ const { type } = asRecord(params.cpt_bid);
58
+ return typeof type === 'string' && CPT_BID_TYPES.includes(type) ? type : undefined;
59
+ }
60
+ function storedCptBidValue(params) {
61
+ const { value } = asRecord(params.cpt_bid);
62
+ return typeof value === 'number' && Number.isFinite(value) ? value : undefined;
63
+ }
64
+ function storedBoolean(value) {
65
+ return typeof value === 'boolean' ? value : undefined;
66
+ }
67
+ function storedNegate(params) {
68
+ const { enabled, type } = asRecord(params.negate);
69
+ if (typeof enabled !== 'boolean') {
70
+ return undefined;
71
+ }
72
+ if (type === null || type === undefined) {
73
+ return { enabled, type: null };
74
+ }
75
+ return typeof type === 'string' && NEGATE_TYPES.includes(type) ? { enabled, type } : undefined;
76
+ }
77
+ function resolveNegate(flags, params) {
78
+ if (flags.negate !== undefined) {
79
+ return { enabled: true, type: flags.negate };
80
+ }
81
+ if (flags['no-negate'] === true) {
82
+ return { enabled: false, type: null };
83
+ }
84
+ return storedNegate(params) ?? { enabled: false, type: null };
85
+ }
86
+ function resolveCptBidValue(cptBidType, bid, params) {
87
+ if (cptBidType === 'set_to') {
88
+ return bid === undefined ? storedCptBidValue(params) : Number(bid);
89
+ }
90
+ if (cptBidType !== undefined && BID_TYPES_READING_MARKUP.has(cptBidType)) {
91
+ return bid === undefined ? (storedCptBidValue(params) ?? null) : Number(bid);
92
+ }
93
+ return null;
94
+ }
95
+ function isSearchTermRule(operateWith) {
96
+ if (operateWith === SEARCH_TERM) {
97
+ return true;
98
+ }
99
+ if (operateWith === TARGETING_KEYWORD) {
100
+ return false;
101
+ }
102
+ const shown = typeof operateWith === 'string' && operateWith.length > 0 ? `"${operateWith}"` : 'missing';
103
+ throw new Error(`${ADD_AS_KEYWORD_ACTION} runs on a "${SEARCH_TERM}" or "${TARGETING_KEYWORD}" rule only; this rule's operate_with is ${shown}.`);
104
+ }
105
+ function rejectForeignFlags(searchTerm, flags) {
106
+ const foreign = (searchTerm ? TARGETING_KEYWORD_FLAGS : SEARCH_TERM_FLAGS).filter(name => isFlagSet(flags, name));
107
+ if (foreign.length === 0) {
108
+ return;
109
+ }
110
+ const applicable = [...SHARED_FLAGS, ...(searchTerm ? SEARCH_TERM_FLAGS : TARGETING_KEYWORD_FLAGS)];
111
+ throw new Error(`${foreign.map(name => dashed(name)).join(', ')} ${foreign.length === 1 ? 'has' : 'have'} no place in the params of an `
112
+ + `operate_with "${searchTerm ? SEARCH_TERM : TARGETING_KEYWORD}" rule, and the API drops params it cannot `
113
+ + `place. Applicable action flags: ${applicable.map(name => dashed(name)).join(', ')}.`);
114
+ }
115
+ function missingFlagsError(missing) {
116
+ const lines = missing.map(name => ` ${dashed(name)} — ${MISSING_REASONS[name]}`);
117
+ return new Error(`The ${ADD_AS_KEYWORD_ACTION} params are incomplete. Pass:\n${lines.join('\n')}`);
118
+ }
119
+ export function buildAddKeywordParams(operateWith, stored, flags) {
120
+ const searchTerm = isSearchTermRule(operateWith);
121
+ rejectForeignFlags(searchTerm, flags);
122
+ const params = asRecord(stored);
123
+ const missing = [];
124
+ const internalIds = flags['target-ad-group'] ?? storedInternalIds(params);
125
+ if (internalIds.length === 0) {
126
+ missing.push('target-ad-group');
127
+ }
128
+ const matchType = flags['match-type'] ?? storedMatchType(params);
129
+ if (matchType === undefined) {
130
+ missing.push('match-type');
131
+ }
132
+ const cptBidType = flags['cpt-bid-type'] ?? storedCptBidType(params);
133
+ if (cptBidType === undefined) {
134
+ missing.push('cpt-bid-type');
135
+ }
136
+ const bid = flags['cpt-bid'];
137
+ if (bid !== undefined && cptBidType === BID_TYPE_IGNORING_VALUE) {
138
+ throw new Error(`--cpt-bid has no meaning with --cpt-bid-type ${BID_TYPE_IGNORING_VALUE}; that type copies the target ad group's default bid.`);
139
+ }
140
+ const cptBidValue = resolveCptBidValue(cptBidType, bid, params);
141
+ if (cptBidValue === undefined) {
142
+ missing.push('cpt-bid');
143
+ }
144
+ if (missing.length > 0) {
145
+ throw missingFlagsError(missing);
146
+ }
147
+ const built = {
148
+ cpt_bid: { type: cptBidType, value: cptBidValue ?? null },
149
+ match_type: matchType,
150
+ targets: { internal_ids: internalIds, type: 'ad-group' },
151
+ };
152
+ if (searchTerm) {
153
+ built.negate = resolveNegate(flags, params);
154
+ built.skip_enable_duplicate_keywords
155
+ = flags['skip-enable-duplicates'] ?? storedBoolean(params.skip_enable_duplicate_keywords) ?? false;
156
+ }
157
+ else {
158
+ built.pause_in_original_ad_group
159
+ = flags['pause-original'] ?? storedBoolean(params.pause_in_original_ad_group) ?? false;
160
+ }
161
+ return built;
162
+ }
163
+ export function requireSingleAction(actions) {
164
+ if (!Array.isArray(actions) || actions.length !== 1) {
165
+ throw new Error('A rule needs exactly one action: the API stores one action and one condition per rule.');
166
+ }
167
+ return asRecord(actions[0]);
168
+ }
169
+ export function rebuildAddKeywordAction(actions, operateWith, flags) {
170
+ const action = requireSingleAction(actions);
171
+ if (action.type !== ADD_AS_KEYWORD_ACTION) {
172
+ throw new Error(`The action flags only apply to an ${ADD_AS_KEYWORD_ACTION} action; this rule's action is "${String(action.type)}".`);
173
+ }
174
+ return [{ ...action, params: buildAddKeywordParams(operateWith, action.params, flags) }];
175
+ }
@@ -4,11 +4,11 @@ export type AsaKeywordMatchType = 'BROAD' | 'EXACT';
4
4
  export type AsaKeywordStatus = 'ACTIVE' | 'PAUSED';
5
5
  export type AsaStatus = 'ENABLED' | 'PAUSED';
6
6
  export type AsaNegativeKeywordScope = 'AD_GROUP' | 'ALL_CAMPAIGN_AD_GROUPS' | 'CAMPAIGN';
7
- export interface AsaMoney {
7
+ export type AsaMoney = {
8
8
  amount: string;
9
9
  currency: string;
10
- }
11
- export interface AsaMetricsDTO {
10
+ };
11
+ export type AsaMetricsDTO = {
12
12
  avg_cpm: string;
13
13
  avg_cpt: string;
14
14
  impressions: number;
@@ -29,16 +29,36 @@ export interface AsaMetricsDTO {
29
29
  view_installs: number;
30
30
  view_new_downloads: number;
31
31
  view_redownloads: number;
32
- }
33
- export interface AsaMeDTO {
32
+ };
33
+ export type AsaMetricsResponse = {
34
+ data: Record<string, unknown>[];
35
+ meta: {
36
+ max_valid_day?: number;
37
+ pagination: {
38
+ count: number;
39
+ page: number;
40
+ pages: number;
41
+ };
42
+ };
43
+ };
44
+ export type AsaEffectiveLimitsDTO = {
45
+ keywords_read_limit_per_minute: number;
46
+ max_breakdown_rows_per_page: number;
47
+ metrics_burst_limit: number;
48
+ metrics_inflight_limit: number;
49
+ metrics_limit_per_minute: number;
50
+ read_limit_per_minute: number;
51
+ };
52
+ export type AsaMeDTO = {
34
53
  access_source: AsaAccessSource;
35
54
  apple_credentials_status: AsaAppleCredentialsStatus;
36
55
  company_id: string;
37
- }
38
- export interface AsaAppleOAuthDTO {
56
+ limits?: AsaEffectiveLimitsDTO;
57
+ };
58
+ export type AsaAppleOAuthDTO = {
39
59
  auth_url: string;
40
- }
41
- export interface AsaAppDTO {
60
+ };
61
+ export type AsaAppDTO = {
42
62
  adam_id: number;
43
63
  bundle_id: null | string;
44
64
  campaign_group_ids: string[];
@@ -47,15 +67,15 @@ export interface AsaAppDTO {
47
67
  internal_id: string;
48
68
  last_synced_at: string;
49
69
  name: string;
50
- }
51
- export interface AsaLocInvoiceDetails {
70
+ };
71
+ export type AsaLocInvoiceDetails = {
52
72
  billing_contact_email: null | string;
53
73
  buyer_email: null | string;
54
74
  buyer_name: null | string;
55
75
  client_name: null | string;
56
76
  order_number: null | string;
57
- }
58
- export interface AsaCampaignGroupDTO {
77
+ };
78
+ export type AsaCampaignGroupDTO = {
59
79
  currency: string;
60
80
  internal_id: string;
61
81
  last_synced_at: string;
@@ -64,8 +84,8 @@ export interface AsaCampaignGroupDTO {
64
84
  parent_org_id: number;
65
85
  payment_model: null | string;
66
86
  time_zone: string;
67
- }
68
- export interface AsaCampaignDTO {
87
+ };
88
+ export type AsaCampaignDTO = {
69
89
  ad_channel_type: string;
70
90
  adam_id: number;
71
91
  app_id: string;
@@ -88,8 +108,8 @@ export interface AsaCampaignDTO {
88
108
  status: AsaStatus;
89
109
  supply_sources: string[];
90
110
  target_cpa: AsaMoney | null;
91
- }
92
- export interface AsaAdGroupDTO {
111
+ };
112
+ export type AsaAdGroupDTO = {
93
113
  ad_group_id: number;
94
114
  app_id: string;
95
115
  automated_keywords_opt_in: boolean | null;
@@ -109,8 +129,8 @@ export interface AsaAdGroupDTO {
109
129
  start_time: null | string;
110
130
  status: AsaStatus | null;
111
131
  target_cpa: AsaMoney | null;
112
- }
113
- export interface AsaKeywordDTO {
132
+ };
133
+ export type AsaKeywordDTO = {
114
134
  ad_group_id: string;
115
135
  app_id: string;
116
136
  bid_amount: AsaMoney;
@@ -122,8 +142,8 @@ export interface AsaKeywordDTO {
122
142
  match_type: AsaKeywordMatchType;
123
143
  status: AsaKeywordStatus | null;
124
144
  text: string;
125
- }
126
- export interface AsaSearchTermDTO {
145
+ };
146
+ export type AsaSearchTermDTO = {
127
147
  ad_group_id: string;
128
148
  app_id: string;
129
149
  campaign_group_id: string;
@@ -136,8 +156,8 @@ export interface AsaSearchTermDTO {
136
156
  search_popularity: null | number;
137
157
  source: null | string;
138
158
  text: null | string;
139
- }
140
- export interface AsaNegativeKeywordDTO {
159
+ };
160
+ export type AsaNegativeKeywordDTO = {
141
161
  ad_group_id: null | string;
142
162
  ad_group_name: null | string;
143
163
  campaign_id: string;
@@ -147,8 +167,8 @@ export interface AsaNegativeKeywordDTO {
147
167
  match_type: AsaKeywordMatchType;
148
168
  status: AsaKeywordStatus;
149
169
  text: string;
150
- }
151
- export interface AsaCreativeDTO {
170
+ };
171
+ export type AsaCreativeDTO = {
152
172
  adam_id: number;
153
173
  app_id: string;
154
174
  campaign_group_id: string;
@@ -160,8 +180,8 @@ export interface AsaCreativeDTO {
160
180
  state: string;
161
181
  state_reasons: string[];
162
182
  type: string;
163
- }
164
- export interface AsaProductPageDTO {
183
+ };
184
+ export type AsaProductPageDTO = {
165
185
  adam_id: number;
166
186
  app_id: string;
167
187
  deep_link: null | string;
@@ -172,8 +192,8 @@ export interface AsaProductPageDTO {
172
192
  last_synced_at: string;
173
193
  name: string;
174
194
  state: string;
175
- }
176
- export interface AsaAdDTO {
195
+ };
196
+ export type AsaAdDTO = {
177
197
  ad_group_id: string;
178
198
  ad_group_name: null | string;
179
199
  ad_id: number;
@@ -191,8 +211,8 @@ export interface AsaAdDTO {
191
211
  serving_state_reasons: string[];
192
212
  serving_status: string;
193
213
  status: AsaStatus;
194
- }
195
- export interface AsaAutomationDTO {
214
+ };
215
+ export type AsaAutomationDTO = {
196
216
  actions: unknown[];
197
217
  apply_to: unknown[];
198
218
  conditions: unknown[];
@@ -206,46 +226,46 @@ export interface AsaAutomationDTO {
206
226
  run_frequency: Record<string, unknown>;
207
227
  status: number;
208
228
  updated_at: string;
209
- }
210
- export interface AsaAutomationRunDTO {
229
+ };
230
+ export type AsaAutomationRunDTO = {
211
231
  [key: string]: unknown;
212
232
  id?: string;
213
- }
214
- export interface AsaAutomationRunEnqueuedDTO {
233
+ };
234
+ export type AsaAutomationRunEnqueuedDTO = {
215
235
  automation_id: string;
216
236
  dry_run: boolean;
217
237
  run_id: null | string;
218
- }
219
- export interface AsaProductPageSyncDTO {
238
+ };
239
+ export type AsaProductPageSyncDTO = {
220
240
  accepted_at: string;
221
241
  message: string;
222
242
  org_targets: number;
223
243
  replayed: boolean;
224
244
  state: string;
225
245
  sync_id: string;
226
- }
227
- export interface AsaCompetitorTopAppDTO {
246
+ };
247
+ export type AsaCompetitorTopAppDTO = {
228
248
  adamId: number;
229
249
  avgSov: string;
230
250
  countries: string[];
231
251
  iconUrl: null | string;
232
252
  name: null | string;
233
253
  termsCount: number;
234
- }
235
- export interface AsaCompetitorContestedTermDTO {
254
+ };
255
+ export type AsaCompetitorContestedTermDTO = {
236
256
  competitorCount: number;
237
257
  maxSov: string;
238
258
  term: string;
239
- }
240
- export interface AsaCompetitorsSummaryTotalDTO {
259
+ };
260
+ export type AsaCompetitorsSummaryTotalDTO = {
241
261
  competitorsCount: number;
242
262
  countriesAsaCount: number;
243
263
  countriesWithAsaTerms: number;
244
264
  mostContestedTerms: AsaCompetitorContestedTermDTO[];
245
265
  topAppsByPerformance: AsaCompetitorTopAppDTO[];
246
266
  totalUniqueTerms: number;
247
- }
248
- export interface AsaCompetitorAppTermsDTO {
267
+ };
268
+ export type AsaCompetitorAppTermsDTO = {
249
269
  adamId: number;
250
270
  countries: Record<string, {
251
271
  sov: string;
@@ -253,12 +273,12 @@ export interface AsaCompetitorAppTermsDTO {
253
273
  }[]>;
254
274
  iconUrl: null | string;
255
275
  name: null | string;
256
- }
257
- export interface AsaCompetitorsSummaryDTO {
276
+ };
277
+ export type AsaCompetitorsSummaryDTO = {
258
278
  byApps: AsaCompetitorAppTermsDTO[];
259
279
  total: AsaCompetitorsSummaryTotalDTO;
260
- }
261
- export interface AsaMutationError {
280
+ };
281
+ export type AsaMutationError = {
262
282
  apple_error_code?: null | string;
263
283
  apple_error_message?: null | string;
264
284
  entity_type?: string;
@@ -267,12 +287,12 @@ export interface AsaMutationError {
267
287
  retryable?: boolean;
268
288
  validation_error_code?: string;
269
289
  validation_error_message?: string;
270
- }
271
- export interface AsaCampaignMutationDTO {
290
+ };
291
+ export type AsaCampaignMutationDTO = {
272
292
  campaign: AsaCampaignMutationEntity | null;
273
293
  errors: AsaMutationError[];
274
- }
275
- export interface AsaCampaignMutationEntity {
294
+ };
295
+ export type AsaCampaignMutationEntity = {
276
296
  campaign_group_id: string;
277
297
  campaign_id: number;
278
298
  internal_id: string;
@@ -282,39 +302,39 @@ export interface AsaCampaignMutationEntity {
282
302
  serving_state_reasons: null | string[];
283
303
  serving_status: null | string;
284
304
  status: AsaStatus;
285
- }
286
- export interface AsaAdGroupMutationDTO {
305
+ };
306
+ export type AsaAdGroupMutationDTO = {
287
307
  ad_group: null | Record<string, unknown>;
288
308
  errors: AsaMutationError[];
289
- }
290
- export interface AsaAdMutationDTO {
309
+ };
310
+ export type AsaAdMutationDTO = {
291
311
  ad: AsaAdDTO | null;
292
312
  errors: AsaMutationError[];
293
- }
294
- export interface AsaKeywordMutationDTO {
313
+ };
314
+ export type AsaKeywordMutationDTO = {
295
315
  errors: AsaMutationError[];
296
316
  is_validation_failure: boolean;
297
317
  keywords: Record<string, unknown>[];
298
- }
299
- export interface AsaNegativeKeywordMutationDTO {
318
+ };
319
+ export type AsaNegativeKeywordMutationDTO = {
300
320
  errors: AsaMutationError[];
301
321
  is_validation_failure: boolean;
302
322
  negative_keywords: Record<string, unknown>[];
303
- }
304
- export interface AsaAutomationMutationDTO {
323
+ };
324
+ export type AsaAutomationMutationDTO = {
305
325
  automation: AsaAutomationDTO | null;
306
- }
326
+ };
307
327
  export type AsaBulkOperationStatus = 'failed' | 'partial' | 'pending' | 'running' | 'success';
308
- export interface AsaBulkOperationAcceptedDTO {
328
+ export type AsaBulkOperationAcceptedDTO = {
309
329
  operation_id: string;
310
- }
311
- export interface AsaBulkOperationCountsDTO {
330
+ };
331
+ export type AsaBulkOperationCountsDTO = {
312
332
  applied: number;
313
333
  failed: number;
314
334
  pending: number;
315
335
  total: number;
316
- }
317
- export interface AsaBulkOperationObjectDTO {
336
+ };
337
+ export type AsaBulkOperationObjectDTO = {
318
338
  apple_error_code: null | string;
319
339
  apple_error_message: null | string;
320
340
  entity_kind: string;
@@ -322,8 +342,8 @@ export interface AsaBulkOperationObjectDTO {
322
342
  item_ref: string;
323
343
  status: string;
324
344
  step_type: string;
325
- }
326
- export interface AsaBulkOperationStateDTO {
345
+ };
346
+ export type AsaBulkOperationStateDTO = {
327
347
  counts: AsaBulkOperationCountsDTO;
328
348
  created_at: string;
329
349
  finished_at: null | string;
@@ -332,8 +352,8 @@ export interface AsaBulkOperationStateDTO {
332
352
  pipelines: Record<string, unknown>[];
333
353
  started_at: null | string;
334
354
  status: AsaBulkOperationStatus;
335
- }
336
- export interface AsaBulkOperationListItemDTO {
355
+ };
356
+ export type AsaBulkOperationListItemDTO = {
337
357
  app_id: string;
338
358
  created_at: string;
339
359
  error: null | string;
@@ -341,21 +361,21 @@ export interface AsaBulkOperationListItemDTO {
341
361
  operation_id: string;
342
362
  started_at: null | string;
343
363
  status: AsaBulkOperationStatus;
344
- }
345
- export interface AsaBulkOperationListDTO {
364
+ };
365
+ export type AsaBulkOperationListDTO = {
346
366
  items: AsaBulkOperationListItemDTO[];
347
367
  limit: number;
348
368
  offset: number;
349
369
  total: number;
350
- }
351
- export interface AsaTemplateIssueDTO {
370
+ };
371
+ export type AsaTemplateIssueDTO = {
352
372
  column: null | string;
353
373
  message: string;
354
374
  row: null | number;
355
375
  sheet: null | string;
356
- }
357
- export interface AsaBulkConvertResultDTO {
376
+ };
377
+ export type AsaBulkConvertResultDTO = {
358
378
  errors: AsaTemplateIssueDTO[];
359
379
  request: null | Record<string, unknown>;
360
380
  warnings: AsaTemplateIssueDTO[];
361
- }
381
+ };
package/dist/lib/auth.js CHANGED
@@ -1,8 +1,9 @@
1
1
  import { readConfig } from './config.js';
2
2
  export async function resolveToken(configDir) {
3
3
  const envToken = process.env.ADAPTY_TOKEN;
4
- if (envToken)
4
+ if (envToken) {
5
5
  return envToken;
6
+ }
6
7
  const config = await readConfig(configDir);
7
8
  return config.access_token ?? null;
8
9
  }
@@ -1,4 +1,4 @@
1
- import type { Config } from '@oclif/core';
2
1
  import { ApiClient } from './api-client.js';
2
+ import type { Config } from '@oclif/core';
3
3
  export declare function buildUserAgent(config: Config): string;
4
4
  export declare function createAuthenticatedClient(config: Config): Promise<ApiClient>;
@@ -6,8 +6,9 @@ export function buildUserAgent(config) {
6
6
  }
7
7
  export async function createAuthenticatedClient(config) {
8
8
  const token = await resolveToken(config.configDir);
9
- if (!token)
9
+ if (!token) {
10
10
  throw new AuthRequiredError();
11
+ }
11
12
  return new ApiClient({
12
13
  token,
13
14
  userAgent: buildUserAgent(config),
@@ -1,9 +1,9 @@
1
- export interface AdaptyConfig {
1
+ export type AdaptyConfig = {
2
2
  access_token?: string;
3
3
  user?: {
4
4
  email: string;
5
5
  name: string;
6
6
  };
7
- }
7
+ };
8
8
  export declare function readConfig(configDir?: string): Promise<AdaptyConfig>;
9
9
  export declare function writeConfig(config: AdaptyConfig, configDir?: string): Promise<void>;
@@ -1,18 +1,18 @@
1
- import { Command } from '@oclif/core';
1
+ import type { Command } from '@oclif/core';
2
2
  export declare const confirmFlags: {
3
3
  yes: import("@oclif/core/interfaces").BooleanFlag<boolean>;
4
4
  };
5
5
  export type ConfirmDecision = 'ask' | 'proceed' | 'refuse';
6
6
  export declare function decideConfirmation(opts: {
7
- isTty: boolean;
7
+ isTty: boolean | undefined;
8
8
  json: boolean;
9
9
  yes: boolean;
10
10
  }): ConfirmDecision;
11
- export interface MutationPreview {
11
+ export type MutationPreview = {
12
12
  body?: unknown;
13
13
  method: string;
14
14
  path: string;
15
15
  summary: string;
16
- }
16
+ };
17
17
  export declare function renderPreview(preview: MutationPreview): string;
18
18
  export declare function confirmMutation(command: Command, preview: MutationPreview, yes: boolean): Promise<void>;
@@ -1,5 +1,5 @@
1
- import { Flags } from '@oclif/core';
2
1
  import { createInterface } from 'node:readline/promises';
2
+ import { Flags } from '@oclif/core';
3
3
  export const confirmFlags = {
4
4
  yes: Flags.boolean({
5
5
  char: 'y',
@@ -7,22 +7,26 @@ export const confirmFlags = {
7
7
  }),
8
8
  };
9
9
  export function decideConfirmation(opts) {
10
- if (opts.yes)
10
+ if (opts.yes) {
11
11
  return 'proceed';
12
- if (opts.json || !opts.isTty)
12
+ }
13
+ if (opts.json || !opts.isTty) {
13
14
  return 'refuse';
15
+ }
14
16
  return 'ask';
15
17
  }
16
18
  export function renderPreview(preview) {
17
19
  const lines = [preview.summary, `${preview.method} ${preview.path}`];
18
- if (preview.body !== undefined)
20
+ if (preview.body !== undefined) {
19
21
  lines.push(JSON.stringify(preview.body, null, 2));
22
+ }
20
23
  return lines.join('\n');
21
24
  }
22
25
  export async function confirmMutation(command, preview, yes) {
23
- const decision = decideConfirmation({ isTty: process.stdin.isTTY === true, json: command.jsonEnabled(), yes });
24
- if (decision === 'proceed')
26
+ const decision = decideConfirmation({ isTty: process.stdin.isTTY, json: command.jsonEnabled(), yes });
27
+ if (decision === 'proceed') {
25
28
  return;
29
+ }
26
30
  if (decision === 'refuse') {
27
31
  const reason = `${preview.summary} changes your account. Re-run with --yes to apply it without a prompt.`;
28
32
  process.stderr.write(`${reason}\n${renderPreview(preview)}\n`);
@@ -32,8 +36,9 @@ export async function confirmMutation(command, preview, yes) {
32
36
  const reader = createInterface({ input: process.stdin, output: process.stderr });
33
37
  try {
34
38
  const answer = await reader.question('Apply? [y/N] ');
35
- if (!/^y(es)?$/i.test(answer.trim()))
39
+ if (!/^y(es)?$/i.test(answer.trim())) {
36
40
  command.error('Cancelled, nothing was sent.', { exit: 1 });
41
+ }
37
42
  }
38
43
  finally {
39
44
  reader.close();