HttpRunner2.X 版本和 3.X 版本的區別到底有哪些?(吐血總結!)


前言

HttpRunner 的版本截止到目前已經更新到3.1.5了,那么很多初學者都有這樣的疑問:
HttpRunner2.X 版本和 3.X 版本的區別到底有哪些?
到底要不要學2.X 版本,還是直接入手3.X 版本呢?

設計理念上的差異

HttpRunner 每一次大版本的更新,都會有設計理念上的大的改變,可以從官方文檔上了解到.

HttpRunner 2.X

HttpRunner 是一款面向 HTTP(S) 協議的通用測試框架,只需編寫維護一份 YAML/JSON 腳本,即可實現自動化測試、性能測試、線上監控、持續集成等多種測試需求。
設計理念

  • 充分復用優秀的開源項目,不追求重復造輪子,而是將強大的輪子組裝成戰車
  • 遵循 約定大於配置 的准則,在框架功能中融入自動化測試最佳工程實踐
  • 追求投入產出比,一份投入即可實現多種測試需求

從 2.0 版本開始,HttpRunner 采用了分層機制,同時,強調如下幾點核心概念:

  • 測試用例(testcase)應該是完整且獨立的,每條測試用例應該是都可以獨立運行的
  • 測試用例是測試步驟(teststep)的 有序 集合,每一個測試步驟對應一個 API 的請求描述
  • 測試用例集(testsuite)是測試用例的 無序 集合,集合中的測試用例應該都是相互獨立,不存在先后依賴關系的;如果確實存在先后依賴關系,那就需要在測試用例中完成依賴的處理

2.X 版本的亮點功能在於用例的分層機制,重復的接口請求可以寫到單獨API層,用例去調用API,層級結構非常清晰,每個層級做好自己的事情。

HttpRunner 3.X

HttpRunner v3.x 支持3種用例格式:pytest、YAML和JSON。
設計理念

  • 約定優於配置
  • 投入產出比很重要
  • 擁抱開源,依賴requests ,pytest ,pydantic ,allure 和 locust

pytest、YAML和JSON格式的測試用例完全等價,包含的信息內容也完全相同。

  • 對於有python基礎的,建議以pytest格式而不是以前的YAML / JSON格式編寫和維護測試用例。
  • 對於新手來說,推薦使用 JSON 格式,雖然描述形式上稍顯累贅,但是不容易出錯(大多編輯器都具有 JSON 格式的檢測功能);
    同時,HttpRunner 也內置了 JSON 格式正確性檢測和樣式美化功能,詳情可查看《Validate & Prettify》 。
  • 對於熟悉 YAML 格式的人來說,編寫維護 YAML 格式的測試用例會更簡潔,但前提是要保證 YAML 格式沒有語法錯誤。

HttpRunner v3.x開始,HttpRunner 作者建議大家回到代碼上,鼓勵大家去寫python代碼了(可能認為代碼還是很重要),用pycharm等編輯器可以自動補齊語法,編寫效率更高。
對於有一些代碼基礎的同學來說,還是很高效的,畢竟還是有很多小伙伴不習慣與yaml格式,總是在語法上犯錯,導致編寫腳本效率很低。

對比差異

2.x 版本和3.x版本功能上對比差異

功能點 HttpRunner 2.X HttpRunner 3.X
python用例框架 unittest pytest(v5.4.3)
錄制.har har2case支持 har2case支持
用例文件格式 YAML/JSON YAML/JSON/Pytest
HTTP(S)請求庫 requests requests
用例分層 三層:API/TestCase/TestSuite 弱化了API層,去掉分層機制
參數化parameters 2.x版本在TestSuites層實現,TestCase不支持 3.x版本TestCase中實現
extract提取變量 支持content.x.x格式/re正則/jsonpath 只支持jmespath表達式
返回html格式 re正則提取 不支持re正則提取
文件上傳 upload關鍵字支持 upload關鍵字支持
validate校驗 comparator 校驗一樣 comparator 校驗一樣
comparator 支持debugytalk.py 自定義 不支持自定義
hook機制 支持 支持
debugtalk.py輔助函數 支持 支持
測試報告 自帶html報告 不自帶報告了
extent report 支持 不支持
Allure 不支持 支持
Locust 支持 支持
CLI命令行運行 支持 支持
學習難度 低難度 偏中高級
穩定性 偏中
作者版本維護 不維護 繼續維護

底層框架區別

HttpRunner 2.X 是基於 Python 的 Unittest 框架運行用例,
HttpRunner 3.X 是基於 Python 的 Pytest 框架運行用例,支持了 Pytest 框架,運行用例性能會得到很大的提升。
既然支持了 Pytest,意味着 Pytest 的一些插件都可以用了,比如 Allure 插件,也可以在 conftest 中寫一些鈎子函數,自己開發插件了,擴展性得到很大的提升!

用例格式區別

HttpRunner 2.X 支持yaml 和 json格式,json和yaml是可以互相轉換,以yaml為例

# 作者-上海悠悠 QQ交流群:717225969
# blog地址 https://www.cnblogs.com/yoyoketang/

config:
    name: logincase
    variables: {}
teststeps:
-
    name: login case1
    request:
        url: http://127.0.0.1:8000/api/v1/login/
        method: POST
        headers:
            Content-Type: application/json
            User-Agent: python-requests/2.18.4
        json:
            username: test
            password: 123456
    validate:
        - eq: [status_code, 200]
        - eq: [headers.Content-Type, application/json]
        - eq: [content.msg, login success!]
        - eq: [content.code, 0]

HttpRunner 3.x 除了支持yaml和json格式,還可以支持pytest格式用例。
yaml格式跟2.x版本是一樣的,可以直接運行上面的yaml格式,會生成一個pytest格式用例

# NOTE: Generated By HttpRunner v3.1.5
# FROM: testcase\login.yml
# 作者-上海悠悠 QQ交流群:717225969
# blog地址 https://www.cnblogs.com/yoyoketang/

from httprunner import HttpRunner, Config, Step, RunRequest, RunTestCase


class TestCaseLogin(HttpRunner):

    config = Config("logincase")

    teststeps = [
        Step(
            RunRequest("login case1")
            .post("http://127.0.0.1:8000/api/v1/login")
            .with_json({"username": "test", "password": "123456"})
            .validate()
            .assert_equal("status_code", 200)
            .assert_equal("body.msg", "login success!")
            .assert_equal("body.code", 0)
            .assert_equal("body.username", "test")
            .assert_length_equal("body.token", 40)
        ),
    ]


if __name__ == "__main__":
    TestCaseLogin().test_start()

extract 提取與validate校驗

HttpRunner 3.x 只支持 jmespath 提取接口返回的json數據格式,jmespath是類似於jsonpath的提取表達式
jmespath 提取示例,訪問/api/test/demo接口,接口返回如下

# 作者-上海悠悠 QQ交流群:717225969
# blog地址 https://www.cnblogs.com/yoyoketang/

{
    "code":0,
    "msg":"成功success!",
    "data":[
        {
            "age":20,
            "create_time":"2019-09-15",
            "id":1,
            "mail":"283340479@qq.com",
            "name":"yoyo",
            "sex":"M"
        },
        {
            "age":21,
            "create_time":"2019-09-16",
            "id":2,
            "mail":"123445@qq.com",
            "name":"yoyo111",
            "sex":"M"
        }
    ]
}

需求:

  • 1.提取code值,校驗結果為:0
  • 2.msg值,校驗結果:成功success!
  • 3.提取data數據,校驗結果長度是:2
  • 4.提取data數據中第一條數據,校驗name的值:yoyo
  • 5.提取data數據中name的值為yoyo的郵箱,並校驗結果是:283340479@qq.com
  • 6.提取data數據組中,年齡大於20的結果,並校驗結果的數量是:1

httprunner3.x 對應的 py 代碼

# 作者-上海悠悠 QQ交流群:717225969
# blog地址 https://www.cnblogs.com/yoyoketang/

from httprunner import HttpRunner, Config, Step, RunRequest, RunTestCase


class TestCaseTestDemo(HttpRunner):

    config = Config("test demo").base_url("http://127.0.0.1:8000")

    teststeps = [
        Step(
            RunRequest("step login")
            .get("/api/test/demo")
            .validate()
            .assert_equal("status_code", 200)
            .assert_equal("body.code", 0)
            .assert_equal("body.msg", "成功success!")
            .assert_equal("body.length(data)", 2)
            .assert_equal("body.data[0].name", "yoyo")
            .assert_equal("body.data[?name=='yoyo'].mail", ["283340479@qq.com"])
            .assert_equal("body.data[?name=='yoyo'].mail|[0]", "283340479@qq.com")
            .assert_equal("body.length(data[?age>`20`])", 1)
        ),
    ]


if __name__ == "__main__":
    TestCaseTestDemo().test_start()

不得不說jmespath在提取json方面是非常強大的,httprunner2.x是可以支持jsonpath表達式的

# 作者-上海悠悠 QQ交流群:717225969
# blog地址 https://www.cnblogs.com/yoyoketang/

    extract:
        code: $.code
    validate:
        - eq: [status_code, 200]
        - eq: [headers.Content-Type, application/json]
        - eq: [$.code, 0]
        - eq: ["$code", 0]

但是2.5.7版本有個小bug,一直沒修復,詳情參考https://www.cnblogs.com/yoyoketang/p/14884606.html

返回html提取

httprunner3.x是不支持html解析的,可以看到源碼里面此功能還沒開發完善.

class StepRequestExtraction(object):
    def __init__(self, step_context: TStep):
        self.__step_context = step_context

    def with_jmespath(self, jmes_path: Text, var_name: Text) -> "StepRequestExtraction":
        self.__step_context.extract[var_name] = jmes_path
        return self

    # def with_regex(self):
    #     # TODO: extract response html with regex
    #     pass
    #
    # def with_jsonpath(self):
    #     # TODO: extract response json with jsonpath
    #     pass

有些接口返回的並不是json格式,如果返回html格式, 那就沒法提取了,httprunner2.x 可以支持正則表達式提取,這點還是很好的

config:
    name: logincase
    variables: {}
teststeps:
-
    name: test demo case1
    request:
        url: https://www.cnblogs.com/yoyoketang/
        method: GET
        headers:
            User-Agent: Fiddler
            Content-Type: application/json
        verify: false
    extract:
        title: '<title>(.+?)</title>'
    validate:
        - eq: [status_code, 200]
        - eq: ['<title>(.+?)</title>', 上海-悠悠 - 博客園]

comparator 校驗方式

httprunner2.x 和 httprunner3.x 支持的 comparator 校驗方式是一樣的

comparator 縮寫 功能
equal "eq", "equals", "equal" 相等
less_than "lt", "less_than" 小於
less_or_equals "le", "less_or_equals" 小於或等於
greater_than "gt", "greater_than" 大於
greater_or_equals "ge", "greater_or_equals" 大於或等於
not_equal "ne", "not_equal" 不等於
string_equals "str_eq", "string_equals" 轉字符串相等
length_equal "len_eq", "length_equal" 長度相等
length_greater_than "len_gt","length_greater_than" 長度大於
length_greater_or_equals "len_ge","length_greater_or_equals" 長度大於或等於
length_less_than "len_lt", "length_less_than" 長度小於
length_less_or_equals ""len_le", "length_less_or_equals" 長度小於或等於
contains check_value 包含 expect_value
contained_by expect_value 包含check_value
type_match type類型匹配
regex_match 正則匹配re.match(expect_value, check_value)
startswith 字符串以xx開頭
endswith 字符串以xx結尾

yaml 中可以寫2種格式校驗

- {"comparator_name": [check_value, expect_value]}
- {"check": check_value, "comparator": comparator_name, "expect": expect_value}

httprunner3.x 並不支持自己定義的校驗方式,httprunner2.x可以支持自定義校驗,如

# debugtalk.py
# 作者-上海悠悠 QQ交流群:717225969
# blog地址 https://www.cnblogs.com/yoyoketang/


# 獲取data數據,斷言每個數據的age字段大於等於expect_age
def all_age_great(data, expect_age):
    """ all age great then expect_age
    """
    for info in data:
        assert info.get('age') >= expect_age

於是 yaml 用例可以這樣寫

# 作者-上海悠悠 QQ交流群:717225969
# blog地址 https://www.cnblogs.com/yoyoketang/

config:
    name: test_demo
    base_url: http://127.0.0.1:8000
    variables: {}

teststeps:
-
    name: test_demo case1
    request:
        url: /api/test/demo
        method: GET
        headers:
            Content-Type: application/json
            User-Agent: python-requests/2.18.4
    validate:
    -    check: content.data
         comparator: all_age_great
         expect: 18
    -    all_age_great: [content.data, 18]

測試報告差異

httprunner3.x 運行用例是pytest框架,也就是意味着可以支持強大的Allure報告了

httprunner 2.x 運行用例是unittest框架,會自帶一個簡單的測試報告

也可以支持自己擴展一個extent report報告模板

版本穩定性與學習成本

穩定性:
httprunner2.x 版本更新到2.5.7了,雖然有一些小BUG,整體上還是很穩定的,目前也很多公司在用了,已經有看得到的成果,穩定性較強!
缺點是作者不繼續維護2.x版本了
httprunner3.x 版本更新到3.1.5了,最近的一次更新是在2021年6月27,距離上一次更新差不多1年了,版本改動也很小,更新的頻率放慢了很多。

學習成本:
httprunner2.x 支持yaml/json格式的用例,意味着我們只需學一個yaml(或json)文件就能寫接口自動化了,初學者可以很快的掌握。
httprunner3.x 支持yaml/json/pytest格式的用例,多了一個pytest格式的用例,那么意味着學習成本會增多了,初學者掌握的難度較大,適合之前就已經有學過pytest的同學。

還有其它細節上的區別,就不一一總結了,如果有同學能補充的可以留言!

網易雲課程

httprunner 2.x實戰教程網易雲課程地址


httprunner 2.x實戰教程點我 ->立即報名

httprunner 3.x實戰教程網易雲課程地址


httprunner 3.x實戰教程點我 ->立即報名


免責聲明!

本站轉載的文章為個人學習借鑒使用,本站對版權不負任何法律責任。如果侵犯了您的隱私權益,請聯系本站郵箱yoyou2525@163.com刪除。



 
粵ICP備18138465號   © 2018-2025 CODEPRJ.COM