Ladění hodnoticího skriptu pomocí azure machine Učení odvozování serveru HTTP

Azure Machine Učení odvozování serveru HTTP je balíček Pythonu, který zpřístupňuje funkci vyhodnocování jako koncový bod HTTP a zabalí kód serveru Flask a závislosti do jednotného balíčku. Je součástí předem připravených imagí Dockeru pro odvozování, které se používají při nasazování modelu se službou Azure Machine Učení. Pomocí samotného balíčku můžete model nasadit místně pro produkční prostředí a také snadno ověřit bodovací (vstupní) skript v místním vývojovém prostředí. Pokud dojde k potížím se skriptem bodování, server vrátí chybu a umístění, kde k chybě došlo.

Server lze také použít k vytvoření ověřovacích bran v kanálu kontinuální integrace a nasazení. Můžete například spustit server s kandidátským skriptem a spustit testovací sadu pro místní koncový bod.

Tento článek se zaměřuje hlavně na uživatele, kteří chtějí odvozovat server k místnímu ladění, ale pomůže vám také pochopit, jak používat server odvozování s online koncovými body.

Místní ladění online koncového bodu

Ladění koncových bodů místně před jejich nasazením do cloudu vám může pomoct zachytit chyby v kódu a konfiguraci dříve. K místnímu ladění koncových bodů můžete použít:

Tento článek se zaměřuje na počítač Azure Učení odvozovat server HTTP.

Následující tabulka obsahuje přehled scénářů, které vám pomůžou vybrat, co je pro vás nejvhodnější.

Scénář Odvození serveru HTTP Místní koncový bod
Aktualizace místního prostředí Pythonu bez opětovného sestavení image Dockeru Yes No
Aktualizace hodnoticího skriptu Ano Yes
Aktualizace konfigurací nasazení (nasazení, prostředí, kód, model) No Ano
Integrace ladicího programu VS Code Ano Yes

Spuštěním serveru HTTP pro odvozování místně se můžete zaměřit na ladění skriptu bodování, aniž by to mělo vliv na konfigurace kontejneru nasazení.

Požadavky

  • Vyžaduje: Python >=3.8
  • Anaconda

Tip

Azure Machine Učení odvozovací server HTTP běží na operačních systémech s Windows a Linuxem.

Instalace

Poznámka:

Abyste se vyhnuli konfliktům balíčků, nainstalujte server do virtuálního prostředí.

Instalaci provedete azureml-inference-server-http packagespuštěním následujícího příkazu v příkazovém řádku nebo terminálu:

python -m pip install azureml-inference-server-http

Místní ladění hodnoticího skriptu

Pokud chcete ladit bodovací skript místně, můžete otestovat, jak se server chová s fiktivním bodovacím skriptem, pomocí nástroje VS Code ladit s balíčkem azureml-inference-server-http nebo otestovat server se skutečným skriptem bodování, souborem modelu a souborem prostředí z našeho úložiště příkladů.

Otestování chování serveru pomocí fiktivního hodnoticího skriptu

  1. Vytvořte adresář pro uložení souborů:

    mkdir server_quickstart
    cd server_quickstart
    
  2. Abyste se vyhnuli konfliktům balíčků, vytvořte virtuální prostředí a aktivujte ho:

    python -m venv myenv
    source myenv/bin/activate
    

    Tip

    Po otestech spusťte deactivate deaktivaci virtuálního prostředí Pythonu.

  3. azureml-inference-server-http Nainstalujte balíček z informačního kanálu pypi:

    python -m pip install azureml-inference-server-http
    
  4. Vytvořte vstupní skript (score.py). Následující příklad vytvoří základní vstupní skript:

    echo '
    import time
    
    def init():
        time.sleep(1)
    
    def run(input_data):
        return {"message":"Hello, World!"}
    ' > score.py
    
  5. Spusťte server (azmlinfsrv) a nastavte score.py ho jako vstupní skript:

    azmlinfsrv --entry_script score.py
    

    Poznámka:

    Server je hostovaný na adrese 0.0.0.0, což znamená, že naslouchá všem IP adresům hostitelského počítače.

  6. Odeslání žádosti o bodování na server pomocí curl:

    curl -p 127.0.0.1:5001/score
    

    Server by měl tomuto typu odpovědět.

    {"message": "Hello, World!"}
    

Po otestech můžete server ukončit stisknutím klávesy Ctrl + C . Teď můžete upravit bodovací skript (score.py) a otestovat změny opětovným spuštěním serveru (azmlinfsrv --entry_script score.py).

