from flask import Flask, request, jsonify from flask_sqlalchemy import SQLAlchemy from flask_cors import CORS import requests from datetime import datetime import base64 app = Flask(__name__) CORS(app) app.config['SQLALCHEMY_DATABASE_URI'] = 'mysql+pymysql://root@localhost/flower' app.config['SQLALCHEMY_TRACK_MODIFICATIONS'] = False UPLOAD_SERVICE_URL = 'https://c.2nicep.com:3000/uploads' db = SQLAlchemy(app) class FlowerShop(db.Model): __tablename__ = 'flower_shop' id = db.Column(db.Integer, primary_key=True, autoincrement=True) name = db.Column(db.String(100), nullable=False) description = db.Column(db.Text, nullable=True) price = db.Column(db.DECIMAL(10, 2), nullable=False) quantity = db.Column(db.Integer, nullable=False, default=0) image_url = db.Column(db.String(255), nullable=True) is_active = db.Column(db.Boolean, default=True) class Order(db.Model): __tablename__ = 'orders' id = db.Column(db.Integer, primary_key=True, autoincrement=True) flower_id = db.Column(db.Integer, db.ForeignKey('flower_shop.id'), nullable=False) quantity = db.Column(db.Integer, nullable=False) total_price = db.Column(db.DECIMAL(10, 2), nullable=False) status = db.Column(db.String(20), nullable=False, default='pending') created_at = db.Column(db.DateTime, nullable=False, default=datetime.utcnow) flower = db.relationship('FlowerShop', backref=db.backref('orders', lazy=True)) API_KEY = "kbt40nMOF8tLGg5IdZStJc4G" SECRET_KEY = "jUoj82HAALIzDWRlrTauoHwLcnB3eAn7" def get_access_token(): url = "https://aip.baidubce.com/oauth/2.0/token" params = {"grant_type": "client_credentials", "client_id": API_KEY, "client_secret": SECRET_KEY} return str(requests.post(url, params=params).json().get("access_token")) @app.route('/api/identify', methods=['POST']) def identify_flower(): if 'image' not in request.files: return jsonify({"error": "没有提供图片文件"}), 400 image_file = request.files['image'] image = base64.b64encode(image_file.read()).decode('utf-8') url = "https://aip.baidubce.com/rest/2.0/image-classify/v1/plant?access_token=" + get_access_token() payload = { "image": image, "baike_num": 0 } headers = { 'Content-Type': 'application/x-www-form-urlencoded', 'Accept': 'application/json' } response = requests.post(url, headers=headers, data=payload) result = response.json() if 'result' in result and len(result['result']) > 0: top_result = result['result'][0] # 检查数据库中是否存在这种花 flower = FlowerShop.query.filter(FlowerShop.name.ilike(f"%{top_result['name']}%")).first() if flower: return jsonify({ "id": flower.id, "name": flower.name, "description": flower.description, "price": float(flower.price), "quantity": flower.quantity, "image_url": flower.image_url }), 200 else: # 如果数据库中没有这种花,返回识别的名称和概率 return jsonify({ "name": top_result['name'], "probability": top_result['score'] }), 200 else: return jsonify({"error": "未能识别花卉"}), 404 def upload_file_to_service(file): if not file: return None files = {'images': (file.filename, file.read(), file.content_type)} try: response = requests.post(UPLOAD_SERVICE_URL, files=files) if response.status_code == 200: return response.json()['files'][0] else: print(f"Upload failed: {response.text}") return None except Exception as e: print(f"Error during upload: {str(e)}") return None @app.route('/api/flowers', methods=['GET']) def get_flowers(): query = request.args.get('query', '') flowers = FlowerShop.query.filter(FlowerShop.name.ilike(f'%{query}%'), FlowerShop.is_active == True).all() return jsonify([{ "id": flower.id, "name": flower.name, "description": flower.description, "price": float(flower.price), "quantity": flower.quantity, "image_url": flower.image_url } for flower in flowers]) @app.route('/api/flowers', methods=['POST']) def add_flower(): name = request.form.get('name') description = request.form.get('description') price = request.form.get('price') quantity = request.form.get('quantity') image = request.files.get('image') if not name or not price or not quantity: return jsonify({"error": "Name, price, and quantity are required"}), 400 try: price = float(price) quantity = int(quantity) except ValueError: return jsonify({"error": "Invalid price or quantity format"}), 400 if quantity < 0: return jsonify({"error": "Quantity must be non-negative"}), 400 image_url = upload_file_to_service(image) try: new_flower = FlowerShop(name=name, description=description, price=price, quantity=quantity, image_url=image_url) db.session.add(new_flower) db.session.commit() except Exception as e: db.session.rollback() print(f"Database error: {str(e)}") return jsonify({"error": "Failed to add flower to database"}), 500 return jsonify({ "message": "Flower added successfully", "id": new_flower.id, "name": new_flower.name, "description": new_flower.description, "price": float(new_flower.price), "quantity": new_flower.quantity, "image_url": new_flower.image_url }), 201 @app.route('/api/my-products', methods=['GET']) def get_my_products(): products = FlowerShop.query.all() return jsonify([{ "id": product.id, "name": product.name, "description": product.description, "price": float(product.price), "quantity": product.quantity, "image_url": product.image_url, "is_active": product.is_active } for product in products]) @app.route('/api/products/', methods=['PUT']) def update_product(product_id): product = FlowerShop.query.get_or_404(product_id) data = request.json product.name = data.get('name', product.name) product.description = data.get('description', product.description) product.price = data.get('price', product.price) product.quantity = data.get('quantity', product.quantity) product.is_active = data.get('is_active', product.is_active) try: db.session.commit() except Exception as e: db.session.rollback() return jsonify({"error": f"Failed to update product: {str(e)}"}), 500 return jsonify({"message": "Product updated successfully"}) @app.route('/api/products//toggle-status', methods=['POST']) def toggle_product_status(product_id): product = FlowerShop.query.get_or_404(product_id) product.is_active = not product.is_active try: db.session.commit() except Exception as e: db.session.rollback() return jsonify({"error": f"Failed to toggle product status: {str(e)}"}), 500 return jsonify({"message": f"Product {'activated' if product.is_active else 'deactivated'} successfully"}) @app.route('/api/orders', methods=['GET']) def get_orders(): try: orders = Order.query.all() return jsonify([{ "id": order.id, "flowerName": order.flower.name if order.flower else "Unknown", "quantity": order.quantity, "totalPrice": float(order.total_price), "status": order.status, "createdAt": order.created_at.isoformat() } for order in orders]) except Exception as e: print(f"Error fetching orders: {str(e)}") return jsonify({"error": "Failed to fetch orders"}), 500 @app.route('/api/orders', methods=['POST']) def create_order(): data = request.json flower_id = data.get('flowerId') quantity = data.get('quantity', 1) if not flower_id or not quantity: return jsonify({"error": "Flower ID and quantity are required"}), 400 flower = FlowerShop.query.get(flower_id) if not flower: return jsonify({"error": "Flower not found"}), 404 if flower.quantity < quantity: return jsonify({"error": "Not enough stock"}), 400 total_price = flower.price * quantity try: new_order = Order(flower_id=flower_id, quantity=quantity, total_price=total_price) flower.quantity -= quantity # 减少库存 db.session.add(new_order) db.session.commit() except Exception as e: db.session.rollback() print(f"Database error: {str(e)}") return jsonify({"error": "Failed to create order"}), 500 return jsonify({ "message": "Order created successfully", "orderId": new_order.id, "totalPrice": float(new_order.total_price) }), 201 @app.route('/api/orders//cancel', methods=['POST']) def cancel_order(order_id): order = Order.query.get_or_404(order_id) if order.status != 'pending': return jsonify({"error": "Only pending orders can be cancelled"}), 400 try: order.status = 'cancelled' order.flower.quantity += order.quantity # 恢复库存 db.session.commit() except Exception as e: db.session.rollback() return jsonify({"error": f"Failed to cancel order: {str(e)}"}), 500 return jsonify({"message": "Order cancelled successfully"}) if __name__ == '__main__': with app.app_context(): db.create_all() app.run(debug=True)