diff --git a/FGBLH/Web鱼壳海豚.json b/FGBLH/Web鱼壳海豚.json index fb443815..e95564cb 100644 --- a/FGBLH/Web鱼壳海豚.json +++ b/FGBLH/Web鱼壳海豚.json @@ -820,6 +820,24 @@ "type": 3, "api": "https://ghfast.top/https://raw.githubusercontent.com/FGBLH/HKL/refs/heads/main/py/catemby.py" }, + { + "key": "大屌视频", + "name": "🐬大屌视频.py|🔞[成人]", + "type": 3, + "api": "https://ghfast.top/https://raw.githubusercontent.com/FGBLH/HKL/refs/heads/main/py/大屌视频.py" + }, + { + "key": "高端视频", + "name": "🐬高端视频.py|🔞[成人]", + "type": 3, + "api": "https://ghfast.top/https://raw.githubusercontent.com/FGBLH/HKL/refs/heads/main/py/高端视频.py" + }, + { + "key": "猫咪AV", + "name": "🐬猫咪AV.py|🔞[成人]", + "type": 3, + "api": "https://ghfast.top/https://raw.githubusercontent.com/FGBLH/HKL/refs/heads/main/py/猫咪AV.py" + }, { "key": "妈妈自拍", "name": "🐬妈妈自拍.py|🔞[成人]", diff --git a/FGBLH/Web鱼壳海豚py.json b/FGBLH/Web鱼壳海豚py.json index f4cea297..8e0be3a8 100644 --- a/FGBLH/Web鱼壳海豚py.json +++ b/FGBLH/Web鱼壳海豚py.json @@ -563,6 +563,24 @@ "type": 3, "api": "https://ghfast.top/https://raw.githubusercontent.com/FGBLH/HKL/refs/heads/main/py/catemby.py" }, + { + "key": "大屌视频", + "name": "🐬大屌视频.py|🔞[成人]", + "type": 3, + "api": "https://ghfast.top/https://raw.githubusercontent.com/FGBLH/HKL/refs/heads/main/py/大屌视频.py" + }, + { + "key": "高端视频", + "name": "🐬高端视频.py|🔞[成人]", + "type": 3, + "api": "https://ghfast.top/https://raw.githubusercontent.com/FGBLH/HKL/refs/heads/main/py/高端视频.py" + }, + { + "key": "猫咪AV", + "name": "🐬猫咪AV.py|🔞[成人]", + "type": 3, + "api": "https://ghfast.top/https://raw.githubusercontent.com/FGBLH/HKL/refs/heads/main/py/猫咪AV.py" + }, { "key": "妈妈自拍", "name": "🐬妈妈自拍.py|🔞[成人]", diff --git a/FGBLH/ok海豚.json b/FGBLH/ok海豚.json index 365e3738..d7af8ec5 100644 --- a/FGBLH/ok海豚.json +++ b/FGBLH/ok海豚.json @@ -748,6 +748,24 @@ "type": 3, "api": "https://ghfast.top/https://raw.githubusercontent.com/FGBLH/HKL/refs/heads/main/py/蜜桃视频.py" }, + { + "key": "大屌视频", + "name": "🐬大屌视频.py|🔞", + "type": 3, + "api": "https://ghfast.top/https://raw.githubusercontent.com/FGBLH/HKL/refs/heads/main/py/大屌视频.py" + }, + { + "key": "高端视频", + "name": "🐬高端视频.py|🔞", + "type": 3, + "api": "https://ghfast.top/https://raw.githubusercontent.com/FGBLH/HKL/refs/heads/main/py/高端视频.py" + }, + { + "key": "猫咪AV", + "name": "🐬猫咪AV.py|🔞", + "type": 3, + "api": "https://ghfast.top/https://raw.githubusercontent.com/FGBLH/HKL/refs/heads/main/py/猫咪AV.py" + }, { "key": "妈妈自拍", "name": "🐬妈妈自拍.py|🔞", diff --git a/FGBLH/ok海豚py.json b/FGBLH/ok海豚py.json index adfa76c8..6964deba 100644 --- a/FGBLH/ok海豚py.json +++ b/FGBLH/ok海豚py.json @@ -580,6 +580,24 @@ "type": 3, "api": "https://ghfast.top/https://raw.githubusercontent.com/FGBLH/HKL/refs/heads/main/py/蜜桃视频.py" }, + { + "key": "大屌视频", + "name": "🐬大屌视频.py|🔞", + "type": 3, + "api": "https://ghfast.top/https://raw.githubusercontent.com/FGBLH/HKL/refs/heads/main/py/大屌视频.py" + }, + { + "key": "高端视频", + "name": "🐬高端视频.py|🔞", + "type": 3, + "api": "https://ghfast.top/https://raw.githubusercontent.com/FGBLH/HKL/refs/heads/main/py/高端视频.py" + }, + { + "key": "猫咪AV", + "name": "🐬猫咪AV.py|🔞", + "type": 3, + "api": "https://ghfast.top/https://raw.githubusercontent.com/FGBLH/HKL/refs/heads/main/py/猫咪AV.py" + }, { "key": "妈妈自拍", "name": "🐬妈妈自拍.py|🔞", diff --git a/FGBLH/py/大屌视频.py b/FGBLH/py/大屌视频.py new file mode 100644 index 00000000..73916fdf --- /dev/null +++ b/FGBLH/py/大屌视频.py @@ -0,0 +1,675 @@ +# -*- coding: utf-8 -*- +import sys +import re +import json +import base64 +import threading +import requests +import urllib3 +import os +import time +import random +from datetime import datetime +from http.server import HTTPServer, BaseHTTPRequestHandler +from socketserver import ThreadingMixIn +from urllib.parse import unquote, quote, urljoin, urlparse + +urllib3.disable_warnings() +sys.path.append('..') +from base.spider import Spider as BaseSpider + +# ========================== 全局本地代理服务器 ========================== +# 用于解决图片防盗链、跨域问题,所有外域图片均通过 127.0.0.1 代理访问 +_proxy_port = 0 +_proxy_started = False +_proxy_session = requests.Session() +_proxy_session.verify = False +_proxy_headers = { + 'User-Agent': 'Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/115.0.0.0 Safari/537.36', + 'Accept': 'text/html,application/xhtml+xml,application/xml;q=0.9,image/webp,image/apng,*/*;q=0.8', + 'Accept-Language': 'zh-CN,zh;q=0.9', + 'Referer': 'https://dadiao.cc/', +} + +class _ThreadedHTTPServer(ThreadingMixIn, HTTPServer): + daemon_threads = True + allow_reuse_address = True + +class _ProxyHandler(BaseHTTPRequestHandler): + def do_GET(self): + try: + real_url = unquote(self.path[1:]) + if not real_url or not real_url.startswith('http'): + self.send_response(404) + self.end_headers() + return + parsed = urlparse(real_url) + referer = f'{parsed.scheme}://{parsed.netloc}/' if parsed.netloc else 'https://dadiao.cc/' + headers = dict(_proxy_headers) + headers['Referer'] = referer + r = _proxy_session.get(real_url, headers=headers, timeout=20, verify=False, stream=True) + content_type = r.headers.get('Content-Type', 'image/jpeg') + content_length = r.headers.get('Content-Length') + self.send_response(200) + self.send_header('Content-Type', content_type) + if content_length: + self.send_header('Content-Length', content_length) + self.send_header('Access-Control-Allow-Origin', '*') + self.send_header('Access-Control-Allow-Methods', 'GET, OPTIONS') + self.end_headers() + for chunk in r.iter_content(chunk_size=8192): + if chunk: + self.wfile.write(chunk) + except BrokenPipeError: + pass + except Exception as e: + try: + self.send_response(404) + self.end_headers() + except: + pass + + def log_message(self, format, *args): + pass + +def _find_free_port(): + import socket + sk = socket.socket(socket.AF_INET, socket.SOCK_STREAM) + sk.bind(('127.0.0.1', 0)) + port = sk.getsockname()[1] + sk.close() + return port + +def _start_proxy(): + global _proxy_port, _proxy_started + if _proxy_started: + return + _proxy_port = _find_free_port() + server = _ThreadedHTTPServer(('127.0.0.1', _proxy_port), _ProxyHandler) + threading.Thread(target=server.serve_forever, daemon=True).start() + _proxy_started = True + +# ========================== Spider 主体 ========================== +class Spider(BaseSpider): + session = requests.Session() + host = 'https://dadiao.cc' + play_host = 'https://m.892539.xyz' + + def __init__(self): + super().__init__() + self._categories_cache = None + self._zone_map = {} + self._sub_cat_names = {} + self._debug = True + self._log('Spider 初始化完成') + + def _log(self, msg): + if self._debug: + print(f'[dadiao] {msg}') + + def getName(self): + return 'dadiao' + + def isVideoFormat(self, url): + if not url: + return False + return '.m3u8' in url or '.mp4' in url or '.ts' in url or url.startswith('magnet:') + + def manualVideoCheck(self): + return False + + def destroy(self): + pass + + def localProxy(self, param): + return [404, 'text/plain', ''] + + def init(self, extend=''): + self.session.verify = False + self.session.headers.update(self._get_headers()) + _start_proxy() + text = self._fetch(self.host) + if text: + self._load_categories(text) + + def _get_headers(self, referer=None): + headers = { + 'User-Agent': 'Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/115.0.0.0 Safari/537.36', + 'Accept': 'text/html,application/xhtml+xml,application/xml;q=0.9,image/webp,image/apng,*/*;q=0.8', + 'Accept-Language': 'zh-CN,zh;q=0.9', + 'Referer': referer or self.host + '/', + } + return headers + + def _proxy_url(self, url): + if not url: + return '' + if url.startswith('http://127.0.0.1'): + return url + if url.startswith('//'): + url = 'https:' + url + elif url.startswith('/'): + url = urljoin(self.host, url) + return f'http://127.0.0.1:{_proxy_port}/{quote(url, safe="")}' + + def _fetch(self, url, referer=None, retries=3): + for i in range(retries): + try: + if referer is None: + referer = self.host + '/' + headers = self._get_headers(referer) + if i > 0: + time.sleep(random.uniform(0.5, 1.5)) + r = self.session.get(url, headers=headers, timeout=30, verify=False) + r.encoding = 'utf-8' + if r.status_code == 200: + return r.text + elif r.status_code in [403, 429, 503]: + self._log(f'请求被拦截 [{r.status_code}],重试 {i+1}/{retries}') + else: + self._log(f'请求返回 [{r.status_code}],终止') + return '' + except Exception as e: + self._log(f'请求异常 [{e}],重试 {i+1}/{retries}') + return '' + + # ========================== 分类加载(蜜桃式:区域为class,子分类为filters) ========================== + def _load_categories(self, text): + if not text: + self._log('首页HTML为空,无法加载分类') + return [] + self._zone_map = {} + self._sub_cat_names = {} + + # 按 zone-tag 与 cate-items 顺序配对提取 + zone_names = re.findall(r'