Integrace se sadou Visual Studio Code

Existují dva způsoby použití editoru Visual Studio Code (VS Code) a rozšíření Pythonu k ladění pomocí balíčku azureml-inference-server-http (režimy spuštění a připojení).

  • Režim spuštění: Nastavte v editoru launch.json VS Code a spusťte azure machine Učení odvozování serveru HTTP v nástroji VS Code.

    1. Spusťte VS Code a otevřete složku obsahující skript (score.py).

    2. Do tohoto pracovního prostoru ve VS Code přidejte následující konfiguraci launch.json :

      launch.json

      {
          "version": "0.2.0",
          "configurations": [
              {
                  "name": "Debug score.py",
                  "type": "python",
                  "request": "launch",
                  "module": "azureml_inference_server_http.amlserver",
                  "args": [
                      "--entry_script",
                      "score.py"
                  ]
              }
          ]
      }
      
    3. Spusťte relaci ladění ve VS Code. Vyberte Spustit –> Spustit ladění (nebo F5).

  • Režim připojení: Spusťte Azure Machine Učení odvozování serveru HTTP na příkazovém řádku a pomocí rozšíření VS Code + Python připojte se k procesu.

    Poznámka:

    Pokud používáte linuxové prostředí, nejprve nainstalujte gdb balíček spuštěním sudo apt-get install -y gdbpříkazu .

    1. Do tohoto pracovního prostoru ve VS Code přidejte následující konfiguraci launch.json :

      launch.json

      {
          "version": "0.2.0",
          "configurations": [
              {
                  "name": "Python: Attach using Process Id",
                  "type": "python",
                  "request": "attach",
                  "processId": "${command:pickProcess}",
                  "justMyCode": true
              },
          ]
      }
      
    2. Spusťte odvozovaný server pomocí rozhraní příkazového řádku (azmlinfsrv --entry_script score.pyCLI).

    3. Spusťte relaci ladění ve VS Code.

      1. Ve VS Code vyberte Spustit –> Spustit ladění (nebo F5).
      2. Zadejte ID azmlinfsrv procesu (nikoli gunicorn) pomocí protokolů (ze serveru odvozování) zobrazených v rozhraní příkazového řádku. Snímek obrazovky rozhraní příkazového řádku s ID procesu serveru

      Poznámka:

      Pokud se výběr procesu nezobrazí, ručně zadejte ID procesu do processId pole launch.jsonpole .

V obou případech můžete nastavit zarážku a ladit krok za krokem.

Kompletní příklad

V této části spustíme server místně s ukázkovými soubory (bodovací skript, soubor modelu a prostředí) v našem ukázkovém úložišti. Ukázkové soubory se také používají v našem článku o nasazení a určení skóre modelu strojového učení pomocí online koncového bodu.

  1. Naklonujte ukázkové úložiště.

    git clone --depth 1 https://github.com/Azure/azureml-examples
    cd azureml-examples/cli/endpoints/online/model-1/
    
  2. Vytvoření a aktivace virtuálního prostředí pomocí conda V tomto příkladu azureml-inference-server-http se balíček nainstaluje automaticky, protože je součástí závislé knihovny azureml-defaults balíčku conda.yml následujícím způsobem.

    # Create the environment from the YAML file
    conda env create --name model-env -f ./environment/conda.yml
    # Activate the new environment
    conda activate model-env
    
  3. Zkontrolujte svůj bodovací skript.

    online bodování/score.py

    import os
    import logging
    import json
    import numpy
    import joblib
    
    
    def init():
        """
        This function is called when the container is initialized/started, typically after create/update of the deployment.
        You can write the logic here to perform init operations like caching the model in memory
        """
        global model
        # AZUREML_MODEL_DIR is an environment variable created during deployment.
        # It is the path to the model folder (./azureml-models/$MODEL_NAME/$VERSION)
        # Please provide your model's folder name if there is one
        model_path = os.path.join(
            os.getenv("AZUREML_MODEL_DIR"), "model/sklearn_regression_model.pkl"
        )
        # deserialize the model file back into a sklearn model
        model = joblib.load(model_path)
        logging.info("Init complete")
    
    
    def run(raw_data):
        """
        This function is called for every invocation of the endpoint to perform the actual scoring/prediction.
        In the example we extract the data from the json input and call the scikit-learn model's predict()
        method and return the result back
        """
        logging.info("model 1: request received")
        data = json.loads(raw_data)["data"]
        data = numpy.array(data)
        result = model.predict(data)
        logging.info("Request processed")
        return result.tolist()
    
  4. Spusťte server odvozování s určením hodnoticího skriptu a souboru modelu. Zadaný adresář modelu (model_dir parametr) se definuje jako AZUREML_MODEL_DIR proměnná a načte se ve skriptu bodování. V tomto případě určíme aktuální adresář (./), protože podadresář je zadaný ve skriptu bodování jako model/sklearn_regression_model.pkl.

    azmlinfsrv --entry_script ./onlinescoring/score.py --model_dir ./
    

    Příklad spouštěcího protokolu se zobrazí, pokud se server spustil a bodovací skript úspěšně vyvolal. V opačném případě se v protokolu zobrazí chybové zprávy.

  5. Otestujte bodovací skript s ukázkovými daty. Otevřete jiný terminál a přejděte do stejného pracovního adresáře a spusťte příkaz. curl Pomocí příkazu odešlete na server ukázkový požadavek a obdržíte výsledek vyhodnocování.

    curl --request POST "127.0.0.1:5001/score" --header "Content-Type:application/json" --data @sample-request.json
    

    Výsledek vyhodnocování se vrátí, pokud ve vašem bodovacím skriptu není žádný problém. Pokud zjistíte, že se něco nepovedlo, můžete zkusit aktualizovat bodovací skript a znovu spustit server a otestovat aktualizovaný skript.

Trasy serveru

Server naslouchá na portu 5001 (jako výchozí) na těchto trasách.

Název Postup
Sonda živé aktivity 127.0.0.1:5001/
Skóre 127.0.0.1:5001/score
OpenAPI (swagger) 127.0.0.1:5001/swagger.json

Parametry serveru

Následující tabulka obsahuje parametry přijaté serverem:

Parametr Požaduje se Výchozí Popis
entry_script True Relativní nebo absolutní cesta ke skriptu bodování.
model_dir False Relativní nebo absolutní cesta k adresáři, ve kterém je model použitý k odvozování.
port False 5001 Obsluhující port serveru.
worker_count False 0 Počet pracovních vláken, která budou zpracovávat souběžné požadavky.
appinsights_instrumentation_key False Instrumentační klíč pro Application Insights, kde se protokoly publikuje.
access_control_allow_origins False Povolte CORS pro zadané zdroje. Oddělte více zdrojů pomocí ",".
Příklad: "microsoft.com, bing.com"

Tok žádosti

Následující kroky vysvětlují, jak azure machine Učení odvozování http serveru (azmlinfsrv) zpracovává příchozí požadavky:

  1. Obálka rozhraní příkazového řádku Pythonu se nachází kolem zásobníku sítě serveru a slouží ke spuštění serveru.
  2. Klient odešle požadavek na server.
  3. Při přijetí požadavku prochází serverem WSGI a pak se odešle jednomu z pracovních procesů.
  4. Požadavky pak zpracovává aplikace Flask , která načte vstupní skript a všechny závislosti.
  5. Nakonec se požadavek odešle do vstupního skriptu. Vstupní skript pak provede volání odvozování načteného modelu a vrátí odpověď.

Diagram procesu serveru HTTP

Principy protokolů

Tady popisujeme protokoly azure machine Učení odvozování serveru HTTP. Protokol můžete získat při místním spuštění azureml-inference-server-http nebo získat protokoly kontejneru, pokud používáte online koncové body.

Poznámka:

Formát protokolování se od verze 0.8.0 změnil. Pokud najdete protokol v jiném stylu, aktualizujte azureml-inference-server-http balíček na nejnovější verzi.

Tip

Pokud používáte online koncové body, začíná Azure Machine Learning Inferencing HTTP server <version>protokol ze serveru odvozování .

Spouštěcí protokoly

Po spuštění serveru se nastavení serveru nejprve zobrazí v protokolech následujícím způsobem:

Azure Machine Learning Inferencing HTTP server <version>


Server Settings
---------------
Entry Script Name: <entry_script>
Model Directory: <model_dir>
Worker Count: <worker_count>
Worker Timeout (seconds): None
Server Port: <port>
Application Insights Enabled: false
Application Insights Key: <appinsights_instrumentation_key>
Inferencing HTTP server version: azmlinfsrv/<version>
CORS for the specified origins: <access_control_allow_origins>


Server Routes
---------------
Liveness Probe: GET   127.0.0.1:<port>/
Score:          POST  127.0.0.1:<port>/score

<logs>

Když například spustíte server, následuje kompletní příklad:

Azure Machine Learning Inferencing HTTP server v0.8.0


