Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

pikpak官方增加了新的验证请求 导致pikpak无法正常使用 我使用了python实现了但是不知道如何修改 #6760

Closed
4 tasks done
hansaes opened this issue Jul 13, 2024 · 3 comments
Labels
enhancement New feature or request

Comments

@hansaes
Copy link

hansaes commented Jul 13, 2024

Please make sure of the following things

  • I have read the documentation.
  • I'm sure there are no duplicate issues or discussions.
  • I'm sure this feature is not implemented.
  • I'm sure it's a reasonable and popular requirement.

Description of the feature / 需求描述

pikpak官方增加了新的验证请求 导致pikpak无法正常使用 我使用了python实现了

Suggested solution / 实现思路

在对每个发送请求的时候 都要经过 v1/shield/captcha/init 获取到captcha_token ,然后对请求的时候携带这个进行验证
登录的时候先请求一次获取最初始化的captcha_token 请求这个的时候请求体captcha_token 可以为空
QQ_1720870227575
只会经行登录 可能会出现 滑块校验 需要完成校验 然后获取到traceid 和pid 来重新生成captcha_token

携带最新captcha_token 去完成登录

在后面请求的时候会需要captcha_sign参数
需要设备id和时间戳 但是时间戳好像是写死的 1720760006845
QQ_1720870506376

之后就是每次请求的时候都去验证携带access_token 和 每次验证之后的captcha_token 发送请求就能正常返回接口
QQ_1720870575584

Additional context / 附件

import requests,json,uuid
import image
import recognize
import os
import time
import hashlib

DEBUG_MODE = True
PROXY= ""


def r(e, t):
    n = t - 1
    if n < 0:
        n = 0
    r = e[n]
    u = r["row"] // 2 + 1
    c = r["column"] // 2 + 1
    f = r["matrix"][u][c]
    l = t + 1
    if l >= len(e):
        l = t
    d = e[l]
    p = l % d["row"]
    h = l % d["column"]
    g = d["matrix"][p][h]
    y = e[t]
    m = 3 % y["row"]
    v = 7 % y["column"]
    w = y["matrix"][m][v]
    b = i(f) + o(w)
    x = i(w) - o(f)
    return [s(a(i(f), o(f))), s(a(i(g), o(g))), s(a(i(w), o(w))), s(a(b, x))]


def i(e):
    return int(e.split(",")[0])


def o(e):
    return int(e.split(",")[1])


def a(e, t):
    return str(e) + "^⁣^" + str(t)


def s(e):
    t = 0
    n = len(e)
    for r in range(n):
        t = u(31 * t + ord(e[r]))
    return t


def u(e):
    t = -2147483648
    n = 2147483647
    if e > n:
        return t + (e - n) % (n - t + 1) - 1
    if e < t:
        return n - (t - e) % (n - t + 1) + 1
    return e


def c(e, t):
    return s(e + "⁣" + str(t))


def img_jj(e, t, n):
    return {"ca": r(e, t), "f": c(n, t)}


def md5(input_string):
    return hashlib.md5(input_string.encode()).hexdigest()


def init(phone,xid):

    url = 'https://user.mypikpak.com/v1/shield/captcha/init'
    body = {
        "client_id": "YvtoWO6GNHiuCl7x",
        "action": "POST:/v1/auth/signin",
        "device_id": xid,
        "captcha_token": "",
        "meta": {
            "phone_number": "+86" +phone 
        }
    }
    headers = {
        'host': 'user.mypikpak.com',
        'content-length': str(len(json.dumps(body))),
        'accept': '*/*',
        'accept-encoding': 'gzip, deflate, br',
        'referer': 'https://pc.mypikpak.com',
        'sec-fetch-dest': 'empty',
        'sec-fetch-mode': 'cors',
        'sec-fetch-site': 'cross-site',
        'user-agent': 'MainWindow Mozilla/5.0 (Windows NT 10.0; WOW64) AppleWebKit/537.36 (KHTML, like Gecko) '
                      'PikPak/2.3.2.4101 Chrome/100.0.4896.160 Electron/18.3.15 Safari/537.36',
        'accept-language': 'zh-CN',
        'content-type': 'application/json',
        'sec-ch-ua': '" Not A;Brand";v="99", "Chromium";v="100"',
        'sec-ch-ua-mobile': '?0',
        'sec-ch-ua-platform': '"Windows"',
        'x-client-id': 'YvtoWO6GNHiuCl7x',
        'x-client-version': '2.3.2.4101',
        'x-device-id': xid,
        'x-device-model': 'electron%2F18.3.15',
        'x-device-name': 'PC-Electron',
        'x-device-sign': 'wdi10.ce6450a2dc704cd49f0be1c4eca40053xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx',
        'x-net-work-type': 'NONE',
        'x-os-version': 'Win32',
        'x-platform-version': '1',
        'x-protocol-version': '301',
        'x-provider-name': 'NONE',
        'x-sdk-version': '6.0.0'
    }
    # print("当前代理",PROXY)
    
    res = requests.post(url, json=body, headers=headers) 
    response_data =  res.json()
    print(response_data)
    if 'url' in response_data:
        if DEBUG_MODE:
            print('初始安全验证:')
            print(json.dumps(response_data, indent=4))
        return response_data


