前言
最近发现,康巴卫视官网支持长达四百多天的回放,但是官网的EPG是默认的每小时一段,回放接口也是每小时一段,并不能按照正常的EPG进行自定义回放。
为了解决该痛点,本文用PHP写了提取和拼接算法,可实现指定日期中任意开始和结束时间点的回放,分享此源码以供学习参考。
源码
<?php
//Written by Wheiss
error_reporting(0);
date_default_timezone_set("PRC");
$id = isset($_GET['id'])?$_GET['id']:'kbws';
$n = [
"kbws" => 17,//康巴卫视
];
if (!isset($n[$id])) die(header("HTTP/1.1 404"));
$playseek = $_GET['playseek']??'';
if ($playseek) {
$t_arr = explode("-",$playseek);
$starttime = strtotime($t_arr[0]);
$endtime = strtotime($t_arr[1]);
//前7天:https://mapi.kangbatv.com/api/v1/program.php?channel_id=17&zone=-6
//当天:https://mapi.kangbatv.com/api/v1/program.php?channel_id=17&zone=0
//前472天:https://mapi.kangbatv.com/api/v1/program.php?channel_id=17&zone=-471
#计算起始点zone值并获取数据
//计算开始点当天0点的时间戳
$startDayDateOn = substr($t_arr[0],0,8).'000000';
$startDayTimeOn = strtotime($startDayDateOn);//开始时间当天0点的时间戳
//计算当天0点的时间戳
$time = time();
$nowDayDateOn = date('Ymd',$time).'000000';
$nowDayTimeOn = strtotime($nowDayDateOn);
$devTime = $startDayTimeOn-$nowDayTimeOn;
$zone = floor($devTime/86400);
$scheduleIdApi = "https://mapi.kangbatv.com/api/v1/program.php?channel_id={$n[$id]}&zone={$zone}";
$data = get_curl($scheduleIdApi,1);
if (!$data) {
$data = get_curl($scheduleIdApi,2);
}
$allEpg = json_decode($data,TRUE);//0-23代表0点到23点的数据
if (empty($allEpg)) die('获取epg数据失败!');
//计算起始点时间差
$startHDateOn = substr($t_arr[0],0,10).'0000';
$startHTimeOn = strtotime($startHDateOn);//开始时间小时所在时间戳
$startDevTime = $starttime-$startHTimeOn;//起始点时间差
//计算起始点和结束点所在序号
$endHDateOn = substr($t_arr[1],0,10).'0000';
$endHTimeOn = strtotime($endHDateOn);//结束时间小时所在时间戳
$startNumber = intval(($startHTimeOn-$startDayTimeOn)/3600);//起始点所在序号
$endNumber = intval(($endHTimeOn-$startDayTimeOn)/3600);//结束点所在序号
//计算开始点和开始小时的数据条数差,结束点和开始点的数据条数差
$startiNumber = floor($startDevTime/5.882);
$deviNumber = floor(($endtime-$starttime)/5.882);
$data = '';
for ($i = $startNumber; $i <= $endNumber; $i++) {//循环取数据
$url = $allEpg[$i]['m3u8'];
$data1 = get_curl($url,1);
if (!$data1) {
$data1 = get_curl($url,2);
}
if (strpos($data1,'#EXTM3U')!==FALSE) $data .= $data1;
}
$m3u8s = explode("\n",trim($data));
$m3u8 = "#EXTM3U\n#EXT-X-VERSION:3\n#EXT-X-MEDIA-SEQUENCE:0\n#EXT-X-TARGETDURATION:6\n";
for ($i = 6+$startiNumber*2,$j = 0; $i < count($m3u8s)-4&&$j<$deviNumber; $i++) {
if (strpos($m3u8s[$i],'#EXTINF')!==FALSE) {
$m3u8 .= $m3u8s[$i]."\n";
$i++;
$m3u8 .= $m3u8s[$i]."\n";
$j++;
} elseif (strpos($m3u8s[$i],'#EXT-X-ENDLIST')!==FALSE) {
$i+=6;
}
}
$m3u8 .= "#EXT-X-ENDLIST\n";
$m3u8 = str_replace('../../','https://pluslive.kangbatv.com/',$m3u8);
header('Connection: keep-alive');
header("Content-Type: application/vnd.apple.mpegurl");
header("Content-Disposition: inline; filename={$id}_{$t_arr[0]}_{$t_arr[1]}.m3u8");
print_r($m3u8);
} else {
$api = "https://mapi.kangbatv.com/api/v1/channel_detail.php?channel_id={$n[$id]}";
$data = get_curl($api,1);
if (!$data) $data = get_curl($api,2);
if ($data) {
$m3u8 = json_decode($data)[0]->channel_stream[0]->m3u8;
} else {
die('获取m3u8链接失败!');
}
header('location:'.$m3u8);
}
exit;
function get_curl($url,$timeout=1){
$ch = curl_init($url);
curl_setopt($ch, CURLOPT_FOLLOWLOCATION, TRUE);//跟随重定向
curl_setopt($ch, CURLOPT_RETURNTRANSFER, TRUE);//不直接输出
curl_setopt($ch, CURLOPT_SSL_VERIFYPEER, FALSE);//忽略SSL验证
curl_setopt($ch, CURLOPT_SSL_VERIFYHOST, FALSE);
curl_setopt($ch, CURLOPT_USERAGENT, 'Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/90.0.4430.93 Safari/537.36');
curl_setopt($ch, CURLOPT_REFERER, 'http://www.kangbatv.com/zb_22587/');
curl_setopt($ch, CURLOPT_CONNECTTIMEOUT,$timeout);
curl_setopt($ch, CURLOPT_TIMEOUT,3);
$data = curl_exec($ch);
curl_close($ch);
return $data;
}
?>
补充说明
URL格式
- 直播示例:http://127.0.0.1/kbtv.php
- 回放示例:http://127.0.0.1/kbtv.php?playseek=20241207213000-20241207223000
Comments NOTHING