diff --git a/sites/magticom.ge/magticom.ge.config.js b/sites/magticom.ge/magticom.ge.config.js new file mode 100644 index 00000000..7dcb425c --- /dev/null +++ b/sites/magticom.ge/magticom.ge.config.js @@ -0,0 +1,88 @@ +const cheerio = require('cheerio') +const axios = require('axios') +const dayjs = require('dayjs') +const utc = require('dayjs/plugin/utc') +const timezone = require('dayjs/plugin/timezone') +const customParseFormat = require('dayjs/plugin/customParseFormat') + +dayjs.extend(utc) +dayjs.extend(timezone) +dayjs.extend(customParseFormat) + +module.exports = { + site: 'magticom.ge', + url: 'https://www.magticom.ge/request/channel-program.php', + request: { + method: 'POST', + headers: { + 'Content-Type': 'application/x-www-form-urlencoded; charset=UTF-8', + Referer: 'https://www.magticom.ge/en/tv/tv-services/tv-guide' + }, + data({ channel, date }) { + const params = new URLSearchParams() + params.append('channelId', channel.site_id) + params.append('start', date.unix()) + params.append('end', date.add(1, 'd').unix()) + + return params + } + }, + logo({ channel }) { + return channel.logo + }, + parser({ content }) { + let programs = [] + const items = parseItems(content) + items.forEach(item => { + programs.push({ + title: item.title, + description: item.info, + start: parseStart(item), + stop: parseStop(item) + }) + }) + + return programs + }, + async channels({ country, lang }) { + const html = await axios + .get(`https://www.magticom.ge/en/tv/tv-services/tv-guide`) + .then(r => r.data) + .catch(console.log) + + const $ = cheerio.load(html) + const channels = $( + '#article > article > div > div > div.tv-guide > div.tv-guide-channels > div.tv-guide-channel' + ).toArray() + + return channels.map(item => { + const $item = cheerio.load(item) + const imgSrc = $item('.tv-guide-channel-title > div > img').attr('src') + const channelId = $item('*').data('id') + return { + lang: 'ka', + site_id: channelId, + name: $item('.tv-guide-channel-title > div > div').text(), + logo: imgSrc ? `https://www.magticom.ge/${imgSrc}` : null + } + }) + } +} + +function parseStart(item) { + return dayjs.tz(item.startTimestamp, 'YYYY-MM-DDTHH:mm:ss', 'Asia/Tbilisi') +} + +function parseStop(item) { + return dayjs.tz(item.endTimestamp, 'YYYY-MM-DDTHH:mm:ss', 'Asia/Tbilisi') +} + +function parseItems(content) { + let data + try { + data = JSON.parse(content) + } catch (err) {} + if (!data || !Array.isArray(data)) return [] + + return data +} diff --git a/sites/magticom.ge/magticom.ge.test.js b/sites/magticom.ge/magticom.ge.test.js new file mode 100644 index 00000000..46d0e69e --- /dev/null +++ b/sites/magticom.ge/magticom.ge.test.js @@ -0,0 +1,71 @@ +// node ./scripts/channels.js --config=./sites/magticom.ge/magticom.ge.config.js --output=./sites/magticom.ge/magticom.ge_ge.channels.xml +// npx epg-grabber --config=sites/magticom.ge/magticom.ge.config.js --channels=sites/magticom.ge/magticom.ge_ge.channels.xml --output=.gh-pages/guides/ge/magticom.ge.epg.xml --days=2 + +const { parser, url, request, logo } = require('./magticom.ge.config.js') +const dayjs = require('dayjs') +const utc = require('dayjs/plugin/utc') +const customParseFormat = require('dayjs/plugin/customParseFormat') +dayjs.extend(customParseFormat) +dayjs.extend(utc) + +const date = dayjs.utc('2021-11-22', 'YYYY-MM-DD').startOf('d') +const channel = { + site_id: '260', + xmltv_id: 'BollywoodTVRossiya.il', + logo: 'https://www.magticom.ge/images/channels/MjAyMS8wNy8yMi8zNDAyZDAzZi00MThlLTQyZWUtYTc1Zi05YjYyZjAzNDIwZjJCb2xseXdvb0RfLV81NjBfeF80MDgucG5n.jpg' +} + +it('can generate valid url', () => { + expect(url).toBe('https://www.magticom.ge/request/channel-program.php') +}) + +it('can generate valid request method', () => { + expect(request.method).toBe('POST') +}) + +it('can generate valid request headers', () => { + expect(request.headers).toMatchObject({ + 'Content-Type': 'application/x-www-form-urlencoded; charset=UTF-8', + Referer: 'https://www.magticom.ge/en/tv/tv-services/tv-guide' + }) +}) + +it('can generate valid request data', () => { + const result = request.data({ channel, date }) + expect(result.has('channelId')).toBe(true) + expect(result.has('start')).toBe(true) + expect(result.has('end')).toBe(true) +}) + +it('can generate valid logo url', () => { + expect(logo({ channel })).toBe( + 'https://www.magticom.ge/images/channels/MjAyMS8wNy8yMi8zNDAyZDAzZi00MThlLTQyZWUtYTc1Zi05YjYyZjAzNDIwZjJCb2xseXdvb0RfLV81NjBfeF80MDgucG5n.jpg' + ) +}) + +it('can parse response', () => { + const content = `[{\"id\":2313254118,\"channelId\":260,\"startTimestamp\":\"2021-11-22T07:00:00\",\"endTimestamp\":\"2021-11-22T09:00:00\",\"duration\":null,\"title\":\"\\u0425\\\/\\u0444 \\\"\\u041d\\u0435\\u0440\\u0430\\u0432\\u043d\\u044b\\u0439 \\u0431\\u0440\\u0430\\u043a\\\".\",\"subTitle\":\"\\u0425\\\/\\u0444 \\\"\\u041d\\u0435\\u0440\\u0430\\u0432\\u043d\\u044b\\u0439 \\u0431\\u0440\\u0430\\u043a\\\".\",\"info\":\"\\u0413\\u0443\\u0434\\u0436\\u0430\\u0440\\u0430\\u0442\\u0435\\u0446 \\u0425\\u0430\\u0441\\u043c\\u0443\\u043a\\u0445 \\u041f\\u0430\\u0442\\u0435\\u043b \\u043f\\u043e\\u0441\\u0441\\u043e\\u0440\\u0438\\u043b\\u0441\\u044f \\u0441 \\u043d\\u043e\\u0432\\u044b\\u043c \\u0441\\u043e\\u0441\\u0435\\u0434\\u043e\\u043c \\u0413\\u0443\\u0433\\u0433\\u0438 \\u0422\\u0430\\u043d\\u0434\\u043e\\u043d\\u043e\\u043c. \\u041d\\u043e \\u0438\\u043c \\u043f\\u0440\\u0438\\u0445\\u043e\\u0434\\u0438\\u0442\\u0441\\u044f \\u043f\\u043e\\u043c\\u0438\\u0440\\u0438\\u0442\\u044c\\u0441\\u044f, \\u043a\\u043e\\u0433\\u0434\\u0430 \\u0438\\u0445 \\u0434\\u0435\\u0442\\u0438 \\u0432\\u043b\\u044e\\u0431\\u043b\\u044f\\u044e\\u0442\\u0441\\u044f \\u0434\\u0440\\u0443\\u0433 \\u0432 \\u0434\\u0440\\u0443\\u0433\\u0430. \\u0420\\u0435\\u0436\\u0438\\u0441\\u0441\\u0435\\u0440: \\u0421\\u0430\\u043d\\u0434\\u0436\\u0430\\u0439 \\u0427\\u0445\\u0435\\u043b. \\u0410\\u043a\\u0442\\u0435\\u0440\\u044b: \\u0420\\u0438\\u0448\\u0438 \\u041a\\u0430\\u043f\\u0443\\u0440, \\u041f\\u0430\\u0440\\u0435\\u0448 \\u0420\\u0430\\u0432\\u0430\\u043b, \\u0412\\u0438\\u0440 \\u0414\\u0430\\u0441. 2017 \\u0433\\u043e\\u0434.\",\"pg\":null,\"year\":null,\"country\":null,\"imageUrl\":null,\"createdBy\":-200,\"creationTimestamp\":\"2021-11-21T18:04:52\",\"epgSourceId\":8,\"startDateStr\":\"20211122070000\",\"genreByGenreId\":null,\"languageByLanguageId\":{\"id\":3,\"name\":\"\\u10e0\\u10e3\\u10e1\\u10e3\\u10da\\u10d8\",\"orderIndex\":3,\"nameShort\":\"ru\"},\"externalId\":\"2021460000084132\",\"programHumanById\":[],\"date\":null,\"time\":null,\"startDate\":null,\"endDate\":null,\"longInfo\":\"\\u0413\\u0443\\u0434\\u0436\\u0430\\u0440\\u0430\\u0442\\u0435\\u0446 \\u0425\\u0430\\u0441\\u043c\\u0443\\u043a\\u0445 \\u041f\\u0430\\u0442\\u0435\\u043b \\u043f\\u043e\\u0441\\u0441\\u043e\\u0440\\u0438\\u043b\\u0441\\u044f \\u0441 \\u043d\\u043e\\u0432\\u044b\\u043c \\u0441\\u043e\\u0441\\u0435\\u0434\\u043e\\u043c \\u0413\\u0443\\u0433\\u0433\\u0438 \\u0422\\u0430\\u043d\\u0434\\u043e\\u043d\\u043e\\u043c. \\u041d\\u043e \\u0438\\u043c \\u043f\\u0440\\u0438\\u0445\\u043e\\u0434\\u0438\\u0442\\u0441\\u044f \\u043f\\u043e\\u043c\\u0438\\u0440\\u0438\\u0442\\u044c\\u0441\\u044f, \\u043a\\u043e\\u0433\\u0434\\u0430 \\u0438\\u0445 \\u0434\\u0435\\u0442\\u0438 \\u0432\\u043b\\u044e\\u0431\\u043b\\u044f\\u044e\\u0442\\u0441\\u044f \\u0434\\u0440\\u0443\\u0433 \\u0432 \\u0434\\u0440\\u0443\\u0433\\u0430. \\u0420\\u0435\\u0436\\u0438\\u0441\\u0441\\u0435\\u0440: \\u0421\\u0430\\u043d\\u0434\\u0436\\u0430\\u0439 \\u0427\\u0445\\u0435\\u043b. \\u0410\\u043a\\u0442\\u0435\\u0440\\u044b: \\u0420\\u0438\\u0448\\u0438 \\u041a\\u0430\\u043f\\u0443\\u0440, \\u041f\\u0430\\u0440\\u0435\\u0448 \\u0420\\u0430\\u0432\\u0430\\u043b, \\u0412\\u0438\\u0440 \\u0414\\u0430\\u0441. 2017 \\u0433\\u043e\\u0434.\"}]` + const result = parser({ content }).map(p => { + p.start = p.start.toJSON() + p.stop = p.stop.toJSON() + return p + }) + + expect(result).toMatchObject([ + { + start: '2021-11-22T03:00:00.000Z', + stop: '2021-11-22T05:00:00.000Z', + title: `Х/ф "Неравный брак".`, + description: `Гуджаратец Хасмукх Пател поссорился с новым соседом Гугги Тандоном. Но им приходится помириться, когда их дети влюбляются друг в друга. Режиссер: Санджай Чхел. Актеры: Риши Капур, Пареш Равал, Вир Дас. 2017 год.` + } + ]) +}) + +it('can handle empty guide', () => { + const result = parser({ + date, + channel, + content: `[]` + }) + expect(result).toMatchObject([]) +}) diff --git a/sites/magticom.ge/magticom.ge_ge.channels.xml b/sites/magticom.ge/magticom.ge_ge.channels.xml new file mode 100644 index 00000000..c62caaa7 --- /dev/null +++ b/sites/magticom.ge/magticom.ge_ge.channels.xml @@ -0,0 +1,122 @@ + + + + 1 TV + 2 TV + 360 Tune Box + A1 + A2 + Abkhazia HD + Adjarasport 1 + Adjarasport 2 + Ajara TV + Amedia Hit + Amedia Premium + Armenia 1 TV + Avto 24 + Az TV + BBC World News Europe + Bollywood TV Rossiya + Brazzers TV Europe + Cartoon Network Russia & South East Europe + Chveni Magti + Cinéma + CNBC Europe + CNN International Europe + Comedy TV + Dardimandi + Da Vinci + Discovery Science Rossiya + DocuBox HD + Domashniy + Dom Kino + Dom Kino Premium + DTX Rossiya + Duck TV SD + Enki Benki + Erox HD + Ertsulovneba + EuroNews Russkiy + Evrokino + FashionBox HD + Fast & FunBox HD + FightBox HD + FilmBox Arthouse Worldwide + FilmBox Russia + Formula + Fox Russia + France 24 English + GDS TV + Gulli Girl + Gurjaani TV + Hollywood HD + Illusion + + Imedi TV + Investigation Discovery Rossiya + Istoriya Telekanal + JimJam Rossiya + Karusel International + Kavkasia TV + M-1 Global TV + Maestro + Magti Hiti + Magti Kino + Marao TV + Mezzo + Moya Planeta + Mtavari Arkhi + MTV 80s + MTV Russia + Mult + Nastoyashcheye Vremya + National Geographic Russia + National Geographic Wild Russia + Nauka + Nickelodeon CIS + Nick Jr CIS + NST + Obieqtivi TV + Ohotnik i Rybolov + Palitra News + Paramount Channel Russia + Paramount Comedy Russia + Peretz International + Perviy kanal CIS + Pos TV + Pyatnitsa! International + Qartuli Arkhi + Quality Channel + RBK TV + Redlight HD + Rioni TV + Rossiya 24 + Rossiya K + RT News + RTR Planeta + RTVi Europe + Rugby TV + Russkiy Illusion + Rustavi 2 + Saperavi TV HD + Sarafan + Setanta Sports Georgia + Setanta Sports + Georgia + Silk Universal + STS International + Telekanal O! + Tiji Russia + TNT Music + TV 25 + TV 1000 Action + TV 1000 East + TV 1000 Russkoe Kino + TV Pirveli + TV XXI + Viasat Explore East + Viasat History + Viasat Nature East + Viasat Sport East + Zagorodny International + Zhivaya Planeta + + \ No newline at end of file