Как развернуть модели TensorFlow в производство с помощью TF Serving

1656596327 kak razvernut modeli tensorflow v proizvodstvo s pomoshhyu tf serving

от Талеса Сильвы

1*xNJAAxtjy5tgQDIcfxd-Yw

Введение

Запуск моделей машинного обучения (ML) в производство стал популярной, постоянной темой. Многие компании и фреймворки предлагают различные решения, направленные на решение этой проблемы.

Чтобы решить эту проблему, Google выпустила TensorFlow (TF) Serving в надежде решить проблему развертывания моделей ML в производстве.

Этот материал предлагает практическое руководство по обслуживанию предварительно обученной сети сверточной семантической сегментации. В конце этой статьи вы сможете использовать TF Serving для развертывания и отправки запросов к Deep CNN, обученному TF. Кроме того, я приведу обзор основных блоков TF Serving, обсудю его API и как это все работает.

Одно, что вы сразу заметите, это то, что для фактического обслуживания модели TF требуется очень мало кода. Если вы хотите ознакомиться с учебником и запустить пример на своей машине, придерживайтесь его как есть. Но если вы хотите знать только об обслуживании TensorFlow, вы можете сосредоточиться на первых двух главах.

Этот материал подчеркивает часть работы, которую мы выполняем здесь, в Daitan Group.

Библиотеки обслуживания TensorFlow — обзор

Давайте потратим немного времени, чтобы понять, как TF Serving обрабатывает полный цикл обслуживания моделей ML. Здесь мы рассмотрим на высоком уровне каждый из основных строительных блоков TF Serving. Цель этого раздела – предоставить мягкое вступление в API обслуживания TF. Для получения подробного обзора перейдите на страницу документации TF Serving.

Обслуживание TensorFlow состоит из нескольких абстракций. Эти абстракции реализуют API для разных задач. Важнейшими из них являются обслуживаемый, загрузчик, источник и менеджер. Давайте рассмотрим, как они взаимодействуют.

1*TwfOoS3M8DaUiB7ntP07_w

В двух словах, жизненный цикл обслуживания начинается, когда TF Serving идентифицирует модель диска. Компонент Source позаботится об этом. Он отвечает за определение новых моделей, которые следует скачать. На практике он следит за файловой системой, чтобы определить когда новая версия модели поступает на диск. Когда он видит новую версию, он продолжает создание загрузчика этой конкретной версии модели.

В общем, Loader знает о модели почти все. Он содержит сведения о том, как его загрузить и как оценить необходимые ресурсы модели, например необходимую оперативную память и память графического процессора. Загрузчик имеет указатель на модель на диске вместе со всеми необходимыми метаданными для загрузки. Но здесь загвоздка: Loader пока не имеет права загружать модель.

После создания загрузчика источник посылает его менеджеру как желаемую версию.

Получив ожидаемую версию модели, менеджер приступает к процессу обслуживания. Здесь есть две возможности. Одна из них состоит в том, что первая версия модели подлежит развертыванию. В этой ситуации менеджер позаботится о наличии необходимых ресурсов. После этого менеджер предоставляет загрузчику разрешение загрузить модель.

Во-вторых, мы создаем новую версию существующей модели. В этом случае менеджер должен ознакомиться с плагином политики версий, прежде чем идти дальше. Политика версий определяет, как происходит процесс загрузки новой версии модели.

В частности, при загрузке новой версии модели мы можем выбрать между сохранением (1) доступности или (2) ресурсов. В первом случае мы заинтересованы, чтобы наша система всегда была доступна для входящих запросов клиентов. Мы знаем, что менеджер позволяет загрузчику создавать экземпляр нового графика с новыми весовыми показателями.

На данный момент у нас есть две версии модели, загруженные одновременно. Но Менеджер выгружает более старую версию только после завершения загрузки и безопасно переключаться между моделями.

С другой стороны, если мы хотим сэкономить ресурсы без дополнительного буфера (для новой версии), мы можем сохранить ресурсы. Для очень трудных моделей может быть полезно иметь небольшой разрыв в доступности в обмен на экономию памяти.

В конце, когда клиент запрашивает дескриптор модели, менеджер возвращает дескриптор обслуживанию.

