Commit ba5481a0 authored by Your Name's avatar Your Name

Sexurity measures!

parent 5c8af90a
......@@ -178,6 +178,12 @@ Examples:
action='store_true',
help='Disable web dashboard (PyQt interface only)'
)
parser.add_argument(
'--edit-odds',
action='store_true',
help='Enable manual odds editing from web interface/API (admin only, default: disabled for security)'
)
# Screen cast options
......@@ -211,7 +217,7 @@ Examples:
parser.add_argument(
'--version',
action='version',
version='MbetterClient 1.0.16'
version='MbetterClient 1.0.19'
)
# Timer options
......@@ -311,6 +317,7 @@ def main():
settings.enable_qt = not args.no_qt and not args.headless
settings.enable_headless = args.headless
settings.enable_web = not args.no_web
settings.edit_odds = args.edit_odds
# Timer settings
if args.start_timer is not None:
......
......@@ -4,7 +4,7 @@ MbetterClient - Cross-platform multimedia client application
A multi-threaded application with video playback, web dashboard, and REST API integration.
"""
__version__ = "1.0.17"
__version__ = "1.0.19"
__author__ = "MBetter Project"
__email__ = "dev@mbetter.net"
__description__ = "Cross-platform multimedia client with video overlay and web dashboard"
......
......@@ -262,7 +262,7 @@ class ApiConfig:
# Request settings
verify_ssl: bool = True
user_agent: str = "MbetterClient/1.0r16"
user_agent: str = "MbetterClient/1.0r19"
max_response_size_mb: int = 100
# Additional API client settings
......@@ -403,7 +403,7 @@ class AppSettings:
timer: TimerConfig = field(default_factory=TimerConfig)
# Application settings
version: str = "1.0.17"
version: str = "1.0.19"
debug_mode: bool = False
dev_message: bool = False # Enable debug mode showing only message bus messages
debug_messages: bool = False # Show all messages passing through the message bus on screen
......@@ -415,6 +415,7 @@ class AppSettings:
enable_api_client: bool = True
enable_screen_cast: bool = True # Enabled by default, can be disabled with --no-screen-cast
enable_report_sync: bool = True # Enabled by default, can be disabled with --no-report-sync
edit_odds: bool = False # Disabled by default for security, enable with --edit-odds for admin access only
# Runtime settings (not persisted)
fullscreen: bool = True
......
......@@ -358,6 +358,7 @@ class WebDashboard(ThreadedComponent):
api_bp.config_manager = self.config_manager
api_bp.message_bus = self.message_bus
api_bp.socketio = self.socketio
api_bp.settings = self.settings
# Pass dependencies to screen cast blueprint
screen_cast_bp.message_bus = self.message_bus
......
......@@ -167,6 +167,7 @@ api_bp.auth_manager = None
api_bp.db_manager = None
api_bp.config_manager = None
api_bp.message_bus = None
api_bp.settings = None
# HLS Streaming Routes (no authentication required)
......@@ -2665,6 +2666,23 @@ def system_status():
return jsonify({"error": str(e)}), 500
@api_bp.route('/settings')
@get_api_auth_decorator()
def get_app_settings():
"""Get application settings including edit_odds flag"""
try:
settings = getattr(api_bp, 'settings', None)
if not settings:
return jsonify({"error": "Settings not available"}), 500
return jsonify({
"edit_odds": getattr(settings, 'edit_odds', False)
})
except Exception as e:
logger.error(f"API settings error: {e}")
return jsonify({"error": str(e)}), 500
@api_bp.route('/debug/match-status')
@get_api_auth_decorator(require_admin=True)
def debug_match_status():
......@@ -4600,6 +4618,26 @@ def get_matches_template_details(template_id):
@get_api_auth_decorator()
def update_matches_template_odds(template_id):
"""Update odds for a match template"""
# Check if edit_odds is enabled (disabled by default for security)
# Only allow if explicitly enabled via command line --edit-odds flag
settings = getattr(api_bp, 'settings', None)
edit_odds_enabled = getattr(settings, 'edit_odds', False) if settings else False
# Check if user is admin (required for editing odds)
from flask import request
is_admin = False
if hasattr(request, 'current_user') and request.current_user:
is_admin = request.current_user.get('is_admin', False)
if not edit_odds_enabled:
return jsonify({
"error": "Manual odds editing is disabled. Start with --edit-odds flag to enable admin-only odds editing.",
"edit_odds_enabled": False
}), 403
if not is_admin:
return jsonify({"error": "Admin access required to modify odds"}), 403
try:
from ..database.models import MatchTemplateModel, MatchOutcomeTemplateModel
......@@ -7903,13 +7941,11 @@ def get_match_reports():
match_stats[match_id]['bets_count'] += 1
match_stats[match_id]['payin'] += float(detail.amount)
# Calculate potential payout if bet was won (use same logic as bet list)
match = session.query(MatchModel).filter_by(id=match_id).first()
# Calculate payout using actual win_amount (stored when bet was settled)
# This ensures consistency with bet list and avoids recalculation issues
if is_bet_detail_winning(detail, match, session):
if match:
outcomes_dict = match.get_outcomes_dict()
odds = outcomes_dict.get(detail.outcome, 0.0)
match_stats[match_id]['payout'] += float(detail.amount) * float(odds)
# Use the actual win_amount stored when the bet was settled
match_stats[match_id]['payout'] += float(detail.win_amount or 0)
# Get match information and merge with stats
matches_data = []
......
......@@ -106,7 +106,7 @@
</div>
<!-- Edit Odds Card -->
<div class="row">
<div class="row" id="edit-odds-section">
<div class="col-12">
<div class="card mb-4">
<div class="card-header d-flex justify-content-between align-items-center">
......@@ -162,10 +162,35 @@ const templateId = config.templateId;
let cachedTemplateData = null;
let isInitialLoad = true;
let editOddsEnabled = false;
// Load template details on page load
document.addEventListener('DOMContentLoaded', function() {
loadTemplateDetails();
// First, check if edit_odds is enabled
fetch('/api/settings')
.then(response => response.json())
.then(settings => {
editOddsEnabled = settings.edit_odds || false;
console.log('Edit odds enabled:', editOddsEnabled);
// Hide edit odds form if disabled
const editOddsSection = document.getElementById('edit-odds-section');
if (!editOddsEnabled && editOddsSection) {
editOddsSection.style.display = 'none';
}
})
.catch(err => {
console.error('Error loading settings:', err);
// Hide edit odds form by default if we can't check
const editOddsSection = document.getElementById('edit-odds-section');
if (editOddsSection) {
editOddsSection.style.display = 'none';
}
})
.finally(() => {
// Then load template details
loadTemplateDetails();
});
});
function loadTemplateDetails() {
......@@ -299,6 +324,12 @@ function renderOutcomesTable(outcomes) {
}
function saveOdds() {
// Check if edit is enabled
if (!editOddsEnabled) {
showError('Manual odds editing is disabled. Start the application with --edit-odds flag to enable it.');
return;
}
const saveBtn = document.getElementById('save-odds-btn');
const tbody = document.getElementById('outcomes-tbody');
const rows = tbody.querySelectorAll('tr');
......
# MbetterClient v1.0.16
Cross-platform multimedia client application
## Installation
1. Extract this package to your desired location
2. Run the executable file
3. The application will create necessary configuration files on first run
## System Requirements
- **Operating System**: Linux 6.12.15-amd64
- **Architecture**: x86_64
- **Memory**: 512 MB RAM minimum, 1 GB recommended
- **Disk Space**: 100 MB free space
## Configuration
The application stores its configuration and database in:
- **Windows**: `%APPDATA%\MbetterClient`
- **macOS**: `~/Library/Application Support/MbetterClient`
- **Linux**: `~/.config/MbetterClient`
## Web Interface
By default, the web interface is available at: http://localhost:5001
Default login credentials:
- Username: admin
- Password: admin
**Please change the default password after first login.**
## Support
For support and documentation, please visit: https://git.nexlab.net/mbetter/mbetterc
## Version Information
- Version: 1.0.16
- Build Date: sissy
- Platform: Linux-6.12.15-amd64-x86_64-with-glibc2.42
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment