深度學習Tensorflow生產環境部署(上·環境準備篇)

最近在研究Tensorflow Serving生產環境部署,尤爲是在作服務器GPU環境部署時,遇到了很多坑。特地總結一下,當作前車可鑑。html

1 系統背景

系統是ubuntu16.04python

ubuntu@ubuntu:/usr/bin$ cat /etc/issue
Ubuntu 16.04.5 LTS \n \l

或者linux

ubuntu@ubuntu:/usr/bin$ uname -m && cat /etc/*release
x86_64
DISTRIB_ID=Ubuntu
DISTRIB_RELEASE=16.04
DISTRIB_CODENAME=xenial
DISTRIB_DESCRIPTION="Ubuntu 16.04.5 LTS"
NAME="Ubuntu"
VERSION="16.04.5 LTS (Xenial Xerus)"
ID=ubuntu
ID_LIKE=debian
PRETTY_NAME="Ubuntu 16.04.5 LTS"
VERSION_ID="16.04"
HOME_URL="http://www.ubuntu.com/"
SUPPORT_URL="http://help.ubuntu.com/"
BUG_REPORT_URL="http://bugs.launchpad.net/ubuntu/"
VERSION_CODENAME=xenial
UBUNTU_CODENAME=xenial

顯卡是Tesla的P40git

ubuntu@ubuntu:~$ nvidia-smi
Thu Jan  3 16:53:36 2019       
+-----------------------------------------------------------------------------+
| NVIDIA-SMI 384.130                Driver Version: 384.130                   |
|-------------------------------+----------------------+----------------------+
| GPU  Name        Persistence-M| Bus-Id        Disp.A | Volatile Uncorr. ECC |
| Fan  Temp  Perf  Pwr:Usage/Cap|         Memory-Usage | GPU-Util  Compute M. |
|===============================+======================+======================|
|   0  Tesla P40           Off  | 00000000:3B:00.0 Off |                    0 |
| N/A   34C    P0    49W / 250W |  22152MiB / 22912MiB |      0%      Default |
+-------------------------------+----------------------+----------------------+
                                                                               
+-----------------------------------------------------------------------------+
| Processes:                                                       GPU Memory |
|  GPU       PID   Type   Process name                             Usage      |
|=============================================================================|
|    0    108329      C   python                                      4963MiB |
|    0    133840      C   tensorflow_model_server                    17179MiB |
+-----------------------------------------------------------------------------+

TensorFlow則是當下最新的1.12.0版本。github

2 背景知識

在介紹如何部署以前,先來了解一下相關的概念。web

2.1 TensorFlow Serving

參考資料算法

TensorFlow Serving是google提供的一種生產環境部署方案,通常來講在作算法訓練後,都會導出一個模型,在應用中直接使用。docker

正常的思路是在flask這種web服務中嵌入tensorflow的模型,提供rest api的雲服務接口。考慮到併發高可用性,通常會採起多進程的部署方式,即一臺雲服務器上同時部署多個flask,每一個進程獨享一部分GPU資源,顯然這樣是很浪費資源的。json

Google提供了一種生產環境的新思路,他們開發了一個tensorflow-serving的服務,能夠自動加載某個路徑下的全部模型,模型經過事先定義的輸入輸出和計算圖,直接提供rpc或者rest的服務。flask

  • 一方面,支持多版本的熱部署(好比當前生產環境部署的是1版本的模型,訓練完成後生成一個2版本的模型,tensorflow會自動加載這個模型,停掉以前的模型)。
  • 另外一方面,tensorflow serving內部經過異步調用的方式,實現高可用,而且自動組織輸入以批次調用的方式節省GPU計算資源。

所以,整個模型的調用方式就變成了:

客戶端 ----> web服務(flask或者tornado) --grpc或者rest--> tensorflow serving

若是咱們想要替換模型或者更新版本,只須要訓練模型並將訓練結果保存到固定的目錄下就能夠了。

2.2 Docker

參考資料:

docker簡單來講就是一種容器技術,若是有作過技術支持的朋友確定瞭解安裝軟件的痛苦——各類系統環境,致使各類安裝報錯...docker解決的問題就是,只要你再服務器上安裝上docker,那麼它會自動屏蔽全部的硬件信息,拉取一個鏡像,就能直接啓動提供服務。

搭建docker也很簡單,若是是mac直接下載dmg文件就能夠雙擊運行;若是是ubuntu直接運行

sudo apt-get install docker

不過Ubuntu安裝後只能經過root使用,若是想讓其餘用戶使用,須要調整docker組,細節百度一下便可。

經常使用的命令也比較少:

# 查看當前部署的服務
docker ps 
# 運行一個容器服務
docker run
# 刪除一個服務
docker kill xxx

2.3 Nvidia-docker

參考資料:

由於docker是虛擬在操做系統之上的,屏蔽了不少底層的信息。若是想使用顯卡這種硬件,一種思路是docker直接把操做系統上的驅動程序和算法庫映射到容器內,可是這樣就喪失了可移植性。

另外一種方法就是在docker啓動的時候掛載一個相似驅動的插件——這就是nvidia-docker的做用。

總的來講,若是想要在docker中使用tensorflow-gpu,須要首先安裝docker-ce(社區版,其餘版本nvidia-docker不必定支持),而後安裝nvidia-container-runtime,最後安裝nvidia-docker2。

當使用的時候,須要直接指定nvidia-docker2運行, 如:

sudo nvidia-docker run -p 8500:8500 --mount type=bind,source=/home/ubuntu/data/east_serving/east_serving,target=/models/east -e MODEL_NAME=east -t tensorflow/serving:1.12.0-gpu &

3 部署實戰

下面就進入部署的實戰篇了:

3.1 Docker\Nvidia-Docker、Tensorflow部署

主要參考:

首先安裝docker-ce:

curl -fsSL https://download.docker.com/linux/ubuntu/gpg | sudo apt-key add -
sudo apt-key fingerprint 0EBFCD88
sudo add-apt-repository "deb [arch=amd64] https://download.docker.com/linux/ubuntu $(lsb_release -cs) stable"
sudo apt-get update
sudo apt-get install docker-ce
sudo service docker restart

若是以前安裝了nvidia-docker1須要刪除掉:

docker volume ls -q -f driver=nvidia-docker | xargs -r -I{} -n1 docker ps -q -a -f volume={} | xargs -r docker rm -f
sudo apt-get purge -y nvidia-docker

修改docker的鏡像地址vi /etc/docker/daemon.json

{
    "registry-mirrors":["https://registry.docker-cn.com","http://hub-mirror.c.163.com"]
}

而後重啓docker配置服務systemctl restart docker.service

更新nvidia-docker地址:

curl -s -L https://nvidia.github.io/nvidia-docker/gpgkey | sudo apt-key add -
curl -s -L https://nvidia.github.io/nvidia-docker/ubuntu16.04/amd64/nvidia-docker.list | sudo tee /etc/apt/sources.list.d/nvidia-docker.list
sudo apt-get update

執行安裝命令:

sudo apt-get install -y nvidia-docker2
sudo pkill -SIGHUP dockerd

測試:

ubuntu@ubuntu:~$ sudo nvidia-docker run --runtime=nvidia --rm nvidia/cuda nvidia-smi
Thu Jan  3 09:52:06 2019       
+-----------------------------------------------------------------------------+
| NVIDIA-SMI 384.130                Driver Version: 384.130                   |
|-------------------------------+----------------------+----------------------+
| GPU  Name        Persistence-M| Bus-Id        Disp.A | Volatile Uncorr. ECC |
| Fan  Temp  Perf  Pwr:Usage/Cap|         Memory-Usage | GPU-Util  Compute M. |
|===============================+======================+======================|
|   0  Tesla P40           Off  | 00000000:3B:00.0 Off |                    0 |
| N/A   35C    P0    49W / 250W |  22152MiB / 22912MiB |      0%      Default |
+-------------------------------+----------------------+----------------------+
                                                                               
+-----------------------------------------------------------------------------+
| Processes:                                                       GPU Memory |
|  GPU       PID   Type   Process name                             Usage      |
|=============================================================================|
+-----------------------------------------------------------------------------+

能夠看到,已經能再docker內部看到顯卡的使用信息了。

在docker容器外,執行nvidia-smi能夠看到有個tensorflow serving的服務

ubuntu@ubuntu:~$ nvidia-smi
Thu Jan  3 17:52:43 2019       
+-----------------------------------------------------------------------------+
| NVIDIA-SMI 384.130                Driver Version: 384.130                   |
|-------------------------------+----------------------+----------------------+
| GPU  Name        Persistence-M| Bus-Id        Disp.A | Volatile Uncorr. ECC |
| Fan  Temp  Perf  Pwr:Usage/Cap|         Memory-Usage | GPU-Util  Compute M. |
|===============================+======================+======================|
|   0  Tesla P40           Off  | 00000000:3B:00.0 Off |                    0 |
| N/A   35C    P0    49W / 250W |  22152MiB / 22912MiB |      0%      Default |
+-------------------------------+----------------------+----------------------+
                                                                               
+-----------------------------------------------------------------------------+
| Processes:                                                       GPU Memory |
|  GPU       PID   Type   Process name                             Usage      |
|=============================================================================|
|    0    108329      C   python                                      4963MiB |
|    0    133840      C   tensorflow_model_server                    17179MiB |
+-----------------------------------------------------------------------------+

注意正常須要配置docker佔用的顯存比例!

4 總結

搞深度學習仍是須要全棧基礎的,涉及到各類linux底層動態庫、硬件、容器等等相關的知識,雖然踩了很多坑,可是不少概念性的東西都獲得了實踐,這纔是工做最大的意義。

相關文章
相關標籤/搜索