newsmode
search
Меню
arrow_back Назад

TorchServe – Hamel’s Blog - Hamel Husain

auto_awesomeКраткое саммари

Хэмел Хусейн делится впечатлениями от экспериментов с TorchServe — инструментом для развёртывания моделей PyTorch. Среди плюсов: автоматическая батчёвка запросов, версионирование моделей, встроенное логирование и метрики. Однако отладка затруднена из-за гибрида Java и Python, а кривая обучения круче, чем у TF Serving, поскольку приходится разбираться в исходниках класса BaseHandler. Автор рекомендует использовать кастомные обработчики вместо «магических» дефолтных и отмечает скрытые ограничения вроде обязательного расширения .pt для torchscript. Пре- и постобработка в TorchServe проще, чем в TFServing, где приходится менять сигнатуру модели через DSL. При этом TF Serving выигрывает в управлении версиями за счёт алиасов вроде «staging» и «production», которых в TorchServe без обратного прокси не реализовать.

Experiments With Torch Serve

Эксперименты с Torch Serve

Why Use Torch Serve

Зачем использовать Torch Serve

  • Automatic batching of requests (optional).
  • Model versioning.
  • Out of the box Logging and metrics.
  • Автоматическая батчёвка запросов (опционально). Версионирование моделей. Логирование и метрики «из коробки».

    Impressions

    Впечатления

  • Torch Serve is an absolute PITA to debug, because its part java and part python (ex: you can’t use an interactive debugger). If you do not need auto-batching, I would rather use FastAPI and scale it with Kubernetes. You have to end up creating custom handlers in many practical scenarios (like using HF models), and at the end of the day you are writing a bunch of code to glue everything together.
  • In comparison to TF Serving, it is harder to get started, but much easier to customize things once you learn the API. The initial learning curve to TorchServe is much steeper than TF Serving, because you have to study the BaseHandler class (read the source code) to understand how things work. It is not clear how the various artifacts you save with the torch-model-archiver work together unless you study BaseHandler. For example:
    • the help docs of torch-model-archiver state that --model-file is mandatory for eager mode models, which is not entirely true because you can load the model in the handler instead of implementing an interface that torch serve knows how to load (e.g. a class with a load_state_dict method like this example. Furthermore, this model file can only contain one class definition extended from torch.nn.modules which is an odd constraint. When you search the internet for using torch-serve, many people are ignoring the prescribed interface and are loading models inside a custom handler instead. Here is an example of doing this with fastai and HuggingFace. I believe it is a better idea to use a custom handler because it is more transparent and easier to understand. The default handlers in the getting started guides are a bit too magical and I think they cause confusion for newcomers. I would argue that the default handlers should only be used after you understand BaseHandler and write a few custom handlers.
    • If you want to use torchscript, your file extension must be .pt (not .pth). This is not documented anywhere, and is an example of something you can only learn from the BaseHandler source code (that particular file extension is hardcoded!).
  • pre and post processing in TorchServe is significantly easier to understand compared to TFServe. Custom handlers allow you to do what you want in pure python, whereas with TFServing you have to modify the model’s signature which involves pushing the pre/post processing into the model’s graph and other confusing steps that use DSLs. This is not surprising, as this is why people like PyTorch in general.
  • I like how you can make REST API requests to manage models. In contrast, TF Serving requires you to update config files (which it periodically checks for updates).
  • I like model versioning in TF Serving a bit more, as it allows you to alias your endpoints - for example “staging” or “production”. It doesn’t appear you can alias your model endpoints in TorchServe without a reverse proxy.
  • Torch Serve — это сущее мучение для отладки, поскольку он частично написан на Java, а частично на Python (например, нельзя использовать интерактивный отладчик). Если вам не нужна автоматическая батчёвка, я бы предпочёл FastAPI и масштабирование через Kubernetes. Во многих практических сценариях (например, при использовании HF-моделей) приходится создавать кастомные обработчики, и в итоге вы пишете кучу кода, чтобы всё это склеить воедино. По сравнению с TF Serving начать сложнее, но настраивать что-то под себя гораздо проще, как только вы освоите API. Начальная кривая обучения TorchServe значительно круче, чем у TF Serving, потому что для понимания принципов работы нужно изучить класс BaseHandler (читать исходный код). Непонятно, как именно различные артефакты, которые вы сохраняете с помощью torch-model-archiver, работают вместе, пока вы не изучите BaseHandler. Например: в справке по torch-model-archiver сказано, что --model-file обязателен для моделей в eager-режиме, что не совсем правда, поскольку можно загрузить модель прямо в обработчике вместо реализации интерфейса, который TorchServe умеет загружать (например, класса с методом load_state_dict, как в этом примере). Более того, этот файл модели может содержать только одно определение класса, унаследованного от torch.nn.modules — странное ограничение. Когда ищешь информацию об использовании torch-serve в интернете, многие игнорируют предписанный интерфейс и вместо этого загружают модели внутри кастомного обработчика. Вот пример такого подхода с fastai и HuggingFace. Я считаю, что использовать кастомный обработчик — лучшая идея, потому что это прозрачнее и понятнее. Дефолтные обработчики из вводных гайдов слишком «магические», и, на мой взгляд, они сбивают новичков с толку. Я бы сказал, что дефолтные обработчики стоит использовать только после того, как вы разберётесь с BaseHandler и напишете несколько кастомных обработчиков. Если хотите использовать torchscript, расширение файла должно быть .pt (не .pth). Это нигде не задокументировано и является примером того, что можно узнать только из исходного кода BaseHandler (это конкретное расширение файла зашито в коде!). Пре- и постобработка в TorchServe значительно проще для понимания по сравнению с TFServe. Кастомные обработчики позволяют делать что угодно на чистом Python, тогда как в TFServing приходится модифицировать сигнатуру модели, что подразумевает встраивание пре-/постобработки в граф модели и другие запутанные шаги с использованием DSL. Это неудивительно — именно за это люди и любят PyTorch в целом. Мне нравится, что управлять моделями можно через REST API-запросы — см. manage models. В TF Serving же приходится править конфиги (которые он периодически проверяет на обновления). Версионирование моделей в TF Serving мне нравится чуть больше, поскольку оно позволяет давать алиасы эндпоинтам — например, «staging» или «production». Похоже, в TorchServe нельзя сделать алиасы для эндпоинтов моделей без обратного прокси.