1. demo
地址:http://www.huchengchun.com:8127/porn_classification
接口說明:
1. http://www.huchengchun.com:8127/porn_classification 提供了一個簡易的網頁工具,用戶可以上傳若干張圖片,服務端會傳回每一張圖片是否是色情圖片的判定,結果的形式是json格式。截圖如下:
返回結果的說明:
- 返回結果整體是一個json,key是加上時間戳后綴的上傳圖片名稱,value是上傳圖片的色情的判定,其中: hentai 表示變態圖片;drawings 表示普通的繪畫圖片;porn表示色情圖片(可能會漏點),sexy 表示性感圖片,neutral 表示中性圖片。
- status 字段表示本次判定的結果是否正常。status = 'normal' 表示正常;status = 'error'表示異常。
2. 還支持了http get 對網頁圖片進行判定,請求的格式為: http://www.huchengchun.com:8127/porn_classification?img_url=xxx
其中 xxx 是網絡圖片的地址,目前只支持以jpg 和png結尾的格式。比如如下的請求返回的結果
http://www.huchengchun.com:8127/porn_classification?img_url=https://pic2.zhimg.com/v2-2cfee04b86d10256be2d98458f45bb4e_1200x500.jpg
{
"status": "normal",
"v2-2cfee04b86d10256be2d98458f45bb4e_1200x500_1569511599.jpg": {
"hentai": "0.0064989934",
"drawings": "0.0012943572",
"porn": "0.1919955",
"neutral": "0.0314714",
"sexy": "0.76873976"
}
}
嗯,確實是性感美女,可以看到判定的結果還是比較准確的。
2. 原理
1. 色情圖片分類模型。
這一部分主要是參考 github nsfw 的 keras 的開源實驗。nsfw 是 Not Suitable for Work 的縮寫,是yahho 最先提出一個一個基於深度學習的色情圖片判定模型,地址: https://github.com/yahoo/open_nsfw.原始的模型是使用 caffe搭建的,但是顯然,現在都已經是9102年了,早已經是tf/keras/pytorch 橫行的時代了,caffe幾乎已經過時了,所以我也懶得去再搭建一個caffe的深度學習環境了。在萬能的github上搜索 nsfw 就可以發現很多其他框架移植的nsfw,這里我選擇了一個相對比較簡單的基於keras 的nsfw的實現,地址是:https://github.com/GantMan/nsfw_model.
作者提供了基於幾十G嘿嘿嘿圖片預訓練的keras h5模型,開箱即用。當然,原始語料那是不可能提供的。如何加載模型,作者已經替你寫好了腳本。幾行代碼就可以實現。
2. web 后端。
- 內網穿透
我自己有一個花了100多軟妹幣買的垃圾騰訊雲服務器。還花了幾十塊錢買了倆域名:www.huchengchun.com ,www.huchengchun.top. 域名是在花生殼買的。這個服務器的配置是4G內存+40G存儲+1M帶寬,搭建換一個個人網站,寫寫博客倒是沒啥問題,但是用作跑深度學習模型顯然是痴心妄想。不過還好,我手里還有一個個人的GPU主機,RTX2080TI, i7 cpu,16G 內存 + 256G SSD,11G 顯存。 顯然如果用它來跑深度學習的服務是再合適不過了。
但,可惜,我這個服務器是連的家里的內網wifi,沒有公網ip,咋通過域名訪問呢?
當然是有辦法的,我們可以使用內網穿透嘛。即我們需要一個有公網ip的機器做反向代理,中間做一個橋梁,對用戶的http請求做轉發,轉發到內網服務器,然后再將內網服務器的響應轉發給用戶。
關於內網穿透這里簡單介紹兩種方法:
1.花生殼客戶端提供的內網穿透功能
2. 開源的frp工具。
具體說明可以參考我自己的這個簡單總結: http://note.youdao.com/noteshare?id=22a62ce23805c456419a865e78ea4ff4
- web 服務
這里的web 服務是使用的flask 框架搭建的。之所以使用flask 搭建主要基於如下的幾個理由:
1. flask 是一個基於python的輕量級web 框架,支持眾多插件,可以快速搭建一個web服務。
2. 因為我們的絕大多數深度學習模型基本前端語言都是python,所以web服務基於python自然可以無縫銜接 深度學習模型了。
關於 flask 的學習,這里我不想展開了,想學習的,可以去官網學習:flask
3. 前端環境
- 因為我本身接觸后端比較多,所以對於前端搭建不是很熟悉。其實我這個demo的需求很簡單:
1. 提供一個界面,用戶可以上傳圖片到服務器
2. 服務器接收到圖片,使用nsfw模型處理,返回response
3. 前端接收server的response,並解析展示出來。
上傳圖片的 html + js + css 代碼我參考了網上別人的demo,見: https://github.com/fozero/frontcode/blob/master/src/02/index.html
其中用到了一點點 jquery + ajax 功能,其他的一些細節還有 flask + ajax 的跨域請求,json 的 pretty 展示等,見參考文獻。
3. 總結 & 其他
通過這個小項目,你可以初步學習:
- 如何使用frp快速進行內網穿透
- flask快速搭建一個web server
- jquery + ajax 快速搭建一個用戶上傳多圖到服務器
- 基於 keras + nsfw 的 色情圖片識別模型(這個模型其實背后基於InceptionV3)
最后類似地,之前我發布過一篇博文:如何訓練一個詩歌生成器,我基於和上面類似的思路,現在也提供了一個http接口,大家可以調用這個接口隨便生成一些詩歌玩玩,地址是:http://www.huchengchun.com:8126/poem_generation
接口說明如下:
服務名稱
|
服務類型
|
端口號
|
啟動腳本位置
|
綁定公網服務器ip
|
綁定公網服務器端口
|
說明
|
poem_prediction
|
python
keras
訓練了一個lstm模型,用於寫詩
|
8126
|
/home/work/server/poem_prediction_8126.sh
|
45.40.207.39
|
8126
|
請求方式:get/post
請求參數:
pr:可以傳入任意非控值,表示隨機預測一個五言絕句
ps:傳入一個長度為6的字符串,返回一個長度為24的句子
pf:傳入一個單個字符,返回一個以該字開頭的五言絕句
ph:傳入四個字,返回以這四個字開頭的五言藏頭詩
|
請求實例
|
返回實例
|
curl -G --data-urlencode "type=text" --data-urlencode "pf=胡" http://www.huchengchun.com:8126/poem_generation
|
{"extra": "", "status": "normal", "response": "胡室金同生,知人古新山。氣虛中一事,主前千水同。"}
|
還有一個 bert_as_service開源項目,基於flask + bert 搭建一個 web server,可以任意文本編碼為固定長度的向量,原文提供了python調用、http調用等多種方式,挺有意思的。我也把這個服務部署在我自己的服務器上了,並且提供了http post 接口,地址:
http://www.huchengchun.com:8125 ,調用實例以及返回實例:
curl -X POST http://www.huchengchun.com:8125/encode \
-H 'content-type: application/json' \
-d '{"id": 123,"texts": ["我愛中國"], "is_tokenized": false}'
|
{"id":123,"result":[[0.043742578476667404,...-0.06586530804634094]],"status":200}
|
最后,以后也許會探索更多好玩的機器學習/深度學習項目,提供接口給大家。
Have Fun!
參考文獻:
1.基於keras 的nsfw: https://github.com/GantMan/nsfw_model.
2.用戶上傳多圖片前端demo:https://github.com/fozero/frontcode/blob/master/src/02/index.html
3.flask 引用templates:https://stackoverflow.com/questions/31002890/how-to-reference-a-html-template-from-a-different-directory-in-python-flask/31003097
4.flask 解決 ajax 跨域請求錯誤的問題: https://stackoverflow.com/questions/26980713/solve-cross-origin-resource-sharing-with-flask