import os import json import logging from datetime import datetime, timedelta from flask import Flask, request, jsonify from recommender import recommend_products from flask_cors import CORS # --- Configure Logging --- logging.basicConfig( level=logging.INFO, format='%(asctime)s - %(name)s - %(levelname)s - %(message)s', handlers=[ logging.FileHandler('app.log'), logging.StreamHandler() ] ) logger = logging.getLogger(__name__) # --- Initialize Flask App and CORS --- app = Flask(__name__) CORS(app, resources={r"/api/*": {"origins": "*"}}) @app.route('/recommend/', methods=['GET']) def get_recommendations(user_id): logger.info(f"=== RECOMMENDATION REQUEST START ===") logger.info(f"Input - User ID: {user_id}") logger.info(f"Request method: {request.method}") logger.info(f"Request headers: {dict(request.headers)}") logger.info(f"Request args: {dict(request.args)}") try: # Get optional parameters top_n = request.args.get('top_n', default=5, type=int) logger.info(f"Parameters - top_n: {top_n}") logger.info("Calling recommend_products function...") recommendations = recommend_products(user_id, top_n) response_data = { "user_id": user_id, "recommendations": recommendations, "total_recommendations": len(recommendations), "timestamp": datetime.now().isoformat() } logger.info(f"Success - Generated {len(recommendations)} recommendations for user {user_id}") logger.info(f"Output - Response data keys: {list(response_data.keys())}") logger.info(f"Output - Recommendation IDs: {[r.get('id') for r in recommendations if isinstance(r, dict)]}") logger.info(f"=== RECOMMENDATION REQUEST END ===") return jsonify(response_data) except Exception as e: logger.error(f"=== RECOMMENDATION REQUEST FAILED ===") logger.error(f"Error type: {type(e).__name__}") logger.error(f"Error message: {str(e)}") logger.exception("Full traceback:") error_response = { "error": str(e), "user_id": user_id, "timestamp": datetime.now().isoformat() } logger.error(f"Returning error response: {error_response}") return jsonify(error_response), 500 @app.route('/health', methods=['GET']) def health_check(): logger.info("=== HEALTH CHECK REQUEST ===") response = { "status": "healthy", "timestamp": datetime.now().isoformat(), "service": "recommendation-api" } logger.info(f"Health check response: {response}") return jsonify(response) @app.errorhandler(404) def not_found(error): logger.warning(f"404 Error - Path: {request.path}, Method: {request.method}") return jsonify({"error": "Endpoint not found"}), 404 @app.errorhandler(500) def internal_error(error): logger.error(f"500 Error - Path: {request.path}, Method: {request.method}") logger.exception("Internal server error:") return jsonify({"error": "Internal server error"}), 500 # ----------------------------------------------------------------------------- # SERVER EXECUTION # ----------------------------------------------------------------------------- if __name__ == '__main__': port = int(os.environ.get("PORT", 7860)) debug_mode = os.environ.get("FLASK_DEBUG", "False").lower() == "true" logger.info(f"=== STARTING RECOMMENDATION SERVER ===") logger.info(f"Debug mode: {debug_mode}") logger.info(f"Port: {port}") logger.info(f"Environment variables: PORT={os.environ.get('PORT')}, FLASK_DEBUG={os.environ.get('FLASK_DEBUG')}") if not debug_mode: logger.info("Using Waitress server for production") from waitress import serve serve(app, host="0.0.0.0", port=port) else: logger.info("Using Flask development server") app.run(debug=True, host="0.0.0.0", port=port)