@attlaz/client 1.97.0 → 1.99.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/dist/Client.d.ts +6 -0
- package/dist/Client.js +15 -0
- package/dist/MarketPulse/Model/Competitor.d.ts +4 -3
- package/dist/MarketPulse/Model/Competitor.js +6 -5
- package/dist/MarketPulse/Model/MatchedVendorProduct.d.ts +6 -0
- package/dist/MarketPulse/Model/MatchedVendorProduct.js +12 -0
- package/dist/MarketPulse/Model/ReviewMatch.d.ts +8 -0
- package/dist/MarketPulse/Model/ReviewMatch.js +5 -0
- package/dist/MarketPulse/Model/TopCompetitor.d.ts +1 -1
- package/dist/MarketPulse/Model/TopCompetitor.js +2 -2
- package/dist/MarketPulse/Model/Vendor.d.ts +9 -0
- package/dist/MarketPulse/Model/Vendor.js +12 -0
- package/dist/MarketPulse/Service/CompetitorEndpoint.d.ts +24 -2
- package/dist/MarketPulse/Service/CompetitorEndpoint.js +27 -2
- package/dist/MarketPulse/Service/VendorEndpoint.d.ts +26 -0
- package/dist/MarketPulse/Service/VendorEndpoint.js +33 -0
- package/dist/MarketPulse/Service/VendorProductEndpoint.js +4 -0
- package/dist/Model/Component/Component.d.ts +25 -0
- package/dist/Model/Component/Component.js +22 -0
- package/dist/Model/Component/ComponentKind.d.ts +8 -0
- package/dist/Model/Component/ComponentKind.js +18 -0
- package/dist/Model/Component/ComponentStatus.d.ts +31 -0
- package/dist/Model/Component/ComponentStatus.js +31 -0
- package/dist/Model/Component/ComponentVersion.d.ts +16 -0
- package/dist/Model/Component/ComponentVersion.js +15 -0
- package/dist/Model/Timezone.d.ts +18 -0
- package/dist/Model/Timezone.js +22 -0
- package/dist/Service/ComponentEndpoint.d.ts +33 -0
- package/dist/Service/ComponentEndpoint.js +100 -0
- package/dist/Service/TimezoneEndpoint.d.ts +13 -0
- package/dist/Service/TimezoneEndpoint.js +15 -0
- package/dist/index.d.ts +8 -1
- package/dist/index.js +7 -0
- package/dist/version.d.ts +1 -1
- package/dist/version.js +1 -1
- package/package.json +9 -10
package/dist/Client.d.ts
CHANGED
|
@@ -8,6 +8,7 @@ import { ChannelEndpoint } from './Service/ChannelEndpoint.js';
|
|
|
8
8
|
import { CodeDeployEndpoint } from './Service/CodeDeployEndpoint.js';
|
|
9
9
|
import { CodeSourceStrategiesEndpoint } from './Service/CodeSourceStrategiesEndpoint.js';
|
|
10
10
|
import { CollectionsEndpoint } from './Service/CollectionsEndpoint.js';
|
|
11
|
+
import { ComponentEndpoint } from './Service/ComponentEndpoint.js';
|
|
11
12
|
import { CommandExecutionEndpoint } from './Service/CommandExecutionEndpoint.js';
|
|
12
13
|
import { ConfigEndpoint } from './Service/ConfigEndpoint.js';
|
|
13
14
|
import { ConfigurationEndpoint } from './Service/ConfigurationEndpoint.js';
|
|
@@ -20,6 +21,7 @@ import { HealthAlertEndpoint } from './Service/HealthAlertEndpoint.js';
|
|
|
20
21
|
import { InboxEndpoint } from './Service/InboxEndpoint.js';
|
|
21
22
|
import { LogEndpoint } from './Logging/Service/LogEndpoint.js';
|
|
22
23
|
import { PlatformEndpoint } from './Service/PlatformEndpoint.js';
|
|
24
|
+
import { TimezoneEndpoint } from './Service/TimezoneEndpoint.js';
|
|
23
25
|
import { PlatformLanguageEndpoint } from './Service/PlatformLanguageEndpoint.js';
|
|
24
26
|
import { ProjectEndpoint } from './Service/ProjectEndpoint.js';
|
|
25
27
|
import { ProjectEnvironmentEndpoint } from './Service/ProjectEnvironmentEndpoint.js';
|
|
@@ -37,6 +39,7 @@ import { ProductGroupEndpoint } from './MarketPulse/Service/ProductGroupEndpoint
|
|
|
37
39
|
import { CatalogProductEndpoint } from './Catalog/Service/CatalogProductEndpoint.js';
|
|
38
40
|
import { GenerateContentEndpoint } from './DataEnrichment/Service/GenerateContentEndpoint.js';
|
|
39
41
|
import { CompetitorEndpoint } from './MarketPulse/Service/CompetitorEndpoint.js';
|
|
42
|
+
import { VendorEndpoint } from './MarketPulse/Service/VendorEndpoint.js';
|
|
40
43
|
import { PulseStatisticsEndpoint } from './MarketPulse/Service/PulseStatisticsEndpoint.js';
|
|
41
44
|
import { QualityEndpoint } from './DataQuality/Service/QualityEndpoint.js';
|
|
42
45
|
import { CatalogFeedEndpoint } from './FeedManagement/Service/CatalogFeedEndpoint.js';
|
|
@@ -100,6 +103,7 @@ export declare class Client {
|
|
|
100
103
|
getConfigEndpoint(): ConfigEndpoint;
|
|
101
104
|
getInboxEndpoint(): InboxEndpoint;
|
|
102
105
|
getPlatformEndpoint(): PlatformEndpoint;
|
|
106
|
+
getTimezoneEndpoint(): TimezoneEndpoint;
|
|
103
107
|
getSubscriberEndpoint(): SubscriberEndpoint;
|
|
104
108
|
getLogEndPoint(): LogEndpoint;
|
|
105
109
|
getFlowEndpoint(): FlowEndpoint;
|
|
@@ -121,6 +125,7 @@ export declare class Client {
|
|
|
121
125
|
getUserActionEndpoint(): UserActionEndpoint;
|
|
122
126
|
getCommandExecutionEndpoint(): CommandExecutionEndpoint;
|
|
123
127
|
getAccessTokenEndpoint(): AccessTokenEndpoint;
|
|
128
|
+
getComponentEndpoint(): ComponentEndpoint;
|
|
124
129
|
getCollectionsEndpoint(): CollectionsEndpoint;
|
|
125
130
|
getRunnerPoolEndpoint(): RunnerPoolEndpoint;
|
|
126
131
|
getProviderTokenEndpoint(): ProviderTokenEndpoint;
|
|
@@ -138,6 +143,7 @@ export declare class Client {
|
|
|
138
143
|
getProductGroupEndpoint(): ProductGroupEndpoint;
|
|
139
144
|
getGenerateContentEndpoint(): GenerateContentEndpoint;
|
|
140
145
|
getCompetitorEndpoint(): CompetitorEndpoint;
|
|
146
|
+
getVendorEndpoint(): VendorEndpoint;
|
|
141
147
|
getPulseStatisticsEndpoint(): PulseStatisticsEndpoint;
|
|
142
148
|
getQualityEndpoint(): QualityEndpoint;
|
|
143
149
|
getCatalogFeedEndpoint(): CatalogFeedEndpoint;
|
package/dist/Client.js
CHANGED
|
@@ -8,6 +8,7 @@ import { ChannelEndpoint } from './Service/ChannelEndpoint.js';
|
|
|
8
8
|
import { CodeDeployEndpoint } from './Service/CodeDeployEndpoint.js';
|
|
9
9
|
import { CodeSourceStrategiesEndpoint } from './Service/CodeSourceStrategiesEndpoint.js';
|
|
10
10
|
import { CollectionsEndpoint } from './Service/CollectionsEndpoint.js';
|
|
11
|
+
import { ComponentEndpoint } from './Service/ComponentEndpoint.js';
|
|
11
12
|
import { CommandExecutionEndpoint } from './Service/CommandExecutionEndpoint.js';
|
|
12
13
|
import { ConfigEndpoint } from './Service/ConfigEndpoint.js';
|
|
13
14
|
import { ConfigurationEndpoint } from './Service/ConfigurationEndpoint.js';
|
|
@@ -20,6 +21,7 @@ import { HealthAlertEndpoint } from './Service/HealthAlertEndpoint.js';
|
|
|
20
21
|
import { InboxEndpoint } from './Service/InboxEndpoint.js';
|
|
21
22
|
import { LogEndpoint } from './Logging/Service/LogEndpoint.js';
|
|
22
23
|
import { PlatformEndpoint } from './Service/PlatformEndpoint.js';
|
|
24
|
+
import { TimezoneEndpoint } from './Service/TimezoneEndpoint.js';
|
|
23
25
|
import { PlatformLanguageEndpoint } from './Service/PlatformLanguageEndpoint.js';
|
|
24
26
|
import { ProjectEndpoint } from './Service/ProjectEndpoint.js';
|
|
25
27
|
import { ProjectEnvironmentEndpoint } from './Service/ProjectEnvironmentEndpoint.js';
|
|
@@ -37,6 +39,7 @@ import { ProductGroupEndpoint } from './MarketPulse/Service/ProductGroupEndpoint
|
|
|
37
39
|
import { CatalogProductEndpoint } from './Catalog/Service/CatalogProductEndpoint.js';
|
|
38
40
|
import { GenerateContentEndpoint } from './DataEnrichment/Service/GenerateContentEndpoint.js';
|
|
39
41
|
import { CompetitorEndpoint } from './MarketPulse/Service/CompetitorEndpoint.js';
|
|
42
|
+
import { VendorEndpoint } from './MarketPulse/Service/VendorEndpoint.js';
|
|
40
43
|
import { PulseStatisticsEndpoint } from './MarketPulse/Service/PulseStatisticsEndpoint.js';
|
|
41
44
|
import { QualityEndpoint } from './DataQuality/Service/QualityEndpoint.js';
|
|
42
45
|
import { CatalogFeedEndpoint } from './FeedManagement/Service/CatalogFeedEndpoint.js';
|
|
@@ -62,6 +65,7 @@ export class Client {
|
|
|
62
65
|
AdapterEndpoint,
|
|
63
66
|
ChannelEndpoint,
|
|
64
67
|
CodeDeployEndpoint,
|
|
68
|
+
ComponentEndpoint,
|
|
65
69
|
CodeSourceStrategiesEndpoint,
|
|
66
70
|
CommandExecutionEndpoint,
|
|
67
71
|
ConfigEndpoint,
|
|
@@ -74,6 +78,7 @@ export class Client {
|
|
|
74
78
|
InboxEndpoint,
|
|
75
79
|
LogEndpoint,
|
|
76
80
|
PlatformEndpoint,
|
|
81
|
+
TimezoneEndpoint,
|
|
77
82
|
PlatformLanguageEndpoint,
|
|
78
83
|
ProjectEndpoint,
|
|
79
84
|
ProjectEnvironmentEndpoint,
|
|
@@ -104,6 +109,7 @@ export class Client {
|
|
|
104
109
|
CatalogProductEndpoint,
|
|
105
110
|
GenerateContentEndpoint,
|
|
106
111
|
CompetitorEndpoint,
|
|
112
|
+
VendorEndpoint,
|
|
107
113
|
PulseStatisticsEndpoint,
|
|
108
114
|
QualityEndpoint,
|
|
109
115
|
CatalogFeedEndpoint,
|
|
@@ -213,6 +219,9 @@ export class Client {
|
|
|
213
219
|
getPlatformEndpoint() {
|
|
214
220
|
return this.getEndpoint('platform', this.Store.PlatformEndpoint);
|
|
215
221
|
}
|
|
222
|
+
getTimezoneEndpoint() {
|
|
223
|
+
return this.getEndpoint('timezone', this.Store.TimezoneEndpoint);
|
|
224
|
+
}
|
|
216
225
|
getSubscriberEndpoint() {
|
|
217
226
|
return this.getEndpoint('subscriber', this.Store.SubscriberEndpoint);
|
|
218
227
|
}
|
|
@@ -276,6 +285,9 @@ export class Client {
|
|
|
276
285
|
getAccessTokenEndpoint() {
|
|
277
286
|
return this.getEndpoint('accesstoken', this.Store.AccessTokenEndpoint);
|
|
278
287
|
}
|
|
288
|
+
getComponentEndpoint() {
|
|
289
|
+
return this.getEndpoint('component', this.Store.ComponentEndpoint);
|
|
290
|
+
}
|
|
279
291
|
getCollectionsEndpoint() {
|
|
280
292
|
return this.getEndpoint('collections', this.Store.CollectionsEndpoint);
|
|
281
293
|
}
|
|
@@ -327,6 +339,9 @@ export class Client {
|
|
|
327
339
|
getCompetitorEndpoint() {
|
|
328
340
|
return this.getEndpoint('competitor', this.Store.CompetitorEndpoint);
|
|
329
341
|
}
|
|
342
|
+
getVendorEndpoint() {
|
|
343
|
+
return this.getEndpoint('vendor', this.Store.VendorEndpoint);
|
|
344
|
+
}
|
|
330
345
|
getPulseStatisticsEndpoint() {
|
|
331
346
|
return this.getEndpoint('pulse-statistics', this.Store.PulseStatisticsEndpoint);
|
|
332
347
|
}
|
|
@@ -11,11 +11,12 @@ export declare class Competitor {
|
|
|
11
11
|
id: string;
|
|
12
12
|
vendorId: string;
|
|
13
13
|
name: string;
|
|
14
|
-
|
|
14
|
+
/** The competitor's storefront root, scheme included — e.g. `https://shop.com/nl`. */
|
|
15
|
+
url: string;
|
|
15
16
|
icon: string | null;
|
|
16
17
|
type: string | null;
|
|
17
|
-
/**
|
|
18
|
-
|
|
18
|
+
/** ISO 4217 code this storefront quotes prices in. */
|
|
19
|
+
currency: string | null;
|
|
19
20
|
matchCount: number;
|
|
20
21
|
productCount: number;
|
|
21
22
|
priceIndex: number;
|
|
@@ -10,11 +10,12 @@ export class Competitor {
|
|
|
10
10
|
id;
|
|
11
11
|
vendorId;
|
|
12
12
|
name;
|
|
13
|
-
|
|
13
|
+
/** The competitor's storefront root, scheme included — e.g. `https://shop.com/nl`. */
|
|
14
|
+
url = '';
|
|
14
15
|
icon = null;
|
|
15
16
|
type = null;
|
|
16
|
-
/**
|
|
17
|
-
|
|
17
|
+
/** ISO 4217 code this storefront quotes prices in. */
|
|
18
|
+
currency = null;
|
|
18
19
|
matchCount = 0;
|
|
19
20
|
productCount = 0;
|
|
20
21
|
priceIndex = 0;
|
|
@@ -28,10 +29,10 @@ export class Competitor {
|
|
|
28
29
|
}
|
|
29
30
|
static parse(raw) {
|
|
30
31
|
const competitor = new Competitor(raw.id, raw.vendor, raw.name ?? '');
|
|
31
|
-
competitor.
|
|
32
|
+
competitor.url = raw.url ?? '';
|
|
32
33
|
competitor.icon = raw.icon ?? null;
|
|
33
34
|
competitor.type = raw.type ?? null;
|
|
34
|
-
competitor.
|
|
35
|
+
competitor.currency = raw.currency ?? null;
|
|
35
36
|
competitor.matchCount = Number(raw.match_count ?? 0);
|
|
36
37
|
competitor.productCount = Number(raw.product_count ?? 0);
|
|
37
38
|
competitor.priceIndex = Number(raw.price_index ?? 0);
|
|
@@ -19,10 +19,16 @@ export declare class MatchedVendorProduct {
|
|
|
19
19
|
image: string | null;
|
|
20
20
|
brand: string | null;
|
|
21
21
|
gtin: string | null;
|
|
22
|
+
sku: string | null;
|
|
22
23
|
url: string | null;
|
|
23
24
|
price: number;
|
|
25
|
+
originalPrice: number | null;
|
|
26
|
+
/** ISO 4217. Null falls back to the vendor's currency — never assume EUR when rendering. */
|
|
27
|
+
currency: string | null;
|
|
24
28
|
shippingCost: number;
|
|
25
29
|
inStock: boolean | null;
|
|
30
|
+
/** The scraped attribute bag (category, tags, variant options). Keys are data, not schema. */
|
|
31
|
+
properties: Record<string, unknown> | null;
|
|
26
32
|
updatedAt: Date | null;
|
|
27
33
|
constructor(id: string);
|
|
28
34
|
static parse(raw: ApiRecord): MatchedVendorProduct;
|
|
@@ -18,10 +18,16 @@ export class MatchedVendorProduct {
|
|
|
18
18
|
image = null;
|
|
19
19
|
brand = null;
|
|
20
20
|
gtin = null;
|
|
21
|
+
sku = null;
|
|
21
22
|
url = null;
|
|
22
23
|
price = 0;
|
|
24
|
+
originalPrice = null;
|
|
25
|
+
/** ISO 4217. Null falls back to the vendor's currency — never assume EUR when rendering. */
|
|
26
|
+
currency = null;
|
|
23
27
|
shippingCost = 0;
|
|
24
28
|
inStock = null;
|
|
29
|
+
/** The scraped attribute bag (category, tags, variant options). Keys are data, not schema. */
|
|
30
|
+
properties = null;
|
|
25
31
|
updatedAt = null;
|
|
26
32
|
constructor(id) {
|
|
27
33
|
this.id = id;
|
|
@@ -38,10 +44,16 @@ export class MatchedVendorProduct {
|
|
|
38
44
|
product.image = raw.image ?? null;
|
|
39
45
|
product.brand = raw.brand ?? null;
|
|
40
46
|
product.gtin = raw.gtin ?? null;
|
|
47
|
+
product.sku = raw.sku ?? null;
|
|
41
48
|
product.url = raw.url ?? null;
|
|
42
49
|
product.price = parseFloat(raw.price) || 0;
|
|
50
|
+
product.originalPrice = raw.original_price === null || raw.original_price === undefined
|
|
51
|
+
? null
|
|
52
|
+
: parseFloat(raw.original_price);
|
|
53
|
+
product.currency = raw.currency ?? null;
|
|
43
54
|
product.shippingCost = parseFloat(raw.shipping_cost) || 0;
|
|
44
55
|
product.inStock = typeof raw.in_stock === 'boolean' ? raw.in_stock : null;
|
|
56
|
+
product.properties = raw.properties ?? null;
|
|
45
57
|
product.updatedAt = raw.updated ? new Date(raw.updated) : null;
|
|
46
58
|
return product;
|
|
47
59
|
}
|
|
@@ -6,11 +6,19 @@ export type ReviewProduct = {
|
|
|
6
6
|
name: string;
|
|
7
7
|
brand: string | null;
|
|
8
8
|
gtin: string | null;
|
|
9
|
+
sku: string | null;
|
|
9
10
|
price: number | null;
|
|
11
|
+
originalPrice: number | null;
|
|
12
|
+
/** ISO 4217. Null falls back to the vendor's currency — never assume EUR when rendering. */
|
|
13
|
+
currency: string | null;
|
|
14
|
+
shippingCost: number | null;
|
|
10
15
|
url: string | null;
|
|
11
16
|
image: string | null;
|
|
17
|
+
/** Lifted out of {@link properties} because the matcher scores against it. */
|
|
12
18
|
category: string | null;
|
|
13
19
|
inStock: boolean | null;
|
|
20
|
+
/** The scraped attribute bag (tags, variant options, …). Keys are data, not schema. */
|
|
21
|
+
properties: Record<string, unknown> | null;
|
|
14
22
|
};
|
|
15
23
|
/** The competitor side additionally names the vendor it came from. */
|
|
16
24
|
export type ReviewCompetitorProduct = ReviewProduct & {
|
|
@@ -45,11 +45,16 @@ export class ReviewMatch {
|
|
|
45
45
|
name: raw.name,
|
|
46
46
|
brand: raw.brand ?? null,
|
|
47
47
|
gtin: raw.gtin ?? null,
|
|
48
|
+
sku: raw.sku ?? null,
|
|
48
49
|
price: raw.price ?? null,
|
|
50
|
+
originalPrice: raw.original_price ?? null,
|
|
51
|
+
currency: raw.currency ?? null,
|
|
52
|
+
shippingCost: raw.shipping_cost ?? null,
|
|
49
53
|
url: raw.url ?? null,
|
|
50
54
|
image: raw.image ?? null,
|
|
51
55
|
category: raw.category ?? null,
|
|
52
56
|
inStock: typeof raw.in_stock === 'boolean' ? raw.in_stock : null,
|
|
57
|
+
properties: raw.properties ?? null,
|
|
53
58
|
};
|
|
54
59
|
}
|
|
55
60
|
}
|
|
@@ -9,7 +9,7 @@ export class TopCompetitor {
|
|
|
9
9
|
competitorId;
|
|
10
10
|
vendorId;
|
|
11
11
|
vendorName = '';
|
|
12
|
-
|
|
12
|
+
vendorUrl = '';
|
|
13
13
|
vendorIcon = null;
|
|
14
14
|
matchCount = 0;
|
|
15
15
|
productCount = 0;
|
|
@@ -26,7 +26,7 @@ export class TopCompetitor {
|
|
|
26
26
|
static parse(raw) {
|
|
27
27
|
const competitor = new TopCompetitor(raw.competitor, raw.vendor);
|
|
28
28
|
competitor.vendorName = raw.vendor_name ?? '';
|
|
29
|
-
competitor.
|
|
29
|
+
competitor.vendorUrl = raw.vendor_url ?? '';
|
|
30
30
|
competitor.vendorIcon = raw.vendor_icon ?? null;
|
|
31
31
|
competitor.matchCount = Number(raw.match_count ?? 0);
|
|
32
32
|
competitor.productCount = Number(raw.product_count ?? 0);
|
|
@@ -2,11 +2,20 @@ import { ApiRecord } from '../../Model/ApiRecord.js';
|
|
|
2
2
|
/**
|
|
3
3
|
* A shop whose products Market Pulse tracks — your own or a competitor's. It is the same entity in
|
|
4
4
|
* both roles; a {@link Competitor} is a vendor as one catalog watches it.
|
|
5
|
+
*
|
|
6
|
+
* One vendor is one storefront view: a single `url`, a single `currency`. A merchant selling in
|
|
7
|
+
* several markets is several vendors.
|
|
5
8
|
*/
|
|
6
9
|
export declare class Vendor {
|
|
7
10
|
id: string;
|
|
8
11
|
name: string;
|
|
12
|
+
/** Storefront root, scheme included, no trailing slash — e.g. `https://shop.com/nl`. */
|
|
13
|
+
url: string;
|
|
9
14
|
icon: string | null;
|
|
15
|
+
/** ISO 4217 code this storefront quotes prices in. */
|
|
16
|
+
currency: string | null;
|
|
17
|
+
/** Platform hint used to pick a scrape strategy, e.g. `shopify`. */
|
|
18
|
+
type: string | null;
|
|
10
19
|
constructor(id: string, name: string);
|
|
11
20
|
static parse(raw: ApiRecord): Vendor;
|
|
12
21
|
}
|
|
@@ -1,18 +1,30 @@
|
|
|
1
1
|
/**
|
|
2
2
|
* A shop whose products Market Pulse tracks — your own or a competitor's. It is the same entity in
|
|
3
3
|
* both roles; a {@link Competitor} is a vendor as one catalog watches it.
|
|
4
|
+
*
|
|
5
|
+
* One vendor is one storefront view: a single `url`, a single `currency`. A merchant selling in
|
|
6
|
+
* several markets is several vendors.
|
|
4
7
|
*/
|
|
5
8
|
export class Vendor {
|
|
6
9
|
id;
|
|
7
10
|
name;
|
|
11
|
+
/** Storefront root, scheme included, no trailing slash — e.g. `https://shop.com/nl`. */
|
|
12
|
+
url = '';
|
|
8
13
|
icon = null;
|
|
14
|
+
/** ISO 4217 code this storefront quotes prices in. */
|
|
15
|
+
currency = null;
|
|
16
|
+
/** Platform hint used to pick a scrape strategy, e.g. `shopify`. */
|
|
17
|
+
type = null;
|
|
9
18
|
constructor(id, name) {
|
|
10
19
|
this.id = id;
|
|
11
20
|
this.name = name;
|
|
12
21
|
}
|
|
13
22
|
static parse(raw) {
|
|
14
23
|
const vendor = new Vendor(raw.id, raw.name ?? '');
|
|
24
|
+
vendor.url = raw.url ?? '';
|
|
15
25
|
vendor.icon = raw.icon ?? null;
|
|
26
|
+
vendor.currency = raw.currency ?? null;
|
|
27
|
+
vendor.type = raw.type ?? null;
|
|
16
28
|
return vendor;
|
|
17
29
|
}
|
|
18
30
|
}
|
|
@@ -10,6 +10,28 @@ import { Competitor } from '../Model/Competitor.js';
|
|
|
10
10
|
export declare class CompetitorEndpoint extends Endpoint {
|
|
11
11
|
getByCatalog(catalogId: CatalogId | string, pagination?: CursorPagination | null): Promise<CollectionResult<Competitor>>;
|
|
12
12
|
getById(competitorId: string): Promise<Competitor | null>;
|
|
13
|
-
/**
|
|
14
|
-
|
|
13
|
+
/**
|
|
14
|
+
* Start watching an existing vendor as a competitor of this catalog.
|
|
15
|
+
*
|
|
16
|
+
* The vendor must already exist — create it with {@link VendorEndpoint.create} first. Re-adding
|
|
17
|
+
* a previously removed competitor reactivates the original link, so its matches and price
|
|
18
|
+
* history survive.
|
|
19
|
+
*
|
|
20
|
+
* Returns the link itself (`id`, `catalog`, `vendor`), not the populated competitor; read it
|
|
21
|
+
* back with {@link getById} if you need the counts and timestamps.
|
|
22
|
+
*/
|
|
23
|
+
add(catalogId: CatalogId | string, vendorId: string): Promise<CompetitorLink | null>;
|
|
24
|
+
/**
|
|
25
|
+
* Stop watching a competitor.
|
|
26
|
+
*
|
|
27
|
+
* The vendor, its products and their price history are kept — only the catalog↔vendor link is
|
|
28
|
+
* retired, so {@link add} can resume it later.
|
|
29
|
+
*/
|
|
30
|
+
remove(catalogId: CatalogId | string, competitorId: string): Promise<void>;
|
|
15
31
|
}
|
|
32
|
+
/** The catalog↔vendor link row returned by {@link CompetitorEndpoint.add}. */
|
|
33
|
+
export type CompetitorLink = {
|
|
34
|
+
id: string;
|
|
35
|
+
catalogId: string;
|
|
36
|
+
vendorId: string;
|
|
37
|
+
};
|
|
@@ -16,9 +16,34 @@ export class CompetitorEndpoint extends Endpoint {
|
|
|
16
16
|
const result = await this.requestObject(path('/pulse/competing-vendors/:competitorId', { competitorId }), null, Competitor.parse, 'GET');
|
|
17
17
|
return result.getData();
|
|
18
18
|
}
|
|
19
|
-
/**
|
|
19
|
+
/**
|
|
20
|
+
* Start watching an existing vendor as a competitor of this catalog.
|
|
21
|
+
*
|
|
22
|
+
* The vendor must already exist — create it with {@link VendorEndpoint.create} first. Re-adding
|
|
23
|
+
* a previously removed competitor reactivates the original link, so its matches and price
|
|
24
|
+
* history survive.
|
|
25
|
+
*
|
|
26
|
+
* Returns the link itself (`id`, `catalog`, `vendor`), not the populated competitor; read it
|
|
27
|
+
* back with {@link getById} if you need the counts and timestamps.
|
|
28
|
+
*/
|
|
20
29
|
async add(catalogId, vendorId) {
|
|
21
|
-
const result = await this.requestObject(path('/pulse/catalogs/:catalogId/competing-vendors', { catalogId: catalogId.toString() }), { vendor: vendorId },
|
|
30
|
+
const result = await this.requestObject(path('/pulse/catalogs/:catalogId/competing-vendors', { catalogId: catalogId.toString() }), { vendor: vendorId }, (raw) => ({
|
|
31
|
+
id: raw.id,
|
|
32
|
+
catalogId: raw.catalog,
|
|
33
|
+
vendorId: raw.vendor,
|
|
34
|
+
}), 'POST');
|
|
22
35
|
return result.getData();
|
|
23
36
|
}
|
|
37
|
+
/**
|
|
38
|
+
* Stop watching a competitor.
|
|
39
|
+
*
|
|
40
|
+
* The vendor, its products and their price history are kept — only the catalog↔vendor link is
|
|
41
|
+
* retired, so {@link add} can resume it later.
|
|
42
|
+
*/
|
|
43
|
+
async remove(catalogId, competitorId) {
|
|
44
|
+
await this.requestObject(path('/pulse/catalogs/:catalogId/competing-vendors/:competitorId', {
|
|
45
|
+
catalogId: catalogId.toString(),
|
|
46
|
+
competitorId,
|
|
47
|
+
}), null, (raw) => raw, 'DELETE');
|
|
48
|
+
}
|
|
24
49
|
}
|
|
@@ -0,0 +1,26 @@
|
|
|
1
|
+
import { Endpoint } from '../../Service/Endpoint.js';
|
|
2
|
+
import { Vendor } from '../Model/Vendor.js';
|
|
3
|
+
/**
|
|
4
|
+
* Vendors — the shops Market Pulse knows about, independent of who watches them.
|
|
5
|
+
*
|
|
6
|
+
* Creating a vendor and watching it as a competitor are separate steps: create here, then link it
|
|
7
|
+
* to a catalog with {@link CompetitorEndpoint.add}. That split is what lets one vendor be watched
|
|
8
|
+
* by several catalogs without being duplicated.
|
|
9
|
+
*
|
|
10
|
+
* There is deliberately no "list vendors" method: vendors are global, so listing them would expose
|
|
11
|
+
* every customer's tracked shops. Discovery gets designed alongside the UI that needs it.
|
|
12
|
+
*/
|
|
13
|
+
export declare class VendorEndpoint extends Endpoint {
|
|
14
|
+
getById(vendorId: string): Promise<Vendor | null>;
|
|
15
|
+
/**
|
|
16
|
+
* Register a shop.
|
|
17
|
+
*
|
|
18
|
+
* `url` is normalised server-side (scheme added, trailing slash dropped, host lowercased), and a
|
|
19
|
+
* storefront that already has a vendor is rejected — so this is safe to call without checking
|
|
20
|
+
* first, but it will throw rather than return the existing vendor.
|
|
21
|
+
*
|
|
22
|
+
* @param url Storefront root. A locale path is significant: `https://shop.com/nl` is a
|
|
23
|
+
* different storefront from `https://shop.com`.
|
|
24
|
+
*/
|
|
25
|
+
create(name: string, url: string, currency?: string | null, type?: string | null): Promise<Vendor | null>;
|
|
26
|
+
}
|
|
@@ -0,0 +1,33 @@
|
|
|
1
|
+
import { path } from '../../Http/Data/Path.js';
|
|
2
|
+
import { Endpoint } from '../../Service/Endpoint.js';
|
|
3
|
+
import { Vendor } from '../Model/Vendor.js';
|
|
4
|
+
/**
|
|
5
|
+
* Vendors — the shops Market Pulse knows about, independent of who watches them.
|
|
6
|
+
*
|
|
7
|
+
* Creating a vendor and watching it as a competitor are separate steps: create here, then link it
|
|
8
|
+
* to a catalog with {@link CompetitorEndpoint.add}. That split is what lets one vendor be watched
|
|
9
|
+
* by several catalogs without being duplicated.
|
|
10
|
+
*
|
|
11
|
+
* There is deliberately no "list vendors" method: vendors are global, so listing them would expose
|
|
12
|
+
* every customer's tracked shops. Discovery gets designed alongside the UI that needs it.
|
|
13
|
+
*/
|
|
14
|
+
export class VendorEndpoint extends Endpoint {
|
|
15
|
+
async getById(vendorId) {
|
|
16
|
+
const result = await this.requestObject(path('/pulse/vendors/:vendorId', { vendorId }), null, Vendor.parse, 'GET');
|
|
17
|
+
return result.getData();
|
|
18
|
+
}
|
|
19
|
+
/**
|
|
20
|
+
* Register a shop.
|
|
21
|
+
*
|
|
22
|
+
* `url` is normalised server-side (scheme added, trailing slash dropped, host lowercased), and a
|
|
23
|
+
* storefront that already has a vendor is rejected — so this is safe to call without checking
|
|
24
|
+
* first, but it will throw rather than return the existing vendor.
|
|
25
|
+
*
|
|
26
|
+
* @param url Storefront root. A locale path is significant: `https://shop.com/nl` is a
|
|
27
|
+
* different storefront from `https://shop.com`.
|
|
28
|
+
*/
|
|
29
|
+
async create(name, url, currency = null, type = null) {
|
|
30
|
+
const result = await this.requestObject('/pulse/vendors', { name, url, currency, type }, Vendor.parse, 'POST');
|
|
31
|
+
return result.getData();
|
|
32
|
+
}
|
|
33
|
+
}
|
|
@@ -55,6 +55,7 @@ export class VendorProductEndpoint extends Endpoint {
|
|
|
55
55
|
image: product.image,
|
|
56
56
|
identifier: product.identifier,
|
|
57
57
|
gtin: product.gtin,
|
|
58
|
+
sku: product.sku,
|
|
58
59
|
brand: product.brand,
|
|
59
60
|
url: product.url,
|
|
60
61
|
currency: product.currency,
|
|
@@ -70,6 +71,7 @@ export class VendorProductEndpoint extends Endpoint {
|
|
|
70
71
|
/** Update the mutable fields of an existing vendor product (JSON-patch style, per the API). */
|
|
71
72
|
async update(product) {
|
|
72
73
|
const operations = [
|
|
74
|
+
{ op: 'add', path: 'name', value: product.name },
|
|
73
75
|
{ op: 'add', path: 'price', value: product.price },
|
|
74
76
|
{ op: 'add', path: 'original_price', value: product.originalPrice },
|
|
75
77
|
{ op: 'add', path: 'brand', value: product.brand },
|
|
@@ -78,6 +80,8 @@ export class VendorProductEndpoint extends Endpoint {
|
|
|
78
80
|
{ op: 'add', path: 'url', value: product.url },
|
|
79
81
|
{ op: 'add', path: 'gtin', value: product.gtin },
|
|
80
82
|
{ op: 'add', path: 'image', value: product.image },
|
|
83
|
+
{ op: 'add', path: 'sku', value: product.sku },
|
|
84
|
+
{ op: 'add', path: 'currency', value: product.currency },
|
|
81
85
|
{ op: 'add', path: 'properties', value: product.properties },
|
|
82
86
|
];
|
|
83
87
|
if (product.id === null) {
|
|
@@ -0,0 +1,25 @@
|
|
|
1
|
+
import { State } from '../State.js';
|
|
2
|
+
import { ComponentKind } from './ComponentKind.js';
|
|
3
|
+
import { ComponentVersion } from './ComponentVersion.js';
|
|
4
|
+
/** One thing the platform builds and deploys: an api, a service, or the runner. */
|
|
5
|
+
export declare class Component {
|
|
6
|
+
id: string;
|
|
7
|
+
name: string;
|
|
8
|
+
kind: ComponentKind;
|
|
9
|
+
/** Registry path without a tag, e.g. `registry.gitlab.com/attlaz/platform/message_service`. */
|
|
10
|
+
imageRepository: string;
|
|
11
|
+
/**
|
|
12
|
+
* The version that *should* be deployed — desired state, set by promoting. Null means the
|
|
13
|
+
* component is not managed this way, never "deploy nothing".
|
|
14
|
+
*/
|
|
15
|
+
activeVersionId: string | null;
|
|
16
|
+
/**
|
|
17
|
+
* The active version itself, present only when requested with `?expand=active_version`.
|
|
18
|
+
* Null both when nothing is promoted and when the caller did not ask for it — check
|
|
19
|
+
* `activeVersionId` to tell those apart.
|
|
20
|
+
*/
|
|
21
|
+
activeVersion: ComponentVersion | null;
|
|
22
|
+
createdAt: Date;
|
|
23
|
+
updatedAt: Date;
|
|
24
|
+
state: State;
|
|
25
|
+
}
|
|
@@ -0,0 +1,22 @@
|
|
|
1
|
+
/** One thing the platform builds and deploys: an api, a service, or the runner. */
|
|
2
|
+
export class Component {
|
|
3
|
+
id;
|
|
4
|
+
name;
|
|
5
|
+
kind;
|
|
6
|
+
/** Registry path without a tag, e.g. `registry.gitlab.com/attlaz/platform/message_service`. */
|
|
7
|
+
imageRepository;
|
|
8
|
+
/**
|
|
9
|
+
* The version that *should* be deployed — desired state, set by promoting. Null means the
|
|
10
|
+
* component is not managed this way, never "deploy nothing".
|
|
11
|
+
*/
|
|
12
|
+
activeVersionId;
|
|
13
|
+
/**
|
|
14
|
+
* The active version itself, present only when requested with `?expand=active_version`.
|
|
15
|
+
* Null both when nothing is promoted and when the caller did not ask for it — check
|
|
16
|
+
* `activeVersionId` to tell those apart.
|
|
17
|
+
*/
|
|
18
|
+
activeVersion = null;
|
|
19
|
+
createdAt;
|
|
20
|
+
updatedAt;
|
|
21
|
+
state;
|
|
22
|
+
}
|
|
@@ -0,0 +1,18 @@
|
|
|
1
|
+
export var ComponentKind;
|
|
2
|
+
(function (ComponentKind) {
|
|
3
|
+
ComponentKind["Api"] = "api";
|
|
4
|
+
ComponentKind["Service"] = "service";
|
|
5
|
+
ComponentKind["Runner"] = "runner";
|
|
6
|
+
})(ComponentKind || (ComponentKind = {}));
|
|
7
|
+
(function (ComponentKind) {
|
|
8
|
+
ComponentKind.fromString = (input) => {
|
|
9
|
+
switch (input) {
|
|
10
|
+
case ComponentKind.Api:
|
|
11
|
+
case ComponentKind.Service:
|
|
12
|
+
case ComponentKind.Runner:
|
|
13
|
+
return input;
|
|
14
|
+
default:
|
|
15
|
+
throw new Error('Unknown ComponentKind "' + input + '"');
|
|
16
|
+
}
|
|
17
|
+
};
|
|
18
|
+
})(ComponentKind || (ComponentKind = {}));
|
|
@@ -0,0 +1,31 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* What one Kubernetes deployment of a component actually runs, as last observed.
|
|
3
|
+
*
|
|
4
|
+
* The counterpart to `Component.activeVersionId`: that is what should run, this is what does.
|
|
5
|
+
* One row per deployment — a component running several version lines has several.
|
|
6
|
+
*/
|
|
7
|
+
export declare class ComponentStatus {
|
|
8
|
+
id: string;
|
|
9
|
+
componentId: string;
|
|
10
|
+
namespace: string;
|
|
11
|
+
deploymentName: string;
|
|
12
|
+
/** Fully-qualified image including the tag, exactly as the container reports it. */
|
|
13
|
+
image: string;
|
|
14
|
+
readyReplicas: number;
|
|
15
|
+
desiredReplicas: number;
|
|
16
|
+
/**
|
|
17
|
+
* Whether enough replicas are ready to serve. **True for a deployment scaled to zero** — with no
|
|
18
|
+
* replicas wanted, the requirement is trivially met. Treat `desiredReplicas > 0 &&
|
|
19
|
+
* readyReplicas < desiredReplicas` as unhealthy rather than trusting this alone.
|
|
20
|
+
*/
|
|
21
|
+
available: boolean;
|
|
22
|
+
/**
|
|
23
|
+
* Reads backwards: false means the last rollout missed its deadline, i.e. the deploy failed.
|
|
24
|
+
* True covers both a settled deployment and one still rolling out. Replica counts cannot
|
|
25
|
+
* substitute — a new pod that never becomes ready leaves the old ones serving, so the counts
|
|
26
|
+
* still look right while the deploy has failed.
|
|
27
|
+
*/
|
|
28
|
+
progressing: boolean;
|
|
29
|
+
/** When the cluster was last read. Stale means nobody has looked, not that all is well. */
|
|
30
|
+
observedAt: Date;
|
|
31
|
+
}
|
|
@@ -0,0 +1,31 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* What one Kubernetes deployment of a component actually runs, as last observed.
|
|
3
|
+
*
|
|
4
|
+
* The counterpart to `Component.activeVersionId`: that is what should run, this is what does.
|
|
5
|
+
* One row per deployment — a component running several version lines has several.
|
|
6
|
+
*/
|
|
7
|
+
export class ComponentStatus {
|
|
8
|
+
id;
|
|
9
|
+
componentId;
|
|
10
|
+
namespace;
|
|
11
|
+
deploymentName;
|
|
12
|
+
/** Fully-qualified image including the tag, exactly as the container reports it. */
|
|
13
|
+
image;
|
|
14
|
+
readyReplicas;
|
|
15
|
+
desiredReplicas;
|
|
16
|
+
/**
|
|
17
|
+
* Whether enough replicas are ready to serve. **True for a deployment scaled to zero** — with no
|
|
18
|
+
* replicas wanted, the requirement is trivially met. Treat `desiredReplicas > 0 &&
|
|
19
|
+
* readyReplicas < desiredReplicas` as unhealthy rather than trusting this alone.
|
|
20
|
+
*/
|
|
21
|
+
available;
|
|
22
|
+
/**
|
|
23
|
+
* Reads backwards: false means the last rollout missed its deadline, i.e. the deploy failed.
|
|
24
|
+
* True covers both a settled deployment and one still rolling out. Replica counts cannot
|
|
25
|
+
* substitute — a new pod that never becomes ready leaves the old ones serving, so the counts
|
|
26
|
+
* still look right while the deploy has failed.
|
|
27
|
+
*/
|
|
28
|
+
progressing;
|
|
29
|
+
/** When the cluster was last read. Stale means nobody has looked, not that all is well. */
|
|
30
|
+
observedAt;
|
|
31
|
+
}
|
|
@@ -0,0 +1,16 @@
|
|
|
1
|
+
import { State } from '../State.js';
|
|
2
|
+
/** One tag of a component as the container registry has it. */
|
|
3
|
+
export declare class ComponentVersion {
|
|
4
|
+
id: string;
|
|
5
|
+
componentId: string;
|
|
6
|
+
/** The registry tag, e.g. `1.15.1`. */
|
|
7
|
+
version: string;
|
|
8
|
+
/** Fully-qualified reference including the tag. */
|
|
9
|
+
image: string;
|
|
10
|
+
/**
|
|
11
|
+
* When the image was published to the registry and became available to select. Not a build time,
|
|
12
|
+
* and not evidence it was ever deployed — most versions never are.
|
|
13
|
+
*/
|
|
14
|
+
releasedAt: Date;
|
|
15
|
+
state: State;
|
|
16
|
+
}
|
|
@@ -0,0 +1,15 @@
|
|
|
1
|
+
/** One tag of a component as the container registry has it. */
|
|
2
|
+
export class ComponentVersion {
|
|
3
|
+
id;
|
|
4
|
+
componentId;
|
|
5
|
+
/** The registry tag, e.g. `1.15.1`. */
|
|
6
|
+
version;
|
|
7
|
+
/** Fully-qualified reference including the tag. */
|
|
8
|
+
image;
|
|
9
|
+
/**
|
|
10
|
+
* When the image was published to the registry and became available to select. Not a build time,
|
|
11
|
+
* and not evidence it was ever deployed — most versions never are.
|
|
12
|
+
*/
|
|
13
|
+
releasedAt;
|
|
14
|
+
state;
|
|
15
|
+
}
|
|
@@ -0,0 +1,18 @@
|
|
|
1
|
+
import { ApiRecord } from './ApiRecord.js';
|
|
2
|
+
/**
|
|
3
|
+
* A timezone the platform accepts, as reported by the API.
|
|
4
|
+
*
|
|
5
|
+
* The list comes from the server rather than from the browser's own `Intl`: the two run different
|
|
6
|
+
* tz database versions, so a browser-built list can offer a zone the API then rejects, or spell one
|
|
7
|
+
* differently from the name the API stores.
|
|
8
|
+
*/
|
|
9
|
+
export declare class Timezone {
|
|
10
|
+
name: string;
|
|
11
|
+
/**
|
|
12
|
+
* Offset from UTC in minutes at the moment the API answered — positive east of Greenwich, and
|
|
13
|
+
* not a whole number of hours everywhere (Asia/Katmandu is 345). It follows daylight saving, so
|
|
14
|
+
* it is a value to display, never one to store or to compare zones by.
|
|
15
|
+
*/
|
|
16
|
+
utcOffsetMinutes: number;
|
|
17
|
+
static parse(raw: ApiRecord): Timezone;
|
|
18
|
+
}
|
|
@@ -0,0 +1,22 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* A timezone the platform accepts, as reported by the API.
|
|
3
|
+
*
|
|
4
|
+
* The list comes from the server rather than from the browser's own `Intl`: the two run different
|
|
5
|
+
* tz database versions, so a browser-built list can offer a zone the API then rejects, or spell one
|
|
6
|
+
* differently from the name the API stores.
|
|
7
|
+
*/
|
|
8
|
+
export class Timezone {
|
|
9
|
+
name;
|
|
10
|
+
/**
|
|
11
|
+
* Offset from UTC in minutes at the moment the API answered — positive east of Greenwich, and
|
|
12
|
+
* not a whole number of hours everywhere (Asia/Katmandu is 345). It follows daylight saving, so
|
|
13
|
+
* it is a value to display, never one to store or to compare zones by.
|
|
14
|
+
*/
|
|
15
|
+
utcOffsetMinutes;
|
|
16
|
+
static parse(raw) {
|
|
17
|
+
const timezone = new Timezone();
|
|
18
|
+
timezone.name = raw.name;
|
|
19
|
+
timezone.utcOffsetMinutes = raw.utc_offset_minutes;
|
|
20
|
+
return timezone;
|
|
21
|
+
}
|
|
22
|
+
}
|
|
@@ -0,0 +1,33 @@
|
|
|
1
|
+
import { Component } from '../Model/Component/Component.js';
|
|
2
|
+
import { ComponentKind } from '../Model/Component/ComponentKind.js';
|
|
3
|
+
import { ComponentStatus } from '../Model/Component/ComponentStatus.js';
|
|
4
|
+
import { ComponentVersion } from '../Model/Component/ComponentVersion.js';
|
|
5
|
+
import { CursorPagination } from '../Model/Pagination/CursorPagination.js';
|
|
6
|
+
import { CollectionResult } from '../Model/Result/CollectionResult.js';
|
|
7
|
+
import { Endpoint } from './Endpoint.js';
|
|
8
|
+
/**
|
|
9
|
+
* The platform's own inventory: what we build, which versions the registry has, what the cluster is
|
|
10
|
+
* actually running, and which version each component should run.
|
|
11
|
+
*
|
|
12
|
+
* Root-only, reads included.
|
|
13
|
+
*/
|
|
14
|
+
export declare class ComponentEndpoint extends Endpoint {
|
|
15
|
+
/**
|
|
16
|
+
* @param expand pass `['active_version']` to receive the promoted version inline instead of
|
|
17
|
+
* just its id — one call rather than one per component.
|
|
18
|
+
* @param kinds restrict to these kinds; a collection, so apis and services can be fetched
|
|
19
|
+
* together without the runner.
|
|
20
|
+
*/
|
|
21
|
+
getAll(pagination?: CursorPagination | null, expand?: string[] | null, kinds?: ComponentKind[] | null): Promise<CollectionResult<Component>>;
|
|
22
|
+
getVersions(componentId: string, pagination?: CursorPagination | null): Promise<CollectionResult<ComponentVersion>>;
|
|
23
|
+
/** Observed state for every component at once — one call, not one per component. */
|
|
24
|
+
getStatus(pagination?: CursorPagination | null): Promise<CollectionResult<ComponentStatus>>;
|
|
25
|
+
/**
|
|
26
|
+
* Declare which version a component should run. Writes desired state only — the rollout is a
|
|
27
|
+
* separate asynchronous step that can fail, so a success here does not mean it is running.
|
|
28
|
+
*/
|
|
29
|
+
setActiveVersion(componentId: string, versionId: string): Promise<void>;
|
|
30
|
+
private static parseComponent;
|
|
31
|
+
private static parseVersion;
|
|
32
|
+
private static parseStatus;
|
|
33
|
+
}
|
|
@@ -0,0 +1,100 @@
|
|
|
1
|
+
import { path } from '../Http/Data/Path.js';
|
|
2
|
+
import { QueryString } from '../Http/Data/QueryString.js';
|
|
3
|
+
import { Component } from '../Model/Component/Component.js';
|
|
4
|
+
import { ComponentKind } from '../Model/Component/ComponentKind.js';
|
|
5
|
+
import { ComponentStatus } from '../Model/Component/ComponentStatus.js';
|
|
6
|
+
import { ComponentVersion } from '../Model/Component/ComponentVersion.js';
|
|
7
|
+
import { State } from '../Model/State.js';
|
|
8
|
+
import { Utils } from '../Utils.js';
|
|
9
|
+
import { Endpoint } from './Endpoint.js';
|
|
10
|
+
/**
|
|
11
|
+
* The platform's own inventory: what we build, which versions the registry has, what the cluster is
|
|
12
|
+
* actually running, and which version each component should run.
|
|
13
|
+
*
|
|
14
|
+
* Root-only, reads included.
|
|
15
|
+
*/
|
|
16
|
+
export class ComponentEndpoint extends Endpoint {
|
|
17
|
+
/**
|
|
18
|
+
* @param expand pass `['active_version']` to receive the promoted version inline instead of
|
|
19
|
+
* just its id — one call rather than one per component.
|
|
20
|
+
* @param kinds restrict to these kinds; a collection, so apis and services can be fetched
|
|
21
|
+
* together without the runner.
|
|
22
|
+
*/
|
|
23
|
+
async getAll(pagination = null, expand = null, kinds = null) {
|
|
24
|
+
const queryString = new QueryString('/system/components');
|
|
25
|
+
queryString.addPagination(pagination);
|
|
26
|
+
if (kinds !== null && kinds.length > 0) {
|
|
27
|
+
queryString.set('kind', kinds);
|
|
28
|
+
}
|
|
29
|
+
if (expand !== null && expand.length > 0) {
|
|
30
|
+
queryString.set('expand', expand);
|
|
31
|
+
}
|
|
32
|
+
return await this.requestCollection(queryString, ComponentEndpoint.parseComponent, null, 'GET');
|
|
33
|
+
}
|
|
34
|
+
async getVersions(componentId, pagination = null) {
|
|
35
|
+
const queryString = new QueryString(path('/system/components/:componentId/versions', { componentId }));
|
|
36
|
+
queryString.addPagination(pagination);
|
|
37
|
+
return await this.requestCollection(queryString, ComponentEndpoint.parseVersion, null, 'GET');
|
|
38
|
+
}
|
|
39
|
+
/** Observed state for every component at once — one call, not one per component. */
|
|
40
|
+
async getStatus(pagination = null) {
|
|
41
|
+
const queryString = new QueryString('/system/component-status');
|
|
42
|
+
queryString.addPagination(pagination);
|
|
43
|
+
return await this.requestCollection(queryString, ComponentEndpoint.parseStatus, null, 'GET');
|
|
44
|
+
}
|
|
45
|
+
/**
|
|
46
|
+
* Declare which version a component should run. Writes desired state only — the rollout is a
|
|
47
|
+
* separate asynchronous step that can fail, so a success here does not mean it is running.
|
|
48
|
+
*/
|
|
49
|
+
async setActiveVersion(componentId, versionId) {
|
|
50
|
+
const queryString = new QueryString(path('/system/components/:componentId/active-version', { componentId }));
|
|
51
|
+
// `_formatted` because formatParameters() strips a trailing `_id` from body keys, which
|
|
52
|
+
// would turn `version_id` into `version` — a key the endpoint does not read.
|
|
53
|
+
await this.requestObject(queryString, { version_id: versionId, _formatted: true }, (raw) => raw, 'POST');
|
|
54
|
+
}
|
|
55
|
+
static parseComponent(raw) {
|
|
56
|
+
const component = new Component();
|
|
57
|
+
component.id = raw.id;
|
|
58
|
+
component.name = raw.name;
|
|
59
|
+
component.kind = ComponentKind.fromString(raw.kind);
|
|
60
|
+
component.imageRepository = raw.image_repository;
|
|
61
|
+
// `active_version` is either the id or, when expanded, the version itself.
|
|
62
|
+
const activeVersion = raw.active_version ?? null;
|
|
63
|
+
if (activeVersion !== null && typeof activeVersion === 'object') {
|
|
64
|
+
component.activeVersion = ComponentEndpoint.parseVersion(activeVersion);
|
|
65
|
+
component.activeVersionId = component.activeVersion.id;
|
|
66
|
+
}
|
|
67
|
+
else {
|
|
68
|
+
component.activeVersionId = activeVersion;
|
|
69
|
+
component.activeVersion = null;
|
|
70
|
+
}
|
|
71
|
+
component.createdAt = Utils.parseRawDate(raw.created_at);
|
|
72
|
+
component.updatedAt = Utils.parseRawDate(raw.updated_at);
|
|
73
|
+
component.state = State.fromString(raw.state);
|
|
74
|
+
return component;
|
|
75
|
+
}
|
|
76
|
+
static parseVersion(raw) {
|
|
77
|
+
const version = new ComponentVersion();
|
|
78
|
+
version.id = raw.id;
|
|
79
|
+
version.componentId = raw.component;
|
|
80
|
+
version.version = raw.version;
|
|
81
|
+
version.image = raw.image;
|
|
82
|
+
version.releasedAt = Utils.parseRawDate(raw.released_at);
|
|
83
|
+
version.state = State.fromString(raw.state);
|
|
84
|
+
return version;
|
|
85
|
+
}
|
|
86
|
+
static parseStatus(raw) {
|
|
87
|
+
const status = new ComponentStatus();
|
|
88
|
+
status.id = raw.id;
|
|
89
|
+
status.componentId = raw.component;
|
|
90
|
+
status.namespace = raw.namespace;
|
|
91
|
+
status.deploymentName = raw.deployment_name;
|
|
92
|
+
status.image = raw.image;
|
|
93
|
+
status.readyReplicas = raw.ready_replicas;
|
|
94
|
+
status.desiredReplicas = raw.desired_replicas;
|
|
95
|
+
status.available = raw.available;
|
|
96
|
+
status.progressing = raw.progressing;
|
|
97
|
+
status.observedAt = Utils.parseRawDate(raw.observed_at);
|
|
98
|
+
return status;
|
|
99
|
+
}
|
|
100
|
+
}
|
|
@@ -0,0 +1,13 @@
|
|
|
1
|
+
import { CollectionResult } from '../Model/Result/CollectionResult.js';
|
|
2
|
+
import { Timezone } from '../Model/Timezone.js';
|
|
3
|
+
import { Endpoint } from './Endpoint.js';
|
|
4
|
+
export declare class TimezoneEndpoint extends Endpoint {
|
|
5
|
+
/**
|
|
6
|
+
* Every timezone a schedule or a user profile can be set to.
|
|
7
|
+
*
|
|
8
|
+
* Deliberately not paginated: this is a fixed reference list of a few hundred entries owned by
|
|
9
|
+
* the platform's runtime, not a growing collection, and a picker needs all of it to filter
|
|
10
|
+
* against.
|
|
11
|
+
*/
|
|
12
|
+
getAll(): Promise<CollectionResult<Timezone>>;
|
|
13
|
+
}
|
|
@@ -0,0 +1,15 @@
|
|
|
1
|
+
import { QueryString } from '../Http/Data/QueryString.js';
|
|
2
|
+
import { Timezone } from '../Model/Timezone.js';
|
|
3
|
+
import { Endpoint } from './Endpoint.js';
|
|
4
|
+
export class TimezoneEndpoint extends Endpoint {
|
|
5
|
+
/**
|
|
6
|
+
* Every timezone a schedule or a user profile can be set to.
|
|
7
|
+
*
|
|
8
|
+
* Deliberately not paginated: this is a fixed reference list of a few hundred entries owned by
|
|
9
|
+
* the platform's runtime, not a growing collection, and a picker needs all of it to filter
|
|
10
|
+
* against.
|
|
11
|
+
*/
|
|
12
|
+
async getAll() {
|
|
13
|
+
return await this.requestCollection(new QueryString('/timezones'), Timezone.parse);
|
|
14
|
+
}
|
|
15
|
+
}
|
package/dist/index.d.ts
CHANGED
|
@@ -127,7 +127,8 @@ export { CatalogProductEndpoint } from './Catalog/Service/CatalogProductEndpoint
|
|
|
127
127
|
export { GenerateContentBatch } from './DataEnrichment/Model/GenerateContentBatch.js';
|
|
128
128
|
export { GenerateContentBatchData } from './DataEnrichment/Model/GenerateContentBatchData.js';
|
|
129
129
|
export { GenerateContentEndpoint } from './DataEnrichment/Service/GenerateContentEndpoint.js';
|
|
130
|
-
export { CompetitorEndpoint } from './MarketPulse/Service/CompetitorEndpoint.js';
|
|
130
|
+
export { CompetitorEndpoint, CompetitorLink } from './MarketPulse/Service/CompetitorEndpoint.js';
|
|
131
|
+
export { VendorEndpoint } from './MarketPulse/Service/VendorEndpoint.js';
|
|
131
132
|
export { MarketSummaryEntry } from './MarketPulse/Model/MarketSummaryEntry.js';
|
|
132
133
|
export { ProductSegmentType } from './MarketPulse/Model/ProductSegmentType.js';
|
|
133
134
|
export { ProductsSegment } from './MarketPulse/Model/ProductsSegment.js';
|
|
@@ -160,6 +161,7 @@ export { SearchResult } from './Model/Search/SearchResult.js';
|
|
|
160
161
|
export { Trigger } from './Model/Trigger/Trigger.js';
|
|
161
162
|
/** Worker* */
|
|
162
163
|
export { Platform } from './Model/Worker/Platform.js';
|
|
164
|
+
export { Timezone } from './Model/Timezone.js';
|
|
163
165
|
export { PlatformImage } from './Model/Worker/PlatformImage.js';
|
|
164
166
|
export { InfrastructureConfiguration } from './Model/Worker/InfrastructureConfiguration.js';
|
|
165
167
|
/** Deployment * */
|
|
@@ -208,6 +210,10 @@ export type { UserActionFilter } from './Model/User/UserActionFilter.js';
|
|
|
208
210
|
export { UserSummary } from './Model/User/UserSummary.js';
|
|
209
211
|
export type { UserSummaryType } from './Model/User/UserSummary.js';
|
|
210
212
|
export { RunnerImage } from './Model/Runner/RunnerImage.js';
|
|
213
|
+
export { Component } from './Model/Component/Component.js';
|
|
214
|
+
export { ComponentKind } from './Model/Component/ComponentKind.js';
|
|
215
|
+
export { ComponentStatus } from './Model/Component/ComponentStatus.js';
|
|
216
|
+
export { ComponentVersion } from './Model/Component/ComponentVersion.js';
|
|
211
217
|
export { CommandExecutionHistory } from './Model/Command/CommandExecutionHistory.js';
|
|
212
218
|
export { CommandExecutionStatus } from './Model/Command/CommandExecutionStatus.js';
|
|
213
219
|
export { CommandExecutionFilter } from './Model/Command/CommandExecutionFilter.js';
|
|
@@ -222,6 +228,7 @@ export { LogEndpoint } from './Logging/Service/LogEndpoint.js';
|
|
|
222
228
|
export { WorkspaceMemberEndpoint } from './Service/WorkspaceMemberEndpoint.js';
|
|
223
229
|
export { InboxEndpoint } from './Service/InboxEndpoint.js';
|
|
224
230
|
export { PlatformEndpoint } from './Service/PlatformEndpoint.js';
|
|
231
|
+
export { TimezoneEndpoint } from './Service/TimezoneEndpoint.js';
|
|
225
232
|
export { CodeDeployEndpoint } from './Service/CodeDeployEndpoint.js';
|
|
226
233
|
export { ProjectEnvironmentEndpoint } from './Service/ProjectEnvironmentEndpoint.js';
|
|
227
234
|
export { SearchEndpoint } from './Service/SearchEndpoint.js';
|
package/dist/index.js
CHANGED
|
@@ -104,6 +104,7 @@ export { CatalogProductEndpoint } from './Catalog/Service/CatalogProductEndpoint
|
|
|
104
104
|
export { GenerateContentBatch } from './DataEnrichment/Model/GenerateContentBatch.js';
|
|
105
105
|
export { GenerateContentEndpoint } from './DataEnrichment/Service/GenerateContentEndpoint.js';
|
|
106
106
|
export { CompetitorEndpoint } from './MarketPulse/Service/CompetitorEndpoint.js';
|
|
107
|
+
export { VendorEndpoint } from './MarketPulse/Service/VendorEndpoint.js';
|
|
107
108
|
export { PulseStatisticsEndpoint } from './MarketPulse/Service/PulseStatisticsEndpoint.js';
|
|
108
109
|
export { QualityDataset } from './DataQuality/Model/QualityDataset.js';
|
|
109
110
|
export { QualityEntity } from './DataQuality/Model/QualityEntity.js';
|
|
@@ -126,6 +127,7 @@ export { SearchResult } from './Model/Search/SearchResult.js';
|
|
|
126
127
|
export { Trigger } from './Model/Trigger/Trigger.js';
|
|
127
128
|
/** Worker* */
|
|
128
129
|
export { Platform } from './Model/Worker/Platform.js';
|
|
130
|
+
export { Timezone } from './Model/Timezone.js';
|
|
129
131
|
export { PlatformImage } from './Model/Worker/PlatformImage.js';
|
|
130
132
|
export { InfrastructureConfiguration } from './Model/Worker/InfrastructureConfiguration.js';
|
|
131
133
|
/** Deployment * */
|
|
@@ -171,6 +173,10 @@ export { UserAuthProvider } from './Model/User/UserAuthProvider.js';
|
|
|
171
173
|
export { UserAction } from './Model/User/UserAction.js';
|
|
172
174
|
export { UserSummary } from './Model/User/UserSummary.js';
|
|
173
175
|
export { RunnerImage } from './Model/Runner/RunnerImage.js';
|
|
176
|
+
export { Component } from './Model/Component/Component.js';
|
|
177
|
+
export { ComponentKind } from './Model/Component/ComponentKind.js';
|
|
178
|
+
export { ComponentStatus } from './Model/Component/ComponentStatus.js';
|
|
179
|
+
export { ComponentVersion } from './Model/Component/ComponentVersion.js';
|
|
174
180
|
export { CommandExecutionHistory } from './Model/Command/CommandExecutionHistory.js';
|
|
175
181
|
export { CommandExecutionStatus } from './Model/Command/CommandExecutionStatus.js';
|
|
176
182
|
export { Endpoint } from './Service/Endpoint.js';
|
|
@@ -185,6 +191,7 @@ export { LogEndpoint } from './Logging/Service/LogEndpoint.js';
|
|
|
185
191
|
export { WorkspaceMemberEndpoint } from './Service/WorkspaceMemberEndpoint.js';
|
|
186
192
|
export { InboxEndpoint } from './Service/InboxEndpoint.js';
|
|
187
193
|
export { PlatformEndpoint } from './Service/PlatformEndpoint.js';
|
|
194
|
+
export { TimezoneEndpoint } from './Service/TimezoneEndpoint.js';
|
|
188
195
|
export { CodeDeployEndpoint } from './Service/CodeDeployEndpoint.js';
|
|
189
196
|
export { ProjectEnvironmentEndpoint } from './Service/ProjectEnvironmentEndpoint.js';
|
|
190
197
|
export { SearchEndpoint } from './Service/SearchEndpoint.js';
|
package/dist/version.d.ts
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
export declare const VERSION = "1.
|
|
1
|
+
export declare const VERSION = "1.98.0";
|
package/dist/version.js
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
export const VERSION = "1.
|
|
1
|
+
export const VERSION = "1.98.0";
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@attlaz/client",
|
|
3
|
-
"version": "1.
|
|
3
|
+
"version": "1.99.0",
|
|
4
4
|
"description": "Javascript Client to access Attlaz API",
|
|
5
5
|
"types": "./dist/index.d.ts",
|
|
6
6
|
"main": "./dist/index.js",
|
|
@@ -37,14 +37,15 @@
|
|
|
37
37
|
"license": "MIT",
|
|
38
38
|
"scripts": {
|
|
39
39
|
"prebuild": "npm run setversion",
|
|
40
|
-
"prepare": "npm run clean && tsc --project tsconfig.
|
|
41
|
-
"build": "npm run clean && tsc",
|
|
40
|
+
"prepare": "npm run clean && tsc --project tsconfig.build.json && npm run setversion",
|
|
41
|
+
"build": "npm run clean && tsc -p tsconfig.build.json",
|
|
42
42
|
"setversion": "node -p \"'export const VERSION = ' + JSON.stringify(require('./package.json').version) + ';'\" > src/version.ts",
|
|
43
43
|
"clean": "rimraf dist",
|
|
44
44
|
"scan": "docker run -v .:/path zricethezav/gitleaks:latest detect --source=\"/path\" ",
|
|
45
|
-
"test": "
|
|
46
|
-
"
|
|
47
|
-
"
|
|
45
|
+
"test": "vitest run --mode unit",
|
|
46
|
+
"typecheck": "tsc --project tsconfig.json --noEmit",
|
|
47
|
+
"test-integration": "vitest run --mode integration",
|
|
48
|
+
"test-live": "vitest --mode unit"
|
|
48
49
|
},
|
|
49
50
|
"publishConfig": {
|
|
50
51
|
"access": "public",
|
|
@@ -52,7 +53,6 @@
|
|
|
52
53
|
"registry": "https://registry.npmjs.org"
|
|
53
54
|
},
|
|
54
55
|
"devDependencies": {
|
|
55
|
-
"@types/jest": "^30.0.0",
|
|
56
56
|
"@types/node": "^26.1.2",
|
|
57
57
|
"@typescript-eslint/eslint-plugin": "^8.59.3",
|
|
58
58
|
"@typescript-eslint/parser": "^8.59.3",
|
|
@@ -63,10 +63,9 @@
|
|
|
63
63
|
"eslint-plugin-jsdoc": "^62.9.0",
|
|
64
64
|
"eslint-plugin-prefer-arrow": "^1.2.3",
|
|
65
65
|
"eslint-plugin-promise": "^7.3.0",
|
|
66
|
-
"jest": "^30.4.2",
|
|
67
66
|
"rimraf": "^6.1.3",
|
|
68
|
-
"
|
|
69
|
-
"
|
|
67
|
+
"typescript": "^6.0.3",
|
|
68
|
+
"vitest": "^4.1.10"
|
|
70
69
|
},
|
|
71
70
|
"directories": {
|
|
72
71
|
"test": "test"
|