- P1: bet.py赔率计算移入锁内防竞态 - P1: config.py TESTERS解析失败添加warning日志 - P2: 新增赛马取消命令(积分退还/任务取消/状态重置) - P3: bet.py清理未使用的_send_to_scope导入 - 将commands.py拆分为commands/包(access/bet/help/race/register) - OpenSpec变更提案: fix-race-conditions-and-logs
75 lines
2.7 KiB
Python
75 lines
2.7 KiB
Python
import asyncio
|
||
from nonebot import on_command
|
||
from nonebot.adapters.onebot.v11 import Bot, Event
|
||
from . import (
|
||
room_store, race_engine, config, logger,
|
||
get_scope, check_access, get_event_id,
|
||
_find_user_horse, _find_duplicate_horse, _get_horses_in_order,
|
||
_format_horse_label, _send_to_scope, _build_race_image_message,
|
||
run_race_with_settlement,
|
||
)
|
||
from ..models import HorseState, RoomState
|
||
|
||
@register_cmd.handle()
|
||
async def handle_register(bot: Bot, event: Event):
|
||
"""Handle horse registration."""
|
||
if not await check_access(bot, event):
|
||
await register_cmd.finish("无权限访问此功能")
|
||
return
|
||
|
||
msg = str(event.get_message()).strip()
|
||
parts = msg.split(None, 1)
|
||
user_id = get_event_id(event)
|
||
horse_name = _normalize_horse_name(parts[1]) if len(parts) > 1 else await room_store.get_last_horse_name(user_id) or ""
|
||
|
||
if not horse_name:
|
||
scope = get_scope(event)
|
||
horse_name = await _get_user_name(bot, scope, user_id)
|
||
# Ensure name is not too long when using nickname as default
|
||
if len(horse_name) > 10:
|
||
horse_name = horse_name[:10]
|
||
|
||
if len(horse_name) > 10:
|
||
await register_cmd.finish("马匹名不能超过10个字符")
|
||
return
|
||
|
||
scope = get_scope(event)
|
||
lock = room_store.get_lock(scope)
|
||
|
||
async with lock:
|
||
room = room_store.get_room(scope)
|
||
if not room:
|
||
room = await room_store.create_room(scope)
|
||
|
||
if room.state != RoomState.WAITING:
|
||
await register_cmd.finish("比赛正在进行中,无法报名")
|
||
return
|
||
|
||
if len(room.horses) >= 8:
|
||
await register_cmd.finish("房间已满(最多8匹马)")
|
||
return
|
||
|
||
duplicate_horse = _find_duplicate_horse(room, horse_name)
|
||
if duplicate_horse:
|
||
await register_cmd.finish(f"马匹名 \"{horse_name}\" 已被 {_format_horse_label(duplicate_horse)} 使用")
|
||
return
|
||
|
||
existing_user_horse = _find_user_horse(room, user_id)
|
||
if existing_user_horse:
|
||
await register_cmd.finish(f"你已经报名了,当前马匹为 {_format_horse_label(existing_user_horse)}")
|
||
return
|
||
|
||
horse_index = room.next_horse_index
|
||
room.next_horse_index += 1
|
||
room.horses[horse_name] = Horse(owner_id=user_id, name=horse_name, index=horse_index)
|
||
await room_store.set_last_horse_name(user_id, horse_name)
|
||
|
||
count = len(room.horses)
|
||
registered_horse = room.horses[horse_name]
|
||
await register_cmd.finish(f"报名成功!{_format_horse_label(registered_horse)} 已加入比赛({count}/8)")
|
||
|
||
|
||
cancel_cmd = on_command("赛马取消报名", priority=5)
|
||
|
||
|