初めに:
Karate-GatlingによるE2E/負荷テストをお手軽に実行する。
KarateはE2Eテストフレームワーク、Gatlingは負荷テストフレームワークであり、
両者を組み合わせたものがKarate-Gatlingである。
本来KarateはMaven/Gradleのサポートとなっているが、
今回は、Karate-Gatlingをsbtでも使用可能にする。
【Karateについて】
【Gatlingについて】
通常のKarate(maven)と比較した場合のメリット
- Mavenでは全部設定しなければならない依存関係が自動計算されるため、シンプルになる
- Gatlingのためにscala用依存関係を別途追加していたが、それらは不要になる
単体のGatlingと比較した場合のメリット
- Karateによるfeatureファイルが使えることにより、Scalaに詳しくなくてもGatlingが使える
- アサーションの条件が非常にわかりやすい構造になる
- 単なるE2Eテストならばfeatureファイルだけでテストすることもできる(IDEA上で実行可能)
テスト作成
テスト作成:ビルド定義
プロジェクト定義は、InteliJ IDEAのsbtテンプレートを使用する。
sbtで動作を可能としたいため、gatling-mavenに変えてgatling-sbtプラグインを使用する
addSbtPlugin("io.gatling" % "gatling-sbt" % "3.2.1")
name := "karate-gatling-sbt"
version := "0.1"
scalaVersion := "2.12.13"
val gatlingVersion = "3.0.2"
val karateVersion = "0.9.6"
//sbt-gatlingがmaven centralに存在しないので、bintrayRepoを追加する
resolvers += Resolver.bintrayRepo("gatling", "sbt-plugins")
enablePlugins(GatlingPlugin)
scalacOptions := Seq(
"-encoding", "UTF-8", "-target:jvm-1.8", "-deprecation",
"-feature", "-unchecked", "-language:implicitConversions", "-language:postfixOps")
libraryDependencies ++= Seq(
// 無くても依存関係が計算されて動作する
// "io.gatling.highcharts" % "gatling-charts-highcharts" % gatlingVersion % "test",
"io.gatling" % "gatling-test-framework" % gatlingVersion % "test",
"com.intuit.karate" % "karate-gatling" % karateVersion % "test",
"com.intuit.karate" % "karate-apache" % karateVersion % "test"
)
テスト作成:テストアサーション定義
function() {
var config = {
urlBase: 'http://localhost:9080/',
};
karate.configure('connectTimeout', 5000);
karate.configure('readTimeout', 5000);
return config;
}
PC性能の問題で負荷がかかり切らないので、今回はいくつかのパターンを停止しておく。
Feature: Karate sample
Background:
* url urlBase
Scenario Outline: get
Given path 'projects'
And header <name> = <values>
And form field clientId = <clientId>
When method <method>
* print <exps>
Then status <status>
And match $ == '#[1]'
And match <expression>
Examples:
| clientId | name | values | method | exps | status | expression |
| '1' | Accept | 'application/json' | get | response | 200 | $[0] contains {"projectName": "プロジェクト001"} |
| '2' | Accept | 'application/json' | get | response | 200 | $[0] contains {"projectName": "プロジェクト002"} |
#| '3' | Accept | 'application/json' | get | response | 200 | $[0] contains {"projectName": "プロジェクト003"} |
#| '4' | Accept | 'application/json' | get | response | 200 | $[0] contains {"projectName": "プロジェクト004"} |
#| '5' | Accept | 'application/json' | get | response | 200 | $[0] contains {"projectName": "プロジェクト005"} |
#| '6' | Accept | 'application/json' | get | response | 200 | $[0] contains {"projectName": "プロジェクト006"} |
#| '7' | Accept | 'application/json' | get | response | 200 | $[0] contains {"projectName": "プロジェクト007"} |
#| '8' | Accept | 'application/json' | get | response | 200 | $[0] contains {"projectName": "プロジェクト008"} |
#| '9' | Accept | 'application/json' | get | response | 200 | $[0] contains {"projectName": "プロジェクト009"} |
#| '10' | Accept | 'application/json' | get | response | 200 | $[0] contains {"projectName": "プロジェクト010"} |
テスト作成:負荷テスト設定定義
scalaファイルで記載すべきなのは負荷に関する定義のみ。
TPSはfeatureのパターン×レートの数となるので注意
今回は2シナリオ×5=10TPSを目標とする。
import com.intuit.karate.gatling.KarateProtocol
import com.intuit.karate.gatling.PreDef._
import com.intuit.karate.http.HttpRequestBuilder
import io.gatling.core.Predef._
import io.gatling.core.structure.ScenarioBuilder
import scala.concurrent.duration._
class KarateSimulation extends Simulation {
// 開始時のレート
val startRate: Double = 0
// 最大負荷のレート(TPSはfeatureのパターン×ユーザの数となるので注意)
val maxRate: Double = 5
// 負荷を段階的に高める時間
val rampUpTime: FiniteDuration = 30.seconds
// 最大負荷のテスト時間(TPSはfeatureのパターン×ユーザの数となるので注意)
val stableTime: FiniteDuration = 90.seconds
val protocol: KarateProtocol = karateProtocol()
protocol.nameResolver = (req: HttpRequestBuilder, _) => req.getUrlAndPath
val search: ScenarioBuilder =
scenario("get").exec(karateFeature("classpath:nablarch.feature"))
setUp(
search
.inject(
rampUsersPerSec(startRate) to maxRate during rampUpTime,
constantUsersPerSec(maxRate) during stableTime
)
.protocols(protocol)
)
}
テスト実行:事前準備
テストさせる対象は、下記とする。
https://github.com/nablarch/nablarch-example-rest
先に、mvn waitt:run-headlessを実行しておくこと。
テスト実行
コマンドラインで下記のコマンドを実行する。
IDEA(sbt shell)で実行する場合、sbt は除いて入力する
sbt test:compile
sbt gatling:test
テスト結果
およそ30+90=120秒間、10TPSの負荷がかかった。エラーはなかった。
※request count.*OK=.KO=. で結果検索できる
================================================================================
---- Global Information --------------------------------------------------------
> request count 1050 (OK=1050 KO=0 )
> min response time 18 (OK=18 KO=- )
> max response time 2433 (OK=2433 KO=- )
> mean response time 151 (OK=151 KO=- )
> std deviation 297 (OK=297 KO=- )
> response time 50th percentile 40 (OK=40 KO=- )
> response time 75th percentile 77 (OK=77 KO=- )
> response time 95th percentile 703 (OK=703 KO=- )
> response time 99th percentile 1649 (OK=1649 KO=- )
> mean requests/sec 8.824 (OK=8.824 KO=- )
---- Response Time Distribution ------------------------------------------------
> t < 800 ms 1011 ( 96%)
> 800 ms < t < 1200 ms 20 ( 2%)
> t > 1200 ms 19 ( 2%)
> failed 0 ( 0%)
================================================================================
Reports generated in 1s.
Please open the following file: C:\Users\aruki\Desktop\dev\karate-gatling-sbt\target\gatling\karatesimulation-20210228145214326\index.html
[info] Simulation KarateSimulation successful.
[info] Simulation(s) execution ended.
[success] Total time: 126 s (02:06), completed 2021/02/28 23:54:17
[IJ]