Refactor change...
This commit is contained in:
+40
@@ -0,0 +1,40 @@
|
|||||||
|
# Python
|
||||||
|
__pycache__/
|
||||||
|
*.py[cod]
|
||||||
|
*$py.class
|
||||||
|
*.so
|
||||||
|
.Python
|
||||||
|
env/
|
||||||
|
venv/
|
||||||
|
*.egg-info/
|
||||||
|
dist/
|
||||||
|
build/
|
||||||
|
|
||||||
|
# IDE
|
||||||
|
.vscode/
|
||||||
|
.idea/
|
||||||
|
*.swp
|
||||||
|
*.swo
|
||||||
|
*~
|
||||||
|
|
||||||
|
# Data files (generated at runtime)
|
||||||
|
data/tournament_state.json
|
||||||
|
data/tournament_results.json
|
||||||
|
data/league_state.json
|
||||||
|
data/players.json
|
||||||
|
|
||||||
|
# Archives (user-generated)
|
||||||
|
data/tournament_archives/
|
||||||
|
data/league_archives/
|
||||||
|
|
||||||
|
# Environment
|
||||||
|
.env
|
||||||
|
.env.local
|
||||||
|
|
||||||
|
# OS
|
||||||
|
.DS_Store
|
||||||
|
Thumbs.db
|
||||||
|
|
||||||
|
# Temporary launcher scripts
|
||||||
|
_run_server.py
|
||||||
|
app_runner.py
|
||||||
@@ -0,0 +1,93 @@
|
|||||||
|
# TV_APP V1.0.0 - Tournament Management System
|
||||||
|
|
||||||
|
A Flask-based web application for managing tournaments with multi-camera streaming support.
|
||||||
|
|
||||||
|
## Quick Start
|
||||||
|
|
||||||
|
### Prerequisites
|
||||||
|
- Python 3.7+
|
||||||
|
|
||||||
|
### Installation & Run
|
||||||
|
|
||||||
|
```bash
|
||||||
|
# Create virtual environment
|
||||||
|
python3 -m venv venv
|
||||||
|
|
||||||
|
# Activate venv
|
||||||
|
source venv/bin/activate # Linux/Mac
|
||||||
|
# or
|
||||||
|
venv\Scripts\activate # Windows
|
||||||
|
|
||||||
|
# Install dependencies
|
||||||
|
pip install -r requirements.txt
|
||||||
|
|
||||||
|
# Run the app
|
||||||
|
python3 tv_app.py
|
||||||
|
```
|
||||||
|
|
||||||
|
The app will be available at: **http://localhost:5000**
|
||||||
|
|
||||||
|
## Project Structure
|
||||||
|
|
||||||
|
```
|
||||||
|
TV_APP_V1.0.0/
|
||||||
|
├── tv_app.py # Main Flask application (2,364 lines)
|
||||||
|
├── requirements.txt # Python dependencies
|
||||||
|
├── README.md # This file
|
||||||
|
│
|
||||||
|
├── app/ # Support modules
|
||||||
|
│ ├── __init__.py
|
||||||
|
│ ├── config.py # Configuration
|
||||||
|
│ ├── models.py # Data models
|
||||||
|
│ ├── storage.py # Persistent storage
|
||||||
|
│ └── utils.py # Utilities
|
||||||
|
│
|
||||||
|
├── templates/ # HTML templates
|
||||||
|
├── static/ # CSS, JS, images
|
||||||
|
├── data/ # Runtime data (JSON state)
|
||||||
|
└── locales/ # Translations (EN, SL)
|
||||||
|
```
|
||||||
|
|
||||||
|
## Features
|
||||||
|
|
||||||
|
✅ Tournament management with live scoring
|
||||||
|
✅ Multi-camera streaming integration
|
||||||
|
✅ Mobile interface for remote access
|
||||||
|
✅ Tournament archiving & history
|
||||||
|
✅ League management
|
||||||
|
✅ Multi-language support (English & Slovenian)
|
||||||
|
✅ JSON-based persistent storage
|
||||||
|
|
||||||
|
## Key URLs
|
||||||
|
|
||||||
|
- **Main Dashboard**: http://localhost:5000/
|
||||||
|
- **Mobile Interface**: http://localhost:5000/mobile
|
||||||
|
- **Archive**: http://localhost:5000/archive
|
||||||
|
- **Tournament View**: http://localhost:5000/tournament
|
||||||
|
- **Results**: http://localhost:5000/results
|
||||||
|
|
||||||
|
## Dependencies
|
||||||
|
|
||||||
|
- Flask 3.0.0
|
||||||
|
- Flask-SocketIO 5.3.4
|
||||||
|
- python-socketio 5.9.0
|
||||||
|
- python-engineio 4.7.1
|
||||||
|
- python-dotenv 1.0.0
|
||||||
|
|
||||||
|
## Development
|
||||||
|
|
||||||
|
The app structure is simple and maintainable:
|
||||||
|
- All Flask routes in `tv_app.py`
|
||||||
|
- Support modules in `app/` package
|
||||||
|
- Ready to split into blueprints if needed
|
||||||
|
|
||||||
|
## Notes
|
||||||
|
|
||||||
|
- Real-time WebSocket synchronization is disabled (not working reliably)
|
||||||
|
- Each instance operates independently
|
||||||
|
- All data is saved to JSON files in `data/` folder
|
||||||
|
- Fully functional and production-ready
|
||||||
|
|
||||||
|
## How to Stop
|
||||||
|
|
||||||
|
Press `Ctrl+C` in the terminal where the app is running.
|
||||||
Binary file not shown.
@@ -0,0 +1,6 @@
|
|||||||
|
"""
|
||||||
|
TV_APP V1.0.0 - App Package
|
||||||
|
|
||||||
|
This package contains support modules for the main Flask application.
|
||||||
|
All routes are in tv_app.py in the project root.
|
||||||
|
"""
|
||||||
@@ -0,0 +1,13 @@
|
|||||||
|
"""
|
||||||
|
Configuration for TV_APP V1.0.0
|
||||||
|
"""
|
||||||
|
|
||||||
|
import os
|
||||||
|
|
||||||
|
|
||||||
|
class Config:
|
||||||
|
"""Base configuration class"""
|
||||||
|
SECRET_KEY = os.getenv('SECRET_KEY', 'your-secret-key-for-sessions')
|
||||||
|
DEBUG = os.getenv('DEBUG', 'False').lower() == 'true'
|
||||||
|
HOST = os.getenv('HOST', '0.0.0.0')
|
||||||
|
PORT = int(os.getenv('PORT', 5000))
|
||||||
+280
@@ -0,0 +1,280 @@
|
|||||||
|
"""
|
||||||
|
Data models and business logic for TV_APP
|
||||||
|
Handles all calculations and data structure creation
|
||||||
|
"""
|
||||||
|
|
||||||
|
from datetime import datetime
|
||||||
|
import random
|
||||||
|
|
||||||
|
NUM_CAMERAS = 6
|
||||||
|
|
||||||
|
|
||||||
|
class Tournament:
|
||||||
|
"""Tournament creation and management"""
|
||||||
|
|
||||||
|
@staticmethod
|
||||||
|
def create_league(enabled_players, tournament_type):
|
||||||
|
"""Create a new league with 5 tournaments"""
|
||||||
|
league_id = f"league_{datetime.now().strftime('%Y%m%d_%H%M%S')}"
|
||||||
|
|
||||||
|
league_data = {
|
||||||
|
'league_id': league_id,
|
||||||
|
'created_at': datetime.now().isoformat(),
|
||||||
|
'tournament_type': tournament_type,
|
||||||
|
'total_tournaments': 5,
|
||||||
|
'current_tournament': 0,
|
||||||
|
'participants': {},
|
||||||
|
'completed_tournaments': [],
|
||||||
|
'league_finished': False
|
||||||
|
}
|
||||||
|
|
||||||
|
# Initialize participants
|
||||||
|
for player in enabled_players:
|
||||||
|
league_data['participants'][str(player['id'])] = {
|
||||||
|
'name': player['name'],
|
||||||
|
'joker_used': False,
|
||||||
|
'tournament_results': [],
|
||||||
|
'total_score': 0,
|
||||||
|
'final_score': 0,
|
||||||
|
'tournaments_participated': 0
|
||||||
|
}
|
||||||
|
|
||||||
|
return league_data
|
||||||
|
|
||||||
|
@staticmethod
|
||||||
|
def create_draft(enabled_players, tournament_type='20_targets', league_tournament_number=None):
|
||||||
|
"""Create draft groups of 6 players and organize rounds"""
|
||||||
|
if len(enabled_players) < 1:
|
||||||
|
return None
|
||||||
|
|
||||||
|
# Shuffle players for random grouping
|
||||||
|
players_copy = enabled_players.copy()
|
||||||
|
random.shuffle(players_copy)
|
||||||
|
|
||||||
|
# Create groups of up to 6
|
||||||
|
groups = []
|
||||||
|
for i in range(0, len(players_copy), NUM_CAMERAS):
|
||||||
|
group = players_copy[i:i + NUM_CAMERAS]
|
||||||
|
groups.append(group)
|
||||||
|
|
||||||
|
# Create rounds
|
||||||
|
rounds = []
|
||||||
|
for i, group in enumerate(groups):
|
||||||
|
rounds.append({
|
||||||
|
'round_number': i + 1,
|
||||||
|
'players': group,
|
||||||
|
'status': 'pending' if i == 0 else 'waiting'
|
||||||
|
})
|
||||||
|
|
||||||
|
tournament_data = {
|
||||||
|
'rounds': rounds,
|
||||||
|
'created_at': datetime.now().isoformat(),
|
||||||
|
'total_players': len(enabled_players),
|
||||||
|
'total_rounds': len(rounds),
|
||||||
|
'current_round': 1,
|
||||||
|
'tournament_type': tournament_type
|
||||||
|
}
|
||||||
|
|
||||||
|
if league_tournament_number:
|
||||||
|
tournament_data['league_tournament_number'] = league_tournament_number
|
||||||
|
|
||||||
|
return tournament_data
|
||||||
|
|
||||||
|
@staticmethod
|
||||||
|
def create_results_structure(tournament_data):
|
||||||
|
"""Create results structure for a tournament"""
|
||||||
|
if not tournament_data:
|
||||||
|
return None
|
||||||
|
|
||||||
|
tournament_type = tournament_data.get('tournament_type', '20_targets')
|
||||||
|
|
||||||
|
# Determine target count and shots per target
|
||||||
|
if tournament_type == '40_targets':
|
||||||
|
num_targets = 40
|
||||||
|
shots_per_target = 2
|
||||||
|
elif tournament_type == '4_targets':
|
||||||
|
num_targets = 4
|
||||||
|
shots_per_target = 5
|
||||||
|
else: # 20_targets (default)
|
||||||
|
num_targets = 20
|
||||||
|
shots_per_target = 2
|
||||||
|
|
||||||
|
results = {
|
||||||
|
'tournament_id': tournament_data.get('created_at', datetime.now().isoformat()),
|
||||||
|
'tournament_type': tournament_type,
|
||||||
|
'participants': {},
|
||||||
|
'tournament_finished': False,
|
||||||
|
'created_at': datetime.now().isoformat()
|
||||||
|
}
|
||||||
|
|
||||||
|
# Add league info if present
|
||||||
|
if 'league_tournament_number' in tournament_data:
|
||||||
|
results['league_tournament_number'] = tournament_data['league_tournament_number']
|
||||||
|
|
||||||
|
# Create structure for each participant
|
||||||
|
all_players = []
|
||||||
|
for round_data in tournament_data['rounds']:
|
||||||
|
all_players.extend(round_data['players'])
|
||||||
|
|
||||||
|
for player in all_players:
|
||||||
|
player_id = str(player['id'])
|
||||||
|
|
||||||
|
# Create target structure based on tournament type
|
||||||
|
targets = {}
|
||||||
|
for i in range(1, num_targets + 1):
|
||||||
|
target = {}
|
||||||
|
for j in range(1, shots_per_target + 1):
|
||||||
|
target[f'shot{j}'] = None
|
||||||
|
targets[str(i)] = target
|
||||||
|
|
||||||
|
results['participants'][player_id] = {
|
||||||
|
'name': player['name'],
|
||||||
|
'targets': targets,
|
||||||
|
'total_score': 0,
|
||||||
|
'completed': False
|
||||||
|
}
|
||||||
|
|
||||||
|
return results
|
||||||
|
|
||||||
|
|
||||||
|
class Scoring:
|
||||||
|
"""Score calculation and ranking"""
|
||||||
|
|
||||||
|
@staticmethod
|
||||||
|
def calculate_total_score(targets):
|
||||||
|
"""Calculate total score from targets, treating None as 0"""
|
||||||
|
total = 0
|
||||||
|
for target in targets.values():
|
||||||
|
for shot_key, shot_value in target.items():
|
||||||
|
if shot_key.startswith('shot') and shot_value is not None:
|
||||||
|
total += shot_value
|
||||||
|
return total
|
||||||
|
|
||||||
|
@staticmethod
|
||||||
|
def is_participant_completed(targets):
|
||||||
|
"""Check if a participant has completed all targets"""
|
||||||
|
for target in targets.values():
|
||||||
|
for shot_key, shot_value in target.items():
|
||||||
|
if shot_key.startswith('shot') and shot_value is None:
|
||||||
|
return False
|
||||||
|
return True
|
||||||
|
|
||||||
|
@staticmethod
|
||||||
|
def calculate_league_final_scores(league_data):
|
||||||
|
"""Calculate final league scores using best 4 tournaments"""
|
||||||
|
for participant_id, participant in league_data['participants'].items():
|
||||||
|
tournament_scores = []
|
||||||
|
|
||||||
|
# Get all tournament scores where player participated
|
||||||
|
for result in participant['tournament_results']:
|
||||||
|
if result['participated']:
|
||||||
|
tournament_scores.append(result['score'])
|
||||||
|
|
||||||
|
# Sort scores descending and take best 4
|
||||||
|
tournament_scores.sort(reverse=True)
|
||||||
|
best_scores = tournament_scores[:4] if len(tournament_scores) > 4 else tournament_scores
|
||||||
|
|
||||||
|
participant['final_score'] = sum(best_scores)
|
||||||
|
participant['tournaments_participated'] = len(tournament_scores)
|
||||||
|
|
||||||
|
@staticmethod
|
||||||
|
def get_league_final_rankings(league_data):
|
||||||
|
"""Get final league rankings sorted by final score"""
|
||||||
|
participants = []
|
||||||
|
for player_id, data in league_data['participants'].items():
|
||||||
|
# Calculate total 10s across all tournaments
|
||||||
|
total_tens = sum(
|
||||||
|
result.get('tens_count', 0) for result in data['tournament_results']
|
||||||
|
if result.get('participated', False)
|
||||||
|
)
|
||||||
|
|
||||||
|
participants.append({
|
||||||
|
'id': player_id,
|
||||||
|
'name': data['name'],
|
||||||
|
'final_score': data['final_score'],
|
||||||
|
'total_score': data['total_score'],
|
||||||
|
'tournaments_participated': data['tournaments_participated'],
|
||||||
|
'joker_used': data['joker_used'],
|
||||||
|
'tournament_results': data['tournament_results'],
|
||||||
|
'total_tens': total_tens
|
||||||
|
})
|
||||||
|
|
||||||
|
# Sort by final score (best 4 tournaments) descending, then by total 10s
|
||||||
|
participants.sort(key=lambda x: (x['final_score'], x['total_tens']), reverse=True)
|
||||||
|
|
||||||
|
# Add rankings
|
||||||
|
for i, participant in enumerate(participants):
|
||||||
|
participant['rank'] = i + 1
|
||||||
|
|
||||||
|
return participants
|
||||||
|
|
||||||
|
@staticmethod
|
||||||
|
def calculate_current_league_standings(league_data):
|
||||||
|
"""Calculate current league standings during active league"""
|
||||||
|
participants = []
|
||||||
|
for player_id, data in league_data['participants'].items():
|
||||||
|
tournament_scores = []
|
||||||
|
completed_tournaments = 0
|
||||||
|
total_tens = 0
|
||||||
|
|
||||||
|
for result in data['tournament_results']:
|
||||||
|
if result['participated']:
|
||||||
|
tournament_scores.append(result['score'])
|
||||||
|
completed_tournaments += 1
|
||||||
|
total_tens += result.get('tens_count', 0)
|
||||||
|
|
||||||
|
# Current score is sum of all completed tournaments
|
||||||
|
current_total = sum(tournament_scores)
|
||||||
|
|
||||||
|
# For display, show what the final score would be if we took best 4 now
|
||||||
|
tournament_scores.sort(reverse=True)
|
||||||
|
projected_final = sum(tournament_scores[:4]) if len(tournament_scores) >= 4 else sum(tournament_scores)
|
||||||
|
|
||||||
|
participants.append({
|
||||||
|
'id': player_id,
|
||||||
|
'name': data['name'],
|
||||||
|
'current_total': current_total,
|
||||||
|
'projected_final': projected_final,
|
||||||
|
'tournaments_completed': completed_tournaments,
|
||||||
|
'joker_used': data['joker_used'],
|
||||||
|
'tournament_results': data['tournament_results'],
|
||||||
|
'total_tens': total_tens
|
||||||
|
})
|
||||||
|
|
||||||
|
# Sort by current total score (descending), then by total 10s
|
||||||
|
participants.sort(key=lambda x: (x['current_total'], x['total_tens']), reverse=True)
|
||||||
|
|
||||||
|
# Add rankings
|
||||||
|
for i, participant in enumerate(participants):
|
||||||
|
participant['rank'] = i + 1
|
||||||
|
|
||||||
|
return participants
|
||||||
|
|
||||||
|
|
||||||
|
class RoundManager:
|
||||||
|
"""Tournament round management"""
|
||||||
|
|
||||||
|
@staticmethod
|
||||||
|
def get_current_round_data(tournament_state):
|
||||||
|
"""Get current round data from tournament"""
|
||||||
|
if not tournament_state:
|
||||||
|
return None
|
||||||
|
|
||||||
|
current_round_num = tournament_state.get('current_round', 1)
|
||||||
|
|
||||||
|
# Find the current round
|
||||||
|
for round_data in tournament_state['rounds']:
|
||||||
|
if round_data['round_number'] == current_round_num:
|
||||||
|
return round_data
|
||||||
|
|
||||||
|
return None
|
||||||
|
|
||||||
|
@staticmethod
|
||||||
|
def get_tournament_format_description(tournament_type):
|
||||||
|
"""Get tournament format description"""
|
||||||
|
formats = {
|
||||||
|
'20_targets': '20 Targets, 2 Shots Per Target',
|
||||||
|
'40_targets': '40 Targets, 2 Shots Per Target',
|
||||||
|
'4_targets': '4 Targets, 5 Shots Per Target'
|
||||||
|
}
|
||||||
|
return formats.get(tournament_type, 'Unknown Format')
|
||||||
+312
@@ -0,0 +1,312 @@
|
|||||||
|
"""
|
||||||
|
File I/O and data persistence for TV_APP
|
||||||
|
Handles all JSON file operations and data archiving
|
||||||
|
"""
|
||||||
|
|
||||||
|
import json
|
||||||
|
import os
|
||||||
|
import glob
|
||||||
|
from datetime import datetime
|
||||||
|
|
||||||
|
# File paths - organized in data directory
|
||||||
|
SETTINGS_FILE = 'data/camera_settings.json'
|
||||||
|
PLAYERS_FILE = 'data/players.json'
|
||||||
|
TOURNAMENT_FILE = 'data/tournament_state.json'
|
||||||
|
RESULTS_FILE = 'data/tournament_results.json'
|
||||||
|
LEAGUE_FILE = 'data/league_state.json'
|
||||||
|
ARCHIVE_DIR = 'data/tournament_archives'
|
||||||
|
LEAGUE_ARCHIVE_DIR = 'data/league_archives'
|
||||||
|
|
||||||
|
# Default settings
|
||||||
|
DEFAULT_SETTINGS = {
|
||||||
|
'camera_titles': {
|
||||||
|
'1': 'Camera 1',
|
||||||
|
'2': 'Camera 2',
|
||||||
|
'3': 'Camera 3',
|
||||||
|
'4': 'Camera 4',
|
||||||
|
'5': 'Camera 5',
|
||||||
|
'6': 'Camera 6'
|
||||||
|
},
|
||||||
|
'display_options': {
|
||||||
|
'show_titles': True,
|
||||||
|
'title_size': 1.1
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
class FileStorage:
|
||||||
|
"""Handle JSON file read/write operations"""
|
||||||
|
|
||||||
|
@staticmethod
|
||||||
|
def _ensure_directory(directory):
|
||||||
|
"""Ensure directory exists"""
|
||||||
|
if not os.path.exists(directory):
|
||||||
|
os.makedirs(directory)
|
||||||
|
|
||||||
|
@staticmethod
|
||||||
|
def _read_json(filepath):
|
||||||
|
"""Read JSON file safely"""
|
||||||
|
try:
|
||||||
|
if os.path.exists(filepath):
|
||||||
|
with open(filepath, 'r', encoding='utf-8') as f:
|
||||||
|
return json.load(f)
|
||||||
|
except (json.JSONDecodeError, IOError) as e:
|
||||||
|
print(f"Error reading {filepath}: {e}")
|
||||||
|
return None
|
||||||
|
|
||||||
|
@staticmethod
|
||||||
|
def _write_json(filepath, data):
|
||||||
|
"""Write JSON file safely"""
|
||||||
|
try:
|
||||||
|
directory = os.path.dirname(filepath)
|
||||||
|
FileStorage._ensure_directory(directory)
|
||||||
|
|
||||||
|
with open(filepath, 'w', encoding='utf-8') as f:
|
||||||
|
json.dump(data, f, indent=2, ensure_ascii=False)
|
||||||
|
return True
|
||||||
|
except IOError as e:
|
||||||
|
print(f"Error writing {filepath}: {e}")
|
||||||
|
return False
|
||||||
|
|
||||||
|
|
||||||
|
class SettingsStorage(FileStorage):
|
||||||
|
"""Manage camera and display settings"""
|
||||||
|
|
||||||
|
@staticmethod
|
||||||
|
def load_settings():
|
||||||
|
"""Load settings from JSON file, create with defaults if not exists"""
|
||||||
|
settings = FileStorage._read_json(SETTINGS_FILE)
|
||||||
|
|
||||||
|
if settings is None:
|
||||||
|
return DEFAULT_SETTINGS.copy()
|
||||||
|
|
||||||
|
# Ensure all required keys exist (backwards compatibility)
|
||||||
|
for key in DEFAULT_SETTINGS:
|
||||||
|
if key not in settings:
|
||||||
|
settings[key] = DEFAULT_SETTINGS[key]
|
||||||
|
|
||||||
|
for camera_id in DEFAULT_SETTINGS['camera_titles']:
|
||||||
|
if camera_id not in settings.get('camera_titles', {}):
|
||||||
|
settings['camera_titles'][camera_id] = DEFAULT_SETTINGS['camera_titles'][camera_id]
|
||||||
|
|
||||||
|
return settings
|
||||||
|
|
||||||
|
@staticmethod
|
||||||
|
def save_settings(settings):
|
||||||
|
"""Save settings to JSON file"""
|
||||||
|
return FileStorage._write_json(SETTINGS_FILE, settings)
|
||||||
|
|
||||||
|
|
||||||
|
class PlayerStorage(FileStorage):
|
||||||
|
"""Manage player data"""
|
||||||
|
|
||||||
|
DEFAULT_PLAYERS = {
|
||||||
|
'players': [
|
||||||
|
{'id': i, 'name': f'Player {i}', 'enabled': True}
|
||||||
|
for i in range(1, 7) # 6 cameras
|
||||||
|
]
|
||||||
|
}
|
||||||
|
|
||||||
|
@staticmethod
|
||||||
|
def load_players():
|
||||||
|
"""Load players from JSON file, create with defaults if not exists"""
|
||||||
|
players = FileStorage._read_json(PLAYERS_FILE)
|
||||||
|
|
||||||
|
if players is None:
|
||||||
|
PlayerStorage.save_players(PlayerStorage.DEFAULT_PLAYERS)
|
||||||
|
return PlayerStorage.DEFAULT_PLAYERS.copy()
|
||||||
|
|
||||||
|
return players
|
||||||
|
|
||||||
|
@staticmethod
|
||||||
|
def save_players(players_data):
|
||||||
|
"""Save players to JSON file"""
|
||||||
|
return FileStorage._write_json(PLAYERS_FILE, players_data)
|
||||||
|
|
||||||
|
|
||||||
|
class TournamentStorage(FileStorage):
|
||||||
|
"""Manage tournament state"""
|
||||||
|
|
||||||
|
@staticmethod
|
||||||
|
def load_tournament_state():
|
||||||
|
"""Load tournament state from JSON file"""
|
||||||
|
return FileStorage._read_json(TOURNAMENT_FILE)
|
||||||
|
|
||||||
|
@staticmethod
|
||||||
|
def save_tournament_state(tournament_data):
|
||||||
|
"""Save tournament state to JSON file"""
|
||||||
|
return FileStorage._write_json(TOURNAMENT_FILE, tournament_data)
|
||||||
|
|
||||||
|
|
||||||
|
class ResultsStorage(FileStorage):
|
||||||
|
"""Manage tournament results"""
|
||||||
|
|
||||||
|
@staticmethod
|
||||||
|
def load_results():
|
||||||
|
"""Load results from JSON file"""
|
||||||
|
return FileStorage._read_json(RESULTS_FILE)
|
||||||
|
|
||||||
|
@staticmethod
|
||||||
|
def save_results(results_data):
|
||||||
|
"""Save results to JSON file"""
|
||||||
|
return FileStorage._write_json(RESULTS_FILE, results_data)
|
||||||
|
|
||||||
|
|
||||||
|
class LeagueStorage(FileStorage):
|
||||||
|
"""Manage league state"""
|
||||||
|
|
||||||
|
@staticmethod
|
||||||
|
def load_league_state():
|
||||||
|
"""Load league state from JSON file"""
|
||||||
|
return FileStorage._read_json(LEAGUE_FILE)
|
||||||
|
|
||||||
|
@staticmethod
|
||||||
|
def save_league_state(league_data):
|
||||||
|
"""Save league state to JSON file"""
|
||||||
|
return FileStorage._write_json(LEAGUE_FILE, league_data)
|
||||||
|
|
||||||
|
|
||||||
|
class ArchiveStorage(FileStorage):
|
||||||
|
"""Manage tournament and league archives"""
|
||||||
|
|
||||||
|
@staticmethod
|
||||||
|
def archive_tournament(tournament_data, results_data):
|
||||||
|
"""Archive completed tournament data"""
|
||||||
|
try:
|
||||||
|
FileStorage._ensure_directory(ARCHIVE_DIR)
|
||||||
|
|
||||||
|
timestamp = datetime.now().strftime("%Y%m%d_%H%M%S")
|
||||||
|
archive_filename = f"tournament_{timestamp}.json"
|
||||||
|
archive_path = os.path.join(ARCHIVE_DIR, archive_filename)
|
||||||
|
|
||||||
|
archive_data = {
|
||||||
|
'tournament': tournament_data,
|
||||||
|
'results': results_data,
|
||||||
|
'archived_at': datetime.now().isoformat()
|
||||||
|
}
|
||||||
|
|
||||||
|
success = FileStorage._write_json(archive_path, archive_data)
|
||||||
|
if success:
|
||||||
|
print(f"Tournament archived to: {archive_path}")
|
||||||
|
return success
|
||||||
|
except Exception as e:
|
||||||
|
print(f"Error archiving tournament: {e}")
|
||||||
|
return False
|
||||||
|
|
||||||
|
@staticmethod
|
||||||
|
def archive_league(league_data):
|
||||||
|
"""Archive completed league data"""
|
||||||
|
try:
|
||||||
|
FileStorage._ensure_directory(LEAGUE_ARCHIVE_DIR)
|
||||||
|
|
||||||
|
timestamp = datetime.now().strftime("%Y%m%d_%H%M%S")
|
||||||
|
archive_filename = f"league_{timestamp}.json"
|
||||||
|
archive_path = os.path.join(LEAGUE_ARCHIVE_DIR, archive_filename)
|
||||||
|
|
||||||
|
archive_data = {
|
||||||
|
'league': league_data,
|
||||||
|
'archived_at': datetime.now().isoformat()
|
||||||
|
}
|
||||||
|
|
||||||
|
success = FileStorage._write_json(archive_path, archive_data)
|
||||||
|
if success:
|
||||||
|
print(f"League archived to: {archive_path}")
|
||||||
|
return success
|
||||||
|
except Exception as e:
|
||||||
|
print(f"Error archiving league: {e}")
|
||||||
|
return False
|
||||||
|
|
||||||
|
@staticmethod
|
||||||
|
def get_archived_tournaments():
|
||||||
|
"""Get list of standalone archived tournaments"""
|
||||||
|
try:
|
||||||
|
if not os.path.exists(ARCHIVE_DIR):
|
||||||
|
return []
|
||||||
|
|
||||||
|
archives = []
|
||||||
|
for file_path in glob.glob(os.path.join(ARCHIVE_DIR, "tournament_*.json")):
|
||||||
|
try:
|
||||||
|
data = FileStorage._read_json(file_path)
|
||||||
|
if not data:
|
||||||
|
continue
|
||||||
|
|
||||||
|
filename = os.path.basename(file_path)
|
||||||
|
archived_at = data.get('archived_at', 'Unknown')
|
||||||
|
tournament_data = data.get('tournament', {})
|
||||||
|
results_data = data.get('results', {})
|
||||||
|
|
||||||
|
# Skip tournaments that are part of a league
|
||||||
|
if tournament_data.get('league_tournament_number') or results_data.get('league_tournament_number'):
|
||||||
|
continue
|
||||||
|
|
||||||
|
archive_info = {
|
||||||
|
'filename': filename,
|
||||||
|
'filepath': file_path,
|
||||||
|
'archived_at': archived_at,
|
||||||
|
'created_at': tournament_data.get('created_at', 'Unknown'),
|
||||||
|
'tournament_type': tournament_data.get('tournament_type', '20_targets'),
|
||||||
|
'total_players': tournament_data.get('total_players', 0),
|
||||||
|
'total_rounds': tournament_data.get('total_rounds', 0),
|
||||||
|
'tournament_finished': results_data.get('tournament_finished', False),
|
||||||
|
'participants_count': len(results_data.get('participants', {}))
|
||||||
|
}
|
||||||
|
|
||||||
|
archives.append(archive_info)
|
||||||
|
except (json.JSONDecodeError, IOError) as e:
|
||||||
|
print(f"Error reading archive {file_path}: {e}")
|
||||||
|
continue
|
||||||
|
|
||||||
|
# Sort by archived date (newest first)
|
||||||
|
archives.sort(key=lambda x: x['archived_at'], reverse=True)
|
||||||
|
return archives
|
||||||
|
except Exception as e:
|
||||||
|
print(f"Error getting archived tournaments: {e}")
|
||||||
|
return []
|
||||||
|
|
||||||
|
@staticmethod
|
||||||
|
def get_archived_leagues():
|
||||||
|
"""Get list of all archived leagues"""
|
||||||
|
try:
|
||||||
|
if not os.path.exists(LEAGUE_ARCHIVE_DIR):
|
||||||
|
return []
|
||||||
|
|
||||||
|
archives = []
|
||||||
|
for file_path in glob.glob(os.path.join(LEAGUE_ARCHIVE_DIR, "league_*.json")):
|
||||||
|
try:
|
||||||
|
data = FileStorage._read_json(file_path)
|
||||||
|
if not data:
|
||||||
|
continue
|
||||||
|
|
||||||
|
filename = os.path.basename(file_path)
|
||||||
|
archived_at = data.get('archived_at', 'Unknown')
|
||||||
|
league_data = data.get('league', {})
|
||||||
|
|
||||||
|
archive_info = {
|
||||||
|
'filename': filename,
|
||||||
|
'filepath': file_path,
|
||||||
|
'archived_at': archived_at,
|
||||||
|
'created_at': league_data.get('created_at', 'Unknown'),
|
||||||
|
'league_id': league_data.get('league_id', 'Unknown'),
|
||||||
|
'tournament_type': league_data.get('tournament_type', '20_targets'),
|
||||||
|
'total_tournaments': league_data.get('total_tournaments', 5),
|
||||||
|
'participants_count': len(league_data.get('participants', {})),
|
||||||
|
'league_finished': league_data.get('league_finished', False),
|
||||||
|
'completed_tournaments': len(league_data.get('completed_tournaments', []))
|
||||||
|
}
|
||||||
|
|
||||||
|
archives.append(archive_info)
|
||||||
|
except (json.JSONDecodeError, IOError) as e:
|
||||||
|
print(f"Error reading league archive {file_path}: {e}")
|
||||||
|
continue
|
||||||
|
|
||||||
|
# Sort by archived date (newest first)
|
||||||
|
archives.sort(key=lambda x: x['archived_at'], reverse=True)
|
||||||
|
return archives
|
||||||
|
except Exception as e:
|
||||||
|
print(f"Error getting archived leagues: {e}")
|
||||||
|
return []
|
||||||
|
|
||||||
|
@staticmethod
|
||||||
|
def load_archive_file(filepath):
|
||||||
|
"""Load a specific archive file"""
|
||||||
|
return FileStorage._read_json(filepath)
|
||||||
@@ -0,0 +1,78 @@
|
|||||||
|
"""
|
||||||
|
Utility functions for TV_APP
|
||||||
|
Helper functions for translations, device detection, and common calculations
|
||||||
|
"""
|
||||||
|
|
||||||
|
import json
|
||||||
|
import os
|
||||||
|
import re
|
||||||
|
from flask import request, session
|
||||||
|
|
||||||
|
DEFAULT_LANGUAGE = 'sl'
|
||||||
|
|
||||||
|
|
||||||
|
def load_translations(language='sl'):
|
||||||
|
"""Load translations for the specified language"""
|
||||||
|
try:
|
||||||
|
locale_file = os.path.join('locales', f'{language}.json')
|
||||||
|
if os.path.exists(locale_file):
|
||||||
|
with open(locale_file, 'r', encoding='utf-8') as f:
|
||||||
|
return json.load(f)
|
||||||
|
except Exception as e:
|
||||||
|
print(f"Error loading translations for {language}: {e}")
|
||||||
|
|
||||||
|
# Fallback to default language
|
||||||
|
try:
|
||||||
|
default_file = os.path.join('locales', f'{DEFAULT_LANGUAGE}.json')
|
||||||
|
with open(default_file, 'r', encoding='utf-8') as f:
|
||||||
|
return json.load(f)
|
||||||
|
except Exception as e:
|
||||||
|
print(f"Error loading default translations: {e}")
|
||||||
|
return {}
|
||||||
|
|
||||||
|
|
||||||
|
def get_current_language():
|
||||||
|
"""Get current language from session or default"""
|
||||||
|
return session.get('language', DEFAULT_LANGUAGE)
|
||||||
|
|
||||||
|
|
||||||
|
def get_translations():
|
||||||
|
"""Get translations for current language"""
|
||||||
|
return load_translations(get_current_language())
|
||||||
|
|
||||||
|
|
||||||
|
def is_mobile_device():
|
||||||
|
"""Check if the request is coming from a mobile device"""
|
||||||
|
user_agent = request.headers.get('User-Agent', '').lower()
|
||||||
|
mobile_patterns = [
|
||||||
|
r'android', r'iphone', r'ipad', r'ipod', r'blackberry',
|
||||||
|
r'iemobile', r'opera mini', r'mobile', r'tablet'
|
||||||
|
]
|
||||||
|
return any(re.search(pattern, user_agent) for pattern in mobile_patterns)
|
||||||
|
|
||||||
|
|
||||||
|
def calculate_tens_from_targets(targets):
|
||||||
|
"""Calculate the number of 10s from a targets dictionary"""
|
||||||
|
tens_count = 0
|
||||||
|
if not targets:
|
||||||
|
return 0
|
||||||
|
|
||||||
|
for target in targets.values():
|
||||||
|
if isinstance(target, dict):
|
||||||
|
for shot_key, shot_value in target.items():
|
||||||
|
if shot_key.startswith('shot') and shot_value == 10:
|
||||||
|
tens_count += 1
|
||||||
|
|
||||||
|
return tens_count
|
||||||
|
|
||||||
|
|
||||||
|
def validate_player_data(player_data):
|
||||||
|
"""Validate player data structure"""
|
||||||
|
required_fields = ['id', 'name', 'enabled']
|
||||||
|
return all(field in player_data for field in required_fields)
|
||||||
|
|
||||||
|
|
||||||
|
def validate_settings(settings):
|
||||||
|
"""Validate settings structure"""
|
||||||
|
required_sections = ['camera_titles', 'display_options']
|
||||||
|
return all(section in settings for section in required_sections)
|
||||||
File diff suppressed because it is too large
Load Diff
@@ -1,406 +0,0 @@
|
|||||||
{
|
|
||||||
"league": {
|
|
||||||
"league_id": "league_20251031_184134",
|
|
||||||
"created_at": "2025-10-31T18:41:34.562185",
|
|
||||||
"tournament_type": "4_targets",
|
|
||||||
"total_tournaments": 5,
|
|
||||||
"current_tournament": 0,
|
|
||||||
"participants": {
|
|
||||||
"1": {
|
|
||||||
"name": "Domen Pleterski",
|
|
||||||
"joker_used": false,
|
|
||||||
"tournament_results": [],
|
|
||||||
"total_score": 0,
|
|
||||||
"final_score": 0,
|
|
||||||
"tournaments_participated": 0
|
|
||||||
},
|
|
||||||
"2": {
|
|
||||||
"name": "Nik Pleterski",
|
|
||||||
"joker_used": false,
|
|
||||||
"tournament_results": [],
|
|
||||||
"total_score": 0,
|
|
||||||
"final_score": 0,
|
|
||||||
"tournaments_participated": 0
|
|
||||||
},
|
|
||||||
"3": {
|
|
||||||
"name": "Ivan Tandler",
|
|
||||||
"joker_used": false,
|
|
||||||
"tournament_results": [],
|
|
||||||
"total_score": 0,
|
|
||||||
"final_score": 0,
|
|
||||||
"tournaments_participated": 0
|
|
||||||
},
|
|
||||||
"4": {
|
|
||||||
"name": "Mateja Pleterski",
|
|
||||||
"joker_used": false,
|
|
||||||
"tournament_results": [],
|
|
||||||
"total_score": 0,
|
|
||||||
"final_score": 0,
|
|
||||||
"tournaments_participated": 0
|
|
||||||
},
|
|
||||||
"5": {
|
|
||||||
"name": "Jo\u017ee Verhnjak",
|
|
||||||
"joker_used": false,
|
|
||||||
"tournament_results": [],
|
|
||||||
"total_score": 0,
|
|
||||||
"final_score": 0,
|
|
||||||
"tournaments_participated": 0
|
|
||||||
},
|
|
||||||
"6": {
|
|
||||||
"name": "Mateja Senica",
|
|
||||||
"joker_used": false,
|
|
||||||
"tournament_results": [],
|
|
||||||
"total_score": 0,
|
|
||||||
"final_score": 0,
|
|
||||||
"tournaments_participated": 0
|
|
||||||
},
|
|
||||||
"7": {
|
|
||||||
"name": "Branko Poker\u017enik",
|
|
||||||
"joker_used": false,
|
|
||||||
"tournament_results": [],
|
|
||||||
"total_score": 0,
|
|
||||||
"final_score": 0,
|
|
||||||
"tournaments_participated": 0
|
|
||||||
},
|
|
||||||
"8": {
|
|
||||||
"name": "Franc \u017digart",
|
|
||||||
"joker_used": false,
|
|
||||||
"tournament_results": [],
|
|
||||||
"total_score": 0,
|
|
||||||
"final_score": 0,
|
|
||||||
"tournaments_participated": 0
|
|
||||||
},
|
|
||||||
"9": {
|
|
||||||
"name": "Janez Bo\u017ei\u010d",
|
|
||||||
"joker_used": false,
|
|
||||||
"tournament_results": [],
|
|
||||||
"total_score": 0,
|
|
||||||
"final_score": 0,
|
|
||||||
"tournaments_participated": 0
|
|
||||||
},
|
|
||||||
"10": {
|
|
||||||
"name": "Mitja \u010ceh",
|
|
||||||
"joker_used": false,
|
|
||||||
"tournament_results": [],
|
|
||||||
"total_score": 0,
|
|
||||||
"final_score": 0,
|
|
||||||
"tournaments_participated": 0
|
|
||||||
},
|
|
||||||
"11": {
|
|
||||||
"name": "Rado Kefer",
|
|
||||||
"joker_used": false,
|
|
||||||
"tournament_results": [],
|
|
||||||
"total_score": 0,
|
|
||||||
"final_score": 0,
|
|
||||||
"tournaments_participated": 0
|
|
||||||
},
|
|
||||||
"12": {
|
|
||||||
"name": "Matej Kvasnik",
|
|
||||||
"joker_used": false,
|
|
||||||
"tournament_results": [],
|
|
||||||
"total_score": 0,
|
|
||||||
"final_score": 0,
|
|
||||||
"tournaments_participated": 0
|
|
||||||
},
|
|
||||||
"13": {
|
|
||||||
"name": "Angelca Mrak",
|
|
||||||
"joker_used": false,
|
|
||||||
"tournament_results": [],
|
|
||||||
"total_score": 0,
|
|
||||||
"final_score": 0,
|
|
||||||
"tournaments_participated": 0
|
|
||||||
},
|
|
||||||
"14": {
|
|
||||||
"name": "Karli Proje",
|
|
||||||
"joker_used": false,
|
|
||||||
"tournament_results": [],
|
|
||||||
"total_score": 0,
|
|
||||||
"final_score": 0,
|
|
||||||
"tournaments_participated": 0
|
|
||||||
},
|
|
||||||
"15": {
|
|
||||||
"name": "Jan Pleterski",
|
|
||||||
"joker_used": false,
|
|
||||||
"tournament_results": [],
|
|
||||||
"total_score": 0,
|
|
||||||
"final_score": 0,
|
|
||||||
"tournaments_participated": 0
|
|
||||||
},
|
|
||||||
"16": {
|
|
||||||
"name": "Silvo Poro\u010dnik",
|
|
||||||
"joker_used": false,
|
|
||||||
"tournament_results": [],
|
|
||||||
"total_score": 0,
|
|
||||||
"final_score": 0,
|
|
||||||
"tournaments_participated": 0
|
|
||||||
},
|
|
||||||
"17": {
|
|
||||||
"name": "Du\u0161an Onuk",
|
|
||||||
"joker_used": false,
|
|
||||||
"tournament_results": [],
|
|
||||||
"total_score": 0,
|
|
||||||
"final_score": 0,
|
|
||||||
"tournaments_participated": 0
|
|
||||||
},
|
|
||||||
"18": {
|
|
||||||
"name": "Matja\u017e Pleterski",
|
|
||||||
"joker_used": false,
|
|
||||||
"tournament_results": [],
|
|
||||||
"total_score": 0,
|
|
||||||
"final_score": 0,
|
|
||||||
"tournaments_participated": 0
|
|
||||||
},
|
|
||||||
"19": {
|
|
||||||
"name": "Franc Rizmal",
|
|
||||||
"joker_used": false,
|
|
||||||
"tournament_results": [],
|
|
||||||
"total_score": 0,
|
|
||||||
"final_score": 0,
|
|
||||||
"tournaments_participated": 0
|
|
||||||
},
|
|
||||||
"20": {
|
|
||||||
"name": "Jo\u017ee Preglav",
|
|
||||||
"joker_used": false,
|
|
||||||
"tournament_results": [],
|
|
||||||
"total_score": 0,
|
|
||||||
"final_score": 0,
|
|
||||||
"tournaments_participated": 0
|
|
||||||
},
|
|
||||||
"21": {
|
|
||||||
"name": "Marko Blimen",
|
|
||||||
"joker_used": false,
|
|
||||||
"tournament_results": [],
|
|
||||||
"total_score": 0,
|
|
||||||
"final_score": 0,
|
|
||||||
"tournaments_participated": 0
|
|
||||||
},
|
|
||||||
"22": {
|
|
||||||
"name": "Doris Fesel",
|
|
||||||
"joker_used": false,
|
|
||||||
"tournament_results": [],
|
|
||||||
"total_score": 0,
|
|
||||||
"final_score": 0,
|
|
||||||
"tournaments_participated": 0
|
|
||||||
},
|
|
||||||
"23": {
|
|
||||||
"name": "Robi Krautberger",
|
|
||||||
"joker_used": false,
|
|
||||||
"tournament_results": [],
|
|
||||||
"total_score": 0,
|
|
||||||
"final_score": 0,
|
|
||||||
"tournaments_participated": 0
|
|
||||||
},
|
|
||||||
"24": {
|
|
||||||
"name": "Jo\u017ee Verdinek",
|
|
||||||
"joker_used": false,
|
|
||||||
"tournament_results": [],
|
|
||||||
"total_score": 0,
|
|
||||||
"final_score": 0,
|
|
||||||
"tournaments_participated": 0
|
|
||||||
},
|
|
||||||
"25": {
|
|
||||||
"name": "Andrej Herman",
|
|
||||||
"joker_used": false,
|
|
||||||
"tournament_results": [],
|
|
||||||
"total_score": 0,
|
|
||||||
"final_score": 0,
|
|
||||||
"tournaments_participated": 0
|
|
||||||
},
|
|
||||||
"26": {
|
|
||||||
"name": "Jakob Herman",
|
|
||||||
"joker_used": false,
|
|
||||||
"tournament_results": [],
|
|
||||||
"total_score": 0,
|
|
||||||
"final_score": 0,
|
|
||||||
"tournaments_participated": 0
|
|
||||||
},
|
|
||||||
"27": {
|
|
||||||
"name": "Janez Mrak",
|
|
||||||
"joker_used": false,
|
|
||||||
"tournament_results": [],
|
|
||||||
"total_score": 0,
|
|
||||||
"final_score": 0,
|
|
||||||
"tournaments_participated": 0
|
|
||||||
},
|
|
||||||
"28": {
|
|
||||||
"name": "An\u017ee Kolar",
|
|
||||||
"joker_used": false,
|
|
||||||
"tournament_results": [],
|
|
||||||
"total_score": 0,
|
|
||||||
"final_score": 0,
|
|
||||||
"tournaments_participated": 0
|
|
||||||
},
|
|
||||||
"29": {
|
|
||||||
"name": "Alen Kolar",
|
|
||||||
"joker_used": false,
|
|
||||||
"tournament_results": [],
|
|
||||||
"total_score": 0,
|
|
||||||
"final_score": 0,
|
|
||||||
"tournaments_participated": 0
|
|
||||||
},
|
|
||||||
"30": {
|
|
||||||
"name": "Maja Hirtl",
|
|
||||||
"joker_used": false,
|
|
||||||
"tournament_results": [],
|
|
||||||
"total_score": 0,
|
|
||||||
"final_score": 0,
|
|
||||||
"tournaments_participated": 0
|
|
||||||
},
|
|
||||||
"31": {
|
|
||||||
"name": "Dejan Ku\u010dnik",
|
|
||||||
"joker_used": false,
|
|
||||||
"tournament_results": [],
|
|
||||||
"total_score": 0,
|
|
||||||
"final_score": 0,
|
|
||||||
"tournaments_participated": 0
|
|
||||||
},
|
|
||||||
"32": {
|
|
||||||
"name": "David Strni\u0161a",
|
|
||||||
"joker_used": false,
|
|
||||||
"tournament_results": [],
|
|
||||||
"total_score": 0,
|
|
||||||
"final_score": 0,
|
|
||||||
"tournaments_participated": 0
|
|
||||||
},
|
|
||||||
"33": {
|
|
||||||
"name": "Namir Uzunovi\u0107",
|
|
||||||
"joker_used": false,
|
|
||||||
"tournament_results": [],
|
|
||||||
"total_score": 0,
|
|
||||||
"final_score": 0,
|
|
||||||
"tournaments_participated": 0
|
|
||||||
},
|
|
||||||
"34": {
|
|
||||||
"name": "Jo\u017ee Planin\u0161ec",
|
|
||||||
"joker_used": false,
|
|
||||||
"tournament_results": [],
|
|
||||||
"total_score": 0,
|
|
||||||
"final_score": 0,
|
|
||||||
"tournaments_participated": 0
|
|
||||||
},
|
|
||||||
"35": {
|
|
||||||
"name": "Vanja Kolar",
|
|
||||||
"joker_used": false,
|
|
||||||
"tournament_results": [],
|
|
||||||
"total_score": 0,
|
|
||||||
"final_score": 0,
|
|
||||||
"tournaments_participated": 0
|
|
||||||
},
|
|
||||||
"36": {
|
|
||||||
"name": "Klara Wankmuller",
|
|
||||||
"joker_used": false,
|
|
||||||
"tournament_results": [],
|
|
||||||
"total_score": 0,
|
|
||||||
"final_score": 0,
|
|
||||||
"tournaments_participated": 0
|
|
||||||
},
|
|
||||||
"37": {
|
|
||||||
"name": "Milan Stramec",
|
|
||||||
"joker_used": false,
|
|
||||||
"tournament_results": [],
|
|
||||||
"total_score": 0,
|
|
||||||
"final_score": 0,
|
|
||||||
"tournaments_participated": 0
|
|
||||||
},
|
|
||||||
"38": {
|
|
||||||
"name": "Bojan Sudar",
|
|
||||||
"joker_used": false,
|
|
||||||
"tournament_results": [],
|
|
||||||
"total_score": 0,
|
|
||||||
"final_score": 0,
|
|
||||||
"tournaments_participated": 0
|
|
||||||
},
|
|
||||||
"39": {
|
|
||||||
"name": "Tia Sudar",
|
|
||||||
"joker_used": false,
|
|
||||||
"tournament_results": [],
|
|
||||||
"total_score": 0,
|
|
||||||
"final_score": 0,
|
|
||||||
"tournaments_participated": 0
|
|
||||||
},
|
|
||||||
"40": {
|
|
||||||
"name": "Jaka Cvar",
|
|
||||||
"joker_used": false,
|
|
||||||
"tournament_results": [],
|
|
||||||
"total_score": 0,
|
|
||||||
"final_score": 0,
|
|
||||||
"tournaments_participated": 0
|
|
||||||
},
|
|
||||||
"41": {
|
|
||||||
"name": "Tadej \u0160truc",
|
|
||||||
"joker_used": false,
|
|
||||||
"tournament_results": [],
|
|
||||||
"total_score": 0,
|
|
||||||
"final_score": 0,
|
|
||||||
"tournaments_participated": 0
|
|
||||||
},
|
|
||||||
"42": {
|
|
||||||
"name": "Jure Glaser",
|
|
||||||
"joker_used": false,
|
|
||||||
"tournament_results": [],
|
|
||||||
"total_score": 0,
|
|
||||||
"final_score": 0,
|
|
||||||
"tournaments_participated": 0
|
|
||||||
},
|
|
||||||
"43": {
|
|
||||||
"name": "Marko Pokr\u017enik",
|
|
||||||
"joker_used": false,
|
|
||||||
"tournament_results": [],
|
|
||||||
"total_score": 0,
|
|
||||||
"final_score": 0,
|
|
||||||
"tournaments_participated": 0
|
|
||||||
},
|
|
||||||
"44": {
|
|
||||||
"name": "Anka Ka\u010dnik",
|
|
||||||
"joker_used": false,
|
|
||||||
"tournament_results": [],
|
|
||||||
"total_score": 0,
|
|
||||||
"final_score": 0,
|
|
||||||
"tournaments_participated": 0
|
|
||||||
},
|
|
||||||
"45": {
|
|
||||||
"name": "Lidija Blimen",
|
|
||||||
"joker_used": false,
|
|
||||||
"tournament_results": [],
|
|
||||||
"total_score": 0,
|
|
||||||
"final_score": 0,
|
|
||||||
"tournaments_participated": 0
|
|
||||||
},
|
|
||||||
"46": {
|
|
||||||
"name": "Tijana \u0160tumpfl",
|
|
||||||
"joker_used": false,
|
|
||||||
"tournament_results": [],
|
|
||||||
"total_score": 0,
|
|
||||||
"final_score": 0,
|
|
||||||
"tournaments_participated": 0
|
|
||||||
},
|
|
||||||
"47": {
|
|
||||||
"name": "Ljuba Mr\u0161ak",
|
|
||||||
"joker_used": false,
|
|
||||||
"tournament_results": [],
|
|
||||||
"total_score": 0,
|
|
||||||
"final_score": 0,
|
|
||||||
"tournaments_participated": 0
|
|
||||||
},
|
|
||||||
"48": {
|
|
||||||
"name": "Janja Salcman",
|
|
||||||
"joker_used": false,
|
|
||||||
"tournament_results": [],
|
|
||||||
"total_score": 0,
|
|
||||||
"final_score": 0,
|
|
||||||
"tournaments_participated": 0
|
|
||||||
},
|
|
||||||
"49": {
|
|
||||||
"name": "Jolanda Verhnjak",
|
|
||||||
"joker_used": false,
|
|
||||||
"tournament_results": [],
|
|
||||||
"total_score": 0,
|
|
||||||
"final_score": 0,
|
|
||||||
"tournaments_participated": 0
|
|
||||||
}
|
|
||||||
},
|
|
||||||
"completed_tournaments": [],
|
|
||||||
"league_finished": false
|
|
||||||
},
|
|
||||||
"archived_at": "2025-10-31T18:41:38.976988"
|
|
||||||
}
|
|
||||||
-249
@@ -1,249 +0,0 @@
|
|||||||
{
|
|
||||||
"players": [
|
|
||||||
{
|
|
||||||
"id": 1,
|
|
||||||
"name": "Domen Pleterski",
|
|
||||||
"enabled": true
|
|
||||||
},
|
|
||||||
{
|
|
||||||
"id": 2,
|
|
||||||
"name": "Nik Pleterski",
|
|
||||||
"enabled": true
|
|
||||||
},
|
|
||||||
{
|
|
||||||
"id": 3,
|
|
||||||
"name": "Ivan Tandler",
|
|
||||||
"enabled": true
|
|
||||||
},
|
|
||||||
{
|
|
||||||
"id": 4,
|
|
||||||
"name": "Mateja Pleterski",
|
|
||||||
"enabled": true
|
|
||||||
},
|
|
||||||
{
|
|
||||||
"id": 5,
|
|
||||||
"name": "Jo\u017ee Verhnjak",
|
|
||||||
"enabled": true
|
|
||||||
},
|
|
||||||
{
|
|
||||||
"id": 6,
|
|
||||||
"name": "Mateja Senica",
|
|
||||||
"enabled": true
|
|
||||||
},
|
|
||||||
{
|
|
||||||
"id": 7,
|
|
||||||
"name": "Branko Poker\u017enik",
|
|
||||||
"enabled": true
|
|
||||||
},
|
|
||||||
{
|
|
||||||
"id": 8,
|
|
||||||
"name": "Franc \u017digart",
|
|
||||||
"enabled": true
|
|
||||||
},
|
|
||||||
{
|
|
||||||
"id": 9,
|
|
||||||
"name": "Janez Bo\u017ei\u010d",
|
|
||||||
"enabled": true
|
|
||||||
},
|
|
||||||
{
|
|
||||||
"id": 10,
|
|
||||||
"name": "Mitja \u010ceh",
|
|
||||||
"enabled": true
|
|
||||||
},
|
|
||||||
{
|
|
||||||
"id": 11,
|
|
||||||
"name": "Rado Kefer",
|
|
||||||
"enabled": true
|
|
||||||
},
|
|
||||||
{
|
|
||||||
"id": 12,
|
|
||||||
"name": "Matej Kvasnik",
|
|
||||||
"enabled": true
|
|
||||||
},
|
|
||||||
{
|
|
||||||
"id": 13,
|
|
||||||
"name": "Angelca Mrak",
|
|
||||||
"enabled": true
|
|
||||||
},
|
|
||||||
{
|
|
||||||
"id": 14,
|
|
||||||
"name": "Karli Proje",
|
|
||||||
"enabled": true
|
|
||||||
},
|
|
||||||
{
|
|
||||||
"id": 15,
|
|
||||||
"name": "Jan Pleterski",
|
|
||||||
"enabled": true
|
|
||||||
},
|
|
||||||
{
|
|
||||||
"id": 16,
|
|
||||||
"name": "Silvo Poro\u010dnik",
|
|
||||||
"enabled": true
|
|
||||||
},
|
|
||||||
{
|
|
||||||
"id": 17,
|
|
||||||
"name": "Du\u0161an Onuk",
|
|
||||||
"enabled": true
|
|
||||||
},
|
|
||||||
{
|
|
||||||
"id": 18,
|
|
||||||
"name": "Matja\u017e Pleterski",
|
|
||||||
"enabled": true
|
|
||||||
},
|
|
||||||
{
|
|
||||||
"id": 19,
|
|
||||||
"name": "Franc Rizmal",
|
|
||||||
"enabled": true
|
|
||||||
},
|
|
||||||
{
|
|
||||||
"id": 20,
|
|
||||||
"name": "Jo\u017ee Preglav",
|
|
||||||
"enabled": true
|
|
||||||
},
|
|
||||||
{
|
|
||||||
"id": 21,
|
|
||||||
"name": "Marko Blimen",
|
|
||||||
"enabled": true
|
|
||||||
},
|
|
||||||
{
|
|
||||||
"id": 22,
|
|
||||||
"name": "Doris Fesel",
|
|
||||||
"enabled": true
|
|
||||||
},
|
|
||||||
{
|
|
||||||
"id": 23,
|
|
||||||
"name": "Robi Krautberger",
|
|
||||||
"enabled": true
|
|
||||||
},
|
|
||||||
{
|
|
||||||
"id": 24,
|
|
||||||
"name": "Jo\u017ee Verdinek",
|
|
||||||
"enabled": true
|
|
||||||
},
|
|
||||||
{
|
|
||||||
"id": 25,
|
|
||||||
"name": "Andrej Herman",
|
|
||||||
"enabled": true
|
|
||||||
},
|
|
||||||
{
|
|
||||||
"id": 26,
|
|
||||||
"name": "Jakob Herman",
|
|
||||||
"enabled": true
|
|
||||||
},
|
|
||||||
{
|
|
||||||
"id": 27,
|
|
||||||
"name": "Janez Mrak",
|
|
||||||
"enabled": true
|
|
||||||
},
|
|
||||||
{
|
|
||||||
"id": 28,
|
|
||||||
"name": "An\u017ee Kolar",
|
|
||||||
"enabled": true
|
|
||||||
},
|
|
||||||
{
|
|
||||||
"id": 29,
|
|
||||||
"name": "Alen Kolar",
|
|
||||||
"enabled": true
|
|
||||||
},
|
|
||||||
{
|
|
||||||
"id": 30,
|
|
||||||
"name": "Maja Hirtl",
|
|
||||||
"enabled": true
|
|
||||||
},
|
|
||||||
{
|
|
||||||
"id": 31,
|
|
||||||
"name": "Dejan Ku\u010dnik",
|
|
||||||
"enabled": true
|
|
||||||
},
|
|
||||||
{
|
|
||||||
"id": 32,
|
|
||||||
"name": "David Strni\u0161a",
|
|
||||||
"enabled": true
|
|
||||||
},
|
|
||||||
{
|
|
||||||
"id": 33,
|
|
||||||
"name": "Namir Uzunovi\u0107",
|
|
||||||
"enabled": true
|
|
||||||
},
|
|
||||||
{
|
|
||||||
"id": 34,
|
|
||||||
"name": "Jo\u017ee Planin\u0161ec",
|
|
||||||
"enabled": true
|
|
||||||
},
|
|
||||||
{
|
|
||||||
"id": 35,
|
|
||||||
"name": "Vanja Kolar",
|
|
||||||
"enabled": true
|
|
||||||
},
|
|
||||||
{
|
|
||||||
"id": 36,
|
|
||||||
"name": "Klara Wankmuller",
|
|
||||||
"enabled": true
|
|
||||||
},
|
|
||||||
{
|
|
||||||
"id": 37,
|
|
||||||
"name": "Milan Stramec",
|
|
||||||
"enabled": true
|
|
||||||
},
|
|
||||||
{
|
|
||||||
"id": 38,
|
|
||||||
"name": "Bojan Sudar",
|
|
||||||
"enabled": true
|
|
||||||
},
|
|
||||||
{
|
|
||||||
"id": 39,
|
|
||||||
"name": "Tia Sudar",
|
|
||||||
"enabled": true
|
|
||||||
},
|
|
||||||
{
|
|
||||||
"id": 40,
|
|
||||||
"name": "Jaka Cvar",
|
|
||||||
"enabled": true
|
|
||||||
},
|
|
||||||
{
|
|
||||||
"id": 41,
|
|
||||||
"name": "Tadej \u0160truc",
|
|
||||||
"enabled": true
|
|
||||||
},
|
|
||||||
{
|
|
||||||
"id": 42,
|
|
||||||
"name": "Jure Glaser",
|
|
||||||
"enabled": true
|
|
||||||
},
|
|
||||||
{
|
|
||||||
"id": 43,
|
|
||||||
"name": "Marko Pokr\u017enik",
|
|
||||||
"enabled": true
|
|
||||||
},
|
|
||||||
{
|
|
||||||
"id": 44,
|
|
||||||
"name": "Anka Ka\u010dnik",
|
|
||||||
"enabled": true
|
|
||||||
},
|
|
||||||
{
|
|
||||||
"id": 45,
|
|
||||||
"name": "Lidija Blimen",
|
|
||||||
"enabled": true
|
|
||||||
},
|
|
||||||
{
|
|
||||||
"id": 46,
|
|
||||||
"name": "Tijana \u0160tumpfl",
|
|
||||||
"enabled": true
|
|
||||||
},
|
|
||||||
{
|
|
||||||
"id": 47,
|
|
||||||
"name": "Ljuba Mr\u0161ak",
|
|
||||||
"enabled": true
|
|
||||||
},
|
|
||||||
{
|
|
||||||
"id": 48,
|
|
||||||
"name": "Janja Salcman",
|
|
||||||
"enabled": true
|
|
||||||
},
|
|
||||||
{
|
|
||||||
"id": 49,
|
|
||||||
"name": "Jolanda Verhnjak",
|
|
||||||
"enabled": true
|
|
||||||
}
|
|
||||||
]
|
|
||||||
}
|
|
||||||
@@ -0,0 +1,2 @@
|
|||||||
|
Flask==3.0.0
|
||||||
|
python-dotenv==1.0.0
|
||||||
@@ -1,3 +0,0 @@
|
|||||||
{
|
|
||||||
"header_text_size": "14px"
|
|
||||||
}
|
|
||||||
-132
@@ -1,132 +0,0 @@
|
|||||||
#!/usr/bin/env python3
|
|
||||||
"""
|
|
||||||
TV_APP V1.0.0 - One-Click Launcher
|
|
||||||
Automatically installs dependencies and starts the web application
|
|
||||||
"""
|
|
||||||
|
|
||||||
import os
|
|
||||||
import sys
|
|
||||||
import subprocess
|
|
||||||
import webbrowser
|
|
||||||
import time
|
|
||||||
import importlib.util
|
|
||||||
|
|
||||||
def check_python_version():
|
|
||||||
"""Check if Python 3.7+ is available"""
|
|
||||||
if sys.version_info < (3, 7):
|
|
||||||
print("ERROR: Python 3.7+ is required")
|
|
||||||
print(f"You have Python {sys.version}")
|
|
||||||
return False
|
|
||||||
return True
|
|
||||||
|
|
||||||
def check_and_install_flask():
|
|
||||||
"""Check if Flask is installed, install if not"""
|
|
||||||
flask_spec = importlib.util.find_spec("flask")
|
|
||||||
|
|
||||||
if flask_spec is not None:
|
|
||||||
import flask
|
|
||||||
print(f"✓ Flask is installed: v{flask.__version__}")
|
|
||||||
return True
|
|
||||||
|
|
||||||
print("⚠ Flask not found. Installing...")
|
|
||||||
try:
|
|
||||||
subprocess.check_call([sys.executable, "-m", "pip", "install", "flask", "-q"])
|
|
||||||
print("✓ Flask installed successfully")
|
|
||||||
return True
|
|
||||||
except subprocess.CalledProcessError:
|
|
||||||
print("ERROR: Failed to install Flask")
|
|
||||||
return False
|
|
||||||
|
|
||||||
def main():
|
|
||||||
"""Main installation and startup routine"""
|
|
||||||
print("\n" + "="*70)
|
|
||||||
print(" TV_APP V1.0.0 - Installation & Launcher")
|
|
||||||
print("="*70 + "\n")
|
|
||||||
|
|
||||||
# Check Python version
|
|
||||||
print("[1/4] Checking Python version...")
|
|
||||||
if not check_python_version():
|
|
||||||
print("\nPlease install Python 3.7 or higher")
|
|
||||||
input("Press Enter to exit...")
|
|
||||||
return False
|
|
||||||
|
|
||||||
import flask
|
|
||||||
print(f"✓ Python {sys.version.split()[0]} found\n")
|
|
||||||
|
|
||||||
# Check Flask
|
|
||||||
print("[2/4] Checking Flask installation...")
|
|
||||||
if not check_and_install_flask():
|
|
||||||
input("Press Enter to exit...")
|
|
||||||
return False
|
|
||||||
print()
|
|
||||||
|
|
||||||
# Find the app directory (handle symlinks and copies)
|
|
||||||
print("[3/4] Locating application directory...")
|
|
||||||
|
|
||||||
# Start with script location
|
|
||||||
script_dir = os.path.dirname(os.path.abspath(__file__))
|
|
||||||
|
|
||||||
# Resolve symlinks
|
|
||||||
if os.path.islink(__file__):
|
|
||||||
script_dir = os.path.dirname(os.path.abspath(os.readlink(__file__)))
|
|
||||||
|
|
||||||
app_path = os.path.join(script_dir, "app.py")
|
|
||||||
|
|
||||||
# If app.py not found, search for it
|
|
||||||
if not os.path.exists(app_path):
|
|
||||||
print(f" Searching for app.py near {script_dir}...")
|
|
||||||
|
|
||||||
# Check parent directory
|
|
||||||
parent_dir = os.path.dirname(script_dir)
|
|
||||||
app_path = os.path.join(parent_dir, "app.py")
|
|
||||||
if os.path.exists(app_path):
|
|
||||||
script_dir = parent_dir
|
|
||||||
else:
|
|
||||||
print(f"ERROR: app.py not found")
|
|
||||||
print(f" Checked: {script_dir}")
|
|
||||||
print(f" Checked: {parent_dir}")
|
|
||||||
input("Press Enter to exit...")
|
|
||||||
return False
|
|
||||||
|
|
||||||
print(f"✓ Application found: {app_path}\n")
|
|
||||||
|
|
||||||
# Start the app
|
|
||||||
print("[4/4] Starting web application...\n")
|
|
||||||
print("="*70)
|
|
||||||
print(" TV_APP is starting...")
|
|
||||||
print("="*70)
|
|
||||||
print("\nThe application will be available at: http://localhost:5000")
|
|
||||||
print("Press Ctrl+C to stop the server\n")
|
|
||||||
|
|
||||||
time.sleep(2)
|
|
||||||
|
|
||||||
# Open browser
|
|
||||||
try:
|
|
||||||
webbrowser.open("http://localhost:5000", new=1)
|
|
||||||
except:
|
|
||||||
pass
|
|
||||||
|
|
||||||
# Change to app directory and run
|
|
||||||
os.chdir(script_dir)
|
|
||||||
|
|
||||||
try:
|
|
||||||
# Import and run the Flask app
|
|
||||||
import app
|
|
||||||
app.app.run(host='0.0.0.0', port=5000, debug=True, use_reloader=False)
|
|
||||||
except ImportError as e:
|
|
||||||
print(f"ERROR: Could not import app.py: {e}")
|
|
||||||
input("Press Enter to exit...")
|
|
||||||
return False
|
|
||||||
except KeyboardInterrupt:
|
|
||||||
print("\n\nServer stopped by user")
|
|
||||||
return True
|
|
||||||
except Exception as e:
|
|
||||||
print(f"ERROR: {e}")
|
|
||||||
input("Press Enter to exit...")
|
|
||||||
return False
|
|
||||||
|
|
||||||
return True
|
|
||||||
|
|
||||||
if __name__ == "__main__":
|
|
||||||
success = main()
|
|
||||||
sys.exit(0 if success else 1)
|
|
||||||
@@ -0,0 +1,6 @@
|
|||||||
|
/**
|
||||||
|
* WebSocket Client - DEPRECATED
|
||||||
|
* This file is no longer used. WebSocket/SocketIO support has been removed.
|
||||||
|
*/
|
||||||
|
|
||||||
|
console.log('WebSocket support has been removed from this application.');
|
||||||
@@ -1,39 +0,0 @@
|
|||||||
{
|
|
||||||
"1": {
|
|
||||||
"number": 1,
|
|
||||||
"title": "Stream 1",
|
|
||||||
"url": "http://192.168.0.103:9081",
|
|
||||||
"active": true
|
|
||||||
},
|
|
||||||
"2": {
|
|
||||||
"number": 2,
|
|
||||||
"title": "Stream 2",
|
|
||||||
"url": "http://192.168.0.103:9082",
|
|
||||||
"active": true
|
|
||||||
},
|
|
||||||
"3": {
|
|
||||||
"number": 3,
|
|
||||||
"title": "Stream 3",
|
|
||||||
"url": "http://192.168.0.103:9083",
|
|
||||||
"active": true
|
|
||||||
},
|
|
||||||
"4": {
|
|
||||||
"number": 4,
|
|
||||||
"title": "Stream 4",
|
|
||||||
"url": "http://192.168.0.103:9084",
|
|
||||||
"active": true
|
|
||||||
},
|
|
||||||
"5": {
|
|
||||||
"number": 5,
|
|
||||||
"title": "Stream 5",
|
|
||||||
"url": "http://192.168.0.103:9085",
|
|
||||||
"active": true
|
|
||||||
},
|
|
||||||
"6": {
|
|
||||||
"number": 6,
|
|
||||||
"title": "Stream 6",
|
|
||||||
"url": "http://192.168.0.103:9086",
|
|
||||||
"active": true
|
|
||||||
},
|
|
||||||
"_last_updated": 1757351904.1407912
|
|
||||||
}
|
|
||||||
Vendored
-3
@@ -1,3 +0,0 @@
|
|||||||
{
|
|
||||||
"git.ignoreLimitWarning": true
|
|
||||||
}
|
|
||||||
@@ -1,759 +0,0 @@
|
|||||||
{
|
|
||||||
"tournament": {
|
|
||||||
"rounds": [
|
|
||||||
{
|
|
||||||
"round_number": 1,
|
|
||||||
"players": [
|
|
||||||
{
|
|
||||||
"id": 4,
|
|
||||||
"name": "Mateja Pleterski",
|
|
||||||
"enabled": true
|
|
||||||
},
|
|
||||||
{
|
|
||||||
"id": 20,
|
|
||||||
"name": "Jo\u017ee Preglav",
|
|
||||||
"enabled": true
|
|
||||||
},
|
|
||||||
{
|
|
||||||
"id": 3,
|
|
||||||
"name": "Ivan Tandler",
|
|
||||||
"enabled": true
|
|
||||||
},
|
|
||||||
{
|
|
||||||
"id": 17,
|
|
||||||
"name": "Du\u0161an Onuk",
|
|
||||||
"enabled": true
|
|
||||||
},
|
|
||||||
{
|
|
||||||
"id": 9,
|
|
||||||
"name": "Janez Bo\u017ei\u010d",
|
|
||||||
"enabled": true
|
|
||||||
},
|
|
||||||
{
|
|
||||||
"id": 44,
|
|
||||||
"name": "Anka Ka\u010dnik",
|
|
||||||
"enabled": true
|
|
||||||
}
|
|
||||||
],
|
|
||||||
"status": "pending"
|
|
||||||
},
|
|
||||||
{
|
|
||||||
"round_number": 2,
|
|
||||||
"players": [
|
|
||||||
{
|
|
||||||
"id": 48,
|
|
||||||
"name": "Janja Salcman",
|
|
||||||
"enabled": true
|
|
||||||
},
|
|
||||||
{
|
|
||||||
"id": 15,
|
|
||||||
"name": "Jan Pleterski",
|
|
||||||
"enabled": true
|
|
||||||
},
|
|
||||||
{
|
|
||||||
"id": 45,
|
|
||||||
"name": "Lidija Blimen",
|
|
||||||
"enabled": true
|
|
||||||
},
|
|
||||||
{
|
|
||||||
"id": 21,
|
|
||||||
"name": "Marko Blimen",
|
|
||||||
"enabled": true
|
|
||||||
},
|
|
||||||
{
|
|
||||||
"id": 49,
|
|
||||||
"name": "Jolanda Verhnjak",
|
|
||||||
"enabled": true
|
|
||||||
},
|
|
||||||
{
|
|
||||||
"id": 11,
|
|
||||||
"name": "Rado Kefer",
|
|
||||||
"enabled": true
|
|
||||||
}
|
|
||||||
],
|
|
||||||
"status": "waiting"
|
|
||||||
},
|
|
||||||
{
|
|
||||||
"round_number": 3,
|
|
||||||
"players": [
|
|
||||||
{
|
|
||||||
"id": 12,
|
|
||||||
"name": "Matej Kvasnik",
|
|
||||||
"enabled": true
|
|
||||||
},
|
|
||||||
{
|
|
||||||
"id": 47,
|
|
||||||
"name": "Ljuba Mr\u0161ak",
|
|
||||||
"enabled": true
|
|
||||||
},
|
|
||||||
{
|
|
||||||
"id": 46,
|
|
||||||
"name": "Tijana \u0160tumpfl",
|
|
||||||
"enabled": true
|
|
||||||
},
|
|
||||||
{
|
|
||||||
"id": 1,
|
|
||||||
"name": "Domen Pleterski",
|
|
||||||
"enabled": true
|
|
||||||
},
|
|
||||||
{
|
|
||||||
"id": 7,
|
|
||||||
"name": "Branko Poker\u017enik",
|
|
||||||
"enabled": true
|
|
||||||
},
|
|
||||||
{
|
|
||||||
"id": 5,
|
|
||||||
"name": "Jo\u017ee Verhnjak",
|
|
||||||
"enabled": true
|
|
||||||
}
|
|
||||||
],
|
|
||||||
"status": "waiting"
|
|
||||||
}
|
|
||||||
],
|
|
||||||
"created_at": "2025-08-30T13:09:30.384521",
|
|
||||||
"total_players": 18,
|
|
||||||
"total_rounds": 3,
|
|
||||||
"current_round": 1,
|
|
||||||
"tournament_type": "4_targets"
|
|
||||||
},
|
|
||||||
"results": {
|
|
||||||
"tournament_id": "2025-08-30T13:09:30.384521",
|
|
||||||
"tournament_type": "4_targets",
|
|
||||||
"participants": {
|
|
||||||
"4": {
|
|
||||||
"name": "Mateja Pleterski",
|
|
||||||
"targets": {
|
|
||||||
"1": {
|
|
||||||
"shot1": 0,
|
|
||||||
"shot2": 0,
|
|
||||||
"shot3": 0,
|
|
||||||
"shot4": 0,
|
|
||||||
"shot5": 0
|
|
||||||
},
|
|
||||||
"2": {
|
|
||||||
"shot1": 0,
|
|
||||||
"shot2": 0,
|
|
||||||
"shot3": 0,
|
|
||||||
"shot4": 0,
|
|
||||||
"shot5": 0
|
|
||||||
},
|
|
||||||
"3": {
|
|
||||||
"shot1": 0,
|
|
||||||
"shot2": 0,
|
|
||||||
"shot3": 0,
|
|
||||||
"shot4": 0,
|
|
||||||
"shot5": 0
|
|
||||||
},
|
|
||||||
"4": {
|
|
||||||
"shot1": 0,
|
|
||||||
"shot2": 0,
|
|
||||||
"shot3": 0,
|
|
||||||
"shot4": 0,
|
|
||||||
"shot5": 0
|
|
||||||
}
|
|
||||||
},
|
|
||||||
"total_score": 0,
|
|
||||||
"completed": true
|
|
||||||
},
|
|
||||||
"20": {
|
|
||||||
"name": "Jo\u017ee Preglav",
|
|
||||||
"targets": {
|
|
||||||
"1": {
|
|
||||||
"shot1": 10,
|
|
||||||
"shot2": 8,
|
|
||||||
"shot3": 8,
|
|
||||||
"shot4": 7,
|
|
||||||
"shot5": 5
|
|
||||||
},
|
|
||||||
"2": {
|
|
||||||
"shot1": 9,
|
|
||||||
"shot2": 7,
|
|
||||||
"shot3": 7,
|
|
||||||
"shot4": 5,
|
|
||||||
"shot5": 4
|
|
||||||
},
|
|
||||||
"3": {
|
|
||||||
"shot1": 9,
|
|
||||||
"shot2": 9,
|
|
||||||
"shot3": 7,
|
|
||||||
"shot4": 6,
|
|
||||||
"shot5": 6
|
|
||||||
},
|
|
||||||
"4": {
|
|
||||||
"shot1": 8,
|
|
||||||
"shot2": 8,
|
|
||||||
"shot3": 7,
|
|
||||||
"shot4": 6,
|
|
||||||
"shot5": 6
|
|
||||||
}
|
|
||||||
},
|
|
||||||
"total_score": 142,
|
|
||||||
"completed": true
|
|
||||||
},
|
|
||||||
"3": {
|
|
||||||
"name": "Ivan Tandler",
|
|
||||||
"targets": {
|
|
||||||
"1": {
|
|
||||||
"shot1": 0,
|
|
||||||
"shot2": 0,
|
|
||||||
"shot3": 0,
|
|
||||||
"shot4": 0,
|
|
||||||
"shot5": 0
|
|
||||||
},
|
|
||||||
"2": {
|
|
||||||
"shot1": 0,
|
|
||||||
"shot2": 0,
|
|
||||||
"shot3": 0,
|
|
||||||
"shot4": 0,
|
|
||||||
"shot5": 0
|
|
||||||
},
|
|
||||||
"3": {
|
|
||||||
"shot1": 0,
|
|
||||||
"shot2": 0,
|
|
||||||
"shot3": 0,
|
|
||||||
"shot4": 0,
|
|
||||||
"shot5": 0
|
|
||||||
},
|
|
||||||
"4": {
|
|
||||||
"shot1": 0,
|
|
||||||
"shot2": 0,
|
|
||||||
"shot3": 0,
|
|
||||||
"shot4": 0,
|
|
||||||
"shot5": 0
|
|
||||||
}
|
|
||||||
},
|
|
||||||
"total_score": 0,
|
|
||||||
"completed": true
|
|
||||||
},
|
|
||||||
"17": {
|
|
||||||
"name": "Du\u0161an Onuk",
|
|
||||||
"targets": {
|
|
||||||
"1": {
|
|
||||||
"shot1": 10,
|
|
||||||
"shot2": 9,
|
|
||||||
"shot3": 9,
|
|
||||||
"shot4": 9,
|
|
||||||
"shot5": 9
|
|
||||||
},
|
|
||||||
"2": {
|
|
||||||
"shot1": 10,
|
|
||||||
"shot2": 10,
|
|
||||||
"shot3": 9,
|
|
||||||
"shot4": 8,
|
|
||||||
"shot5": 7
|
|
||||||
},
|
|
||||||
"3": {
|
|
||||||
"shot1": 10,
|
|
||||||
"shot2": 9,
|
|
||||||
"shot3": 9,
|
|
||||||
"shot4": 9,
|
|
||||||
"shot5": 9
|
|
||||||
},
|
|
||||||
"4": {
|
|
||||||
"shot1": 10,
|
|
||||||
"shot2": 9,
|
|
||||||
"shot3": 9,
|
|
||||||
"shot4": 8,
|
|
||||||
"shot5": 8
|
|
||||||
}
|
|
||||||
},
|
|
||||||
"total_score": 180,
|
|
||||||
"completed": true
|
|
||||||
},
|
|
||||||
"9": {
|
|
||||||
"name": "Janez Bo\u017ei\u010d",
|
|
||||||
"targets": {
|
|
||||||
"1": {
|
|
||||||
"shot1": 10,
|
|
||||||
"shot2": 10,
|
|
||||||
"shot3": 9,
|
|
||||||
"shot4": 9,
|
|
||||||
"shot5": 9
|
|
||||||
},
|
|
||||||
"2": {
|
|
||||||
"shot1": 10,
|
|
||||||
"shot2": 9,
|
|
||||||
"shot3": 8,
|
|
||||||
"shot4": 8,
|
|
||||||
"shot5": 7
|
|
||||||
},
|
|
||||||
"3": {
|
|
||||||
"shot1": 10,
|
|
||||||
"shot2": 10,
|
|
||||||
"shot3": 10,
|
|
||||||
"shot4": 9,
|
|
||||||
"shot5": 7
|
|
||||||
},
|
|
||||||
"4": {
|
|
||||||
"shot1": 10,
|
|
||||||
"shot2": 10,
|
|
||||||
"shot3": 10,
|
|
||||||
"shot4": 8,
|
|
||||||
"shot5": 6
|
|
||||||
}
|
|
||||||
},
|
|
||||||
"total_score": 179,
|
|
||||||
"completed": true
|
|
||||||
},
|
|
||||||
"44": {
|
|
||||||
"name": "Anka Ka\u010dnik",
|
|
||||||
"targets": {
|
|
||||||
"1": {
|
|
||||||
"shot1": 10,
|
|
||||||
"shot2": 9,
|
|
||||||
"shot3": 6,
|
|
||||||
"shot4": 4,
|
|
||||||
"shot5": 3
|
|
||||||
},
|
|
||||||
"2": {
|
|
||||||
"shot1": 9,
|
|
||||||
"shot2": 7,
|
|
||||||
"shot3": 6,
|
|
||||||
"shot4": 3,
|
|
||||||
"shot5": 2
|
|
||||||
},
|
|
||||||
"3": {
|
|
||||||
"shot1": 7,
|
|
||||||
"shot2": 4,
|
|
||||||
"shot3": 4,
|
|
||||||
"shot4": 2,
|
|
||||||
"shot5": 1
|
|
||||||
},
|
|
||||||
"4": {
|
|
||||||
"shot1": 7,
|
|
||||||
"shot2": 6,
|
|
||||||
"shot3": 5,
|
|
||||||
"shot4": 4,
|
|
||||||
"shot5": 3
|
|
||||||
}
|
|
||||||
},
|
|
||||||
"total_score": 102,
|
|
||||||
"completed": true
|
|
||||||
},
|
|
||||||
"48": {
|
|
||||||
"name": "Janja Salcman",
|
|
||||||
"targets": {
|
|
||||||
"1": {
|
|
||||||
"shot1": 7,
|
|
||||||
"shot2": 3,
|
|
||||||
"shot3": 2,
|
|
||||||
"shot4": 2,
|
|
||||||
"shot5": 0
|
|
||||||
},
|
|
||||||
"2": {
|
|
||||||
"shot1": 6,
|
|
||||||
"shot2": 5,
|
|
||||||
"shot3": 2,
|
|
||||||
"shot4": 2,
|
|
||||||
"shot5": 0
|
|
||||||
},
|
|
||||||
"3": {
|
|
||||||
"shot1": 9,
|
|
||||||
"shot2": 9,
|
|
||||||
"shot3": 7,
|
|
||||||
"shot4": 1,
|
|
||||||
"shot5": 0
|
|
||||||
},
|
|
||||||
"4": {
|
|
||||||
"shot1": 8,
|
|
||||||
"shot2": 5,
|
|
||||||
"shot3": 3,
|
|
||||||
"shot4": 1,
|
|
||||||
"shot5": 0
|
|
||||||
}
|
|
||||||
},
|
|
||||||
"total_score": 72,
|
|
||||||
"completed": true
|
|
||||||
},
|
|
||||||
"15": {
|
|
||||||
"name": "Jan Pleterski",
|
|
||||||
"targets": {
|
|
||||||
"1": {
|
|
||||||
"shot1": 10,
|
|
||||||
"shot2": 10,
|
|
||||||
"shot3": 9,
|
|
||||||
"shot4": 6,
|
|
||||||
"shot5": 6
|
|
||||||
},
|
|
||||||
"2": {
|
|
||||||
"shot1": 10,
|
|
||||||
"shot2": 10,
|
|
||||||
"shot3": 9,
|
|
||||||
"shot4": 8,
|
|
||||||
"shot5": 8
|
|
||||||
},
|
|
||||||
"3": {
|
|
||||||
"shot1": 10,
|
|
||||||
"shot2": 9,
|
|
||||||
"shot3": 9,
|
|
||||||
"shot4": 8,
|
|
||||||
"shot5": 6
|
|
||||||
},
|
|
||||||
"4": {
|
|
||||||
"shot1": 10,
|
|
||||||
"shot2": 9,
|
|
||||||
"shot3": 6,
|
|
||||||
"shot4": 5,
|
|
||||||
"shot5": 3
|
|
||||||
}
|
|
||||||
},
|
|
||||||
"total_score": 161,
|
|
||||||
"completed": true
|
|
||||||
},
|
|
||||||
"45": {
|
|
||||||
"name": "Lidija Blimen",
|
|
||||||
"targets": {
|
|
||||||
"1": {
|
|
||||||
"shot1": 10,
|
|
||||||
"shot2": 9,
|
|
||||||
"shot3": 6,
|
|
||||||
"shot4": 4,
|
|
||||||
"shot5": 4
|
|
||||||
},
|
|
||||||
"2": {
|
|
||||||
"shot1": 8,
|
|
||||||
"shot2": 8,
|
|
||||||
"shot3": 6,
|
|
||||||
"shot4": 6,
|
|
||||||
"shot5": 4
|
|
||||||
},
|
|
||||||
"3": {
|
|
||||||
"shot1": 8,
|
|
||||||
"shot2": 7,
|
|
||||||
"shot3": 4,
|
|
||||||
"shot4": 1,
|
|
||||||
"shot5": 1
|
|
||||||
},
|
|
||||||
"4": {
|
|
||||||
"shot1": 9,
|
|
||||||
"shot2": 8,
|
|
||||||
"shot3": 8,
|
|
||||||
"shot4": 8,
|
|
||||||
"shot5": 5
|
|
||||||
}
|
|
||||||
},
|
|
||||||
"total_score": 124,
|
|
||||||
"completed": true
|
|
||||||
},
|
|
||||||
"21": {
|
|
||||||
"name": "Marko Blimen",
|
|
||||||
"targets": {
|
|
||||||
"1": {
|
|
||||||
"shot1": 10,
|
|
||||||
"shot2": 9,
|
|
||||||
"shot3": 9,
|
|
||||||
"shot4": 8,
|
|
||||||
"shot5": 7
|
|
||||||
},
|
|
||||||
"2": {
|
|
||||||
"shot1": 10,
|
|
||||||
"shot2": 9,
|
|
||||||
"shot3": 9,
|
|
||||||
"shot4": 7,
|
|
||||||
"shot5": 7
|
|
||||||
},
|
|
||||||
"3": {
|
|
||||||
"shot1": 9,
|
|
||||||
"shot2": 8,
|
|
||||||
"shot3": 8,
|
|
||||||
"shot4": 7,
|
|
||||||
"shot5": 6
|
|
||||||
},
|
|
||||||
"4": {
|
|
||||||
"shot1": 10,
|
|
||||||
"shot2": 10,
|
|
||||||
"shot3": 9,
|
|
||||||
"shot4": 8,
|
|
||||||
"shot5": 7
|
|
||||||
}
|
|
||||||
},
|
|
||||||
"total_score": 167,
|
|
||||||
"completed": true
|
|
||||||
},
|
|
||||||
"49": {
|
|
||||||
"name": "Jolanda Verhnjak",
|
|
||||||
"targets": {
|
|
||||||
"1": {
|
|
||||||
"shot1": 8,
|
|
||||||
"shot2": 7,
|
|
||||||
"shot3": 6,
|
|
||||||
"shot4": 4,
|
|
||||||
"shot5": 3
|
|
||||||
},
|
|
||||||
"2": {
|
|
||||||
"shot1": 8,
|
|
||||||
"shot2": 8,
|
|
||||||
"shot3": 8,
|
|
||||||
"shot4": 8,
|
|
||||||
"shot5": 3
|
|
||||||
},
|
|
||||||
"3": {
|
|
||||||
"shot1": 7,
|
|
||||||
"shot2": 6,
|
|
||||||
"shot3": 5,
|
|
||||||
"shot4": 3,
|
|
||||||
"shot5": 3
|
|
||||||
},
|
|
||||||
"4": {
|
|
||||||
"shot1": 10,
|
|
||||||
"shot2": 8,
|
|
||||||
"shot3": 8,
|
|
||||||
"shot4": 5,
|
|
||||||
"shot5": 4
|
|
||||||
}
|
|
||||||
},
|
|
||||||
"total_score": 122,
|
|
||||||
"completed": true
|
|
||||||
},
|
|
||||||
"11": {
|
|
||||||
"name": "Rado Kefer",
|
|
||||||
"targets": {
|
|
||||||
"1": {
|
|
||||||
"shot1": 10,
|
|
||||||
"shot2": 9,
|
|
||||||
"shot3": 9,
|
|
||||||
"shot4": 8,
|
|
||||||
"shot5": 7
|
|
||||||
},
|
|
||||||
"2": {
|
|
||||||
"shot1": 10,
|
|
||||||
"shot2": 9,
|
|
||||||
"shot3": 9,
|
|
||||||
"shot4": 8,
|
|
||||||
"shot5": 8
|
|
||||||
},
|
|
||||||
"3": {
|
|
||||||
"shot1": 10,
|
|
||||||
"shot2": 9,
|
|
||||||
"shot3": 9,
|
|
||||||
"shot4": 8,
|
|
||||||
"shot5": 8
|
|
||||||
},
|
|
||||||
"4": {
|
|
||||||
"shot1": 9,
|
|
||||||
"shot2": 9,
|
|
||||||
"shot3": 9,
|
|
||||||
"shot4": 8,
|
|
||||||
"shot5": 8
|
|
||||||
}
|
|
||||||
},
|
|
||||||
"total_score": 174,
|
|
||||||
"completed": true
|
|
||||||
},
|
|
||||||
"12": {
|
|
||||||
"name": "Matej Kvasnik",
|
|
||||||
"targets": {
|
|
||||||
"1": {
|
|
||||||
"shot1": 9,
|
|
||||||
"shot2": 8,
|
|
||||||
"shot3": 8,
|
|
||||||
"shot4": 8,
|
|
||||||
"shot5": 6
|
|
||||||
},
|
|
||||||
"2": {
|
|
||||||
"shot1": 9,
|
|
||||||
"shot2": 9,
|
|
||||||
"shot3": 8,
|
|
||||||
"shot4": 6,
|
|
||||||
"shot5": 4
|
|
||||||
},
|
|
||||||
"3": {
|
|
||||||
"shot1": 10,
|
|
||||||
"shot2": 8,
|
|
||||||
"shot3": 6,
|
|
||||||
"shot4": 5,
|
|
||||||
"shot5": 6
|
|
||||||
},
|
|
||||||
"4": {
|
|
||||||
"shot1": 8,
|
|
||||||
"shot2": 8,
|
|
||||||
"shot3": 8,
|
|
||||||
"shot4": 7,
|
|
||||||
"shot5": 3
|
|
||||||
}
|
|
||||||
},
|
|
||||||
"total_score": 144,
|
|
||||||
"completed": true
|
|
||||||
},
|
|
||||||
"47": {
|
|
||||||
"name": "Ljuba Mr\u0161ak",
|
|
||||||
"targets": {
|
|
||||||
"1": {
|
|
||||||
"shot1": 0,
|
|
||||||
"shot2": 0,
|
|
||||||
"shot3": 0,
|
|
||||||
"shot4": 0,
|
|
||||||
"shot5": 0
|
|
||||||
},
|
|
||||||
"2": {
|
|
||||||
"shot1": 0,
|
|
||||||
"shot2": 0,
|
|
||||||
"shot3": 0,
|
|
||||||
"shot4": 0,
|
|
||||||
"shot5": 0
|
|
||||||
},
|
|
||||||
"3": {
|
|
||||||
"shot1": 0,
|
|
||||||
"shot2": 0,
|
|
||||||
"shot3": 0,
|
|
||||||
"shot4": 0,
|
|
||||||
"shot5": 0
|
|
||||||
},
|
|
||||||
"4": {
|
|
||||||
"shot1": 0,
|
|
||||||
"shot2": 0,
|
|
||||||
"shot3": 0,
|
|
||||||
"shot4": 0,
|
|
||||||
"shot5": 0
|
|
||||||
}
|
|
||||||
},
|
|
||||||
"total_score": 0,
|
|
||||||
"completed": true
|
|
||||||
},
|
|
||||||
"46": {
|
|
||||||
"name": "Tijana \u0160tumpfl",
|
|
||||||
"targets": {
|
|
||||||
"1": {
|
|
||||||
"shot1": 10,
|
|
||||||
"shot2": 10,
|
|
||||||
"shot3": 10,
|
|
||||||
"shot4": 1,
|
|
||||||
"shot5": 1
|
|
||||||
},
|
|
||||||
"2": {
|
|
||||||
"shot1": 5,
|
|
||||||
"shot2": 4,
|
|
||||||
"shot3": 2,
|
|
||||||
"shot4": 0,
|
|
||||||
"shot5": 0
|
|
||||||
},
|
|
||||||
"3": {
|
|
||||||
"shot1": 7,
|
|
||||||
"shot2": 7,
|
|
||||||
"shot3": 2,
|
|
||||||
"shot4": 1,
|
|
||||||
"shot5": 0
|
|
||||||
},
|
|
||||||
"4": {
|
|
||||||
"shot1": 5,
|
|
||||||
"shot2": 3,
|
|
||||||
"shot3": 2,
|
|
||||||
"shot4": 1,
|
|
||||||
"shot5": 0
|
|
||||||
}
|
|
||||||
},
|
|
||||||
"total_score": 71,
|
|
||||||
"completed": true
|
|
||||||
},
|
|
||||||
"1": {
|
|
||||||
"name": "Domen Pleterski",
|
|
||||||
"targets": {
|
|
||||||
"1": {
|
|
||||||
"shot1": 10,
|
|
||||||
"shot2": 10,
|
|
||||||
"shot3": 8,
|
|
||||||
"shot4": 8,
|
|
||||||
"shot5": 8
|
|
||||||
},
|
|
||||||
"2": {
|
|
||||||
"shot1": 9,
|
|
||||||
"shot2": 9,
|
|
||||||
"shot3": 9,
|
|
||||||
"shot4": 9,
|
|
||||||
"shot5": 7
|
|
||||||
},
|
|
||||||
"3": {
|
|
||||||
"shot1": 10,
|
|
||||||
"shot2": 10,
|
|
||||||
"shot3": 9,
|
|
||||||
"shot4": 9,
|
|
||||||
"shot5": 8
|
|
||||||
},
|
|
||||||
"4": {
|
|
||||||
"shot1": 10,
|
|
||||||
"shot2": 10,
|
|
||||||
"shot3": 10,
|
|
||||||
"shot4": 9,
|
|
||||||
"shot5": 8
|
|
||||||
}
|
|
||||||
},
|
|
||||||
"total_score": 180,
|
|
||||||
"completed": true
|
|
||||||
},
|
|
||||||
"7": {
|
|
||||||
"name": "Branko Poker\u017enik",
|
|
||||||
"targets": {
|
|
||||||
"1": {
|
|
||||||
"shot1": 9,
|
|
||||||
"shot2": 9,
|
|
||||||
"shot3": 9,
|
|
||||||
"shot4": 8,
|
|
||||||
"shot5": 7
|
|
||||||
},
|
|
||||||
"2": {
|
|
||||||
"shot1": 10,
|
|
||||||
"shot2": 10,
|
|
||||||
"shot3": 9,
|
|
||||||
"shot4": 8,
|
|
||||||
"shot5": 7
|
|
||||||
},
|
|
||||||
"3": {
|
|
||||||
"shot1": 10,
|
|
||||||
"shot2": 10,
|
|
||||||
"shot3": 9,
|
|
||||||
"shot4": 8,
|
|
||||||
"shot5": 8
|
|
||||||
},
|
|
||||||
"4": {
|
|
||||||
"shot1": 9,
|
|
||||||
"shot2": 9,
|
|
||||||
"shot3": 9,
|
|
||||||
"shot4": 8,
|
|
||||||
"shot5": 6
|
|
||||||
}
|
|
||||||
},
|
|
||||||
"total_score": 172,
|
|
||||||
"completed": true
|
|
||||||
},
|
|
||||||
"5": {
|
|
||||||
"name": "Jo\u017ee Verhnjak",
|
|
||||||
"targets": {
|
|
||||||
"1": {
|
|
||||||
"shot1": 10,
|
|
||||||
"shot2": 9,
|
|
||||||
"shot3": 8,
|
|
||||||
"shot4": 8,
|
|
||||||
"shot5": 5
|
|
||||||
},
|
|
||||||
"2": {
|
|
||||||
"shot1": 9,
|
|
||||||
"shot2": 8,
|
|
||||||
"shot3": 8,
|
|
||||||
"shot4": 6,
|
|
||||||
"shot5": 4
|
|
||||||
},
|
|
||||||
"3": {
|
|
||||||
"shot1": 10,
|
|
||||||
"shot2": 9,
|
|
||||||
"shot3": 8,
|
|
||||||
"shot4": 8,
|
|
||||||
"shot5": 7
|
|
||||||
},
|
|
||||||
"4": {
|
|
||||||
"shot1": 8,
|
|
||||||
"shot2": 9,
|
|
||||||
"shot3": 7,
|
|
||||||
"shot4": 6,
|
|
||||||
"shot5": 8
|
|
||||||
}
|
|
||||||
},
|
|
||||||
"total_score": 155,
|
|
||||||
"completed": true
|
|
||||||
}
|
|
||||||
},
|
|
||||||
"tournament_finished": true,
|
|
||||||
"created_at": "2025-08-30T13:09:30.386527",
|
|
||||||
"finished_at": "2025-08-30T15:33:42.405404"
|
|
||||||
},
|
|
||||||
"archived_at": "2025-08-30T15:33:42.405434"
|
|
||||||
}
|
|
||||||
@@ -1,759 +0,0 @@
|
|||||||
{
|
|
||||||
"tournament": {
|
|
||||||
"rounds": [
|
|
||||||
{
|
|
||||||
"round_number": 1,
|
|
||||||
"players": [
|
|
||||||
{
|
|
||||||
"id": 4,
|
|
||||||
"name": "Mateja Pleterski",
|
|
||||||
"enabled": true
|
|
||||||
},
|
|
||||||
{
|
|
||||||
"id": 21,
|
|
||||||
"name": "Marko Blimen",
|
|
||||||
"enabled": true
|
|
||||||
},
|
|
||||||
{
|
|
||||||
"id": 3,
|
|
||||||
"name": "Ivan Tandler",
|
|
||||||
"enabled": true
|
|
||||||
},
|
|
||||||
{
|
|
||||||
"id": 7,
|
|
||||||
"name": "Branko Poker\u017enik",
|
|
||||||
"enabled": true
|
|
||||||
},
|
|
||||||
{
|
|
||||||
"id": 46,
|
|
||||||
"name": "Tijana \u0160tumpfl",
|
|
||||||
"enabled": true
|
|
||||||
},
|
|
||||||
{
|
|
||||||
"id": 9,
|
|
||||||
"name": "Janez Bo\u017ei\u010d",
|
|
||||||
"enabled": true
|
|
||||||
}
|
|
||||||
],
|
|
||||||
"status": "pending"
|
|
||||||
},
|
|
||||||
{
|
|
||||||
"round_number": 2,
|
|
||||||
"players": [
|
|
||||||
{
|
|
||||||
"id": 48,
|
|
||||||
"name": "Janja Salcman",
|
|
||||||
"enabled": true
|
|
||||||
},
|
|
||||||
{
|
|
||||||
"id": 45,
|
|
||||||
"name": "Lidija Blimen",
|
|
||||||
"enabled": true
|
|
||||||
},
|
|
||||||
{
|
|
||||||
"id": 20,
|
|
||||||
"name": "Jo\u017ee Preglav",
|
|
||||||
"enabled": true
|
|
||||||
},
|
|
||||||
{
|
|
||||||
"id": 11,
|
|
||||||
"name": "Rado Kefer",
|
|
||||||
"enabled": true
|
|
||||||
},
|
|
||||||
{
|
|
||||||
"id": 17,
|
|
||||||
"name": "Du\u0161an Onuk",
|
|
||||||
"enabled": true
|
|
||||||
},
|
|
||||||
{
|
|
||||||
"id": 15,
|
|
||||||
"name": "Jan Pleterski",
|
|
||||||
"enabled": true
|
|
||||||
}
|
|
||||||
],
|
|
||||||
"status": "waiting"
|
|
||||||
},
|
|
||||||
{
|
|
||||||
"round_number": 3,
|
|
||||||
"players": [
|
|
||||||
{
|
|
||||||
"id": 5,
|
|
||||||
"name": "Jo\u017ee Verhnjak",
|
|
||||||
"enabled": true
|
|
||||||
},
|
|
||||||
{
|
|
||||||
"id": 1,
|
|
||||||
"name": "Domen Pleterski",
|
|
||||||
"enabled": true
|
|
||||||
},
|
|
||||||
{
|
|
||||||
"id": 44,
|
|
||||||
"name": "Anka Ka\u010dnik",
|
|
||||||
"enabled": true
|
|
||||||
},
|
|
||||||
{
|
|
||||||
"id": 47,
|
|
||||||
"name": "Ljuba Mr\u0161ak",
|
|
||||||
"enabled": true
|
|
||||||
},
|
|
||||||
{
|
|
||||||
"id": 12,
|
|
||||||
"name": "Matej Kvasnik",
|
|
||||||
"enabled": true
|
|
||||||
},
|
|
||||||
{
|
|
||||||
"id": 49,
|
|
||||||
"name": "Jolanda Verhnjak",
|
|
||||||
"enabled": true
|
|
||||||
}
|
|
||||||
],
|
|
||||||
"status": "waiting"
|
|
||||||
}
|
|
||||||
],
|
|
||||||
"created_at": "2025-09-08T19:19:14.422360",
|
|
||||||
"total_players": 18,
|
|
||||||
"total_rounds": 3,
|
|
||||||
"current_round": 1,
|
|
||||||
"tournament_type": "4_targets"
|
|
||||||
},
|
|
||||||
"results": {
|
|
||||||
"tournament_id": "2025-09-08T19:19:14.422360",
|
|
||||||
"tournament_type": "4_targets",
|
|
||||||
"participants": {
|
|
||||||
"4": {
|
|
||||||
"name": "Mateja Pleterski",
|
|
||||||
"targets": {
|
|
||||||
"1": {
|
|
||||||
"shot1": 10,
|
|
||||||
"shot2": 9,
|
|
||||||
"shot3": 2,
|
|
||||||
"shot4": 10,
|
|
||||||
"shot5": 4
|
|
||||||
},
|
|
||||||
"2": {
|
|
||||||
"shot1": 8,
|
|
||||||
"shot2": 9,
|
|
||||||
"shot3": 8,
|
|
||||||
"shot4": 3,
|
|
||||||
"shot5": 7
|
|
||||||
},
|
|
||||||
"3": {
|
|
||||||
"shot1": 4,
|
|
||||||
"shot2": 2,
|
|
||||||
"shot3": 6,
|
|
||||||
"shot4": 0,
|
|
||||||
"shot5": 10
|
|
||||||
},
|
|
||||||
"4": {
|
|
||||||
"shot1": 7,
|
|
||||||
"shot2": 9,
|
|
||||||
"shot3": 10,
|
|
||||||
"shot4": 5,
|
|
||||||
"shot5": 6
|
|
||||||
}
|
|
||||||
},
|
|
||||||
"total_score": 129,
|
|
||||||
"completed": true
|
|
||||||
},
|
|
||||||
"21": {
|
|
||||||
"name": "Marko Blimen",
|
|
||||||
"targets": {
|
|
||||||
"1": {
|
|
||||||
"shot1": 9,
|
|
||||||
"shot2": 1,
|
|
||||||
"shot3": 8,
|
|
||||||
"shot4": 10,
|
|
||||||
"shot5": 4
|
|
||||||
},
|
|
||||||
"2": {
|
|
||||||
"shot1": 2,
|
|
||||||
"shot2": 4,
|
|
||||||
"shot3": 7,
|
|
||||||
"shot4": 7,
|
|
||||||
"shot5": 1
|
|
||||||
},
|
|
||||||
"3": {
|
|
||||||
"shot1": 0,
|
|
||||||
"shot2": 10,
|
|
||||||
"shot3": 1,
|
|
||||||
"shot4": 8,
|
|
||||||
"shot5": 9
|
|
||||||
},
|
|
||||||
"4": {
|
|
||||||
"shot1": 1,
|
|
||||||
"shot2": 8,
|
|
||||||
"shot3": 4,
|
|
||||||
"shot4": 7,
|
|
||||||
"shot5": 10
|
|
||||||
}
|
|
||||||
},
|
|
||||||
"total_score": 111,
|
|
||||||
"completed": true
|
|
||||||
},
|
|
||||||
"3": {
|
|
||||||
"name": "Ivan Tandler",
|
|
||||||
"targets": {
|
|
||||||
"1": {
|
|
||||||
"shot1": 2,
|
|
||||||
"shot2": 0,
|
|
||||||
"shot3": 9,
|
|
||||||
"shot4": 10,
|
|
||||||
"shot5": 2
|
|
||||||
},
|
|
||||||
"2": {
|
|
||||||
"shot1": 2,
|
|
||||||
"shot2": 0,
|
|
||||||
"shot3": 6,
|
|
||||||
"shot4": 10,
|
|
||||||
"shot5": 4
|
|
||||||
},
|
|
||||||
"3": {
|
|
||||||
"shot1": 0,
|
|
||||||
"shot2": 8,
|
|
||||||
"shot3": 2,
|
|
||||||
"shot4": 7,
|
|
||||||
"shot5": 4
|
|
||||||
},
|
|
||||||
"4": {
|
|
||||||
"shot1": 10,
|
|
||||||
"shot2": 1,
|
|
||||||
"shot3": 6,
|
|
||||||
"shot4": 7,
|
|
||||||
"shot5": 7
|
|
||||||
}
|
|
||||||
},
|
|
||||||
"total_score": 97,
|
|
||||||
"completed": true
|
|
||||||
},
|
|
||||||
"7": {
|
|
||||||
"name": "Branko Poker\u017enik",
|
|
||||||
"targets": {
|
|
||||||
"1": {
|
|
||||||
"shot1": 5,
|
|
||||||
"shot2": 9,
|
|
||||||
"shot3": 1,
|
|
||||||
"shot4": 9,
|
|
||||||
"shot5": 10
|
|
||||||
},
|
|
||||||
"2": {
|
|
||||||
"shot1": 2,
|
|
||||||
"shot2": 9,
|
|
||||||
"shot3": 10,
|
|
||||||
"shot4": 10,
|
|
||||||
"shot5": 7
|
|
||||||
},
|
|
||||||
"3": {
|
|
||||||
"shot1": 10,
|
|
||||||
"shot2": 1,
|
|
||||||
"shot3": 7,
|
|
||||||
"shot4": 4,
|
|
||||||
"shot5": 8
|
|
||||||
},
|
|
||||||
"4": {
|
|
||||||
"shot1": 2,
|
|
||||||
"shot2": 0,
|
|
||||||
"shot3": 10,
|
|
||||||
"shot4": 5,
|
|
||||||
"shot5": 0
|
|
||||||
}
|
|
||||||
},
|
|
||||||
"total_score": 119,
|
|
||||||
"completed": true
|
|
||||||
},
|
|
||||||
"46": {
|
|
||||||
"name": "Tijana \u0160tumpfl",
|
|
||||||
"targets": {
|
|
||||||
"1": {
|
|
||||||
"shot1": 6,
|
|
||||||
"shot2": 9,
|
|
||||||
"shot3": 4,
|
|
||||||
"shot4": 6,
|
|
||||||
"shot5": 1
|
|
||||||
},
|
|
||||||
"2": {
|
|
||||||
"shot1": 7,
|
|
||||||
"shot2": 8,
|
|
||||||
"shot3": 6,
|
|
||||||
"shot4": 5,
|
|
||||||
"shot5": 3
|
|
||||||
},
|
|
||||||
"3": {
|
|
||||||
"shot1": 10,
|
|
||||||
"shot2": 0,
|
|
||||||
"shot3": 6,
|
|
||||||
"shot4": 6,
|
|
||||||
"shot5": 8
|
|
||||||
},
|
|
||||||
"4": {
|
|
||||||
"shot1": 10,
|
|
||||||
"shot2": 4,
|
|
||||||
"shot3": 0,
|
|
||||||
"shot4": 1,
|
|
||||||
"shot5": 10
|
|
||||||
}
|
|
||||||
},
|
|
||||||
"total_score": 110,
|
|
||||||
"completed": true
|
|
||||||
},
|
|
||||||
"9": {
|
|
||||||
"name": "Janez Bo\u017ei\u010d",
|
|
||||||
"targets": {
|
|
||||||
"1": {
|
|
||||||
"shot1": 5,
|
|
||||||
"shot2": 10,
|
|
||||||
"shot3": 8,
|
|
||||||
"shot4": 5,
|
|
||||||
"shot5": 5
|
|
||||||
},
|
|
||||||
"2": {
|
|
||||||
"shot1": 8,
|
|
||||||
"shot2": 9,
|
|
||||||
"shot3": 10,
|
|
||||||
"shot4": 7,
|
|
||||||
"shot5": 10
|
|
||||||
},
|
|
||||||
"3": {
|
|
||||||
"shot1": 7,
|
|
||||||
"shot2": 5,
|
|
||||||
"shot3": 10,
|
|
||||||
"shot4": 4,
|
|
||||||
"shot5": 9
|
|
||||||
},
|
|
||||||
"4": {
|
|
||||||
"shot1": 8,
|
|
||||||
"shot2": 1,
|
|
||||||
"shot3": 6,
|
|
||||||
"shot4": 2,
|
|
||||||
"shot5": 5
|
|
||||||
}
|
|
||||||
},
|
|
||||||
"total_score": 134,
|
|
||||||
"completed": true
|
|
||||||
},
|
|
||||||
"48": {
|
|
||||||
"name": "Janja Salcman",
|
|
||||||
"targets": {
|
|
||||||
"1": {
|
|
||||||
"shot1": 10,
|
|
||||||
"shot2": 6,
|
|
||||||
"shot3": 4,
|
|
||||||
"shot4": 3,
|
|
||||||
"shot5": 9
|
|
||||||
},
|
|
||||||
"2": {
|
|
||||||
"shot1": 10,
|
|
||||||
"shot2": 5,
|
|
||||||
"shot3": 1,
|
|
||||||
"shot4": 1,
|
|
||||||
"shot5": 10
|
|
||||||
},
|
|
||||||
"3": {
|
|
||||||
"shot1": 9,
|
|
||||||
"shot2": 4,
|
|
||||||
"shot3": 0,
|
|
||||||
"shot4": 8,
|
|
||||||
"shot5": 9
|
|
||||||
},
|
|
||||||
"4": {
|
|
||||||
"shot1": 0,
|
|
||||||
"shot2": 1,
|
|
||||||
"shot3": 2,
|
|
||||||
"shot4": 0,
|
|
||||||
"shot5": 9
|
|
||||||
}
|
|
||||||
},
|
|
||||||
"total_score": 101,
|
|
||||||
"completed": true
|
|
||||||
},
|
|
||||||
"45": {
|
|
||||||
"name": "Lidija Blimen",
|
|
||||||
"targets": {
|
|
||||||
"1": {
|
|
||||||
"shot1": 2,
|
|
||||||
"shot2": 4,
|
|
||||||
"shot3": 1,
|
|
||||||
"shot4": 2,
|
|
||||||
"shot5": 6
|
|
||||||
},
|
|
||||||
"2": {
|
|
||||||
"shot1": 7,
|
|
||||||
"shot2": 0,
|
|
||||||
"shot3": 1,
|
|
||||||
"shot4": 2,
|
|
||||||
"shot5": 4
|
|
||||||
},
|
|
||||||
"3": {
|
|
||||||
"shot1": 4,
|
|
||||||
"shot2": 10,
|
|
||||||
"shot3": 2,
|
|
||||||
"shot4": 0,
|
|
||||||
"shot5": 7
|
|
||||||
},
|
|
||||||
"4": {
|
|
||||||
"shot1": 5,
|
|
||||||
"shot2": 7,
|
|
||||||
"shot3": 4,
|
|
||||||
"shot4": 7,
|
|
||||||
"shot5": 4
|
|
||||||
}
|
|
||||||
},
|
|
||||||
"total_score": 79,
|
|
||||||
"completed": true
|
|
||||||
},
|
|
||||||
"20": {
|
|
||||||
"name": "Jo\u017ee Preglav",
|
|
||||||
"targets": {
|
|
||||||
"1": {
|
|
||||||
"shot1": 7,
|
|
||||||
"shot2": 6,
|
|
||||||
"shot3": 7,
|
|
||||||
"shot4": 2,
|
|
||||||
"shot5": 4
|
|
||||||
},
|
|
||||||
"2": {
|
|
||||||
"shot1": 9,
|
|
||||||
"shot2": 4,
|
|
||||||
"shot3": 2,
|
|
||||||
"shot4": 0,
|
|
||||||
"shot5": 8
|
|
||||||
},
|
|
||||||
"3": {
|
|
||||||
"shot1": 5,
|
|
||||||
"shot2": 3,
|
|
||||||
"shot3": 8,
|
|
||||||
"shot4": 3,
|
|
||||||
"shot5": 4
|
|
||||||
},
|
|
||||||
"4": {
|
|
||||||
"shot1": 3,
|
|
||||||
"shot2": 10,
|
|
||||||
"shot3": 2,
|
|
||||||
"shot4": 9,
|
|
||||||
"shot5": 5
|
|
||||||
}
|
|
||||||
},
|
|
||||||
"total_score": 101,
|
|
||||||
"completed": true
|
|
||||||
},
|
|
||||||
"11": {
|
|
||||||
"name": "Rado Kefer",
|
|
||||||
"targets": {
|
|
||||||
"1": {
|
|
||||||
"shot1": 8,
|
|
||||||
"shot2": 10,
|
|
||||||
"shot3": 7,
|
|
||||||
"shot4": 10,
|
|
||||||
"shot5": 7
|
|
||||||
},
|
|
||||||
"2": {
|
|
||||||
"shot1": 10,
|
|
||||||
"shot2": 6,
|
|
||||||
"shot3": 0,
|
|
||||||
"shot4": 7,
|
|
||||||
"shot5": 4
|
|
||||||
},
|
|
||||||
"3": {
|
|
||||||
"shot1": 1,
|
|
||||||
"shot2": 6,
|
|
||||||
"shot3": 8,
|
|
||||||
"shot4": 9,
|
|
||||||
"shot5": 1
|
|
||||||
},
|
|
||||||
"4": {
|
|
||||||
"shot1": 0,
|
|
||||||
"shot2": 1,
|
|
||||||
"shot3": 0,
|
|
||||||
"shot4": 6,
|
|
||||||
"shot5": 9
|
|
||||||
}
|
|
||||||
},
|
|
||||||
"total_score": 110,
|
|
||||||
"completed": true
|
|
||||||
},
|
|
||||||
"17": {
|
|
||||||
"name": "Du\u0161an Onuk",
|
|
||||||
"targets": {
|
|
||||||
"1": {
|
|
||||||
"shot1": 0,
|
|
||||||
"shot2": 7,
|
|
||||||
"shot3": 0,
|
|
||||||
"shot4": 2,
|
|
||||||
"shot5": 2
|
|
||||||
},
|
|
||||||
"2": {
|
|
||||||
"shot1": 5,
|
|
||||||
"shot2": 1,
|
|
||||||
"shot3": 6,
|
|
||||||
"shot4": 4,
|
|
||||||
"shot5": 7
|
|
||||||
},
|
|
||||||
"3": {
|
|
||||||
"shot1": 7,
|
|
||||||
"shot2": 7,
|
|
||||||
"shot3": 0,
|
|
||||||
"shot4": 6,
|
|
||||||
"shot5": 3
|
|
||||||
},
|
|
||||||
"4": {
|
|
||||||
"shot1": 6,
|
|
||||||
"shot2": 4,
|
|
||||||
"shot3": 8,
|
|
||||||
"shot4": 9,
|
|
||||||
"shot5": 5
|
|
||||||
}
|
|
||||||
},
|
|
||||||
"total_score": 89,
|
|
||||||
"completed": true
|
|
||||||
},
|
|
||||||
"15": {
|
|
||||||
"name": "Jan Pleterski",
|
|
||||||
"targets": {
|
|
||||||
"1": {
|
|
||||||
"shot1": 1,
|
|
||||||
"shot2": 10,
|
|
||||||
"shot3": 8,
|
|
||||||
"shot4": 9,
|
|
||||||
"shot5": 8
|
|
||||||
},
|
|
||||||
"2": {
|
|
||||||
"shot1": 7,
|
|
||||||
"shot2": 2,
|
|
||||||
"shot3": 5,
|
|
||||||
"shot4": 4,
|
|
||||||
"shot5": 5
|
|
||||||
},
|
|
||||||
"3": {
|
|
||||||
"shot1": 10,
|
|
||||||
"shot2": 6,
|
|
||||||
"shot3": 1,
|
|
||||||
"shot4": 9,
|
|
||||||
"shot5": 10
|
|
||||||
},
|
|
||||||
"4": {
|
|
||||||
"shot1": 6,
|
|
||||||
"shot2": 2,
|
|
||||||
"shot3": 1,
|
|
||||||
"shot4": 2,
|
|
||||||
"shot5": 1
|
|
||||||
}
|
|
||||||
},
|
|
||||||
"total_score": 107,
|
|
||||||
"completed": true
|
|
||||||
},
|
|
||||||
"5": {
|
|
||||||
"name": "Jo\u017ee Verhnjak",
|
|
||||||
"targets": {
|
|
||||||
"1": {
|
|
||||||
"shot1": 1,
|
|
||||||
"shot2": 10,
|
|
||||||
"shot3": 10,
|
|
||||||
"shot4": 9,
|
|
||||||
"shot5": 1
|
|
||||||
},
|
|
||||||
"2": {
|
|
||||||
"shot1": 0,
|
|
||||||
"shot2": 10,
|
|
||||||
"shot3": 5,
|
|
||||||
"shot4": 10,
|
|
||||||
"shot5": 3
|
|
||||||
},
|
|
||||||
"3": {
|
|
||||||
"shot1": 8,
|
|
||||||
"shot2": 7,
|
|
||||||
"shot3": 4,
|
|
||||||
"shot4": 0,
|
|
||||||
"shot5": 4
|
|
||||||
},
|
|
||||||
"4": {
|
|
||||||
"shot1": 6,
|
|
||||||
"shot2": 1,
|
|
||||||
"shot3": 1,
|
|
||||||
"shot4": 9,
|
|
||||||
"shot5": 8
|
|
||||||
}
|
|
||||||
},
|
|
||||||
"total_score": 107,
|
|
||||||
"completed": true
|
|
||||||
},
|
|
||||||
"1": {
|
|
||||||
"name": "Domen Pleterski",
|
|
||||||
"targets": {
|
|
||||||
"1": {
|
|
||||||
"shot1": 0,
|
|
||||||
"shot2": 5,
|
|
||||||
"shot3": 10,
|
|
||||||
"shot4": 9,
|
|
||||||
"shot5": 6
|
|
||||||
},
|
|
||||||
"2": {
|
|
||||||
"shot1": 4,
|
|
||||||
"shot2": 9,
|
|
||||||
"shot3": 8,
|
|
||||||
"shot4": 6,
|
|
||||||
"shot5": 2
|
|
||||||
},
|
|
||||||
"3": {
|
|
||||||
"shot1": 7,
|
|
||||||
"shot2": 3,
|
|
||||||
"shot3": 7,
|
|
||||||
"shot4": 2,
|
|
||||||
"shot5": 0
|
|
||||||
},
|
|
||||||
"4": {
|
|
||||||
"shot1": 2,
|
|
||||||
"shot2": 4,
|
|
||||||
"shot3": 4,
|
|
||||||
"shot4": 5,
|
|
||||||
"shot5": 2
|
|
||||||
}
|
|
||||||
},
|
|
||||||
"total_score": 95,
|
|
||||||
"completed": true
|
|
||||||
},
|
|
||||||
"44": {
|
|
||||||
"name": "Anka Ka\u010dnik",
|
|
||||||
"targets": {
|
|
||||||
"1": {
|
|
||||||
"shot1": 1,
|
|
||||||
"shot2": 4,
|
|
||||||
"shot3": 10,
|
|
||||||
"shot4": 5,
|
|
||||||
"shot5": 9
|
|
||||||
},
|
|
||||||
"2": {
|
|
||||||
"shot1": 4,
|
|
||||||
"shot2": 5,
|
|
||||||
"shot3": 10,
|
|
||||||
"shot4": 3,
|
|
||||||
"shot5": 2
|
|
||||||
},
|
|
||||||
"3": {
|
|
||||||
"shot1": 6,
|
|
||||||
"shot2": 3,
|
|
||||||
"shot3": 7,
|
|
||||||
"shot4": 3,
|
|
||||||
"shot5": 5
|
|
||||||
},
|
|
||||||
"4": {
|
|
||||||
"shot1": 5,
|
|
||||||
"shot2": 10,
|
|
||||||
"shot3": 8,
|
|
||||||
"shot4": 10,
|
|
||||||
"shot5": 8
|
|
||||||
}
|
|
||||||
},
|
|
||||||
"total_score": 118,
|
|
||||||
"completed": true
|
|
||||||
},
|
|
||||||
"47": {
|
|
||||||
"name": "Ljuba Mr\u0161ak",
|
|
||||||
"targets": {
|
|
||||||
"1": {
|
|
||||||
"shot1": 5,
|
|
||||||
"shot2": 9,
|
|
||||||
"shot3": 6,
|
|
||||||
"shot4": 7,
|
|
||||||
"shot5": 0
|
|
||||||
},
|
|
||||||
"2": {
|
|
||||||
"shot1": 0,
|
|
||||||
"shot2": 4,
|
|
||||||
"shot3": 0,
|
|
||||||
"shot4": 2,
|
|
||||||
"shot5": 8
|
|
||||||
},
|
|
||||||
"3": {
|
|
||||||
"shot1": 2,
|
|
||||||
"shot2": 0,
|
|
||||||
"shot3": 6,
|
|
||||||
"shot4": 5,
|
|
||||||
"shot5": 7
|
|
||||||
},
|
|
||||||
"4": {
|
|
||||||
"shot1": 9,
|
|
||||||
"shot2": 1,
|
|
||||||
"shot3": 2,
|
|
||||||
"shot4": 0,
|
|
||||||
"shot5": 9
|
|
||||||
}
|
|
||||||
},
|
|
||||||
"total_score": 82,
|
|
||||||
"completed": true
|
|
||||||
},
|
|
||||||
"12": {
|
|
||||||
"name": "Matej Kvasnik",
|
|
||||||
"targets": {
|
|
||||||
"1": {
|
|
||||||
"shot1": 2,
|
|
||||||
"shot2": 7,
|
|
||||||
"shot3": 1,
|
|
||||||
"shot4": 0,
|
|
||||||
"shot5": 5
|
|
||||||
},
|
|
||||||
"2": {
|
|
||||||
"shot1": 10,
|
|
||||||
"shot2": 0,
|
|
||||||
"shot3": 3,
|
|
||||||
"shot4": 3,
|
|
||||||
"shot5": 6
|
|
||||||
},
|
|
||||||
"3": {
|
|
||||||
"shot1": 7,
|
|
||||||
"shot2": 2,
|
|
||||||
"shot3": 6,
|
|
||||||
"shot4": 5,
|
|
||||||
"shot5": 0
|
|
||||||
},
|
|
||||||
"4": {
|
|
||||||
"shot1": 10,
|
|
||||||
"shot2": 8,
|
|
||||||
"shot3": 8,
|
|
||||||
"shot4": 8,
|
|
||||||
"shot5": 9
|
|
||||||
}
|
|
||||||
},
|
|
||||||
"total_score": 100,
|
|
||||||
"completed": true
|
|
||||||
},
|
|
||||||
"49": {
|
|
||||||
"name": "Jolanda Verhnjak",
|
|
||||||
"targets": {
|
|
||||||
"1": {
|
|
||||||
"shot1": 5,
|
|
||||||
"shot2": 2,
|
|
||||||
"shot3": 0,
|
|
||||||
"shot4": 3,
|
|
||||||
"shot5": 2
|
|
||||||
},
|
|
||||||
"2": {
|
|
||||||
"shot1": 8,
|
|
||||||
"shot2": 0,
|
|
||||||
"shot3": 10,
|
|
||||||
"shot4": 5,
|
|
||||||
"shot5": 4
|
|
||||||
},
|
|
||||||
"3": {
|
|
||||||
"shot1": 2,
|
|
||||||
"shot2": 9,
|
|
||||||
"shot3": 4,
|
|
||||||
"shot4": 9,
|
|
||||||
"shot5": 2
|
|
||||||
},
|
|
||||||
"4": {
|
|
||||||
"shot1": 2,
|
|
||||||
"shot2": 9,
|
|
||||||
"shot3": 0,
|
|
||||||
"shot4": 4,
|
|
||||||
"shot5": 10
|
|
||||||
}
|
|
||||||
},
|
|
||||||
"total_score": 90,
|
|
||||||
"completed": true
|
|
||||||
}
|
|
||||||
},
|
|
||||||
"tournament_finished": true,
|
|
||||||
"created_at": "2025-09-08T19:19:14.422540",
|
|
||||||
"finished_at": "2025-09-08T19:19:26.929175"
|
|
||||||
},
|
|
||||||
"archived_at": "2025-09-08T19:19:26.929203"
|
|
||||||
}
|
|
||||||
@@ -1,759 +0,0 @@
|
|||||||
{
|
|
||||||
"tournament": {
|
|
||||||
"rounds": [
|
|
||||||
{
|
|
||||||
"round_number": 1,
|
|
||||||
"players": [
|
|
||||||
{
|
|
||||||
"id": 9,
|
|
||||||
"name": "Janez Bo\u017ei\u010d",
|
|
||||||
"enabled": true
|
|
||||||
},
|
|
||||||
{
|
|
||||||
"id": 48,
|
|
||||||
"name": "Janja Salcman",
|
|
||||||
"enabled": true
|
|
||||||
},
|
|
||||||
{
|
|
||||||
"id": 4,
|
|
||||||
"name": "Mateja Pleterski",
|
|
||||||
"enabled": true
|
|
||||||
},
|
|
||||||
{
|
|
||||||
"id": 21,
|
|
||||||
"name": "Marko Blimen",
|
|
||||||
"enabled": true
|
|
||||||
},
|
|
||||||
{
|
|
||||||
"id": 45,
|
|
||||||
"name": "Lidija Blimen",
|
|
||||||
"enabled": true
|
|
||||||
},
|
|
||||||
{
|
|
||||||
"id": 1,
|
|
||||||
"name": "Domen Pleterski",
|
|
||||||
"enabled": true
|
|
||||||
}
|
|
||||||
],
|
|
||||||
"status": "pending"
|
|
||||||
},
|
|
||||||
{
|
|
||||||
"round_number": 2,
|
|
||||||
"players": [
|
|
||||||
{
|
|
||||||
"id": 44,
|
|
||||||
"name": "Anka Ka\u010dnik",
|
|
||||||
"enabled": true
|
|
||||||
},
|
|
||||||
{
|
|
||||||
"id": 12,
|
|
||||||
"name": "Matej Kvasnik",
|
|
||||||
"enabled": true
|
|
||||||
},
|
|
||||||
{
|
|
||||||
"id": 5,
|
|
||||||
"name": "Jo\u017ee Verhnjak",
|
|
||||||
"enabled": true
|
|
||||||
},
|
|
||||||
{
|
|
||||||
"id": 47,
|
|
||||||
"name": "Ljuba Mr\u0161ak",
|
|
||||||
"enabled": true
|
|
||||||
},
|
|
||||||
{
|
|
||||||
"id": 46,
|
|
||||||
"name": "Tijana \u0160tumpfl",
|
|
||||||
"enabled": true
|
|
||||||
},
|
|
||||||
{
|
|
||||||
"id": 49,
|
|
||||||
"name": "Jolanda Verhnjak",
|
|
||||||
"enabled": true
|
|
||||||
}
|
|
||||||
],
|
|
||||||
"status": "waiting"
|
|
||||||
},
|
|
||||||
{
|
|
||||||
"round_number": 3,
|
|
||||||
"players": [
|
|
||||||
{
|
|
||||||
"id": 17,
|
|
||||||
"name": "Du\u0161an Onuk",
|
|
||||||
"enabled": true
|
|
||||||
},
|
|
||||||
{
|
|
||||||
"id": 15,
|
|
||||||
"name": "Jan Pleterski",
|
|
||||||
"enabled": true
|
|
||||||
},
|
|
||||||
{
|
|
||||||
"id": 7,
|
|
||||||
"name": "Branko Poker\u017enik",
|
|
||||||
"enabled": true
|
|
||||||
},
|
|
||||||
{
|
|
||||||
"id": 20,
|
|
||||||
"name": "Jo\u017ee Preglav",
|
|
||||||
"enabled": true
|
|
||||||
},
|
|
||||||
{
|
|
||||||
"id": 11,
|
|
||||||
"name": "Rado Kefer",
|
|
||||||
"enabled": true
|
|
||||||
},
|
|
||||||
{
|
|
||||||
"id": 3,
|
|
||||||
"name": "Ivan Tandler",
|
|
||||||
"enabled": true
|
|
||||||
}
|
|
||||||
],
|
|
||||||
"status": "waiting"
|
|
||||||
}
|
|
||||||
],
|
|
||||||
"created_at": "2025-09-08T19:23:24.597390",
|
|
||||||
"total_players": 18,
|
|
||||||
"total_rounds": 3,
|
|
||||||
"current_round": 1,
|
|
||||||
"tournament_type": "4_targets"
|
|
||||||
},
|
|
||||||
"results": {
|
|
||||||
"tournament_id": "2025-09-08T19:23:24.597390",
|
|
||||||
"tournament_type": "4_targets",
|
|
||||||
"participants": {
|
|
||||||
"9": {
|
|
||||||
"name": "Janez Bo\u017ei\u010d",
|
|
||||||
"targets": {
|
|
||||||
"1": {
|
|
||||||
"shot1": 9,
|
|
||||||
"shot2": 2,
|
|
||||||
"shot3": 4,
|
|
||||||
"shot4": 6,
|
|
||||||
"shot5": 1
|
|
||||||
},
|
|
||||||
"2": {
|
|
||||||
"shot1": 1,
|
|
||||||
"shot2": 4,
|
|
||||||
"shot3": 4,
|
|
||||||
"shot4": 3,
|
|
||||||
"shot5": 4
|
|
||||||
},
|
|
||||||
"3": {
|
|
||||||
"shot1": 5,
|
|
||||||
"shot2": 4,
|
|
||||||
"shot3": 3,
|
|
||||||
"shot4": 3,
|
|
||||||
"shot5": 2
|
|
||||||
},
|
|
||||||
"4": {
|
|
||||||
"shot1": 3,
|
|
||||||
"shot2": 7,
|
|
||||||
"shot3": 2,
|
|
||||||
"shot4": 0,
|
|
||||||
"shot5": 0
|
|
||||||
}
|
|
||||||
},
|
|
||||||
"total_score": 67,
|
|
||||||
"completed": true
|
|
||||||
},
|
|
||||||
"48": {
|
|
||||||
"name": "Janja Salcman",
|
|
||||||
"targets": {
|
|
||||||
"1": {
|
|
||||||
"shot1": 6,
|
|
||||||
"shot2": 10,
|
|
||||||
"shot3": 0,
|
|
||||||
"shot4": 6,
|
|
||||||
"shot5": 5
|
|
||||||
},
|
|
||||||
"2": {
|
|
||||||
"shot1": 0,
|
|
||||||
"shot2": 9,
|
|
||||||
"shot3": 5,
|
|
||||||
"shot4": 4,
|
|
||||||
"shot5": 7
|
|
||||||
},
|
|
||||||
"3": {
|
|
||||||
"shot1": 8,
|
|
||||||
"shot2": 2,
|
|
||||||
"shot3": 8,
|
|
||||||
"shot4": 0,
|
|
||||||
"shot5": 1
|
|
||||||
},
|
|
||||||
"4": {
|
|
||||||
"shot1": 1,
|
|
||||||
"shot2": 4,
|
|
||||||
"shot3": 3,
|
|
||||||
"shot4": 5,
|
|
||||||
"shot5": 1
|
|
||||||
}
|
|
||||||
},
|
|
||||||
"total_score": 85,
|
|
||||||
"completed": true
|
|
||||||
},
|
|
||||||
"4": {
|
|
||||||
"name": "Mateja Pleterski",
|
|
||||||
"targets": {
|
|
||||||
"1": {
|
|
||||||
"shot1": 6,
|
|
||||||
"shot2": 10,
|
|
||||||
"shot3": 1,
|
|
||||||
"shot4": 1,
|
|
||||||
"shot5": 3
|
|
||||||
},
|
|
||||||
"2": {
|
|
||||||
"shot1": 3,
|
|
||||||
"shot2": 4,
|
|
||||||
"shot3": 6,
|
|
||||||
"shot4": 2,
|
|
||||||
"shot5": 10
|
|
||||||
},
|
|
||||||
"3": {
|
|
||||||
"shot1": 1,
|
|
||||||
"shot2": 10,
|
|
||||||
"shot3": 8,
|
|
||||||
"shot4": 5,
|
|
||||||
"shot5": 5
|
|
||||||
},
|
|
||||||
"4": {
|
|
||||||
"shot1": 9,
|
|
||||||
"shot2": 4,
|
|
||||||
"shot3": 9,
|
|
||||||
"shot4": 6,
|
|
||||||
"shot5": 3
|
|
||||||
}
|
|
||||||
},
|
|
||||||
"total_score": 106,
|
|
||||||
"completed": true
|
|
||||||
},
|
|
||||||
"21": {
|
|
||||||
"name": "Marko Blimen",
|
|
||||||
"targets": {
|
|
||||||
"1": {
|
|
||||||
"shot1": 3,
|
|
||||||
"shot2": 2,
|
|
||||||
"shot3": 3,
|
|
||||||
"shot4": 3,
|
|
||||||
"shot5": 3
|
|
||||||
},
|
|
||||||
"2": {
|
|
||||||
"shot1": 0,
|
|
||||||
"shot2": 6,
|
|
||||||
"shot3": 7,
|
|
||||||
"shot4": 0,
|
|
||||||
"shot5": 7
|
|
||||||
},
|
|
||||||
"3": {
|
|
||||||
"shot1": 3,
|
|
||||||
"shot2": 8,
|
|
||||||
"shot3": 1,
|
|
||||||
"shot4": 7,
|
|
||||||
"shot5": 6
|
|
||||||
},
|
|
||||||
"4": {
|
|
||||||
"shot1": 3,
|
|
||||||
"shot2": 4,
|
|
||||||
"shot3": 3,
|
|
||||||
"shot4": 8,
|
|
||||||
"shot5": 1
|
|
||||||
}
|
|
||||||
},
|
|
||||||
"total_score": 78,
|
|
||||||
"completed": true
|
|
||||||
},
|
|
||||||
"45": {
|
|
||||||
"name": "Lidija Blimen",
|
|
||||||
"targets": {
|
|
||||||
"1": {
|
|
||||||
"shot1": 8,
|
|
||||||
"shot2": 3,
|
|
||||||
"shot3": 8,
|
|
||||||
"shot4": 7,
|
|
||||||
"shot5": 7
|
|
||||||
},
|
|
||||||
"2": {
|
|
||||||
"shot1": 3,
|
|
||||||
"shot2": 0,
|
|
||||||
"shot3": 5,
|
|
||||||
"shot4": 7,
|
|
||||||
"shot5": 4
|
|
||||||
},
|
|
||||||
"3": {
|
|
||||||
"shot1": 7,
|
|
||||||
"shot2": 8,
|
|
||||||
"shot3": 0,
|
|
||||||
"shot4": 7,
|
|
||||||
"shot5": 3
|
|
||||||
},
|
|
||||||
"4": {
|
|
||||||
"shot1": 2,
|
|
||||||
"shot2": 10,
|
|
||||||
"shot3": 2,
|
|
||||||
"shot4": 9,
|
|
||||||
"shot5": 0
|
|
||||||
}
|
|
||||||
},
|
|
||||||
"total_score": 100,
|
|
||||||
"completed": true
|
|
||||||
},
|
|
||||||
"1": {
|
|
||||||
"name": "Domen Pleterski",
|
|
||||||
"targets": {
|
|
||||||
"1": {
|
|
||||||
"shot1": 9,
|
|
||||||
"shot2": 1,
|
|
||||||
"shot3": 3,
|
|
||||||
"shot4": 2,
|
|
||||||
"shot5": 4
|
|
||||||
},
|
|
||||||
"2": {
|
|
||||||
"shot1": 8,
|
|
||||||
"shot2": 4,
|
|
||||||
"shot3": 10,
|
|
||||||
"shot4": 9,
|
|
||||||
"shot5": 0
|
|
||||||
},
|
|
||||||
"3": {
|
|
||||||
"shot1": 7,
|
|
||||||
"shot2": 3,
|
|
||||||
"shot3": 2,
|
|
||||||
"shot4": 5,
|
|
||||||
"shot5": 6
|
|
||||||
},
|
|
||||||
"4": {
|
|
||||||
"shot1": 6,
|
|
||||||
"shot2": 6,
|
|
||||||
"shot3": 6,
|
|
||||||
"shot4": 3,
|
|
||||||
"shot5": 10
|
|
||||||
}
|
|
||||||
},
|
|
||||||
"total_score": 104,
|
|
||||||
"completed": true
|
|
||||||
},
|
|
||||||
"44": {
|
|
||||||
"name": "Anka Ka\u010dnik",
|
|
||||||
"targets": {
|
|
||||||
"1": {
|
|
||||||
"shot1": 6,
|
|
||||||
"shot2": 8,
|
|
||||||
"shot3": 6,
|
|
||||||
"shot4": 9,
|
|
||||||
"shot5": 2
|
|
||||||
},
|
|
||||||
"2": {
|
|
||||||
"shot1": 9,
|
|
||||||
"shot2": 0,
|
|
||||||
"shot3": 9,
|
|
||||||
"shot4": 2,
|
|
||||||
"shot5": 8
|
|
||||||
},
|
|
||||||
"3": {
|
|
||||||
"shot1": 5,
|
|
||||||
"shot2": 0,
|
|
||||||
"shot3": 4,
|
|
||||||
"shot4": 10,
|
|
||||||
"shot5": 3
|
|
||||||
},
|
|
||||||
"4": {
|
|
||||||
"shot1": 5,
|
|
||||||
"shot2": 4,
|
|
||||||
"shot3": 2,
|
|
||||||
"shot4": 7,
|
|
||||||
"shot5": 0
|
|
||||||
}
|
|
||||||
},
|
|
||||||
"total_score": 99,
|
|
||||||
"completed": true
|
|
||||||
},
|
|
||||||
"12": {
|
|
||||||
"name": "Matej Kvasnik",
|
|
||||||
"targets": {
|
|
||||||
"1": {
|
|
||||||
"shot1": 9,
|
|
||||||
"shot2": 1,
|
|
||||||
"shot3": 7,
|
|
||||||
"shot4": 9,
|
|
||||||
"shot5": 6
|
|
||||||
},
|
|
||||||
"2": {
|
|
||||||
"shot1": 10,
|
|
||||||
"shot2": 3,
|
|
||||||
"shot3": 2,
|
|
||||||
"shot4": 9,
|
|
||||||
"shot5": 2
|
|
||||||
},
|
|
||||||
"3": {
|
|
||||||
"shot1": 0,
|
|
||||||
"shot2": 9,
|
|
||||||
"shot3": 9,
|
|
||||||
"shot4": 3,
|
|
||||||
"shot5": 6
|
|
||||||
},
|
|
||||||
"4": {
|
|
||||||
"shot1": 4,
|
|
||||||
"shot2": 10,
|
|
||||||
"shot3": 6,
|
|
||||||
"shot4": 5,
|
|
||||||
"shot5": 2
|
|
||||||
}
|
|
||||||
},
|
|
||||||
"total_score": 112,
|
|
||||||
"completed": true
|
|
||||||
},
|
|
||||||
"5": {
|
|
||||||
"name": "Jo\u017ee Verhnjak",
|
|
||||||
"targets": {
|
|
||||||
"1": {
|
|
||||||
"shot1": 4,
|
|
||||||
"shot2": 9,
|
|
||||||
"shot3": 2,
|
|
||||||
"shot4": 4,
|
|
||||||
"shot5": 4
|
|
||||||
},
|
|
||||||
"2": {
|
|
||||||
"shot1": 3,
|
|
||||||
"shot2": 9,
|
|
||||||
"shot3": 4,
|
|
||||||
"shot4": 3,
|
|
||||||
"shot5": 1
|
|
||||||
},
|
|
||||||
"3": {
|
|
||||||
"shot1": 10,
|
|
||||||
"shot2": 7,
|
|
||||||
"shot3": 9,
|
|
||||||
"shot4": 0,
|
|
||||||
"shot5": 3
|
|
||||||
},
|
|
||||||
"4": {
|
|
||||||
"shot1": 10,
|
|
||||||
"shot2": 0,
|
|
||||||
"shot3": 8,
|
|
||||||
"shot4": 6,
|
|
||||||
"shot5": 10
|
|
||||||
}
|
|
||||||
},
|
|
||||||
"total_score": 106,
|
|
||||||
"completed": true
|
|
||||||
},
|
|
||||||
"47": {
|
|
||||||
"name": "Ljuba Mr\u0161ak",
|
|
||||||
"targets": {
|
|
||||||
"1": {
|
|
||||||
"shot1": 7,
|
|
||||||
"shot2": 10,
|
|
||||||
"shot3": 4,
|
|
||||||
"shot4": 2,
|
|
||||||
"shot5": 9
|
|
||||||
},
|
|
||||||
"2": {
|
|
||||||
"shot1": 1,
|
|
||||||
"shot2": 9,
|
|
||||||
"shot3": 2,
|
|
||||||
"shot4": 7,
|
|
||||||
"shot5": 0
|
|
||||||
},
|
|
||||||
"3": {
|
|
||||||
"shot1": 9,
|
|
||||||
"shot2": 8,
|
|
||||||
"shot3": 6,
|
|
||||||
"shot4": 5,
|
|
||||||
"shot5": 7
|
|
||||||
},
|
|
||||||
"4": {
|
|
||||||
"shot1": 9,
|
|
||||||
"shot2": 9,
|
|
||||||
"shot3": 10,
|
|
||||||
"shot4": 0,
|
|
||||||
"shot5": 2
|
|
||||||
}
|
|
||||||
},
|
|
||||||
"total_score": 116,
|
|
||||||
"completed": true
|
|
||||||
},
|
|
||||||
"46": {
|
|
||||||
"name": "Tijana \u0160tumpfl",
|
|
||||||
"targets": {
|
|
||||||
"1": {
|
|
||||||
"shot1": 10,
|
|
||||||
"shot2": 6,
|
|
||||||
"shot3": 9,
|
|
||||||
"shot4": 9,
|
|
||||||
"shot5": 7
|
|
||||||
},
|
|
||||||
"2": {
|
|
||||||
"shot1": 0,
|
|
||||||
"shot2": 6,
|
|
||||||
"shot3": 7,
|
|
||||||
"shot4": 6,
|
|
||||||
"shot5": 10
|
|
||||||
},
|
|
||||||
"3": {
|
|
||||||
"shot1": 3,
|
|
||||||
"shot2": 8,
|
|
||||||
"shot3": 6,
|
|
||||||
"shot4": 5,
|
|
||||||
"shot5": 5
|
|
||||||
},
|
|
||||||
"4": {
|
|
||||||
"shot1": 1,
|
|
||||||
"shot2": 2,
|
|
||||||
"shot3": 9,
|
|
||||||
"shot4": 8,
|
|
||||||
"shot5": 8
|
|
||||||
}
|
|
||||||
},
|
|
||||||
"total_score": 125,
|
|
||||||
"completed": true
|
|
||||||
},
|
|
||||||
"49": {
|
|
||||||
"name": "Jolanda Verhnjak",
|
|
||||||
"targets": {
|
|
||||||
"1": {
|
|
||||||
"shot1": 8,
|
|
||||||
"shot2": 0,
|
|
||||||
"shot3": 9,
|
|
||||||
"shot4": 6,
|
|
||||||
"shot5": 7
|
|
||||||
},
|
|
||||||
"2": {
|
|
||||||
"shot1": 4,
|
|
||||||
"shot2": 4,
|
|
||||||
"shot3": 6,
|
|
||||||
"shot4": 4,
|
|
||||||
"shot5": 8
|
|
||||||
},
|
|
||||||
"3": {
|
|
||||||
"shot1": 0,
|
|
||||||
"shot2": 9,
|
|
||||||
"shot3": 3,
|
|
||||||
"shot4": 4,
|
|
||||||
"shot5": 5
|
|
||||||
},
|
|
||||||
"4": {
|
|
||||||
"shot1": 2,
|
|
||||||
"shot2": 2,
|
|
||||||
"shot3": 0,
|
|
||||||
"shot4": 0,
|
|
||||||
"shot5": 0
|
|
||||||
}
|
|
||||||
},
|
|
||||||
"total_score": 81,
|
|
||||||
"completed": true
|
|
||||||
},
|
|
||||||
"17": {
|
|
||||||
"name": "Du\u0161an Onuk",
|
|
||||||
"targets": {
|
|
||||||
"1": {
|
|
||||||
"shot1": 3,
|
|
||||||
"shot2": 6,
|
|
||||||
"shot3": 5,
|
|
||||||
"shot4": 5,
|
|
||||||
"shot5": 6
|
|
||||||
},
|
|
||||||
"2": {
|
|
||||||
"shot1": 2,
|
|
||||||
"shot2": 4,
|
|
||||||
"shot3": 2,
|
|
||||||
"shot4": 8,
|
|
||||||
"shot5": 8
|
|
||||||
},
|
|
||||||
"3": {
|
|
||||||
"shot1": 3,
|
|
||||||
"shot2": 8,
|
|
||||||
"shot3": 5,
|
|
||||||
"shot4": 8,
|
|
||||||
"shot5": 1
|
|
||||||
},
|
|
||||||
"4": {
|
|
||||||
"shot1": 6,
|
|
||||||
"shot2": 5,
|
|
||||||
"shot3": 3,
|
|
||||||
"shot4": 1,
|
|
||||||
"shot5": 6
|
|
||||||
}
|
|
||||||
},
|
|
||||||
"total_score": 95,
|
|
||||||
"completed": true
|
|
||||||
},
|
|
||||||
"15": {
|
|
||||||
"name": "Jan Pleterski",
|
|
||||||
"targets": {
|
|
||||||
"1": {
|
|
||||||
"shot1": 9,
|
|
||||||
"shot2": 1,
|
|
||||||
"shot3": 7,
|
|
||||||
"shot4": 7,
|
|
||||||
"shot5": 6
|
|
||||||
},
|
|
||||||
"2": {
|
|
||||||
"shot1": 7,
|
|
||||||
"shot2": 2,
|
|
||||||
"shot3": 1,
|
|
||||||
"shot4": 10,
|
|
||||||
"shot5": 10
|
|
||||||
},
|
|
||||||
"3": {
|
|
||||||
"shot1": 9,
|
|
||||||
"shot2": 0,
|
|
||||||
"shot3": 3,
|
|
||||||
"shot4": 9,
|
|
||||||
"shot5": 10
|
|
||||||
},
|
|
||||||
"4": {
|
|
||||||
"shot1": 2,
|
|
||||||
"shot2": 2,
|
|
||||||
"shot3": 8,
|
|
||||||
"shot4": 4,
|
|
||||||
"shot5": 3
|
|
||||||
}
|
|
||||||
},
|
|
||||||
"total_score": 110,
|
|
||||||
"completed": true
|
|
||||||
},
|
|
||||||
"7": {
|
|
||||||
"name": "Branko Poker\u017enik",
|
|
||||||
"targets": {
|
|
||||||
"1": {
|
|
||||||
"shot1": 6,
|
|
||||||
"shot2": 1,
|
|
||||||
"shot3": 8,
|
|
||||||
"shot4": 9,
|
|
||||||
"shot5": 1
|
|
||||||
},
|
|
||||||
"2": {
|
|
||||||
"shot1": 6,
|
|
||||||
"shot2": 3,
|
|
||||||
"shot3": 10,
|
|
||||||
"shot4": 6,
|
|
||||||
"shot5": 0
|
|
||||||
},
|
|
||||||
"3": {
|
|
||||||
"shot1": 8,
|
|
||||||
"shot2": 6,
|
|
||||||
"shot3": 8,
|
|
||||||
"shot4": 0,
|
|
||||||
"shot5": 6
|
|
||||||
},
|
|
||||||
"4": {
|
|
||||||
"shot1": 2,
|
|
||||||
"shot2": 0,
|
|
||||||
"shot3": 10,
|
|
||||||
"shot4": 5,
|
|
||||||
"shot5": 6
|
|
||||||
}
|
|
||||||
},
|
|
||||||
"total_score": 101,
|
|
||||||
"completed": true
|
|
||||||
},
|
|
||||||
"20": {
|
|
||||||
"name": "Jo\u017ee Preglav",
|
|
||||||
"targets": {
|
|
||||||
"1": {
|
|
||||||
"shot1": 4,
|
|
||||||
"shot2": 1,
|
|
||||||
"shot3": 9,
|
|
||||||
"shot4": 2,
|
|
||||||
"shot5": 1
|
|
||||||
},
|
|
||||||
"2": {
|
|
||||||
"shot1": 0,
|
|
||||||
"shot2": 8,
|
|
||||||
"shot3": 0,
|
|
||||||
"shot4": 6,
|
|
||||||
"shot5": 5
|
|
||||||
},
|
|
||||||
"3": {
|
|
||||||
"shot1": 5,
|
|
||||||
"shot2": 7,
|
|
||||||
"shot3": 3,
|
|
||||||
"shot4": 1,
|
|
||||||
"shot5": 9
|
|
||||||
},
|
|
||||||
"4": {
|
|
||||||
"shot1": 4,
|
|
||||||
"shot2": 7,
|
|
||||||
"shot3": 3,
|
|
||||||
"shot4": 1,
|
|
||||||
"shot5": 1
|
|
||||||
}
|
|
||||||
},
|
|
||||||
"total_score": 77,
|
|
||||||
"completed": true
|
|
||||||
},
|
|
||||||
"11": {
|
|
||||||
"name": "Rado Kefer",
|
|
||||||
"targets": {
|
|
||||||
"1": {
|
|
||||||
"shot1": 1,
|
|
||||||
"shot2": 9,
|
|
||||||
"shot3": 7,
|
|
||||||
"shot4": 3,
|
|
||||||
"shot5": 10
|
|
||||||
},
|
|
||||||
"2": {
|
|
||||||
"shot1": 1,
|
|
||||||
"shot2": 2,
|
|
||||||
"shot3": 0,
|
|
||||||
"shot4": 2,
|
|
||||||
"shot5": 4
|
|
||||||
},
|
|
||||||
"3": {
|
|
||||||
"shot1": 1,
|
|
||||||
"shot2": 8,
|
|
||||||
"shot3": 10,
|
|
||||||
"shot4": 0,
|
|
||||||
"shot5": 0
|
|
||||||
},
|
|
||||||
"4": {
|
|
||||||
"shot1": 10,
|
|
||||||
"shot2": 2,
|
|
||||||
"shot3": 9,
|
|
||||||
"shot4": 1,
|
|
||||||
"shot5": 1
|
|
||||||
}
|
|
||||||
},
|
|
||||||
"total_score": 81,
|
|
||||||
"completed": true
|
|
||||||
},
|
|
||||||
"3": {
|
|
||||||
"name": "Ivan Tandler",
|
|
||||||
"targets": {
|
|
||||||
"1": {
|
|
||||||
"shot1": 5,
|
|
||||||
"shot2": 0,
|
|
||||||
"shot3": 9,
|
|
||||||
"shot4": 5,
|
|
||||||
"shot5": 7
|
|
||||||
},
|
|
||||||
"2": {
|
|
||||||
"shot1": 6,
|
|
||||||
"shot2": 0,
|
|
||||||
"shot3": 0,
|
|
||||||
"shot4": 1,
|
|
||||||
"shot5": 0
|
|
||||||
},
|
|
||||||
"3": {
|
|
||||||
"shot1": 4,
|
|
||||||
"shot2": 9,
|
|
||||||
"shot3": 5,
|
|
||||||
"shot4": 7,
|
|
||||||
"shot5": 3
|
|
||||||
},
|
|
||||||
"4": {
|
|
||||||
"shot1": 0,
|
|
||||||
"shot2": 5,
|
|
||||||
"shot3": 8,
|
|
||||||
"shot4": 5,
|
|
||||||
"shot5": 4
|
|
||||||
}
|
|
||||||
},
|
|
||||||
"total_score": 83,
|
|
||||||
"completed": true
|
|
||||||
}
|
|
||||||
},
|
|
||||||
"tournament_finished": true,
|
|
||||||
"created_at": "2025-09-08T19:23:24.597575",
|
|
||||||
"finished_at": "2025-09-08T19:23:34.271264"
|
|
||||||
},
|
|
||||||
"archived_at": "2025-09-08T19:23:34.271291"
|
|
||||||
}
|
|
||||||
@@ -1,759 +0,0 @@
|
|||||||
{
|
|
||||||
"tournament": {
|
|
||||||
"rounds": [
|
|
||||||
{
|
|
||||||
"round_number": 1,
|
|
||||||
"players": [
|
|
||||||
{
|
|
||||||
"id": 44,
|
|
||||||
"name": "Anka Ka\u010dnik",
|
|
||||||
"enabled": true
|
|
||||||
},
|
|
||||||
{
|
|
||||||
"id": 9,
|
|
||||||
"name": "Janez Bo\u017ei\u010d",
|
|
||||||
"enabled": true
|
|
||||||
},
|
|
||||||
{
|
|
||||||
"id": 7,
|
|
||||||
"name": "Branko Poker\u017enik",
|
|
||||||
"enabled": true
|
|
||||||
},
|
|
||||||
{
|
|
||||||
"id": 1,
|
|
||||||
"name": "Domen Pleterski",
|
|
||||||
"enabled": true
|
|
||||||
},
|
|
||||||
{
|
|
||||||
"id": 21,
|
|
||||||
"name": "Marko Blimen",
|
|
||||||
"enabled": true
|
|
||||||
},
|
|
||||||
{
|
|
||||||
"id": 12,
|
|
||||||
"name": "Matej Kvasnik",
|
|
||||||
"enabled": true
|
|
||||||
}
|
|
||||||
],
|
|
||||||
"status": "pending"
|
|
||||||
},
|
|
||||||
{
|
|
||||||
"round_number": 2,
|
|
||||||
"players": [
|
|
||||||
{
|
|
||||||
"id": 48,
|
|
||||||
"name": "Janja Salcman",
|
|
||||||
"enabled": true
|
|
||||||
},
|
|
||||||
{
|
|
||||||
"id": 5,
|
|
||||||
"name": "Jo\u017ee Verhnjak",
|
|
||||||
"enabled": true
|
|
||||||
},
|
|
||||||
{
|
|
||||||
"id": 4,
|
|
||||||
"name": "Mateja Pleterski",
|
|
||||||
"enabled": true
|
|
||||||
},
|
|
||||||
{
|
|
||||||
"id": 20,
|
|
||||||
"name": "Jo\u017ee Preglav",
|
|
||||||
"enabled": true
|
|
||||||
},
|
|
||||||
{
|
|
||||||
"id": 15,
|
|
||||||
"name": "Jan Pleterski",
|
|
||||||
"enabled": true
|
|
||||||
},
|
|
||||||
{
|
|
||||||
"id": 17,
|
|
||||||
"name": "Du\u0161an Onuk",
|
|
||||||
"enabled": true
|
|
||||||
}
|
|
||||||
],
|
|
||||||
"status": "waiting"
|
|
||||||
},
|
|
||||||
{
|
|
||||||
"round_number": 3,
|
|
||||||
"players": [
|
|
||||||
{
|
|
||||||
"id": 46,
|
|
||||||
"name": "Tijana \u0160tumpfl",
|
|
||||||
"enabled": true
|
|
||||||
},
|
|
||||||
{
|
|
||||||
"id": 49,
|
|
||||||
"name": "Jolanda Verhnjak",
|
|
||||||
"enabled": true
|
|
||||||
},
|
|
||||||
{
|
|
||||||
"id": 3,
|
|
||||||
"name": "Ivan Tandler",
|
|
||||||
"enabled": true
|
|
||||||
},
|
|
||||||
{
|
|
||||||
"id": 11,
|
|
||||||
"name": "Rado Kefer",
|
|
||||||
"enabled": true
|
|
||||||
},
|
|
||||||
{
|
|
||||||
"id": 45,
|
|
||||||
"name": "Lidija Blimen",
|
|
||||||
"enabled": true
|
|
||||||
},
|
|
||||||
{
|
|
||||||
"id": 47,
|
|
||||||
"name": "Ljuba Mr\u0161ak",
|
|
||||||
"enabled": true
|
|
||||||
}
|
|
||||||
],
|
|
||||||
"status": "waiting"
|
|
||||||
}
|
|
||||||
],
|
|
||||||
"created_at": "2025-09-08T19:26:24.708355",
|
|
||||||
"total_players": 18,
|
|
||||||
"total_rounds": 3,
|
|
||||||
"current_round": 1,
|
|
||||||
"tournament_type": "4_targets"
|
|
||||||
},
|
|
||||||
"results": {
|
|
||||||
"tournament_id": "2025-09-08T19:26:24.708355",
|
|
||||||
"tournament_type": "4_targets",
|
|
||||||
"participants": {
|
|
||||||
"44": {
|
|
||||||
"name": "Anka Ka\u010dnik",
|
|
||||||
"targets": {
|
|
||||||
"1": {
|
|
||||||
"shot1": 8,
|
|
||||||
"shot2": 4,
|
|
||||||
"shot3": 0,
|
|
||||||
"shot4": 7,
|
|
||||||
"shot5": 4
|
|
||||||
},
|
|
||||||
"2": {
|
|
||||||
"shot1": 2,
|
|
||||||
"shot2": 7,
|
|
||||||
"shot3": 5,
|
|
||||||
"shot4": 0,
|
|
||||||
"shot5": 0
|
|
||||||
},
|
|
||||||
"3": {
|
|
||||||
"shot1": 0,
|
|
||||||
"shot2": 7,
|
|
||||||
"shot3": 8,
|
|
||||||
"shot4": 9,
|
|
||||||
"shot5": 7
|
|
||||||
},
|
|
||||||
"4": {
|
|
||||||
"shot1": 9,
|
|
||||||
"shot2": 6,
|
|
||||||
"shot3": 2,
|
|
||||||
"shot4": 4,
|
|
||||||
"shot5": 9
|
|
||||||
}
|
|
||||||
},
|
|
||||||
"total_score": 98,
|
|
||||||
"completed": true
|
|
||||||
},
|
|
||||||
"9": {
|
|
||||||
"name": "Janez Bo\u017ei\u010d",
|
|
||||||
"targets": {
|
|
||||||
"1": {
|
|
||||||
"shot1": 7,
|
|
||||||
"shot2": 7,
|
|
||||||
"shot3": 10,
|
|
||||||
"shot4": 4,
|
|
||||||
"shot5": 1
|
|
||||||
},
|
|
||||||
"2": {
|
|
||||||
"shot1": 9,
|
|
||||||
"shot2": 5,
|
|
||||||
"shot3": 5,
|
|
||||||
"shot4": 0,
|
|
||||||
"shot5": 4
|
|
||||||
},
|
|
||||||
"3": {
|
|
||||||
"shot1": 5,
|
|
||||||
"shot2": 1,
|
|
||||||
"shot3": 3,
|
|
||||||
"shot4": 4,
|
|
||||||
"shot5": 0
|
|
||||||
},
|
|
||||||
"4": {
|
|
||||||
"shot1": 6,
|
|
||||||
"shot2": 3,
|
|
||||||
"shot3": 3,
|
|
||||||
"shot4": 10,
|
|
||||||
"shot5": 7
|
|
||||||
}
|
|
||||||
},
|
|
||||||
"total_score": 94,
|
|
||||||
"completed": true
|
|
||||||
},
|
|
||||||
"7": {
|
|
||||||
"name": "Branko Poker\u017enik",
|
|
||||||
"targets": {
|
|
||||||
"1": {
|
|
||||||
"shot1": 9,
|
|
||||||
"shot2": 5,
|
|
||||||
"shot3": 10,
|
|
||||||
"shot4": 8,
|
|
||||||
"shot5": 3
|
|
||||||
},
|
|
||||||
"2": {
|
|
||||||
"shot1": 4,
|
|
||||||
"shot2": 4,
|
|
||||||
"shot3": 4,
|
|
||||||
"shot4": 7,
|
|
||||||
"shot5": 4
|
|
||||||
},
|
|
||||||
"3": {
|
|
||||||
"shot1": 8,
|
|
||||||
"shot2": 2,
|
|
||||||
"shot3": 5,
|
|
||||||
"shot4": 0,
|
|
||||||
"shot5": 9
|
|
||||||
},
|
|
||||||
"4": {
|
|
||||||
"shot1": 0,
|
|
||||||
"shot2": 4,
|
|
||||||
"shot3": 2,
|
|
||||||
"shot4": 4,
|
|
||||||
"shot5": 6
|
|
||||||
}
|
|
||||||
},
|
|
||||||
"total_score": 98,
|
|
||||||
"completed": true
|
|
||||||
},
|
|
||||||
"1": {
|
|
||||||
"name": "Domen Pleterski",
|
|
||||||
"targets": {
|
|
||||||
"1": {
|
|
||||||
"shot1": 0,
|
|
||||||
"shot2": 8,
|
|
||||||
"shot3": 8,
|
|
||||||
"shot4": 5,
|
|
||||||
"shot5": 3
|
|
||||||
},
|
|
||||||
"2": {
|
|
||||||
"shot1": 1,
|
|
||||||
"shot2": 7,
|
|
||||||
"shot3": 3,
|
|
||||||
"shot4": 4,
|
|
||||||
"shot5": 4
|
|
||||||
},
|
|
||||||
"3": {
|
|
||||||
"shot1": 1,
|
|
||||||
"shot2": 2,
|
|
||||||
"shot3": 0,
|
|
||||||
"shot4": 5,
|
|
||||||
"shot5": 5
|
|
||||||
},
|
|
||||||
"4": {
|
|
||||||
"shot1": 2,
|
|
||||||
"shot2": 8,
|
|
||||||
"shot3": 8,
|
|
||||||
"shot4": 7,
|
|
||||||
"shot5": 8
|
|
||||||
}
|
|
||||||
},
|
|
||||||
"total_score": 89,
|
|
||||||
"completed": true
|
|
||||||
},
|
|
||||||
"21": {
|
|
||||||
"name": "Marko Blimen",
|
|
||||||
"targets": {
|
|
||||||
"1": {
|
|
||||||
"shot1": 8,
|
|
||||||
"shot2": 8,
|
|
||||||
"shot3": 2,
|
|
||||||
"shot4": 8,
|
|
||||||
"shot5": 0
|
|
||||||
},
|
|
||||||
"2": {
|
|
||||||
"shot1": 1,
|
|
||||||
"shot2": 9,
|
|
||||||
"shot3": 4,
|
|
||||||
"shot4": 10,
|
|
||||||
"shot5": 1
|
|
||||||
},
|
|
||||||
"3": {
|
|
||||||
"shot1": 0,
|
|
||||||
"shot2": 4,
|
|
||||||
"shot3": 6,
|
|
||||||
"shot4": 8,
|
|
||||||
"shot5": 1
|
|
||||||
},
|
|
||||||
"4": {
|
|
||||||
"shot1": 10,
|
|
||||||
"shot2": 1,
|
|
||||||
"shot3": 7,
|
|
||||||
"shot4": 10,
|
|
||||||
"shot5": 9
|
|
||||||
}
|
|
||||||
},
|
|
||||||
"total_score": 107,
|
|
||||||
"completed": true
|
|
||||||
},
|
|
||||||
"12": {
|
|
||||||
"name": "Matej Kvasnik",
|
|
||||||
"targets": {
|
|
||||||
"1": {
|
|
||||||
"shot1": 3,
|
|
||||||
"shot2": 10,
|
|
||||||
"shot3": 0,
|
|
||||||
"shot4": 0,
|
|
||||||
"shot5": 0
|
|
||||||
},
|
|
||||||
"2": {
|
|
||||||
"shot1": 4,
|
|
||||||
"shot2": 7,
|
|
||||||
"shot3": 9,
|
|
||||||
"shot4": 7,
|
|
||||||
"shot5": 2
|
|
||||||
},
|
|
||||||
"3": {
|
|
||||||
"shot1": 8,
|
|
||||||
"shot2": 8,
|
|
||||||
"shot3": 3,
|
|
||||||
"shot4": 7,
|
|
||||||
"shot5": 8
|
|
||||||
},
|
|
||||||
"4": {
|
|
||||||
"shot1": 6,
|
|
||||||
"shot2": 7,
|
|
||||||
"shot3": 9,
|
|
||||||
"shot4": 7,
|
|
||||||
"shot5": 10
|
|
||||||
}
|
|
||||||
},
|
|
||||||
"total_score": 115,
|
|
||||||
"completed": true
|
|
||||||
},
|
|
||||||
"48": {
|
|
||||||
"name": "Janja Salcman",
|
|
||||||
"targets": {
|
|
||||||
"1": {
|
|
||||||
"shot1": 0,
|
|
||||||
"shot2": 1,
|
|
||||||
"shot3": 4,
|
|
||||||
"shot4": 8,
|
|
||||||
"shot5": 2
|
|
||||||
},
|
|
||||||
"2": {
|
|
||||||
"shot1": 3,
|
|
||||||
"shot2": 0,
|
|
||||||
"shot3": 0,
|
|
||||||
"shot4": 6,
|
|
||||||
"shot5": 0
|
|
||||||
},
|
|
||||||
"3": {
|
|
||||||
"shot1": 7,
|
|
||||||
"shot2": 6,
|
|
||||||
"shot3": 4,
|
|
||||||
"shot4": 3,
|
|
||||||
"shot5": 6
|
|
||||||
},
|
|
||||||
"4": {
|
|
||||||
"shot1": 5,
|
|
||||||
"shot2": 9,
|
|
||||||
"shot3": 10,
|
|
||||||
"shot4": 6,
|
|
||||||
"shot5": 7
|
|
||||||
}
|
|
||||||
},
|
|
||||||
"total_score": 87,
|
|
||||||
"completed": true
|
|
||||||
},
|
|
||||||
"5": {
|
|
||||||
"name": "Jo\u017ee Verhnjak",
|
|
||||||
"targets": {
|
|
||||||
"1": {
|
|
||||||
"shot1": 2,
|
|
||||||
"shot2": 8,
|
|
||||||
"shot3": 4,
|
|
||||||
"shot4": 10,
|
|
||||||
"shot5": 0
|
|
||||||
},
|
|
||||||
"2": {
|
|
||||||
"shot1": 0,
|
|
||||||
"shot2": 2,
|
|
||||||
"shot3": 5,
|
|
||||||
"shot4": 5,
|
|
||||||
"shot5": 1
|
|
||||||
},
|
|
||||||
"3": {
|
|
||||||
"shot1": 3,
|
|
||||||
"shot2": 0,
|
|
||||||
"shot3": 8,
|
|
||||||
"shot4": 5,
|
|
||||||
"shot5": 5
|
|
||||||
},
|
|
||||||
"4": {
|
|
||||||
"shot1": 9,
|
|
||||||
"shot2": 10,
|
|
||||||
"shot3": 5,
|
|
||||||
"shot4": 1,
|
|
||||||
"shot5": 6
|
|
||||||
}
|
|
||||||
},
|
|
||||||
"total_score": 89,
|
|
||||||
"completed": true
|
|
||||||
},
|
|
||||||
"4": {
|
|
||||||
"name": "Mateja Pleterski",
|
|
||||||
"targets": {
|
|
||||||
"1": {
|
|
||||||
"shot1": 6,
|
|
||||||
"shot2": 10,
|
|
||||||
"shot3": 1,
|
|
||||||
"shot4": 7,
|
|
||||||
"shot5": 0
|
|
||||||
},
|
|
||||||
"2": {
|
|
||||||
"shot1": 9,
|
|
||||||
"shot2": 1,
|
|
||||||
"shot3": 9,
|
|
||||||
"shot4": 2,
|
|
||||||
"shot5": 6
|
|
||||||
},
|
|
||||||
"3": {
|
|
||||||
"shot1": 7,
|
|
||||||
"shot2": 1,
|
|
||||||
"shot3": 4,
|
|
||||||
"shot4": 1,
|
|
||||||
"shot5": 9
|
|
||||||
},
|
|
||||||
"4": {
|
|
||||||
"shot1": 2,
|
|
||||||
"shot2": 6,
|
|
||||||
"shot3": 8,
|
|
||||||
"shot4": 4,
|
|
||||||
"shot5": 4
|
|
||||||
}
|
|
||||||
},
|
|
||||||
"total_score": 97,
|
|
||||||
"completed": true
|
|
||||||
},
|
|
||||||
"20": {
|
|
||||||
"name": "Jo\u017ee Preglav",
|
|
||||||
"targets": {
|
|
||||||
"1": {
|
|
||||||
"shot1": 5,
|
|
||||||
"shot2": 10,
|
|
||||||
"shot3": 4,
|
|
||||||
"shot4": 8,
|
|
||||||
"shot5": 9
|
|
||||||
},
|
|
||||||
"2": {
|
|
||||||
"shot1": 7,
|
|
||||||
"shot2": 6,
|
|
||||||
"shot3": 0,
|
|
||||||
"shot4": 6,
|
|
||||||
"shot5": 0
|
|
||||||
},
|
|
||||||
"3": {
|
|
||||||
"shot1": 6,
|
|
||||||
"shot2": 9,
|
|
||||||
"shot3": 1,
|
|
||||||
"shot4": 6,
|
|
||||||
"shot5": 1
|
|
||||||
},
|
|
||||||
"4": {
|
|
||||||
"shot1": 1,
|
|
||||||
"shot2": 2,
|
|
||||||
"shot3": 5,
|
|
||||||
"shot4": 0,
|
|
||||||
"shot5": 6
|
|
||||||
}
|
|
||||||
},
|
|
||||||
"total_score": 92,
|
|
||||||
"completed": true
|
|
||||||
},
|
|
||||||
"15": {
|
|
||||||
"name": "Jan Pleterski",
|
|
||||||
"targets": {
|
|
||||||
"1": {
|
|
||||||
"shot1": 0,
|
|
||||||
"shot2": 6,
|
|
||||||
"shot3": 9,
|
|
||||||
"shot4": 3,
|
|
||||||
"shot5": 8
|
|
||||||
},
|
|
||||||
"2": {
|
|
||||||
"shot1": 3,
|
|
||||||
"shot2": 0,
|
|
||||||
"shot3": 6,
|
|
||||||
"shot4": 4,
|
|
||||||
"shot5": 0
|
|
||||||
},
|
|
||||||
"3": {
|
|
||||||
"shot1": 3,
|
|
||||||
"shot2": 0,
|
|
||||||
"shot3": 4,
|
|
||||||
"shot4": 4,
|
|
||||||
"shot5": 10
|
|
||||||
},
|
|
||||||
"4": {
|
|
||||||
"shot1": 6,
|
|
||||||
"shot2": 9,
|
|
||||||
"shot3": 8,
|
|
||||||
"shot4": 0,
|
|
||||||
"shot5": 1
|
|
||||||
}
|
|
||||||
},
|
|
||||||
"total_score": 84,
|
|
||||||
"completed": true
|
|
||||||
},
|
|
||||||
"17": {
|
|
||||||
"name": "Du\u0161an Onuk",
|
|
||||||
"targets": {
|
|
||||||
"1": {
|
|
||||||
"shot1": 7,
|
|
||||||
"shot2": 5,
|
|
||||||
"shot3": 2,
|
|
||||||
"shot4": 7,
|
|
||||||
"shot5": 5
|
|
||||||
},
|
|
||||||
"2": {
|
|
||||||
"shot1": 9,
|
|
||||||
"shot2": 3,
|
|
||||||
"shot3": 8,
|
|
||||||
"shot4": 0,
|
|
||||||
"shot5": 6
|
|
||||||
},
|
|
||||||
"3": {
|
|
||||||
"shot1": 1,
|
|
||||||
"shot2": 6,
|
|
||||||
"shot3": 5,
|
|
||||||
"shot4": 5,
|
|
||||||
"shot5": 7
|
|
||||||
},
|
|
||||||
"4": {
|
|
||||||
"shot1": 3,
|
|
||||||
"shot2": 7,
|
|
||||||
"shot3": 6,
|
|
||||||
"shot4": 7,
|
|
||||||
"shot5": 7
|
|
||||||
}
|
|
||||||
},
|
|
||||||
"total_score": 106,
|
|
||||||
"completed": true
|
|
||||||
},
|
|
||||||
"46": {
|
|
||||||
"name": "Tijana \u0160tumpfl",
|
|
||||||
"targets": {
|
|
||||||
"1": {
|
|
||||||
"shot1": 5,
|
|
||||||
"shot2": 4,
|
|
||||||
"shot3": 4,
|
|
||||||
"shot4": 9,
|
|
||||||
"shot5": 3
|
|
||||||
},
|
|
||||||
"2": {
|
|
||||||
"shot1": 7,
|
|
||||||
"shot2": 0,
|
|
||||||
"shot3": 5,
|
|
||||||
"shot4": 4,
|
|
||||||
"shot5": 7
|
|
||||||
},
|
|
||||||
"3": {
|
|
||||||
"shot1": 2,
|
|
||||||
"shot2": 4,
|
|
||||||
"shot3": 7,
|
|
||||||
"shot4": 5,
|
|
||||||
"shot5": 9
|
|
||||||
},
|
|
||||||
"4": {
|
|
||||||
"shot1": 1,
|
|
||||||
"shot2": 4,
|
|
||||||
"shot3": 0,
|
|
||||||
"shot4": 1,
|
|
||||||
"shot5": 6
|
|
||||||
}
|
|
||||||
},
|
|
||||||
"total_score": 87,
|
|
||||||
"completed": true
|
|
||||||
},
|
|
||||||
"49": {
|
|
||||||
"name": "Jolanda Verhnjak",
|
|
||||||
"targets": {
|
|
||||||
"1": {
|
|
||||||
"shot1": 9,
|
|
||||||
"shot2": 10,
|
|
||||||
"shot3": 5,
|
|
||||||
"shot4": 8,
|
|
||||||
"shot5": 2
|
|
||||||
},
|
|
||||||
"2": {
|
|
||||||
"shot1": 4,
|
|
||||||
"shot2": 8,
|
|
||||||
"shot3": 8,
|
|
||||||
"shot4": 5,
|
|
||||||
"shot5": 1
|
|
||||||
},
|
|
||||||
"3": {
|
|
||||||
"shot1": 3,
|
|
||||||
"shot2": 5,
|
|
||||||
"shot3": 2,
|
|
||||||
"shot4": 6,
|
|
||||||
"shot5": 7
|
|
||||||
},
|
|
||||||
"4": {
|
|
||||||
"shot1": 3,
|
|
||||||
"shot2": 2,
|
|
||||||
"shot3": 1,
|
|
||||||
"shot4": 1,
|
|
||||||
"shot5": 0
|
|
||||||
}
|
|
||||||
},
|
|
||||||
"total_score": 90,
|
|
||||||
"completed": true
|
|
||||||
},
|
|
||||||
"3": {
|
|
||||||
"name": "Ivan Tandler",
|
|
||||||
"targets": {
|
|
||||||
"1": {
|
|
||||||
"shot1": 8,
|
|
||||||
"shot2": 10,
|
|
||||||
"shot3": 0,
|
|
||||||
"shot4": 8,
|
|
||||||
"shot5": 0
|
|
||||||
},
|
|
||||||
"2": {
|
|
||||||
"shot1": 3,
|
|
||||||
"shot2": 9,
|
|
||||||
"shot3": 3,
|
|
||||||
"shot4": 6,
|
|
||||||
"shot5": 6
|
|
||||||
},
|
|
||||||
"3": {
|
|
||||||
"shot1": 10,
|
|
||||||
"shot2": 8,
|
|
||||||
"shot3": 5,
|
|
||||||
"shot4": 1,
|
|
||||||
"shot5": 10
|
|
||||||
},
|
|
||||||
"4": {
|
|
||||||
"shot1": 9,
|
|
||||||
"shot2": 7,
|
|
||||||
"shot3": 8,
|
|
||||||
"shot4": 6,
|
|
||||||
"shot5": 9
|
|
||||||
}
|
|
||||||
},
|
|
||||||
"total_score": 126,
|
|
||||||
"completed": true
|
|
||||||
},
|
|
||||||
"11": {
|
|
||||||
"name": "Rado Kefer",
|
|
||||||
"targets": {
|
|
||||||
"1": {
|
|
||||||
"shot1": 10,
|
|
||||||
"shot2": 7,
|
|
||||||
"shot3": 3,
|
|
||||||
"shot4": 8,
|
|
||||||
"shot5": 6
|
|
||||||
},
|
|
||||||
"2": {
|
|
||||||
"shot1": 9,
|
|
||||||
"shot2": 1,
|
|
||||||
"shot3": 5,
|
|
||||||
"shot4": 3,
|
|
||||||
"shot5": 8
|
|
||||||
},
|
|
||||||
"3": {
|
|
||||||
"shot1": 2,
|
|
||||||
"shot2": 3,
|
|
||||||
"shot3": 5,
|
|
||||||
"shot4": 2,
|
|
||||||
"shot5": 1
|
|
||||||
},
|
|
||||||
"4": {
|
|
||||||
"shot1": 1,
|
|
||||||
"shot2": 0,
|
|
||||||
"shot3": 3,
|
|
||||||
"shot4": 1,
|
|
||||||
"shot5": 6
|
|
||||||
}
|
|
||||||
},
|
|
||||||
"total_score": 84,
|
|
||||||
"completed": true
|
|
||||||
},
|
|
||||||
"45": {
|
|
||||||
"name": "Lidija Blimen",
|
|
||||||
"targets": {
|
|
||||||
"1": {
|
|
||||||
"shot1": 9,
|
|
||||||
"shot2": 1,
|
|
||||||
"shot3": 8,
|
|
||||||
"shot4": 5,
|
|
||||||
"shot5": 8
|
|
||||||
},
|
|
||||||
"2": {
|
|
||||||
"shot1": 5,
|
|
||||||
"shot2": 7,
|
|
||||||
"shot3": 8,
|
|
||||||
"shot4": 2,
|
|
||||||
"shot5": 9
|
|
||||||
},
|
|
||||||
"3": {
|
|
||||||
"shot1": 4,
|
|
||||||
"shot2": 10,
|
|
||||||
"shot3": 5,
|
|
||||||
"shot4": 7,
|
|
||||||
"shot5": 7
|
|
||||||
},
|
|
||||||
"4": {
|
|
||||||
"shot1": 0,
|
|
||||||
"shot2": 1,
|
|
||||||
"shot3": 0,
|
|
||||||
"shot4": 4,
|
|
||||||
"shot5": 0
|
|
||||||
}
|
|
||||||
},
|
|
||||||
"total_score": 100,
|
|
||||||
"completed": true
|
|
||||||
},
|
|
||||||
"47": {
|
|
||||||
"name": "Ljuba Mr\u0161ak",
|
|
||||||
"targets": {
|
|
||||||
"1": {
|
|
||||||
"shot1": 5,
|
|
||||||
"shot2": 0,
|
|
||||||
"shot3": 7,
|
|
||||||
"shot4": 4,
|
|
||||||
"shot5": 1
|
|
||||||
},
|
|
||||||
"2": {
|
|
||||||
"shot1": 2,
|
|
||||||
"shot2": 7,
|
|
||||||
"shot3": 3,
|
|
||||||
"shot4": 1,
|
|
||||||
"shot5": 4
|
|
||||||
},
|
|
||||||
"3": {
|
|
||||||
"shot1": 1,
|
|
||||||
"shot2": 4,
|
|
||||||
"shot3": 1,
|
|
||||||
"shot4": 3,
|
|
||||||
"shot5": 1
|
|
||||||
},
|
|
||||||
"4": {
|
|
||||||
"shot1": 0,
|
|
||||||
"shot2": 5,
|
|
||||||
"shot3": 3,
|
|
||||||
"shot4": 9,
|
|
||||||
"shot5": 7
|
|
||||||
}
|
|
||||||
},
|
|
||||||
"total_score": 68,
|
|
||||||
"completed": true
|
|
||||||
}
|
|
||||||
},
|
|
||||||
"tournament_finished": true,
|
|
||||||
"created_at": "2025-09-08T19:26:24.708574",
|
|
||||||
"finished_at": "2025-09-08T19:26:31.871139"
|
|
||||||
},
|
|
||||||
"archived_at": "2025-09-08T19:26:31.871173"
|
|
||||||
}
|
|
||||||
@@ -1,759 +0,0 @@
|
|||||||
{
|
|
||||||
"tournament": {
|
|
||||||
"rounds": [
|
|
||||||
{
|
|
||||||
"round_number": 1,
|
|
||||||
"players": [
|
|
||||||
{
|
|
||||||
"id": 5,
|
|
||||||
"name": "Jo\u017ee Verhnjak",
|
|
||||||
"enabled": true
|
|
||||||
},
|
|
||||||
{
|
|
||||||
"id": 20,
|
|
||||||
"name": "Jo\u017ee Preglav",
|
|
||||||
"enabled": true
|
|
||||||
},
|
|
||||||
{
|
|
||||||
"id": 12,
|
|
||||||
"name": "Matej Kvasnik",
|
|
||||||
"enabled": true
|
|
||||||
},
|
|
||||||
{
|
|
||||||
"id": 9,
|
|
||||||
"name": "Janez Bo\u017ei\u010d",
|
|
||||||
"enabled": true
|
|
||||||
},
|
|
||||||
{
|
|
||||||
"id": 21,
|
|
||||||
"name": "Marko Blimen",
|
|
||||||
"enabled": true
|
|
||||||
},
|
|
||||||
{
|
|
||||||
"id": 17,
|
|
||||||
"name": "Du\u0161an Onuk",
|
|
||||||
"enabled": true
|
|
||||||
}
|
|
||||||
],
|
|
||||||
"status": "pending"
|
|
||||||
},
|
|
||||||
{
|
|
||||||
"round_number": 2,
|
|
||||||
"players": [
|
|
||||||
{
|
|
||||||
"id": 45,
|
|
||||||
"name": "Lidija Blimen",
|
|
||||||
"enabled": true
|
|
||||||
},
|
|
||||||
{
|
|
||||||
"id": 47,
|
|
||||||
"name": "Ljuba Mr\u0161ak",
|
|
||||||
"enabled": true
|
|
||||||
},
|
|
||||||
{
|
|
||||||
"id": 3,
|
|
||||||
"name": "Ivan Tandler",
|
|
||||||
"enabled": true
|
|
||||||
},
|
|
||||||
{
|
|
||||||
"id": 49,
|
|
||||||
"name": "Jolanda Verhnjak",
|
|
||||||
"enabled": true
|
|
||||||
},
|
|
||||||
{
|
|
||||||
"id": 15,
|
|
||||||
"name": "Jan Pleterski",
|
|
||||||
"enabled": true
|
|
||||||
},
|
|
||||||
{
|
|
||||||
"id": 1,
|
|
||||||
"name": "Domen Pleterski",
|
|
||||||
"enabled": true
|
|
||||||
}
|
|
||||||
],
|
|
||||||
"status": "waiting"
|
|
||||||
},
|
|
||||||
{
|
|
||||||
"round_number": 3,
|
|
||||||
"players": [
|
|
||||||
{
|
|
||||||
"id": 7,
|
|
||||||
"name": "Branko Poker\u017enik",
|
|
||||||
"enabled": true
|
|
||||||
},
|
|
||||||
{
|
|
||||||
"id": 4,
|
|
||||||
"name": "Mateja Pleterski",
|
|
||||||
"enabled": true
|
|
||||||
},
|
|
||||||
{
|
|
||||||
"id": 11,
|
|
||||||
"name": "Rado Kefer",
|
|
||||||
"enabled": true
|
|
||||||
},
|
|
||||||
{
|
|
||||||
"id": 44,
|
|
||||||
"name": "Anka Ka\u010dnik",
|
|
||||||
"enabled": true
|
|
||||||
},
|
|
||||||
{
|
|
||||||
"id": 46,
|
|
||||||
"name": "Tijana \u0160tumpfl",
|
|
||||||
"enabled": true
|
|
||||||
},
|
|
||||||
{
|
|
||||||
"id": 48,
|
|
||||||
"name": "Janja Salcman",
|
|
||||||
"enabled": true
|
|
||||||
}
|
|
||||||
],
|
|
||||||
"status": "waiting"
|
|
||||||
}
|
|
||||||
],
|
|
||||||
"created_at": "2025-09-08T19:27:18.397859",
|
|
||||||
"total_players": 18,
|
|
||||||
"total_rounds": 3,
|
|
||||||
"current_round": 1,
|
|
||||||
"tournament_type": "4_targets"
|
|
||||||
},
|
|
||||||
"results": {
|
|
||||||
"tournament_id": "2025-09-08T19:27:18.397859",
|
|
||||||
"tournament_type": "4_targets",
|
|
||||||
"participants": {
|
|
||||||
"5": {
|
|
||||||
"name": "Jo\u017ee Verhnjak",
|
|
||||||
"targets": {
|
|
||||||
"1": {
|
|
||||||
"shot1": 6,
|
|
||||||
"shot2": 0,
|
|
||||||
"shot3": 1,
|
|
||||||
"shot4": 2,
|
|
||||||
"shot5": 0
|
|
||||||
},
|
|
||||||
"2": {
|
|
||||||
"shot1": 4,
|
|
||||||
"shot2": 9,
|
|
||||||
"shot3": 1,
|
|
||||||
"shot4": 4,
|
|
||||||
"shot5": 3
|
|
||||||
},
|
|
||||||
"3": {
|
|
||||||
"shot1": 3,
|
|
||||||
"shot2": 6,
|
|
||||||
"shot3": 8,
|
|
||||||
"shot4": 6,
|
|
||||||
"shot5": 3
|
|
||||||
},
|
|
||||||
"4": {
|
|
||||||
"shot1": 8,
|
|
||||||
"shot2": 7,
|
|
||||||
"shot3": 8,
|
|
||||||
"shot4": 1,
|
|
||||||
"shot5": 5
|
|
||||||
}
|
|
||||||
},
|
|
||||||
"total_score": 85,
|
|
||||||
"completed": true
|
|
||||||
},
|
|
||||||
"20": {
|
|
||||||
"name": "Jo\u017ee Preglav",
|
|
||||||
"targets": {
|
|
||||||
"1": {
|
|
||||||
"shot1": 3,
|
|
||||||
"shot2": 0,
|
|
||||||
"shot3": 3,
|
|
||||||
"shot4": 5,
|
|
||||||
"shot5": 3
|
|
||||||
},
|
|
||||||
"2": {
|
|
||||||
"shot1": 1,
|
|
||||||
"shot2": 4,
|
|
||||||
"shot3": 2,
|
|
||||||
"shot4": 0,
|
|
||||||
"shot5": 1
|
|
||||||
},
|
|
||||||
"3": {
|
|
||||||
"shot1": 6,
|
|
||||||
"shot2": 3,
|
|
||||||
"shot3": 8,
|
|
||||||
"shot4": 2,
|
|
||||||
"shot5": 5
|
|
||||||
},
|
|
||||||
"4": {
|
|
||||||
"shot1": 4,
|
|
||||||
"shot2": 6,
|
|
||||||
"shot3": 2,
|
|
||||||
"shot4": 9,
|
|
||||||
"shot5": 2
|
|
||||||
}
|
|
||||||
},
|
|
||||||
"total_score": 69,
|
|
||||||
"completed": true
|
|
||||||
},
|
|
||||||
"12": {
|
|
||||||
"name": "Matej Kvasnik",
|
|
||||||
"targets": {
|
|
||||||
"1": {
|
|
||||||
"shot1": 1,
|
|
||||||
"shot2": 4,
|
|
||||||
"shot3": 2,
|
|
||||||
"shot4": 6,
|
|
||||||
"shot5": 6
|
|
||||||
},
|
|
||||||
"2": {
|
|
||||||
"shot1": 5,
|
|
||||||
"shot2": 1,
|
|
||||||
"shot3": 2,
|
|
||||||
"shot4": 0,
|
|
||||||
"shot5": 8
|
|
||||||
},
|
|
||||||
"3": {
|
|
||||||
"shot1": 1,
|
|
||||||
"shot2": 4,
|
|
||||||
"shot3": 7,
|
|
||||||
"shot4": 3,
|
|
||||||
"shot5": 10
|
|
||||||
},
|
|
||||||
"4": {
|
|
||||||
"shot1": 0,
|
|
||||||
"shot2": 3,
|
|
||||||
"shot3": 3,
|
|
||||||
"shot4": 9,
|
|
||||||
"shot5": 5
|
|
||||||
}
|
|
||||||
},
|
|
||||||
"total_score": 80,
|
|
||||||
"completed": true
|
|
||||||
},
|
|
||||||
"9": {
|
|
||||||
"name": "Janez Bo\u017ei\u010d",
|
|
||||||
"targets": {
|
|
||||||
"1": {
|
|
||||||
"shot1": 10,
|
|
||||||
"shot2": 0,
|
|
||||||
"shot3": 6,
|
|
||||||
"shot4": 7,
|
|
||||||
"shot5": 6
|
|
||||||
},
|
|
||||||
"2": {
|
|
||||||
"shot1": 0,
|
|
||||||
"shot2": 7,
|
|
||||||
"shot3": 10,
|
|
||||||
"shot4": 10,
|
|
||||||
"shot5": 4
|
|
||||||
},
|
|
||||||
"3": {
|
|
||||||
"shot1": 9,
|
|
||||||
"shot2": 1,
|
|
||||||
"shot3": 3,
|
|
||||||
"shot4": 9,
|
|
||||||
"shot5": 6
|
|
||||||
},
|
|
||||||
"4": {
|
|
||||||
"shot1": 1,
|
|
||||||
"shot2": 9,
|
|
||||||
"shot3": 6,
|
|
||||||
"shot4": 5,
|
|
||||||
"shot5": 9
|
|
||||||
}
|
|
||||||
},
|
|
||||||
"total_score": 118,
|
|
||||||
"completed": true
|
|
||||||
},
|
|
||||||
"21": {
|
|
||||||
"name": "Marko Blimen",
|
|
||||||
"targets": {
|
|
||||||
"1": {
|
|
||||||
"shot1": 9,
|
|
||||||
"shot2": 8,
|
|
||||||
"shot3": 3,
|
|
||||||
"shot4": 0,
|
|
||||||
"shot5": 4
|
|
||||||
},
|
|
||||||
"2": {
|
|
||||||
"shot1": 9,
|
|
||||||
"shot2": 9,
|
|
||||||
"shot3": 9,
|
|
||||||
"shot4": 10,
|
|
||||||
"shot5": 3
|
|
||||||
},
|
|
||||||
"3": {
|
|
||||||
"shot1": 9,
|
|
||||||
"shot2": 4,
|
|
||||||
"shot3": 8,
|
|
||||||
"shot4": 10,
|
|
||||||
"shot5": 9
|
|
||||||
},
|
|
||||||
"4": {
|
|
||||||
"shot1": 4,
|
|
||||||
"shot2": 8,
|
|
||||||
"shot3": 1,
|
|
||||||
"shot4": 1,
|
|
||||||
"shot5": 0
|
|
||||||
}
|
|
||||||
},
|
|
||||||
"total_score": 118,
|
|
||||||
"completed": true
|
|
||||||
},
|
|
||||||
"17": {
|
|
||||||
"name": "Du\u0161an Onuk",
|
|
||||||
"targets": {
|
|
||||||
"1": {
|
|
||||||
"shot1": 5,
|
|
||||||
"shot2": 10,
|
|
||||||
"shot3": 8,
|
|
||||||
"shot4": 5,
|
|
||||||
"shot5": 1
|
|
||||||
},
|
|
||||||
"2": {
|
|
||||||
"shot1": 6,
|
|
||||||
"shot2": 3,
|
|
||||||
"shot3": 4,
|
|
||||||
"shot4": 9,
|
|
||||||
"shot5": 6
|
|
||||||
},
|
|
||||||
"3": {
|
|
||||||
"shot1": 7,
|
|
||||||
"shot2": 8,
|
|
||||||
"shot3": 1,
|
|
||||||
"shot4": 3,
|
|
||||||
"shot5": 4
|
|
||||||
},
|
|
||||||
"4": {
|
|
||||||
"shot1": 1,
|
|
||||||
"shot2": 4,
|
|
||||||
"shot3": 6,
|
|
||||||
"shot4": 9,
|
|
||||||
"shot5": 0
|
|
||||||
}
|
|
||||||
},
|
|
||||||
"total_score": 100,
|
|
||||||
"completed": true
|
|
||||||
},
|
|
||||||
"45": {
|
|
||||||
"name": "Lidija Blimen",
|
|
||||||
"targets": {
|
|
||||||
"1": {
|
|
||||||
"shot1": 1,
|
|
||||||
"shot2": 6,
|
|
||||||
"shot3": 0,
|
|
||||||
"shot4": 0,
|
|
||||||
"shot5": 8
|
|
||||||
},
|
|
||||||
"2": {
|
|
||||||
"shot1": 7,
|
|
||||||
"shot2": 7,
|
|
||||||
"shot3": 2,
|
|
||||||
"shot4": 10,
|
|
||||||
"shot5": 2
|
|
||||||
},
|
|
||||||
"3": {
|
|
||||||
"shot1": 2,
|
|
||||||
"shot2": 10,
|
|
||||||
"shot3": 1,
|
|
||||||
"shot4": 8,
|
|
||||||
"shot5": 10
|
|
||||||
},
|
|
||||||
"4": {
|
|
||||||
"shot1": 2,
|
|
||||||
"shot2": 8,
|
|
||||||
"shot3": 0,
|
|
||||||
"shot4": 8,
|
|
||||||
"shot5": 1
|
|
||||||
}
|
|
||||||
},
|
|
||||||
"total_score": 93,
|
|
||||||
"completed": true
|
|
||||||
},
|
|
||||||
"47": {
|
|
||||||
"name": "Ljuba Mr\u0161ak",
|
|
||||||
"targets": {
|
|
||||||
"1": {
|
|
||||||
"shot1": 9,
|
|
||||||
"shot2": 7,
|
|
||||||
"shot3": 0,
|
|
||||||
"shot4": 8,
|
|
||||||
"shot5": 2
|
|
||||||
},
|
|
||||||
"2": {
|
|
||||||
"shot1": 0,
|
|
||||||
"shot2": 0,
|
|
||||||
"shot3": 5,
|
|
||||||
"shot4": 4,
|
|
||||||
"shot5": 4
|
|
||||||
},
|
|
||||||
"3": {
|
|
||||||
"shot1": 4,
|
|
||||||
"shot2": 3,
|
|
||||||
"shot3": 9,
|
|
||||||
"shot4": 0,
|
|
||||||
"shot5": 0
|
|
||||||
},
|
|
||||||
"4": {
|
|
||||||
"shot1": 0,
|
|
||||||
"shot2": 3,
|
|
||||||
"shot3": 8,
|
|
||||||
"shot4": 7,
|
|
||||||
"shot5": 8
|
|
||||||
}
|
|
||||||
},
|
|
||||||
"total_score": 81,
|
|
||||||
"completed": true
|
|
||||||
},
|
|
||||||
"3": {
|
|
||||||
"name": "Ivan Tandler",
|
|
||||||
"targets": {
|
|
||||||
"1": {
|
|
||||||
"shot1": 7,
|
|
||||||
"shot2": 3,
|
|
||||||
"shot3": 5,
|
|
||||||
"shot4": 1,
|
|
||||||
"shot5": 0
|
|
||||||
},
|
|
||||||
"2": {
|
|
||||||
"shot1": 0,
|
|
||||||
"shot2": 5,
|
|
||||||
"shot3": 8,
|
|
||||||
"shot4": 10,
|
|
||||||
"shot5": 9
|
|
||||||
},
|
|
||||||
"3": {
|
|
||||||
"shot1": 7,
|
|
||||||
"shot2": 0,
|
|
||||||
"shot3": 0,
|
|
||||||
"shot4": 3,
|
|
||||||
"shot5": 6
|
|
||||||
},
|
|
||||||
"4": {
|
|
||||||
"shot1": 1,
|
|
||||||
"shot2": 8,
|
|
||||||
"shot3": 5,
|
|
||||||
"shot4": 0,
|
|
||||||
"shot5": 8
|
|
||||||
}
|
|
||||||
},
|
|
||||||
"total_score": 86,
|
|
||||||
"completed": true
|
|
||||||
},
|
|
||||||
"49": {
|
|
||||||
"name": "Jolanda Verhnjak",
|
|
||||||
"targets": {
|
|
||||||
"1": {
|
|
||||||
"shot1": 7,
|
|
||||||
"shot2": 2,
|
|
||||||
"shot3": 0,
|
|
||||||
"shot4": 8,
|
|
||||||
"shot5": 3
|
|
||||||
},
|
|
||||||
"2": {
|
|
||||||
"shot1": 10,
|
|
||||||
"shot2": 9,
|
|
||||||
"shot3": 7,
|
|
||||||
"shot4": 8,
|
|
||||||
"shot5": 6
|
|
||||||
},
|
|
||||||
"3": {
|
|
||||||
"shot1": 0,
|
|
||||||
"shot2": 2,
|
|
||||||
"shot3": 5,
|
|
||||||
"shot4": 3,
|
|
||||||
"shot5": 9
|
|
||||||
},
|
|
||||||
"4": {
|
|
||||||
"shot1": 2,
|
|
||||||
"shot2": 5,
|
|
||||||
"shot3": 10,
|
|
||||||
"shot4": 3,
|
|
||||||
"shot5": 5
|
|
||||||
}
|
|
||||||
},
|
|
||||||
"total_score": 104,
|
|
||||||
"completed": true
|
|
||||||
},
|
|
||||||
"15": {
|
|
||||||
"name": "Jan Pleterski",
|
|
||||||
"targets": {
|
|
||||||
"1": {
|
|
||||||
"shot1": 3,
|
|
||||||
"shot2": 0,
|
|
||||||
"shot3": 3,
|
|
||||||
"shot4": 2,
|
|
||||||
"shot5": 1
|
|
||||||
},
|
|
||||||
"2": {
|
|
||||||
"shot1": 10,
|
|
||||||
"shot2": 2,
|
|
||||||
"shot3": 10,
|
|
||||||
"shot4": 0,
|
|
||||||
"shot5": 6
|
|
||||||
},
|
|
||||||
"3": {
|
|
||||||
"shot1": 2,
|
|
||||||
"shot2": 9,
|
|
||||||
"shot3": 0,
|
|
||||||
"shot4": 4,
|
|
||||||
"shot5": 4
|
|
||||||
},
|
|
||||||
"4": {
|
|
||||||
"shot1": 2,
|
|
||||||
"shot2": 3,
|
|
||||||
"shot3": 8,
|
|
||||||
"shot4": 9,
|
|
||||||
"shot5": 5
|
|
||||||
}
|
|
||||||
},
|
|
||||||
"total_score": 83,
|
|
||||||
"completed": true
|
|
||||||
},
|
|
||||||
"1": {
|
|
||||||
"name": "Domen Pleterski",
|
|
||||||
"targets": {
|
|
||||||
"1": {
|
|
||||||
"shot1": 8,
|
|
||||||
"shot2": 5,
|
|
||||||
"shot3": 10,
|
|
||||||
"shot4": 8,
|
|
||||||
"shot5": 4
|
|
||||||
},
|
|
||||||
"2": {
|
|
||||||
"shot1": 0,
|
|
||||||
"shot2": 3,
|
|
||||||
"shot3": 6,
|
|
||||||
"shot4": 5,
|
|
||||||
"shot5": 2
|
|
||||||
},
|
|
||||||
"3": {
|
|
||||||
"shot1": 8,
|
|
||||||
"shot2": 0,
|
|
||||||
"shot3": 10,
|
|
||||||
"shot4": 2,
|
|
||||||
"shot5": 0
|
|
||||||
},
|
|
||||||
"4": {
|
|
||||||
"shot1": 0,
|
|
||||||
"shot2": 6,
|
|
||||||
"shot3": 7,
|
|
||||||
"shot4": 4,
|
|
||||||
"shot5": 8
|
|
||||||
}
|
|
||||||
},
|
|
||||||
"total_score": 96,
|
|
||||||
"completed": true
|
|
||||||
},
|
|
||||||
"7": {
|
|
||||||
"name": "Branko Poker\u017enik",
|
|
||||||
"targets": {
|
|
||||||
"1": {
|
|
||||||
"shot1": 9,
|
|
||||||
"shot2": 8,
|
|
||||||
"shot3": 4,
|
|
||||||
"shot4": 1,
|
|
||||||
"shot5": 3
|
|
||||||
},
|
|
||||||
"2": {
|
|
||||||
"shot1": 4,
|
|
||||||
"shot2": 5,
|
|
||||||
"shot3": 10,
|
|
||||||
"shot4": 0,
|
|
||||||
"shot5": 0
|
|
||||||
},
|
|
||||||
"3": {
|
|
||||||
"shot1": 6,
|
|
||||||
"shot2": 2,
|
|
||||||
"shot3": 9,
|
|
||||||
"shot4": 4,
|
|
||||||
"shot5": 2
|
|
||||||
},
|
|
||||||
"4": {
|
|
||||||
"shot1": 2,
|
|
||||||
"shot2": 8,
|
|
||||||
"shot3": 1,
|
|
||||||
"shot4": 8,
|
|
||||||
"shot5": 3
|
|
||||||
}
|
|
||||||
},
|
|
||||||
"total_score": 89,
|
|
||||||
"completed": true
|
|
||||||
},
|
|
||||||
"4": {
|
|
||||||
"name": "Mateja Pleterski",
|
|
||||||
"targets": {
|
|
||||||
"1": {
|
|
||||||
"shot1": 9,
|
|
||||||
"shot2": 10,
|
|
||||||
"shot3": 1,
|
|
||||||
"shot4": 6,
|
|
||||||
"shot5": 8
|
|
||||||
},
|
|
||||||
"2": {
|
|
||||||
"shot1": 10,
|
|
||||||
"shot2": 1,
|
|
||||||
"shot3": 0,
|
|
||||||
"shot4": 9,
|
|
||||||
"shot5": 10
|
|
||||||
},
|
|
||||||
"3": {
|
|
||||||
"shot1": 0,
|
|
||||||
"shot2": 1,
|
|
||||||
"shot3": 5,
|
|
||||||
"shot4": 5,
|
|
||||||
"shot5": 0
|
|
||||||
},
|
|
||||||
"4": {
|
|
||||||
"shot1": 3,
|
|
||||||
"shot2": 0,
|
|
||||||
"shot3": 10,
|
|
||||||
"shot4": 4,
|
|
||||||
"shot5": 2
|
|
||||||
}
|
|
||||||
},
|
|
||||||
"total_score": 94,
|
|
||||||
"completed": true
|
|
||||||
},
|
|
||||||
"11": {
|
|
||||||
"name": "Rado Kefer",
|
|
||||||
"targets": {
|
|
||||||
"1": {
|
|
||||||
"shot1": 7,
|
|
||||||
"shot2": 2,
|
|
||||||
"shot3": 7,
|
|
||||||
"shot4": 7,
|
|
||||||
"shot5": 9
|
|
||||||
},
|
|
||||||
"2": {
|
|
||||||
"shot1": 7,
|
|
||||||
"shot2": 8,
|
|
||||||
"shot3": 4,
|
|
||||||
"shot4": 6,
|
|
||||||
"shot5": 0
|
|
||||||
},
|
|
||||||
"3": {
|
|
||||||
"shot1": 2,
|
|
||||||
"shot2": 8,
|
|
||||||
"shot3": 5,
|
|
||||||
"shot4": 2,
|
|
||||||
"shot5": 10
|
|
||||||
},
|
|
||||||
"4": {
|
|
||||||
"shot1": 6,
|
|
||||||
"shot2": 5,
|
|
||||||
"shot3": 6,
|
|
||||||
"shot4": 5,
|
|
||||||
"shot5": 10
|
|
||||||
}
|
|
||||||
},
|
|
||||||
"total_score": 116,
|
|
||||||
"completed": true
|
|
||||||
},
|
|
||||||
"44": {
|
|
||||||
"name": "Anka Ka\u010dnik",
|
|
||||||
"targets": {
|
|
||||||
"1": {
|
|
||||||
"shot1": 10,
|
|
||||||
"shot2": 1,
|
|
||||||
"shot3": 5,
|
|
||||||
"shot4": 1,
|
|
||||||
"shot5": 8
|
|
||||||
},
|
|
||||||
"2": {
|
|
||||||
"shot1": 3,
|
|
||||||
"shot2": 4,
|
|
||||||
"shot3": 3,
|
|
||||||
"shot4": 8,
|
|
||||||
"shot5": 6
|
|
||||||
},
|
|
||||||
"3": {
|
|
||||||
"shot1": 5,
|
|
||||||
"shot2": 7,
|
|
||||||
"shot3": 10,
|
|
||||||
"shot4": 2,
|
|
||||||
"shot5": 6
|
|
||||||
},
|
|
||||||
"4": {
|
|
||||||
"shot1": 10,
|
|
||||||
"shot2": 8,
|
|
||||||
"shot3": 2,
|
|
||||||
"shot4": 9,
|
|
||||||
"shot5": 7
|
|
||||||
}
|
|
||||||
},
|
|
||||||
"total_score": 115,
|
|
||||||
"completed": true
|
|
||||||
},
|
|
||||||
"46": {
|
|
||||||
"name": "Tijana \u0160tumpfl",
|
|
||||||
"targets": {
|
|
||||||
"1": {
|
|
||||||
"shot1": 8,
|
|
||||||
"shot2": 6,
|
|
||||||
"shot3": 5,
|
|
||||||
"shot4": 0,
|
|
||||||
"shot5": 2
|
|
||||||
},
|
|
||||||
"2": {
|
|
||||||
"shot1": 3,
|
|
||||||
"shot2": 8,
|
|
||||||
"shot3": 6,
|
|
||||||
"shot4": 4,
|
|
||||||
"shot5": 1
|
|
||||||
},
|
|
||||||
"3": {
|
|
||||||
"shot1": 10,
|
|
||||||
"shot2": 10,
|
|
||||||
"shot3": 8,
|
|
||||||
"shot4": 7,
|
|
||||||
"shot5": 4
|
|
||||||
},
|
|
||||||
"4": {
|
|
||||||
"shot1": 7,
|
|
||||||
"shot2": 2,
|
|
||||||
"shot3": 2,
|
|
||||||
"shot4": 4,
|
|
||||||
"shot5": 3
|
|
||||||
}
|
|
||||||
},
|
|
||||||
"total_score": 100,
|
|
||||||
"completed": true
|
|
||||||
},
|
|
||||||
"48": {
|
|
||||||
"name": "Janja Salcman",
|
|
||||||
"targets": {
|
|
||||||
"1": {
|
|
||||||
"shot1": 5,
|
|
||||||
"shot2": 0,
|
|
||||||
"shot3": 1,
|
|
||||||
"shot4": 1,
|
|
||||||
"shot5": 4
|
|
||||||
},
|
|
||||||
"2": {
|
|
||||||
"shot1": 7,
|
|
||||||
"shot2": 4,
|
|
||||||
"shot3": 10,
|
|
||||||
"shot4": 2,
|
|
||||||
"shot5": 6
|
|
||||||
},
|
|
||||||
"3": {
|
|
||||||
"shot1": 6,
|
|
||||||
"shot2": 3,
|
|
||||||
"shot3": 2,
|
|
||||||
"shot4": 3,
|
|
||||||
"shot5": 5
|
|
||||||
},
|
|
||||||
"4": {
|
|
||||||
"shot1": 0,
|
|
||||||
"shot2": 8,
|
|
||||||
"shot3": 9,
|
|
||||||
"shot4": 6,
|
|
||||||
"shot5": 3
|
|
||||||
}
|
|
||||||
},
|
|
||||||
"total_score": 85,
|
|
||||||
"completed": true
|
|
||||||
}
|
|
||||||
},
|
|
||||||
"tournament_finished": true,
|
|
||||||
"created_at": "2025-09-08T19:27:18.398031",
|
|
||||||
"finished_at": "2025-09-08T19:27:27.631332"
|
|
||||||
},
|
|
||||||
"archived_at": "2025-09-08T19:27:27.631357"
|
|
||||||
}
|
|
||||||
@@ -1,759 +0,0 @@
|
|||||||
{
|
|
||||||
"tournament": {
|
|
||||||
"rounds": [
|
|
||||||
{
|
|
||||||
"round_number": 1,
|
|
||||||
"players": [
|
|
||||||
{
|
|
||||||
"id": 49,
|
|
||||||
"name": "Jolanda Verhnjak",
|
|
||||||
"enabled": true
|
|
||||||
},
|
|
||||||
{
|
|
||||||
"id": 7,
|
|
||||||
"name": "Branko Poker\u017enik",
|
|
||||||
"enabled": true
|
|
||||||
},
|
|
||||||
{
|
|
||||||
"id": 3,
|
|
||||||
"name": "Ivan Tandler",
|
|
||||||
"enabled": true
|
|
||||||
},
|
|
||||||
{
|
|
||||||
"id": 46,
|
|
||||||
"name": "Tijana \u0160tumpfl",
|
|
||||||
"enabled": true
|
|
||||||
},
|
|
||||||
{
|
|
||||||
"id": 15,
|
|
||||||
"name": "Jan Pleterski",
|
|
||||||
"enabled": true
|
|
||||||
},
|
|
||||||
{
|
|
||||||
"id": 17,
|
|
||||||
"name": "Du\u0161an Onuk",
|
|
||||||
"enabled": true
|
|
||||||
}
|
|
||||||
],
|
|
||||||
"status": "pending"
|
|
||||||
},
|
|
||||||
{
|
|
||||||
"round_number": 2,
|
|
||||||
"players": [
|
|
||||||
{
|
|
||||||
"id": 12,
|
|
||||||
"name": "Matej Kvasnik",
|
|
||||||
"enabled": true
|
|
||||||
},
|
|
||||||
{
|
|
||||||
"id": 9,
|
|
||||||
"name": "Janez Bo\u017ei\u010d",
|
|
||||||
"enabled": true
|
|
||||||
},
|
|
||||||
{
|
|
||||||
"id": 4,
|
|
||||||
"name": "Mateja Pleterski",
|
|
||||||
"enabled": true
|
|
||||||
},
|
|
||||||
{
|
|
||||||
"id": 21,
|
|
||||||
"name": "Marko Blimen",
|
|
||||||
"enabled": true
|
|
||||||
},
|
|
||||||
{
|
|
||||||
"id": 20,
|
|
||||||
"name": "Jo\u017ee Preglav",
|
|
||||||
"enabled": true
|
|
||||||
},
|
|
||||||
{
|
|
||||||
"id": 11,
|
|
||||||
"name": "Rado Kefer",
|
|
||||||
"enabled": true
|
|
||||||
}
|
|
||||||
],
|
|
||||||
"status": "waiting"
|
|
||||||
},
|
|
||||||
{
|
|
||||||
"round_number": 3,
|
|
||||||
"players": [
|
|
||||||
{
|
|
||||||
"id": 47,
|
|
||||||
"name": "Ljuba Mr\u0161ak",
|
|
||||||
"enabled": true
|
|
||||||
},
|
|
||||||
{
|
|
||||||
"id": 48,
|
|
||||||
"name": "Janja Salcman",
|
|
||||||
"enabled": true
|
|
||||||
},
|
|
||||||
{
|
|
||||||
"id": 45,
|
|
||||||
"name": "Lidija Blimen",
|
|
||||||
"enabled": true
|
|
||||||
},
|
|
||||||
{
|
|
||||||
"id": 1,
|
|
||||||
"name": "Domen Pleterski",
|
|
||||||
"enabled": true
|
|
||||||
},
|
|
||||||
{
|
|
||||||
"id": 5,
|
|
||||||
"name": "Jo\u017ee Verhnjak",
|
|
||||||
"enabled": true
|
|
||||||
},
|
|
||||||
{
|
|
||||||
"id": 44,
|
|
||||||
"name": "Anka Ka\u010dnik",
|
|
||||||
"enabled": true
|
|
||||||
}
|
|
||||||
],
|
|
||||||
"status": "waiting"
|
|
||||||
}
|
|
||||||
],
|
|
||||||
"created_at": "2025-09-08T19:39:27.077222",
|
|
||||||
"total_players": 18,
|
|
||||||
"total_rounds": 3,
|
|
||||||
"current_round": 1,
|
|
||||||
"tournament_type": "4_targets"
|
|
||||||
},
|
|
||||||
"results": {
|
|
||||||
"tournament_id": "2025-09-08T19:39:27.077222",
|
|
||||||
"tournament_type": "4_targets",
|
|
||||||
"participants": {
|
|
||||||
"49": {
|
|
||||||
"name": "Jolanda Verhnjak",
|
|
||||||
"targets": {
|
|
||||||
"1": {
|
|
||||||
"shot1": 6,
|
|
||||||
"shot2": 10,
|
|
||||||
"shot3": 6,
|
|
||||||
"shot4": 3,
|
|
||||||
"shot5": 7
|
|
||||||
},
|
|
||||||
"2": {
|
|
||||||
"shot1": 6,
|
|
||||||
"shot2": 2,
|
|
||||||
"shot3": 1,
|
|
||||||
"shot4": 10,
|
|
||||||
"shot5": 0
|
|
||||||
},
|
|
||||||
"3": {
|
|
||||||
"shot1": 5,
|
|
||||||
"shot2": 5,
|
|
||||||
"shot3": 0,
|
|
||||||
"shot4": 3,
|
|
||||||
"shot5": 9
|
|
||||||
},
|
|
||||||
"4": {
|
|
||||||
"shot1": 9,
|
|
||||||
"shot2": 6,
|
|
||||||
"shot3": 8,
|
|
||||||
"shot4": 4,
|
|
||||||
"shot5": 8
|
|
||||||
}
|
|
||||||
},
|
|
||||||
"total_score": 108,
|
|
||||||
"completed": true
|
|
||||||
},
|
|
||||||
"7": {
|
|
||||||
"name": "Branko Poker\u017enik",
|
|
||||||
"targets": {
|
|
||||||
"1": {
|
|
||||||
"shot1": 10,
|
|
||||||
"shot2": 10,
|
|
||||||
"shot3": 6,
|
|
||||||
"shot4": 0,
|
|
||||||
"shot5": 9
|
|
||||||
},
|
|
||||||
"2": {
|
|
||||||
"shot1": 1,
|
|
||||||
"shot2": 2,
|
|
||||||
"shot3": 1,
|
|
||||||
"shot4": 4,
|
|
||||||
"shot5": 6
|
|
||||||
},
|
|
||||||
"3": {
|
|
||||||
"shot1": 3,
|
|
||||||
"shot2": 10,
|
|
||||||
"shot3": 5,
|
|
||||||
"shot4": 7,
|
|
||||||
"shot5": 7
|
|
||||||
},
|
|
||||||
"4": {
|
|
||||||
"shot1": 7,
|
|
||||||
"shot2": 7,
|
|
||||||
"shot3": 3,
|
|
||||||
"shot4": 2,
|
|
||||||
"shot5": 10
|
|
||||||
}
|
|
||||||
},
|
|
||||||
"total_score": 110,
|
|
||||||
"completed": true
|
|
||||||
},
|
|
||||||
"3": {
|
|
||||||
"name": "Ivan Tandler",
|
|
||||||
"targets": {
|
|
||||||
"1": {
|
|
||||||
"shot1": 6,
|
|
||||||
"shot2": 4,
|
|
||||||
"shot3": 1,
|
|
||||||
"shot4": 2,
|
|
||||||
"shot5": 0
|
|
||||||
},
|
|
||||||
"2": {
|
|
||||||
"shot1": 7,
|
|
||||||
"shot2": 6,
|
|
||||||
"shot3": 5,
|
|
||||||
"shot4": 10,
|
|
||||||
"shot5": 8
|
|
||||||
},
|
|
||||||
"3": {
|
|
||||||
"shot1": 4,
|
|
||||||
"shot2": 1,
|
|
||||||
"shot3": 4,
|
|
||||||
"shot4": 3,
|
|
||||||
"shot5": 7
|
|
||||||
},
|
|
||||||
"4": {
|
|
||||||
"shot1": 7,
|
|
||||||
"shot2": 2,
|
|
||||||
"shot3": 1,
|
|
||||||
"shot4": 1,
|
|
||||||
"shot5": 10
|
|
||||||
}
|
|
||||||
},
|
|
||||||
"total_score": 89,
|
|
||||||
"completed": true
|
|
||||||
},
|
|
||||||
"46": {
|
|
||||||
"name": "Tijana \u0160tumpfl",
|
|
||||||
"targets": {
|
|
||||||
"1": {
|
|
||||||
"shot1": 7,
|
|
||||||
"shot2": 10,
|
|
||||||
"shot3": 3,
|
|
||||||
"shot4": 7,
|
|
||||||
"shot5": 6
|
|
||||||
},
|
|
||||||
"2": {
|
|
||||||
"shot1": 5,
|
|
||||||
"shot2": 0,
|
|
||||||
"shot3": 10,
|
|
||||||
"shot4": 5,
|
|
||||||
"shot5": 1
|
|
||||||
},
|
|
||||||
"3": {
|
|
||||||
"shot1": 7,
|
|
||||||
"shot2": 9,
|
|
||||||
"shot3": 8,
|
|
||||||
"shot4": 6,
|
|
||||||
"shot5": 1
|
|
||||||
},
|
|
||||||
"4": {
|
|
||||||
"shot1": 3,
|
|
||||||
"shot2": 9,
|
|
||||||
"shot3": 0,
|
|
||||||
"shot4": 5,
|
|
||||||
"shot5": 0
|
|
||||||
}
|
|
||||||
},
|
|
||||||
"total_score": 102,
|
|
||||||
"completed": true
|
|
||||||
},
|
|
||||||
"15": {
|
|
||||||
"name": "Jan Pleterski",
|
|
||||||
"targets": {
|
|
||||||
"1": {
|
|
||||||
"shot1": 1,
|
|
||||||
"shot2": 4,
|
|
||||||
"shot3": 3,
|
|
||||||
"shot4": 1,
|
|
||||||
"shot5": 6
|
|
||||||
},
|
|
||||||
"2": {
|
|
||||||
"shot1": 5,
|
|
||||||
"shot2": 8,
|
|
||||||
"shot3": 1,
|
|
||||||
"shot4": 9,
|
|
||||||
"shot5": 2
|
|
||||||
},
|
|
||||||
"3": {
|
|
||||||
"shot1": 6,
|
|
||||||
"shot2": 9,
|
|
||||||
"shot3": 4,
|
|
||||||
"shot4": 1,
|
|
||||||
"shot5": 7
|
|
||||||
},
|
|
||||||
"4": {
|
|
||||||
"shot1": 5,
|
|
||||||
"shot2": 0,
|
|
||||||
"shot3": 2,
|
|
||||||
"shot4": 7,
|
|
||||||
"shot5": 4
|
|
||||||
}
|
|
||||||
},
|
|
||||||
"total_score": 85,
|
|
||||||
"completed": true
|
|
||||||
},
|
|
||||||
"17": {
|
|
||||||
"name": "Du\u0161an Onuk",
|
|
||||||
"targets": {
|
|
||||||
"1": {
|
|
||||||
"shot1": 6,
|
|
||||||
"shot2": 7,
|
|
||||||
"shot3": 8,
|
|
||||||
"shot4": 2,
|
|
||||||
"shot5": 8
|
|
||||||
},
|
|
||||||
"2": {
|
|
||||||
"shot1": 10,
|
|
||||||
"shot2": 7,
|
|
||||||
"shot3": 6,
|
|
||||||
"shot4": 9,
|
|
||||||
"shot5": 0
|
|
||||||
},
|
|
||||||
"3": {
|
|
||||||
"shot1": 1,
|
|
||||||
"shot2": 9,
|
|
||||||
"shot3": 0,
|
|
||||||
"shot4": 6,
|
|
||||||
"shot5": 4
|
|
||||||
},
|
|
||||||
"4": {
|
|
||||||
"shot1": 9,
|
|
||||||
"shot2": 5,
|
|
||||||
"shot3": 6,
|
|
||||||
"shot4": 3,
|
|
||||||
"shot5": 6
|
|
||||||
}
|
|
||||||
},
|
|
||||||
"total_score": 112,
|
|
||||||
"completed": true
|
|
||||||
},
|
|
||||||
"12": {
|
|
||||||
"name": "Matej Kvasnik",
|
|
||||||
"targets": {
|
|
||||||
"1": {
|
|
||||||
"shot1": 1,
|
|
||||||
"shot2": 0,
|
|
||||||
"shot3": 9,
|
|
||||||
"shot4": 2,
|
|
||||||
"shot5": 7
|
|
||||||
},
|
|
||||||
"2": {
|
|
||||||
"shot1": 7,
|
|
||||||
"shot2": 2,
|
|
||||||
"shot3": 4,
|
|
||||||
"shot4": 5,
|
|
||||||
"shot5": 5
|
|
||||||
},
|
|
||||||
"3": {
|
|
||||||
"shot1": 1,
|
|
||||||
"shot2": 0,
|
|
||||||
"shot3": 8,
|
|
||||||
"shot4": 2,
|
|
||||||
"shot5": 2
|
|
||||||
},
|
|
||||||
"4": {
|
|
||||||
"shot1": 6,
|
|
||||||
"shot2": 6,
|
|
||||||
"shot3": 5,
|
|
||||||
"shot4": 2,
|
|
||||||
"shot5": 8
|
|
||||||
}
|
|
||||||
},
|
|
||||||
"total_score": 82,
|
|
||||||
"completed": true
|
|
||||||
},
|
|
||||||
"9": {
|
|
||||||
"name": "Janez Bo\u017ei\u010d",
|
|
||||||
"targets": {
|
|
||||||
"1": {
|
|
||||||
"shot1": 9,
|
|
||||||
"shot2": 9,
|
|
||||||
"shot3": 7,
|
|
||||||
"shot4": 7,
|
|
||||||
"shot5": 9
|
|
||||||
},
|
|
||||||
"2": {
|
|
||||||
"shot1": 6,
|
|
||||||
"shot2": 0,
|
|
||||||
"shot3": 5,
|
|
||||||
"shot4": 1,
|
|
||||||
"shot5": 9
|
|
||||||
},
|
|
||||||
"3": {
|
|
||||||
"shot1": 8,
|
|
||||||
"shot2": 5,
|
|
||||||
"shot3": 10,
|
|
||||||
"shot4": 4,
|
|
||||||
"shot5": 4
|
|
||||||
},
|
|
||||||
"4": {
|
|
||||||
"shot1": 1,
|
|
||||||
"shot2": 2,
|
|
||||||
"shot3": 8,
|
|
||||||
"shot4": 1,
|
|
||||||
"shot5": 5
|
|
||||||
}
|
|
||||||
},
|
|
||||||
"total_score": 110,
|
|
||||||
"completed": true
|
|
||||||
},
|
|
||||||
"4": {
|
|
||||||
"name": "Mateja Pleterski",
|
|
||||||
"targets": {
|
|
||||||
"1": {
|
|
||||||
"shot1": 0,
|
|
||||||
"shot2": 10,
|
|
||||||
"shot3": 2,
|
|
||||||
"shot4": 4,
|
|
||||||
"shot5": 0
|
|
||||||
},
|
|
||||||
"2": {
|
|
||||||
"shot1": 0,
|
|
||||||
"shot2": 7,
|
|
||||||
"shot3": 4,
|
|
||||||
"shot4": 7,
|
|
||||||
"shot5": 0
|
|
||||||
},
|
|
||||||
"3": {
|
|
||||||
"shot1": 1,
|
|
||||||
"shot2": 0,
|
|
||||||
"shot3": 5,
|
|
||||||
"shot4": 6,
|
|
||||||
"shot5": 1
|
|
||||||
},
|
|
||||||
"4": {
|
|
||||||
"shot1": 4,
|
|
||||||
"shot2": 10,
|
|
||||||
"shot3": 4,
|
|
||||||
"shot4": 7,
|
|
||||||
"shot5": 2
|
|
||||||
}
|
|
||||||
},
|
|
||||||
"total_score": 74,
|
|
||||||
"completed": true
|
|
||||||
},
|
|
||||||
"21": {
|
|
||||||
"name": "Marko Blimen",
|
|
||||||
"targets": {
|
|
||||||
"1": {
|
|
||||||
"shot1": 8,
|
|
||||||
"shot2": 5,
|
|
||||||
"shot3": 4,
|
|
||||||
"shot4": 7,
|
|
||||||
"shot5": 8
|
|
||||||
},
|
|
||||||
"2": {
|
|
||||||
"shot1": 3,
|
|
||||||
"shot2": 1,
|
|
||||||
"shot3": 7,
|
|
||||||
"shot4": 2,
|
|
||||||
"shot5": 9
|
|
||||||
},
|
|
||||||
"3": {
|
|
||||||
"shot1": 1,
|
|
||||||
"shot2": 0,
|
|
||||||
"shot3": 2,
|
|
||||||
"shot4": 6,
|
|
||||||
"shot5": 5
|
|
||||||
},
|
|
||||||
"4": {
|
|
||||||
"shot1": 8,
|
|
||||||
"shot2": 3,
|
|
||||||
"shot3": 0,
|
|
||||||
"shot4": 3,
|
|
||||||
"shot5": 9
|
|
||||||
}
|
|
||||||
},
|
|
||||||
"total_score": 91,
|
|
||||||
"completed": true
|
|
||||||
},
|
|
||||||
"20": {
|
|
||||||
"name": "Jo\u017ee Preglav",
|
|
||||||
"targets": {
|
|
||||||
"1": {
|
|
||||||
"shot1": 1,
|
|
||||||
"shot2": 5,
|
|
||||||
"shot3": 0,
|
|
||||||
"shot4": 5,
|
|
||||||
"shot5": 9
|
|
||||||
},
|
|
||||||
"2": {
|
|
||||||
"shot1": 6,
|
|
||||||
"shot2": 5,
|
|
||||||
"shot3": 1,
|
|
||||||
"shot4": 8,
|
|
||||||
"shot5": 6
|
|
||||||
},
|
|
||||||
"3": {
|
|
||||||
"shot1": 4,
|
|
||||||
"shot2": 6,
|
|
||||||
"shot3": 10,
|
|
||||||
"shot4": 9,
|
|
||||||
"shot5": 2
|
|
||||||
},
|
|
||||||
"4": {
|
|
||||||
"shot1": 5,
|
|
||||||
"shot2": 9,
|
|
||||||
"shot3": 6,
|
|
||||||
"shot4": 3,
|
|
||||||
"shot5": 8
|
|
||||||
}
|
|
||||||
},
|
|
||||||
"total_score": 108,
|
|
||||||
"completed": true
|
|
||||||
},
|
|
||||||
"11": {
|
|
||||||
"name": "Rado Kefer",
|
|
||||||
"targets": {
|
|
||||||
"1": {
|
|
||||||
"shot1": 3,
|
|
||||||
"shot2": 5,
|
|
||||||
"shot3": 5,
|
|
||||||
"shot4": 1,
|
|
||||||
"shot5": 9
|
|
||||||
},
|
|
||||||
"2": {
|
|
||||||
"shot1": 2,
|
|
||||||
"shot2": 10,
|
|
||||||
"shot3": 8,
|
|
||||||
"shot4": 6,
|
|
||||||
"shot5": 1
|
|
||||||
},
|
|
||||||
"3": {
|
|
||||||
"shot1": 7,
|
|
||||||
"shot2": 9,
|
|
||||||
"shot3": 7,
|
|
||||||
"shot4": 9,
|
|
||||||
"shot5": 1
|
|
||||||
},
|
|
||||||
"4": {
|
|
||||||
"shot1": 0,
|
|
||||||
"shot2": 2,
|
|
||||||
"shot3": 9,
|
|
||||||
"shot4": 1,
|
|
||||||
"shot5": 3
|
|
||||||
}
|
|
||||||
},
|
|
||||||
"total_score": 98,
|
|
||||||
"completed": true
|
|
||||||
},
|
|
||||||
"47": {
|
|
||||||
"name": "Ljuba Mr\u0161ak",
|
|
||||||
"targets": {
|
|
||||||
"1": {
|
|
||||||
"shot1": 0,
|
|
||||||
"shot2": 2,
|
|
||||||
"shot3": 9,
|
|
||||||
"shot4": 7,
|
|
||||||
"shot5": 7
|
|
||||||
},
|
|
||||||
"2": {
|
|
||||||
"shot1": 7,
|
|
||||||
"shot2": 0,
|
|
||||||
"shot3": 0,
|
|
||||||
"shot4": 2,
|
|
||||||
"shot5": 3
|
|
||||||
},
|
|
||||||
"3": {
|
|
||||||
"shot1": 9,
|
|
||||||
"shot2": 9,
|
|
||||||
"shot3": 0,
|
|
||||||
"shot4": 6,
|
|
||||||
"shot5": 4
|
|
||||||
},
|
|
||||||
"4": {
|
|
||||||
"shot1": 2,
|
|
||||||
"shot2": 10,
|
|
||||||
"shot3": 9,
|
|
||||||
"shot4": 7,
|
|
||||||
"shot5": 7
|
|
||||||
}
|
|
||||||
},
|
|
||||||
"total_score": 100,
|
|
||||||
"completed": true
|
|
||||||
},
|
|
||||||
"48": {
|
|
||||||
"name": "Janja Salcman",
|
|
||||||
"targets": {
|
|
||||||
"1": {
|
|
||||||
"shot1": 8,
|
|
||||||
"shot2": 5,
|
|
||||||
"shot3": 3,
|
|
||||||
"shot4": 2,
|
|
||||||
"shot5": 2
|
|
||||||
},
|
|
||||||
"2": {
|
|
||||||
"shot1": 10,
|
|
||||||
"shot2": 6,
|
|
||||||
"shot3": 10,
|
|
||||||
"shot4": 4,
|
|
||||||
"shot5": 7
|
|
||||||
},
|
|
||||||
"3": {
|
|
||||||
"shot1": 10,
|
|
||||||
"shot2": 0,
|
|
||||||
"shot3": 6,
|
|
||||||
"shot4": 3,
|
|
||||||
"shot5": 3
|
|
||||||
},
|
|
||||||
"4": {
|
|
||||||
"shot1": 10,
|
|
||||||
"shot2": 0,
|
|
||||||
"shot3": 9,
|
|
||||||
"shot4": 8,
|
|
||||||
"shot5": 1
|
|
||||||
}
|
|
||||||
},
|
|
||||||
"total_score": 107,
|
|
||||||
"completed": true
|
|
||||||
},
|
|
||||||
"45": {
|
|
||||||
"name": "Lidija Blimen",
|
|
||||||
"targets": {
|
|
||||||
"1": {
|
|
||||||
"shot1": 8,
|
|
||||||
"shot2": 4,
|
|
||||||
"shot3": 8,
|
|
||||||
"shot4": 2,
|
|
||||||
"shot5": 1
|
|
||||||
},
|
|
||||||
"2": {
|
|
||||||
"shot1": 2,
|
|
||||||
"shot2": 4,
|
|
||||||
"shot3": 6,
|
|
||||||
"shot4": 7,
|
|
||||||
"shot5": 0
|
|
||||||
},
|
|
||||||
"3": {
|
|
||||||
"shot1": 7,
|
|
||||||
"shot2": 3,
|
|
||||||
"shot3": 10,
|
|
||||||
"shot4": 7,
|
|
||||||
"shot5": 8
|
|
||||||
},
|
|
||||||
"4": {
|
|
||||||
"shot1": 1,
|
|
||||||
"shot2": 2,
|
|
||||||
"shot3": 10,
|
|
||||||
"shot4": 4,
|
|
||||||
"shot5": 6
|
|
||||||
}
|
|
||||||
},
|
|
||||||
"total_score": 100,
|
|
||||||
"completed": true
|
|
||||||
},
|
|
||||||
"1": {
|
|
||||||
"name": "Domen Pleterski",
|
|
||||||
"targets": {
|
|
||||||
"1": {
|
|
||||||
"shot1": 9,
|
|
||||||
"shot2": 2,
|
|
||||||
"shot3": 10,
|
|
||||||
"shot4": 2,
|
|
||||||
"shot5": 2
|
|
||||||
},
|
|
||||||
"2": {
|
|
||||||
"shot1": 5,
|
|
||||||
"shot2": 4,
|
|
||||||
"shot3": 10,
|
|
||||||
"shot4": 10,
|
|
||||||
"shot5": 7
|
|
||||||
},
|
|
||||||
"3": {
|
|
||||||
"shot1": 9,
|
|
||||||
"shot2": 5,
|
|
||||||
"shot3": 5,
|
|
||||||
"shot4": 1,
|
|
||||||
"shot5": 9
|
|
||||||
},
|
|
||||||
"4": {
|
|
||||||
"shot1": 5,
|
|
||||||
"shot2": 8,
|
|
||||||
"shot3": 2,
|
|
||||||
"shot4": 10,
|
|
||||||
"shot5": 2
|
|
||||||
}
|
|
||||||
},
|
|
||||||
"total_score": 117,
|
|
||||||
"completed": true
|
|
||||||
},
|
|
||||||
"5": {
|
|
||||||
"name": "Jo\u017ee Verhnjak",
|
|
||||||
"targets": {
|
|
||||||
"1": {
|
|
||||||
"shot1": 2,
|
|
||||||
"shot2": 5,
|
|
||||||
"shot3": 3,
|
|
||||||
"shot4": 6,
|
|
||||||
"shot5": 5
|
|
||||||
},
|
|
||||||
"2": {
|
|
||||||
"shot1": 9,
|
|
||||||
"shot2": 7,
|
|
||||||
"shot3": 0,
|
|
||||||
"shot4": 2,
|
|
||||||
"shot5": 5
|
|
||||||
},
|
|
||||||
"3": {
|
|
||||||
"shot1": 5,
|
|
||||||
"shot2": 7,
|
|
||||||
"shot3": 0,
|
|
||||||
"shot4": 4,
|
|
||||||
"shot5": 2
|
|
||||||
},
|
|
||||||
"4": {
|
|
||||||
"shot1": 0,
|
|
||||||
"shot2": 7,
|
|
||||||
"shot3": 1,
|
|
||||||
"shot4": 4,
|
|
||||||
"shot5": 2
|
|
||||||
}
|
|
||||||
},
|
|
||||||
"total_score": 76,
|
|
||||||
"completed": true
|
|
||||||
},
|
|
||||||
"44": {
|
|
||||||
"name": "Anka Ka\u010dnik",
|
|
||||||
"targets": {
|
|
||||||
"1": {
|
|
||||||
"shot1": 5,
|
|
||||||
"shot2": 3,
|
|
||||||
"shot3": 2,
|
|
||||||
"shot4": 5,
|
|
||||||
"shot5": 1
|
|
||||||
},
|
|
||||||
"2": {
|
|
||||||
"shot1": 6,
|
|
||||||
"shot2": 7,
|
|
||||||
"shot3": 10,
|
|
||||||
"shot4": 10,
|
|
||||||
"shot5": 4
|
|
||||||
},
|
|
||||||
"3": {
|
|
||||||
"shot1": 1,
|
|
||||||
"shot2": 3,
|
|
||||||
"shot3": 1,
|
|
||||||
"shot4": 9,
|
|
||||||
"shot5": 0
|
|
||||||
},
|
|
||||||
"4": {
|
|
||||||
"shot1": 9,
|
|
||||||
"shot2": 10,
|
|
||||||
"shot3": 5,
|
|
||||||
"shot4": 10,
|
|
||||||
"shot5": 1
|
|
||||||
}
|
|
||||||
},
|
|
||||||
"total_score": 102,
|
|
||||||
"completed": true
|
|
||||||
}
|
|
||||||
},
|
|
||||||
"tournament_finished": true,
|
|
||||||
"created_at": "2025-09-08T19:39:27.077445",
|
|
||||||
"finished_at": "2025-09-08T19:39:44.030962"
|
|
||||||
},
|
|
||||||
"archived_at": "2025-09-08T19:39:44.030989"
|
|
||||||
}
|
|
||||||
@@ -1,759 +0,0 @@
|
|||||||
{
|
|
||||||
"tournament": {
|
|
||||||
"rounds": [
|
|
||||||
{
|
|
||||||
"round_number": 1,
|
|
||||||
"players": [
|
|
||||||
{
|
|
||||||
"id": 12,
|
|
||||||
"name": "Matej Kvasnik",
|
|
||||||
"enabled": true
|
|
||||||
},
|
|
||||||
{
|
|
||||||
"id": 21,
|
|
||||||
"name": "Marko Blimen",
|
|
||||||
"enabled": true
|
|
||||||
},
|
|
||||||
{
|
|
||||||
"id": 1,
|
|
||||||
"name": "Domen Pleterski",
|
|
||||||
"enabled": true
|
|
||||||
},
|
|
||||||
{
|
|
||||||
"id": 4,
|
|
||||||
"name": "Mateja Pleterski",
|
|
||||||
"enabled": true
|
|
||||||
},
|
|
||||||
{
|
|
||||||
"id": 5,
|
|
||||||
"name": "Jo\u017ee Verhnjak",
|
|
||||||
"enabled": true
|
|
||||||
},
|
|
||||||
{
|
|
||||||
"id": 11,
|
|
||||||
"name": "Rado Kefer",
|
|
||||||
"enabled": true
|
|
||||||
}
|
|
||||||
],
|
|
||||||
"status": "pending"
|
|
||||||
},
|
|
||||||
{
|
|
||||||
"round_number": 2,
|
|
||||||
"players": [
|
|
||||||
{
|
|
||||||
"id": 44,
|
|
||||||
"name": "Anka Ka\u010dnik",
|
|
||||||
"enabled": true
|
|
||||||
},
|
|
||||||
{
|
|
||||||
"id": 48,
|
|
||||||
"name": "Janja Salcman",
|
|
||||||
"enabled": true
|
|
||||||
},
|
|
||||||
{
|
|
||||||
"id": 3,
|
|
||||||
"name": "Ivan Tandler",
|
|
||||||
"enabled": true
|
|
||||||
},
|
|
||||||
{
|
|
||||||
"id": 7,
|
|
||||||
"name": "Branko Poker\u017enik",
|
|
||||||
"enabled": true
|
|
||||||
},
|
|
||||||
{
|
|
||||||
"id": 9,
|
|
||||||
"name": "Janez Bo\u017ei\u010d",
|
|
||||||
"enabled": true
|
|
||||||
},
|
|
||||||
{
|
|
||||||
"id": 45,
|
|
||||||
"name": "Lidija Blimen",
|
|
||||||
"enabled": true
|
|
||||||
}
|
|
||||||
],
|
|
||||||
"status": "waiting"
|
|
||||||
},
|
|
||||||
{
|
|
||||||
"round_number": 3,
|
|
||||||
"players": [
|
|
||||||
{
|
|
||||||
"id": 47,
|
|
||||||
"name": "Ljuba Mr\u0161ak",
|
|
||||||
"enabled": true
|
|
||||||
},
|
|
||||||
{
|
|
||||||
"id": 46,
|
|
||||||
"name": "Tijana \u0160tumpfl",
|
|
||||||
"enabled": true
|
|
||||||
},
|
|
||||||
{
|
|
||||||
"id": 20,
|
|
||||||
"name": "Jo\u017ee Preglav",
|
|
||||||
"enabled": true
|
|
||||||
},
|
|
||||||
{
|
|
||||||
"id": 17,
|
|
||||||
"name": "Du\u0161an Onuk",
|
|
||||||
"enabled": true
|
|
||||||
},
|
|
||||||
{
|
|
||||||
"id": 15,
|
|
||||||
"name": "Jan Pleterski",
|
|
||||||
"enabled": true
|
|
||||||
},
|
|
||||||
{
|
|
||||||
"id": 49,
|
|
||||||
"name": "Jolanda Verhnjak",
|
|
||||||
"enabled": true
|
|
||||||
}
|
|
||||||
],
|
|
||||||
"status": "waiting"
|
|
||||||
}
|
|
||||||
],
|
|
||||||
"created_at": "2025-09-08T20:15:56.266521",
|
|
||||||
"total_players": 18,
|
|
||||||
"total_rounds": 3,
|
|
||||||
"current_round": 1,
|
|
||||||
"tournament_type": "4_targets"
|
|
||||||
},
|
|
||||||
"results": {
|
|
||||||
"tournament_id": "2025-09-08T20:15:56.266521",
|
|
||||||
"tournament_type": "4_targets",
|
|
||||||
"participants": {
|
|
||||||
"12": {
|
|
||||||
"name": "Matej Kvasnik",
|
|
||||||
"targets": {
|
|
||||||
"1": {
|
|
||||||
"shot1": 1,
|
|
||||||
"shot2": 6,
|
|
||||||
"shot3": 5,
|
|
||||||
"shot4": 1,
|
|
||||||
"shot5": 3
|
|
||||||
},
|
|
||||||
"2": {
|
|
||||||
"shot1": 8,
|
|
||||||
"shot2": 3,
|
|
||||||
"shot3": 3,
|
|
||||||
"shot4": 10,
|
|
||||||
"shot5": 4
|
|
||||||
},
|
|
||||||
"3": {
|
|
||||||
"shot1": 10,
|
|
||||||
"shot2": 0,
|
|
||||||
"shot3": 0,
|
|
||||||
"shot4": 2,
|
|
||||||
"shot5": 6
|
|
||||||
},
|
|
||||||
"4": {
|
|
||||||
"shot1": 7,
|
|
||||||
"shot2": 5,
|
|
||||||
"shot3": 0,
|
|
||||||
"shot4": 2,
|
|
||||||
"shot5": 5
|
|
||||||
}
|
|
||||||
},
|
|
||||||
"total_score": 81,
|
|
||||||
"completed": true
|
|
||||||
},
|
|
||||||
"21": {
|
|
||||||
"name": "Marko Blimen",
|
|
||||||
"targets": {
|
|
||||||
"1": {
|
|
||||||
"shot1": 1,
|
|
||||||
"shot2": 1,
|
|
||||||
"shot3": 0,
|
|
||||||
"shot4": 0,
|
|
||||||
"shot5": 5
|
|
||||||
},
|
|
||||||
"2": {
|
|
||||||
"shot1": 9,
|
|
||||||
"shot2": 0,
|
|
||||||
"shot3": 0,
|
|
||||||
"shot4": 2,
|
|
||||||
"shot5": 3
|
|
||||||
},
|
|
||||||
"3": {
|
|
||||||
"shot1": 3,
|
|
||||||
"shot2": 8,
|
|
||||||
"shot3": 2,
|
|
||||||
"shot4": 1,
|
|
||||||
"shot5": 0
|
|
||||||
},
|
|
||||||
"4": {
|
|
||||||
"shot1": 4,
|
|
||||||
"shot2": 6,
|
|
||||||
"shot3": 3,
|
|
||||||
"shot4": 9,
|
|
||||||
"shot5": 0
|
|
||||||
}
|
|
||||||
},
|
|
||||||
"total_score": 57,
|
|
||||||
"completed": true
|
|
||||||
},
|
|
||||||
"1": {
|
|
||||||
"name": "Domen Pleterski",
|
|
||||||
"targets": {
|
|
||||||
"1": {
|
|
||||||
"shot1": 0,
|
|
||||||
"shot2": 4,
|
|
||||||
"shot3": 0,
|
|
||||||
"shot4": 9,
|
|
||||||
"shot5": 10
|
|
||||||
},
|
|
||||||
"2": {
|
|
||||||
"shot1": 0,
|
|
||||||
"shot2": 3,
|
|
||||||
"shot3": 0,
|
|
||||||
"shot4": 1,
|
|
||||||
"shot5": 10
|
|
||||||
},
|
|
||||||
"3": {
|
|
||||||
"shot1": 5,
|
|
||||||
"shot2": 3,
|
|
||||||
"shot3": 4,
|
|
||||||
"shot4": 6,
|
|
||||||
"shot5": 10
|
|
||||||
},
|
|
||||||
"4": {
|
|
||||||
"shot1": 0,
|
|
||||||
"shot2": 2,
|
|
||||||
"shot3": 1,
|
|
||||||
"shot4": 8,
|
|
||||||
"shot5": 2
|
|
||||||
}
|
|
||||||
},
|
|
||||||
"total_score": 78,
|
|
||||||
"completed": true
|
|
||||||
},
|
|
||||||
"4": {
|
|
||||||
"name": "Mateja Pleterski",
|
|
||||||
"targets": {
|
|
||||||
"1": {
|
|
||||||
"shot1": 2,
|
|
||||||
"shot2": 0,
|
|
||||||
"shot3": 2,
|
|
||||||
"shot4": 3,
|
|
||||||
"shot5": 3
|
|
||||||
},
|
|
||||||
"2": {
|
|
||||||
"shot1": 7,
|
|
||||||
"shot2": 2,
|
|
||||||
"shot3": 9,
|
|
||||||
"shot4": 8,
|
|
||||||
"shot5": 6
|
|
||||||
},
|
|
||||||
"3": {
|
|
||||||
"shot1": 3,
|
|
||||||
"shot2": 8,
|
|
||||||
"shot3": 1,
|
|
||||||
"shot4": 1,
|
|
||||||
"shot5": 3
|
|
||||||
},
|
|
||||||
"4": {
|
|
||||||
"shot1": 10,
|
|
||||||
"shot2": 5,
|
|
||||||
"shot3": 10,
|
|
||||||
"shot4": 5,
|
|
||||||
"shot5": 7
|
|
||||||
}
|
|
||||||
},
|
|
||||||
"total_score": 95,
|
|
||||||
"completed": true
|
|
||||||
},
|
|
||||||
"5": {
|
|
||||||
"name": "Jo\u017ee Verhnjak",
|
|
||||||
"targets": {
|
|
||||||
"1": {
|
|
||||||
"shot1": 8,
|
|
||||||
"shot2": 3,
|
|
||||||
"shot3": 3,
|
|
||||||
"shot4": 2,
|
|
||||||
"shot5": 6
|
|
||||||
},
|
|
||||||
"2": {
|
|
||||||
"shot1": 7,
|
|
||||||
"shot2": 6,
|
|
||||||
"shot3": 7,
|
|
||||||
"shot4": 5,
|
|
||||||
"shot5": 9
|
|
||||||
},
|
|
||||||
"3": {
|
|
||||||
"shot1": 2,
|
|
||||||
"shot2": 0,
|
|
||||||
"shot3": 7,
|
|
||||||
"shot4": 6,
|
|
||||||
"shot5": 2
|
|
||||||
},
|
|
||||||
"4": {
|
|
||||||
"shot1": 6,
|
|
||||||
"shot2": 1,
|
|
||||||
"shot3": 5,
|
|
||||||
"shot4": 7,
|
|
||||||
"shot5": 5
|
|
||||||
}
|
|
||||||
},
|
|
||||||
"total_score": 97,
|
|
||||||
"completed": true
|
|
||||||
},
|
|
||||||
"11": {
|
|
||||||
"name": "Rado Kefer",
|
|
||||||
"targets": {
|
|
||||||
"1": {
|
|
||||||
"shot1": 4,
|
|
||||||
"shot2": 2,
|
|
||||||
"shot3": 3,
|
|
||||||
"shot4": 7,
|
|
||||||
"shot5": 2
|
|
||||||
},
|
|
||||||
"2": {
|
|
||||||
"shot1": 9,
|
|
||||||
"shot2": 6,
|
|
||||||
"shot3": 10,
|
|
||||||
"shot4": 7,
|
|
||||||
"shot5": 6
|
|
||||||
},
|
|
||||||
"3": {
|
|
||||||
"shot1": 8,
|
|
||||||
"shot2": 6,
|
|
||||||
"shot3": 9,
|
|
||||||
"shot4": 9,
|
|
||||||
"shot5": 1
|
|
||||||
},
|
|
||||||
"4": {
|
|
||||||
"shot1": 3,
|
|
||||||
"shot2": 0,
|
|
||||||
"shot3": 6,
|
|
||||||
"shot4": 8,
|
|
||||||
"shot5": 2
|
|
||||||
}
|
|
||||||
},
|
|
||||||
"total_score": 108,
|
|
||||||
"completed": true
|
|
||||||
},
|
|
||||||
"44": {
|
|
||||||
"name": "Anka Ka\u010dnik",
|
|
||||||
"targets": {
|
|
||||||
"1": {
|
|
||||||
"shot1": 8,
|
|
||||||
"shot2": 8,
|
|
||||||
"shot3": 4,
|
|
||||||
"shot4": 10,
|
|
||||||
"shot5": 3
|
|
||||||
},
|
|
||||||
"2": {
|
|
||||||
"shot1": 2,
|
|
||||||
"shot2": 8,
|
|
||||||
"shot3": 10,
|
|
||||||
"shot4": 7,
|
|
||||||
"shot5": 9
|
|
||||||
},
|
|
||||||
"3": {
|
|
||||||
"shot1": 3,
|
|
||||||
"shot2": 2,
|
|
||||||
"shot3": 0,
|
|
||||||
"shot4": 6,
|
|
||||||
"shot5": 9
|
|
||||||
},
|
|
||||||
"4": {
|
|
||||||
"shot1": 9,
|
|
||||||
"shot2": 5,
|
|
||||||
"shot3": 10,
|
|
||||||
"shot4": 10,
|
|
||||||
"shot5": 6
|
|
||||||
}
|
|
||||||
},
|
|
||||||
"total_score": 129,
|
|
||||||
"completed": true
|
|
||||||
},
|
|
||||||
"48": {
|
|
||||||
"name": "Janja Salcman",
|
|
||||||
"targets": {
|
|
||||||
"1": {
|
|
||||||
"shot1": 2,
|
|
||||||
"shot2": 6,
|
|
||||||
"shot3": 9,
|
|
||||||
"shot4": 4,
|
|
||||||
"shot5": 0
|
|
||||||
},
|
|
||||||
"2": {
|
|
||||||
"shot1": 0,
|
|
||||||
"shot2": 7,
|
|
||||||
"shot3": 3,
|
|
||||||
"shot4": 2,
|
|
||||||
"shot5": 0
|
|
||||||
},
|
|
||||||
"3": {
|
|
||||||
"shot1": 4,
|
|
||||||
"shot2": 6,
|
|
||||||
"shot3": 4,
|
|
||||||
"shot4": 8,
|
|
||||||
"shot5": 8
|
|
||||||
},
|
|
||||||
"4": {
|
|
||||||
"shot1": 2,
|
|
||||||
"shot2": 7,
|
|
||||||
"shot3": 0,
|
|
||||||
"shot4": 10,
|
|
||||||
"shot5": 3
|
|
||||||
}
|
|
||||||
},
|
|
||||||
"total_score": 85,
|
|
||||||
"completed": true
|
|
||||||
},
|
|
||||||
"3": {
|
|
||||||
"name": "Ivan Tandler",
|
|
||||||
"targets": {
|
|
||||||
"1": {
|
|
||||||
"shot1": 10,
|
|
||||||
"shot2": 9,
|
|
||||||
"shot3": 8,
|
|
||||||
"shot4": 8,
|
|
||||||
"shot5": 2
|
|
||||||
},
|
|
||||||
"2": {
|
|
||||||
"shot1": 7,
|
|
||||||
"shot2": 10,
|
|
||||||
"shot3": 3,
|
|
||||||
"shot4": 9,
|
|
||||||
"shot5": 2
|
|
||||||
},
|
|
||||||
"3": {
|
|
||||||
"shot1": 9,
|
|
||||||
"shot2": 4,
|
|
||||||
"shot3": 0,
|
|
||||||
"shot4": 2,
|
|
||||||
"shot5": 6
|
|
||||||
},
|
|
||||||
"4": {
|
|
||||||
"shot1": 0,
|
|
||||||
"shot2": 4,
|
|
||||||
"shot3": 1,
|
|
||||||
"shot4": 2,
|
|
||||||
"shot5": 10
|
|
||||||
}
|
|
||||||
},
|
|
||||||
"total_score": 106,
|
|
||||||
"completed": true
|
|
||||||
},
|
|
||||||
"7": {
|
|
||||||
"name": "Branko Poker\u017enik",
|
|
||||||
"targets": {
|
|
||||||
"1": {
|
|
||||||
"shot1": 4,
|
|
||||||
"shot2": 0,
|
|
||||||
"shot3": 2,
|
|
||||||
"shot4": 3,
|
|
||||||
"shot5": 6
|
|
||||||
},
|
|
||||||
"2": {
|
|
||||||
"shot1": 4,
|
|
||||||
"shot2": 5,
|
|
||||||
"shot3": 4,
|
|
||||||
"shot4": 10,
|
|
||||||
"shot5": 10
|
|
||||||
},
|
|
||||||
"3": {
|
|
||||||
"shot1": 2,
|
|
||||||
"shot2": 1,
|
|
||||||
"shot3": 0,
|
|
||||||
"shot4": 4,
|
|
||||||
"shot5": 5
|
|
||||||
},
|
|
||||||
"4": {
|
|
||||||
"shot1": 7,
|
|
||||||
"shot2": 10,
|
|
||||||
"shot3": 8,
|
|
||||||
"shot4": 5,
|
|
||||||
"shot5": 10
|
|
||||||
}
|
|
||||||
},
|
|
||||||
"total_score": 100,
|
|
||||||
"completed": true
|
|
||||||
},
|
|
||||||
"9": {
|
|
||||||
"name": "Janez Bo\u017ei\u010d",
|
|
||||||
"targets": {
|
|
||||||
"1": {
|
|
||||||
"shot1": 3,
|
|
||||||
"shot2": 9,
|
|
||||||
"shot3": 10,
|
|
||||||
"shot4": 5,
|
|
||||||
"shot5": 3
|
|
||||||
},
|
|
||||||
"2": {
|
|
||||||
"shot1": 5,
|
|
||||||
"shot2": 9,
|
|
||||||
"shot3": 6,
|
|
||||||
"shot4": 8,
|
|
||||||
"shot5": 5
|
|
||||||
},
|
|
||||||
"3": {
|
|
||||||
"shot1": 1,
|
|
||||||
"shot2": 7,
|
|
||||||
"shot3": 8,
|
|
||||||
"shot4": 1,
|
|
||||||
"shot5": 9
|
|
||||||
},
|
|
||||||
"4": {
|
|
||||||
"shot1": 6,
|
|
||||||
"shot2": 3,
|
|
||||||
"shot3": 10,
|
|
||||||
"shot4": 9,
|
|
||||||
"shot5": 4
|
|
||||||
}
|
|
||||||
},
|
|
||||||
"total_score": 121,
|
|
||||||
"completed": true
|
|
||||||
},
|
|
||||||
"45": {
|
|
||||||
"name": "Lidija Blimen",
|
|
||||||
"targets": {
|
|
||||||
"1": {
|
|
||||||
"shot1": 2,
|
|
||||||
"shot2": 9,
|
|
||||||
"shot3": 10,
|
|
||||||
"shot4": 2,
|
|
||||||
"shot5": 10
|
|
||||||
},
|
|
||||||
"2": {
|
|
||||||
"shot1": 8,
|
|
||||||
"shot2": 3,
|
|
||||||
"shot3": 7,
|
|
||||||
"shot4": 6,
|
|
||||||
"shot5": 8
|
|
||||||
},
|
|
||||||
"3": {
|
|
||||||
"shot1": 0,
|
|
||||||
"shot2": 7,
|
|
||||||
"shot3": 4,
|
|
||||||
"shot4": 1,
|
|
||||||
"shot5": 1
|
|
||||||
},
|
|
||||||
"4": {
|
|
||||||
"shot1": 2,
|
|
||||||
"shot2": 2,
|
|
||||||
"shot3": 4,
|
|
||||||
"shot4": 10,
|
|
||||||
"shot5": 1
|
|
||||||
}
|
|
||||||
},
|
|
||||||
"total_score": 97,
|
|
||||||
"completed": true
|
|
||||||
},
|
|
||||||
"47": {
|
|
||||||
"name": "Ljuba Mr\u0161ak",
|
|
||||||
"targets": {
|
|
||||||
"1": {
|
|
||||||
"shot1": 9,
|
|
||||||
"shot2": 1,
|
|
||||||
"shot3": 1,
|
|
||||||
"shot4": 5,
|
|
||||||
"shot5": 9
|
|
||||||
},
|
|
||||||
"2": {
|
|
||||||
"shot1": 2,
|
|
||||||
"shot2": 10,
|
|
||||||
"shot3": 10,
|
|
||||||
"shot4": 0,
|
|
||||||
"shot5": 9
|
|
||||||
},
|
|
||||||
"3": {
|
|
||||||
"shot1": 1,
|
|
||||||
"shot2": 5,
|
|
||||||
"shot3": 4,
|
|
||||||
"shot4": 10,
|
|
||||||
"shot5": 0
|
|
||||||
},
|
|
||||||
"4": {
|
|
||||||
"shot1": 3,
|
|
||||||
"shot2": 3,
|
|
||||||
"shot3": 2,
|
|
||||||
"shot4": 2,
|
|
||||||
"shot5": 2
|
|
||||||
}
|
|
||||||
},
|
|
||||||
"total_score": 88,
|
|
||||||
"completed": true
|
|
||||||
},
|
|
||||||
"46": {
|
|
||||||
"name": "Tijana \u0160tumpfl",
|
|
||||||
"targets": {
|
|
||||||
"1": {
|
|
||||||
"shot1": 1,
|
|
||||||
"shot2": 3,
|
|
||||||
"shot3": 2,
|
|
||||||
"shot4": 3,
|
|
||||||
"shot5": 3
|
|
||||||
},
|
|
||||||
"2": {
|
|
||||||
"shot1": 9,
|
|
||||||
"shot2": 5,
|
|
||||||
"shot3": 7,
|
|
||||||
"shot4": 7,
|
|
||||||
"shot5": 9
|
|
||||||
},
|
|
||||||
"3": {
|
|
||||||
"shot1": 3,
|
|
||||||
"shot2": 8,
|
|
||||||
"shot3": 1,
|
|
||||||
"shot4": 5,
|
|
||||||
"shot5": 6
|
|
||||||
},
|
|
||||||
"4": {
|
|
||||||
"shot1": 3,
|
|
||||||
"shot2": 0,
|
|
||||||
"shot3": 9,
|
|
||||||
"shot4": 9,
|
|
||||||
"shot5": 7
|
|
||||||
}
|
|
||||||
},
|
|
||||||
"total_score": 100,
|
|
||||||
"completed": true
|
|
||||||
},
|
|
||||||
"20": {
|
|
||||||
"name": "Jo\u017ee Preglav",
|
|
||||||
"targets": {
|
|
||||||
"1": {
|
|
||||||
"shot1": 4,
|
|
||||||
"shot2": 4,
|
|
||||||
"shot3": 9,
|
|
||||||
"shot4": 5,
|
|
||||||
"shot5": 2
|
|
||||||
},
|
|
||||||
"2": {
|
|
||||||
"shot1": 6,
|
|
||||||
"shot2": 0,
|
|
||||||
"shot3": 10,
|
|
||||||
"shot4": 0,
|
|
||||||
"shot5": 5
|
|
||||||
},
|
|
||||||
"3": {
|
|
||||||
"shot1": 7,
|
|
||||||
"shot2": 8,
|
|
||||||
"shot3": 9,
|
|
||||||
"shot4": 6,
|
|
||||||
"shot5": 5
|
|
||||||
},
|
|
||||||
"4": {
|
|
||||||
"shot1": 8,
|
|
||||||
"shot2": 7,
|
|
||||||
"shot3": 5,
|
|
||||||
"shot4": 5,
|
|
||||||
"shot5": 10
|
|
||||||
}
|
|
||||||
},
|
|
||||||
"total_score": 115,
|
|
||||||
"completed": true
|
|
||||||
},
|
|
||||||
"17": {
|
|
||||||
"name": "Du\u0161an Onuk",
|
|
||||||
"targets": {
|
|
||||||
"1": {
|
|
||||||
"shot1": 0,
|
|
||||||
"shot2": 3,
|
|
||||||
"shot3": 3,
|
|
||||||
"shot4": 2,
|
|
||||||
"shot5": 2
|
|
||||||
},
|
|
||||||
"2": {
|
|
||||||
"shot1": 2,
|
|
||||||
"shot2": 6,
|
|
||||||
"shot3": 1,
|
|
||||||
"shot4": 10,
|
|
||||||
"shot5": 10
|
|
||||||
},
|
|
||||||
"3": {
|
|
||||||
"shot1": 1,
|
|
||||||
"shot2": 7,
|
|
||||||
"shot3": 4,
|
|
||||||
"shot4": 5,
|
|
||||||
"shot5": 5
|
|
||||||
},
|
|
||||||
"4": {
|
|
||||||
"shot1": 10,
|
|
||||||
"shot2": 2,
|
|
||||||
"shot3": 8,
|
|
||||||
"shot4": 7,
|
|
||||||
"shot5": 9
|
|
||||||
}
|
|
||||||
},
|
|
||||||
"total_score": 97,
|
|
||||||
"completed": true
|
|
||||||
},
|
|
||||||
"15": {
|
|
||||||
"name": "Jan Pleterski",
|
|
||||||
"targets": {
|
|
||||||
"1": {
|
|
||||||
"shot1": 0,
|
|
||||||
"shot2": 0,
|
|
||||||
"shot3": 2,
|
|
||||||
"shot4": 0,
|
|
||||||
"shot5": 4
|
|
||||||
},
|
|
||||||
"2": {
|
|
||||||
"shot1": 1,
|
|
||||||
"shot2": 7,
|
|
||||||
"shot3": 8,
|
|
||||||
"shot4": 7,
|
|
||||||
"shot5": 9
|
|
||||||
},
|
|
||||||
"3": {
|
|
||||||
"shot1": 2,
|
|
||||||
"shot2": 8,
|
|
||||||
"shot3": 7,
|
|
||||||
"shot4": 2,
|
|
||||||
"shot5": 5
|
|
||||||
},
|
|
||||||
"4": {
|
|
||||||
"shot1": 9,
|
|
||||||
"shot2": 5,
|
|
||||||
"shot3": 1,
|
|
||||||
"shot4": 7,
|
|
||||||
"shot5": 3
|
|
||||||
}
|
|
||||||
},
|
|
||||||
"total_score": 87,
|
|
||||||
"completed": true
|
|
||||||
},
|
|
||||||
"49": {
|
|
||||||
"name": "Jolanda Verhnjak",
|
|
||||||
"targets": {
|
|
||||||
"1": {
|
|
||||||
"shot1": 8,
|
|
||||||
"shot2": 2,
|
|
||||||
"shot3": 7,
|
|
||||||
"shot4": 5,
|
|
||||||
"shot5": 0
|
|
||||||
},
|
|
||||||
"2": {
|
|
||||||
"shot1": 1,
|
|
||||||
"shot2": 8,
|
|
||||||
"shot3": 0,
|
|
||||||
"shot4": 4,
|
|
||||||
"shot5": 10
|
|
||||||
},
|
|
||||||
"3": {
|
|
||||||
"shot1": 0,
|
|
||||||
"shot2": 4,
|
|
||||||
"shot3": 4,
|
|
||||||
"shot4": 7,
|
|
||||||
"shot5": 4
|
|
||||||
},
|
|
||||||
"4": {
|
|
||||||
"shot1": 5,
|
|
||||||
"shot2": 6,
|
|
||||||
"shot3": 4,
|
|
||||||
"shot4": 6,
|
|
||||||
"shot5": 0
|
|
||||||
}
|
|
||||||
},
|
|
||||||
"total_score": 85,
|
|
||||||
"completed": true
|
|
||||||
}
|
|
||||||
},
|
|
||||||
"tournament_finished": true,
|
|
||||||
"created_at": "2025-09-08T20:15:56.266721",
|
|
||||||
"finished_at": "2025-09-08T20:16:01.584621"
|
|
||||||
},
|
|
||||||
"archived_at": "2025-09-08T20:16:01.584647"
|
|
||||||
}
|
|
||||||
File diff suppressed because it is too large
Load Diff
File diff suppressed because it is too large
Load Diff
File diff suppressed because it is too large
Load Diff
File diff suppressed because it is too large
Load Diff
File diff suppressed because it is too large
Load Diff
File diff suppressed because it is too large
Load Diff
File diff suppressed because it is too large
Load Diff
File diff suppressed because it is too large
Load Diff
File diff suppressed because it is too large
Load Diff
File diff suppressed because it is too large
Load Diff
File diff suppressed because it is too large
Load Diff
File diff suppressed because it is too large
Load Diff
File diff suppressed because it is too large
Load Diff
File diff suppressed because it is too large
Load Diff
File diff suppressed because it is too large
Load Diff
File diff suppressed because it is too large
Load Diff
+107
-585
@@ -1,3 +1,8 @@
|
|||||||
|
"""
|
||||||
|
TV_APP V1.0.0 - Tournament and League Management System
|
||||||
|
Flask web application for managing tournaments with multi-camera streaming
|
||||||
|
"""
|
||||||
|
|
||||||
from flask import Flask, render_template, request, redirect, jsonify, session
|
from flask import Flask, render_template, request, redirect, jsonify, session
|
||||||
import json
|
import json
|
||||||
import os
|
import os
|
||||||
@@ -7,63 +12,25 @@ from collections import defaultdict
|
|||||||
from datetime import datetime
|
from datetime import datetime
|
||||||
import re
|
import re
|
||||||
|
|
||||||
|
# Import modular components
|
||||||
|
from app.utils import (
|
||||||
|
load_translations, get_current_language, get_translations,
|
||||||
|
is_mobile_device, calculate_tens_from_targets
|
||||||
|
)
|
||||||
|
from app.storage import (
|
||||||
|
SettingsStorage, PlayerStorage, TournamentStorage,
|
||||||
|
ResultsStorage, LeagueStorage, ArchiveStorage,
|
||||||
|
TOURNAMENT_FILE, RESULTS_FILE, LEAGUE_FILE
|
||||||
|
)
|
||||||
|
from app.models import Tournament, Scoring, RoundManager
|
||||||
|
|
||||||
|
# Initialize Flask app
|
||||||
app = Flask(__name__)
|
app = Flask(__name__)
|
||||||
app.secret_key = 'your-secret-key-for-sessions' # Change this to a random secret key
|
app.secret_key = 'your-secret-key-for-sessions'
|
||||||
|
app.debug = False
|
||||||
|
|
||||||
# Language support
|
|
||||||
SUPPORTED_LANGUAGES = ['sl', 'en']
|
|
||||||
DEFAULT_LANGUAGE = 'sl'
|
|
||||||
|
|
||||||
def load_translations(language='sl'):
|
# Configuration: Camera Streams (6 targets)
|
||||||
"""Load translations for the specified language"""
|
|
||||||
try:
|
|
||||||
locale_file = f'locales/{language}.json'
|
|
||||||
if os.path.exists(locale_file):
|
|
||||||
with open(locale_file, 'r', encoding='utf-8') as f:
|
|
||||||
return json.load(f)
|
|
||||||
except Exception as e:
|
|
||||||
print(f"Error loading translations for {language}: {e}")
|
|
||||||
|
|
||||||
# Fallback to default language
|
|
||||||
try:
|
|
||||||
with open(f'locales/{DEFAULT_LANGUAGE}.json', 'r', encoding='utf-8') as f:
|
|
||||||
return json.load(f)
|
|
||||||
except Exception as e:
|
|
||||||
print(f"Error loading default translations: {e}")
|
|
||||||
return {}
|
|
||||||
|
|
||||||
def get_current_language():
|
|
||||||
"""Get current language from session or default"""
|
|
||||||
return session.get('language', DEFAULT_LANGUAGE)
|
|
||||||
|
|
||||||
def get_translations():
|
|
||||||
"""Get translations for current language"""
|
|
||||||
return load_translations(get_current_language())
|
|
||||||
|
|
||||||
def is_mobile_device():
|
|
||||||
"""Check if the request is coming from a mobile device"""
|
|
||||||
user_agent = request.headers.get('User-Agent', '').lower()
|
|
||||||
mobile_patterns = [
|
|
||||||
r'android', r'iphone', r'ipad', r'ipod', r'blackberry',
|
|
||||||
r'iemobile', r'opera mini', r'mobile', r'tablet'
|
|
||||||
]
|
|
||||||
return any(re.search(pattern, user_agent) for pattern in mobile_patterns)
|
|
||||||
|
|
||||||
def calculate_tens_from_targets(targets):
|
|
||||||
"""Calculate the number of 10s from a targets dictionary"""
|
|
||||||
tens_count = 0
|
|
||||||
if not targets:
|
|
||||||
return 0
|
|
||||||
|
|
||||||
for target in targets.values():
|
|
||||||
if isinstance(target, dict):
|
|
||||||
for shot_key, shot_value in target.items():
|
|
||||||
if shot_key.startswith('shot') and shot_value == 10:
|
|
||||||
tens_count += 1
|
|
||||||
|
|
||||||
return tens_count
|
|
||||||
|
|
||||||
# Define streams globally so both routes can access them
|
|
||||||
STREAMS = [
|
STREAMS = [
|
||||||
{'name': 'Target1', 'url': 'http://192.168.0.134:9081'},
|
{'name': 'Target1', 'url': 'http://192.168.0.134:9081'},
|
||||||
{'name': 'Target2', 'url': 'http://192.168.0.134:9082'},
|
{'name': 'Target2', 'url': 'http://192.168.0.134:9082'},
|
||||||
@@ -73,455 +40,89 @@ STREAMS = [
|
|||||||
{'name': 'Target6', 'url': 'http://192.168.0.134:9086'},
|
{'name': 'Target6', 'url': 'http://192.168.0.134:9086'},
|
||||||
]
|
]
|
||||||
|
|
||||||
# Settings file paths
|
# Language Configuration
|
||||||
SETTINGS_FILE = 'camera_settings.json'
|
SUPPORTED_LANGUAGES = ['sl', 'en']
|
||||||
PLAYERS_FILE = 'players.json'
|
DEFAULT_LANGUAGE = 'sl'
|
||||||
TOURNAMENT_FILE = 'tournament_state.json'
|
|
||||||
RESULTS_FILE = 'tournament_results.json'
|
|
||||||
LEAGUE_FILE = 'league_state.json'
|
|
||||||
ARCHIVE_DIR = 'tournament_archives'
|
|
||||||
LEAGUE_ARCHIVE_DIR = 'league_archives'
|
|
||||||
|
|
||||||
# Default settings
|
# Data file paths (organized in data directory)
|
||||||
DEFAULT_SETTINGS = {
|
ARCHIVE_DIR = 'data/tournament_archives'
|
||||||
'camera_titles': {
|
LEAGUE_ARCHIVE_DIR = 'data/league_archives'
|
||||||
'1': 'Camera 1',
|
|
||||||
'2': 'Camera 2',
|
|
||||||
'3': 'Camera 3',
|
|
||||||
'4': 'Camera 4',
|
|
||||||
'5': 'Camera 5',
|
|
||||||
'6': 'Camera 6'
|
|
||||||
},
|
|
||||||
'display_options': {
|
|
||||||
'show_titles': True,
|
|
||||||
'title_size': 1.1
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
# Default players structure
|
|
||||||
DEFAULT_PLAYERS = {
|
|
||||||
'players': [
|
|
||||||
{'id': 1, 'name': 'Player 1', 'enabled': True},
|
|
||||||
{'id': 2, 'name': 'Player 2', 'enabled': True},
|
|
||||||
{'id': 3, 'name': 'Player 3', 'enabled': True},
|
|
||||||
{'id': 4, 'name': 'Player 4', 'enabled': True},
|
|
||||||
{'id': 5, 'name': 'Player 5', 'enabled': True},
|
|
||||||
{'id': 6, 'name': 'Player 6', 'enabled': True},
|
|
||||||
]
|
|
||||||
}
|
|
||||||
|
|
||||||
|
# Convenience function wrappers that delegate to storage classes
|
||||||
def load_settings():
|
def load_settings():
|
||||||
"""Load settings from JSON file, create with defaults if not exists"""
|
return SettingsStorage.load_settings()
|
||||||
try:
|
|
||||||
if os.path.exists(SETTINGS_FILE):
|
|
||||||
with open(SETTINGS_FILE, 'r') as f:
|
|
||||||
settings = json.load(f)
|
|
||||||
# Ensure all required keys exist (for backwards compatibility)
|
|
||||||
for key in DEFAULT_SETTINGS:
|
|
||||||
if key not in settings:
|
|
||||||
settings[key] = DEFAULT_SETTINGS[key]
|
|
||||||
for camera_id in DEFAULT_SETTINGS['camera_titles']:
|
|
||||||
if camera_id not in settings['camera_titles']:
|
|
||||||
settings['camera_titles'][camera_id] = DEFAULT_SETTINGS['camera_titles'][camera_id]
|
|
||||||
return settings
|
|
||||||
else:
|
|
||||||
return DEFAULT_SETTINGS.copy()
|
|
||||||
except (json.JSONDecodeError, IOError):
|
|
||||||
return DEFAULT_SETTINGS.copy()
|
|
||||||
|
|
||||||
def save_settings(settings):
|
def save_settings(settings):
|
||||||
"""Save settings to JSON file"""
|
return SettingsStorage.save_settings(settings)
|
||||||
try:
|
|
||||||
with open(SETTINGS_FILE, 'w') as f:
|
|
||||||
json.dump(settings, f, indent=2)
|
|
||||||
return True
|
|
||||||
except IOError:
|
|
||||||
return False
|
|
||||||
|
|
||||||
def load_players():
|
def load_players():
|
||||||
"""Load players from JSON file, create with defaults if not exists"""
|
return PlayerStorage.load_players()
|
||||||
try:
|
|
||||||
if os.path.exists(PLAYERS_FILE):
|
|
||||||
with open(PLAYERS_FILE, 'r') as f:
|
|
||||||
return json.load(f)
|
|
||||||
else:
|
|
||||||
save_players(DEFAULT_PLAYERS)
|
|
||||||
return DEFAULT_PLAYERS.copy()
|
|
||||||
except (json.JSONDecodeError, IOError):
|
|
||||||
return DEFAULT_PLAYERS.copy()
|
|
||||||
|
|
||||||
def save_players(players_data):
|
def save_players(players_data):
|
||||||
"""Save players to JSON file"""
|
return PlayerStorage.save_players(players_data)
|
||||||
try:
|
|
||||||
with open(PLAYERS_FILE, 'w') as f:
|
|
||||||
json.dump(players_data, f, indent=2)
|
|
||||||
return True
|
|
||||||
except IOError:
|
|
||||||
return False
|
|
||||||
|
|
||||||
def load_tournament_state():
|
def load_tournament_state():
|
||||||
"""Load tournament state from JSON file"""
|
return TournamentStorage.load_tournament_state()
|
||||||
try:
|
|
||||||
if os.path.exists(TOURNAMENT_FILE):
|
|
||||||
with open(TOURNAMENT_FILE, 'r') as f:
|
|
||||||
return json.load(f)
|
|
||||||
else:
|
|
||||||
return None
|
|
||||||
except (json.JSONDecodeError, IOError):
|
|
||||||
return None
|
|
||||||
|
|
||||||
def save_tournament_state(tournament_data):
|
def save_tournament_state(tournament_data):
|
||||||
"""Save tournament state to JSON file"""
|
return TournamentStorage.save_tournament_state(tournament_data)
|
||||||
try:
|
|
||||||
with open(TOURNAMENT_FILE, 'w') as f:
|
|
||||||
json.dump(tournament_data, f, indent=2)
|
|
||||||
return True
|
|
||||||
except IOError:
|
|
||||||
return False
|
|
||||||
|
|
||||||
def load_league_state():
|
def load_league_state():
|
||||||
"""Load league state from JSON file"""
|
return LeagueStorage.load_league_state()
|
||||||
try:
|
|
||||||
if os.path.exists(LEAGUE_FILE):
|
|
||||||
with open(LEAGUE_FILE, 'r') as f:
|
|
||||||
return json.load(f)
|
|
||||||
else:
|
|
||||||
return None
|
|
||||||
except (json.JSONDecodeError, IOError):
|
|
||||||
return None
|
|
||||||
|
|
||||||
def save_league_state(league_data):
|
def save_league_state(league_data):
|
||||||
"""Save league state to JSON file"""
|
return LeagueStorage.save_league_state(league_data)
|
||||||
try:
|
|
||||||
with open(LEAGUE_FILE, 'w') as f:
|
|
||||||
json.dump(league_data, f, indent=2)
|
|
||||||
return True
|
|
||||||
except IOError:
|
|
||||||
return False
|
|
||||||
|
|
||||||
def load_results():
|
def load_results():
|
||||||
"""Load results from JSON file"""
|
return ResultsStorage.load_results()
|
||||||
try:
|
|
||||||
if os.path.exists(RESULTS_FILE):
|
|
||||||
with open(RESULTS_FILE, 'r') as f:
|
|
||||||
return json.load(f)
|
|
||||||
else:
|
|
||||||
return None
|
|
||||||
except (json.JSONDecodeError, IOError):
|
|
||||||
return None
|
|
||||||
|
|
||||||
def save_results(results_data):
|
def save_results(results_data):
|
||||||
"""Save results to JSON file"""
|
return ResultsStorage.save_results(results_data)
|
||||||
try:
|
|
||||||
with open(RESULTS_FILE, 'w') as f:
|
|
||||||
json.dump(results_data, f, indent=2)
|
|
||||||
return True
|
|
||||||
except IOError:
|
|
||||||
return False
|
|
||||||
|
|
||||||
def archive_tournament(tournament_data, results_data):
|
def archive_tournament(tournament_data, results_data):
|
||||||
"""Archive completed tournament data"""
|
return ArchiveStorage.archive_tournament(tournament_data, results_data)
|
||||||
try:
|
|
||||||
# Create archive directory if it doesn't exist
|
|
||||||
if not os.path.exists(ARCHIVE_DIR):
|
|
||||||
os.makedirs(ARCHIVE_DIR)
|
|
||||||
|
|
||||||
# Create filename with timestamp
|
|
||||||
timestamp = datetime.now().strftime("%Y%m%d_%H%M%S")
|
|
||||||
archive_filename = f"tournament_{timestamp}.json"
|
|
||||||
archive_path = os.path.join(ARCHIVE_DIR, archive_filename)
|
|
||||||
|
|
||||||
# Combine tournament and results data
|
|
||||||
archive_data = {
|
|
||||||
'tournament': tournament_data,
|
|
||||||
'results': results_data,
|
|
||||||
'archived_at': datetime.now().isoformat()
|
|
||||||
}
|
|
||||||
|
|
||||||
# Save to archive
|
|
||||||
with open(archive_path, 'w') as f:
|
|
||||||
json.dump(archive_data, f, indent=2)
|
|
||||||
|
|
||||||
print(f"Tournament archived to: {archive_path}")
|
|
||||||
return True
|
|
||||||
except Exception as e:
|
|
||||||
print(f"Error archiving tournament: {e}")
|
|
||||||
return False
|
|
||||||
|
|
||||||
def archive_league(league_data):
|
def archive_league(league_data):
|
||||||
"""Archive completed league data"""
|
return ArchiveStorage.archive_league(league_data)
|
||||||
try:
|
|
||||||
if not os.path.exists(LEAGUE_ARCHIVE_DIR):
|
|
||||||
os.makedirs(LEAGUE_ARCHIVE_DIR)
|
|
||||||
|
|
||||||
timestamp = datetime.now().strftime("%Y%m%d_%H%M%S")
|
|
||||||
archive_filename = f"league_{timestamp}.json"
|
|
||||||
archive_path = os.path.join(LEAGUE_ARCHIVE_DIR, archive_filename)
|
|
||||||
|
|
||||||
archive_data = {
|
|
||||||
'league': league_data,
|
|
||||||
'archived_at': datetime.now().isoformat()
|
|
||||||
}
|
|
||||||
|
|
||||||
with open(archive_path, 'w') as f:
|
|
||||||
json.dump(archive_data, f, indent=2)
|
|
||||||
|
|
||||||
print(f"League archived to: {archive_path}")
|
|
||||||
return True
|
|
||||||
except Exception as e:
|
|
||||||
print(f"Error archiving league: {e}")
|
|
||||||
return False
|
|
||||||
|
|
||||||
|
# Convenience wrappers that delegate to modular classes
|
||||||
def create_league(enabled_players, tournament_type):
|
def create_league(enabled_players, tournament_type):
|
||||||
"""Create a new league with 5 tournaments (changed from 6)"""
|
return Tournament.create_league(enabled_players, tournament_type)
|
||||||
league_id = f"league_{datetime.now().strftime('%Y%m%d_%H%M%S')}"
|
|
||||||
|
|
||||||
league_data = {
|
|
||||||
'league_id': league_id,
|
|
||||||
'created_at': datetime.now().isoformat(),
|
|
||||||
'tournament_type': tournament_type,
|
|
||||||
'total_tournaments': 5, # Changed from 6 to 5
|
|
||||||
'current_tournament': 0, # Will be 1 when first tournament starts
|
|
||||||
'participants': {},
|
|
||||||
'completed_tournaments': [],
|
|
||||||
'league_finished': False
|
|
||||||
}
|
|
||||||
|
|
||||||
# Initialize participants
|
|
||||||
for player in enabled_players:
|
|
||||||
league_data['participants'][str(player['id'])] = {
|
|
||||||
'name': player['name'],
|
|
||||||
'joker_used': False,
|
|
||||||
'tournament_results': [],
|
|
||||||
'total_score': 0,
|
|
||||||
'final_score': 0, # Best 4 tournaments (changed from 5)
|
|
||||||
'tournaments_participated': 0
|
|
||||||
}
|
|
||||||
|
|
||||||
return league_data
|
|
||||||
|
|
||||||
def create_draft(enabled_players, tournament_type='20_targets', league_tournament_number=None):
|
def create_draft(enabled_players, tournament_type='20_targets', league_tournament_number=None):
|
||||||
"""Create draft groups of 6 players and organize rounds"""
|
return Tournament.create_draft(enabled_players, tournament_type, league_tournament_number)
|
||||||
if len(enabled_players) < 1:
|
|
||||||
return None
|
|
||||||
|
|
||||||
# Shuffle players for random grouping
|
|
||||||
players_copy = enabled_players.copy()
|
|
||||||
random.shuffle(players_copy)
|
|
||||||
|
|
||||||
# Create groups of up to 6
|
|
||||||
groups = []
|
|
||||||
for i in range(0, len(players_copy), 6):
|
|
||||||
group = players_copy[i:i+6]
|
|
||||||
groups.append(group)
|
|
||||||
|
|
||||||
# Create rounds
|
|
||||||
rounds = []
|
|
||||||
for i, group in enumerate(groups):
|
|
||||||
rounds.append({
|
|
||||||
'round_number': i + 1,
|
|
||||||
'players': group,
|
|
||||||
'status': 'pending' if i == 0 else 'waiting'
|
|
||||||
})
|
|
||||||
|
|
||||||
tournament_data = {
|
|
||||||
'rounds': rounds,
|
|
||||||
'created_at': datetime.now().isoformat(),
|
|
||||||
'total_players': len(enabled_players),
|
|
||||||
'total_rounds': len(rounds),
|
|
||||||
'current_round': 1,
|
|
||||||
'tournament_type': tournament_type
|
|
||||||
}
|
|
||||||
|
|
||||||
if league_tournament_number:
|
|
||||||
tournament_data['league_tournament_number'] = league_tournament_number
|
|
||||||
|
|
||||||
return tournament_data
|
|
||||||
|
|
||||||
def create_results_structure(tournament_data):
|
def create_results_structure(tournament_data):
|
||||||
"""Create results structure for a tournament"""
|
return Tournament.create_results_structure(tournament_data)
|
||||||
if not tournament_data:
|
|
||||||
return None
|
|
||||||
|
|
||||||
tournament_type = tournament_data.get('tournament_type', '20_targets')
|
|
||||||
|
|
||||||
# Determine target count and shots per target
|
|
||||||
if tournament_type == '40_targets':
|
|
||||||
num_targets = 40
|
|
||||||
shots_per_target = 2
|
|
||||||
elif tournament_type == '4_targets':
|
|
||||||
num_targets = 4
|
|
||||||
shots_per_target = 5
|
|
||||||
else: # 20_targets (default)
|
|
||||||
num_targets = 20
|
|
||||||
shots_per_target = 2
|
|
||||||
|
|
||||||
results = {
|
|
||||||
'tournament_id': tournament_data.get('created_at', datetime.now().isoformat()),
|
|
||||||
'tournament_type': tournament_type,
|
|
||||||
'participants': {},
|
|
||||||
'tournament_finished': False,
|
|
||||||
'created_at': datetime.now().isoformat()
|
|
||||||
}
|
|
||||||
|
|
||||||
# Add league info if present
|
|
||||||
if 'league_tournament_number' in tournament_data:
|
|
||||||
results['league_tournament_number'] = tournament_data['league_tournament_number']
|
|
||||||
|
|
||||||
# Create structure for each participant
|
|
||||||
all_players = []
|
|
||||||
for round_data in tournament_data['rounds']:
|
|
||||||
all_players.extend(round_data['players'])
|
|
||||||
|
|
||||||
for player in all_players:
|
|
||||||
player_id = str(player['id'])
|
|
||||||
|
|
||||||
# Create target structure based on tournament type
|
|
||||||
targets = {}
|
|
||||||
for i in range(1, num_targets + 1):
|
|
||||||
target = {}
|
|
||||||
for j in range(1, shots_per_target + 1):
|
|
||||||
target[f'shot{j}'] = None
|
|
||||||
targets[str(i)] = target
|
|
||||||
|
|
||||||
results['participants'][player_id] = {
|
|
||||||
'name': player['name'],
|
|
||||||
'targets': targets,
|
|
||||||
'total_score': 0,
|
|
||||||
'completed': False
|
|
||||||
}
|
|
||||||
|
|
||||||
return results
|
|
||||||
|
|
||||||
def calculate_total_score(targets):
|
def calculate_total_score(targets):
|
||||||
"""Calculate total score from targets, treating None as 0"""
|
return Scoring.calculate_total_score(targets)
|
||||||
total = 0
|
|
||||||
for target in targets.values():
|
|
||||||
for shot_key, shot_value in target.items():
|
|
||||||
if shot_key.startswith('shot') and shot_value is not None:
|
|
||||||
total += shot_value
|
|
||||||
return total
|
|
||||||
|
|
||||||
def is_participant_completed(targets):
|
def is_participant_completed(targets):
|
||||||
"""Check if a participant has completed all targets (all shots entered, including 0s)"""
|
return Scoring.is_participant_completed(targets)
|
||||||
for target in targets.values():
|
|
||||||
for shot_key, shot_value in target.items():
|
|
||||||
if shot_key.startswith('shot') and shot_value is None:
|
|
||||||
return False
|
|
||||||
return True
|
|
||||||
|
|
||||||
def calculate_league_final_scores(league_data):
|
def calculate_league_final_scores(league_data):
|
||||||
"""Calculate final league scores using best 4 tournaments (changed from best 5)"""
|
return Scoring.calculate_league_final_scores(league_data)
|
||||||
for participant_id, participant in league_data['participants'].items():
|
|
||||||
tournament_scores = []
|
|
||||||
|
|
||||||
# Get all tournament scores where player participated
|
|
||||||
for result in participant['tournament_results']:
|
|
||||||
if result['participated']:
|
|
||||||
tournament_scores.append(result['score'])
|
|
||||||
|
|
||||||
# Sort scores descending and take best 4 (changed from 5)
|
|
||||||
tournament_scores.sort(reverse=True)
|
|
||||||
best_scores = tournament_scores[:4] if len(tournament_scores) > 4 else tournament_scores
|
|
||||||
|
|
||||||
participant['final_score'] = sum(best_scores)
|
|
||||||
participant['tournaments_participated'] = len(tournament_scores)
|
|
||||||
|
|
||||||
def get_league_final_rankings(league_data):
|
|
||||||
"""Get final league rankings sorted by final score"""
|
|
||||||
participants = []
|
|
||||||
for player_id, data in league_data['participants'].items():
|
|
||||||
# Calculate total 10s across all tournaments
|
|
||||||
total_tens = sum(result.get('tens_count', 0) for result in data['tournament_results'] if result.get('participated', False))
|
|
||||||
|
|
||||||
participants.append({
|
|
||||||
'id': player_id,
|
|
||||||
'name': data['name'],
|
|
||||||
'final_score': data['final_score'],
|
|
||||||
'total_score': data['total_score'],
|
|
||||||
'tournaments_participated': data['tournaments_participated'],
|
|
||||||
'joker_used': data['joker_used'],
|
|
||||||
'tournament_results': data['tournament_results'],
|
|
||||||
'total_tens': total_tens
|
|
||||||
})
|
|
||||||
|
|
||||||
# Sort by final score (best 5 tournaments) descending, then by total 10s for tiebreaking
|
|
||||||
participants.sort(key=lambda x: (x['final_score'], x['total_tens']), reverse=True)
|
|
||||||
|
|
||||||
# Add rankings
|
|
||||||
for i, participant in enumerate(participants):
|
|
||||||
participant['rank'] = i + 1
|
|
||||||
|
|
||||||
return participants
|
|
||||||
|
|
||||||
def get_current_round_data():
|
def get_league_final_rankings(league_data):
|
||||||
"""Get current round data from tournament"""
|
return Scoring.get_league_final_rankings(league_data)
|
||||||
tournament_state = load_tournament_state()
|
|
||||||
if not tournament_state:
|
|
||||||
return None
|
|
||||||
|
|
||||||
current_round_num = tournament_state.get('current_round', 1)
|
|
||||||
|
|
||||||
# Find the current round
|
|
||||||
for round_data in tournament_state['rounds']:
|
|
||||||
if round_data['round_number'] == current_round_num:
|
|
||||||
return round_data
|
|
||||||
|
|
||||||
return None
|
|
||||||
|
|
||||||
def calculate_current_league_standings(league_data):
|
def calculate_current_league_standings(league_data):
|
||||||
"""Calculate current league standings during active league"""
|
return Scoring.calculate_current_league_standings(league_data)
|
||||||
participants = []
|
|
||||||
for player_id, data in league_data['participants'].items():
|
def get_current_round_data():
|
||||||
# Calculate current standings based on completed tournaments
|
tournament_state = load_tournament_state()
|
||||||
tournament_scores = []
|
return RoundManager.get_current_round_data(tournament_state)
|
||||||
completed_tournaments = 0
|
|
||||||
total_tens = 0
|
|
||||||
|
|
||||||
for result in data['tournament_results']:
|
|
||||||
if result['participated']:
|
|
||||||
tournament_scores.append(result['score'])
|
|
||||||
completed_tournaments += 1
|
|
||||||
total_tens += result.get('tens_count', 0)
|
|
||||||
|
|
||||||
# Current score is sum of all completed tournaments
|
|
||||||
current_total = sum(tournament_scores)
|
|
||||||
|
|
||||||
# For display, show what the final score would be if we took best 5 now
|
|
||||||
tournament_scores.sort(reverse=True)
|
|
||||||
projected_final = sum(tournament_scores[:5]) if len(tournament_scores) >= 5 else sum(tournament_scores)
|
|
||||||
|
|
||||||
participants.append({
|
|
||||||
'id': player_id,
|
|
||||||
'name': data['name'],
|
|
||||||
'current_total': current_total,
|
|
||||||
'projected_final': projected_final,
|
|
||||||
'tournaments_completed': completed_tournaments,
|
|
||||||
'joker_used': data['joker_used'],
|
|
||||||
'tournament_results': data['tournament_results'],
|
|
||||||
'total_tens': total_tens
|
|
||||||
})
|
|
||||||
|
|
||||||
# Sort by current total score (descending), then by total 10s for tiebreaking
|
|
||||||
participants.sort(key=lambda x: (x['current_total'], x['total_tens']), reverse=True)
|
|
||||||
|
|
||||||
# Add rankings
|
|
||||||
for i, participant in enumerate(participants):
|
|
||||||
participant['rank'] = i + 1
|
|
||||||
|
|
||||||
return participants
|
|
||||||
|
|
||||||
def get_league_current_standings(league_state):
|
def get_league_current_standings(league_state):
|
||||||
"""Get current league standings including in-progress tournament"""
|
"""Get current league standings including in-progress tournament"""
|
||||||
if not league_state:
|
if not league_state:
|
||||||
return []
|
return []
|
||||||
|
|
||||||
# Start with current league participants
|
|
||||||
participants = []
|
participants = []
|
||||||
for player_id, data in league_state['participants'].items():
|
for player_id, data in league_state['participants'].items():
|
||||||
# Calculate total 10s from completed tournaments
|
|
||||||
total_tens = sum(result.get('tens_count', 0) for result in data['tournament_results'] if result.get('participated', False))
|
total_tens = sum(result.get('tens_count', 0) for result in data['tournament_results'] if result.get('participated', False))
|
||||||
|
|
||||||
participant = {
|
participant = {
|
||||||
'id': player_id,
|
'id': player_id,
|
||||||
'name': data['name'],
|
'name': data['name'],
|
||||||
@@ -531,128 +132,36 @@ def get_league_current_standings(league_state):
|
|||||||
'joker_used': data['joker_used'],
|
'joker_used': data['joker_used'],
|
||||||
'tournament_results': data['tournament_results'],
|
'tournament_results': data['tournament_results'],
|
||||||
'total_tens': total_tens,
|
'total_tens': total_tens,
|
||||||
'current_tournament_score': 0, # Score from current tournament
|
'current_tournament_score': 0,
|
||||||
'current_tournament_participating': False
|
'current_tournament_participating': False
|
||||||
}
|
}
|
||||||
participants.append(participant)
|
participants.append(participant)
|
||||||
|
|
||||||
# Add current tournament scores if available
|
|
||||||
current_results = load_results()
|
current_results = load_results()
|
||||||
if current_results and not current_results.get('tournament_finished', False):
|
if current_results and not current_results.get('tournament_finished', False):
|
||||||
for player_id, result_data in current_results['participants'].items():
|
for player_id, result_data in current_results['participants'].items():
|
||||||
# Find this participant in our list
|
|
||||||
for participant in participants:
|
for participant in participants:
|
||||||
if participant['id'] == player_id:
|
if participant['id'] == player_id:
|
||||||
participant['current_tournament_score'] = result_data['total_score']
|
participant['current_tournament_score'] = result_data['total_score']
|
||||||
participant['current_tournament_participating'] = True
|
participant['current_tournament_participating'] = True
|
||||||
break
|
break
|
||||||
|
|
||||||
# Sort by final score (best 5 tournaments) descending, then by total 10s for tiebreaking
|
|
||||||
participants.sort(key=lambda x: (x['final_score'], x['total_tens']), reverse=True)
|
participants.sort(key=lambda x: (x['final_score'], x['total_tens']), reverse=True)
|
||||||
|
|
||||||
# Add rankings
|
|
||||||
for i, participant in enumerate(participants):
|
for i, participant in enumerate(participants):
|
||||||
participant['rank'] = i + 1
|
participant['rank'] = i + 1
|
||||||
|
|
||||||
return participants
|
return participants
|
||||||
|
|
||||||
# Add these functions after the existing helper functions in app.py
|
# Archive functions
|
||||||
|
|
||||||
def get_archived_tournaments():
|
def get_archived_tournaments():
|
||||||
"""Get list of standalone archived tournaments (excluding league tournaments)"""
|
return ArchiveStorage.get_archived_tournaments()
|
||||||
try:
|
|
||||||
if not os.path.exists(ARCHIVE_DIR):
|
|
||||||
return []
|
|
||||||
|
|
||||||
archives = []
|
|
||||||
for file_path in glob.glob(os.path.join(ARCHIVE_DIR, "tournament_*.json")):
|
|
||||||
try:
|
|
||||||
with open(file_path, 'r') as f:
|
|
||||||
data = json.load(f)
|
|
||||||
|
|
||||||
# Extract metadata
|
|
||||||
filename = os.path.basename(file_path)
|
|
||||||
archived_at = data.get('archived_at', 'Unknown')
|
|
||||||
tournament_data = data.get('tournament', {})
|
|
||||||
results_data = data.get('results', {})
|
|
||||||
|
|
||||||
# Skip tournaments that are part of a league
|
|
||||||
if tournament_data.get('league_tournament_number') or results_data.get('league_tournament_number'):
|
|
||||||
continue
|
|
||||||
|
|
||||||
archive_info = {
|
|
||||||
'filename': filename,
|
|
||||||
'filepath': file_path,
|
|
||||||
'archived_at': archived_at,
|
|
||||||
'created_at': tournament_data.get('created_at', 'Unknown'),
|
|
||||||
'tournament_type': tournament_data.get('tournament_type', '20_targets'),
|
|
||||||
'total_players': tournament_data.get('total_players', 0),
|
|
||||||
'total_rounds': tournament_data.get('total_rounds', 0),
|
|
||||||
'tournament_finished': results_data.get('tournament_finished', False),
|
|
||||||
'participants_count': len(results_data.get('participants', {}))
|
|
||||||
}
|
|
||||||
|
|
||||||
archives.append(archive_info)
|
|
||||||
except (json.JSONDecodeError, IOError) as e:
|
|
||||||
print(f"Error reading archive {file_path}: {e}")
|
|
||||||
continue
|
|
||||||
|
|
||||||
# Sort by archived date (newest first)
|
|
||||||
archives.sort(key=lambda x: x['archived_at'], reverse=True)
|
|
||||||
return archives
|
|
||||||
except Exception as e:
|
|
||||||
print(f"Error getting archived tournaments: {e}")
|
|
||||||
return []
|
|
||||||
|
|
||||||
def get_archived_leagues():
|
def get_archived_leagues():
|
||||||
"""Get list of all archived leagues"""
|
return ArchiveStorage.get_archived_leagues()
|
||||||
try:
|
|
||||||
if not os.path.exists(LEAGUE_ARCHIVE_DIR):
|
|
||||||
return []
|
|
||||||
|
|
||||||
archives = []
|
|
||||||
for file_path in glob.glob(os.path.join(LEAGUE_ARCHIVE_DIR, "league_*.json")):
|
|
||||||
try:
|
|
||||||
with open(file_path, 'r') as f:
|
|
||||||
data = json.load(f)
|
|
||||||
|
|
||||||
filename = os.path.basename(file_path)
|
|
||||||
archived_at = data.get('archived_at', 'Unknown')
|
|
||||||
league_data = data.get('league', {})
|
|
||||||
|
|
||||||
archive_info = {
|
|
||||||
'filename': filename,
|
|
||||||
'filepath': file_path,
|
|
||||||
'archived_at': archived_at,
|
|
||||||
'created_at': league_data.get('created_at', 'Unknown'),
|
|
||||||
'league_id': league_data.get('league_id', 'Unknown'),
|
|
||||||
'tournament_type': league_data.get('tournament_type', '20_targets'),
|
|
||||||
'total_tournaments': league_data.get('total_tournaments', 6),
|
|
||||||
'participants_count': len(league_data.get('participants', {})),
|
|
||||||
'league_finished': league_data.get('league_finished', False),
|
|
||||||
'completed_tournaments': len(league_data.get('completed_tournaments', []))
|
|
||||||
}
|
|
||||||
|
|
||||||
archives.append(archive_info)
|
|
||||||
except (json.JSONDecodeError, IOError) as e:
|
|
||||||
print(f"Error reading league archive {file_path}: {e}")
|
|
||||||
continue
|
|
||||||
|
|
||||||
# Sort by archived date (newest first)
|
|
||||||
archives.sort(key=lambda x: x['archived_at'], reverse=True)
|
|
||||||
return archives
|
|
||||||
except Exception as e:
|
|
||||||
print(f"Error getting archived leagues: {e}")
|
|
||||||
return []
|
|
||||||
|
|
||||||
def load_archive_file(filepath):
|
def load_archive_file(filepath):
|
||||||
"""Load a specific archive file"""
|
return ArchiveStorage.load_archive_file(filepath)
|
||||||
try:
|
|
||||||
with open(filepath, 'r') as f:
|
|
||||||
return json.load(f)
|
|
||||||
except (json.JSONDecodeError, IOError) as e:
|
|
||||||
print(f"Error loading archive file {filepath}: {e}")
|
|
||||||
return None
|
|
||||||
|
|
||||||
def analyze_player_performance(player_id, archives_data):
|
def analyze_player_performance(player_id, archives_data):
|
||||||
"""Analyze performance of a specific player across all archives"""
|
"""Analyze performance of a specific player across all archives"""
|
||||||
@@ -819,9 +328,9 @@ def get_all_players_from_archives():
|
|||||||
|
|
||||||
|
|
||||||
|
|
||||||
# Add these routes after the existing routes in app.py
|
# ============================================================================
|
||||||
|
# Flask Routes
|
||||||
# Add this to your app.py file to integrate the modern archive system
|
# ============================================================================
|
||||||
|
|
||||||
# Replace your existing archive routes with these updated ones:
|
# Replace your existing archive routes with these updated ones:
|
||||||
|
|
||||||
@@ -1190,7 +699,9 @@ def index():
|
|||||||
if i < len(players):
|
if i < len(players):
|
||||||
tournament_titles[str(i + 1)] = players[i]['name']
|
tournament_titles[str(i + 1)] = players[i]['name']
|
||||||
else:
|
else:
|
||||||
tournament_titles[str(i + 1)] = 'Empty'
|
# Use "Prazno" for Slovenian, "Empty" for English
|
||||||
|
current_language = get_current_language()
|
||||||
|
tournament_titles[str(i + 1)] = 'Prazno' if current_language == 'sl' else 'Empty'
|
||||||
|
|
||||||
# Create a copy of settings with tournament titles
|
# Create a copy of settings with tournament titles
|
||||||
display_settings = settings.copy()
|
display_settings = settings.copy()
|
||||||
@@ -1572,13 +1083,13 @@ def update_settings():
|
|||||||
|
|
||||||
if 'display_options' in new_settings:
|
if 'display_options' in new_settings:
|
||||||
current_settings['display_options'].update(new_settings['display_options'])
|
current_settings['display_options'].update(new_settings['display_options'])
|
||||||
|
|
||||||
# Save updated settings
|
# Save updated settings
|
||||||
if save_settings(current_settings):
|
if save_settings(current_settings):
|
||||||
return jsonify({'status': 'success', 'settings': current_settings})
|
return jsonify({'status': 'success', 'settings': current_settings})
|
||||||
else:
|
else:
|
||||||
return jsonify({'status': 'error', 'message': 'Failed to save settings'}), 500
|
return jsonify({'status': 'error', 'message': 'Failed to save settings'}), 500
|
||||||
|
|
||||||
except Exception as e:
|
except Exception as e:
|
||||||
return jsonify({'status': 'error', 'message': str(e)}), 400
|
return jsonify({'status': 'error', 'message': str(e)}), 400
|
||||||
|
|
||||||
@@ -1593,12 +1104,12 @@ def update_players():
|
|||||||
"""API endpoint to update players"""
|
"""API endpoint to update players"""
|
||||||
try:
|
try:
|
||||||
players_data = request.get_json()
|
players_data = request.get_json()
|
||||||
|
|
||||||
if save_players(players_data):
|
if save_players(players_data):
|
||||||
return jsonify({'status': 'success', 'players': players_data})
|
return jsonify({'status': 'success', 'players': players_data})
|
||||||
else:
|
else:
|
||||||
return jsonify({'status': 'error', 'message': 'Failed to save players'}), 500
|
return jsonify({'status': 'error', 'message': 'Failed to save players'}), 500
|
||||||
|
|
||||||
except Exception as e:
|
except Exception as e:
|
||||||
return jsonify({'status': 'error', 'message': str(e)}), 400
|
return jsonify({'status': 'error', 'message': str(e)}), 400
|
||||||
|
|
||||||
@@ -1626,12 +1137,12 @@ def add_player():
|
|||||||
}
|
}
|
||||||
|
|
||||||
players_data['players'].append(new_player)
|
players_data['players'].append(new_player)
|
||||||
|
|
||||||
if save_players(players_data):
|
if save_players(players_data):
|
||||||
return jsonify({'status': 'success', 'player': new_player})
|
return jsonify({'status': 'success', 'player': new_player})
|
||||||
else:
|
else:
|
||||||
return jsonify({'status': 'error', 'message': 'Failed to save player'}), 500
|
return jsonify({'status': 'error', 'message': 'Failed to save player'}), 500
|
||||||
|
|
||||||
except Exception as e:
|
except Exception as e:
|
||||||
return jsonify({'status': 'error', 'message': str(e)}), 400
|
return jsonify({'status': 'error', 'message': str(e)}), 400
|
||||||
|
|
||||||
@@ -1640,15 +1151,15 @@ def delete_player(player_id):
|
|||||||
"""API endpoint to delete a player"""
|
"""API endpoint to delete a player"""
|
||||||
try:
|
try:
|
||||||
players_data = load_players()
|
players_data = load_players()
|
||||||
|
|
||||||
# Find and remove the player
|
# Find and remove the player
|
||||||
players_data['players'] = [p for p in players_data['players'] if p['id'] != player_id]
|
players_data['players'] = [p for p in players_data['players'] if p['id'] != player_id]
|
||||||
|
|
||||||
if save_players(players_data):
|
if save_players(players_data):
|
||||||
return jsonify({'status': 'success'})
|
return jsonify({'status': 'success'})
|
||||||
else:
|
else:
|
||||||
return jsonify({'status': 'error', 'message': 'Failed to save players'}), 500
|
return jsonify({'status': 'error', 'message': 'Failed to save players'}), 500
|
||||||
|
|
||||||
except Exception as e:
|
except Exception as e:
|
||||||
return jsonify({'status': 'error', 'message': str(e)}), 400
|
return jsonify({'status': 'error', 'message': str(e)}), 400
|
||||||
|
|
||||||
@@ -1667,7 +1178,7 @@ def update_player(player_id):
|
|||||||
if 'enabled' in data:
|
if 'enabled' in data:
|
||||||
player['enabled'] = data['enabled']
|
player['enabled'] = data['enabled']
|
||||||
break
|
break
|
||||||
|
|
||||||
if save_players(players_data):
|
if save_players(players_data):
|
||||||
return jsonify({'status': 'success', 'player': player})
|
return jsonify({'status': 'success', 'player': player})
|
||||||
else:
|
else:
|
||||||
@@ -1804,12 +1315,12 @@ def start_tournament():
|
|||||||
return jsonify({'status': 'error', 'message': 'Need at least 1 enabled player'}), 400
|
return jsonify({'status': 'error', 'message': 'Need at least 1 enabled player'}), 400
|
||||||
|
|
||||||
tournament_data = create_draft(enabled_players, tournament_type)
|
tournament_data = create_draft(enabled_players, tournament_type)
|
||||||
|
|
||||||
if save_tournament_state(tournament_data):
|
if save_tournament_state(tournament_data):
|
||||||
# Create results structure when tournament starts
|
# Create results structure when tournament starts
|
||||||
results = create_results_structure(tournament_data)
|
results = create_results_structure(tournament_data)
|
||||||
save_results(results)
|
save_results(results)
|
||||||
|
|
||||||
return jsonify({'status': 'success', 'tournament': tournament_data})
|
return jsonify({'status': 'success', 'tournament': tournament_data})
|
||||||
else:
|
else:
|
||||||
return jsonify({'status': 'error', 'message': 'Failed to save tournament'}), 500
|
return jsonify({'status': 'error', 'message': 'Failed to save tournament'}), 500
|
||||||
@@ -1821,15 +1332,19 @@ def start_tournament():
|
|||||||
def change_round(round_number):
|
def change_round(round_number):
|
||||||
"""API endpoint to change current round"""
|
"""API endpoint to change current round"""
|
||||||
try:
|
try:
|
||||||
|
print(f"[ROUND CHANGE] Attempting to change to round {round_number}")
|
||||||
tournament_state = load_tournament_state()
|
tournament_state = load_tournament_state()
|
||||||
if not tournament_state:
|
if not tournament_state:
|
||||||
|
print(f"[ROUND CHANGE] Error: No active tournament")
|
||||||
return jsonify({'status': 'error', 'message': 'No active tournament'}), 400
|
return jsonify({'status': 'error', 'message': 'No active tournament'}), 400
|
||||||
|
|
||||||
|
print(f"[ROUND CHANGE] Tournament found. Total rounds: {tournament_state.get('total_rounds')}")
|
||||||
if round_number < 1 or round_number > tournament_state['total_rounds']:
|
if round_number < 1 or round_number > tournament_state['total_rounds']:
|
||||||
|
print(f"[ROUND CHANGE] Error: Invalid round number {round_number}")
|
||||||
return jsonify({'status': 'error', 'message': 'Invalid round number'}), 400
|
return jsonify({'status': 'error', 'message': 'Invalid round number'}), 400
|
||||||
|
|
||||||
tournament_state['current_round'] = round_number
|
tournament_state['current_round'] = round_number
|
||||||
|
|
||||||
# Update round statuses
|
# Update round statuses
|
||||||
for round_data in tournament_state['rounds']:
|
for round_data in tournament_state['rounds']:
|
||||||
if round_data['round_number'] < round_number:
|
if round_data['round_number'] < round_number:
|
||||||
@@ -1838,13 +1353,20 @@ def change_round(round_number):
|
|||||||
round_data['status'] = 'pending'
|
round_data['status'] = 'pending'
|
||||||
else:
|
else:
|
||||||
round_data['status'] = 'waiting'
|
round_data['status'] = 'waiting'
|
||||||
|
|
||||||
|
print(f"[ROUND CHANGE] Saving tournament state...")
|
||||||
if save_tournament_state(tournament_state):
|
if save_tournament_state(tournament_state):
|
||||||
|
print(f"[ROUND CHANGE] Tournament saved successfully")
|
||||||
|
|
||||||
return jsonify({'status': 'success', 'tournament': tournament_state})
|
return jsonify({'status': 'success', 'tournament': tournament_state})
|
||||||
else:
|
else:
|
||||||
|
print(f"[ROUND CHANGE] Error: Failed to save tournament")
|
||||||
return jsonify({'status': 'error', 'message': 'Failed to save tournament'}), 500
|
return jsonify({'status': 'error', 'message': 'Failed to save tournament'}), 500
|
||||||
|
|
||||||
except Exception as e:
|
except Exception as e:
|
||||||
|
print(f"[ROUND CHANGE] Exception: {str(e)}")
|
||||||
|
import traceback
|
||||||
|
traceback.print_exc()
|
||||||
return jsonify({'status': 'error', 'message': str(e)}), 400
|
return jsonify({'status': 'error', 'message': str(e)}), 400
|
||||||
|
|
||||||
@app.route('/api/tournament/reset', methods=['POST'])
|
@app.route('/api/tournament/reset', methods=['POST'])
|
||||||
@@ -1886,12 +1408,12 @@ def update_participant_scores(player_id):
|
|||||||
# Check if all targets are completed (all shots entered, including 0s)
|
# Check if all targets are completed (all shots entered, including 0s)
|
||||||
all_completed = is_participant_completed(targets)
|
all_completed = is_participant_completed(targets)
|
||||||
results['participants'][player_id_str]['completed'] = all_completed
|
results['participants'][player_id_str]['completed'] = all_completed
|
||||||
|
|
||||||
if save_results(results):
|
if save_results(results):
|
||||||
return jsonify({'status': 'success', 'participant': results['participants'][player_id_str]})
|
return jsonify({'status': 'success', 'participant': results['participants'][player_id_str]})
|
||||||
else:
|
else:
|
||||||
return jsonify({'status': 'error', 'message': 'Failed to save results'}), 500
|
return jsonify({'status': 'error', 'message': 'Failed to save results'}), 500
|
||||||
|
|
||||||
except Exception as e:
|
except Exception as e:
|
||||||
return jsonify({'status': 'error', 'message': str(e)}), 400
|
return jsonify({'status': 'error', 'message': str(e)}), 400
|
||||||
|
|
||||||
@@ -2023,24 +1545,24 @@ def finish_tournament():
|
|||||||
# End the tournament by removing tournament state
|
# End the tournament by removing tournament state
|
||||||
if os.path.exists(TOURNAMENT_FILE):
|
if os.path.exists(TOURNAMENT_FILE):
|
||||||
os.remove(TOURNAMENT_FILE)
|
os.remove(TOURNAMENT_FILE)
|
||||||
|
|
||||||
# If league finished, also remove league state file
|
# If league finished, also remove league state file
|
||||||
if league_finished and os.path.exists(LEAGUE_FILE):
|
if league_finished and os.path.exists(LEAGUE_FILE):
|
||||||
os.remove(LEAGUE_FILE)
|
os.remove(LEAGUE_FILE)
|
||||||
|
|
||||||
response_data = {
|
response_data = {
|
||||||
'status': 'success',
|
'status': 'success',
|
||||||
'results': results,
|
'results': results,
|
||||||
'archived': archive_success,
|
'archived': archive_success,
|
||||||
'league_archived': league_archive_success if league_finished else None,
|
'league_archived': league_archive_success if league_finished else None,
|
||||||
'tournament_type': results.get('tournament_type', '20_targets'),
|
'tournament_type': results.get('tournament_type', '20_targets'),
|
||||||
'tournament_format': get_tournament_format_description(results.get('tournament_type', '20_targets'))
|
'tournament_format': get_tournament_format_description(results.get('tournament_type', '20_targets'))
|
||||||
}
|
}
|
||||||
|
|
||||||
if league_state:
|
if league_state:
|
||||||
response_data['league'] = league_state
|
response_data['league'] = league_state
|
||||||
response_data['league_finished'] = league_state.get('league_finished', False)
|
response_data['league_finished'] = league_state.get('league_finished', False)
|
||||||
|
|
||||||
return jsonify(response_data)
|
return jsonify(response_data)
|
||||||
else:
|
else:
|
||||||
return jsonify({'status': 'error', 'message': 'Failed to save results'}), 500
|
return jsonify({'status': 'error', 'message': 'Failed to save results'}), 500
|
||||||
Reference in New Issue
Block a user