Server Settings
---------------
Entry Script Name: /home/user-name/azureml-examples/cli/endpoints/online/model-1/onlinescoring/score.py
Model Directory: ./
Worker Count: 1
Worker Timeout (seconds): None
Server Port: 5001
Application Insights Enabled: false
Application Insights Key: None
Inferencing HTTP server version: azmlinfsrv/0.8.0
CORS for the specified origins: None


Server Routes
---------------
Liveness Probe: GET   127.0.0.1:5001/
Score:          POST  127.0.0.1:5001/score

2022-12-24 07:37:53,318 I [32726] gunicorn.error - Starting gunicorn 20.1.0
2022-12-24 07:37:53,319 I [32726] gunicorn.error - Listening at: http://0.0.0.0:5001 (32726)
2022-12-24 07:37:53,319 I [32726] gunicorn.error - Using worker: sync
2022-12-24 07:37:53,322 I [32756] gunicorn.error - Booting worker with pid: 32756
Initializing logger
2022-12-24 07:37:53,779 I [32756] azmlinfsrv - Starting up app insights client
2022-12-24 07:37:54,518 I [32756] azmlinfsrv.user_script - Found user script at /home/user-name/azureml-examples/cli/endpoints/online/model-1/onlinescoring/score.py
2022-12-24 07:37:54,518 I [32756] azmlinfsrv.user_script - run() is not decorated. Server will invoke it with the input in JSON string.
2022-12-24 07:37:54,518 I [32756] azmlinfsrv.user_script - Invoking user's init function
2022-12-24 07:37:55,974 I [32756] azmlinfsrv.user_script - Users's init has completed successfully
2022-12-24 07:37:55,976 I [32756] azmlinfsrv.swagger - Swaggers are prepared for the following versions: [2, 3, 3.1].
2022-12-24 07:37:55,977 I [32756] azmlinfsrv - AML_FLASK_ONE_COMPATIBILITY is set, but patching is not necessary.

Formát protokolu

Protokoly ze serveru odvozování se generují v následujícím formátu, s výjimkou skriptů spouštěče, protože nejsou součástí balíčku Python:

<UTC Time> | <level> [<pid>] <logger name> - <message>

Tady <pid> je ID procesu a <level> je prvním znakem úrovně protokolování – E pro CHYBU, I pro INFORMACE atd.

V Pythonu je šest úrovní protokolování s čísly přidruženými ke závažnosti:

Úroveň protokolování Číselná hodnota
Kritické 50
CHYBA 40
UPOZORNĚNÍ 30
INFO 20
LADIT 10
NOTSET 0

Příručka pro řešení problémů

V této části vám poskytneme základní tipy pro řešení potíží pro Azure Machine Učení odvozování serveru HTTP. Pokud chcete řešit potíže s online koncovými body, projděte si také řešení potíží s nasazením online koncových bodů.

Základní kroky

Základní kroky pro řešení potíží jsou:

  1. Shromážděte informace o verzi pro vaše prostředí Pythonu.
  2. Ujistěte se, že verze balíčku pythonu azureml-inference-server-http, která je zadaná v souboru prostředí, odpovídá verzi serveru HTTP pro odvozování AzureML, která se zobrazila v spouštěcím protokolu. Někdy překladač závislostí pipu vede k neočekávaným verzím nainstalovaných balíčků.
  3. Pokud ve svém prostředí zadáte Flask (a jeho závislosti), odeberte je. Mezi závislosti patří Flask, , Jinja2itsdangerous, Werkzeug, MarkupSafe, a click. Flask je v balíčku serveru uvedený jako závislost a je nejlepší nechat ho nainstalovat. Když server podporuje nové verze Flasku, automaticky je získáte.

Verze serveru

Balíček azureml-inference-server-http serveru se publikuje do PyPI. Náš protokol změn a všechny předchozí verze najdete na naší stránce PyPI. Pokud používáte starší verzi, aktualizujte na nejnovější verzi.

  • 0.4.x: Verze, která je součástí trénovacích obrázků ≤ 20220601 a v azureml-defaults>=1.34,<=1.43. 0.4.13 je poslední stabilní verze. Pokud používáte server před verzí 0.4.11, můžou se zobrazit problémy se závislostmi Flasku, například nejde importovat název Markup z jinja2. Pokud je to možné, doporučujeme upgradovat na 0.4.13 nebo 0.8.x (nejnovější verzi).
  • 0.6.x: Verze, která je předinstalovaná v odvozování obrázků ≤ 20220516. Nejnovější stabilní verze je 0.6.1.
  • 0.7.x: První verze, která podporuje Flask 2. Nejnovější stabilní verze je 0.7.7.
  • 0.8.x: Formát protokolu se změnil a podpora Pythonu 3.6 se ukončila.

