diff --git a/README.md b/README.md index 3e1f0a7e..3df947ca 100644 --- a/README.md +++ b/README.md @@ -91,7 +91,7 @@ As explained previously, the RTE Sampler has 4 types of waiters which work as sy ## Compatibility -The plugin is tested with Jmeter 3.1, 3.2, 3.3, 4.0 and 5.0 in Java 8 and 9. Code base is implemented in Java 1.8, so lower versions of JVM are not supported. +The plugin is tested with Jmeter 3.1, 3.2, 3.3, 4.0 and 5.0 in Java 8 and 11. Code base is implemented in Java 1.8, so lower versions of JVM are not supported. ## Contributing diff --git a/jmeter-plugins-build/Dockerfile b/jmeter-plugins-build/Dockerfile new file mode 100644 index 00000000..b57041de --- /dev/null +++ b/jmeter-plugins-build/Dockerfile @@ -0,0 +1,32 @@ +FROM maven:3.5 + +# install tightvnc and execute-on-vnc script to be able to run UI unit tests with assertjswing +ENV USER="root" \ + PASSWORD="password" + +# we update each time the apt-get to avoid potential issues with cached updates (instead of latest ones) when install is changed https://docs.docker.com/develop/develop-images/dockerfile_best-practices/#apt-get +# additionally we keep installs separated to keep related things together and properly identifiable with the root cause for the requirement (in a preluding comment) +RUN apt-get update \ + && apt-get -y install tightvncserver \ + && mkdir /root/.vnc \ + && echo $PASSWORD | vncpasswd -f > /root/.vnc/passwd \ + && chmod 0600 /root/.vnc/passwd + +# install jdk9 +ENV JAVA_DEBIAN_VERSION="11.0.2+9-3~bpo9+1" +RUN echo 'deb http://ftp.debian.org/debian stretch-backports main' > /etc/apt/sources.list.d/backports.list \ + && apt-get update \ + && apt-get install -y openjdk-11-jdk-headless="$JAVA_DEBIAN_VERSION" + +# install taurus for integration tests with blazemeter and different jmeter versions +ENV TAURUS_VERSION=1.13.3 +RUN apt-get update \ + && apt-get -y install python default-jre-headless python-tk python-pip python-dev libxml2-dev libxslt-dev zlib1g-dev net-tools \ + && pip install bzt==$TAURUS_VERSION + +# install ssh client to be able to release code and use git with ssh +RUN apt-get update \ + && apt-get -y install openssh-client + +COPY scripts/* / +RUN chmod +x /*.sh diff --git a/jmeter-plugins-build/scripts/execute-on-vnc.sh b/jmeter-plugins-build/scripts/execute-on-vnc.sh new file mode 100644 index 00000000..9965e0ca --- /dev/null +++ b/jmeter-plugins-build/scripts/execute-on-vnc.sh @@ -0,0 +1,33 @@ +#/bin/bash +# extracted from https://raw.githubusercontent.com/croesch/beefiles/master/src/execute-on-vnc.sh +# but adding proper exit code for the passed command + +NEW_DISPLAY=42 +DONE="no" + +while [ "$DONE" == "no" ] +do + out=$(xdpyinfo -display :${NEW_DISPLAY} 2>&1) + if [[ "$out" == name* ]] || [[ "$out" == Invalid* ]] + then + # command succeeded; or failed with access error; display exists + (( NEW_DISPLAY+=1 )) + else + # display doesn't exist + DONE="yes" + fi +done + +echo "Using first available display :${NEW_DISPLAY}" + +OLD_DISPLAY=${DISPLAY} +vncserver ":${NEW_DISPLAY}" -localhost -geometry 1600x1200 -depth 16 +export DISPLAY=:${NEW_DISPLAY} + +eval "$@" +EXIT_CODE=$? + +export DISPLAY=${OLD_DISPLAY} +vncserver -kill ":${NEW_DISPLAY}" + +exit $EXIT_CODE \ No newline at end of file diff --git a/jmeter-plugins-build/scripts/release.sh b/jmeter-plugins-build/scripts/release.sh new file mode 100644 index 00000000..3984f359 --- /dev/null +++ b/jmeter-plugins-build/scripts/release.sh @@ -0,0 +1,24 @@ +#/bin/bash +set -ex + +eval $(ssh-agent -s) +/set-git-credentials.sh + +# get a new clean copy of master branch +git checkout master && git reset --hard origin/master + +# we need this to later on use with nextSnapshot due to https://github.com/mojohaus/versions-maven-plugin/issues/207 +ORIGINAL_VERSION=$(mvn -q -Dexec.executable="echo" -Dexec.args='${project.version}' --non-recursive exec:exec) + +# get a new clean copy of production branch +git checkout production && git reset --hard origin/production +git merge master +mvn versions:set -DremoveSnapshot +/execute-on-vnc.sh mvn --batch-mode clean verify +mvn --batch-mode scm:checkin -Dmessage="[RELEASE][skip ci] Fix release version \${project.version}" -Dincludes=pom.xml +mvn --batch-mode scm:check-local-modification -DpushChanges=false +mvn --batch-mode scm:tag -Dtag="\${project.version}" + +git checkout master && git merge production +mvn --batch-mode versions:set -DnextSnapshot=true +mvn --batch-mode scm:checkin -Dmessage="[RELEASE][skip ci] Increase version to next development version \${project.version}" -Dincludes=pom.xml diff --git a/jmeter-plugins-build/scripts/set-git-credentials.sh b/jmeter-plugins-build/scripts/set-git-credentials.sh new file mode 100644 index 00000000..9316da5f --- /dev/null +++ b/jmeter-plugins-build/scripts/set-git-credentials.sh @@ -0,0 +1,11 @@ +#/bin/bash +# this has been extracted from https://docs.gitlab.com/ee/ci/ssh_keys/#verifying-the-ssh-host-keys +set -e + +echo "$SSH_PRIVATE_KEY" | tr -d '\r' | ssh-add - > /dev/null +mkdir -p ~/.ssh +chmod 700 ~/.ssh +echo "$SSH_KNOWN_HOSTS" > ~/.ssh/known_hosts +chmod 644 ~/.ssh/known_hosts +git config --global user.email "gitlab@abstracta.us" +git config --global user.name "Gitlab" diff --git a/pom.xml b/pom.xml index d8c88552..45deb0f4 100644 --- a/pom.xml +++ b/pom.xml @@ -6,7 +6,7 @@ com.blazemeter.jmeter jmeter-bzm-rte jar - 1.1 + 1.1.1 RTEPlugin Sampler as JMeter plugin @@ -106,6 +106,15 @@ + + org.apache.maven.plugins + maven-surefire-plugin + 2.21.0 + + + false + + org.apache.maven.plugins maven-failsafe-plugin @@ -113,6 +122,7 @@ both 10 + false @@ -275,7 +285,6 @@ org.apache.maven.plugins maven-surefire-plugin - 2.21.0 ${jacoco.agent.ut.arg} diff --git a/src/main/java/com/blazemeter/jmeter/rte/sampler/LabelInputRowGUI.java b/src/main/java/com/blazemeter/jmeter/rte/sampler/LabelInputRowGUI.java index 13e0f667..b4b94795 100644 --- a/src/main/java/com/blazemeter/jmeter/rte/sampler/LabelInputRowGUI.java +++ b/src/main/java/com/blazemeter/jmeter/rte/sampler/LabelInputRowGUI.java @@ -6,13 +6,19 @@ public class LabelInputRowGUI extends InputTestElement { - private static final String LABEL = "LabelInputRowGUI.column"; + private static final String LABEL = "LabelInputRowGUI.label"; public LabelInputRowGUI() { } public String getLabel() { - return getPropertyAsString(LABEL, ""); + /* + We keep support for initial incorrect property name to avoid compatibility issues. We should + remove this once the new version gets used by all users (and the probability of someone using + the incorrect property is low) + */ + String val = getPropertyAsString(LABEL, null); + return val == null ? getPropertyAsString("LabelInputRowGUI.column") : val; } public void setLabel(String label) { diff --git a/src/test/java/com/blazemeter/jmeter/rte/core/listeners/RequestListenerIT.java b/src/test/java/com/blazemeter/jmeter/rte/core/listeners/RequestListenerIT.java index 1f8c7321..f99a89b4 100644 --- a/src/test/java/com/blazemeter/jmeter/rte/core/listeners/RequestListenerIT.java +++ b/src/test/java/com/blazemeter/jmeter/rte/core/listeners/RequestListenerIT.java @@ -17,8 +17,9 @@ public abstract class RequestListenerIT> { protected T listener; @Before - public void setup() throws Exception { + public void setup() { result = new SampleResult(); + result.sampleStart(); listener = buildRequestListener(result); } diff --git a/src/test/java/com/blazemeter/jmeter/rte/sampler/gui/InputPanelIT.java b/src/test/java/com/blazemeter/jmeter/rte/sampler/gui/InputPanelIT.java index e66f6e0e..8e7dbf55 100644 --- a/src/test/java/com/blazemeter/jmeter/rte/sampler/gui/InputPanelIT.java +++ b/src/test/java/com/blazemeter/jmeter/rte/sampler/gui/InputPanelIT.java @@ -3,7 +3,6 @@ import static org.assertj.swing.fixture.Containers.showInFrame; import static org.assertj.swing.timing.Pause.pause; import static org.assertj.swing.timing.Timeout.timeout; -import static org.junit.Assert.assertFalse; import com.blazemeter.jmeter.rte.core.CoordInput; import com.blazemeter.jmeter.rte.core.Input; @@ -46,9 +45,12 @@ public class InputPanelIT { private static final long CHANGE_TIMEOUT_MILLIS = 10000; private static final LabelInput USER_LABEL_INPUT = new LabelInput("User", "TESTUSR"); private static final CoordInput PASS_COORD_INPUT = new CoordInput(new Position(1, 2), "TESTPSW"); - private static final String DELETE_BUTTON ="deleteButton"; - private static final String UP_BUTTON ="upButton"; - private static final String DOWN_BUTTON ="downButton"; + private static final CoordInput NAME_INPUT = new CoordInput(new Position(4, 2), "TESTNAME"); + private static final LabelInput EMAIL_INPUT = new LabelInput("eMail", "test@example.com"); + private static final String DELETE_BUTTON = "deleteButton"; + private static final String UP_BUTTON = "upButton"; + private static final String DOWN_BUTTON = "downButton"; + private FrameFixture frame; private InputPanel panel; private JTableFixture inputTable; @@ -100,21 +102,29 @@ public void tearDown() { @Test public void shouldAddLabelInputWhenClickAddLabel() { - clickAddLabel(); - setInputLabelRow(0, USER_LABEL_INPUT); + addFieldByLabel(0, USER_LABEL_INPUT); assertInputs(USER_LABEL_INPUT); } - private void clickAddLabel() { + private void addFieldByLabel(int row, LabelInput input) { frame.button("addLabelInputButton").click(); + awaitAddedRow(row); + setInputRow(row, input, (panel, i) -> setTextField(panel, "fieldLabel", i.getLabel())); } - private void setInputLabelRow(int row, LabelInput input) { - setInputRow(row, input, (panel, i) -> setTextField(panel, "fieldLabel", i.getLabel())); + private void awaitAddedRow(int row) { + pause(new Condition("row " + row + " added") { + + @Override + public boolean test() { + return inputTable.rowCount() > row; + } + + }, CHANGE_TIMEOUT_MILLIS); } private void setInputRow(int row, T input, - BiConsumer fieldSetter) { + BiConsumer fieldSetter) { JTableCellFixture fieldCell = inputTable .cell(TableCell.row(row).column(0)); fieldCell.startEditing(); @@ -168,16 +178,13 @@ private String buildInputsString(List inputsList) { @Test public void shouldAddCoordInputWhenClickAddCoord() { - clickAddCoord(); - setInputCoordRow(0, PASS_COORD_INPUT); + addFieldByCoord(0, PASS_COORD_INPUT); assertInputs(PASS_COORD_INPUT); } - private void clickAddCoord() { + private void addFieldByCoord(int row, CoordInput input) { frame.button("addCoordInputButton").click(); - } - - private void setInputCoordRow(int row, CoordInput input) { + awaitAddedRow(row); setInputRow(row, input, (panel, i) -> { Position position = i.getPosition(); setTextField(panel, "fieldRow", String.valueOf(position.getRow())); @@ -187,26 +194,20 @@ private void setInputCoordRow(int row, CoordInput input) { @Test public void shouldGetCoordAndLabelInputsWhenClickAddCoordAndAddLabel() { - clickAddLabel(); - setInputLabelRow(0, USER_LABEL_INPUT); - clickAddCoord(); - setInputCoordRow(1, PASS_COORD_INPUT); - clickAddCoord(); - CoordInput nameInput = new CoordInput(new Position(4, 2), "TESTNAME"); - setInputCoordRow(2, nameInput); - clickAddLabel(); - LabelInput emailInput = new LabelInput("eMail", "test@example.com"); - setInputLabelRow(3, emailInput); - assertInputs(USER_LABEL_INPUT, PASS_COORD_INPUT, nameInput, emailInput); + int row = 0; + addFieldByLabel(row++, USER_LABEL_INPUT); + addFieldByCoord(row++, PASS_COORD_INPUT); + addFieldByCoord(row++, NAME_INPUT); + addFieldByLabel(row, EMAIL_INPUT); + assertInputs(USER_LABEL_INPUT, PASS_COORD_INPUT, NAME_INPUT, EMAIL_INPUT); } @Test public void shouldNotMoveFirstRowWhenClickUp() { - clickAddLabel(); - setInputLabelRow(0, USER_LABEL_INPUT); - clickAddCoord(); - setInputCoordRow(1, PASS_COORD_INPUT); + int row = 0; + addFieldByLabel(row++, USER_LABEL_INPUT); + addFieldByCoord(row, PASS_COORD_INPUT); inputTable.selectRows(0); clickUpButton(); assertInputs(USER_LABEL_INPUT, PASS_COORD_INPUT); @@ -218,39 +219,32 @@ private void clickUpButton() { @Test public void shouldMoveUpLastRowWhenClickUp() { - clickAddLabel(); - setInputLabelRow(0, USER_LABEL_INPUT); - clickAddCoord(); - setInputCoordRow(1, PASS_COORD_INPUT); - inputTable.selectRows(1); + int row = 0; + addFieldByLabel(row++, USER_LABEL_INPUT); + addFieldByCoord(row, PASS_COORD_INPUT); + inputTable.selectRows(row); clickUpButton(); assertInputs(PASS_COORD_INPUT, USER_LABEL_INPUT); } @Test public void shouldMoveUpSelectedRowsWhenClickUp() { - clickAddLabel(); - setInputLabelRow(0, USER_LABEL_INPUT); - clickAddCoord(); - setInputCoordRow(1, PASS_COORD_INPUT); - clickAddCoord(); - CoordInput nameInput = new CoordInput(new Position(4, 2), "TESTNAME"); - setInputCoordRow(2, nameInput); - clickAddLabel(); - LabelInput emailInput = new LabelInput("eMail", "test@example.com"); - setInputLabelRow(3, emailInput); - inputTable.selectRows(3,1); + int row = 0; + addFieldByLabel(row++, USER_LABEL_INPUT); + addFieldByCoord(row++, PASS_COORD_INPUT); + addFieldByCoord(row++, NAME_INPUT); + addFieldByLabel(row, EMAIL_INPUT); + inputTable.selectRows(3, 1); clickUpButton(); - assertInputs(PASS_COORD_INPUT, USER_LABEL_INPUT, emailInput, nameInput); + assertInputs(PASS_COORD_INPUT, USER_LABEL_INPUT, EMAIL_INPUT, NAME_INPUT); } @Test public void shouldMoveDownFirstRowWhenClickDown() { - clickAddLabel(); - setInputLabelRow(0, USER_LABEL_INPUT); - clickAddCoord(); - setInputCoordRow(1, PASS_COORD_INPUT); - inputTable.selectRows(0); + int row = 0; + addFieldByLabel(row++, USER_LABEL_INPUT); + addFieldByCoord(row, PASS_COORD_INPUT); + inputTable.selectRows(0); clickDownButton(); assertInputs(PASS_COORD_INPUT, USER_LABEL_INPUT); } @@ -261,42 +255,33 @@ private void clickDownButton() { @Test public void shouldNotMoveLastRowWhenClickDown() { - clickAddLabel(); - setInputLabelRow(0, USER_LABEL_INPUT); - clickAddCoord(); - setInputCoordRow(1, PASS_COORD_INPUT); - inputTable.selectRows(1); + int row = 0; + addFieldByLabel(row++, USER_LABEL_INPUT); + addFieldByCoord(row, PASS_COORD_INPUT); + inputTable.selectRows(row); clickDownButton(); assertInputs(USER_LABEL_INPUT, PASS_COORD_INPUT); } @Test public void shouldMoveDownSelectedRowsWhenClickDown() { - clickAddLabel(); - setInputLabelRow(0, USER_LABEL_INPUT); - clickAddCoord(); - setInputCoordRow(1, PASS_COORD_INPUT); - clickAddCoord(); - CoordInput nameInput = new CoordInput(new Position(4, 2), "TESTNAME"); - setInputCoordRow(2, nameInput); - clickAddLabel(); - LabelInput emailInput = new LabelInput("eMail", "test@example.com"); - setInputLabelRow(3, emailInput); - inputTable.selectRows(0,2); + int row = 0; + addFieldByLabel(row++, USER_LABEL_INPUT); + addFieldByCoord(row++, PASS_COORD_INPUT); + addFieldByCoord(row++, NAME_INPUT); + addFieldByLabel(row, EMAIL_INPUT); + inputTable.selectRows(0, 2); clickDownButton(); - assertInputs(PASS_COORD_INPUT, USER_LABEL_INPUT, emailInput, nameInput); + assertInputs(PASS_COORD_INPUT, USER_LABEL_INPUT, EMAIL_INPUT, NAME_INPUT); } @Test public void shouldDeleteSelectedRowsWhenClickDelete() { - clickAddLabel(); - setInputLabelRow(0, USER_LABEL_INPUT); - clickAddCoord(); - setInputCoordRow(1, PASS_COORD_INPUT); - clickAddCoord(); - CoordInput nameInput = new CoordInput(new Position(4, 2), "TESTNAME"); - setInputCoordRow(2, nameInput); - inputTable.selectRows(0,2); + int row = 0; + addFieldByLabel(row++, USER_LABEL_INPUT); + addFieldByCoord(row++, PASS_COORD_INPUT); + addFieldByCoord(row, NAME_INPUT); + inputTable.selectRows(0, 2); clickDeleteButton(); assertInputs(PASS_COORD_INPUT); } @@ -307,8 +292,7 @@ private void clickDeleteButton() { @Test public void shouldNotChangeInputsWhenCopyFromEmptyClipboard() { - clickAddLabel(); - setInputLabelRow(0,USER_LABEL_INPUT); + addFieldByLabel(0, USER_LABEL_INPUT); setTextToClipboard(null); clickAddFromClipboard(); assertInputs(USER_LABEL_INPUT); @@ -335,8 +319,7 @@ public void shouldAddInputsWhenCopyFromClipboard() { @Test public void shouldEnableDeleteButtonWhenAddOneInput() { - clickAddLabel(); - setInputLabelRow(0, USER_LABEL_INPUT); + addFieldByLabel(0, USER_LABEL_INPUT); waitButtonEnabled(DELETE_BUTTON, true); } @@ -351,48 +334,43 @@ public boolean test() { @Test public void shouldDisableDeleteButtonWhenDeleteUniqueInput() { - clickAddLabel(); - setInputLabelRow(0, USER_LABEL_INPUT); + addFieldByLabel(0, USER_LABEL_INPUT); clickDeleteButton(); - waitButtonEnabled(DELETE_BUTTON,false); + waitButtonEnabled(DELETE_BUTTON, false); } @Test public void shouldDisableUpButtonWhenOneInputIsLeft() { - clickAddLabel(); - setInputLabelRow(0, USER_LABEL_INPUT); - clickAddCoord(); - setInputCoordRow(1, PASS_COORD_INPUT); + int row = 0; + addFieldByLabel(row++, USER_LABEL_INPUT); + addFieldByCoord(row, PASS_COORD_INPUT); clickDeleteButton(); - waitButtonEnabled(UP_BUTTON,false); + waitButtonEnabled(UP_BUTTON, false); } @Test public void checkEnableUpButtonWithTwoInputs() { - clickAddLabel(); - setInputLabelRow(0, USER_LABEL_INPUT); - clickAddCoord(); - setInputCoordRow(1, PASS_COORD_INPUT); + int row = 0; + addFieldByLabel(row++, USER_LABEL_INPUT); + addFieldByCoord(row, PASS_COORD_INPUT); waitButtonEnabled(UP_BUTTON, true); } @Test public void shouldEnableDownButtonWhenAddTwoInputs() { - clickAddLabel(); - setInputLabelRow(0, USER_LABEL_INPUT); - clickAddCoord(); - setInputCoordRow(1, PASS_COORD_INPUT); - waitButtonEnabled(DOWN_BUTTON,true); + int row = 0; + addFieldByLabel(row++, USER_LABEL_INPUT); + addFieldByCoord(row, PASS_COORD_INPUT); + waitButtonEnabled(DOWN_BUTTON, true); } @Test public void shouldDisableDownButtonWhenOneInputIsLeft() { - clickAddLabel(); - setInputLabelRow(0, USER_LABEL_INPUT); - clickAddCoord(); - setInputCoordRow(1, PASS_COORD_INPUT); + int row = 0; + addFieldByLabel(row++, USER_LABEL_INPUT); + addFieldByCoord(row, PASS_COORD_INPUT); clickDeleteButton(); - waitButtonEnabled(DOWN_BUTTON,false); + waitButtonEnabled(DOWN_BUTTON, false); } } diff --git a/src/test/resources/jmeter/RTESampler3270.jmx b/src/test/resources/jmeter/RTESampler3270.jmx index a8671a58..5e3b0a1b 100644 --- a/src/test/resources/jmeter/RTESampler3270.jmx +++ b/src/test/resources/jmeter/RTESampler3270.jmx @@ -1,5 +1,5 @@ - + @@ -12,6 +12,31 @@ + + + + userColumn + 1 + = + + + username + testusr + = + + + passwordLabel + Password + = + + + password + testpsw + = + + + + continue @@ -92,9 +117,10 @@ println("server started...") - 2 - 1 + 2 + ${userColumn} testusr + ${username} @@ -129,6 +155,46 @@ println("server started...") + + + + + ${passwordLabel} + ${password} + + + + ENTER + SEND_INPUT + true + 14000 + false + 1 + 1 + 30000 + false + 1000 + 60000 + false + + 30000 + 1 + 1 + + + + + + + Welcome + + + Assertion.response_data + false + 2 + + + diff --git a/src/test/resources/jmeter/RTESampler5250.jmx b/src/test/resources/jmeter/RTESampler5250.jmx index 88d72e5b..dfa67d76 100644 --- a/src/test/resources/jmeter/RTESampler5250.jmx +++ b/src/test/resources/jmeter/RTESampler5250.jmx @@ -1,5 +1,5 @@ - + @@ -12,6 +12,31 @@ + + + + userColumn + 53 + = + + + username + TESTUSR + = + + + passwordLabel + Password + = + + + password + TESTPSW + = + + + + continue @@ -72,14 +97,14 @@ println("server started...") - 6 - 53 + 6 + ${userColumn} TESTUSR + ${username} - - 7 - 53 - TESTPSW + + ${password} + ${passwordLabel} @@ -105,7 +130,7 @@ println("server started...") - IBM i Main Menu + IBM i Main Menu Assertion.response_data diff --git a/src/test/resources/jmeter/testJMeter.yaml b/src/test/resources/jmeter/testJMeter.yaml index c95d0445..248938e8 100644 --- a/src/test/resources/jmeter/testJMeter.yaml +++ b/src/test/resources/jmeter/testJMeter.yaml @@ -2,6 +2,7 @@ modules: jmeter: path: ".jmeter" version: "4.0" + detect-plugins: false properties: log_level: DEBUG user.classpath: lib diff --git a/src/test/resources/jmeter/testJMeterBZ.yaml b/src/test/resources/jmeter/testJMeterBZ.yaml index e0dd1e65..8ae53251 100644 --- a/src/test/resources/jmeter/testJMeterBZ.yaml +++ b/src/test/resources/jmeter/testJMeterBZ.yaml @@ -3,6 +3,7 @@ provisioning: cloud modules: jmeter: version: "4.0" + detect-plugins: false properties: log_level: DEBUG user.classpath: lib diff --git a/src/test/resources/mockito-extensions/org.mockito.plugins.MockMaker b/src/test/resources/mockito-extensions/org.mockito.plugins.MockMaker old mode 100755 new mode 100644