├── .editorconfig
├── .gitignore
├── .release-it.json
├── .travis.yml
├── LICENSE
├── README.adoc
├── bootstrap.sh
├── build.gradle
├── gradle.properties
├── gradle
└── wrapper
│ ├── gradle-wrapper.jar
│ └── gradle-wrapper.properties
├── gradlew
├── gradlew.bat
├── nb-actions.xml
├── sample-project
├── build.gradle
├── gradle
│ └── wrapper
│ │ ├── gradle-wrapper.jar
│ │ └── gradle-wrapper.properties
├── gradlew
├── gradlew.bat
└── src
│ └── gatling
│ ├── resources
│ └── search.csv
│ └── simulations
│ └── SampleSimulation.scala
├── src
├── main
│ ├── groovy
│ │ └── com
│ │ │ └── github
│ │ │ └── lkishalmi
│ │ │ └── gradle
│ │ │ └── gatling
│ │ │ ├── GatlingPlugin.groovy
│ │ │ ├── GatlingPluginExtension.groovy
│ │ │ ├── GatlingRunTask.groovy
│ │ │ ├── JvmConfigurable.groovy
│ │ │ └── LogbackConfigTaskAction.groovy
│ └── resources
│ │ └── META-INF
│ │ └── gradle-plugins
│ │ └── com.github.lkishalmi.gatling.properties
└── test
│ ├── groovy
│ ├── functional
│ │ ├── GradleCompatibilitySpec.groovy
│ │ ├── LogbackConfigTaskActionTest.groovy
│ │ ├── WhenCompileSimulationSpec.groovy
│ │ ├── WhenRunFailingSimulationSpec.groovy
│ │ ├── WhenRunSimulationSpec.groovy
│ │ └── WhenRunSimulationSysPropsJvmArgsSpec.groovy
│ ├── helper
│ │ ├── GatlingDebug.groovy
│ │ ├── GatlingFuncSpec.groovy
│ │ ├── GatlingSpec.groovy
│ │ └── GatlingUnitSpec.groovy
│ └── unit
│ │ ├── GatlingPluginTest.groovy
│ │ └── GatlingRunTaskTest.groovy
│ └── resources
│ ├── gatling-debug
│ └── src
│ │ └── gatling
│ │ ├── resources
│ │ └── .gitkeep
│ │ └── simulations
│ │ └── GatlingDebugSimulation.scala
│ └── gradle-layout
│ └── src
│ ├── gatling
│ ├── resources
│ │ └── search.csv
│ └── simulations
│ │ └── computerdatabase
│ │ ├── BasicSimulation.scala
│ │ └── advanced
│ │ └── AdvancedSimulationStep03.scala
│ ├── main
│ └── java
│ │ └── computerdatabase
│ │ └── MainUtils.java
│ └── test
│ └── java
│ └── computerdatabase
│ └── TestUtils.java
└── travis_build.sh
/.editorconfig:
--------------------------------------------------------------------------------
1 | root = true
2 |
3 | [*]
4 | end_of_line = lf
5 | insert_final_newline = true
6 | charset = utf-8
7 | trim_trailing_whitespace = true
8 | indent_style = space
9 |
10 | [*.groovy]
11 | indent_size = 4
12 | max_line_length=180
13 |
14 | [*.{yml,yaml,conf,json,avsc,gradle}]
15 | indent_size = 2
16 |
17 |
--------------------------------------------------------------------------------
/.gitignore:
--------------------------------------------------------------------------------
1 | /src/test/resources/gradle-layout/userHome
2 | /.idea
3 | /gradle-gatling-plugin.iml
4 | .gradle
5 | build/
6 |
7 | *.iml
8 | out
9 |
10 | # Ignore Gradle GUI config
11 | gradle-app.setting
12 |
13 | # Avoid ignoring Gradle wrapper jar file (.jar files are usually ignored)
14 | !gradle-wrapper.jar
15 |
16 | .DS_Store
--------------------------------------------------------------------------------
/.release-it.json:
--------------------------------------------------------------------------------
1 | {
2 | "git": {
3 | "requireCommits": true,
4 | "commit": false,
5 | "push": true,
6 | "tag": true
7 | },
8 |
9 | "npm": {
10 | "publish": false
11 | },
12 |
13 | "github": {
14 | "release": true
15 | },
16 |
17 | "plugins": {
18 | "@release-it/conventional-changelog": {
19 | "preset": "angular"
20 | }
21 | }
22 | }
23 |
--------------------------------------------------------------------------------
/.travis.yml:
--------------------------------------------------------------------------------
1 | language: java
2 |
3 | dist: xenial
4 |
5 | jdk:
6 | - openjdk8
7 |
8 | before_cache:
9 | - rm -f $HOME/.gradle/caches/modules-2/modules-2.lock
10 | - rm -fr $HOME/.gradle/caches/*/plugin-resolution/
11 | cache:
12 | directories:
13 | - $HOME/.gradle/caches/
14 | - $HOME/.gradle/wrapper/
15 |
16 | script: ./travis_build.sh
17 |
18 | deploy:
19 | - provider: script
20 | skip_cleanup: true
21 | script: ./gradlew publishPlugin -Pgradle.publish.key=${GRADLE_PUBLISH_KEY} -Pgradle.publish.secret=${GRADLE_PUBLISH_SECRET} -Dorg.gradle.project.version=${TRAVIS_TAG}
22 | on:
23 | tags: true
24 | repo: ${TRAVIS_REPO_SLUG}
25 |
26 |
--------------------------------------------------------------------------------
/LICENSE:
--------------------------------------------------------------------------------
1 | Apache License
2 | Version 2.0, January 2004
3 | http://www.apache.org/licenses/
4 |
5 | TERMS AND CONDITIONS FOR USE, REPRODUCTION, AND DISTRIBUTION
6 |
7 | 1. Definitions.
8 |
9 | "License" shall mean the terms and conditions for use, reproduction,
10 | and distribution as defined by Sections 1 through 9 of this document.
11 |
12 | "Licensor" shall mean the copyright owner or entity authorized by
13 | the copyright owner that is granting the License.
14 |
15 | "Legal Entity" shall mean the union of the acting entity and all
16 | other entities that control, are controlled by, or are under common
17 | control with that entity. For the purposes of this definition,
18 | "control" means (i) the power, direct or indirect, to cause the
19 | direction or management of such entity, whether by contract or
20 | otherwise, or (ii) ownership of fifty percent (50%) or more of the
21 | outstanding shares, or (iii) beneficial ownership of such entity.
22 |
23 | "You" (or "Your") shall mean an individual or Legal Entity
24 | exercising permissions granted by this License.
25 |
26 | "Source" form shall mean the preferred form for making modifications,
27 | including but not limited to software source code, documentation
28 | source, and configuration files.
29 |
30 | "Object" form shall mean any form resulting from mechanical
31 | transformation or translation of a Source form, including but
32 | not limited to compiled object code, generated documentation,
33 | and conversions to other media types.
34 |
35 | "Work" shall mean the work of authorship, whether in Source or
36 | Object form, made available under the License, as indicated by a
37 | copyright notice that is included in or attached to the work
38 | (an example is provided in the Appendix below).
39 |
40 | "Derivative Works" shall mean any work, whether in Source or Object
41 | form, that is based on (or derived from) the Work and for which the
42 | editorial revisions, annotations, elaborations, or other modifications
43 | represent, as a whole, an original work of authorship. For the purposes
44 | of this License, Derivative Works shall not include works that remain
45 | separable from, or merely link (or bind by name) to the interfaces of,
46 | the Work and Derivative Works thereof.
47 |
48 | "Contribution" shall mean any work of authorship, including
49 | the original version of the Work and any modifications or additions
50 | to that Work or Derivative Works thereof, that is intentionally
51 | submitted to Licensor for inclusion in the Work by the copyright owner
52 | or by an individual or Legal Entity authorized to submit on behalf of
53 | the copyright owner. For the purposes of this definition, "submitted"
54 | means any form of electronic, verbal, or written communication sent
55 | to the Licensor or its representatives, including but not limited to
56 | communication on electronic mailing lists, source code control systems,
57 | and issue tracking systems that are managed by, or on behalf of, the
58 | Licensor for the purpose of discussing and improving the Work, but
59 | excluding communication that is conspicuously marked or otherwise
60 | designated in writing by the copyright owner as "Not a Contribution."
61 |
62 | "Contributor" shall mean Licensor and any individual or Legal Entity
63 | on behalf of whom a Contribution has been received by Licensor and
64 | subsequently incorporated within the Work.
65 |
66 | 2. Grant of Copyright License. Subject to the terms and conditions of
67 | this License, each Contributor hereby grants to You a perpetual,
68 | worldwide, non-exclusive, no-charge, royalty-free, irrevocable
69 | copyright license to reproduce, prepare Derivative Works of,
70 | publicly display, publicly perform, sublicense, and distribute the
71 | Work and such Derivative Works in Source or Object form.
72 |
73 | 3. Grant of Patent License. Subject to the terms and conditions of
74 | this License, each Contributor hereby grants to You a perpetual,
75 | worldwide, non-exclusive, no-charge, royalty-free, irrevocable
76 | (except as stated in this section) patent license to make, have made,
77 | use, offer to sell, sell, import, and otherwise transfer the Work,
78 | where such license applies only to those patent claims licensable
79 | by such Contributor that are necessarily infringed by their
80 | Contribution(s) alone or by combination of their Contribution(s)
81 | with the Work to which such Contribution(s) was submitted. If You
82 | institute patent litigation against any entity (including a
83 | cross-claim or counterclaim in a lawsuit) alleging that the Work
84 | or a Contribution incorporated within the Work constitutes direct
85 | or contributory patent infringement, then any patent licenses
86 | granted to You under this License for that Work shall terminate
87 | as of the date such litigation is filed.
88 |
89 | 4. Redistribution. You may reproduce and distribute copies of the
90 | Work or Derivative Works thereof in any medium, with or without
91 | modifications, and in Source or Object form, provided that You
92 | meet the following conditions:
93 |
94 | (a) You must give any other recipients of the Work or
95 | Derivative Works a copy of this License; and
96 |
97 | (b) You must cause any modified files to carry prominent notices
98 | stating that You changed the files; and
99 |
100 | (c) You must retain, in the Source form of any Derivative Works
101 | that You distribute, all copyright, patent, trademark, and
102 | attribution notices from the Source form of the Work,
103 | excluding those notices that do not pertain to any part of
104 | the Derivative Works; and
105 |
106 | (d) If the Work includes a "NOTICE" text file as part of its
107 | distribution, then any Derivative Works that You distribute must
108 | include a readable copy of the attribution notices contained
109 | within such NOTICE file, excluding those notices that do not
110 | pertain to any part of the Derivative Works, in at least one
111 | of the following places: within a NOTICE text file distributed
112 | as part of the Derivative Works; within the Source form or
113 | documentation, if provided along with the Derivative Works; or,
114 | within a display generated by the Derivative Works, if and
115 | wherever such third-party notices normally appear. The contents
116 | of the NOTICE file are for informational purposes only and
117 | do not modify the License. You may add Your own attribution
118 | notices within Derivative Works that You distribute, alongside
119 | or as an addendum to the NOTICE text from the Work, provided
120 | that such additional attribution notices cannot be construed
121 | as modifying the License.
122 |
123 | You may add Your own copyright statement to Your modifications and
124 | may provide additional or different license terms and conditions
125 | for use, reproduction, or distribution of Your modifications, or
126 | for any such Derivative Works as a whole, provided Your use,
127 | reproduction, and distribution of the Work otherwise complies with
128 | the conditions stated in this License.
129 |
130 | 5. Submission of Contributions. Unless You explicitly state otherwise,
131 | any Contribution intentionally submitted for inclusion in the Work
132 | by You to the Licensor shall be under the terms and conditions of
133 | this License, without any additional terms or conditions.
134 | Notwithstanding the above, nothing herein shall supersede or modify
135 | the terms of any separate license agreement you may have executed
136 | with Licensor regarding such Contributions.
137 |
138 | 6. Trademarks. This License does not grant permission to use the trade
139 | names, trademarks, service marks, or product names of the Licensor,
140 | except as required for reasonable and customary use in describing the
141 | origin of the Work and reproducing the content of the NOTICE file.
142 |
143 | 7. Disclaimer of Warranty. Unless required by applicable law or
144 | agreed to in writing, Licensor provides the Work (and each
145 | Contributor provides its Contributions) on an "AS IS" BASIS,
146 | WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or
147 | implied, including, without limitation, any warranties or conditions
148 | of TITLE, NON-INFRINGEMENT, MERCHANTABILITY, or FITNESS FOR A
149 | PARTICULAR PURPOSE. You are solely responsible for determining the
150 | appropriateness of using or redistributing the Work and assume any
151 | risks associated with Your exercise of permissions under this License.
152 |
153 | 8. Limitation of Liability. In no event and under no legal theory,
154 | whether in tort (including negligence), contract, or otherwise,
155 | unless required by applicable law (such as deliberate and grossly
156 | negligent acts) or agreed to in writing, shall any Contributor be
157 | liable to You for damages, including any direct, indirect, special,
158 | incidental, or consequential damages of any character arising as a
159 | result of this License or out of the use or inability to use the
160 | Work (including but not limited to damages for loss of goodwill,
161 | work stoppage, computer failure or malfunction, or any and all
162 | other commercial damages or losses), even if such Contributor
163 | has been advised of the possibility of such damages.
164 |
165 | 9. Accepting Warranty or Additional Liability. While redistributing
166 | the Work or Derivative Works thereof, You may choose to offer,
167 | and charge a fee for, acceptance of support, warranty, indemnity,
168 | or other liability obligations and/or rights consistent with this
169 | License. However, in accepting such obligations, You may act only
170 | on Your own behalf and on Your sole responsibility, not on behalf
171 | of any other Contributor, and only if You agree to indemnify,
172 | defend, and hold each Contributor harmless for any liability
173 | incurred by, or claims asserted against, such Contributor by reason
174 | of your accepting any such warranty or additional liability.
175 |
176 | END OF TERMS AND CONDITIONS
177 |
178 | APPENDIX: How to apply the Apache License to your work.
179 |
180 | To apply the Apache License to your work, attach the following
181 | boilerplate notice, with the fields enclosed by brackets "{}"
182 | replaced with your own identifying information. (Don't include
183 | the brackets!) The text should be enclosed in the appropriate
184 | comment syntax for the file format. We also recommend that a
185 | file or class name and description of purpose be included on the
186 | same "printed page" as the copyright notice for easier
187 | identification within third-party archives.
188 |
189 | Copyright {yyyy} {name of copyright owner}
190 |
191 | Licensed under the Apache License, Version 2.0 (the "License");
192 | you may not use this file except in compliance with the License.
193 | You may obtain a copy of the License at
194 |
195 | http://www.apache.org/licenses/LICENSE-2.0
196 |
197 | Unless required by applicable law or agreed to in writing, software
198 | distributed under the License is distributed on an "AS IS" BASIS,
199 | WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
200 | See the License for the specific language governing permissions and
201 | limitations under the License.
202 |
203 |
--------------------------------------------------------------------------------
/README.adoc:
--------------------------------------------------------------------------------
1 | = Deprecated: Gatling Plugin for Gradle
2 | :gatlingToolVersion: 3.3.1
3 | :scalaVersion: 2.12.8
4 | :tip-caption: :bulb:
5 | :note-caption: :information_source:
6 | :important-caption: :heavy_exclamation_mark:
7 | :caution-caption: :fire:
8 | :warning-caption: :warning:
9 |
10 | [WARNING]
11 | ====
12 | Gatling officially supports https://github.com/gatling/gatling-gradle-plugin[Gradle].
13 |
14 | This plugin is deprecated and unsupported.
15 | ====
16 |
--------------------------------------------------------------------------------
/bootstrap.sh:
--------------------------------------------------------------------------------
1 | #!/bin/bash
2 |
3 | if [ $# -ne 1 ]; then
4 | echo "Usage: bootstrap.sh SAMPLE_PROJECT_FOLDER"
5 | exit 1
6 | fi
7 |
8 | DEST=$1
9 |
10 | if [ -a $DEST ]; then
11 | echo "$DEST already exists"
12 | exit 2
13 | fi
14 |
15 | mkdir -p $DEST
16 | cd $DEST
17 |
18 | git init
19 | git remote add origin https://github.com/lkishalmi/gradle-gatling-plugin.git
20 | git config core.sparseCheckout true
21 | echo "sample-project/" >> .git/info/sparse-checkout
22 | git pull origin master
23 |
24 | mv sample-project/* .
25 | rm -rf .git sample-project
26 |
--------------------------------------------------------------------------------
/build.gradle:
--------------------------------------------------------------------------------
1 | plugins {
2 | id 'java-gradle-plugin'
3 | id 'groovy'
4 | id 'com.gradle.plugin-publish' version '0.11.0'
5 | id 'maven-publish'
6 | }
7 |
8 | description = 'Gatling Plugin for Gradle'
9 |
10 | sourceCompatibility = '1.8'
11 | targetCompatibility = '1.8'
12 |
13 | repositories {
14 | jcenter()
15 | }
16 |
17 | dependencies {
18 | testImplementation('org.spockframework:spock-core:1.3-groovy-2.4') {
19 | exclude module: 'groovy-all'
20 | }
21 | testImplementation 'commons-io:commons-io:2.5'
22 | testImplementation 'com.github.stefanbirkner:system-rules:1.19.0'
23 | }
24 |
25 | test {
26 | testLogging {
27 | events "passed", "skipped", "failed"
28 | exceptionFormat "full"
29 | showStandardStreams = false
30 | }
31 | }
32 |
33 | pluginBundle {
34 | website = 'https://github.com/lkishalmi/gradle-gatling-plugin'
35 | vcsUrl = 'https://github.com/lkishalmi/gradle-gatling-plugin'
36 | description = 'Gatling Simulation Execution'
37 | tags = ['gatling', 'load test', 'stress test', 'performance test', 'scala']
38 |
39 | plugins {
40 | gatlingPlugin {
41 | displayName = 'Gatling Simulation Execution'
42 | id = 'com.github.lkishalmi.gatling'
43 | }
44 | }
45 | }
46 |
47 | validatePlugins.failOnWarning = false
48 |
--------------------------------------------------------------------------------
/gradle.properties:
--------------------------------------------------------------------------------
1 | group=com.github.lkishalmi.gatling
2 | org.gradle.daemon=true
3 | netbeans.license=apache20
--------------------------------------------------------------------------------
/gradle/wrapper/gradle-wrapper.jar:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/lkishalmi/gradle-gatling-plugin/b9a320dc11ea6d57280ef00c55a42779abe0b928/gradle/wrapper/gradle-wrapper.jar
--------------------------------------------------------------------------------
/gradle/wrapper/gradle-wrapper.properties:
--------------------------------------------------------------------------------
1 | #Wed Aug 31 21:54:57 EEST 2016
2 | distributionBase=GRADLE_USER_HOME
3 | distributionPath=wrapper/dists
4 | zipStoreBase=GRADLE_USER_HOME
5 | zipStorePath=wrapper/dists
6 | distributionUrl=https\://services.gradle.org/distributions/gradle-6.3-bin.zip
7 |
--------------------------------------------------------------------------------
/gradlew:
--------------------------------------------------------------------------------
1 | #!/usr/bin/env bash
2 |
3 | ##############################################################################
4 | ##
5 | ## Gradle start up script for UN*X
6 | ##
7 | ##############################################################################
8 |
9 | # Add default JVM options here. You can also use JAVA_OPTS and GRADLE_OPTS to pass JVM options to this script.
10 | DEFAULT_JVM_OPTS=""
11 |
12 | APP_NAME="Gradle"
13 | APP_BASE_NAME=`basename "$0"`
14 |
15 | # Use the maximum available, or set MAX_FD != -1 to use that value.
16 | MAX_FD="maximum"
17 |
18 | warn ( ) {
19 | echo "$*"
20 | }
21 |
22 | die ( ) {
23 | echo
24 | echo "$*"
25 | echo
26 | exit 1
27 | }
28 |
29 | # OS specific support (must be 'true' or 'false').
30 | cygwin=false
31 | msys=false
32 | darwin=false
33 | case "`uname`" in
34 | CYGWIN* )
35 | cygwin=true
36 | ;;
37 | Darwin* )
38 | darwin=true
39 | ;;
40 | MINGW* )
41 | msys=true
42 | ;;
43 | esac
44 |
45 | # Attempt to set APP_HOME
46 | # Resolve links: $0 may be a link
47 | PRG="$0"
48 | # Need this for relative symlinks.
49 | while [ -h "$PRG" ] ; do
50 | ls=`ls -ld "$PRG"`
51 | link=`expr "$ls" : '.*-> \(.*\)$'`
52 | if expr "$link" : '/.*' > /dev/null; then
53 | PRG="$link"
54 | else
55 | PRG=`dirname "$PRG"`"/$link"
56 | fi
57 | done
58 | SAVED="`pwd`"
59 | cd "`dirname \"$PRG\"`/" >/dev/null
60 | APP_HOME="`pwd -P`"
61 | cd "$SAVED" >/dev/null
62 |
63 | CLASSPATH=$APP_HOME/gradle/wrapper/gradle-wrapper.jar
64 |
65 | # Determine the Java command to use to start the JVM.
66 | if [ -n "$JAVA_HOME" ] ; then
67 | if [ -x "$JAVA_HOME/jre/sh/java" ] ; then
68 | # IBM's JDK on AIX uses strange locations for the executables
69 | JAVACMD="$JAVA_HOME/jre/sh/java"
70 | else
71 | JAVACMD="$JAVA_HOME/bin/java"
72 | fi
73 | if [ ! -x "$JAVACMD" ] ; then
74 | die "ERROR: JAVA_HOME is set to an invalid directory: $JAVA_HOME
75 |
76 | Please set the JAVA_HOME variable in your environment to match the
77 | location of your Java installation."
78 | fi
79 | else
80 | JAVACMD="java"
81 | which java >/dev/null 2>&1 || die "ERROR: JAVA_HOME is not set and no 'java' command could be found in your PATH.
82 |
83 | Please set the JAVA_HOME variable in your environment to match the
84 | location of your Java installation."
85 | fi
86 |
87 | # Increase the maximum file descriptors if we can.
88 | if [ "$cygwin" = "false" -a "$darwin" = "false" ] ; then
89 | MAX_FD_LIMIT=`ulimit -H -n`
90 | if [ $? -eq 0 ] ; then
91 | if [ "$MAX_FD" = "maximum" -o "$MAX_FD" = "max" ] ; then
92 | MAX_FD="$MAX_FD_LIMIT"
93 | fi
94 | ulimit -n $MAX_FD
95 | if [ $? -ne 0 ] ; then
96 | warn "Could not set maximum file descriptor limit: $MAX_FD"
97 | fi
98 | else
99 | warn "Could not query maximum file descriptor limit: $MAX_FD_LIMIT"
100 | fi
101 | fi
102 |
103 | # For Darwin, add options to specify how the application appears in the dock
104 | if $darwin; then
105 | GRADLE_OPTS="$GRADLE_OPTS \"-Xdock:name=$APP_NAME\" \"-Xdock:icon=$APP_HOME/media/gradle.icns\""
106 | fi
107 |
108 | # For Cygwin, switch paths to Windows format before running java
109 | if $cygwin ; then
110 | APP_HOME=`cygpath --path --mixed "$APP_HOME"`
111 | CLASSPATH=`cygpath --path --mixed "$CLASSPATH"`
112 | JAVACMD=`cygpath --unix "$JAVACMD"`
113 |
114 | # We build the pattern for arguments to be converted via cygpath
115 | ROOTDIRSRAW=`find -L / -maxdepth 1 -mindepth 1 -type d 2>/dev/null`
116 | SEP=""
117 | for dir in $ROOTDIRSRAW ; do
118 | ROOTDIRS="$ROOTDIRS$SEP$dir"
119 | SEP="|"
120 | done
121 | OURCYGPATTERN="(^($ROOTDIRS))"
122 | # Add a user-defined pattern to the cygpath arguments
123 | if [ "$GRADLE_CYGPATTERN" != "" ] ; then
124 | OURCYGPATTERN="$OURCYGPATTERN|($GRADLE_CYGPATTERN)"
125 | fi
126 | # Now convert the arguments - kludge to limit ourselves to /bin/sh
127 | i=0
128 | for arg in "$@" ; do
129 | CHECK=`echo "$arg"|egrep -c "$OURCYGPATTERN" -`
130 | CHECK2=`echo "$arg"|egrep -c "^-"` ### Determine if an option
131 |
132 | if [ $CHECK -ne 0 ] && [ $CHECK2 -eq 0 ] ; then ### Added a condition
133 | eval `echo args$i`=`cygpath --path --ignore --mixed "$arg"`
134 | else
135 | eval `echo args$i`="\"$arg\""
136 | fi
137 | i=$((i+1))
138 | done
139 | case $i in
140 | (0) set -- ;;
141 | (1) set -- "$args0" ;;
142 | (2) set -- "$args0" "$args1" ;;
143 | (3) set -- "$args0" "$args1" "$args2" ;;
144 | (4) set -- "$args0" "$args1" "$args2" "$args3" ;;
145 | (5) set -- "$args0" "$args1" "$args2" "$args3" "$args4" ;;
146 | (6) set -- "$args0" "$args1" "$args2" "$args3" "$args4" "$args5" ;;
147 | (7) set -- "$args0" "$args1" "$args2" "$args3" "$args4" "$args5" "$args6" ;;
148 | (8) set -- "$args0" "$args1" "$args2" "$args3" "$args4" "$args5" "$args6" "$args7" ;;
149 | (9) set -- "$args0" "$args1" "$args2" "$args3" "$args4" "$args5" "$args6" "$args7" "$args8" ;;
150 | esac
151 | fi
152 |
153 | # Split up the JVM_OPTS And GRADLE_OPTS values into an array, following the shell quoting and substitution rules
154 | function splitJvmOpts() {
155 | JVM_OPTS=("$@")
156 | }
157 | eval splitJvmOpts $DEFAULT_JVM_OPTS $JAVA_OPTS $GRADLE_OPTS
158 | JVM_OPTS[${#JVM_OPTS[*]}]="-Dorg.gradle.appname=$APP_BASE_NAME"
159 |
160 | exec "$JAVACMD" "${JVM_OPTS[@]}" -classpath "$CLASSPATH" org.gradle.wrapper.GradleWrapperMain "$@"
161 |
--------------------------------------------------------------------------------
/gradlew.bat:
--------------------------------------------------------------------------------
1 | @if "%DEBUG%" == "" @echo off
2 | @rem ##########################################################################
3 | @rem
4 | @rem Gradle startup script for Windows
5 | @rem
6 | @rem ##########################################################################
7 |
8 | @rem Set local scope for the variables with windows NT shell
9 | if "%OS%"=="Windows_NT" setlocal
10 |
11 | @rem Add default JVM options here. You can also use JAVA_OPTS and GRADLE_OPTS to pass JVM options to this script.
12 | set DEFAULT_JVM_OPTS=
13 |
14 | set DIRNAME=%~dp0
15 | if "%DIRNAME%" == "" set DIRNAME=.
16 | set APP_BASE_NAME=%~n0
17 | set APP_HOME=%DIRNAME%
18 |
19 | @rem Find java.exe
20 | if defined JAVA_HOME goto findJavaFromJavaHome
21 |
22 | set JAVA_EXE=java.exe
23 | %JAVA_EXE% -version >NUL 2>&1
24 | if "%ERRORLEVEL%" == "0" goto init
25 |
26 | echo.
27 | echo ERROR: JAVA_HOME is not set and no 'java' command could be found in your PATH.
28 | echo.
29 | echo Please set the JAVA_HOME variable in your environment to match the
30 | echo location of your Java installation.
31 |
32 | goto fail
33 |
34 | :findJavaFromJavaHome
35 | set JAVA_HOME=%JAVA_HOME:"=%
36 | set JAVA_EXE=%JAVA_HOME%/bin/java.exe
37 |
38 | if exist "%JAVA_EXE%" goto init
39 |
40 | echo.
41 | echo ERROR: JAVA_HOME is set to an invalid directory: %JAVA_HOME%
42 | echo.
43 | echo Please set the JAVA_HOME variable in your environment to match the
44 | echo location of your Java installation.
45 |
46 | goto fail
47 |
48 | :init
49 | @rem Get command-line arguments, handling Windows variants
50 |
51 | if not "%OS%" == "Windows_NT" goto win9xME_args
52 | if "%@eval[2+2]" == "4" goto 4NT_args
53 |
54 | :win9xME_args
55 | @rem Slurp the command line arguments.
56 | set CMD_LINE_ARGS=
57 | set _SKIP=2
58 |
59 | :win9xME_args_slurp
60 | if "x%~1" == "x" goto execute
61 |
62 | set CMD_LINE_ARGS=%*
63 | goto execute
64 |
65 | :4NT_args
66 | @rem Get arguments from the 4NT Shell from JP Software
67 | set CMD_LINE_ARGS=%$
68 |
69 | :execute
70 | @rem Setup the command line
71 |
72 | set CLASSPATH=%APP_HOME%\gradle\wrapper\gradle-wrapper.jar
73 |
74 | @rem Execute Gradle
75 | "%JAVA_EXE%" %DEFAULT_JVM_OPTS% %JAVA_OPTS% %GRADLE_OPTS% "-Dorg.gradle.appname=%APP_BASE_NAME%" -classpath "%CLASSPATH%" org.gradle.wrapper.GradleWrapperMain %CMD_LINE_ARGS%
76 |
77 | :end
78 | @rem End local scope for the variables with windows NT shell
79 | if "%ERRORLEVEL%"=="0" goto mainEnd
80 |
81 | :fail
82 | rem Set variable GRADLE_EXIT_CONSOLE if you need the _script_ return code instead of
83 | rem the _cmd.exe /c_ return code!
84 | if not "" == "%GRADLE_EXIT_CONSOLE%" exit 1
85 | exit /b 1
86 |
87 | :mainEnd
88 | if "%OS%"=="Windows_NT" endlocal
89 |
90 | :omega
91 |
--------------------------------------------------------------------------------
/nb-actions.xml:
--------------------------------------------------------------------------------
1 |
2 |
3 |
4 |
5 | -Pversion=${input:Version,0.4.x}
6 | clean
7 | publishPlugins
8 |
9 |
10 |
--------------------------------------------------------------------------------
/sample-project/build.gradle:
--------------------------------------------------------------------------------
1 | plugins {
2 | id "com.github.lkishalmi.gatling" version "3.3.4"
3 | }
4 |
5 | repositories {
6 | jcenter()
7 | }
8 |
--------------------------------------------------------------------------------
/sample-project/gradle/wrapper/gradle-wrapper.jar:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/lkishalmi/gradle-gatling-plugin/b9a320dc11ea6d57280ef00c55a42779abe0b928/sample-project/gradle/wrapper/gradle-wrapper.jar
--------------------------------------------------------------------------------
/sample-project/gradle/wrapper/gradle-wrapper.properties:
--------------------------------------------------------------------------------
1 | distributionBase=GRADLE_USER_HOME
2 | distributionPath=wrapper/dists
3 | distributionUrl=https\://services.gradle.org/distributions/gradle-6.3-bin.zip
4 | zipStoreBase=GRADLE_USER_HOME
5 | zipStorePath=wrapper/dists
6 |
--------------------------------------------------------------------------------
/sample-project/gradlew:
--------------------------------------------------------------------------------
1 | #!/usr/bin/env sh
2 |
3 | ##############################################################################
4 | ##
5 | ## Gradle start up script for UN*X
6 | ##
7 | ##############################################################################
8 |
9 | # Attempt to set APP_HOME
10 | # Resolve links: $0 may be a link
11 | PRG="$0"
12 | # Need this for relative symlinks.
13 | while [ -h "$PRG" ] ; do
14 | ls=`ls -ld "$PRG"`
15 | link=`expr "$ls" : '.*-> \(.*\)$'`
16 | if expr "$link" : '/.*' > /dev/null; then
17 | PRG="$link"
18 | else
19 | PRG=`dirname "$PRG"`"/$link"
20 | fi
21 | done
22 | SAVED="`pwd`"
23 | cd "`dirname \"$PRG\"`/" >/dev/null
24 | APP_HOME="`pwd -P`"
25 | cd "$SAVED" >/dev/null
26 |
27 | APP_NAME="Gradle"
28 | APP_BASE_NAME=`basename "$0"`
29 |
30 | # Add default JVM options here. You can also use JAVA_OPTS and GRADLE_OPTS to pass JVM options to this script.
31 | DEFAULT_JVM_OPTS=""
32 |
33 | # Use the maximum available, or set MAX_FD != -1 to use that value.
34 | MAX_FD="maximum"
35 |
36 | warn () {
37 | echo "$*"
38 | }
39 |
40 | die () {
41 | echo
42 | echo "$*"
43 | echo
44 | exit 1
45 | }
46 |
47 | # OS specific support (must be 'true' or 'false').
48 | cygwin=false
49 | msys=false
50 | darwin=false
51 | nonstop=false
52 | case "`uname`" in
53 | CYGWIN* )
54 | cygwin=true
55 | ;;
56 | Darwin* )
57 | darwin=true
58 | ;;
59 | MINGW* )
60 | msys=true
61 | ;;
62 | NONSTOP* )
63 | nonstop=true
64 | ;;
65 | esac
66 |
67 | CLASSPATH=$APP_HOME/gradle/wrapper/gradle-wrapper.jar
68 |
69 | # Determine the Java command to use to start the JVM.
70 | if [ -n "$JAVA_HOME" ] ; then
71 | if [ -x "$JAVA_HOME/jre/sh/java" ] ; then
72 | # IBM's JDK on AIX uses strange locations for the executables
73 | JAVACMD="$JAVA_HOME/jre/sh/java"
74 | else
75 | JAVACMD="$JAVA_HOME/bin/java"
76 | fi
77 | if [ ! -x "$JAVACMD" ] ; then
78 | die "ERROR: JAVA_HOME is set to an invalid directory: $JAVA_HOME
79 |
80 | Please set the JAVA_HOME variable in your environment to match the
81 | location of your Java installation."
82 | fi
83 | else
84 | JAVACMD="java"
85 | which java >/dev/null 2>&1 || die "ERROR: JAVA_HOME is not set and no 'java' command could be found in your PATH.
86 |
87 | Please set the JAVA_HOME variable in your environment to match the
88 | location of your Java installation."
89 | fi
90 |
91 | # Increase the maximum file descriptors if we can.
92 | if [ "$cygwin" = "false" -a "$darwin" = "false" -a "$nonstop" = "false" ] ; then
93 | MAX_FD_LIMIT=`ulimit -H -n`
94 | if [ $? -eq 0 ] ; then
95 | if [ "$MAX_FD" = "maximum" -o "$MAX_FD" = "max" ] ; then
96 | MAX_FD="$MAX_FD_LIMIT"
97 | fi
98 | ulimit -n $MAX_FD
99 | if [ $? -ne 0 ] ; then
100 | warn "Could not set maximum file descriptor limit: $MAX_FD"
101 | fi
102 | else
103 | warn "Could not query maximum file descriptor limit: $MAX_FD_LIMIT"
104 | fi
105 | fi
106 |
107 | # For Darwin, add options to specify how the application appears in the dock
108 | if $darwin; then
109 | GRADLE_OPTS="$GRADLE_OPTS \"-Xdock:name=$APP_NAME\" \"-Xdock:icon=$APP_HOME/media/gradle.icns\""
110 | fi
111 |
112 | # For Cygwin, switch paths to Windows format before running java
113 | if $cygwin ; then
114 | APP_HOME=`cygpath --path --mixed "$APP_HOME"`
115 | CLASSPATH=`cygpath --path --mixed "$CLASSPATH"`
116 | JAVACMD=`cygpath --unix "$JAVACMD"`
117 |
118 | # We build the pattern for arguments to be converted via cygpath
119 | ROOTDIRSRAW=`find -L / -maxdepth 1 -mindepth 1 -type d 2>/dev/null`
120 | SEP=""
121 | for dir in $ROOTDIRSRAW ; do
122 | ROOTDIRS="$ROOTDIRS$SEP$dir"
123 | SEP="|"
124 | done
125 | OURCYGPATTERN="(^($ROOTDIRS))"
126 | # Add a user-defined pattern to the cygpath arguments
127 | if [ "$GRADLE_CYGPATTERN" != "" ] ; then
128 | OURCYGPATTERN="$OURCYGPATTERN|($GRADLE_CYGPATTERN)"
129 | fi
130 | # Now convert the arguments - kludge to limit ourselves to /bin/sh
131 | i=0
132 | for arg in "$@" ; do
133 | CHECK=`echo "$arg"|egrep -c "$OURCYGPATTERN" -`
134 | CHECK2=`echo "$arg"|egrep -c "^-"` ### Determine if an option
135 |
136 | if [ $CHECK -ne 0 ] && [ $CHECK2 -eq 0 ] ; then ### Added a condition
137 | eval `echo args$i`=`cygpath --path --ignore --mixed "$arg"`
138 | else
139 | eval `echo args$i`="\"$arg\""
140 | fi
141 | i=$((i+1))
142 | done
143 | case $i in
144 | (0) set -- ;;
145 | (1) set -- "$args0" ;;
146 | (2) set -- "$args0" "$args1" ;;
147 | (3) set -- "$args0" "$args1" "$args2" ;;
148 | (4) set -- "$args0" "$args1" "$args2" "$args3" ;;
149 | (5) set -- "$args0" "$args1" "$args2" "$args3" "$args4" ;;
150 | (6) set -- "$args0" "$args1" "$args2" "$args3" "$args4" "$args5" ;;
151 | (7) set -- "$args0" "$args1" "$args2" "$args3" "$args4" "$args5" "$args6" ;;
152 | (8) set -- "$args0" "$args1" "$args2" "$args3" "$args4" "$args5" "$args6" "$args7" ;;
153 | (9) set -- "$args0" "$args1" "$args2" "$args3" "$args4" "$args5" "$args6" "$args7" "$args8" ;;
154 | esac
155 | fi
156 |
157 | # Escape application args
158 | save () {
159 | for i do printf %s\\n "$i" | sed "s/'/'\\\\''/g;1s/^/'/;\$s/\$/' \\\\/" ; done
160 | echo " "
161 | }
162 | APP_ARGS=$(save "$@")
163 |
164 | # Collect all arguments for the java command, following the shell quoting and substitution rules
165 | eval set -- $DEFAULT_JVM_OPTS $JAVA_OPTS $GRADLE_OPTS "\"-Dorg.gradle.appname=$APP_BASE_NAME\"" -classpath "\"$CLASSPATH\"" org.gradle.wrapper.GradleWrapperMain "$APP_ARGS"
166 |
167 | # by default we should be in the correct project dir, but when run from Finder on Mac, the cwd is wrong
168 | if [ "$(uname)" = "Darwin" ] && [ "$HOME" = "$PWD" ]; then
169 | cd "$(dirname "$0")"
170 | fi
171 |
172 | exec "$JAVACMD" "$@"
173 |
--------------------------------------------------------------------------------
/sample-project/gradlew.bat:
--------------------------------------------------------------------------------
1 | @if "%DEBUG%" == "" @echo off
2 | @rem ##########################################################################
3 | @rem
4 | @rem Gradle startup script for Windows
5 | @rem
6 | @rem ##########################################################################
7 |
8 | @rem Set local scope for the variables with windows NT shell
9 | if "%OS%"=="Windows_NT" setlocal
10 |
11 | set DIRNAME=%~dp0
12 | if "%DIRNAME%" == "" set DIRNAME=.
13 | set APP_BASE_NAME=%~n0
14 | set APP_HOME=%DIRNAME%
15 |
16 | @rem Add default JVM options here. You can also use JAVA_OPTS and GRADLE_OPTS to pass JVM options to this script.
17 | set DEFAULT_JVM_OPTS=
18 |
19 | @rem Find java.exe
20 | if defined JAVA_HOME goto findJavaFromJavaHome
21 |
22 | set JAVA_EXE=java.exe
23 | %JAVA_EXE% -version >NUL 2>&1
24 | if "%ERRORLEVEL%" == "0" goto init
25 |
26 | echo.
27 | echo ERROR: JAVA_HOME is not set and no 'java' command could be found in your PATH.
28 | echo.
29 | echo Please set the JAVA_HOME variable in your environment to match the
30 | echo location of your Java installation.
31 |
32 | goto fail
33 |
34 | :findJavaFromJavaHome
35 | set JAVA_HOME=%JAVA_HOME:"=%
36 | set JAVA_EXE=%JAVA_HOME%/bin/java.exe
37 |
38 | if exist "%JAVA_EXE%" goto init
39 |
40 | echo.
41 | echo ERROR: JAVA_HOME is set to an invalid directory: %JAVA_HOME%
42 | echo.
43 | echo Please set the JAVA_HOME variable in your environment to match the
44 | echo location of your Java installation.
45 |
46 | goto fail
47 |
48 | :init
49 | @rem Get command-line arguments, handling Windows variants
50 |
51 | if not "%OS%" == "Windows_NT" goto win9xME_args
52 |
53 | :win9xME_args
54 | @rem Slurp the command line arguments.
55 | set CMD_LINE_ARGS=
56 | set _SKIP=2
57 |
58 | :win9xME_args_slurp
59 | if "x%~1" == "x" goto execute
60 |
61 | set CMD_LINE_ARGS=%*
62 |
63 | :execute
64 | @rem Setup the command line
65 |
66 | set CLASSPATH=%APP_HOME%\gradle\wrapper\gradle-wrapper.jar
67 |
68 | @rem Execute Gradle
69 | "%JAVA_EXE%" %DEFAULT_JVM_OPTS% %JAVA_OPTS% %GRADLE_OPTS% "-Dorg.gradle.appname=%APP_BASE_NAME%" -classpath "%CLASSPATH%" org.gradle.wrapper.GradleWrapperMain %CMD_LINE_ARGS%
70 |
71 | :end
72 | @rem End local scope for the variables with windows NT shell
73 | if "%ERRORLEVEL%"=="0" goto mainEnd
74 |
75 | :fail
76 | rem Set variable GRADLE_EXIT_CONSOLE if you need the _script_ return code instead of
77 | rem the _cmd.exe /c_ return code!
78 | if not "" == "%GRADLE_EXIT_CONSOLE%" exit 1
79 | exit /b 1
80 |
81 | :mainEnd
82 | if "%OS%"=="Windows_NT" endlocal
83 |
84 | :omega
85 |
--------------------------------------------------------------------------------
/sample-project/src/gatling/resources/search.csv:
--------------------------------------------------------------------------------
1 | searchCriterion,searchComputerName
2 | Macbook,MacBook Pro
3 | eee,ASUS Eee PC 1005PE
--------------------------------------------------------------------------------
/sample-project/src/gatling/simulations/SampleSimulation.scala:
--------------------------------------------------------------------------------
1 | import scala.concurrent.duration._
2 |
3 | import io.gatling.core.Predef._
4 | import io.gatling.http.Predef._
5 |
6 | class SampleSimulation extends Simulation {
7 |
8 | object Search {
9 |
10 | val feeder = csv("search.csv").random
11 |
12 | val search = exec(
13 | http("Home")
14 | .get("/")
15 | ).pause(1)
16 | .feed(feeder)
17 | .exec(
18 | http("Search")
19 | .get("/computers?f=${searchCriterion}")
20 | .check(css("a:contains('${searchComputerName}')", "href").saveAs("computerURL"))
21 | )
22 | .pause(1)
23 | .exec(
24 | http("Select")
25 | .get("${computerURL}")
26 | .check(status.is(200))
27 | )
28 | .pause(1)
29 | }
30 |
31 | val httpProtocol = http
32 | .baseUrl("http://computer-database.gatling.io")
33 | .acceptHeader("text/html,application/xhtml+xml,application/xml;q=0.9,*/*;q=0.8")
34 | .doNotTrackHeader("1")
35 | .acceptLanguageHeader("en-US,en;q=0.5")
36 | .acceptEncodingHeader("gzip, deflate")
37 | .userAgentHeader("Mozilla/5.0 (Macintosh; Intel Mac OS X 10.8; rv:16.0) Gecko/20100101 Firefox/16.0")
38 |
39 | val users = scenario("Users").exec(Search.search)
40 |
41 | setUp(users.inject(rampUsers(1) during (1 seconds))).protocols(httpProtocol)
42 | }
43 |
--------------------------------------------------------------------------------
/src/main/groovy/com/github/lkishalmi/gradle/gatling/GatlingPlugin.groovy:
--------------------------------------------------------------------------------
1 | package com.github.lkishalmi.gradle.gatling
2 |
3 | import org.gradle.api.GradleException
4 | import org.gradle.api.Plugin
5 | import org.gradle.api.Project
6 | import org.gradle.api.plugins.scala.ScalaPlugin
7 | import org.gradle.util.GradleVersion
8 | import org.gradle.util.VersionNumber
9 |
10 | /**
11 | *
12 | * @author Laszlo Kishalmi
13 | */
14 | class GatlingPlugin implements Plugin {
15 |
16 | public static def GATLING_EXTENSION_NAME = 'gatling'
17 |
18 | public static def GATLING_RUN_TASK_NAME = 'gatlingRun'
19 |
20 | static String GATLING_TASK_NAME_PREFIX = "$GATLING_RUN_TASK_NAME-"
21 |
22 | private Project project
23 |
24 | void apply(Project project) {
25 |
26 | if (VersionNumber.parse(GradleVersion.current().version).major < 4) {
27 | throw new GradleException("Current Gradle version (${GradleVersion.current().version}) is unsupported. Minimal supported version is 4.0")
28 | }
29 |
30 | this.project = project
31 |
32 | project.pluginManager.apply ScalaPlugin
33 |
34 | GatlingPluginExtension gatlingExt = project.extensions.create(GATLING_EXTENSION_NAME, GatlingPluginExtension, project)
35 |
36 | createConfiguration(gatlingExt)
37 |
38 | createGatlingTask(GATLING_RUN_TASK_NAME, null)
39 |
40 | project.tasks.getByName("processGatlingResources").doLast(new LogbackConfigTaskAction())
41 |
42 | project.tasks.addRule("Pattern: $GATLING_RUN_TASK_NAME-: Executes single Gatling simulation.") { String taskName ->
43 | if (taskName.startsWith(GATLING_TASK_NAME_PREFIX)) {
44 | createGatlingTask(taskName, (taskName - GATLING_TASK_NAME_PREFIX))
45 | }
46 | }
47 | }
48 |
49 | void createGatlingTask(String taskName, String simulationFQN = null) {
50 | def task = project.tasks.create(name: taskName,
51 | dependsOn: project.tasks.gatlingClasses, type: GatlingRunTask,
52 | description: "Execute Gatling simulation", group: "Gatling")
53 |
54 | if (simulationFQN) {
55 | task.configure {
56 | simulations = {
57 | include "${simulationFQN.replace('.', '/')}.scala"
58 | }
59 | }
60 | }
61 | }
62 |
63 | void createConfiguration(GatlingPluginExtension gatlingExt) {
64 | project.sourceSets {
65 | gatling {
66 | scala.srcDirs = [gatlingExt.SIMULATIONS_DIR]
67 | resources.srcDirs = [gatlingExt.RESOURCES_DIR]
68 | }
69 | }
70 |
71 | project.configurations {
72 | gatling { visible = false }
73 | gatlingImplementation.extendsFrom(gatling)
74 | }
75 |
76 | project.dependencies {
77 | gatlingRuntimeOnly project.sourceSets.gatling.output
78 | }
79 |
80 | project.afterEvaluate { Project p ->
81 | p.dependencies {
82 | implementation "org.scala-lang:scala-library:${p.extensions.getByType(GatlingPluginExtension).scalaVersion}"
83 | gatlingImplementation "org.scala-lang:scala-library:${p.extensions.getByType(GatlingPluginExtension).scalaVersion}"
84 | gatling "io.gatling.highcharts:gatling-charts-highcharts:${p.extensions.getByType(GatlingPluginExtension).toolVersion}"
85 |
86 | if (gatlingExt.includeMainOutput) {
87 | gatlingImplementation project.sourceSets.main.output
88 | }
89 | if (gatlingExt.includeTestOutput) {
90 | gatlingImplementation project.sourceSets.test.output
91 | }
92 | }
93 | }
94 | }
95 | }
96 |
97 |
--------------------------------------------------------------------------------
/src/main/groovy/com/github/lkishalmi/gradle/gatling/GatlingPluginExtension.groovy:
--------------------------------------------------------------------------------
1 | package com.github.lkishalmi.gradle.gatling
2 |
3 | import org.gradle.api.Project
4 |
5 | class GatlingPluginExtension implements JvmConfigurable {
6 |
7 | static final String GATLING_MAIN_CLASS = 'io.gatling.app.Gatling'
8 |
9 | static final String SIMULATIONS_DIR = "src/gatling/simulations"
10 |
11 | static final String RESOURCES_DIR = "src/gatling/resources"
12 |
13 | static final String GATLING_TOOL_VERSION = '3.3.1'
14 |
15 | static final String SCALA_VERSION = '2.12.8'
16 |
17 | static final Closure DEFAULT_SIMULATIONS = { include("**/*Simulation*.scala") }
18 |
19 | def toolVersion = GATLING_TOOL_VERSION
20 |
21 | def scalaVersion = SCALA_VERSION
22 |
23 | Closure simulations = DEFAULT_SIMULATIONS
24 |
25 | Boolean includeMainOutput = true
26 | Boolean includeTestOutput = true
27 |
28 | String logLevel = "WARN"
29 |
30 | private final Project project
31 |
32 | GatlingPluginExtension(Project project) {
33 | this.project = project
34 | this.jvmArgs = DEFAULT_JVM_ARGS
35 | this.systemProperties = DEFAULT_SYSTEM_PROPS
36 | }
37 | }
38 |
--------------------------------------------------------------------------------
/src/main/groovy/com/github/lkishalmi/gradle/gatling/GatlingRunTask.groovy:
--------------------------------------------------------------------------------
1 | package com.github.lkishalmi.gradle.gatling
2 |
3 | import org.gradle.api.Action
4 | import org.gradle.api.DefaultTask
5 | import org.gradle.api.file.FileTree
6 | import org.gradle.api.tasks.InputFiles
7 | import org.gradle.api.tasks.OutputDirectory
8 | import org.gradle.api.tasks.TaskAction
9 | import org.gradle.api.tasks.TaskExecutionException
10 | import org.gradle.process.ExecResult
11 | import org.gradle.process.JavaExecSpec
12 |
13 | import java.nio.file.Path
14 | import java.nio.file.Paths
15 |
16 | class GatlingRunTask extends DefaultTask implements JvmConfigurable {
17 |
18 | Closure simulations
19 |
20 | @OutputDirectory
21 | File gatlingReportDir = project.file("${project.reportsDir}/gatling")
22 |
23 | @InputFiles
24 | FileTree getSimulationSources() {
25 | def simulationFilter = this.simulations ?: project.gatling.simulations
26 | return project.sourceSets.gatling.scala.matching(simulationFilter)
27 | }
28 |
29 | List createGatlingArgs() {
30 |
31 | File scalaClasses = project.sourceSets.gatling.output.classesDirs.filter {
32 | it.parentFile.name == 'scala'
33 | }.singleFile
34 |
35 | return ['-bf', scalaClasses.absolutePath,
36 | "-rsf", "${project.sourceSets.gatling.output.resourcesDir}",
37 | "-rf", gatlingReportDir.absolutePath]
38 | }
39 |
40 | Iterable simulationFilesToFQN() {
41 |
42 | def scalaSrcDirs = project.sourceSets.gatling.scala.srcDirs.collect { Paths.get(it.absolutePath) }
43 | def scalaFiles = getSimulationSources().collect { Paths.get(it.absolutePath) }
44 |
45 | return scalaFiles.collect { Path srcFile ->
46 | scalaSrcDirs.find { srcFile.startsWith(it) }.relativize(srcFile).join(".") - ".scala"
47 | }
48 | }
49 |
50 | @TaskAction
51 | void gatlingRun() {
52 | def gatlingExt = project.extensions.getByType(GatlingPluginExtension)
53 |
54 | Map results = simulationFilesToFQN().collectEntries { String simulationClzName ->
55 | [(simulationClzName): project.javaexec({ JavaExecSpec exec ->
56 | exec.main = GatlingPluginExtension.GATLING_MAIN_CLASS
57 | exec.classpath = project.configurations.gatlingRuntimeClasspath
58 |
59 | exec.jvmArgs this.jvmArgs ?: gatlingExt.jvmArgs
60 | exec.systemProperties System.properties
61 | exec.systemProperties this.systemProperties ?: gatlingExt.systemProperties
62 |
63 | exec.args this.createGatlingArgs()
64 | exec.args "-s", simulationClzName
65 |
66 | exec.standardInput = System.in
67 |
68 | exec.ignoreExitValue = true
69 | } as Action)]
70 | }
71 |
72 | Map failed = results.findAll { it.value.exitValue != 0 }
73 |
74 | if (!failed.isEmpty()) {
75 | throw new TaskExecutionException(this, new RuntimeException("There're failed simulations: ${failed.keySet().sort().join(", ")}"))
76 | }
77 |
78 | }
79 | }
80 |
--------------------------------------------------------------------------------
/src/main/groovy/com/github/lkishalmi/gradle/gatling/JvmConfigurable.groovy:
--------------------------------------------------------------------------------
1 | package com.github.lkishalmi.gradle.gatling
2 |
3 | trait JvmConfigurable {
4 |
5 | static final List DEFAULT_JVM_ARGS = [
6 | '-Xmx1G',
7 | '-XX:+HeapDumpOnOutOfMemoryError',
8 | '-XX:+UseG1GC',
9 | '-XX:MaxGCPauseMillis=30',
10 | '-XX:G1HeapRegionSize=16m',
11 | '-XX:InitiatingHeapOccupancyPercent=75',
12 | '-XX:+ParallelRefProcEnabled',
13 | '-XX:+PerfDisableSharedMem',
14 | '-XX:+OptimizeStringConcat'
15 | ]
16 |
17 | static final Map DEFAULT_SYSTEM_PROPS = ["java.net.preferIPv4Stack": true, "java.net.preferIPv6Addresses": false]
18 |
19 | List jvmArgs
20 |
21 | Map systemProperties
22 |
23 | }
24 |
--------------------------------------------------------------------------------
/src/main/groovy/com/github/lkishalmi/gradle/gatling/LogbackConfigTaskAction.groovy:
--------------------------------------------------------------------------------
1 | package com.github.lkishalmi.gradle.gatling
2 |
3 | import org.gradle.api.Action
4 | import org.gradle.api.Task
5 |
6 | class LogbackConfigTaskAction implements Action {
7 | static def template(String logLevel) {
8 | """
9 |
10 |
11 |
12 | %d{HH:mm:ss.SSS} [%-5level] %logger{15} - %msg%n%rEx
13 |
14 | false
15 |
16 |
17 |
18 |
19 | """
20 | }
21 |
22 | void execute(Task gatlingRunTask) {
23 | def gatlingExt = gatlingRunTask.project.extensions.getByType(GatlingPluginExtension)
24 | if (!gatlingRunTask.project.file("${GatlingPluginExtension.RESOURCES_DIR}/logback.xml").exists()) {
25 | new File(gatlingRunTask.project.buildDir, "resources/gatling/logback.xml").with {
26 | parentFile.mkdirs()
27 | text = template(gatlingExt.logLevel)
28 | }
29 | }
30 | }
31 | }
32 |
--------------------------------------------------------------------------------
/src/main/resources/META-INF/gradle-plugins/com.github.lkishalmi.gatling.properties:
--------------------------------------------------------------------------------
1 | implementation-class=com.github.lkishalmi.gradle.gatling.GatlingPlugin
--------------------------------------------------------------------------------
/src/test/groovy/functional/GradleCompatibilitySpec.groovy:
--------------------------------------------------------------------------------
1 | package functional
2 |
3 | import helper.GatlingFuncSpec
4 | import org.gradle.testkit.runner.BuildResult
5 | import org.gradle.testkit.runner.GradleRunner
6 | import spock.lang.Unroll
7 |
8 | import static org.gradle.testkit.runner.TaskOutcome.SUCCESS
9 |
10 | class GradleCompatibilitySpec extends GatlingFuncSpec {
11 |
12 | BuildResult executeGradleTaskWithVersion(String task, String gradleVersion, boolean shouldFail) {
13 | def runner = GradleRunner.create().forwardOutput()
14 | .withProjectDir(projectDir.root)
15 | .withArguments("--stacktrace", task)
16 | .withPluginClasspath()
17 | .withDebug(true)
18 | .withGradleVersion(gradleVersion)
19 |
20 | if (shouldFail) {
21 | return runner.buildAndFail()
22 | } else {
23 | return runner.build()
24 | }
25 | }
26 |
27 | @Unroll
28 | void 'should succeed for version #gradleVersion that greater than 4.0'() {
29 | given:
30 | prepareTest()
31 | when:
32 | BuildResult result = executeGradleTaskWithVersion('tasks', gradleVersion, false)
33 | then:
34 | result.task(":tasks").outcome == SUCCESS
35 | where:
36 | gradleVersion << ["4.0.1", "4.10.2", "5.0", "5.6.4", "6.0", "6.3"]
37 | }
38 |
39 | @Unroll
40 | void 'should fail for version #gradleVersion that less than 4.0'() {
41 | given:
42 | prepareTest()
43 | when:
44 | BuildResult result = executeGradleTaskWithVersion('tasks', gradleVersion, true)
45 | then:
46 | result.output.contains("Current Gradle version (${gradleVersion}) is unsupported. Minimal supported version is 4.0")
47 | where:
48 | gradleVersion << ["3.5", "3.0", "2.9"]
49 | }
50 | }
51 |
--------------------------------------------------------------------------------
/src/test/groovy/functional/LogbackConfigTaskActionTest.groovy:
--------------------------------------------------------------------------------
1 | package functional
2 |
3 | import helper.GatlingFuncSpec
4 | import org.gradle.testkit.runner.BuildResult
5 |
6 | import static org.gradle.testkit.runner.TaskOutcome.SUCCESS
7 |
8 | class LogbackConfigTaskActionTest extends GatlingFuncSpec {
9 |
10 | static def PROCESS_GATLING_RESOURCES_TASK_NAME = "processGatlingResources"
11 |
12 | File logbackConfig
13 |
14 | XmlSlurper xml = new XmlSlurper()
15 |
16 | def setup() {
17 | prepareTest()
18 | logbackConfig = new File(buildDir, "resources/gatling/logback.xml".toString())
19 | }
20 |
21 | def "should create sample logback using logLevel from extension"() {
22 | when:
23 | BuildResult result = executeGradle(PROCESS_GATLING_RESOURCES_TASK_NAME)
24 | then:
25 | result.task(":$PROCESS_GATLING_RESOURCES_TASK_NAME").outcome == SUCCESS
26 | and:
27 | logbackConfig.exists()
28 | and:
29 | xml.parse(logbackConfig).root.@level == "WARN"
30 | }
31 |
32 | def "should override logLevel via extension"() {
33 | given:
34 | buildFile << 'gatling { logLevel = "QQQQ" }'
35 | when:
36 | BuildResult result = executeGradle(PROCESS_GATLING_RESOURCES_TASK_NAME)
37 | then:
38 | result.task(":$PROCESS_GATLING_RESOURCES_TASK_NAME").outcome == SUCCESS
39 | and:
40 | logbackConfig.exists()
41 | and:
42 | xml.parse(logbackConfig).root.@level == "QQQQ"
43 | }
44 |
45 | def "should not create sample logback.xml when it exists"() {
46 | given: ""
47 | new File(projectDir.root, "src/gatling/resources/logback.xml") << """"""
48 | when:
49 | BuildResult result = executeGradle(PROCESS_GATLING_RESOURCES_TASK_NAME)
50 | then:
51 | result.task(":$PROCESS_GATLING_RESOURCES_TASK_NAME").outcome == SUCCESS
52 | and:
53 | logbackConfig.exists()
54 | and:
55 | xml.parse(logbackConfig).@attr == "value"
56 | }
57 | }
58 |
--------------------------------------------------------------------------------
/src/test/groovy/functional/WhenCompileSimulationSpec.groovy:
--------------------------------------------------------------------------------
1 | package functional
2 |
3 | import helper.GatlingFuncSpec
4 | import org.gradle.testkit.runner.BuildResult
5 | import org.gradle.testkit.runner.UnexpectedBuildFailure
6 | import spock.lang.Ignore
7 | import spock.lang.Unroll
8 |
9 | import static org.gradle.testkit.runner.TaskOutcome.SUCCESS
10 |
11 | class WhenCompileSimulationSpec extends GatlingFuncSpec {
12 |
13 | static def GATLING_CLASSES_TASK_NAME = "gatlingClasses"
14 |
15 | def setup() {
16 | prepareTest()
17 | }
18 |
19 | def "should compile"() {
20 | when:
21 | BuildResult result = executeGradle(GATLING_CLASSES_TASK_NAME)
22 | then: "compiled successfully"
23 | result.task(":$GATLING_CLASSES_TASK_NAME").outcome == SUCCESS
24 | and: "only layout specific simulations were compiled"
25 | def classesDir = new File(buildDir, "classes/scala/gatling")
26 | classesDir.exists()
27 | and: "only layout specific resources are copied"
28 | def resourcesDir = new File(buildDir, "resources/gatling")
29 | resourcesDir.exists()
30 | new File(resourcesDir, "search.csv").exists()
31 | and: "main classes are compiled"
32 | def mainDir = new File(buildDir, "classes/java/main")
33 | mainDir.exists()
34 | and: "test classes are compiled"
35 | def testDir = new File(buildDir, "classes/java/test")
36 | testDir.exists()
37 | }
38 |
39 | @Unroll
40 | def "should not compile without #dir"() {
41 | setup:
42 | assert new File(projectDir.root, dir).deleteDir()
43 | when:
44 | executeGradle(GATLING_CLASSES_TASK_NAME)
45 | then:
46 | def e = thrown(UnexpectedBuildFailure)
47 | and:
48 | e.buildResult.output.contains(message)
49 | where:
50 | layout || dir || message
51 | 'gradle' | 'src/main' | "TestUtils.java:5: error: cannot find symbol"
52 | 'gradle' | 'src/test' | "not found: value TestUtils"
53 | }
54 |
55 | def "should not compile without required dependencies"() {
56 | given:
57 | buildFile.text = """
58 | plugins { id 'com.github.lkishalmi.gatling' }
59 | repositories { jcenter() }
60 | """
61 | when:
62 | executeGradle(GATLING_CLASSES_TASK_NAME)
63 | then:
64 | def e = thrown(UnexpectedBuildFailure)
65 | and:
66 | e.buildResult.output.contains("object lang is not a member of package org.apache.commons")
67 | }
68 |
69 | def "should not compile with main and test output excluded"() {
70 | given:
71 | buildFile << """
72 | gatling {
73 | includeMainOutput = false
74 | includeTestOutput = false
75 | }
76 | """
77 | when:
78 | executeGradle(GATLING_CLASSES_TASK_NAME)
79 | then:
80 | def e = thrown(UnexpectedBuildFailure)
81 | and:
82 | e.buildResult.output.contains("object MainUtils is not a member of package computerdatabase")
83 | }
84 |
85 | def "should not compile with test output excluded"() {
86 | given:
87 | buildFile << "gatling { includeTestOutput = false }"
88 | when:
89 | executeGradle(GATLING_CLASSES_TASK_NAME)
90 | then:
91 | def e = thrown(UnexpectedBuildFailure)
92 | and:
93 | e.buildResult.output.contains("not found: value TestUtils")
94 | }
95 | }
96 |
--------------------------------------------------------------------------------
/src/test/groovy/functional/WhenRunFailingSimulationSpec.groovy:
--------------------------------------------------------------------------------
1 | package functional
2 |
3 | import helper.GatlingFuncSpec
4 | import org.gradle.testkit.runner.UnexpectedBuildFailure
5 |
6 | import static com.github.lkishalmi.gradle.gatling.GatlingPlugin.GATLING_RUN_TASK_NAME
7 | import static org.gradle.testkit.runner.TaskOutcome.FAILED
8 | import static org.gradle.testkit.runner.TaskOutcome.SUCCESS
9 |
10 | class WhenRunFailingSimulationSpec extends GatlingFuncSpec {
11 |
12 | def setup() {
13 | prepareTest()
14 | }
15 |
16 | def "should execute all simulations even if one fails because of gatling assertions"() {
17 | given:
18 | buildFile << """
19 | gatling {
20 | simulations = {
21 | include 'computerdatabase/AFailedSimulation.scala'
22 | include 'computerdatabase/BasicSimulation.scala'
23 | }
24 | }
25 | """
26 | and: "add incorrect simulation"
27 | new File(srcDir, "computerdatabase/AFailedSimulation.scala").text = """
28 | package computerdatabase
29 | import io.gatling.core.Predef._
30 | import io.gatling.http.Predef._
31 | class AFailedSimulation extends Simulation {
32 | val httpConf = http.baseUrl("http://qwe.asd.io")
33 | val scn = scenario("Scenario Name").exec(http("request_1").get("/"))
34 | setUp(scn.inject(atOnceUsers(1)).protocols(httpConf)).assertions(
35 | global.successfulRequests.percent.gt(99)
36 | )
37 | }
38 | """
39 | when:
40 | executeGradle(GATLING_RUN_TASK_NAME)
41 | then:
42 | UnexpectedBuildFailure ex = thrown(UnexpectedBuildFailure)
43 | ex.buildResult.task(":$GATLING_RUN_TASK_NAME").outcome == FAILED
44 | and: "only single simulation reported as failed"
45 | ex.buildResult.output.readLines().any {
46 | it.endsWith("There're failed simulations: computerdatabase.AFailedSimulation")
47 | }
48 | and: "all simulations were run"
49 | with(new File(buildDir, "reports/gatling")) { reports ->
50 | reports.exists() && reports.listFiles().size() == 2
51 | reports.listFiles().find { it.name.startsWith("basicsimulation") } != null
52 | reports.listFiles().find { it.name.startsWith("afailedsimulation") } != null
53 | new File(reports.listFiles().find { it.name.startsWith("afailedsimulation") }, "simulation.log").text.contains("UnknownHostException: qwe.asd.io")
54 | }
55 | }
56 |
57 | def "should ignore if simulation without assertions fails with HTTP requests"() {
58 | given:
59 | buildFile << """
60 | gatling {
61 | simulations = {
62 | include 'computerdatabase/AFailedSimulation.scala'
63 | include 'computerdatabase/BasicSimulation.scala'
64 | }
65 | }
66 | """
67 | and: "add incorrect simulation"
68 | new File(srcDir, "computerdatabase/AFailedSimulation.scala").text = """
69 | package computerdatabase
70 | import io.gatling.core.Predef._
71 | import io.gatling.http.Predef._
72 | class AFailedSimulation extends Simulation {
73 | val httpConf = http.baseUrl("http://qwe.asd.io")
74 | val scn = scenario("Scenario Name").exec(http("request_1").get("/"))
75 | setUp(scn.inject(atOnceUsers(1)).protocols(httpConf))
76 | }
77 | """
78 | when:
79 | def buildResult = executeGradle(GATLING_RUN_TASK_NAME)
80 | then:
81 | buildResult.task(":$GATLING_RUN_TASK_NAME").outcome == SUCCESS
82 | and:
83 | with(new File(buildDir, "reports/gatling")) { reports ->
84 | reports.exists() && reports.listFiles().size() == 2
85 | reports.listFiles().find { it.name.startsWith("basicsimulation") } != null
86 | reports.listFiles().find { it.name.startsWith("afailedsimulation") } != null
87 | new File(reports.listFiles().find { it.name.startsWith("afailedsimulation") }, "simulation.log").text.contains("UnknownHostException: qwe.asd.io")
88 | }
89 | }
90 |
91 | def "should execute all simulations even if one fails because of gatling runtime"() {
92 | given:
93 | buildFile << """
94 | gatling {
95 | simulations = {
96 | include 'computerdatabase/BasicSimulation.scala'
97 | include 'computerdatabase/AFailedSimulation.scala'
98 | }
99 | }
100 | """
101 | and: "add incorrect simulation"
102 | new File(srcDir, "computerdatabase/AFailedSimulation.scala").text = """
103 | package computerdatabase
104 | import io.gatling.core.Predef._
105 | import io.gatling.http.Predef._
106 | class AFailedSimulation extends Simulation {}
107 | """
108 | when:
109 | executeGradle(GATLING_RUN_TASK_NAME)
110 | then:
111 | UnexpectedBuildFailure ex = thrown(UnexpectedBuildFailure)
112 | ex.buildResult.task(":$GATLING_RUN_TASK_NAME").outcome == FAILED
113 | and: "only single simulation reported as failed"
114 | ex.buildResult.output.readLines().any {
115 | it.endsWith("There're failed simulations: computerdatabase.AFailedSimulation")
116 | }
117 | and:
118 | with(new File(buildDir, "reports/gatling")) { reports ->
119 | reports.exists() && reports.listFiles().size() == 1
120 | reports.listFiles().find { it.name.startsWith("basicsimulation") } != null
121 | }
122 | }
123 | }
124 |
--------------------------------------------------------------------------------
/src/test/groovy/functional/WhenRunSimulationSpec.groovy:
--------------------------------------------------------------------------------
1 | package functional
2 |
3 | import helper.GatlingFuncSpec
4 | import org.gradle.testkit.runner.BuildResult
5 |
6 | import static com.github.lkishalmi.gradle.gatling.GatlingPlugin.GATLING_RUN_TASK_NAME
7 | import static org.gradle.testkit.runner.TaskOutcome.SUCCESS
8 | import static org.gradle.testkit.runner.TaskOutcome.UP_TO_DATE
9 |
10 | class WhenRunSimulationSpec extends GatlingFuncSpec {
11 |
12 | def "should execute all simulations by default"() {
13 | setup:
14 | prepareTest()
15 | when:
16 | BuildResult result = executeGradle(GATLING_RUN_TASK_NAME)
17 | then: "default tasks were executed successfully"
18 | result.task(":$GATLING_RUN_TASK_NAME").outcome == SUCCESS
19 | result.task(":gatlingClasses").outcome == SUCCESS
20 | and: "all simulations were run"
21 | def reports = new File(buildDir, "reports/gatling")
22 | reports.exists() && reports.listFiles().size() == 2
23 | and: "logs doesn't contain INFO"
24 | !result.output.split().any { it.contains("INFO") }
25 | }
26 |
27 | def "should execute only #simulation when initiated by rule"() {
28 | setup:
29 | prepareTest()
30 | when:
31 | BuildResult result = executeGradle("$GATLING_RUN_TASK_NAME-computerdatabase.BasicSimulation")
32 | then: "custom task was run successfully"
33 | result.task(":$GATLING_RUN_TASK_NAME-computerdatabase.BasicSimulation").outcome == SUCCESS
34 | and: "only one simulation was executed"
35 | new File(buildDir, "reports/gatling").listFiles().size() == 1
36 | and: "logs doesn't contain INFO"
37 | !result.output.split().any { it.contains("INFO") }
38 | }
39 |
40 | def "should allow Gatling config override"() {
41 | given:
42 | prepareTest()
43 | and: "override config by disabling reports"
44 | new File(new File(projectDir.root, "src/gatling/resources"), "gatling.conf") << """
45 | gatling.charting.noReports = true
46 | """
47 | when:
48 | BuildResult result = executeGradle(GATLING_RUN_TASK_NAME)
49 | then:
50 | result.task(":$GATLING_RUN_TASK_NAME").outcome == SUCCESS
51 | and: "no reports generated"
52 | with(new File(buildDir, "reports/gatling").listFiles()) { reports ->
53 | reports.size() == 2
54 | reports.find { it.name.startsWith("basicsimulation") } != null
55 | reports.find { it.name.startsWith("basicsimulation") }.listFiles().collect { it.name } == ["simulation.log"]
56 | reports.find { it.name.startsWith("advancedsimulationstep03") } != null
57 | reports.find { it.name.startsWith("advancedsimulationstep03") }.listFiles().collect { it.name } == ["simulation.log"]
58 |
59 | }
60 | }
61 |
62 | def "should not fail when layout is incorrect"() {
63 | setup:
64 | prepareTest(null)
65 | when:
66 | BuildResult result = executeGradle(GATLING_RUN_TASK_NAME)
67 | then: "default tasks were executed successfully"
68 | result.task(":$GATLING_RUN_TASK_NAME").outcome == SUCCESS
69 | result.task(":gatlingClasses").outcome == UP_TO_DATE
70 | and: "no simulations compiled"
71 | !new File(buildDir, "classes/gatling").exists()
72 | and: "no simulations run"
73 | with(new File(buildDir, "reports/gatling")) {
74 | it.exists()
75 | it.list().size() == 0
76 | }
77 | }
78 |
79 | def "should not run gatling if no changes to source code"() {
80 | given:
81 | prepareTest()
82 | buildFile << """
83 | gatling { simulations = { include 'computerdatabase/BasicSimulation.scala' } }
84 | """
85 | when: '1st time'
86 | BuildResult result = executeGradle("$GATLING_RUN_TASK_NAME")
87 | then:
88 | result.task(":compileGatlingScala").outcome == SUCCESS
89 | result.task(":$GATLING_RUN_TASK_NAME").outcome == SUCCESS
90 |
91 | when: '2nd time no changes'
92 | result = executeGradle("$GATLING_RUN_TASK_NAME")
93 | then:
94 | result.task(":compileGatlingScala").outcome == UP_TO_DATE
95 | result.task(":$GATLING_RUN_TASK_NAME").outcome == UP_TO_DATE
96 |
97 | when: '3r time with changes'
98 | new File(new File(srcDir, "computerdatabase"), "BasicSimulation.scala") << """
99 | case class MyClz(str: String) // some fake code to change source file
100 | """
101 | result = executeGradle("$GATLING_RUN_TASK_NAME")
102 | then:
103 | result.task(":compileGatlingScala").outcome == SUCCESS
104 | result.task(":$GATLING_RUN_TASK_NAME").outcome == SUCCESS
105 | }
106 | }
107 |
--------------------------------------------------------------------------------
/src/test/groovy/functional/WhenRunSimulationSysPropsJvmArgsSpec.groovy:
--------------------------------------------------------------------------------
1 | package functional
2 |
3 | import com.github.lkishalmi.gradle.gatling.GatlingPluginExtension
4 | import helper.GatlingDebug
5 | import helper.GatlingFuncSpec
6 | import org.gradle.testkit.runner.BuildResult
7 | import org.junit.Rule
8 | import org.junit.contrib.java.lang.system.EnvironmentVariables
9 | import org.junit.contrib.java.lang.system.RestoreSystemProperties
10 |
11 | import static com.github.lkishalmi.gradle.gatling.GatlingPlugin.GATLING_RUN_TASK_NAME
12 |
13 | class WhenRunSimulationSysPropsJvmArgsSpec extends GatlingFuncSpec {
14 |
15 | @Rule
16 | public final RestoreSystemProperties restoreSystemProperties = new RestoreSystemProperties()
17 |
18 | @Rule
19 | public final EnvironmentVariables environmentVariables = new EnvironmentVariables()
20 |
21 | def setup() {
22 | prepareTest("/gatling-debug")
23 | new File(new File(projectDir.root, "src/gatling/resources"), "gatling.conf").text = "gatling.data.writers = []"
24 | }
25 |
26 | def "should set memory limits from jvmArgs of gatling extension"() {
27 | when: "default Xmx from gatling extension"
28 | BuildResult result = executeGradle(GATLING_RUN_TASK_NAME)
29 | then:
30 | with(new GatlingDebug(result)) {
31 | heap.max == 1024 * 1024 * 1024// 1GB
32 | }
33 |
34 | when: "override via gatling extension"
35 | buildFile << """
36 | gatling {
37 | jvmArgs = ['-Xms32m']
38 | }
39 | """
40 | and:
41 | result = executeGradle("--rerun-tasks", GATLING_RUN_TASK_NAME)
42 | then:
43 | with(new GatlingDebug(result)) {
44 | heap.min == 32 * 1024 * 1024
45 | }
46 | }
47 |
48 | def "should configure jvmArgs from extension"() {
49 | when: "default jvmArgs from gatling extension"
50 | BuildResult result = executeGradle(GATLING_RUN_TASK_NAME)
51 | then:
52 | with(new GatlingDebug(result)) {
53 | jvmArgs.sort() == GatlingPluginExtension.DEFAULT_JVM_ARGS.findAll { it.startsWith("-X") }.sort()
54 | }
55 |
56 | when: "override via gatling extension"
57 | buildFile << """
58 | gatling {
59 | jvmArgs = ['-Xms32m', '-XX:+UseG1GC']
60 | }
61 | """
62 | and:
63 | result = executeGradle("--rerun-tasks", GATLING_RUN_TASK_NAME)
64 | then:
65 | with(new GatlingDebug(result)) {
66 | jvmArgs.sort() == ['-Xms32m', '-XX:+UseG1GC'].sort()
67 | }
68 | }
69 |
70 | def "should override jvmArgs from gatlingRun properties"() {
71 | when: "override via gatlingRun"
72 | buildFile << """
73 | gatling {
74 | jvmArgs = ['-Xms32m', '-XX:+AggressiveOpts']
75 | }
76 | gatlingRun {
77 | jvmArgs = ['-Xms128m', '-XX:+UseG1GC']
78 | }
79 | """
80 | and:
81 | def result = executeGradle(GATLING_RUN_TASK_NAME)
82 | then:
83 | with(new GatlingDebug(result)) {
84 | jvmArgs.sort() == ['-Xms128m', '-XX:+UseG1GC'].sort()
85 | }
86 | }
87 |
88 | def "should configure system properties from extension"() {
89 | when: "defalts from extension"
90 | def result = executeGradle(GATLING_RUN_TASK_NAME)
91 | then:
92 | with(new GatlingDebug(result)) {
93 | systemProperties.keySet().intersect(GatlingPluginExtension.DEFAULT_SYSTEM_PROPS.keySet()).size() == GatlingPluginExtension.DEFAULT_SYSTEM_PROPS.size()
94 | }
95 |
96 | when: "override via extension"
97 | buildFile << """
98 | gatling {
99 | systemProperties = ['gradle_gatling_1': 'aaa', 'gradle_gatling_2' : 'bbb']
100 | }
101 | """
102 | and:
103 | result = executeGradle("--rerun-tasks", GATLING_RUN_TASK_NAME)
104 | then:
105 | with(new GatlingDebug(result)) {
106 | systemProperties.keySet().findAll { it.startsWith("gradle_gatling_") } == ['gradle_gatling_1', 'gradle_gatling_2'] as Set
107 | systemProperties["gradle_gatling_1"] == "aaa"
108 | systemProperties["gradle_gatling_2"] == "bbb"
109 |
110 | systemProperties.keySet().intersect(GatlingPluginExtension.DEFAULT_SYSTEM_PROPS.keySet()).size() == 0
111 | }
112 | }
113 |
114 | def "should extend system properties from extension"() {
115 | }
116 |
117 | def "should extend system properties from gatlingRun properties"() {
118 | given: "override via gatlingRun"
119 | buildFile << """
120 | gatling {
121 | systemProperties = ['gradle_gatling_1': 'aaa', 'gradle_gatling_2' : 'bbb']
122 | }
123 | gatlingRun {
124 | systemProperties = ['gradle_gatling_2' : 'qwerty', 'gradle_gatling_3' : 'ccc']
125 | }
126 | """
127 | when:
128 | def result = executeGradle(GATLING_RUN_TASK_NAME)
129 | then:
130 | with(new GatlingDebug(result)) {
131 | systemProperties.keySet().findAll { it.startsWith("gradle_gatling_") } == ['gradle_gatling_2', 'gradle_gatling_3'] as Set
132 | systemProperties["gradle_gatling_2"] == "qwerty"
133 | }
134 | }
135 |
136 | def "should pass env vars upstream"() {
137 | given:
138 | environmentVariables.set("GRADLE_GATLING_ENV_UPSTREAM", "env_upstream_value")
139 | when:
140 | def result = executeGradle(GATLING_RUN_TASK_NAME)
141 | then:
142 | with(new GatlingDebug(result)) {
143 | env["GRADLE_GATLING_ENV_UPSTREAM"] == "env_upstream_value"
144 | }
145 | }
146 |
147 | def "should pass system properties upstream"() {
148 | given:
149 | System.setProperty("gradle_gatling_sys_upstream", "sys_upstream_value")
150 | when:
151 | def result = executeGradle(GATLING_RUN_TASK_NAME)
152 | then:
153 | with(new GatlingDebug(result)) {
154 | systemProperties["gradle_gatling_sys_upstream"] == "sys_upstream_value"
155 | }
156 | }
157 | }
158 |
--------------------------------------------------------------------------------
/src/test/groovy/helper/GatlingDebug.groovy:
--------------------------------------------------------------------------------
1 | package helper
2 |
3 | import com.github.lkishalmi.gradle.gatling.GatlingPlugin
4 | import groovy.json.JsonSlurper
5 | import org.gradle.testkit.runner.BuildResult
6 | import org.gradle.testkit.runner.TaskOutcome
7 |
8 | class GatlingDebug {
9 |
10 | Map systemProperties
11 | Map env
12 |
13 | List jvmArgs
14 | List argv
15 |
16 | Map heap
17 |
18 | GatlingDebug(BuildResult buildResult) {
19 | assert buildResult.task(":$GatlingPlugin.GATLING_RUN_TASK_NAME").outcome == TaskOutcome.SUCCESS
20 |
21 | def lines = buildResult.output.readLines().findAll { it.startsWith("@@@@") }
22 | assert lines.size() == 4
23 |
24 | def jsonSlurper = new JsonSlurper()
25 |
26 | this.heap = jsonSlurper.parseText(lines.find { it.startsWith("@@@@.heap") } - "@@@@.heap ")
27 | this.jvmArgs = jsonSlurper.parseText(lines.find { it.startsWith("@@@@.jvm") } - "@@@@.jvm ")
28 | this.systemProperties = jsonSlurper.parseText((lines.find { it.startsWith("@@@@.sys") } - "@@@@.sys "))
29 | this.env = jsonSlurper.parseText((lines.find { it.startsWith("@@@@.env") } - "@@@@.env "))
30 |
31 | this.argv = this.systemProperties["sun.java.command"].split("\\s") as List
32 | }
33 | }
34 |
--------------------------------------------------------------------------------
/src/test/groovy/helper/GatlingFuncSpec.groovy:
--------------------------------------------------------------------------------
1 | package helper
2 |
3 | import org.gradle.testkit.runner.BuildResult
4 | import org.gradle.testkit.runner.GradleRunner
5 |
6 | abstract class GatlingFuncSpec extends GatlingSpec {
7 |
8 | static def GATLING_HOST_NAME_SYS_PROP = "-Dgatling.hostName=HTTP://COMPUTER-DATABASE.GATLING.IO"
9 |
10 | void prepareTest(String fixtureDir = "/gradle-layout") {
11 | createBuildFolder(fixtureDir)
12 | generateBuildScripts()
13 | }
14 |
15 | BuildResult executeGradle(String... gradleArgs) {
16 | GradleRunner.create().forwardOutput()
17 | .withProjectDir(projectDir.getRoot())
18 | .withArguments(["--stacktrace", GATLING_HOST_NAME_SYS_PROP] + (gradleArgs as List))
19 | .withPluginClasspath()
20 | .withDebug(true)
21 | .build()
22 | }
23 | }
24 |
--------------------------------------------------------------------------------
/src/test/groovy/helper/GatlingSpec.groovy:
--------------------------------------------------------------------------------
1 | package helper
2 |
3 | import org.junit.Rule
4 | import org.junit.rules.TemporaryFolder
5 | import spock.lang.Specification
6 |
7 | import static org.apache.commons.io.FileUtils.copyDirectory
8 |
9 | abstract class GatlingSpec extends Specification {
10 | @Rule
11 | public final TemporaryFolder projectDir = new TemporaryFolder()
12 |
13 | File srcDir
14 |
15 | File buildDir
16 |
17 | File buildFile
18 |
19 | def createBuildFolder(String fixtureDir) {
20 | if (fixtureDir) {
21 | copyDirectory(new File(this.class.getResource(fixtureDir).file), projectDir.root)
22 | }
23 | srcDir = new File(projectDir.root, "src/gatling/simulations")
24 | buildDir = new File(projectDir.root, "build")
25 | }
26 |
27 | def generateBuildScripts() {
28 | buildFile = projectDir.newFile("build.gradle")
29 | buildFile.text = """
30 | plugins { id 'com.github.lkishalmi.gatling' }
31 | repositories { jcenter() }
32 | dependencies { gatling group: 'commons-lang', name: 'commons-lang', version: '2.6' }
33 | """
34 | }
35 | }
36 |
--------------------------------------------------------------------------------
/src/test/groovy/helper/GatlingUnitSpec.groovy:
--------------------------------------------------------------------------------
1 | package helper
2 |
3 | import com.github.lkishalmi.gradle.gatling.GatlingPluginExtension
4 | import com.github.lkishalmi.gradle.gatling.GatlingRunTask
5 | import org.gradle.api.Project
6 | import org.gradle.testfixtures.ProjectBuilder
7 |
8 | import static com.github.lkishalmi.gradle.gatling.GatlingPlugin.GATLING_RUN_TASK_NAME
9 |
10 | abstract class GatlingUnitSpec extends GatlingSpec {
11 | Project project
12 |
13 | GatlingPluginExtension gatlingExt
14 |
15 | GatlingRunTask gatlingRunTask
16 |
17 | def setup() {
18 | createBuildFolder("/gradle-layout")
19 |
20 | project = ProjectBuilder.builder().withProjectDir(projectDir.root).build()
21 | project.pluginManager.apply 'com.github.lkishalmi.gatling'
22 |
23 | gatlingExt = project.extensions.getByType(GatlingPluginExtension)
24 | gatlingRunTask = project.tasks.getByName(GATLING_RUN_TASK_NAME) as GatlingRunTask
25 | }
26 |
27 | }
28 |
--------------------------------------------------------------------------------
/src/test/groovy/unit/GatlingPluginTest.groovy:
--------------------------------------------------------------------------------
1 | package unit
2 |
3 | import com.github.lkishalmi.gradle.gatling.GatlingPluginExtension
4 | import com.github.lkishalmi.gradle.gatling.GatlingRunTask
5 | import com.github.lkishalmi.gradle.gatling.LogbackConfigTaskAction
6 | import helper.GatlingUnitSpec
7 | import org.gradle.language.jvm.tasks.ProcessResources
8 |
9 | class GatlingPluginTest extends GatlingUnitSpec {
10 |
11 | def "should create gatling configurations"() {
12 | expect:
13 | ['gatling', 'gatlingCompile', 'gatlingRuntime', 'gatlingImplementation', 'gatlingRuntimeOnly'].every {
14 | project.configurations.getByName(it) != null
15 | }
16 | }
17 |
18 | def "should create gatling extension for project "() {
19 | expect:
20 | with(gatlingExt) {
21 | it instanceof GatlingPluginExtension
22 | it.simulations == DEFAULT_SIMULATIONS
23 | it.jvmArgs == DEFAULT_JVM_ARGS
24 | it.systemProperties == DEFAULT_SYSTEM_PROPS
25 | it.logLevel == "WARN"
26 | }
27 | }
28 |
29 | def "should add gatling dependencies with default version"() {
30 | when:
31 | project.evaluate()
32 | then:
33 | project.configurations.getByName("gatling").allDependencies.find {
34 | it.name == "gatling-charts-highcharts" && it.version == GatlingPluginExtension.GATLING_TOOL_VERSION
35 | }
36 | project.configurations.getByName("gatlingImplementation").allDependencies.find {
37 | it.name == "scala-library" && it.version == GatlingPluginExtension.SCALA_VERSION
38 | }
39 | project.configurations.getByName("implementation").allDependencies.find {
40 | it.name == "scala-library" && it.version == GatlingPluginExtension.SCALA_VERSION
41 | }
42 | }
43 |
44 | def "should allow overriding gatling version via extension"() {
45 | when:
46 | project.gatling { toolVersion = '3.0.0-RC1' }
47 | and:
48 | project.evaluate()
49 | then:
50 | project.configurations.getByName("gatling").allDependencies.find {
51 | it.name == "gatling-charts-highcharts" && it.version == "3.0.0-RC1"
52 | }
53 | }
54 |
55 | def "should allow overriding scala version via extension"() {
56 | when:
57 | project.gatling { scalaVersion = '2.11.3' }
58 | and:
59 | project.evaluate()
60 | then:
61 | project.configurations.getByName("gatlingImplementation").allDependencies.find {
62 | it.name == "scala-library" && it.version == "2.11.3"
63 | }
64 | project.configurations.getByName("implementation").allDependencies.find {
65 | it.name == "scala-library" && it.version == "2.11.3"
66 | }
67 | }
68 |
69 | def "should create gatlingRun task"() {
70 | expect:
71 | with(gatlingRunTask) {
72 | it instanceof GatlingRunTask
73 | it.simulations == null
74 | it.jvmArgs == null
75 | it.systemProperties == null
76 | }
77 | }
78 |
79 | def "should create processGatlingResources task"() {
80 | expect:
81 | with(project.tasks.getByName("processGatlingResources")) {
82 | it instanceof ProcessResources
83 | it != null
84 | it.actions.find { it.action instanceof LogbackConfigTaskAction } != null
85 | }
86 | }
87 | }
88 |
--------------------------------------------------------------------------------
/src/test/groovy/unit/GatlingRunTaskTest.groovy:
--------------------------------------------------------------------------------
1 | package unit
2 |
3 | import com.github.lkishalmi.gradle.gatling.GatlingPluginExtension
4 | import helper.GatlingUnitSpec
5 | import org.codehaus.groovy.runtime.typehandling.GroovyCastException
6 | import spock.lang.Unroll
7 |
8 | import static com.github.lkishalmi.gradle.gatling.GatlingPluginExtension.SIMULATIONS_DIR
9 | import static org.apache.commons.io.FileUtils.copyFileToDirectory
10 | import static org.apache.commons.io.FileUtils.moveFileToDirectory
11 |
12 | class GatlingRunTaskTest extends GatlingUnitSpec {
13 |
14 | def "should resolve simulations using default filter"() {
15 | when:
16 | def gatlingRunSimulations = gatlingRunTask.simulationFilesToFQN()
17 | then:
18 | gatlingRunSimulations.size() == 2
19 | and:
20 | "computerdatabase.advanced.AdvancedSimulationStep03" in gatlingRunSimulations
21 | and:
22 | "computerdatabase.BasicSimulation" in gatlingRunSimulations
23 | }
24 |
25 | def "should resolve simulations using custom filter"() {
26 | given:
27 | project.gatling.simulations = { include "**/*AdvancedSimulation*" }
28 | when:
29 | def gatlingRunSimulations = gatlingRunTask.simulationFilesToFQN()
30 | then:
31 | gatlingRunSimulations == ["computerdatabase.advanced.AdvancedSimulationStep03"]
32 | }
33 |
34 | def "should resolve simulations using gatlingRun filter"() {
35 | given:
36 | project.gatling.simulations = GatlingPluginExtension.DEFAULT_SIMULATIONS
37 | and:
38 | project.gatlingRun.simulations = { include "**/*AdvancedSimulation*" }
39 | when:
40 | def gatlingRunSimulations = gatlingRunTask.simulationFilesToFQN()
41 | then:
42 | gatlingRunSimulations == ["computerdatabase.advanced.AdvancedSimulationStep03"]
43 | }
44 |
45 | @Unroll
46 | def "should fail if extension filter is not a closure but #val"() {
47 | when:
48 | project.gatling.simulations = val
49 | then:
50 | def ex = thrown(GroovyCastException)
51 | ex.message.contains(val.toString())
52 | where:
53 | val << ["", "qwerty", ["1", "2"]]
54 | }
55 |
56 | @Unroll
57 | def "should fail if gatlingRun filter not a closure but #val"() {
58 | when:
59 | project.gatlingRun.simulations = val
60 | then:
61 | def ex = thrown(GroovyCastException)
62 | ex.message.contains(val.toString())
63 | where:
64 | val << ["", "qwerty", ["1", "2"]]
65 | }
66 |
67 | def "should override simulations dirs via sourceSet"() {
68 | given:
69 | def overridenSrc = "test/gatling/scala"
70 |
71 | when: 'using source dirs without simulations'
72 | project.sourceSets {
73 | gatling.scala.srcDirs = [overridenSrc]
74 | }
75 | then:
76 | gatlingRunTask.simulationFilesToFQN().size() == 0
77 |
78 | when: 'put simulations into overridden source dir'
79 | copyFileToDirectory(new File(projectDir.root, "${SIMULATIONS_DIR}/computerdatabase/BasicSimulation.scala"),
80 | new File(projectDir.root, "$overridenSrc/computerdatabase"))
81 | then:
82 | gatlingRunTask.simulationFilesToFQN() == ["computerdatabase.BasicSimulation"]
83 | }
84 |
85 | def "should extend simulations dirs via sourceSet"() {
86 | given:
87 | def overridenSrc = "test/gatling/scala"
88 |
89 | when: 'source dirs without simulations'
90 | project.sourceSets {
91 | gatling.scala.srcDir overridenSrc
92 | }
93 | then:
94 | gatlingRunTask.simulationFilesToFQN().size() == 2
95 |
96 | when: "hide one simulation"
97 | moveFileToDirectory(new File(projectDir.root, "${SIMULATIONS_DIR}/computerdatabase/BasicSimulation.scala"),
98 | projectDir.root, true)
99 | then:
100 | gatlingRunTask.simulationFilesToFQN() == ["computerdatabase.advanced.AdvancedSimulationStep03"]
101 |
102 | when: 'move simulation back to overridden source dir'
103 | moveFileToDirectory(new File(projectDir.root, "BasicSimulation.scala"), new File(projectDir.root, "$overridenSrc/computerdatabase"), true)
104 | then:
105 | gatlingRunTask.simulationFilesToFQN().size() == 2
106 | }
107 |
108 | def "should not find missing simulations via gatling extension"() {
109 | when: 'default src layout'
110 | project.gatling.simulations = {
111 | include "computerdatabase/BasicSimulation.scala"
112 | include "some.missing.file"
113 | }
114 | then:
115 | gatlingRunTask.simulationFilesToFQN() == ["computerdatabase.BasicSimulation"]
116 |
117 | when: 'custom src layout'
118 | project.sourceSets {
119 | gatling.scala.srcDirs = ["missing/gatling"]
120 | }
121 | then:
122 | gatlingRunTask.simulationFilesToFQN().size() == 0
123 | }
124 |
125 | def "should not find missing simulations via gatlingRun"() {
126 | when: 'default src layout'
127 | project.gatlingRun.simulations = {
128 | include "computerdatabase/BasicSimulation.scala"
129 | include "some.missing.file"
130 | }
131 | then:
132 | gatlingRunTask.simulationFilesToFQN() == ["computerdatabase.BasicSimulation"]
133 |
134 | when: 'custom src layout'
135 | project.sourceSets {
136 | gatling.scala.srcDirs = ["missing/gatling"]
137 | }
138 | then:
139 | gatlingRunTask.simulationFilesToFQN().size() == 0
140 | }
141 |
142 |
143 | }
144 |
--------------------------------------------------------------------------------
/src/test/resources/gatling-debug/src/gatling/resources/.gitkeep:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/lkishalmi/gradle-gatling-plugin/b9a320dc11ea6d57280ef00c55a42779abe0b928/src/test/resources/gatling-debug/src/gatling/resources/.gitkeep
--------------------------------------------------------------------------------
/src/test/resources/gatling-debug/src/gatling/simulations/GatlingDebugSimulation.scala:
--------------------------------------------------------------------------------
1 | /*
2 | * Copyright 2011-2018 GatlingCorp (https://gatling.io)
3 | *
4 | * Licensed under the Apache License, Version 2.0 (the "License");
5 | * you may not use this file except in compliance with the License.
6 | * You may obtain a copy of the License at
7 | *
8 | * http://www.apache.org/licenses/LICENSE-2.0
9 | *
10 | * Unless required by applicable law or agreed to in writing, software
11 | * distributed under the License is distributed on an "AS IS" BASIS,
12 | * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13 | * See the License for the specific language governing permissions and
14 | * limitations under the License.
15 | */
16 |
17 | import io.gatling.core.Predef._
18 | import io.gatling.http.Predef._
19 | import scala.collection.JavaConverters._
20 | import java.lang.management.ManagementFactory
21 | import java.lang.management.RuntimeMXBean
22 | import java.util
23 |
24 | class GatlingDebugSimulation extends Simulation {
25 |
26 | import org.json4s._
27 | import org.json4s.jackson.JsonMethods._
28 | import org.json4s.jackson.Serialization
29 | import org.json4s.jackson.Serialization._
30 |
31 | implicit val formats = DefaultFormats
32 |
33 | private val heapMemory = ManagementFactory.getMemoryMXBean.getHeapMemoryUsage
34 |
35 | println(s"""@@@@.heap {"min": ${heapMemory.getInit}, "max": ${heapMemory.getMax}}""")
36 |
37 | private val jvmArgs = ManagementFactory.getRuntimeMXBean.getInputArguments
38 |
39 | println(s"@@@@.jvm ${write(jvmArgs.asScala.filterNot(_.startsWith("-D")))}}")
40 |
41 | println(s"@@@@.env ${write(System.getenv.asScala)}}")
42 |
43 | println(s"@@@@.sys ${write(System.getProperties.asScala)}}")
44 |
45 | setUp(scenario("Scenario Name").pause(1).inject(atOnceUsers(0)))
46 | }
47 |
--------------------------------------------------------------------------------
/src/test/resources/gradle-layout/src/gatling/resources/search.csv:
--------------------------------------------------------------------------------
1 | searchCriterion,searchComputerName
2 | Macbook,MacBook Pro
3 | eee,ASUS Eee PC 1005PE
--------------------------------------------------------------------------------
/src/test/resources/gradle-layout/src/gatling/simulations/computerdatabase/BasicSimulation.scala:
--------------------------------------------------------------------------------
1 | /*
2 | * Copyright 2011-2018 GatlingCorp (https://gatling.io)
3 | *
4 | * Licensed under the Apache License, Version 2.0 (the "License");
5 | * you may not use this file except in compliance with the License.
6 | * You may obtain a copy of the License at
7 | *
8 | * http://www.apache.org/licenses/LICENSE-2.0
9 | *
10 | * Unless required by applicable law or agreed to in writing, software
11 | * distributed under the License is distributed on an "AS IS" BASIS,
12 | * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13 | * See the License for the specific language governing permissions and
14 | * limitations under the License.
15 | */
16 |
17 | package computerdatabase
18 | import io.gatling.core.Predef._
19 | import io.gatling.http.Predef._
20 | import scala.concurrent.duration._
21 | import org.apache.commons.lang.StringUtils.lowerCase
22 |
23 | class BasicSimulation extends Simulation {
24 |
25 | val httpConf = http
26 | .baseUrl(lowerCase(TestUtils.hostName())) // Here is the root for all relative URLs
27 | .acceptHeader("text/html,application/xhtml+xml,application/xml;q=0.9,*/*;q=0.8") // Here are the common headers
28 | .doNotTrackHeader("1")
29 | .acceptLanguageHeader("en-US,en;q=0.5")
30 | .acceptEncodingHeader("gzip, deflate")
31 | .userAgentHeader("Mozilla/5.0 (Macintosh; Intel Mac OS X 10.8; rv:16.0) Gecko/20100101 Firefox/16.0")
32 |
33 | val scn = scenario("Scenario Name") // A scenario is a chain of requests and pauses
34 | .exec(http("request_1").get("/"))
35 | .pause(1) // Note that Gatling has recorded real time pauses
36 | .exec(http("request_2").get("/computers?f=macbook"))
37 | .pause(1)
38 | .exec(http("request_3").get("/computers/6"))
39 |
40 | setUp(scn.inject(atOnceUsers(1)).protocols(httpConf)).assertions(
41 | global.successfulRequests.percent.gt(99)
42 | )
43 | }
44 |
--------------------------------------------------------------------------------
/src/test/resources/gradle-layout/src/gatling/simulations/computerdatabase/advanced/AdvancedSimulationStep03.scala:
--------------------------------------------------------------------------------
1 | package computerdatabase.advanced
2 |
3 | import org.apache.commons.lang.StringUtils.lowerCase
4 | import io.gatling.core.Predef._
5 | import io.gatling.http.Predef._
6 | import scala.concurrent.duration._
7 |
8 | class AdvancedSimulationStep03 extends Simulation {
9 |
10 | object Search {
11 |
12 | // We need dynamic data so that all users don't play the same and we end up with a behavior completely different from the live system (caching, JIT...)
13 | // ==> Feeders!
14 |
15 | val feeder = csv("search.csv").random // default is queue, so for this test, we use random to avoid feeder starvation
16 |
17 | val search = exec(http("Home").get("/"))
18 | .pause(1)
19 | .feed(feeder) // every time a user passes here, a record is popped from the feeder and injected into the user's session
20 | .exec(http("Search")
21 | .get("/computers?f=${searchCriterion}") // use session data thanks to Gatling's EL
22 | .check(css("a:contains('${searchComputerName}')", "href"))) // use a CSS selector with an EL, save the result of the capture group
23 | }
24 |
25 | val httpConf = http
26 | .baseUrl(lowerCase(computerdatabase.MainUtils.hostName()))
27 | .acceptHeader("text/html,application/xhtml+xml,application/xml;q=0.9,*/*;q=0.8")
28 | .doNotTrackHeader("1")
29 | .acceptLanguageHeader("en-US,en;q=0.5")
30 | .acceptEncodingHeader("gzip, deflate")
31 | .userAgentHeader("Mozilla/5.0 (Macintosh; Intel Mac OS X 10.8; rv:16.0) Gecko/20100101 Firefox/16.0")
32 |
33 | val users = scenario("Users").exec(Search.search)
34 |
35 | setUp(users.inject(atOnceUsers(1))).protocols(httpConf).assertions(
36 | global.successfulRequests.percent.gt(99)
37 | )
38 | }
39 |
--------------------------------------------------------------------------------
/src/test/resources/gradle-layout/src/main/java/computerdatabase/MainUtils.java:
--------------------------------------------------------------------------------
1 | package computerdatabase;
2 |
3 | public class MainUtils {
4 | public static String hostName() {
5 | return System.getProperty("gatling.hostName");
6 | }
7 | }
--------------------------------------------------------------------------------
/src/test/resources/gradle-layout/src/test/java/computerdatabase/TestUtils.java:
--------------------------------------------------------------------------------
1 | package computerdatabase;
2 |
3 | public class TestUtils {
4 | public static String hostName() {
5 | return MainUtils.hostName();
6 | }
7 | }
--------------------------------------------------------------------------------
/travis_build.sh:
--------------------------------------------------------------------------------
1 | #!/bin/bash
2 | set -ev
3 |
4 | if [ -z "${TRAVIS_TAG}" ]; then
5 | ./gradlew check
6 | fi
7 |
--------------------------------------------------------------------------------