添加pass
This commit is contained in:
@@ -1,6 +1,6 @@
|
||||
import { getStringMD5 } from "./EncryUtils.js";
|
||||
import { getddCalcuURL, getddCalcuURL720p } from "./ddCalcuURL.js";
|
||||
import { printDebug, printYellow } from "./colorOut.js";
|
||||
import { printDebug, printGreen, printRed, printYellow } from "./colorOut.js";
|
||||
import { fetchUrl } from "./net.js";
|
||||
|
||||
/**
|
||||
@@ -177,4 +177,55 @@ async function getAndroidURL720p(pid) {
|
||||
|
||||
}
|
||||
|
||||
export { getAndroidURL, getAndroidURL720p }
|
||||
async function get302URL(resObj) {
|
||||
try {
|
||||
let z = 1
|
||||
while (z <= 6) {
|
||||
if (z >= 2) {
|
||||
printYellow(`获取失败,正在第${z - 1}次重试`)
|
||||
}
|
||||
const controller = new AbortController()
|
||||
const timeoutId = setTimeout(() => {
|
||||
controller.abort()
|
||||
printRed("请求超时")
|
||||
}, 6000);
|
||||
const obj = await fetch(`${resObj.url}`, {
|
||||
method: "GET",
|
||||
redirect: "manual",
|
||||
signal: controller.signal
|
||||
}).catch(err => {
|
||||
clearTimeout(timeoutId);
|
||||
console.log(err)
|
||||
})
|
||||
clearTimeout(timeoutId);
|
||||
const location = obj.headers.get("Location")
|
||||
|
||||
if (location != "" && location != undefined && location != null) {
|
||||
if (!location.startsWith("http://bofang")) {
|
||||
return location
|
||||
}
|
||||
}
|
||||
if (z != 6) {
|
||||
await delay(150)
|
||||
}
|
||||
z++
|
||||
}
|
||||
} catch (error) {
|
||||
console.log(error)
|
||||
}
|
||||
printRed(`获取失败,返回原链接`)
|
||||
return ""
|
||||
}
|
||||
|
||||
function printLoginInfo(resObj) {
|
||||
if (resObj.content.body?.auth?.logined) {
|
||||
printGreen("登录认证成功")
|
||||
if (resObj.content.body.auth.authResult == "FAIL") {
|
||||
printRed(`认证失败 视频内容不完整 可能缺少相关VIP: ${resObj.content.body.auth.resultDesc}`)
|
||||
}
|
||||
} else {
|
||||
printYellow("未登录")
|
||||
}
|
||||
}
|
||||
|
||||
export { getAndroidURL, getAndroidURL720p, get302URL, printLoginInfo }
|
||||
|
||||
197
utils/appUtils.js
Normal file
197
utils/appUtils.js
Normal file
@@ -0,0 +1,197 @@
|
||||
import { get302URL, getAndroidURL, getAndroidURL720p, printLoginInfo } from "./androidURL.js";
|
||||
import { readFileSync } from "./fileUtil.js";
|
||||
import { host, rateType, token, userId } from "../config.js";
|
||||
import { printDebug, printGreen, printGrey, printRed, printYellow } from "./colorOut.js";
|
||||
|
||||
// url缓存 降低请求频率
|
||||
const urlCache = {}
|
||||
|
||||
function interfaceStr(url, headers) {
|
||||
|
||||
let result = {
|
||||
content: null,
|
||||
contentType: 'text/plain;charset=UTF-8'
|
||||
}
|
||||
let fileName = process.cwd() + "/interface.txt"
|
||||
switch (url) {
|
||||
case "/playback.xml":
|
||||
fileName = process.cwd() + "/playback.xml"
|
||||
result.contentType = "text/xml;charset=UTF-8"
|
||||
break;
|
||||
|
||||
case "/txt":
|
||||
fileName = process.cwd() + "/interfaceTXT.txt"
|
||||
break;
|
||||
|
||||
case "/m3u":
|
||||
result.contentType = "audio/x-mpegurl; charset=utf-8"
|
||||
break;
|
||||
|
||||
default:
|
||||
break;
|
||||
}
|
||||
try {
|
||||
result.content = readFileSync(fileName)
|
||||
} catch (error) {
|
||||
printRed("文件获取失败")
|
||||
console.log(error)
|
||||
return result
|
||||
}
|
||||
if (url == "/playback.xml") {
|
||||
return result
|
||||
}
|
||||
|
||||
let replaceHost = `http://${headers.host}`
|
||||
|
||||
if (host != "" && (headers["x-real-ip"] || headers["x-forwarded-for"] || host.indexOf(headers.host) != -1)) {
|
||||
replaceHost = host
|
||||
}
|
||||
|
||||
result.content = `${result.content}`.replaceAll("${replace}", replaceHost);
|
||||
|
||||
return result
|
||||
}
|
||||
|
||||
async function channel(url) {
|
||||
|
||||
let result = {
|
||||
code: 200,
|
||||
pID: "",
|
||||
desc: "服务异常",
|
||||
playURL: ""
|
||||
}
|
||||
// 处理频道ID
|
||||
let urlSplit = url.split("/")[1]
|
||||
let pid = urlSplit
|
||||
let params = ""
|
||||
|
||||
// 处理回放参数
|
||||
if (urlSplit.match(/\?/)) {
|
||||
printGreen("处理传入参数")
|
||||
|
||||
const urlSplit1 = urlSplit.split("?")
|
||||
pid = urlSplit1[0]
|
||||
params = urlSplit1[1]
|
||||
} else {
|
||||
printGrey("无参数传入")
|
||||
}
|
||||
|
||||
if (isNaN(pid)) {
|
||||
result.desc = "地址格式错误"
|
||||
return result
|
||||
}
|
||||
|
||||
printYellow("频道ID " + pid)
|
||||
|
||||
// 是否存在缓存
|
||||
const cache = channelCache(pid, params)
|
||||
if (cache.haveCache) {
|
||||
result.code = cache.code
|
||||
result.playURL = cache.playURL
|
||||
result.desc = cache.cacheDesc
|
||||
return result
|
||||
}
|
||||
|
||||
let resObj = {}
|
||||
try {
|
||||
// 未登录请求720p
|
||||
if (rateType >= 3 && (userId == "" || token == "")) {
|
||||
resObj = await getAndroidURL720p(pid)
|
||||
} else {
|
||||
resObj = await getAndroidURL(userId, token, pid, rateType)
|
||||
}
|
||||
} catch (error) {
|
||||
console.log(error)
|
||||
result.desc = "链接请求出错"
|
||||
return result
|
||||
}
|
||||
printDebug(`添加加密字段后链接 ${resObj.url}`)
|
||||
|
||||
if (resObj.url != "") {
|
||||
const location = await get302URL(resObj)
|
||||
if (location != "") {
|
||||
resObj.url = location
|
||||
}
|
||||
}
|
||||
printLoginInfo(resObj)
|
||||
// printRed(resObj.url)
|
||||
printGreen(`添加节目缓存 ${pid}`)
|
||||
// 缓存有效时长
|
||||
let addTime = 3 * 60 * 60 * 1000
|
||||
// 节目调整
|
||||
if (resObj.url == "") {
|
||||
addTime = 1 * 60 * 1000
|
||||
}
|
||||
// 加入缓存
|
||||
urlCache[pid] = {
|
||||
// 有效期3小时 节目调整时改为1分钟
|
||||
valTime: Date.now() + addTime,
|
||||
url: resObj.url,
|
||||
content: resObj.content,
|
||||
}
|
||||
|
||||
if (resObj.url == "") {
|
||||
let msg = resObj.content != null ? resObj.content.message : "节目调整,暂不提供服务"
|
||||
result.desc = `${pid} ${msg}`
|
||||
return result
|
||||
}
|
||||
let playURL = resObj.url
|
||||
|
||||
// 添加回放参数
|
||||
if (params != "") {
|
||||
const resultParams = new URLSearchParams(params);
|
||||
for (const [key, value] of resultParams) {
|
||||
playURL = `${playURL}&${key}=${value}`
|
||||
}
|
||||
}
|
||||
|
||||
printGreen("链接获取成功")
|
||||
result.code = 302
|
||||
result.playURL = playURL
|
||||
return result
|
||||
}
|
||||
|
||||
function channelCache(pid, params) {
|
||||
let cache = {
|
||||
haveCache: false,
|
||||
code: 200,
|
||||
pID: "",
|
||||
playURL: "",
|
||||
cacheDesc: ""
|
||||
}
|
||||
if (typeof urlCache[pid] === "object") {
|
||||
const valTime = urlCache[pid].valTime - Date.now()
|
||||
// 缓存是否有效
|
||||
if (valTime >= 0) {
|
||||
cache.haveCache = true
|
||||
let playURL = urlCache[pid].url
|
||||
let msg = "节目调整,暂不提供服务"
|
||||
if (urlCache[pid].content != null) {
|
||||
printLoginInfo(urlCache[pid])
|
||||
msg = urlCache[pid].content.message
|
||||
}
|
||||
// 节目调整
|
||||
if (playURL == "") {
|
||||
cache.cacheDesc = `${pid} ${msg}`
|
||||
return cache
|
||||
}
|
||||
|
||||
// 添加回放参数
|
||||
if (params != "") {
|
||||
const resultParams = new URLSearchParams(params);
|
||||
for (const [key, value] of resultParams) {
|
||||
playURL = `${playURL}&${key}=${value}`
|
||||
}
|
||||
}
|
||||
printGreen("使用缓存数据")
|
||||
cache.code = 302
|
||||
cache.cacheDesc = "缓存获取成功"
|
||||
cache.playURL = playURL
|
||||
return cache
|
||||
}
|
||||
}
|
||||
cache.cacheDesc = "暂无缓存"
|
||||
return cache
|
||||
}
|
||||
|
||||
export { interfaceStr, channel, channelCache }
|
||||
@@ -97,7 +97,6 @@ function getEncryptURL(exports, videoURL) {
|
||||
|
||||
|
||||
/**
|
||||
* h5端现已失效
|
||||
* 获取ddCalcu
|
||||
* @param {string} puData - 服务器返回的那个东东
|
||||
* @param {string} programId - 节目ID
|
||||
@@ -138,6 +137,9 @@ function getddCalcu(puData, programId, clientType, rateType) {
|
||||
if (clientType == "android" && rateType == "2") {
|
||||
words[0] = "v"
|
||||
}
|
||||
if (userId.length > 3 && userId.length <= 8) {
|
||||
words[0] = "e"
|
||||
}
|
||||
const puDataLength = puData.length
|
||||
let ddCalcu = []
|
||||
for (let i = 0; i < puDataLength / 2; i++) {
|
||||
@@ -146,7 +148,7 @@ function getddCalcu(puData, programId, clientType, rateType) {
|
||||
ddCalcu.push(puData[i])
|
||||
switch (i) {
|
||||
case 1:
|
||||
ddCalcu.push(userId.length > 8 ? words[i - 1] : "v")
|
||||
ddCalcu.push(words[i - 1])
|
||||
break;
|
||||
case 2:
|
||||
ddCalcu.push(keys[parseInt(getDateString(new Date())[0])])
|
||||
|
||||
18
utils/net.js
18
utils/net.js
@@ -1,7 +1,5 @@
|
||||
import os from "os"
|
||||
|
||||
// const controller = new AbortController();
|
||||
// const timeoutId = setTimeout(() => controller.abort(), 15000);
|
||||
import { printRed } from "./colorOut.js";
|
||||
|
||||
function getLocalIPv(ver = 4) {
|
||||
const ips = []
|
||||
@@ -26,11 +24,19 @@ function getLocalIPv(ver = 4) {
|
||||
}
|
||||
|
||||
async function fetchUrl(url, opts = {}) {
|
||||
// opts["signal"] = controller.signal
|
||||
const controller = new AbortController();
|
||||
const timeoutId = setTimeout(() => {
|
||||
controller.abort()
|
||||
printRed("请求超时")
|
||||
}, 6000);
|
||||
opts["signal"] = controller.signal
|
||||
const res = await fetch(url, opts)
|
||||
.then(r => r.json())
|
||||
.catch(err => console.log(err))
|
||||
// clearTimeout(timeoutId);
|
||||
.catch(err => {
|
||||
console.log(err)
|
||||
clearTimeout(timeoutId);
|
||||
})
|
||||
clearTimeout(timeoutId);
|
||||
return res
|
||||
}
|
||||
|
||||
|
||||
@@ -1,7 +1,7 @@
|
||||
import { dataList } from "./fetchList.js"
|
||||
import { appendFile, appendFileSync, copyFileSync, renameFileSync, writeFile } from "./fileUtil.js"
|
||||
import { updatePlaybackData } from "./playback.js"
|
||||
import { /* refreshToken as mrefreshToken, */ host, token, userId } from "../config.js"
|
||||
import { /* refreshToken as mrefreshToken, */ host, pass, token, userId } from "../config.js"
|
||||
import refreshToken from "./refreshToken.js"
|
||||
import { printGreen, printRed, printYellow } from "./colorOut.js"
|
||||
import { getDateString } from "./time.js"
|
||||
@@ -38,7 +38,7 @@ async function updateTV(hours) {
|
||||
// }
|
||||
}
|
||||
}
|
||||
appendFile(interfacePath, `#EXTM3U x-tvg-url="\${replace}/playback.xml" catchup="append" catchup-source="?playbackbegin=\${(b)yyyyMMddHHmmss}&playbackend=\${(e)yyyyMMddHHmmss}"\n`)
|
||||
appendFile(interfacePath, `#EXTM3U x-tvg-url="\${replace}/${pass == "" ? "" : pass + "/"}playback.xml" catchup="append" catchup-source="?playbackbegin=\${(b)yyyyMMddHHmmss}&playbackend=\${(e)yyyyMMddHHmmss}"\n`)
|
||||
printYellow("开始更新TV...")
|
||||
// 回放
|
||||
const playbackFile = `${process.cwd()}/playback.xml.bak`
|
||||
@@ -58,9 +58,9 @@ async function updateTV(hours) {
|
||||
await updatePlaybackData(data[j], playbackFile)
|
||||
|
||||
// 写入节目
|
||||
appendFile(interfacePath, `#EXTINF:-1 tvg-id="${data[j].name}" tvg-name="${data[j].name}" tvg-logo="${data[j].pics.highResolutionH}" group-title="${datas[i].name}",${data[j].name}\n\${replace}/${data[j].pID}\n`)
|
||||
appendFile(interfacePath, `#EXTINF:-1 tvg-id="${data[j].name}" tvg-name="${data[j].name}" tvg-logo="${data[j].pics.highResolutionH}" group-title="${datas[i].name}",${data[j].name}\n\${replace}/${pass == "" ? "" : pass + "/"}${data[j].pID}\n`)
|
||||
// txt
|
||||
appendFile(interfaceTXTPath, `${data[j].name},\${replace}/${data[j].pID}\n`)
|
||||
appendFile(interfaceTXTPath, `${data[j].name},\${replace}/${pass == "" ? "" : pass + "/"}${data[j].pID}\n`)
|
||||
// printGreen(` 节目链接更新成功`)
|
||||
}
|
||||
printGreen(`分类###:${datas[i].name} 更新完成!`)
|
||||
@@ -142,8 +142,8 @@ async function updatePE(hours) {
|
||||
}
|
||||
const competitionDesc = `${data.competitionName} ${pkInfoTitle} ${replay.name} ${timeStr}`
|
||||
// 写入赛事
|
||||
appendFileSync(interfacePath, `#EXTINF:-1 tvg-id="${pkInfoTitle}" tvg-name="${competitionDesc}" tvg-logo="${data.competitionLogo}" group-title="体育-${relativeDate}",${competitionDesc}\n\${replace}/${replay.pID}\n`)
|
||||
appendFileSync(interfaceTXTPath, `${competitionDesc},\${replace}/${replay.pID}\n`)
|
||||
appendFileSync(interfacePath, `#EXTINF:-1 tvg-id="${pkInfoTitle}" tvg-name="${competitionDesc}" tvg-logo="${data.competitionLogo}" group-title="体育-${relativeDate}",${competitionDesc}\n\${replace}/${pass == "" ? "" : pass + "/"}${replay.pID}\n`)
|
||||
appendFileSync(interfaceTXTPath, `${competitionDesc},\${replace}/${pass == "" ? "" : pass + "/"}${replay.pID}\n`)
|
||||
}
|
||||
}
|
||||
continue
|
||||
@@ -156,8 +156,8 @@ async function updatePE(hours) {
|
||||
}
|
||||
const competitionDesc = `${data.competitionName} ${pkInfoTitle} ${live.name} ${live.startTimeStr.substring(11, 16)}`
|
||||
// 写入赛事
|
||||
appendFileSync(interfacePath, `#EXTINF:-1 tvg-id="${pkInfoTitle}" tvg-name="${competitionDesc}" tvg-logo="${data.competitionLogo}" group-title="体育-${relativeDate}",${competitionDesc}\n\${replace}/${live.pID}\n`)
|
||||
appendFileSync(interfaceTXTPath, `${competitionDesc},\${replace}/${live.pID}\n`)
|
||||
appendFileSync(interfacePath, `#EXTINF:-1 tvg-id="${pkInfoTitle}" tvg-name="${competitionDesc}" tvg-logo="${data.competitionLogo}" group-title="体育-${relativeDate}",${competitionDesc}\n\${replace}/${pass == "" ? "" : pass + "/"}${live.pID}\n`)
|
||||
appendFileSync(interfaceTXTPath, `${competitionDesc},\${replace}/${pass == "" ? "" : pass + "/"}${live.pID}\n`)
|
||||
}
|
||||
} catch (error) {
|
||||
printRed(`${data.mgdbId} ${pkInfoTitle} 更新失败`)
|
||||
|
||||
Reference in New Issue
Block a user