import requests from typing import Optional # 在脚本顶端维护可用的 token 数组(按顺序尝试) TOKENS = [ # 在此添加更多 token:"token2", "token3", ... ] HOME_URL = "https://m-zjt.kefang.net/api/zms/zhijiaotong/page/homePageData" PUNCH_URL = "https://m-zjt.kefang.net/api/zms/attendance/attendanceRecord/punchCourseByStudent" def punch(attendance_id: str, token: str) -> requests.Response: payload = { "attendanceId": attendance_id } headers = { "User-Agent": "Dart/3.6 (dart:io)", "Accept-Encoding": "gzip", "Content-Type": "application/x-www-form-urlencoded", "content-length": "32", "Cookie": f"token={token}", "Host": "m-zjt.kefang.net", } return requests.put(PUNCH_URL, data=payload, headers=headers, verify=False) def extract_content_id(payload: dict) -> Optional[str]: data = payload.get("data", {}) # Prefer messages array for attendance messages = data.get("messages") if isinstance(messages, list): for msg in messages: # look for 打卡 type if (msg.get("type") == "打卡") or ("打卡" in str(msg.get("tradeType", ""))): cid = msg.get("contentId") if cid: return str(cid) # fallback: single data.message presence indicates info, but no contentId return None def main(): # 依次使用 TOKENS 尝试获取打卡 contentId 并发起打卡 for token in TOKENS: headers = { "User-Agent": "Dart/3.6 (dart:io)", "Accept-Encoding": "gzip", "content-type": "application/x-www-form-urlencoded", "Cookie": f"token={token}", "host": "m-zjt.kefang.net", } try: resp = requests.get(HOME_URL, headers=headers, verify=False) print(resp.text) except Exception as e: # 当前 token 请求失败,继续尝试下一个 continue try: payload = resp.json() except ValueError: # 非 JSON 或解析失败,继续尝试下一个 token continue content_id = extract_content_id(payload) if not content_id: # 未获取到打卡消息,尝试下一个 token continue # 找到 contentId,执行打卡 try: punch_resp = punch(content_id, token) print(punch_resp.text) if punch_resp.status_code == 200: print("打卡成功!") return except Exception: # 打卡失败,尝试下一个 token continue # 所有 token 尝试失败 print("未获取到打卡信息") raise SystemExit(0) if __name__ == "__main__": main()