mirror of
https://github.com/iptv-org/iptv
synced 2025-12-17 02:47:33 -05:00
Update scripts
This commit is contained in:
@@ -1,117 +1,125 @@
|
||||
import { Stream } from '../models'
|
||||
import { TESTING } from '../constants'
|
||||
import mediaInfoFactory from 'mediainfo.js'
|
||||
import axios, { AxiosInstance, AxiosProxyConfig, AxiosRequestConfig } from 'axios'
|
||||
import { ProxyParser } from './proxyParser.js'
|
||||
import { OptionValues } from 'commander'
|
||||
import { SocksProxyAgent } from 'socks-proxy-agent'
|
||||
|
||||
export type TestResult = {
|
||||
status: {
|
||||
ok: boolean
|
||||
code: string
|
||||
}
|
||||
}
|
||||
|
||||
export type StreamTesterProps = {
|
||||
options: OptionValues
|
||||
}
|
||||
|
||||
export class StreamTester {
|
||||
client: AxiosInstance
|
||||
options: OptionValues
|
||||
|
||||
constructor({ options }: StreamTesterProps) {
|
||||
const proxyParser = new ProxyParser()
|
||||
let request: AxiosRequestConfig = {
|
||||
responseType: 'arraybuffer'
|
||||
}
|
||||
|
||||
if (options.proxy !== undefined) {
|
||||
const proxy = proxyParser.parse(options.proxy) as AxiosProxyConfig
|
||||
|
||||
if (
|
||||
proxy.protocol &&
|
||||
['socks', 'socks5', 'socks5h', 'socks4', 'socks4a'].includes(String(proxy.protocol))
|
||||
) {
|
||||
const socksProxyAgent = new SocksProxyAgent(options.proxy)
|
||||
|
||||
request = { ...request, ...{ httpAgent: socksProxyAgent, httpsAgent: socksProxyAgent } }
|
||||
} else {
|
||||
request = { ...request, ...{ proxy } }
|
||||
}
|
||||
}
|
||||
|
||||
this.client = axios.create(request)
|
||||
this.options = options
|
||||
}
|
||||
|
||||
async test(stream: Stream): Promise<TestResult> {
|
||||
if (TESTING) {
|
||||
const results = (await import('../../tests/__data__/input/playlist_test/results.js')).default
|
||||
|
||||
return results[stream.url as keyof typeof results]
|
||||
} else {
|
||||
try {
|
||||
const res = await this.client(stream.url, {
|
||||
signal: AbortSignal.timeout(this.options.timeout),
|
||||
headers: {
|
||||
'User-Agent': stream.getUserAgent() || 'Mozilla/5.0',
|
||||
Referer: stream.getReferrer()
|
||||
}
|
||||
})
|
||||
|
||||
const mediainfo = await mediaInfoFactory({ format: 'object' })
|
||||
const buffer = await res.data
|
||||
const result = await mediainfo.analyzeData(
|
||||
() => buffer.byteLength,
|
||||
(size: any, offset: number | undefined) =>
|
||||
Buffer.from(buffer).subarray(offset, offset + size)
|
||||
)
|
||||
|
||||
if (result && result.media && result.media.track.length > 0) {
|
||||
return {
|
||||
status: {
|
||||
ok: true,
|
||||
code: 'OK'
|
||||
}
|
||||
}
|
||||
} else {
|
||||
return {
|
||||
status: {
|
||||
ok: false,
|
||||
code: 'NO_VIDEO'
|
||||
}
|
||||
}
|
||||
}
|
||||
} catch (error: any) {
|
||||
let code = 'UNKNOWN_ERROR'
|
||||
if (error.name === 'CanceledError') {
|
||||
code = 'TIMEOUT'
|
||||
} else if (error.name === 'AxiosError') {
|
||||
if (error.response) {
|
||||
const status = error.response?.status
|
||||
const statusText = error.response?.statusText.toUpperCase().replace(/\s+/, '_')
|
||||
code = `HTTP_${status}_${statusText}`
|
||||
} else {
|
||||
code = `AXIOS_${error.code}`
|
||||
}
|
||||
} else if (error.cause) {
|
||||
const cause = error.cause as Error & { code?: string }
|
||||
if (cause.code) {
|
||||
code = cause.code
|
||||
} else {
|
||||
code = cause.name
|
||||
}
|
||||
}
|
||||
|
||||
return {
|
||||
status: {
|
||||
ok: false,
|
||||
code
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
import axios, { AxiosInstance, AxiosProxyConfig, AxiosRequestConfig, AxiosResponse } from 'axios'
|
||||
import { SocksProxyAgent } from 'socks-proxy-agent'
|
||||
import { ProxyParser } from './proxyParser.js'
|
||||
import mediaInfoFactory from 'mediainfo.js'
|
||||
import { OptionValues } from 'commander'
|
||||
import { TESTING } from '../constants'
|
||||
import { Stream } from '../models'
|
||||
|
||||
export type StreamTesterResult = {
|
||||
status: {
|
||||
ok: boolean
|
||||
code: string
|
||||
}
|
||||
}
|
||||
|
||||
export type StreamTesterError = {
|
||||
name: string
|
||||
code?: string
|
||||
cause?: Error & { code?: string }
|
||||
response?: AxiosResponse
|
||||
}
|
||||
|
||||
export type StreamTesterProps = {
|
||||
options: OptionValues
|
||||
}
|
||||
|
||||
export class StreamTester {
|
||||
client: AxiosInstance
|
||||
options: OptionValues
|
||||
|
||||
constructor({ options }: StreamTesterProps) {
|
||||
const proxyParser = new ProxyParser()
|
||||
let request: AxiosRequestConfig = {
|
||||
responseType: 'arraybuffer'
|
||||
}
|
||||
|
||||
if (options.proxy !== undefined) {
|
||||
const proxy = proxyParser.parse(options.proxy) as AxiosProxyConfig
|
||||
|
||||
if (
|
||||
proxy.protocol &&
|
||||
['socks', 'socks5', 'socks5h', 'socks4', 'socks4a'].includes(String(proxy.protocol))
|
||||
) {
|
||||
const socksProxyAgent = new SocksProxyAgent(options.proxy)
|
||||
|
||||
request = { ...request, ...{ httpAgent: socksProxyAgent, httpsAgent: socksProxyAgent } }
|
||||
} else {
|
||||
request = { ...request, ...{ proxy } }
|
||||
}
|
||||
}
|
||||
|
||||
this.client = axios.create(request)
|
||||
this.options = options
|
||||
}
|
||||
|
||||
async test(stream: Stream): Promise<StreamTesterResult> {
|
||||
if (TESTING) {
|
||||
const results = (await import('../../tests/__data__/input/playlist_test/results.js')).default
|
||||
|
||||
return results[stream.url as keyof typeof results]
|
||||
} else {
|
||||
try {
|
||||
const res = await this.client(stream.url, {
|
||||
signal: AbortSignal.timeout(this.options.timeout),
|
||||
headers: {
|
||||
'User-Agent': stream.user_agent || 'Mozilla/5.0',
|
||||
Referer: stream.referrer
|
||||
}
|
||||
})
|
||||
|
||||
const mediainfo = await mediaInfoFactory({ format: 'object' })
|
||||
const buffer = await res.data
|
||||
const result = await mediainfo.analyzeData(
|
||||
() => buffer.byteLength,
|
||||
(size: number, offset: number) => Buffer.from(buffer).subarray(offset, offset + size)
|
||||
)
|
||||
|
||||
if (result && result.media && result.media.track.length > 0) {
|
||||
return {
|
||||
status: {
|
||||
ok: true,
|
||||
code: 'OK'
|
||||
}
|
||||
}
|
||||
} else {
|
||||
return {
|
||||
status: {
|
||||
ok: false,
|
||||
code: 'NO_VIDEO'
|
||||
}
|
||||
}
|
||||
}
|
||||
} catch (err: unknown) {
|
||||
const error = err as StreamTesterError
|
||||
|
||||
let code = 'UNKNOWN_ERROR'
|
||||
if (error.name === 'CanceledError') {
|
||||
code = 'TIMEOUT'
|
||||
} else if (error.name === 'AxiosError') {
|
||||
if (error.response) {
|
||||
const status = error.response?.status
|
||||
const statusText = error.response?.statusText.toUpperCase().replace(/\s+/, '_')
|
||||
code = `HTTP_${status}_${statusText}`
|
||||
} else {
|
||||
code = `AXIOS_${error.code}`
|
||||
}
|
||||
} else if (error.cause) {
|
||||
const cause = error.cause
|
||||
if (cause.code) {
|
||||
code = cause.code
|
||||
} else {
|
||||
code = cause.name
|
||||
}
|
||||
}
|
||||
|
||||
return {
|
||||
status: {
|
||||
ok: false,
|
||||
code
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user