diff --git a/rog/management/commands/debug_checkin.py b/rog/management/commands/debug_checkin.py new file mode 100644 index 0000000..e857384 --- /dev/null +++ b/rog/management/commands/debug_checkin.py @@ -0,0 +1,56 @@ +from django.core.management.base import BaseCommand +from rog.models import GpsLog, GpsCheckin, Entry + +class Command(BaseCommand): + help = 'Debug checkin data for specific team' + + def add_arguments(self, parser): + parser.add_argument('zekken', type=str, help='Zekken number to check') + parser.add_argument('--event', type=str, default='岐阜ロゲイニング2025', help='Event name') + + def handle(self, *args, **options): + zekken = options['zekken'] + event_name = options['event'] + + self.stdout.write(f'=== Debugging checkin data for zekken {zekken}, event {event_name} ===') + + # Entry確認 + self.stdout.write('\n=== Entry Records ===') + entries = Entry.objects.filter(zekken_number=int(zekken), event__event_name=event_name) + self.stdout.write(f'Found {entries.count()} entries') + for entry in entries: + self.stdout.write(f' Team: {entry.team.team_name}, Zekken: {entry.zekken_number}, Event ID: {entry.event.id}') + + if not entries.exists(): + self.stdout.write('❌ No entries found') + return + + entry = entries.first() + + # GpsLog確認(文字列として検索) + self.stdout.write('\n=== GpsLog Records (str zekken) ===') + logs_str = GpsLog.objects.filter(zekken_number=str(zekken), event_code=event_name) + self.stdout.write(f'Found {logs_str.count()} records in GpsLog (str)') + for log in logs_str[:10]: + self.stdout.write(f' ID: {log.id}, CP: {log.cp_number}, Time: {log.checkin_time}, Event: {log.event_code}') + + # GpsLog確認(整数として検索) + self.stdout.write('\n=== GpsLog Records (int zekken) ===') + logs_int = GpsLog.objects.filter(zekken_number=int(zekken), event_code=event_name) + self.stdout.write(f'Found {logs_int.count()} records in GpsLog (int)') + for log in logs_int[:10]: + self.stdout.write(f' ID: {log.id}, CP: {log.cp_number}, Time: {log.checkin_time}, Event: {log.event_code}') + + # GpsCheckin確認 + self.stdout.write('\n=== GpsCheckin Records ===') + checkins = GpsCheckin.objects.filter(zekken=str(zekken), event_code=event_name) + self.stdout.write(f'Found {checkins.count()} records in GpsCheckin') + for checkin in checkins[:10]: + self.stdout.write(f' ID: {checkin.id}, CP: {checkin.cp_number}, Time: {checkin.checkin_time}, Event: {checkin.event_code}') + + # 全てのGpsLogレコードから類似のものを検索 + self.stdout.write('\n=== All GpsLog Records for this event ===') + all_logs = GpsLog.objects.filter(event_code=event_name) + self.stdout.write(f'Total records in event: {all_logs.count()}') + for log in all_logs[:5]: + self.stdout.write(f' ID: {log.id}, Zekken: {log.zekken_number} (type: {type(log.zekken_number)}), CP: {log.cp_number}, Event: {log.event_code}') diff --git a/rog/views_apis/api_edit.py b/rog/views_apis/api_edit.py index 6af53d1..fc83a00 100755 --- a/rog/views_apis/api_edit.py +++ b/rog/views_apis/api_edit.py @@ -18,6 +18,12 @@ from urllib.parse import urljoin logger = logging.getLogger(__name__) +def get_next_serial_number(): + """次のserial_numberを取得""" + from django.db.models import Max + max_serial = GpsLog.objects.aggregate(Max('serial_number'))['serial_number__max'] + return (max_serial or 0) + 1 + """ 解説 この実装では以下の処理を行っています: @@ -246,10 +252,7 @@ def start_checkin(request): event_code=event_code, cp_number="START", serial_number=0, - latitude=0.0, - longitude=0.0, - checkin_time=timezone.now(), - extra_data={"source": "admin_start"} + checkin_time=timezone.now() ) logger.info(f"Team {entry.team.team_name} (zekken: {zekken_number}) started at {start_info.checkin_time}") @@ -344,7 +347,7 @@ def add_checkin(request): "message": "指定されたゼッケン番号のチームが見つかりません" }, status=status.HTTP_404_NOT_FOUND) - logger.info(f"[ADMIN_CHECKIN] ✅ Team found - ID: {request_id}, team_name: '{entry.team_name}', zekken: {zekken_number}, entry_id: {entry.id}") + logger.info(f"[ADMIN_CHECKIN] ✅ Team found - ID: {request_id}, team_name: '{entry.team.team_name}', zekken: {zekken_number}, entry_id: {entry.id}") # チームがスタートしているか確認(オプション) start_record = GpsLog.objects.filter( @@ -358,16 +361,13 @@ def add_checkin(request): # スタート情報がない場合は自動的にスタートさせる # 注意: 管理画面からの操作なので、自動スタートを許可 GpsLog.objects.create( + serial_number=get_next_serial_number(), zekken_number=zekken_number, event_code=event_code, cp_number="START", - serial_number=0, - latitude=0.0, - longitude=0.0, - checkin_time=timezone.now(), - extra_data={"auto_start": True, "source": "admin_bulk_checkin"} + checkin_time=timezone.now() ) - logger.info(f"[ADMIN_CHECKIN] ✅ Auto-started team - ID: {request_id}, team_name: '{entry.team_name}', zekken: {zekken_number}") + logger.info(f"[ADMIN_CHECKIN] ✅ Auto-started team - ID: {request_id}, team_name: '{entry.team.team_name}', zekken: {zekken_number}") # チェックポイントリストを解析 cp_list = [cp.strip() for cp in cp_list_string.split(',') if cp.strip()] @@ -412,11 +412,11 @@ def add_checkin(request): # チェックポイント登録 checkpoint = GpsLog.objects.create( + serial_number=get_next_serial_number(), zekken_number=zekken_number, event_code=event_code, cp_number=cp_number, - checkin_time=timezone.now(), - is_service_checked=event_cp.is_service_cp if event_cp else False + checkin_time=timezone.now() ) logger.info(f"Successfully registered CP {cp_number} for team: {entry.team_name} (zekken: {zekken_number})")