Skip to content

Commit

Permalink
Adds the ability to pass the config in grab()
Browse files Browse the repository at this point in the history
  • Loading branch information
freearhey committed Nov 25, 2023
1 parent fa19d29 commit f2db2cd
Show file tree
Hide file tree
Showing 5 changed files with 107 additions and 57 deletions.
26 changes: 14 additions & 12 deletions src/client.js
Original file line number Diff line number Diff line change
Expand Up @@ -14,18 +14,20 @@ module.exports.parseResponse = parseResponse
let timeout

function create(config) {
const client = setupCookie(
setupCache(
axios.create({
jar,
ignoreCookieErrors: true,
headers: {
'User-Agent':
'Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/79.0.3945.130 Safari/537.36 Edg/79.0.309.71'
}
})
)
)
const client = axios.defaults.cache
? axios
: setupCookie(
setupCache(
axios.create({
jar,
ignoreCookieErrors: true,
headers: {
'User-Agent':
'Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/79.0.3945.130 Safari/537.36 Edg/79.0.309.71'
}
})
)
)

client.interceptors.request.use(
function (request) {
Expand Down
54 changes: 27 additions & 27 deletions src/config.js
Original file line number Diff line number Diff line change
@@ -1,34 +1,34 @@
const tough = require('tough-cookie')
const { merge } = require('lodash')

module.exports.load = load
module.exports.parse = parse

function load(config) {
if (!config.site) throw new Error("The required 'site' property is missing")
if (!config.url) throw new Error("The required 'url' property is missing")
if (typeof config.url !== 'function' && typeof config.url !== 'string')
throw new Error("The 'url' property should return the function or string")
if (!config.parser) throw new Error("The required 'parser' function is missing")
if (typeof config.parser !== 'function')
throw new Error("The 'parser' property should return the function")
if (config.logo && typeof config.logo !== 'function')
throw new Error("The 'logo' property should return the function")
function parse(config) {
if (!config.site) throw new Error("The required 'site' property is missing")
if (!config.url) throw new Error("The required 'url' property is missing")
if (typeof config.url !== 'function' && typeof config.url !== 'string')
throw new Error("The 'url' property should return the function or string")
if (!config.parser) throw new Error("The required 'parser' function is missing")
if (typeof config.parser !== 'function')
throw new Error("The 'parser' property should return the function")
if (config.logo && typeof config.logo !== 'function')
throw new Error("The 'logo' property should return the function")

const defaultConfig = {
days: 1,
lang: 'en',
delay: 3000,
output: 'guide.xml',
request: {
method: 'GET',
maxContentLength: 5 * 1024 * 1024,
timeout: 5000,
withCredentials: true,
jar: new tough.CookieJar(),
responseType: 'arraybuffer',
cache: false
}
}
const defaultConfig = {
days: 1,
lang: 'en',
delay: 3000,
output: 'guide.xml',
request: {
method: 'GET',
maxContentLength: 5 * 1024 * 1024,
timeout: 5000,
withCredentials: true,
jar: new tough.CookieJar(),
responseType: 'arraybuffer',
cache: false
}
}

return merge(defaultConfig, config)
return merge(defaultConfig, config)
}
20 changes: 13 additions & 7 deletions src/index.js
Original file line number Diff line number Diff line change
Expand Up @@ -3,7 +3,7 @@ const { create: createClient, buildRequest, parseResponse } = require('./client'
const { parseChannels, parsePrograms } = require('./parser')
const { sleep, isPromise, getUTCDate } = require('./utils')
const { generate: generateXMLTV } = require('./xmltv')
const { load: loadConfig } = require('./config')
const { parse: parseConfig } = require('./config')
const Channel = require('./Channel')
const Program = require('./Program')

Expand All @@ -14,7 +14,7 @@ module.exports.Program = Program

class EPGGrabber {
constructor(config = {}) {
this.config = loadConfig(config)
this.config = config
this.client = createClient(config)
}

Expand All @@ -26,26 +26,32 @@ class EPGGrabber {
return logo
}

async grab(channel, date, cb = () => {}) {
async grab(channel, date, config = {}, cb = () => {}) {
if (typeof config == 'function') {
cb = config
config = {}
}
config = merge(this.config, config)
config = parseConfig(config)
if (!(channel instanceof Channel)) {
throw new Error('The first argument must be the "Channel" class')
}

await sleep(this.config.delay)
await sleep(config.delay)

date = typeof date === 'string' ? getUTCDate(date) : date
return buildRequest({ channel, date, config: this.config })
return buildRequest({ channel, date, config })
.then(this.client)
.then(parseResponse)
.then(data => merge({ channel, date, config: this.config }, data))
.then(data => merge({ channel, date, config }, data))
.then(parsePrograms)
.then(programs => {
cb({ channel, date, programs })

return programs
})
.catch(err => {
if (this.config.debug) console.log('Error:', JSON.stringify(err, null, 2))
if (config.debug) console.log('Error:', JSON.stringify(err, null, 2))
cb({ channel, date, programs: [] }, err)

return []
Expand Down
4 changes: 2 additions & 2 deletions tests/config.test.js
Original file line number Diff line number Diff line change
@@ -1,9 +1,9 @@
import { load as loadConfig } from '../src/config'
import { parse as parseConfig } from '../src/config'
import path from 'path'
import fs from 'fs'

it('can load config', () => {
const config = loadConfig(require(path.resolve('./tests/__data__/input/example.config.js')))
const config = parseConfig(require(path.resolve('./tests/__data__/input/example.config.js')))
expect(config).toMatchObject({
days: 2,
delay: 3000,
Expand Down
60 changes: 51 additions & 9 deletions tests/index.test.js
Original file line number Diff line number Diff line change
Expand Up @@ -28,24 +28,26 @@ it('return "Connection timeout" error if server does not response', done => {
name: 'CNN'
})
const grabber = new EPGGrabber(config)
grabber.grab(channel, '2022-01-01', (data, err) => {
expect(err.message).toBe('Connection timeout')
done()
})
grabber
.grab(channel, '2022-01-01', (data, err) => {
expect(err.message).toBe('Connection timeout')
done()
})
.catch(done)
})

it('can grab single channel programs', done => {
const data = {
data: {
toString: () => 'string'
toString: () => '[{"title":"Program1"}]'
}
}
axios.mockImplementation(() => Promise.resolve(data))

const config = {
site: 'example.com',
url: 'http://example.com/20210319/1tv.json',
parser: () => []
parser: ({ content }) => JSON.parse(content)
}
const channel = new Channel({
site: 'example.com',
Expand All @@ -56,13 +58,53 @@ it('can grab single channel programs', done => {
})
const grabber = new EPGGrabber(config)
grabber
.grab(channel, '2022-01-01', (data, err) => {
.grab(channel, '2022-01-01')
.then(programs => {
expect(programs[0].titles).toMatchObject([
{
lang: 'fr',
value: 'Program1'
}
])
done()
})
.catch(done)
})

it('can use a different config for different requests', done => {
const data = {
data: {
toString: () => '[{"title":"Program1"}]'
}
}
axios.mockImplementation(() => Promise.resolve(data))

const config = {
site: 'example.com',
url: 'http://example.com/20210319/1tv.json',
parser: ({ content }) => JSON.parse(content)
}
const channel = new Channel({
site: 'example.com',
site_id: '1',
xmltv_id: '1TV.fr',
lang: 'fr',
name: '1TV'
})
const grabber = new EPGGrabber()
grabber
.grab(channel, '2022-01-01', config, (data, err) => {
if (err) {
done()
done(err)
}
})
.then(programs => {
expect(programs.length).toBe(0)
expect(programs[0].titles).toMatchObject([
{
lang: 'fr',
value: 'Program1'
}
])
done()
})
})
Expand Down

0 comments on commit f2db2cd

Please sign in to comment.