This page walks through the full directory layout of AVL Tree Car Backend, explains what each module is responsible for, and traces the two key lifecycles — an HTTP request and a Socket.IO event — from the moment they arrive at the server to the moment a response leaves it. Understanding this structure makes it straightforward to extend the AVL logic, add new routes, or wire up additional socket events.Documentation Index
Fetch the complete documentation index at: https://mintlify.com/tutosrive/avl_tree_car/llms.txt
Use this file to discover all available pages before exploring further.
Directory layout
Module breakdown
run.py — entry point
run.py instantiates the Main class with "*" as the allowed CORS origin, then calls main.socketio.run(main.app, host='localhost', port=4500, debug=True). It is the only file you need to execute directly; all other wiring happens inside Main.__configs().
src/main.py — the Main class
Main is the composition root of the application. Its __init__ creates the Flask app, instantiates a shared AVLTree and Car model, and immediately calls __configs(). Inside __configs() it applies CORS for all origins, constructs a SocketManager, registers socket handlers via SocketAVLTree, and mounts the three router classes (MainRoute, AVLRouter, DataRouter). Nothing else in the codebase reaches Flask directly — every registration flows through Main.
src/models/ — domain models
All models expose a
to_dict() method so they can be serialised cleanly inside jsonify() or Socket.IO emit() calls without any extra transformation step in controllers.| File | Responsibility |
|---|---|
obstacle.py | Value object for a single road obstacle. Holds x, y, type_id, and a randomly generated 8-character id created by RandomsUtils. |
node.py | A single AVL tree node wrapping an Obstacle. Tracks left, right, parent, and height pointers. |
tree.py | Full AVL tree implementation: insert, delete, search, _rebalance, update_height, _rotate_left, _rotate_right, and the three traversal generators. The tree is keyed on obstacle.x. |
responses.py | Three response shapes: BaseFlaskResponse for HTTP (status, ok, message, data, error), ReturnModels for internal controller returns, and ResponseSocket for Socket.IO emits. |
car.py | The car entity used by the simulation. |
src/routers/ — HTTP routing layer
Router (base class) wraps app.add_url_rule and registers each URL twice — once without a trailing slash and once with — so both forms are accepted by Flask. Subclasses call self.register_routes(url, handler, *methods) and keep all route logic private to the class.
AVL_router.pymountsGET /avl,POST /avl/node/add,POST /avl/node/remove, andPOST /avl/add/configs, forwarding each request body toAVLController.Data_router.pymountsGET /dataandGET|POST /data/json/<filename>for serving JSON assets fromsrc/data/.main_route.pymountsGET /and returns the health-check response{"status": 200, "ok": true, "message": "Hello From Flask!"}.
src/controllers/ — business logic layer
Controllers receive validated request data from routers (or socket events), drive the appropriate model methods, and build the response object that gets serialised back to the caller.
avl_controller.pyconstructs anObstaclefrom the request body, callsAVLTree.insert()orAVLTree.delete(), and maps the returnedReturnModelsinto aBaseFlaskResponse.data_controller.pyreads files from thesrc/data/folder and returns their JSON content directly.socket_avl_controller.pyhandles socket-specific operations: it emits the current balanced tree after mutations (get_tree_avl), streams traversal results (emit_road), and resets the tree onavl_reseted.
src/sockets/ — Socket.IO layer
SocketManager extends Flask-SocketIO’s SocketIO class and adds a register_handler convenience method. Every event is routed through handle_event, which constructs a ResponseSocket, calls the provided callback (optionally passing the emit reference or extra arguments), and then emits the result back to the client — unless the callback takes control of emit itself (need_control_emit=True).
SocketAVLTree sets the active namespace to /AVLTree and registers the following events on it:
| Client emits | Server emits back | Handler |
|---|---|---|
connect | connected | default connect handler |
disconnect | disconnected | default disconnect handler |
reset_avl | avl_reseted | SocketAVLController.emit_avl_reseted |
remove_obstacle | avl_tree_balanced | SocketAVLController.emit_obstacle_removed |
get_tree_avl | avl_tree_balanced | SocketAVLController.get_tree_avl |
road_preorder | preorder | SocketAVLController.emit_road |
road_inorder | inorder | SocketAVLController.emit_road |
road_posorder | posorder | SocketAVLController.emit_road |
src/utils/ — utility helpers
randoms_utils.pygenerates the random alphanumeric IDs assigned to each newObstacle.others_utils.pycontainsUtils.validate_json_configs()for validating bulk config payloads, and tree-to-dict serialisation helpers used before emitting tree state over sockets.files_utils.pywraps file-system reads so controllers never touchopen()directly.
src/data/obstacles_types.json — obstacle catalogue
Defines the ten obstacle types the simulation supports. The type_id field in an obstacle payload maps to one of these entries:
Request lifecycle
An inbound HTTP request travels through four discrete layers before a response is returned:- Flask router —
AVLRouter,DataRouter, orMainRoutematches the URL and HTTP method, then extracts the JSON body fromrequest.jsonand passes it to the appropriate controller method. - Controller —
AVLController(orDataController) validates the incoming data, constructs the domain model objects (Obstacle, etc.), and calls the relevantAVLTreemethod. - AVLTree model — performs the structural operation (insert, delete, search), runs height updates and rotations to restore the AVL invariant, and returns a
ReturnModelsresult. - Response — the controller maps
ReturnModelsinto aBaseFlaskResponse, which is serialised to JSON by Flask’sjsonify()and returned to the HTTP client.
Socket.IO event lifecycle
Real-time events follow a similar path through the socket layer:- Client emits — the browser frontend emits a named event (e.g.,
get_tree_avl) on the/AVLTreenamespace with an optional message payload. SocketManager.handle_event— receives the raw message, constructs aResponseSocket, and dispatches to the registered callback with the appropriate argument signature (with or withoutemitcontrol).SocketAVLControllermethod — drives theAVLTreemodel (e.g., serialises the current tree into a dict), writes the result into theResponseSocket, and either callsemitdirectly (whenneed_control_emit=True) or returns sohandle_eventcan emit automatically.emitback — the response dict is pushed to the client under the configured emit-event name (e.g.,avl_tree_balanced), still scoped to the/AVLTreenamespace.
The
SocketManager.namespace property is mutated to /AVLTree by SocketAVLTree at startup. Basic connection events (connect, disconnect) remain on the default / namespace, while all AVL tree events operate on /AVLTree.