109 lines
4.3 KiB
Python
109 lines
4.3 KiB
Python
import json
|
||
from datetime import datetime, timezone, timedelta
|
||
from os.path import exists as file_exists
|
||
from urllib.request import Request, urlopen
|
||
import xml.etree.ElementTree as ET
|
||
|
||
from constants import XMLTV, CITY
|
||
|
||
date = datetime.now(timezone.utc).replace(tzinfo=None) + timedelta(hours=+9)
|
||
ymd = date.strftime('%Y%m%d')
|
||
guide = XMLTV()
|
||
|
||
|
||
def fix(inp: str) -> str:
|
||
out = inp.replace('&', '&')
|
||
out = out.replace('<', '<')
|
||
out = out.replace('>', '>')
|
||
|
||
return out
|
||
|
||
|
||
def genre(_: str) -> str:
|
||
genres = json.load(open('data/genre.json', encoding='utf-8'))
|
||
|
||
for gen in genres:
|
||
if _ == gen:
|
||
return genres[gen]
|
||
|
||
return '未知'
|
||
|
||
|
||
def request_url() -> str:
|
||
request = 'https://tvguide.myjcom.jp/api/getEpgInfo/?channels='
|
||
xmlfile = open('data/channels.xml', 'r', encoding='utf-8').read().splitlines()
|
||
|
||
for line in xmlfile:
|
||
tree = ET.ElementTree(ET.fromstring(line))
|
||
root = tree.getroot()
|
||
chid = root.attrib['id']
|
||
request += f'{chid}_{ymd}%2C'
|
||
|
||
return f'{request}&rectime=&rec4k='
|
||
|
||
|
||
# TODO: Find an easier way to do this.
|
||
if not file_exists('data/channels.xml'):
|
||
c_areas = [CITY.OSAKA1.value, CITY.NARA.value]
|
||
c_adult = 'true'
|
||
|
||
for area in c_areas: # GR
|
||
req = Request('https://tvguide.myjcom.jp/api/mypage/getEpgChannelList/?channelType=2&area={}&channelGenre=&course=&chart=&is_adult={}'.format(area, c_adult))
|
||
req.add_header('user-agent', 'Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/131.0.0.0 Safari/537.36')
|
||
data = urlopen(req).read()
|
||
data = json.loads(data)
|
||
|
||
for ch in data['header']:
|
||
chid = '{}_{}_{}_{}'.format(ch['channel_type'], ch['channel_id'], ch['network_id'], ymd)
|
||
j1 = '200_00010_0_{}'.format(ymd)
|
||
j2 = '200_00055_0_{}'.format(ymd)
|
||
|
||
if j1 not in chid and j2 not in chid:
|
||
guide.add_channel(chid[0:chid.rfind('_')], ch['channel_name'], ch['logo_url'])
|
||
print('Added channel:', ch['channel_name'])
|
||
|
||
for c_type in [3, 5, 120]: # BS / BS4K / CS
|
||
req = Request('https://tvguide.myjcom.jp/api/mypage/getEpgChannelList/?channelType={}&area=1&channelGenre=&course=&chart=&is_adult={}'.format(c_type, c_adult))
|
||
req.add_header('user-agent', 'Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/131.0.0.0 Safari/537.36') # This is required, otherwise we get a 403: Forbidden error.
|
||
channel_data = urlopen(req).read()
|
||
channel_data = json.loads(channel_data)
|
||
|
||
for ch in channel_data['header']:
|
||
chid = '{}_{}_{}_{}'.format(ch['channel_type'], ch['channel_id'], ch['network_id'], ymd)
|
||
j1 = '200_00010_0_{}'.format(ymd)
|
||
j2 = '200_00055_0_{}'.format(ymd)
|
||
|
||
if j1 not in chid and j2 not in chid:
|
||
guide.add_channel(chid[0:chid.rfind('_')], ch['channel_name'], ch['logo_url'])
|
||
print('Added channel:', ch['channel_name'])
|
||
|
||
guide.write_channels()
|
||
else:
|
||
guide.channels = open('data/channels.xml', mode='r', encoding='UTF-8').read().splitlines()
|
||
|
||
|
||
for x in range(0, 7):
|
||
req = Request(request_url())
|
||
req.add_header('user-agent', 'Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/131.0.0.0 Safari/537.36')
|
||
data = urlopen(req).read()
|
||
data = json.loads(data)
|
||
|
||
for chid in data:
|
||
for epg_data in data[chid]:
|
||
channel = chid[0:chid.rfind('_')]
|
||
title = fix(epg_data['title'])
|
||
comment = fix(epg_data['commentary'])
|
||
start = datetime.fromtimestamp(datetime.strptime(epg_data['programStart'], '%Y%m%d%H%M%S').timestamp() - 32400).strftime('%Y%m%d%H%M%S')
|
||
end = datetime.fromtimestamp(datetime.strptime(epg_data['programEnd'], '%Y%m%d%H%M%S').timestamp() - 32400).strftime('%Y%m%d%H%M%S')
|
||
gen = genre(epg_data['sortGenre'])
|
||
attr = epg_data['attr']
|
||
icon = 'https://tvguide.myjcom.jp{}'.format(epg_data['imgPath']) if int(epg_data['hasImage']) == 1 and epg_data['imgPath'] else None
|
||
|
||
guide.add_programme(channel, title, comment, start, end, gen, attr, icon)
|
||
|
||
print('Added EPG info for', title)
|
||
|
||
date += timedelta(days=1)
|
||
ymd = date.strftime('%Y%m%d')
|
||
|
||
guide.create()
|