Благодаря этому обзору мы готовы погрузиться в реальную программу. В следующих разделах мы описываем, как обслуживать сверточную нейронную сеть (CNN) с помощью TF Serving.

Экспорт модели для обслуживания

Первым шагом для обслуживания модели ML, созданной в TensorFlow, убедиться, что она имеет правильный формат. Для этого TensorFlow предоставляет класс SavedModel.

SavedModel – это универсальный формат сериализации для моделей TensorFlow. Если вы знакомы с TF, вы, вероятно, использовали TensorFlow Saver для сохранения переменных вашей модели.

TensorFlow Saver предоставляет функции для сохранения/восстановления файлов контрольной точки модели на/с диска. В самом деле, SavedModel оборачивает TensorFlow Saver и должен быть стандартным способом экспорта моделей TF для обслуживания.

Объект SavedModel имеет несколько приятных функций.

Во-первых, он позволяет сохранять более одного метаграфика в одном объекте SavedModel. Другими словами, это позволяет нам иметь разные графики для разных задач.

Например, предположим, что вы только что закончили обучение модели. В большинстве ситуаций, чтобы заключить, ваш график не требует определенных операций, касающихся обучения. Эти операции могут включать переменные оптимизатора, тензоры планирования скорости обучения, дополнительные операции предварительной обработки и т.п.

Кроме того, вы можете предоставить квантованную версию графика для мобильного развертывания.

1*WHJcm2nqCaCXk6XVgU_b-g

В этом контексте SavedModel позволяет сохранять графики с разными конфигурациями. В нашем примере мы имели бы три разных графика с соответствующими тегами, такими как «обучение», «вывод» и «мобильный». Кроме того, все эти три графики имеют одинаковый набор переменных, что подчеркивает эффективность памяти.

Не так давно, когда мы хотели развернуть модели TF на мобильных устройствах, нам нужно было знать названия входных и выходных тензоров для подачи и получения данных в/из модели. Эта потребность заставила программистов искать нужный им тензор среди всех тензоров графа. Если бы тензоры были неправильно названы, задача могла бы быть очень изнурительной.

Чтобы облегчить работу, SavedModel предлагает поддержку SignatureDefs. Подводя итог, SignatureDefs определяют сигнатуру вычисления, которое поддерживает TensorFlow. Он определяет правильные входные и выходные тензоры для вычислительного графика. Проще говоря, с помощью этих сигнатур можно указать точные узлы для ввода и вывода.

Для использования своих встроенных API обслуживания, TF Serving требует, чтобы модели включали один или несколько SignatureDefs.

1*0yHcL0JGeLXJqhQo0see1w

Чтобы создать такие сигнатуры, нам нужно предоставить определение входов, выходов и нужного имени метода. Входы и Выходы представляют отображение от строки к объектам TensorInfo (подробнее о последнем). Здесь мы определяем тензоры по умолчанию для подачи и получения данных в и из графика. The название_метода Параметр нацелен на один из API высокого уровня обслуживания TF.

В настоящее время существует три обслуживающих API: классификация, прогнозирование и регрессия. Каждое определение подписи соответствует определенному API RPC. Classification SegnatureDef используется для Classify RPC API. Predict SegnatureDef используется для APC Predict RPC и далее.

Для подписи классификации должен быть входной тензор (для получения данных) и по крайней мере один из двух возможных выходных тензоров: классы и оценки. Регрессия SignatureDef требует ровно одного тензора для ввода и другого для вывода. Наконец, подпись Predict разрешает динамическое количество входных и выходных тензоров.

Кроме того, SavedModel поддерживает хранение активов в случаях, когда инициализация операций зависит от внешних файлов. Кроме того, у него есть механизмы очистки устройств перед созданием SavedModel.

Теперь давайте посмотрим, как мы можем сделать это на практике.

Настройка среды

Прежде чем начать, клонируйте этот TensorFlow DeepLab-v3 реализация по Github.

DeepLab – это лучшая семантическая сегментация ConvNet от Google. В сущности, сеть принимает изображение как входные данные и выводит маску, отделяющую определенные объекты от фона.

