2017-01-18 108 views
8

假設我想測試下瓶API(從http://flask-restful-cn.readthedocs.io/en/0.3.5/quickstart.html#a-minimal-api):如何單元測試瓶的RESTful API

import flask 
import flask_restful 

app = flask.Flask(__name__) 
api = flask_restful.Api(app) 

class HelloWorld(flask_restful.Resource): 
    def get(self): 
     return {'hello': 'world'} 

api.add_resource(HelloWorld, '/') 

if __name__ == "__main__": 
    app.run(debug=True) 

救以此爲flaskapi.py並運行它,在我運行在同一目錄腳本test_flaskapi.py

import unittest 
import flaskapi 
import requests 

class TestFlaskApiUsingRequests(unittest.TestCase): 
    def test_hello_world(self): 
     response = requests.get('http://localhost:5000') 
     self.assertEqual(response.json(), {'hello': 'world'}) 


class TestFlaskApi(unittest.TestCase): 
    def setUp(self): 
     self.app = flaskapi.app.test_client() 

    def test_hello_world(self): 
     response = self.app.get('/') 

if __name__ == "__main__": 
    unittest.main() 

兩個測試通過,但對於第二個測試類(在TestFlaskApi定義)我還沒有想出如何斷言JSON響應預期(即{'hello': 'world'})。這是因爲它是flask.wrappers.Response(它可能基本上是一個Werkzeug響應對象(參見http://werkzeug.pocoo.org/docs/0.11/wrappers/))的實例,並且我還找不到requests'Response'對象的等效方法json()

如何在第二個response的JSON內容上做出斷言?

回答

8

我發現我可以通過施加json.loads()get_data()方法的輸出得到JSON數據:

import unittest 
import flaskapi 
import requests 
import json 
import sys 

class TestFlaskApiUsingRequests(unittest.TestCase): 
    def test_hello_world(self): 
     response = requests.get('http://localhost:5000') 
     self.assertEqual(response.json(), {'hello': 'world'}) 


class TestFlaskApi(unittest.TestCase): 
    def setUp(self): 
     self.app = flaskapi.app.test_client() 

    def test_hello_world(self): 
     response = self.app.get('/') 
     self.assertEqual(json.loads(response.get_data().decode(sys.getdefaultencoding())), {'hello': 'world'}) 


if __name__ == "__main__": 
    unittest.main() 

兩個測試都通過如期望:

.. 
---------------------------------------------------------------------- 
Ran 2 tests in 0.019s 

OK 
[Finished in 0.3s] 
+0

「狀態:Flask API目前未處於活動開發狀態。」來自https://github.com/flask-api/flask-api – TheGrimmScientist

2

隨着Python3,我得到了錯誤TypeError: the JSON object must be str, not bytes。需要解碼:

# in TestFlaskApi.test_hello_world 
self.assertEqual(json.loads(response.get_data().decode()), {'hello': 'world'}) 

This question給出瞭解釋。

8

瓶提供了test_client您可以在您的測試中使用:

from source.api import app 
from unittest import TestCase 

class TestIntegrations(TestCase): 
    def setUp(self): 
     self.app = app.test_client() 

    def test_thing(self): 
     response = self.app.get('/') 
     assert <make your assertion here> 

Flask Testing Docs

+0

(發佈爲幫助其他人在這裏着陸的答案,看到一個更清潔的方式來寫這些測試) – TheGrimmScientist

+0

乾淨和consice。 – Prakhar

7

你正在做什麼沒有單元測試。在任何情況下,當你使用請求庫或瓶子客戶端時,當你對端點進行真正的http調用並測試交互時,你正在做integration testing

問題標題或方法不準確。