Spaces:
Sleeping
Sleeping
| from flask import Flask, request, jsonify | |
| from flask_cors import CORS | |
| from flask_socketio import SocketIO, emit | |
| import pymongo | |
| from bson.objectid import ObjectId | |
| import redis | |
| import json | |
| from redis.exceptions import RedisError | |
| # Khởi tạo Flask app và SocketIO | |
| app = Flask(__name__) | |
| CORS(app) | |
| socketio = SocketIO(app, cors_allowed_origins="*") | |
| # Khởi tạo Redis client | |
| redis_client = redis.Redis(host='localhost', port=6379, db=0) | |
| CACHE_EXPIRE_TIME = 300 # 5 phút | |
| # MongoDB connection | |
| mongo_url = "mongodb+srv://ip6ofme:JL1S4hjMWRoko8AJ@cluster0.x0vo0.mongodb.net/" | |
| client = pymongo.MongoClient(mongo_url) | |
| db = client["test"] | |
| pdf_collection = db["PdfDetails"] | |
| voter_collection = db["Voters"] | |
| # API để upload file và lưu thông tin vào MongoDB | |
| def upload_file(): | |
| # Chỉ lưu thông tin vào MongoDB | |
| title = request.form.get('title') | |
| group = request.form.get('group') | |
| firebase_url = request.form.get('url') | |
| new_pdf = { | |
| 'title': title, | |
| 'group': group, | |
| 'url': firebase_url, | |
| 'votes': 0 | |
| } | |
| result = pdf_collection.insert_one(new_pdf) | |
| return jsonify({'status': 'ok', 'id': str(result.inserted_id)}) | |
| # API để lấy số lượng votes của file theo ID | |
| def get_votes(): | |
| file_id = request.args.get('id') | |
| try: | |
| file = pdf_collection.find_one({'_id': ObjectId(file_id)}) | |
| if not file: | |
| return jsonify({'status': 'error', 'message': 'File not found'}), 404 | |
| return jsonify({'status': 'ok', 'votes': file.get('votes', 0)}) | |
| except Exception as e: | |
| return jsonify({'status': 'error', 'message': str(e)}), 500 | |
| # API để lấy danh sách tất cả các file | |
| def get_files(): | |
| try: | |
| files = pdf_collection.find({}) | |
| file_list = [] | |
| for file in files: | |
| file_list.append({ | |
| 'id': str(file['_id']), | |
| 'title': file['title'], | |
| 'group': file['group'], | |
| 'url': file['url'], | |
| 'votes': file.get('votes', 0) | |
| }) | |
| return jsonify({'status': 'ok', 'data': file_list}) | |
| except Exception as e: | |
| print(f"Error: {str(e)}") | |
| return jsonify({'status': 'error', 'message': str(e)}), 500 | |
| # API để đăng ký người bình chọn | |
| def register_voter(): | |
| data = request.json | |
| name = data.get('name') | |
| group = data.get('group') | |
| role = data.get('role') # Thêm trường role | |
| new_voter = { | |
| 'name': name, | |
| 'group': group, | |
| 'role': role, # Lưu role vào MongoDB | |
| 'number_of_votes': 0 | |
| } | |
| result = voter_collection.insert_one(new_voter) | |
| return jsonify({'status': 'ok', 'id': str(result.inserted_id)}) | |
| # API để bình chọn | |
| def vote_by_voter(): | |
| data = request.json | |
| voter_id = data.get('voter_id') | |
| file_id = data.get('file_id') | |
| vote_count = data.get('vote_count', 1) | |
| if vote_count <= 0: | |
| return jsonify({'status': 'error', 'message': 'Vote count must be greater than 0'}), 400 | |
| voter = voter_collection.find_one({'_id': ObjectId(voter_id)}) | |
| if not voter: | |
| return jsonify({'status': 'error', 'message': 'Voter not found'}), 404 | |
| max_votes = 10 if voter['role'] == 'judge' else 2 | |
| if voter['number_of_votes'] + vote_count > max_votes: | |
| return jsonify({'status': 'error', 'message': 'Maximum votes exceeded'}), 400 | |
| try: | |
| # Cập nhật MongoDB | |
| voter_collection.update_one({'_id': ObjectId(voter_id)}, {'$inc': {'number_of_votes': vote_count}}) | |
| pdf_collection.update_one({'_id': ObjectId(file_id)}, {'$inc': {'votes': vote_count}}) | |
| # Xóa cache | |
| redis_client.delete('all_files') | |
| redis_client.delete(f'voter:{voter_id}') | |
| # Emit socket event | |
| updated_file = pdf_collection.find_one({'_id': ObjectId(file_id)}) | |
| socketio.emit('vote_update', { | |
| 'file_id': file_id, | |
| 'votes': updated_file.get('votes', 0) | |
| }) | |
| return jsonify({'status': 'ok', 'message': f'Vote recorded successfully with {vote_count} votes'}) | |
| except Exception as e: | |
| return jsonify({'status': 'error', 'message': str(e)}), 500 | |
| # API để lấy thông tin người bình chọn | |
| def get_voter(): | |
| voter_id = request.args.get('id') | |
| # Kiểm tra cache | |
| cached_voter = redis_client.get(f'voter:{voter_id}') | |
| if cached_voter: | |
| return jsonify(json.loads(cached_voter)) | |
| voter = voter_collection.find_one({'_id': ObjectId(voter_id)}) | |
| if not voter: | |
| return jsonify({'status': 'error', 'message': 'Voter not found'}), 404 | |
| voter_data = { | |
| 'status': 'ok', | |
| 'name': voter['name'], | |
| 'group': voter['group'], | |
| 'role': voter['role'], | |
| 'number_of_votes': voter['number_of_votes'] | |
| } | |
| # Lưu vào cache | |
| redis_client.setex(f'voter:{voter_id}', CACHE_EXPIRE_TIME, json.dumps(voter_data)) | |
| return jsonify(voter_data) | |
| # Socket events | |
| def handle_connect(): | |
| print('Client connected') | |
| def handle_disconnect(): | |
| print('Client disconnected') | |
| # Khởi chạy server | |
| if __name__ == "__main__": | |
| socketio.run(app, port=5000, debug=True) | |