![Team Sport (teamsport.cz) scraper avatar](https://images.apifyusercontent.com/QwcNdh209IBtTaIhbM79c82lItbReH8Ku86CitF3LWc/rs:fill:92:92/aHR0cHM6Ly9pLmltZ3VyLmNvbS9aYXBKSmlGLnBuZw.webp)
Team Sport (teamsport.cz) scraper
DeprecatedView all Actors![Team Sport (teamsport.cz) scraper](https://images.apifyusercontent.com/QwcNdh209IBtTaIhbM79c82lItbReH8Ku86CitF3LWc/rs:fill:92:92/aHR0cHM6Ly9pLmltZ3VyLmNvbS9aYXBKSmlGLnBuZw.webp)
![](data:image/png;base64,iVBORw0KGgoAAAANSUhEUgAAAgAAAAIACAYAAAD0eNT6AAAABHNCSVQICAgIfAhkiAAAIABJREFUeJzsnedXI0ma9a+QkEXeI2xRQJmuru6Znjmz+8/vftqzb+/Oti1DQRVWBnmDDCDQ+6H3RoWSTCFAVM1sPr9zODhJGUplRtx4rGN1dXUEQRAEQRBsxdzXHoAgCIIgCF8eEQCCIAiCYENEAAiCIAiCDREBIAiCIAg2RASAIAiCINgQEQCCIAiCYENEAAiCIAiCDREBIAiCIAg2RASAIAiCINgQEQCCIAiCYENEAAiCIAiCDREBIAiCIAg2RASAIAiCINgQEQCCIAiCYENEAAiCIAiCDREBIAiCIAg2RASAIAiCINgQEQCCIAiCYENEAAiCIAiCDREBIAiCIAg2RASAIAiCINgQEQCCIAiCYENEAAiCIAiCDREBIAiCIAg2RASAIAiCINgQEQCCIAiCYENEAAiCIAiCDREBIAiCIAg2RASAIAiCINgQEQCCIAiCYENEAAiCIAiCDREBIAiCIAg2RASAIAiCINgQEQCCIAiCYENEAAiCIAiCDREBIAiCIAg2RASAIAiCINgQEQCCIAiCYENEAAiCIAiCDREBIAiCIAg2RASAIAiCINgQEQCCIAiCYENEAAiCIAiCDREBIAiCIAg2RASAIAiCINgQEQCCIAiCYENEAAiCIAiCDREBIAiCIAg2RASAIAiCINgQEQCCIAiCYENEAAiCIAiCDREBIAiCIAg2RASAIAiCINgQEQCCIAiCYENEAAiCIAiCDREBIAiCIAg2RASAIAiCINgQEQCCIAiCYENEAAiCIAiCDREBIAiCIAg2RASAIAiCINgQEQCCIAiCYENEAAiCIAiCDREBIAiCIAg2RASAIAiCINgQEQCCIAiCYENEAAiCIAiCDREBIAiCIAg2RASAIAiCINgQEQCCIAiCYENEAAiCIAiCDREBIAiCIAg2RASAIAiCINgQEQCCIAiCYENEAAiCIAiCDREBIAiCIAg2RASAIAiCINgQEQCCIAiCYENEAAiCIAiCDREBIAiCIAg2RASAIAiCINgQEQCCIAiCYENEAAiCIAiCDREBIAiCIAg2RASAIAiCINgQEQCCIAiCYENEAAiCIAiCDREBIAiCIAg2RASAIAiCINgQEQCCIAiCYENEAAiCIAiCDREBIAiCIAg2RASAIAiCINgQEQCCIAiCYENEAAiCIAiCDREBIAiCIAg2RASAIAiCINgQEQCCIAiCYENEAAiCIAiCDREBIAiCIAg2RASAIAiCINgQEQCCIAiCYENEAAiCIAiCDREBIAiCIAg2RASAIAiCINgQEQCCIAiCYENEAAiCIAiCDREBIAiCIAg2RASAIAiCINgQEQCCIAiCYENEAAiCIAiCDREBIAiCIAg2RASAIAiCINgQEQCCIAiCYENEAAiCIAiCDREBIAiCIAg2RASAIAiCINgQEQCCIAiCYENEAAiCIAiCDREBIAiCIAg2RASAIAiCINgQEQCCIAiCYENEAAiCIAiCDREBIAiCIAg2RASAIAiCINgQEQCCIAiCYENEAAiCIAiCDREBIAiCIAg2RASAIAiCINgQEQCCIAiCYENEAAiCIAiCDREBIAiCIAg2RASAIAiCINgQEQCCIAiCYENEAAiCIAiCDREBIAiCIAg2RASAIAiCINgQEQCCIAiCYENEAAiCIAiCDREBIAiCIAg2RASAIAiCINgQEQCCIAiCYENEAAiCIAiCDREBIAiCIAg2RASAIAiCINgQEQCCIAiCYENEAAiCIAiCDREBIAiCIAg2RASAIAiCINgQEQCCIAiCYENEAAiCIAiCDREBIAiCIAg2RASAIAiCINgQEQCCIAiCYENEAAiCIAiCDREBIAiCIAg2RASAIAiCINgQEQCCIAiCYENEAAiCIAiCDREBIAiCIAg2RASAIAiCINgQEQCCIAiCYENEAAiCIAiCDREBIAiCIAg2RASAIAiCINgQEQCCIAiCYENEAAiCIAiCDREBIAiCIAg2RASAIAiCINgQEQCCIAiCYENEAAiCIAiCDREBIAiCIAg2RASAIAiCINgQEQCCIAiCYENEAAiCIAiCDREBIAiCIAg2RASAIAiCINgQEQCCIAiCYENEAAiCIAiCDREBIAiCIAg2RASAIAiCINgQEQCCIAiCYENEAAiCIAiCDREBIAiCIAg2RASAIAiCINgQEQCCIAiCYENEAAiCIAiCDREBIAiCIAg2RASAIAiCINgQEQCCIAiCYENEAAiCIAiCDREBIAiCIAg2RASAIAiCINgQEQCCIAiCYENEAAiCIAiCDREBIAiCIAg2RASAIAiCINgQ19cewCRcLhe8Xi8WFhYQDAYRDocRDocRCATg9Xrh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AAgQAQAAgAARAAAACBABAACAABEAAAAIEAEAAIAAEQAAAAgQAQAAgAARAAAACBABAACAABEAAAAIEAEAAIAAEQAAAAgQAQAAgAARAAAACBABAACAABEAAAAIEAEAAIAAEQAAAAgQAQAAgAARAAAACBABAACAABEAAAAIEAEAAIAAEQAAAAgQAQAAgAARAAAACBABAACAABEAAAAIEAEAAIAAEQAAAAgQAQAAgAARAAAACBABAACAABEAAAAIEAEAAIAAEQAAAAgQAQAAgAARAAAACBABAACAABEAAAAIEAEAAIAAEQAAAAgQAQAAgAARAAAACBABAACAABEAAAAIEAEAAIAAEQAAAAgQAQAAgAARAAAACBABAACAABEAAAAIEAEAAIAAEQAAAAgQAQAAgAARAAAACBABAACAABEAAAAIEAEAAIAAEQAAAAgQAQAAgAARAAAACBABAACAABEAAAAIEAEAAIAAEQAAAAgQAQAAgAARAAAACBABAACAABEAAAAIEAEAAIAAEQAAAAgQAQAAgAARAAAACBABAACAABEAAAAIEAEAAIAAEQAAAAgQAQAAgAARAAAACBABAACAABEAAAAIEAEAAIAAEQAAAAgQAQAAgAARAAAACBABAACAABEAAAAIEAEAAIAAEQAAAAgQAQAAgAARAAAACBABAACAABEAAAAIEAEAAIAAEQAAAAgQAQAAgAARAAAACBABAACAABEAAAAIEAEAAIAAEQAAAAgQAQAAgAARAAAACBABAACAABEAAAAIEAEAAIAAEQAAAAgQAQAAgAARAAAACBABAACAABEAAAAIEAEAAIAAEQAAAAgQAQAAgAARAAAACBABAACAABEAAAAIEAEAAIAAEQAAAAgQAQAAgAARAAAACBABAACAABEAAAAIEAEAAIAAEQAAAAgQAQAAgAARAAAACBABAACAABEAAAAIEAEAAIAAEQAAAAgQAQAAgAARAAAACBABAACAABEAAAAIEAEAAIAAEQAAAAgQAQAAgAARAAAACBABAACAABEAAAAIEAEAAIAAEQAAAAgQAQAAgAARAAAACBABAACAABEAAAAIEAEAAIAAEQAAAAgQAQAAgAARAAAACBABAACAABEAAAAIEAEAAIAAEQAAAAgQAQAAgAARAAAACBABAACAABEAAAAIEAEAAIAAEQAAAAgQAQAAgAARAAAACBABAACAABEAAAAIEAEAAIAAEQAAAAgQAQAAgAARAAAACBABAACAABEAAAAIEAEAAIAAEQAAAAgQAQAAgAARAAAACBABAACAABEAAAAIEAEAAIAAEQAAAAgQAQAAgAARAAAACBABAACAABEAAAAIEAEAAIAAEQAAAAgQAQAAgAARAAAACBABAACAABEAAAAIEAEAAIAAEQAAAAgQAQAAgAARAAAACBABAACAABEAAAAIEAEAAIAAEQAAAAgQAQAAgAARAAAACBABAACAABEAAAAIEAEAAIAAEQAAAAgQAQAAgAARAAAACBABAACAAP0/3c9j2sdFlWcAAAAASUVORK5CYII=)
This Actor is deprecated
This Actor is unavailable because the developer has decided to deprecate it. Would you like to try a similar Actor instead?
See alternative Actors![Team Sport (teamsport.cz) scraper](https://images.apifyusercontent.com/QwcNdh209IBtTaIhbM79c82lItbReH8Ku86CitF3LWc/rs:fill:92:92/aHR0cHM6Ly9pLmltZ3VyLmNvbS9aYXBKSmlGLnBuZw.webp)
Team Sport (teamsport.cz) scraper
strajk/team-sport-teamsport-cz-scraper
Scrapes products titles, prices, images and availability. Does NOT scrape product details.
Dockerfile
1FROM apify/actor-node:16
2
3COPY package.json ./
4
5RUN npm --quiet set progress=false \
6 && npm install --only=prod --no-optional
7
8COPY . ./
INPUT_SCHEMA.json
1{
2 "title": "Team Sport (teamsport.cz) scraper",
3 "description": "Scrapes products titles, prices, images and availability. Does NOT scrape product details.",
4 "type": "object",
5 "schemaVersion": 1,
6 "properties": {
7 "mode": {
8 "title": "Mode",
9 "description": "",
10 "type": "string",
11 "editor": "select",
12 "default": "TEST",
13 "prefill": "TEST",
14 "enum": [
15 "TEST",
16 "FULL"
17 ],
18 "enumTitles": [
19 "TEST",
20 "FULL"
21 ]
22 },
23 "APIFY_DONT_STORE_IN_DATASET": {
24 "sectionCaption": "Advanced",
25 "sectionDescription": "Advanced options, use only if you know what you're doing.",
26 "title": "Don't store in dataset",
27 "description": "If set to true, the actor will not store the results in the default dataset. Useful when using alternative storage, like own database",
28 "type": "boolean",
29 "default": false,
30 "editor": "checkbox"
31 },
32 "PG_CONNECTION_STRING_NORMALIZED": {
33 "title": "Postgres connection string for normalized data",
34 "description": "If set, actor will store normalized data in Postgres database in PG_DATA_TABLE and PG_DATA_PRICE_TABLE tables",
35 "type": "string",
36 "editor": "textfield"
37 },
38 "PG_DATA_TABLE": {
39 "title": "Postgres table name for product data",
40 "description": "Table name for storing product name, url, image, ...",
41 "type": "string",
42 "editor": "textfield"
43 },
44 "PG_DATA_PRICE_TABLE": {
45 "title": "Postgres table name for price data",
46 "description": "Table name for storing price, original price, stock status, ...",
47 "type": "string",
48 "editor": "textfield"
49 }
50 },
51 "required": [
52 "mode"
53 ]
54}
apify.json
1{
2 "name": "team-sport-teamsport-cz-scraper",
3 "version": "0.1",
4 "buildTag": "latest",
5 "env": null,
6 "defaultRunOptions": {
7 "build": "latest",
8 "timeoutSecs": 3600,
9 "memoryMbytes": 1024
10 }
11}
main.js
1import { Actor } from "apify3";
2import { CheerioCrawler, createCheerioRouter } from "crawlee";
3import { init, save, toNumberOrNull } from "./_utils/common.js";
4
5var LABEL;
6
7(function (LABEL) {
8 LABEL["INDEX"] = "INDEX";
9 LABEL["PRODUCTS"] = "PRODUCTS";
10})(LABEL || (LABEL = {}));
11var MODE;
12
13(function (MODE) {
14 MODE["TEST"] = "TEST";
15 MODE["FULL"] = "FULL";
16})(MODE || (MODE = {}));
17
18// TODO: Solve ?listcnt nicer
19
20async function enqueueInitial(type, crawler) {
21 if (type === MODE.FULL) {
22 await crawler.addRequests([
23 {
24 userData: { label: LABEL.INDEX },
25 url: `https://www.teamsport.cz/znacky/`,
26 },
27 ]);
28 } else if (type === MODE.TEST) {
29 await crawler.addRequests([
30 {
31 userData: { label: LABEL.PRODUCTS },
32 url: `https://www.teamsport.cz/bbb/`,
33 },
34 {
35 userData: { label: LABEL.PRODUCTS },
36 url: `https://www.teamsport.cz/five-ten/`,
37 },
38 {
39 userData: { label: LABEL.PRODUCTS },
40 url: `https://www.teamsport.cz/fox-racing/`,
41 },
42 ]);
43 }
44}
45
46const router = createCheerioRouter();
47
48router.addHandler(LABEL.INDEX, async ({ crawler, $ }) => {
49 const requests = [];
50 $(`.commonListVyrobcu .listLinks a`).each((i, el) => {
51 const url = $(el).attr(`href`);
52 const name = $(el).text();
53 requests.push({
54 userData: { label: LABEL.PRODUCTS, category: name },
55 url: url + `?listcnt=999`,
56 });
57 });
58 await crawler.addRequests(requests);
59});
60
61router.addHandler(LABEL.PRODUCTS, async ({ crawler, $ }) => {
62 const products = [];
63 $(`.categoryProducts article.product`).each((i, el) => {
64 const id = $(el).find(`[data-productid]`).attr(`data-productid`);
65 const url = $(el).find(`a.product__href`).attr(`href`);
66 const title = $(el).find(`a.product__href`).attr(`title`);
67 const priceRaw = $(el).find(`.product__wrapper__inner__price__new`).text(); // `640 Kč`
68 const price = priceRaw.replace(/\D/g, ``);
69 const priceOrigRaw = $(el)
70 .find(`.product__wrapper__inner__price__old`)
71 .text(); // `640 Kč`
72 const priceOrig = priceOrigRaw.replace(/\D/g, ``);
73 const img = $(el).find(`.product__img__src`).attr(`src`);
74 const product = {
75 pid: id,
76 name: title,
77 url: url,
78 img: img,
79 inStock: true, // FIXME: either style='color:#29b237;' or 'skladem'
80 currentPrice: toNumberOrNull(price),
81 originalPrice: toNumberOrNull(priceOrig),
82 currency: `CZK`,
83 };
84 products.push(product);
85 });
86 void save(products);
87});
88
89void Actor.main(async () => {
90 const input = await Actor.getInput();
91 const { mode = MODE.FULL, ...rest } = input ?? {};
92 await init({ actorNameOverride: `teamsport-cz` }, rest);
93 const crawler = new CheerioCrawler({ requestHandler: router });
94 await enqueueInitial(mode, crawler);
95 await crawler.run();
96});
package.json
1{
2 "name": "team-sport-teamsport-cz-scraper",
3 "description": "Scrapes products titles, prices, images and availability. Does NOT scrape product details.",
4 "type": "module",
5 "scripts": {
6 "start": "node ./main.js",
7 "push-to-apify-platform": "npx apify push"
8 },
9 "dependencies": {
10 "apify3": "npm:apify@^3.0.2",
11 "crawlee": "*",
12 "pg": "*",
13 "pg-connection-string": "*",
14 "dotenv": "*",
15 "find-config": "*",
16 "@elastic/elasticsearch": "*",
17 "filenamify": "*"
18 },
19 "apify": {
20 "title": "Team Sport (teamsport.cz) scraper",
21 "description": "Scrapes products titles, prices, images and availability. Does NOT scrape product details.",
22 "isPublic": true,
23 "isDeprecated": false,
24 "isAnonymouslyRunnable": true,
25 "notice": "",
26 "pictureUrl": "",
27 "seoTitle": "",
28 "seoDescription": "",
29 "categories": [
30 "ECOMMERCE"
31 ]
32 }
33}
.actor/actor.json
1{
2 "actorSpecification": 1,
3 "name": "team-sport-teamsport-cz-scraper",
4 "title": "Team Sport (teamsport.cz) scraper",
5 "description": "Scrapes products titles, prices, images and availability. Does NOT scrape product details.",
6 "version": "0.1.0",
7 "storages": {
8 "dataset": {
9 "actorSpecification": 1,
10 "title": "Team Sport (teamsport.cz) scraper",
11 "description": "Scrapes products titles, prices, images and availability. Does NOT scrape product details.",
12 "views": {
13 "overview": {
14 "title": "Overview",
15 "description": "Overview of the most important fields",
16 "transformation": {
17 "fields": [
18 "pid",
19 "name",
20 "url",
21 "img",
22 "inStock",
23 "currentPrice",
24 "originalPrice",
25 "currency"
26 ]
27 },
28 "display": {
29 "component": "table",
30 "columns": [
31 {
32 "label": "Pid",
33 "field": "pid",
34 "format": "text"
35 },
36 {
37 "label": "Name",
38 "field": "name",
39 "format": "text"
40 },
41 {
42 "label": "Url",
43 "field": "url",
44 "format": "link"
45 },
46 {
47 "label": "Img",
48 "field": "img",
49 "format": "image"
50 },
51 {
52 "label": "In Stock",
53 "field": "inStock",
54 "format": "boolean"
55 },
56 {
57 "label": "Current Price",
58 "field": "currentPrice",
59 "format": "number"
60 },
61 {
62 "label": "Original Price",
63 "field": "originalPrice",
64 "format": "number"
65 },
66 {
67 "label": "Currency",
68 "field": "currency",
69 "format": "text"
70 }
71 ]
72 }
73 }
74 }
75 }
76 }
77}
.actor/logo.png
_utils/common.js
1import { createHash } from 'crypto'
2import os from "os"
3import path from "path"
4// eslint-disable-next-line @apify/apify-actor/no-forbidden-node-internals
5import fs from "fs"
6import pg from "pg"
7import pgConnectionString from 'pg-connection-string'
8import { config } from 'dotenv'
9import findConfig from "find-config"
10import { Client as ElasticClient } from "@elastic/elasticsearch"
11import filenamify from 'filenamify'
12import { Dataset } from 'crawlee'
13
14config({ path: findConfig(`.env`) })
15
16const elasticIndexName = `actors-monorepo-shops`
17
18const globalLogsProps = {
19 __NODE_STARTED: new Date().toISOString(),
20}
21
22let actorName
23let pgClient
24let pgClientNormalized
25let elasticClient
26export async function init ({ actorNameOverride }, restInput) {
27 parseEnvFromInput(restInput)
28
29 if (os.platform() === `darwin`) {
30 const filePath = process.argv[1] // ~/Projects/apify-actors-monorepo/actors/foo.ts
31 const basename = path.basename(filePath) // foo.ts
32 actorName = actorNameOverride ?? basename.split(`.`)[0] // foo
33 const gitBranch = fs.readFileSync(path.join(process.cwd(), `..`, `.git/HEAD`), `utf8`)
34 .split(` `)[1]
35 .trim()
36 .replace(`refs/heads/`, ``)
37 const gitCommit = fs.readFileSync(path.join(process.cwd(), `..`, `.git/refs/heads/${gitBranch}`), `utf8`)
38 const gitCommitShort = gitCommit.substring(0, 7)
39 globalLogsProps.__GIT_COMMIT = gitCommitShort
40 }
41
42 if (process.env.APIFY_IS_AT_HOME) {
43 actorName = actorNameOverride ?? process.env.APIFY_ACTOR_ID // Name would be better, but it's not in ENV
44 }
45
46 /* ELASTIC */
47 /* ======= */
48 if (process.env.ELASTIC_CLOUD_ID) {
49 elasticClient = new ElasticClient({
50 cloud: { id: process.env.ELASTIC_CLOUD_ID },
51 auth: { apiKey: process.env.ELASTIC_CLOUD_API_KEY },
52 })
53
54 // const mapping = await elasticClient.indices.getMapping({ index: actorName })
55
56 // eslint-disable-next-line no-inner-declarations
57 async function enforceIndexMapping () {
58 const doesIndexExist = await elasticClient.indices.exists({ index: elasticIndexName })
59 if (!doesIndexExist) await elasticClient.indices.create({ index: elasticIndexName })
60 await elasticClient.indices.putMapping({
61 index: elasticIndexName,
62 body: {
63 properties: {
64 _discount: { type: `float` },
65 originalPrice: { type: `float` },
66 currentPrice: { type: `float` },
67 },
68 },
69 })
70 }
71
72 try {
73 await enforceIndexMapping()
74 } catch (err) {
75 if (err.message.includes(`cannot be changed from type`)) {
76 console.log(`Elastic index ${elasticIndexName} already exists with incorrect mappings. As existing mapping cannot be changed, index will be deleted and recreated.`)
77 await elasticClient.indices.delete({ index: elasticIndexName })
78 await enforceIndexMapping()
79 }
80 }
81 }
82
83 /* POSTGRESQL */
84 /* ========== */
85 if (process.env.PG_CONNECTION_STRING) {
86 const pgConfig = pgConnectionString(process.env.PG_CONNECTION_STRING)
87 // const pgPool = new pg.Pool(pgConfig)
88
89 pgClient = new pg.Client(pgConfig)
90 await pgClient.connect()
91
92 // Check if table exists and have proper columns
93 const { rows: tables } = await pgClient.query(`
94 SELECT table_name
95 FROM information_schema.tables
96 WHERE table_schema = 'public'
97 `)
98
99 // eslint-disable-next-line camelcase
100 const tableExists = tables.some(({ table_name }) => table_name === process.env.PG_DATA_TABLE)
101 if (!tableExists) {
102 throw new Error(`Table ${process.env.PG_DATA_TABLE} does not exist in database ${pgConfig.database}`)
103 }
104
105 // TODO: Handle pgClient closing
106 }
107
108 if (process.env.PG_CONNECTION_STRING_NORMALIZED) {
109 const pgConfig = pgConnectionString(process.env.PG_CONNECTION_STRING_NORMALIZED)
110
111 pgClientNormalized = new pg.Client(pgConfig)
112 await pgClientNormalized.connect()
113
114 // Check if table exists and have proper columns
115 const { rows: tables } = await pgClientNormalized.query(`
116 SELECT table_name
117 FROM information_schema.tables
118 WHERE table_schema = 'public'
119 `)
120
121 // eslint-disable-next-line camelcase
122 const tableMainExists = tables.some(({ table_name }) => table_name === process.env.PG_DATA_TABLE)
123 // eslint-disable-next-line camelcase
124 const tablePricesExists = tables.some(({ table_name }) => table_name === process.env.PG_DATA_PRICE_TABLE)
125 if (!tableMainExists) throw new Error(`Table ${process.env.PG_DATA_TABLE} does not exist in database ${pgConfig.database}`)
126 if (!tablePricesExists) throw new Error(`Table ${process.env.PG_DATA_PRICE_TABLE} does not exist in database ${pgConfig.database}`)
127
128 // TODO: Handle pgClient closing
129 }
130}
131
132// inspired by @drobnikj
133// TODO: Similar, but less obfuscated for easier debugging
134export const createUniqueKeyFromUrl = (url) => {
135 const hash = createHash(`sha256`)
136 const cleanUrl = url.split(`://`)[1] // Remove protocol
137 hash.update(cleanUrl)
138 return hash.digest(`hex`)
139}
140
141/**
142 *
143 * @param {Date} datetime
144 * @return {Promise<void>}
145 */
146export const sleepUntil = async (datetime) => {
147 const now = new Date()
148 const difference = datetime - now
149 if (difference > 0) {
150 return new Promise((resolve) => {
151 setTimeout(resolve, difference)
152 })
153 }
154 return Promise.resolve()
155}
156
157export function parsePrice (string) {
158 let amount, currency
159 const noText = string.replace(/[^\d,.]/g, ``)
160 const decimals = noText.match(/([,.])(\d{2})$/)
161 if (decimals) {
162 const decimalSeparator = decimals[1]
163 // eslint-disable-next-line @typescript-eslint/no-unused-vars, no-unused-vars
164 const decimalAmount = decimals[2]
165 amount = parseInt(noText.split(decimalSeparator)[0])
166 } {
167 const justNumbers = noText.replace(/[,.]/g, ``)
168 amount = parseInt(justNumbers)
169 }
170 return { amount, currency }
171}
172
173export function toNumberOrNull (str) {
174 // TODO: Handle better, but only after adding test
175 if (str === undefined) return null
176 if (str === null) return null
177 if (str === ``) return null
178 const num = Number(str)
179 if (Number.isNaN(num)) return null
180 return num
181}
182
183export async function save (objs) {
184 if (!Array.isArray(objs)) objs = [objs]
185 if (objs.length === 0) return
186
187 const objsExtended = objs.map((obj) => {
188 const objExtended = {
189 ...obj,
190 actorName,
191 ...globalLogsProps,
192 // __NODE_VERSION: global.process.versions.node,
193 // __NODE_UPTIME: global.process.uptime().toFixed(2), // seconds, 2 decimals
194 }
195 // if run on Apify
196 if (process.env.APIFY_IS_AT_HOME) {
197 objExtended.__APIFY_ACTOR_ID = process.env.APIFY_ACTOR_ID
198 objExtended.__APIFY_ACTOR_RUN_ID = process.env.APIFY_ACTOR_RUN_ID
199 objExtended.__APIFY_ACTOR_BUILD_ID = process.env.APIFY_ACTOR_BUILD_ID
200 objExtended.__APIFY_ACTOR_BUILD_NUMBER = process.env.APIFY_ACTOR_BUILD_NUMBER
201 objExtended.__APIFY_ACTOR_TASK_ID = process.env.APIFY_ACTOR_TASK_ID
202 if (!process.env.APIFY_DONT_STORE_IN_DATASET) void Dataset.pushData(obj)
203 }
204 return objExtended
205 })
206 // if runs on local machine (MacOS)
207 if (os.platform() === `darwin`) {
208 const cwd = process.cwd() // ~/Projects/apify-actors-monorepo/actors
209 const storageDir = path.join(cwd, `${actorName}.storage`) // ~/Projects/apify-actors-monorepo/actors/foo.storage
210 if (!fs.existsSync(storageDir)) fs.mkdirSync(storageDir)
211 const dataDir = path.join(storageDir, `data`) // ~/Projects/apify-actors-monorepo/actors/foo.storage/data
212 if (!fs.existsSync(dataDir)) fs.mkdirSync(dataDir)
213 for (const objExtended of objsExtended) {
214 const id = objExtended.id ?? objExtended.pid // ?? uuidv4()
215 const fileName = `${filenamify(id)}.json`
216 const dataFilePath = path.join(dataDir, fileName) // ~/Projects/apify-actors-monorepo/actors/foo.storage/data/foo.json
217 fs.writeFileSync(dataFilePath, JSON.stringify(objExtended, null, 2))
218 }
219 }
220
221 if (pgClient) {
222 const objsPg = objs.map((obj) => ({
223 ...obj,
224 // TODO: This is becoming not nice, and not clear
225 shop: actorName,
226 scrapedAt: new Date().toISOString().split(`T`)[0],
227 }))
228
229 const columns = getColumns(objsPg)
230 const values = getValues(objsPg)
231 const queryString = `
232 INSERT INTO public."${process.env.PG_DATA_TABLE}" (${columns})
233 VALUES (${values})
234 `
235 try {
236 const { rowCount } = await pgClient.query(queryString)
237 console.log(`[save] saved to database: ${JSON.stringify(rowCount)}`)
238 } catch (err) {
239 if (err.message.includes(`violates unique constraint`)) console.warn(`PostgresSQL: violates unique constraint`)
240 else throw err
241 }
242 }
243
244 // Only make sense for HlidacShopu
245 if (pgClientNormalized) {
246 const objsPgData = objs.map((obj) => ({
247 shop: actorName,
248 pid: obj.pid,
249 name: obj.name,
250 url: obj.url,
251 img: obj.img,
252 }))
253
254 const objsPgDataPrice = objs.map((obj) => ({
255 shop: actorName,
256 pid: obj.pid,
257 scrapedAt: new Date().toISOString().split(`T`)[0],
258 currentPrice: obj.currentPrice,
259 originalPrice: obj.originalPrice,
260 inStock: obj.inStock,
261 }))
262
263 const queryString = `
264 INSERT INTO public."${process.env.PG_DATA_TABLE}" (${getColumns(objsPgData)})
265 VALUES (${getValues(objsPgData)})
266 ON CONFLICT DO NOTHING
267 `
268 try {
269 const { rowCount } = await pgClientNormalized.query(queryString)
270 console.log(`[save] saved to database (data): ${JSON.stringify(rowCount)}`)
271 } catch (err) {
272 if (err.message.includes(`violates unique constraint`)) console.warn(`PostgresSQL: violates unique constraint`)
273 else throw err
274 }
275
276 const queryStringPrice = `
277 INSERT INTO public."${process.env.PG_DATA_PRICE_TABLE}" (${getColumns(objsPgDataPrice)})
278 VALUES (${getValues(objsPgDataPrice)})
279 ON CONFLICT DO NOTHING
280 `
281 try {
282 const { rowCount } = await pgClientNormalized.query(queryStringPrice)
283 console.log(`[save] saved to database (price): ${JSON.stringify(rowCount)}`)
284 } catch (err) {
285 if (err.message.includes(`violates unique constraint`)) console.warn(`PostgresSQL: violates unique constraint`)
286 else throw err
287 }
288 }
289
290 if (elasticClient) {
291 // .index creates or updates the document
292 // .create creates a new document if it doesn't exist, 409 if it does
293 // try {
294 // const res = await elasticClient.index({
295 // index: `actors-monorepo-shops`, // TODO: Consider using actorName
296 // id, // foo-bar
297 // document: objExtended, // {...}
298 // })
299 // } catch (err) {
300 // // https://discuss.elastic.co/t/elasticsearch-503-ok-false-message-the-requested-deployment-is-currently-unavailable/200583
301 // if (err.message.includes(`requested resource is currently unavailable`)) console.log(`Elasticsearch is unavailable, skipping, but not aborting`)
302 // else throw err
303 // }
304 }
305}
306
307function getColumns (objs) {
308 return Object.keys(objs[0]).map((key) => `"${key}"`).join(`, `)
309}
310
311function getValues (objs) {
312 return objs.map(objPg => Object.values(objPg).map((value) => {
313 // escape strings to prevent SQL injection
314 if (typeof value === `string`) return `'${value.replace(/'/g, `''`)}'`
315 // convert to DB specific null
316 if (typeof value === `undefined` || value === null) return `NULL`
317 return value
318 }).join(`, `)).join(`), (`)
319}
320
321export function parseEnvFromInput (input) {
322 const env = {}
323 for (const key in input) {
324 if (key === key.toUpperCase()) env[key] = input[key]
325 }
326 console.log(`[parseEnvFromInput] ${JSON.stringify(env)}`)
327 Object.assign(process.env, env)
328}
Developer
Maintained by Community
Categories