App Engine部署的图像预测API无法读取云存储模型求助
问题描述
已成功将应用部署至App Engine,但调用/predict API时无法完成图像预测,Postman测试返回错误。已配置调用存储模型的Cloud Storage Bucket,但问题仍存在。
app.py
import os import numpy as np import tensorflow as tf from flask import Flask, request, jsonify #from tensorflow import keras #from keras.models import load_model from PIL import Image from flask_cors import CORS app = Flask(__name__) CORS(app) # global variable model = None #model #db = None # download model file from cloud storage def download_model_file(): from google.cloud import storage # model bucket details BUCKET_NAME = "spezia-bucket" PROJECT_ID = "capstone-spezia" GCS_MODEL_FILE = "spezia_model.h5" # initialise a client client = storage.Client(PROJECT_ID) # create a bucket object for our bucket bucket = client.bucket(BUCKET_NAME) # create a blob object from the filepath blob = bucket.blob(GCS_MODEL_FILE) #with blob.open("r") as model: # print(model.read()) folder = '/tmp/' if not os.path.exists(folder) : os.makedirs(folder) # download the file to a destination blob.download_to_filename(folder + "model_spezia.h5") #model = load_model('spezia_model.h5') @app.route('/') def main(): return 'Welcome to Spezia ML Team API for predict many spices' @app.route('/predict', methods=['POST']) def recognize_image(): try: # deploy model global model if not model: download_model_file() model = tf.keras.models.load_model('/tmp/model_spezia.h5') # open image from request img_sample = Image.open(request.files['image']) image_path = img_sample image_path = image_path.convert('RGB') image_path.close() # prepare image for prediction img = np.array(img_sample.resize((150,150))) x = np.expand_dims(img, axis=0) images = np.vstack([x]) image_path.close() # predict prediction_array = model.predict(images) class_names = ['asam jawa', 'cengkeh', 'daun jeruk', 'daun salam', 'jahe', 'kayu manis', 'keluak', 'kemiri', 'ketumbar', 'kunyit', 'lada hitam', 'pekak','serai'] result = { 'prediction': class_names[np.argmax(prediction_array)], 'confidence': '{:2.0f}%'.format(100 * np.max(prediction_array)) } return jsonify(isError=False, message='Success', statusCode=200, data=result), 200 except Exception as e: print(str(e)) return jsonify(message='Something went wrong'), 500 if __name__ == '__main__': app.run(debug=True, port=8080)
requirements.txt
Flask==2.2.2 Flask-Cors==3.0.10 tensorflow==2.11.0 keras==2.11.0 numpy==1.23.5 Pillow==9.3.0 google-cloud-storage==2.7.0
排查与修复方案
1. 图像处理逻辑错误
代码中存在提前关闭图像文件的问题:打开图像后将img_sample赋值给image_path,转换为RGB后直接关闭了文件对象,后续尝试使用已关闭的img_sample进行resize操作会触发错误。
修正代码:
# 修正后的图像处理逻辑 img_sample = Image.open(request.files['image']) img_sample = img_sample.convert('RGB') # 直接操作原对象 img = np.array(img_sample.resize((150,150))) img_sample.close() # 所有处理完成后再关闭文件
同时删除重复的image_path.close()语句。
2. 模型加载验证与权限检查
- 为App Engine默认服务账号(格式:
PROJECT_ID@appspot.gserviceaccount.com)添加roles/storage.objectViewer角色,确保有权限从Cloud Storage下载模型文件。 - 在模型加载后添加验证代码,确认模型是否正确加载:
if not model: download_model_file() model = tf.keras.models.load_model('/tmp/model_spezia.h5') print("模型输入形状:", model.input_shape) # 打印模型信息验证加载状态
3. 路径拼接优化
使用os.path.join拼接文件路径,避免因分隔符问题导致的文件找不到错误:
blob.download_to_filename(os.path.join(folder, "model_spezia.h5"))
4. 日志增强排查
替换简单的print为日志模块输出,方便在App Engine控制台查看详细错误:
import logging # 异常处理块修改为 except Exception as e: logging.error(f"预测错误详情: {str(e)}") return jsonify(message='Something went wrong'), 500
5. 运行环境指定
在app.yaml中添加Python版本声明,确保环境兼容依赖版本:
runtime: python39
内容的提问来源于stack exchange,提问作者masyara
相关产品推荐
相关产品推荐

