import requests import json import time import logging from app.core.config import settings from typing import Dict, Any, Optional, List class WecomClient: """企业微信客户端""" def __init__(self): self.corp_id = settings.WECHAT_CORP_ID self.corp_secret = settings.WECHAT_CORP_SECRET self.access_token = None self.token_expires_at = 0 async def get_access_token(self) -> str: """获取访问令牌""" # 检查令牌是否过期 if self.access_token and time.time() < self.token_expires_at: return self.access_token # 获取新令牌 url = f"https://qyapi.weixin.qq.com/cgi-bin/gettoken?corpid={self.corp_id}&corpsecret={self.corp_secret}" try: response = requests.get(url) result = response.json() if result.get("errcode") == 0: self.access_token = result.get("access_token") self.token_expires_at = time.time() + result.get("expires_in") - 200 # 提前200秒过期 return self.access_token else: logging.error(f"获取企业微信访问令牌失败: {result}") return None except Exception as e: logging.exception(f"获取企业微信访问令牌异常: {str(e)}") return None async def miniprogram_to_userid(self, openid: str) -> Optional[Dict[str, Any]]: """ 小程序openid转换为企业微信userid Args: openid: 小程序用户的openid Returns: Dict: 包含userid或pending_id的字典 """ token = await self.get_access_token() if not token: return None url = f"https://qyapi.weixin.qq.com/cgi-bin/miniprogram/jscode2session?access_token={token}" data = { "code": openid, "grant_type": "authorization_code" } try: response = requests.post(url, json=data) result = response.json() if result.get("errcode") == 0: return { "userid": result.get("userid"), "pending_id": result.get("pending_id") } else: logging.error(f"小程序openid转换失败: {result}") return None except Exception as e: logging.exception(f"小程序openid转换异常: {str(e)}") return None async def get_user_in_group_chat(self, userid: str) -> List[str]: """ 获取用户所在的群聊列表 Args: userid: 企业微信用户ID Returns: List[str]: 群聊ID列表 """ token = await self.get_access_token() if not token: return [] url = f"https://qyapi.weixin.qq.com/cgi-bin/externalcontact/list_group_chat?access_token={token}" # 先获取所有群聊 try: response = requests.post(url, json={}) result = response.json() if result.get("errcode") != 0: logging.error(f"获取群聊列表失败: {result}") return [] chat_ids = [] for chat in result.get("group_chat_list", []): chat_id = chat.get("chat_id") # 获取群聊详情 detail_url = f"https://qyapi.weixin.qq.com/cgi-bin/externalcontact/groupchat/get?access_token={token}" detail_response = requests.post(detail_url, json={"chat_id": chat_id}) detail_result = detail_response.json() if detail_result.get("errcode") == 0: group_chat = detail_result.get("group_chat", {}) members = group_chat.get("member_list", []) # 检查用户是否在群内 for member in members: if member.get("userid") == userid: chat_ids.append(chat_id) break return chat_ids except Exception as e: logging.exception(f"获取用户群聊异常: {str(e)}") return [] wecom_client = WecomClient()