def save_image(img_data, img_path):
    if not os.path.exists(os.path.dirname(img_path)):
        os.makedirs(os.path.dirname(img_path))
    with open(img_path, "wb") as f:
        f.write(img_data)


def get_image(xid):
    url = "https://user.mypikpak.com/pzzl/gen"
    params = {
        "deviceid": xid,
        "traceid": ""
    }

    response = requests.get(url, params=params, verify=False)
    imgs_json = response.json()
    frames = imgs_json["frames"]
    pid = imgs_json['pid']
    traceid = imgs_json['traceid']

    if DEBUG_MODE:
        print('滑块ID:')
        print(json.dumps(pid, indent=4))

    params = {
        'deviceid': xid,
        'pid': pid,
        'traceid': traceid
    }
    response1 = requests.get(f"https://user.mypikpak.com/pzzl/image", params=params, verify=False, proxies={"http": PROXY})
    img_data = response1.content

    # 保存初始图片
    save_image(img_data, f'temp/1.png')
    # 保存拼图图片
    image.run(f'temp/1.png', frames)
    # 识别图片
    select_id = recognize.run()

    # 删除缓存图片
    # image.delete_img()

    json_data = img_jj(frames, int(select_id), pid)
    f = json_data['f']
    npac = json_data['ca']
    d_request_data = {
        "pid": pid,
        "device_id": xid,
        "f": f
    }
    response2 = requests.post(f"https://paperkiteidleplus.top/document/pikpak/hash.php", json=d_request_data, verify=False)
    response_data = response2.json()
    d = response_data['d']

    params = {
        'pid': pid,
        'deviceid': xid,
        'traceid': traceid,
        'f': f,
        'n': npac[0],
        'p': npac[1],
        'a': npac[2],
        'c': npac[3],
        'd': d
    }
    response3 = requests.get(f"https://user.mypikpak.com/pzzl/verify", params=params, verify=False, proxies={"http": PROXY})
    response_data = response3.json()

    result = {'pid': pid, 'traceid': traceid, 'response_data': response_data}
    return result



def signin(xid,captcha_token):

    url = 'https://user.mypikpak.com/v1/auth/signin'
    body = {
        "username":"+8615980189332",
        "password":"h1234123",
        "client_id":"YvtoWO6GNHiuCl7x"}
    headers = {
        'host': 'user.mypikpak.com',
        'content-length': str(len(json.dumps(body))),
        'accept': '*/*',
        'accept-encoding': 'gzip, deflate, br',
        'referer': 'https://pc.mypikpak.com',
        'sec-fetch-dest': 'empty',
        'sec-fetch-mode': 'cors',
        'sec-fetch-site': 'cross-site',
        'user-agent': 'MainWindow Mozilla/5.0 (Windows NT 10.0; WOW64) AppleWebKit/537.36 (KHTML, like Gecko) '
                      'PikPak/2.3.2.4101 Chrome/100.0.4896.160 Electron/18.3.15 Safari/537.36',
        'accept-language': 'zh-CN',
        'content-type': 'application/json',
        'sec-ch-ua': '" Not A;Brand";v="99", "Chromium";v="100"',
        'sec-ch-ua-mobile': '?0',
        'sec-ch-ua-platform': '"Windows"',
        'x-client-id': 'YvtoWO6GNHiuCl7x',
        'x-client-version': '2.3.2.4101',
        'x-device-id': xid,
        'x-device-model': 'electron%2F18.3.15',
        'x-device-name': 'PC-Electron',
        'x-device-sign': 'wdi10.ce6450a2dc704cd49f0be1c4eca40053xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx',
        'x-net-work-type': 'NONE',
        'x-os-version': 'Win32',
        'x-platform-version': '1',
        'x-protocol-version': '301',
        'x-provider-name': 'NONE',
        'x-sdk-version': '6.0.0',
        'x-captcha-token' : captcha_token,
    }
    # print("当前代理",PROXY)
    
    res = requests.post(url, json=body, headers=headers) 
    response_data =  res.json()
    print(response_data)
    return response_data
    # if 'url' in response_data:
    #     if DEBUG_MODE:
    #         print('初始安全验证:')
    #         print(json.dumps(response_data, indent=4))
    #     return response_data