Эта версия была обучена на наборе данных сегментации VOC Pascal. Таким образом, он может сегментироваться и распознаваться до 20 классов. Если вы хотите узнать больше о семантической сегментации и DeepLab-v3, ознакомьтесь с «Погружение в сети глубокой сверточной семантической сегментации» и Deeplab_V3.

Все файлы, связанные с обслуживанием, находятся в: ./deelab_v3/serving/. Там вы найдете два важных файла: deeplab_saved_model.py и deeplab_client.ipynb

Перед тем как идти дальше, обязательно загрузите предварительно подготовленную модель Deelab-v3. Выделите хранилище GitHub выше, нажмите ссылку контрольные точки и загрузите папку с именем 16645/.

В конце концов у вас должна быть папка с именем tboard_logs/ с 16645/ папку, расположенную внутри нее.

1*ScNnPqBm0IgcyyB6QAvkeA

Теперь нам нужно создать две виртуальные среды Python. Один для Python 3, а другой для Python 2. Для каждого env убедитесь, что установлены необходимые зависимости. Их можно найти в файлах serving_requirements.txt и client_requirements.txt.

Нам нужны две среды Python, потому что наша модель, DeepLab-v3, была разработана под Python 3. Однако API TensorFlow Serving Python опубликована только для Python 2. Поэтому для экспорта модели и запуска TF-сервиса мы используем Python 3 env. Для запуска клиентского кода с помощью TF Serving Python API мы используем пакет PIP (доступен только для Python 2).

Обратите внимание, что вы можете отказаться от env Python 2, используя API обслуживание с bazel. Дополнительные сведения см. в разделе Установка обслуживания TF.

Завершив этот шаг, давайте начнем с того, что действительно имеет значение.

Как это сделать

Для использования SavedModel TensorFlow предоставляет простой в использовании высокоуровневый класс полезности под названием SavedModelBuilder. Класс SavedModelBuilder предоставляет функции для сохранения нескольких метаграфов, связанных переменных и активов.

Рассмотрим текущий пример того, как экспортировать модель CNN глубокой сегментации для обслуживания.

Как упоминалось выше, для экспорта модели мы используем класс SavedModelBuilder. Он сгенерирует файл буфера протокола SavedModel вместе с переменными и активами модели (если необходимо).

Давайте разберем код.

SavedModelBuilder получает (как входные данные) каталог, где хранятся данные модели. Вот, экспортный_путь переменная является конкатенацией база_пути экспорта и модель_версия. В результате разные версии модели будут сохранены в отдельных каталогах внутри база_пути экспорта папку.

Скажем, у нас есть базовая версия нашей модели в производстве, но мы хотим развернуть ее новую версию. Мы улучшили точность нашей модели и хотим предложить эту новую версию нашим клиентам.

Чтобы экспортировать другую версию того же графика, мы можем просто установить FLAGS.model_version к большему целому значению. Затем внутри будет создана другая папка (в которой хранится новая версия нашей модели). база_пути экспорта папку.

Теперь нам нужно указать тензора входа и выхода нашей модели. Для этого мы используем SignatureDefs. Подписи определяют тип модели, которую мы хотим экспортировать. Он обеспечивает отображение строк (логических имен тензоров) к объектам TensorInfo. Идея состоит в том, что вместо ссылок на фактические имена тензоров для ввода/вывода клиенты могут ссылаться на логические имена, определенные сигнатурами.

Для обслуживания семантической сегментации CNN мы собираемся создать a Предсказать Подпись. Заметьте, что build_signature_def() функция принимает отображение для тензоров ввода и вывода, а также требуемый API.

SignatureDef требует спецификации: входов, выходов и имени метода. Обратите внимание, что мы ожидаем три значения для входы изображение и еще два тензора, определяющих его размеры (высота и ширина). Для выходымы определили только один результат – маску вывода сегментации.

Обратите внимание, что строки ‘image’, ‘height’, ‘width’ и ‘segmentation_map’ не являются тензорами. Это логические названия, которые ссылаются на фактические тензоры. input_tensor, image_height_tensorи тензор_ширины изображения. Таким образом, это может быть любая уникальная строка, которая вам нравится.