Závislosti balíčků

Nejdůležitější balíčky pro server azureml-inference-server-http jsou následující balíčky:

  • Baňky
  • opencensus-ext-azure
  • odvození schématu

Pokud jste zadali azureml-defaults ve svém prostředí Pythonu, závisí balíček azureml-inference-server-http a nainstaluje se automaticky.

Tip

Pokud používáte sadu Python SDK v1 a explicitně nezadáte azureml-defaults v prostředí Pythonu, může sada SDK přidat balíček za vás. Uzamkne ho ale na verzi, na které je sada SDK zapnutá. Pokud je 1.38.0například verze sady SDK, přidá azureml-defaults==1.38.0 se do požadavků pip prostředí.

Nejčastější dotazy

1. Při spuštění serveru došlo k následující chybě:


TypeError: register() takes 3 positional arguments but 4 were given

  File "/var/azureml-server/aml_blueprint.py", line 251, in register

    super(AMLBlueprint, self).register(app, options, first_registration)

TypeError: register() takes 3 positional arguments but 4 were given

Ve svém prostředí Pythonu máte nainstalovaný Flask 2 , ale používáte verzi azureml-inference-server-http , která nepodporuje Flask 2. Přidali jsme azureml-inference-server-http>=0.7.0podporu pro Flask 2, která je také součástí azureml-defaults>=1.44.

  • Pokud tento balíček nepoužíváte v imagi Dockeru AzureML, použijte nejnovější verzi azureml-inference-server-http nebo azureml-defaults.

  • Pokud tento balíček používáte s imagí Dockeru AzureML, ujistěte se, že používáte image integrovanou nebo po červenci 2022. Verze image je dostupná v protokolech kontejneru. Měli byste být schopni najít protokol podobný následujícímu:

    2022-08-22T17:05:02,147738763+00:00 | gunicorn/run | AzureML Container Runtime Information
    2022-08-22T17:05:02,161963207+00:00 | gunicorn/run | ###############################################
    2022-08-22T17:05:02,168970479+00:00 | gunicorn/run | 
    2022-08-22T17:05:02,174364834+00:00 | gunicorn/run | 
    2022-08-22T17:05:02,187280665+00:00 | gunicorn/run | AzureML image information: openmpi4.1.0-ubuntu20.04, Materializaton Build:20220708.v2
    2022-08-22T17:05:02,188930082+00:00 | gunicorn/run | 
    2022-08-22T17:05:02,190557998+00:00 | gunicorn/run | 
    

    Datum sestavení obrázku se zobrazí po "Materialization Build", který v předchozím příkladu je 20220708, nebo 8. července 2022. Tato image je kompatibilní s Flaskem 2. Pokud v protokolu kontejneru nevidíte banner podobný tomuto typu, je vaše image zahlcená a měla by se aktualizovat. Pokud používáte image CUDA a nemůžete najít novější image, zkontrolujte, jestli je vaše image v Kontejnerech AzureML zastaralá. Pokud ano, měli byste být schopni najít náhrady.

  • Pokud používáte server s online koncovým bodem, najdete protokoly také v části Protokoly nasazení na stránce online koncového bodu v studio Azure Machine Learning. Pokud nasadíte pomocí sady SDK v1 a explicitně nezadáte image v konfiguraci nasazení, použije se výchozí verze openmpi4.1.0-ubuntu20.04 , která odpovídá vaší místní sadě nástrojů sady SDK, což nemusí být nejnovější verze image. Například sada SDK 1.43 se ve výchozím nastavení použije openmpi4.1.0-ubuntu20.04:20220616, což není kompatibilní. Ujistěte se, že pro nasazení používáte nejnovější sadu SDK.

  • Pokud z nějakého důvodu nemůžete aktualizovat image, můžete se dočasně vyhnout problému připnutím azureml-defaults==1.43 nebo azureml-inference-server-http~=0.4.13, který nainstaluje starší verzi serveru s Flask 1.0.x.

2. Narazil(a) jsem na moduly ImportError nebo ModuleNotFoundError na moduly opencensus, MarkupSafejinja2, nebo click při spuštění, jako je následující zpráva:

ImportError: cannot import name 'Markup' from 'jinja2'

Starší verze (<= 0.4.10) serveru nepřipnuly závislost Flasku na kompatibilní verze. Tento problém je opravený v nejnovější verzi serveru.

Další kroky