def get_new_token(result, xid, captcha):
    traceid = result['traceid']
    pid = result['pid']
    res = requests.get(
                f"https://user.mypikpak.com/credit/v1/report?deviceid={xid}&captcha_token={captcha}&type"
                f"=pzzlSlider&result=0&data={pid}&traceid={traceid}", verify=False,  proxies={"http": PROXY})
    response_data = res.json()
    if DEBUG_MODE:
        print('获取验证TOKEN:')
        print(json.dumps(response_data, indent=4))
    return response_data

def get_files(xid, Authorization,captcha_token):
    url = "https://api-drive.mypikpak.com/drive/v1/files?thumbnail_size=SIZE_MEDIUM&limit=500&parent_id=&with_audit=true&filters=%7B%22phase%22%3A%7B%22eq%22%3A%22PHASE_TYPE_COMPLETE%22%7D%2C%22trashed%22%3A%7B%22eq%22%3Afalse%7D%7D"
    # params = {
    #     "thumbnail_size": "SIZE_MEDIUM",
    #     "limit": "500",
    #     "parent_id": "VO1beZPpQxjygcVK3dBp_c_jo1",
    #     "with_audit": "true",
    #     "filters": '{"phase":{"eq":"PHASE_TYPE_COMPLETE"},"trashed":{"eq":false}}'
    # }

    headers = {
        # 'host': 'user.mypikpak.com',
        # 'accept': '*/*',
        # # 'accept-encoding': 'gzip, deflate, br',
        # 'referer': 'https://mypikpak.com/',
        # # 'sec-fetch-dest': 'empty',
        # # 'sec-fetch-mode': 'cors',
        # # 'sec-fetch-site': 'cross-site',
        'User-Agent': 'Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/126.0.0.0 Safari/537.36',
        # 'accept-language': 'zh-CN',
        'content-type': 'application/json',
        # # 'sec-ch-ua': '" Not A;Brand";v="99", "Chromium";v="100"',
        'sec-ch-ua-mobile': '?0',
        'sec-ch-ua-platform': '"Windows"',
        # 'x-client-id': 'Y2TN1x5YLvmxfay',
        # # 'x-client-version': '2.3.2.4101',
        'X-Device-Id': "c30a6efc8aaa4290bc342806a9d242ac",
        # 'x-device-model': 'electron%2F18.3.15',
        # 'x-device-name': 'PC-Electron',
        # 'x-device-sign': 'wdi10.ce6450a2dc704cd49f0be1c4eca40053xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx',
        # 'x-net-work-type': 'NONE',
        # 'x-os-version': 'Win32',
        # 'x-platform-version': '1',
        # 'x-protocol-version': '301',
        # 'x-provider-name': 'NONE',
        # 'x-sdk-version': '6.0.0',
        "Authorization": "Bearer " + Authorization,
        'x-captcha-token' : captcha_token,
    }

    res = requests.get(url=url, headers=headers,verify=False)
    print(res.text)

