98 lines
3.3 KiB
Python
98 lines
3.3 KiB
Python
from datetime import datetime, UTC
|
|
|
|
from yuxi.channel.extensions.alipay.types import AlipayAccount, AlipayInboundEvent
|
|
from yuxi.channel.message.models import MessageType, PeerInfo, PeerKind, UnifiedMessage
|
|
|
|
|
|
def convert_alipay_event(event: AlipayInboundEvent, account: AlipayAccount) -> UnifiedMessage | None:
|
|
msg_type = _map_msg_type(event)
|
|
|
|
if event.msg_type == "event":
|
|
if event.event_type in ("follow", "enter"):
|
|
return _build_event_message(event, account, msg_type)
|
|
return None
|
|
|
|
return UnifiedMessage(
|
|
msg_id=event.msg_id,
|
|
channel_type="alipay",
|
|
account_id=account.account_id,
|
|
content=_extract_content(event),
|
|
sender=PeerInfo(
|
|
kind=PeerKind.DIRECT,
|
|
id=event.from_user_id,
|
|
display_name=event.from_user_name or event.from_user_id,
|
|
),
|
|
message_type=msg_type,
|
|
media_urls=_extract_media_urls(event),
|
|
timestamp=datetime.fromtimestamp(event.create_time / 1000, tz=UTC),
|
|
raw_payload=event.raw,
|
|
metadata={
|
|
"FromAlipayUserId": event.from_user_id,
|
|
"AppId": event.app_id,
|
|
"MsgType": event.msg_type,
|
|
"EventType": event.event_type or "",
|
|
},
|
|
body_for_agent=_extract_content(event),
|
|
)
|
|
|
|
|
|
def _map_msg_type(event: AlipayInboundEvent) -> MessageType:
|
|
if event.msg_type == "text":
|
|
return MessageType.TEXT
|
|
if event.msg_type == "image":
|
|
return MessageType.IMAGE
|
|
return MessageType.EVENT
|
|
|
|
|
|
def _extract_content(event: AlipayInboundEvent) -> str:
|
|
if event.msg_type == "text":
|
|
return (event.biz_content or {}).get("content", "")
|
|
if event.msg_type == "image":
|
|
return "[图片消息]"
|
|
if event.msg_type == "event":
|
|
event_names = {
|
|
"follow": "关注了生活号",
|
|
"unfollow": "取消关注",
|
|
"enter": "进入了生活号",
|
|
"click": f"点击了菜单: {(event.biz_content or {}).get('action_name', '')}",
|
|
}
|
|
return event_names.get(event.event_type or "", f"事件: {event.event_type}")
|
|
return ""
|
|
|
|
|
|
def _extract_media_urls(event: AlipayInboundEvent) -> list[str]:
|
|
if event.msg_type == "image":
|
|
biz = event.biz_content or {}
|
|
urls = []
|
|
if biz.get("pic_url"):
|
|
urls.append(biz["pic_url"])
|
|
if biz.get("media_id"):
|
|
urls.append(f"alipay://media/{biz['media_id']}")
|
|
return urls
|
|
return []
|
|
|
|
|
|
def _build_event_message(event: AlipayInboundEvent, account: AlipayAccount, msg_type: MessageType) -> UnifiedMessage:
|
|
return UnifiedMessage(
|
|
msg_id=event.msg_id,
|
|
channel_type="alipay",
|
|
account_id=account.account_id,
|
|
content=_extract_content(event),
|
|
sender=PeerInfo(
|
|
kind=PeerKind.DIRECT,
|
|
id=event.from_user_id,
|
|
display_name=event.from_user_name or event.from_user_id,
|
|
),
|
|
message_type=msg_type,
|
|
media_urls=[],
|
|
timestamp=datetime.fromtimestamp(event.create_time / 1000, tz=UTC),
|
|
raw_payload=event.raw,
|
|
metadata={
|
|
"FromAlipayUserId": event.from_user_id,
|
|
"AppId": event.app_id,
|
|
"MsgType": event.msg_type,
|
|
"EventType": event.event_type or "",
|
|
},
|
|
body_for_agent=_extract_content(event),
|
|
)
|