أهلا
لدي مشروع TensorFlow 2.0 به واجهة برمجة تطبيقات Flask صغيرة أمامه حتى أتمكن من تقديم طلبات إلى النموذج من خلال مكالمات HTTP مع المعالجة المسبقة للبيانات التي تم إجراؤها بالفعل في واجهة برمجة التطبيقات. اخترت Gunicorn لتشغيل تطبيق Flask / TensorFlow الخاص بي في حاوية عامل إرساء. للأسف ، العملية العمالية التي أنشأها Gunicorn معلقة في الحاوية حتى قتلها Gunicorn. الخادم لا يأتي أبدًا ولا يمكنني تقديم طلبات إليه. علاوة على ذلك ، فإن إعداد Gunicorn نفسه يعمل بشكل لا تشوبه شائبة خارج عامل الإرساء ، في الجهاز المضيف.
سجلات Docker (يتم تعليقها هناك وتطبع خطأ انتهاء المهلة بعد وقت طويل)
[2019-10-03 18:03:05 +0000] [1] [INFO] Starting gunicorn 19.9.0
[2019-10-03 18:03:05 +0000] [1] [INFO] Listening at: http://127.0.0.1:8000 (1)
[2019-10-03 18:03:05 +0000] [1] [INFO] Using worker: sync
[2019-10-03 18:03:05 +0000] [8] [INFO] Booting worker with pid: 8
2019-10-03 18:03:08.126584: I tensorflow/core/platform/cpu_feature_guard.cc:142] Your CPU supports instructions that this TensorFlow binary was not compiled to use: AVX2 FMA
2019-10-03 18:03:08.130017: I tensorflow/core/platform/profile_utils/cpu_utils.cc:94] CPU Frequency: 3392000000 Hz
2019-10-03 18:03:08.130306: I tensorflow/compiler/xla/service/service.cc:168] XLA service 0x55fbb23fb2d0 executing computations on platform Host. Devices:
2019-10-03 18:03:08.130365: I tensorflow/compiler/xla/service/service.cc:175] StreamExecutor device (0): Host, Default Version
ملف عامل ميناء:
FROM python
RUN pip install gunicorn
WORKDIR /usr/src/app
COPY requirements.txt ./
RUN pip install --no-cache-dir -r requirements.txt
COPY . .
EXPOSE 8000
CMD [ "gunicorn", "--chdir", "src", "api:app" ]
api.py:
from flask import Flask, request
import inference
app = Flask(__name__)
@app.route('/', methods=['GET', 'POST'])
def predict():
if request.method == 'GET':
return 'POST a json payload of {"imageBase64": "base64base64base64"} to this address to predict.'
try:
result = inference.run(request.json['imageBase64'])
return result
except Exception as e:
return {'error': str(e)}, 500
if __name__ == "__main__":
app.run()
else:
print('\n * Server ready!')
الاستدلال
# Import packages
from __future__ import absolute_import, division, print_function, unicode_literals
import os
import tensorflow as tf
from tensorflow import keras
import PIL
import numpy as np
from io import BytesIO
import base64
import json
print("TensorFlow version is ", tf.__version__)
# Set variables
##########################################################################################
##########################################################################################
model_name = 'catsdogs'
base_dir = os.path.join(os.path.dirname(__file__), '..')
model_dir = os.path.join(base_dir, 'models')
##########################################################################################
##########################################################################################
# Load model
model = keras.models.load_model(os.path.join(model_dir, model_name + '.h5'))
# Load metadata
with open(os.path.join(model_dir, model_name + '_metadata.json')) as metadataFile:
metadata = json.load(metadataFile)
# Split metadata
labels = metadata['training_labels']
image_size = metadata['image_size']
# Exported function for inference
def run(imgBase64):
# Decode the base64 string
image = PIL.Image.open(BytesIO(base64.b64decode(imgBase64)))
# Pepare image
image = image.resize((image_size, image_size), resample=PIL.Image.BILINEAR)
image = image.convert("RGB")
# Run prediction
tensor = tf.cast(np.array(image), tf.float32) / 255.
tensor = tf.expand_dims(tensor, 0, name=None)
result = model.predict(tensor, steps=1)
# Combine result with labels
labeledResult = {}
for i, label in enumerate(labels):
labeledResult[label] = float(result[0][labels[label]])
return labeledResult
لقد بحثت عن حل لهذا للأعمار ولم أتمكن من التوصل إلى أي شيء ، أي مساعدة ستكون موضع تقدير كبير.
شكرا!
هل يحد إعداد Docker الخاص بك من الحد الأقصى للذاكرة المتاحة للحاوية؟
تعاني من نفس الشيء. لا أعتقد أن جونيكورن هو المسؤول. أحصل على نفس الخطأ عند تشغيل python3 api.py
من bash shell في الحاوية.
tlaanemaa هل يمكنك تأكيد ما يقول mackdelany ؟
مهلا. آسف لتختفي من هذا القبيل.
يحد الإعداد الخاص بي من ذاكرة الوصول العشوائي لـ Docker قليلاً ولكن حدث نفس الشيء حتى عندما أزلت القيد.
سأحاول تشغيل ملف api بدون gunicorn و r eport.
شكرا!
tlaanemaa أي أخبار عنها؟
تضمين التغريدة
عذرًا ، لقد انجرفت بعيدًا مع أشياء أخرى ولم يكن لدي الوقت الكافي للمضي قدمًا في هذا الأمر.
سأحاول أن أزعج هذا اليوم وأعود إليك
لذلك حاولت تشغيل التطبيق بدون gunicorn في الحاوية ونجح ذلك.
يوجد أدناه جزء CMD من ملف Dockerfile الخاص بي
يعمل:
CMD [ "python", "src/api.py" ]
السجلات:
2019-12-02 11:40:45.649503: I tensorflow/core/platform/cpu_feature_guard.cc:142] Your CPU supports instructions that this TensorFlow binary was not compiled to use: AVX2 FMA
2019-12-02 11:40:45.653496: I tensorflow/core/platform/profile_utils/cpu_utils.cc:94] CPU Frequency: 2208000000 Hz
2019-12-02 11:40:45.653999: I tensorflow/compiler/xla/service/service.cc:168] XLA service 0x55f969cf6a40 executing computations on platform Host. Devices:
2019-12-02 11:40:45.654045: I tensorflow/compiler/xla/service/service.cc:175] StreamExecutor device (0): Host, Default Version
TensorFlow version is 2.0.0
* Serving Flask app "api" (lazy loading)
* Environment: production
WARNING: This is a development server. Do not use it in a production deployment.
Use a production WSGI server instead.
* Debug mode: off
* Running on http://127.0.0.1:5000/ (Press CTRL+C to quit)
لا يعمل:
CMD [ "gunicorn", "--chdir", "src", "api:app" ]
السجلات:
[2019-12-02 11:39:22 +0000] [1] [INFO] Starting gunicorn 20.0.4
[2019-12-02 11:39:22 +0000] [1] [INFO] Listening at: http://127.0.0.1:8000 (1)
[2019-12-02 11:39:22 +0000] [1] [INFO] Using worker: sync
[2019-12-02 11:39:22 +0000] [9] [INFO] Booting worker with pid: 9
2019-12-02 11:39:24.041188: I tensorflow/core/platform/cpu_feature_guard.cc:142] Your CPU supports instructions that this TensorFlow binary was not compiled to use: AVX2 FMA
2019-12-02 11:39:24.046495: I tensorflow/core/platform/profile_utils/cpu_utils.cc:94] CPU Frequency: 2208000000 Hz
2019-12-02 11:39:24.047129: I tensorflow/compiler/xla/service/service.cc:168] XLA service 0x5623e18b5200 executing computations on platform Host. Devices:
2019-12-02 11:39:24.047183: I tensorflow/compiler/xla/service/service.cc:175] StreamExecutor device (0): Host, Default Version
أيضًا ، لقد فتحت المستودع حتى تتمكن من التجول إذا كنت تريد ذلك.
يمكن أن تكون مفيدة
Listening at: http://127.0.0.1:8000 (1)
هل يمكن أن تكون المشكلة أن البونكورن يستمع إلى مضيف محلي داخل حاوية بحيث لا يمكن الوصول إليه من الخارج؟
لا أعتقد ذلك لأن تطبيق flask كان يفعل الشيء نفسه وكان ذلك يعمل.
أيضًا ، لا يسجل إصدار gunicorn إصدار tensorflow الذي يشير إلى حدوث المشكلة قبل سطر السجل هذا في الكود. عند الجري بدون gunicorn ، فقط قارورة ، ثم يسجل ذلك.
TensorFlow version is 2.0.0
ماذا تقول على مستوى التصحيح؟
tlaanemaa كيف يتم تكوين شبكة Docker daemon الخاصة بك؟ وفقًا لتعليق من CaselIT ، يبدو من المحتمل أن عميلك غير قادر على الوصول إلى منفذ Gunicorn عبر شبكة Docker.
هل يمكنك محاولة بدء Gunicorn بـ arg -b 0.0.0.0:8000
؟
لا أعتقد أن المشكلة تكمن في الشبكة لأنه يبدو ، من السجلات على الأقل ، أن الخادم لا يبدأ على الإطلاق لأنه لا يصل أبدًا إلى خطوط السجل التي تأتي بعد استيراد tensorflow
ومع ذلك فقد جربت اقتراحك ولكنه يعطيني خطأ
CMD [ "gunicorn", "-b", "0.0.0.0:8000", "--chdir", "src", "api:app" ]
_سجل_
usage: gunicorn [OPTIONS] [APP_MODULE]
gunicorn: error: unrecognized arguments: -d
إذا كنت تريد أن تجرب نفسك ثم هي صورة comtainer المتاحة في registry.gitlab.com/tlaanemaa/image-classifier
tlaanemaa هل يمكنك إعادة نشر أمر إنشاء الصورة وأمر تشغيل الحاوية Dockerfile
المحدّث؟
تضمين التغريدة
docker build -t tlaanemaa/image-classifier .
_Dockerfile وقت الإرسال: _
FROM python:3.7
RUN pip install gunicorn
WORKDIR /usr/src/app
COPY requirements.txt ./
RUN pip install --no-cache-dir -r requirements.txt
COPY . .
EXPOSE 8000
CMD [ "gunicorn", "-b", "0.0.0.0:8000", "--chdir", "src", "api:app" ]
ما هو سجل عامل الإرساء الكامل ، هل يمكنك لصق سطر الأوامر الذي يستخدمه أخيرًا؟
ما لم يكن يفعل شيئًا لا يمكن التخلي عنه أثناء تصحيح هذه المشكلة ، فهل يمكنك تشغيله بدون Portainer في الوقت الحالي؟
هذا يعمل بالنسبة لي ، Docker Desktop for Mac 2.1.0.5:
docker build -t tlaanemaa/image-classifier .
docker run -it --rm -p 8000:8000 tlaanemaa/image-classifier
يقبل طلبات POST
.
الرجاء تشغيل ونشر الإخراج والنتيجة كاملة.
لقد جربته وهو يعمل الآن.
هل يمكن أن يكون العلم -b
الذي أصلحه؟
شكرا جزيلا!
ما هو مثير للاهتمام الآن هو أنه عندما أقوم بطلبات POST ، فإن الهدف يكون سريعًا ولكن طلبات GET تكون بطيئة للغاية. بعد فترة من القيام بطلبات GET ، تصبح هذه الطلبات سريعة ولكن بعد ذلك يصبح POST بطيئًا للغاية وينتهي العامل. بمجرد استجابتها لهذا POST ، تكون POSTs سريعة مرة أخرى و GETs بطيئة. يبدو كما لو كان بإمكانه القيام بسرعة واحدة ويستغرق الأمر وقتًا للتبديل: D
هذه هي السجلات عندما يكون GET سريعًا ويكون POST بطيئًا بسبب انتهاء مهلة العامل:
[2020-01-10 09:34:46 +0000] [1] [CRITICAL] WORKER TIMEOUT (pid:72)
[2020-01-10 09:34:46 +0000] [72] [INFO] Worker exiting (pid: 72)
[2020-01-10 09:34:47 +0000] [131] [INFO] Booting worker with pid: 131
TensorFlow version is 2.0.0
2020-01-10 09:34:48.946351: I tensorflow/core/platform/cpu_feature_guard.cc:142] Your CPU supports instructions that this TensorFlow binary was not compiled to use: AVX2 FMA
2020-01-10 09:34:48.951124: I tensorflow/core/platform/profile_utils/cpu_utils.cc:94] CPU Frequency: 2208000000 Hz
2020-01-10 09:34:48.951612: I tensorflow/compiler/xla/service/service.cc:168] XLA service 0x56481dbabd80 executing computations on platform Host. Devices:
2020-01-10 09:34:48.951665: I tensorflow/compiler/xla/service/service.cc:175] StreamExecutor device (0): Host, Default Version
* Server ready!
أيضًا ، في بعض الحالات ، لا يبدو أن السجل * Server ready!
يظهر في سجلات عامل الإرساء. كان من الممكن أن يكون مضللًا أيضًا. لست متأكدا ما سبب ذلك
سيتم تكوين الخادم الحالي في Docker الخاص بك بشكل فردي / متزامن ، والذي سيكون تافهًا لجعله مشغولًا / محظورًا ، لذلك من المحتمل أنك ترى ذلك. حاول إضافة بعض الوسائط مثل --workers=2 --threads=4 --worker-class=gthread
.
شكرا ياjavabrett
التي أصلحت ذلك!
كان لديه نفس المشكلة. بقدر ما أستطيع تخمينه من سجلاتي الخاصة ، يبدو أن tensorflow
يستخدم gevent
، ولا يمكنك استخدام gevent
في نفس الوقت في gunicorn
. لا تُحدث العلامات --workers
و --threads
أي فرق بالنسبة لي ، لكن التغيير من --worker-class=gevent
إلى --worker-class=gthread
أصلح المشكلة بالنسبة لي. شكرا ياjavabrett
أهلا! بصفتي مشرفًا على gevent ومساهمًا في هذا المشروع ، يمكنني القول بشكل قاطع أن gevent و gunicorn يعملان معًا بشكل جيد. قد تتدخل مكتبات مختلفة ، لكن هذا ليس خطأ أي من gunicorn أو gevent. الرجاء فتح مشكلة جديدة إذا لم يكن الأمر كذلك بالنسبة لك. شكرا!
التعليق الأكثر فائدة
كان لديه نفس المشكلة. بقدر ما أستطيع تخمينه من سجلاتي الخاصة ، يبدو أن
tensorflow
يستخدمgevent
، ولا يمكنك استخدامgevent
في نفس الوقت فيgunicorn
. لا تُحدث العلامات--workers
و--threads
أي فرق بالنسبة لي ، لكن التغيير من--worker-class=gevent
إلى--worker-class=gthread
أصلح المشكلة بالنسبة لي. شكرا ياjavabrett