Кроме того, отображения в SignatureDefs касаются объектов protobuf TensorInfo, а не фактических тензоров. Для создания объектов TensorInfo мы используем функцию утилиты: tf.saved_model.utils.build_tensor_info(тензор).

Вот и все. Теперь мы называем add_meta_graph_and_variables() функция создания объекта буфера протокола SavedModel. Затем запускаем сохранить() метод, и он будет сохранять снимок нашей модели на диске, содержащем переменные и активы модели.

Теперь мы можем запустить deeplab_saved_model.py для экспорта нашей модели.

Если все прошло хорошо, вы увидите папку ./serving/versions/1. Обратите внимание, что ‘1’ представляет текущую версию модели. Внутри каждого подкаталога версии вы увидите следующие файлы:

1*pDEnXV2Ewsrlz6bSWJBTyQ
  • saved_model.pb или saved_model.pbtxt. Это сериализированный файл SavedModel. Он включает одно или несколько определений графов модели, а также определение сигнатур.
  • Переменные. Эта папка содержит сериализированные переменные графики.

Теперь мы готовы запустить нашу модель сервера. Для этого запустите:

$ tensorflow_model_server --port=9000 --model_name=deeplab --model_base_path=<full/path/to/serving/versions/>

The model_base_path ссылается на то место, где была сохранена экспортируемая модель. Кроме того, мы не указываем папку версии в пути. Управление версиями модели обрабатывается TF Serving.

Формирование запросов клиентов

Код клиента очень прост. Посмотрите на это: deeplab_client.ipynb.

Сначала мы читаем изображение, которое мы хотим отправить на сервер, и конвертируем его в нужный формат.

Далее мы создаем заглушку gRPC. Заглушка позволяет нам вызывать способы удаленного сервера. Для этого мы создаем экземпляр beta_create_PredictionService_stub класс с prediction_service_pb2 модуль. На этом этапе заглушка содержит необходимую логику для вызова удаленных процедур (с сервера), как будто они локальные.

Теперь необходимо создать и установить объект запроса. Поскольку сервер реализует TensorFlow Predict API, нам нужно проанализировать запрос Predict. Чтобы отправить запрос Predict, сначала мы создаем экземпляр PredictRequest класс с predict_pb2 модуль. Нам также нужно указать модель_спец.название и model_spec.signature_name параметры The имя param – это аргумент ‘model_name’, который мы определили при запуске сервера. И имя_подписи ссылается на логическое имя, предназначенное для signature_def_map() параметр add_meta_graph() рутина.

Далее мы должны предоставить входящие данные, как указано в сигнатуре сервера. Помните, что на сервере мы определили Predict API для ожидания изображения и двух скаляров (высота и ширина изображения). Для подачи входных данных в объект запроса TensorFlow предоставляет утилиту tf.make_tensor_proto(). Этот метод создает объект TensorProto из объекта numpy/Python. Мы можем использовать его для подачи изображения и размеров объекта запроса.

Похоже, что мы готовы вызвать сервер. Для этого мы вызываем Предусмотреть() метод (с помощью заглушки) и передать объект запросу в качестве аргумента.

Для запросов, которые возвращают один ответ, gRPC поддерживает синхронные и асинхронные вызовы. Таким образом, если вы хотите выполнить какую-либо работу во время обработки запроса, мы можем позвонить по телефону Predict.future() вместо Предусмотреть().

Теперь мы можем получить и наслаждаться результатами.

1*tVrioWYLRyxTA-MXYoMCdA

Надеюсь, вам понравилась эта статья. Спасибо, что прочли!

Если вы хотите больше, посмотрите:

Как научить свой собственный FaceID ConvNet с помощью выполнения TensorFlow Eager
Лица повсюду – от фотографий и видео на веб-сайтах социальных сетей до программ безопасности потребителей, таких как…medium.freecodecamp.orgПогружение в сети глубокой сверточной семантической сегментации и Deelab_V3
Глубокие сверточные нейронные сети (DCNN) добились чрезвычайного успеха в различных программах компьютерного зрения.medium.freecodecamp.org

1*RzOHqzrJEIrB5ZY0nJAcvg

Добавить комментарий

Ваш адрес email не будет опубликован.