def download_files(xid, Authorization,captcha_token):
    url = "https://api-drive.mypikpak.com/drive/v1/files/VO1edfoIeSQ5wssvLzngFImMo1?usage=FETCH"
    # params = {
    #     "thumbnail_size": "SIZE_MEDIUM",
    #     "limit": "500",
    #     "parent_id": "VO1beZPpQxjygcVK3dBp_c_jo1",
    #     "with_audit": "true",
    #     "filters": '{"phase":{"eq":"PHASE_TYPE_COMPLETE"},"trashed":{"eq":false}}'
    # }

    headers = {
        # 'host': 'user.mypikpak.com',
        # 'accept': '*/*',
        # # 'accept-encoding': 'gzip, deflate, br',
        # 'referer': 'https://mypikpak.com/',
        # # 'sec-fetch-dest': 'empty',
        # # 'sec-fetch-mode': 'cors',
        # # 'sec-fetch-site': 'cross-site',
        'User-Agent': 'Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/126.0.0.0 Safari/537.36',
        # 'accept-language': 'zh-CN',
        'content-type': 'application/json',
        # # 'sec-ch-ua': '" Not A;Brand";v="99", "Chromium";v="100"',
        'sec-ch-ua-mobile': '?0',
        'sec-ch-ua-platform': '"Windows"',
        # 'x-client-id': 'Y2TN1x5YLvmxfay',
        # # 'x-client-version': '2.3.2.4101',
        'X-Device-Id': "c30a6efc8aaa4290bc342806a9d242ac",
        # 'x-device-model': 'electron%2F18.3.15',
        # 'x-device-name': 'PC-Electron',
        # 'x-device-sign': 'wdi10.ce6450a2dc704cd49f0be1c4eca40053xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx',
        # 'x-net-work-type': 'NONE',
        # 'x-os-version': 'Win32',
        # 'x-platform-version': '1',
        # 'x-protocol-version': '301',
        # 'x-provider-name': 'NONE',
        # 'x-sdk-version': '6.0.0',
        "Authorization": "Bearer " + Authorization,
        'x-captcha-token' : captcha_token,
    }

    res = requests.get(url=url, headers=headers,verify=False)
    print(res.text)

    res = requests.get(url=res.json()["web_content_link"],headers=headers,verify=False)
    # print(res.text)
    with open("1.mp4","wb") as f:
        f.write(res.content)

def init1(action,xid, captcha_token, sub, sign, t):
    url = 'https://user.mypikpak.com/v1/shield/captcha/init'
    # body = {
    #     "client_id": "YUMx5nI8ZU8Ap8pm",
    #     "action": "GET:/drive/v1/files",
    #     "device_id": xid,
    #     "captcha_token": captcha_token,
    #     "meta": {
    #         # "captcha_sign": "1." + sign,
    #         "captcha_sign":  sign,
    #         "client_version": "2.0.0",
    #         "package_name": "mypikpak.com",
    #         "user_id": sub,
    #         "timestamp": t
    #     },
    # }    
    body = {
    "client_id": "YUMx5nI8ZU8Ap8pm",
    "action": action,
    "device_id": xid,
    "captcha_token": captcha_token,
    "meta": {
        "captcha_sign": "1."+sign,
        "client_version": "2.0.0",
        "package_name": "mypikpak.com",
        "user_id": sub,
        "timestamp": t
    }
}

    print(body)
    headers = {
        'host': 'user.mypikpak.com',
        'content-length': str(len(json.dumps(body))),
        'accept': '*/*',
        'accept-encoding': 'gzip, deflate, br',
        'accept-language': 'zh-CN',
        'referer': 'https://pc.mypikpak.com',
        'sec-fetch-dest': 'empty',
        'sec-fetch-mode': 'cors',
        'sec-fetch-site': 'cross-site',
        'user-agent': 'MainWindow Mozilla/5.0 (Windows NT 10.0; WOW64) AppleWebKit/537.36 (KHTML, like Gecko) '
                      'PikPak/2.3.2.4101 Chrome/100.0.4896.160 Electron/18.3.15 Safari/537.36',
        'content-type': 'application/json',
        'sec-ch-ua': '" Not A;Brand";v="99", "Chromium";v="100"',
        'sec-ch-ua-mobile': '?0',
        'sec-ch-ua-platform': '"Windows"',
        'x-client-id': 'YUMx5nI8ZU8Ap8pm',
        'x-client-version': '2.3.2.4101',
        'x-device-id': xid,
        'x-device-model': 'electron%2F18.3.15',
        'x-device-name': 'PC-Electron',
        'x-device-sign': 'wdi10.c30a6efc8aaa4290bc342806a9d242acxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx',
        'x-net-work-type': 'NONE',
        'x-os-version': 'Win32',
        'x-platform-version': '1',
        'x-protocol-version': '301',
        'x-provider-name': 'NONE',
        'x-sdk-version': '6.0.0'
    }
    res = requests.post(url, json=body, headers=headers, verify=False, proxies={"http": PROXY})
    response_data = res.json()
    if DEBUG_MODE:
        print('二次安全验证:')
        print(json.dumps(response_data, indent=4))
    return response_data

