main.py 3.2 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990
  1. # app.py
  2. from flask import Flask, render_template, request
  3. from flask_socketio import SocketIO, join_room, leave_room
  4. from flask_cors import CORS
  5. import logging
  6. import os
  7. app = Flask(__name__)
  8. CORS(app, resources={r"/*": {"origins": "*"}})
  9. app.config['SECRET_KEY'] = os.environ.get('SECRET_KEY', 'secret!')
  10. socketio = SocketIO(app, cors_allowed_origins="*", logger=True, engineio_logger=True, ping_timeout=60)
  11. # 配置日志
  12. logging.basicConfig(level=logging.DEBUG, format='%(asctime)s - %(levelname)s - %(message)s')
  13. rooms = {}
  14. user_rooms = {}
  15. @socketio.on('connect')
  16. def on_connect():
  17. logging.info(f"Client connected: {request.sid}")
  18. @socketio.on('disconnect')
  19. def on_disconnect():
  20. logging.info(f"Client disconnected: {request.sid}")
  21. room = user_rooms.get(request.sid)
  22. if room:
  23. leave_room(room)
  24. username = rooms[room].pop(request.sid, None)
  25. del user_rooms[request.sid]
  26. if username:
  27. socketio.emit('update_user_list', list(rooms[room].values()), room=room)
  28. if not rooms[room]:
  29. del rooms[room]
  30. socketio.emit('user_left', username, room=room)
  31. @socketio.on('join')
  32. def on_join(data):
  33. room = data['room']
  34. username = data['username']
  35. join_room(room)
  36. if room not in rooms:
  37. rooms[room] = {}
  38. rooms[room][request.sid] = username
  39. user_rooms[request.sid] = room
  40. logging.info(f"User {username} ({request.sid}) joined room {room}")
  41. socketio.emit('user_joined', username, room=room, skip_sid=request.sid)
  42. socketio.emit('update_user_list', list(rooms[room].values()), room=room)
  43. socketio.emit('message', {'type': 'system', 'msg': f'{username} 加入了房间'}, room=room)
  44. @socketio.on('leave')
  45. def on_leave():
  46. room = user_rooms.get(request.sid)
  47. if room:
  48. username = rooms[room].pop(request.sid, None)
  49. leave_room(room)
  50. del user_rooms[request.sid]
  51. logging.info(f"User {username} ({request.sid}) left room {room}")
  52. socketio.emit('user_left', username, room=room)
  53. socketio.emit('update_user_list', list(rooms[room].values()), room=room)
  54. socketio.emit('message', {'type': 'system', 'msg': f'{username} 离开了房间'}, room=room)
  55. @socketio.on('offer')
  56. def handle_offer(data):
  57. data['sender'] = rooms[user_rooms[request.sid]][request.sid]
  58. logging.info(f"Offer from {data['sender']} to {data.get('target')}")
  59. socketio.emit('offer', data, room=data.get('target'))
  60. @socketio.on('answer')
  61. def handle_answer(data):
  62. data['sender'] = rooms[user_rooms[request.sid]][request.sid]
  63. logging.info(f"Answer from {data['sender']} to {data.get('target')}")
  64. socketio.emit('answer', data, room=data.get('target'))
  65. @socketio.on('candidate')
  66. def handle_candidate(data):
  67. data['sender'] = rooms[user_rooms[request.sid]][request.sid]
  68. logging.info(f"ICE candidate from {data['sender']} to {data.get('target')}")
  69. socketio.emit('candidate', data, room=data.get('target'))
  70. @app.route('/room/<room_id>')
  71. def room(room_id):
  72. return render_template('room.html', room_id=room_id)
  73. @socketio.on_error()
  74. def error_handler(e):
  75. logging.error(f"SocketIO error: {str(e)}")
  76. if __name__ == '__main__':
  77. socketio.run(app, host='0.0.0.0', port=int(os.environ.get('PORT', 15000)), debug=False)