File size: 3,988 Bytes
0f30007
 
97fe330
0f30007
 
a7e74e9
 
 
 
 
 
 
 
 
 
 
 
 
 
 
0f30007
 
97fe330
 
 
 
 
 
7741f33
 
 
 
 
97fe330
a7e74e9
97fe330
 
 
0f30007
 
 
 
 
 
 
 
 
 
21e99f3
0f30007
 
 
 
 
 
 
 
 
 
a7e74e9
0f30007
 
 
 
97fe330
 
0f30007
21e99f3
0f30007
 
 
 
 
 
 
 
 
 
327d8d0
0f30007
 
 
 
 
 
 
 
 
 
 
 
 
 
 
e26318c
 
 
 
 
0f30007
 
e26318c
0f30007
 
 
 
 
 
 
58875bc
 
0f30007
 
ec289a5
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
import os
import re
import shutil
import requests
import gradio as gr
from datetime import datetime
from zoneinfo import ZoneInfo
from tzlocal import get_localzone

TIMEOUT = 15
API = os.getenv("api_tiktok")


def timestamp(naive_time: datetime = None, target_tz=ZoneInfo("Asia/Shanghai")):
    if not naive_time:
        naive_time = datetime.now()

    local_tz = get_localzone()
    aware_local = naive_time.replace(tzinfo=local_tz)
    return aware_local.astimezone(target_tz).strftime("%Y-%m-%d %H:%M:%S")


def download_file(url, video_id, cache_dir="./__pycache__"):
    if os.path.exists(cache_dir):
        shutil.rmtree(cache_dir)

    os.makedirs(cache_dir)
    local_file = f"{cache_dir}/{video_id}.mp4"
    response = requests.get(url, stream=True)
    if response.status_code == 200:
        with open(local_file, "wb") as file:
            for chunk in response.iter_content(chunk_size=8192):
                file.write(chunk)

    print(f"[{timestamp()}] File was downloaded to {local_file}")
    return local_file


def extract_fst_url(text):
    url_pattern = r'(https?://[^\s"]+)'
    match = re.search(url_pattern, text)
    if match:
        return match.group(1)
    else:
        return None


def infer(video_url):
    video = parse_time = desc = avatar = author = sign = None
    if not video_url:
        desc = "The video sharing link is empty!"
        return video, parse_time, desc, avatar, author, sign

    video_url = extract_fst_url(video_url)
    if not video_url:
        desc = "Please enter a valid video sharing link!"
        return video, parse_time, desc, avatar, author, sign

    try:
        response = requests.get(API, params={"url": video_url}, timeout=TIMEOUT)
        response_json = response.json()
        retcode = response_json["code"]
        if retcode == 200:
            response_data = response_json["data"]
            video_id = response_data["play_url"].split("video_id=")[1].split("&")[0]
            video = download_file(response_data["video_url"], video_id)
            parse_time = response_data["parse_time"]

            additional_data = response_data["additional_data"][0]
            desc = additional_data["desc"]
            avatar = additional_data["url"].split("?from=")[0]
            author = additional_data["nickname"]
            sign = additional_data["signature"]

        else:
            desc = f"Interface call failed, error code: HTTP {retcode}"

    except Exception as e:
        desc = f"Video parsing failed: {e}"

    return video, parse_time, desc, avatar, author, sign


if __name__ == "__main__":
    gr.Interface(
        fn=infer,
        inputs=[
            gr.Textbox(
                label="Please enter TikTok video sharing short link",
                placeholder="https://v.douyin.com/*",
                show_copy_button=True,
            ),
        ],
        outputs=[
            gr.Video(
                label="Video download",
                show_download_button=True,
                show_share_button=False,
            ),
            gr.Textbox(label="Parsing time", show_copy_button=True),
            gr.Textbox(label="Video description", show_copy_button=True),
            gr.Image(label="Author avatar", show_share_button=False),
            gr.Textbox(label="Author nickname", show_copy_button=True),
            gr.TextArea(label="Author signature", show_copy_button=True),
        ],
        title="Parse TikTok video without watermark",
        description="This site does not provide any video storage services, only to provide the most basic resolution services",
        flagging_mode="never",
        examples=[
            "https://v.douyin.com/8FVe5DzarE0",
            "8.20 Njc:/ [email protected] 11/03 黑塔女士举世无双!# 大黑塔 # 黑塔 # 崩坏星穹铁道 # 再创世的凯歌 # 天才俱乐部  https://v.douyin.com/8FVe5DzarE0/ 复制此链接,打开Dou音搜索,直接观看视频!",
        ],
        cache_examples=False,
    ).launch()