def get_sign(xid, t):
    e = [{ "alg": "md5","salt": "C9qPpZLN8ucRTaTiUMWYS9cQvWOE"},
    {
        "alg": "md5",
        "salt": "+r6CQVxjzJV6LCV"
    },
    {
        "alg": "md5",
        "salt": "F"
    },
    {
        "alg": "md5",
        "salt": "pFJRC"
    },
    {
        "alg": "md5",
        "salt": "9WXYIDGrwTCz2OiVlgZa90qpECPD6olt"
    },
    {
        "alg": "md5",
        "salt": "/750aCr4lm/Sly/c"
    },
    {
        "alg": "md5",
        "salt": "RB+DT/gZCrbV"
    },
    {
        "alg": "md5",
        "salt": ""
    },
    {
        "alg": "md5",
        "salt": "CyLsf7hdkIRxRm215hl"
    },
    {
        "alg": "md5",
        "salt": "7xHvLi2tOYP0Y92b"
    },
    {
        "alg": "md5",
        "salt": "ZGTXXxu8E/MIWaEDB+Sm/"
    },
    {
        "alg": "md5",
        "salt": "1UI3"
    }, {
        "alg": "md5",
        "salt": "E7fP5Pfijd+7K+t6Tg/NhuLq0eEUVChpJSkrKxpO"
    },{
        "alg": "md5",
        "salt": "ihtqpG6FMt65+Xk+tWUH2"
    },{
        "alg": "md5",
        "salt": "NhXXU9rg4XXdzo7u5o"
    }
]
    md5_hash = f"YUMx5nI8ZU8Ap8pm2.0.0mypikpak.com{xid}{t}"
    print(md5_hash)
    for item in e:
        md5_hash += item["salt"]
        md5_hash = md5(md5_hash)
    return md5_hash


if __name__ == "__main__":
    xid = str(uuid.uuid4()).replace("-", "") 
    # xid = "c30a6efc8aaa4290bc342806a9d242ac"
    phone = "159xxxxxxxx"
    Init = init(phone,xid)
    print(Init)
    while True:
        print('验证滑块中...')
        img_info = get_image(xid)
        if img_info['response_data']['result'] == 'accept':
            print('验证通过!!!')
            break
        else:
            print('验证失败, 重新验证滑块中...')
    captcha_token_info = get_new_token(img_info, xid, Init['captcha_token'])
    # captcha_token_info = {
    # "captcha_token": "xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx",
    # "expires_in": 300
    # }
    access_token_info = signin(xid,captcha_token_info['captcha_token'])
#     access_token_info = {
#     "token_type": "Bearer",
#     "access_token": "xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx",
#     "refresh_token": "os.6Gz6ZRmLlGaSFk0XqFJuoYE2uNFUZZ5FTiNIFKqPzNaS9h3kJmnn5j3r",
#     "expires_in": 7200,
#     "sub": "ZpIWKIAbIJFvg6LB"
# }
    # get_files(xid,access_token_info["access_token"], captcha_token_info['captcha_token'])

    # current_time = str(int(round(time.time() * 1000)))
    current_time = "1720760006845"
    sign = get_sign(xid, current_time)
    # print(sign)
    # sign = "1.c196bc487a4c388b80f880aabbfa3fca"
    # xid = "c30a6efc8aaa4290bc342806a9d242ac"
    get_response = init1("GET:/drive/v1/files",xid, captcha_token_info['captcha_token'], access_token_info['sub'], sign, current_time)

    # get_files(xid,access_token_info["access_token"], get_response['captcha_token'])
    download_response = init1("GET:/drive/v1/files/VO1edfoIeSQ5wssvLzngFImMo1",xid, captcha_token_info['captcha_token'], access_token_info['sub'], sign, current_time)
    download_files(xid,access_token_info["access_token"], download_response['captcha_token'])
@hansaes hansaes added the enhancement New feature or request label Jul 13, 2024
@foxxorcat
Copy link
Contributor

pikpak 使用迅雷同款验证方式(底层估计也是迅雷那套),复制一份迅雷的改下配置就行

@xixky
Copy link

xixky commented Jul 14, 2024

pikpak 现在想禁止第三方客户端了,强推官方的webdav

@Three-taile-dragon
Copy link
Contributor

#6775 已PR

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
enhancement New feature or request
Projects
None yet
Development

No branches or pull requests

4 participants