diff --git a/libraries/pom.xml b/libraries/pom.xml index e893572cf9..bf50e699b8 100644 --- a/libraries/pom.xml +++ b/libraries/pom.xml @@ -169,26 +169,31 @@ net.serenity-bdd serenity-core ${serenity.version} + test net.serenity-bdd serenity-junit ${serenity.version} + test net.serenity-bdd serenity-jbehave ${serenity.jbehave.version} + test net.serenity-bdd serenity-rest-assured ${serenity.version} + test net.serenity-bdd serenity-jira-requirements-provider ${serenity.jira.version} + test com.fasterxml.jackson.core @@ -231,17 +236,36 @@ datanucleus-xml 5.0.0-release - - com.zaxxer - HikariCP - 2.6.1 - compile - - - org.postgresql - postgresql - 42.0.0 - + + + org.springframework + spring-web + 4.3.8.RELEASE + + + net.serenity-bdd + serenity-spring + ${serenity.version} + test + + + io.rest-assured + spring-mock-mvc + 3.0.3 + test + + + com.zaxxer + HikariCP + 2.6.1 + compile + + + org.postgresql + postgresql + 42.0.0 + + @@ -261,10 +285,10 @@ 2.5 1.2.0 2.8.5 - 1.2.5-rc.11 + 1.4.0 1.24.0 1.1.3-rc.5 - 1.2.5-rc.6 + 1.4.0 diff --git a/libraries/src/main/java/com/baeldung/serenity/spring/KonamiCodeController.java b/libraries/src/main/java/com/baeldung/serenity/spring/KonamiCodeController.java new file mode 100644 index 0000000000..f8ae66c229 --- /dev/null +++ b/libraries/src/main/java/com/baeldung/serenity/spring/KonamiCodeController.java @@ -0,0 +1,28 @@ +package com.baeldung.serenity.spring; + +import org.springframework.http.MediaType; +import org.springframework.web.bind.annotation.GetMapping; +import org.springframework.web.bind.annotation.RequestMapping; +import org.springframework.web.bind.annotation.RequestParam; +import org.springframework.web.bind.annotation.RestController; + +/** + * @author aiet + */ +@RequestMapping(value = "/konamicode", produces = MediaType.APPLICATION_JSON_UTF8_VALUE) +@RestController +public class KonamiCodeController { + + private final String classicCode = "↑↑↓↓←→←→BA"; + + @GetMapping("/classic") + public String classicCode() { + return classicCode; + } + + @GetMapping("/cheatable") + public boolean cheatCheck(@RequestParam String cheatcode){ + return classicCode.equals(cheatcode); + } + +} diff --git a/libraries/src/main/java/com/baeldung/serenity/spring/KonamiCodeService.java b/libraries/src/main/java/com/baeldung/serenity/spring/KonamiCodeService.java new file mode 100644 index 0000000000..2aa1804ba5 --- /dev/null +++ b/libraries/src/main/java/com/baeldung/serenity/spring/KonamiCodeService.java @@ -0,0 +1,39 @@ +package com.baeldung.serenity.spring; + +import org.springframework.stereotype.Service; + +/** + * refer to Konami Code + */ +@Service +public class KonamiCodeService { + + private String classicCode = "↑↑↓↓←→←→BA"; + + public String getClassicCode() { + return classicCode; + } + + public void alterClassicCode(String newCode) { + classicCode = newCode; + } + + public boolean cheatWith(String cheatcode) { + if ("↑↑↓↓←→←→BA".equals(cheatcode)) { + stageLeft++; + return true; + } + return false; + } + + private int stageLeft = 1; + + public void clearStage() { + stageLeft = 0; + } + + public int stageLeft() { + return stageLeft; + } + +} diff --git a/libraries/src/main/java/com/baeldung/serenity/spring/KonamiCodeServiceInjectionController.java b/libraries/src/main/java/com/baeldung/serenity/spring/KonamiCodeServiceInjectionController.java new file mode 100644 index 0000000000..bb80963aa3 --- /dev/null +++ b/libraries/src/main/java/com/baeldung/serenity/spring/KonamiCodeServiceInjectionController.java @@ -0,0 +1,41 @@ +package com.baeldung.serenity.spring; + +import org.springframework.http.MediaType; +import org.springframework.web.bind.annotation.*; + +/** + * @author aiet + */ +@RequestMapping(value = "/konamicode", produces = MediaType.APPLICATION_JSON_UTF8_VALUE) +@RestController +public class KonamiCodeServiceInjectionController { + + private KonamiCodeService konamiCodeService; + + public KonamiCodeServiceInjectionController(KonamiCodeService konamiCodeService) { + this.konamiCodeService = konamiCodeService; + } + + @PutMapping("/stages") + public void clearStage(@RequestParam String action) { + if ("clear".equals(action)) { + konamiCodeService.clearStage(); + } + } + + @GetMapping("/classic") + public String classicCode() { + return konamiCodeService.getClassicCode(); + } + + @GetMapping("/cheatable") + public boolean cheatCheck(@RequestParam String cheatcode) { + return konamiCodeService.cheatWith(cheatcode); + } + + @GetMapping("/stages") + public int stageLeft() { + return konamiCodeService.stageLeft(); + } + +} diff --git a/libraries/src/test/java/com/baeldung/serenity/spring/KonamCheatClassDirtiesContextTest.java b/libraries/src/test/java/com/baeldung/serenity/spring/KonamCheatClassDirtiesContextTest.java new file mode 100644 index 0000000000..6331b548eb --- /dev/null +++ b/libraries/src/test/java/com/baeldung/serenity/spring/KonamCheatClassDirtiesContextTest.java @@ -0,0 +1,74 @@ +package com.baeldung.serenity.spring; + +import com.baeldung.serenity.spring.steps.KonamiCodeServiceInjectionSteps; +import net.serenitybdd.junit.runners.SerenityRunner; +import net.serenitybdd.junit.spring.integration.SpringIntegrationClassRule; +import net.thucydides.core.annotations.Steps; +import net.thucydides.core.annotations.Title; +import org.junit.ClassRule; +import org.junit.Test; +import org.junit.runner.RunWith; +import org.junit.runners.Suite; +import org.springframework.test.annotation.DirtiesContext; +import org.springframework.test.context.ContextConfiguration; + +import static org.springframework.test.annotation.DirtiesContext.ClassMode.AFTER_CLASS; + +/** + * @author aiet + */ + +@RunWith(Suite.class) +@Suite.SuiteClasses({ + KonamCheatClassDirtiesContextTest.DirtiesContextTest.class, KonamCheatClassDirtiesContextTest.AnotherDirtiesContextTest.class + }) +public class KonamCheatClassDirtiesContextTest { + + @RunWith(SerenityRunner.class) + @ContextConfiguration(classes = KonamiCodeService.class) + public static abstract class Base { + + @Steps KonamiCodeServiceInjectionSteps cheatSteps; + + @ClassRule public static SpringIntegrationClassRule springIntegrationClassRule = new SpringIntegrationClassRule(); + + void hiddenStageShouldBeUnlockedAfterCheating() { + fetchAndCheat(); + cheatSteps.aStageRemains(); + + cheatSteps.letsHack(); + + fetchAndCheat(); + cheatSteps.noStageRemains(); + } + + private void fetchAndCheat() { + cheatSteps.gameStageCleared(); + cheatSteps.fetchLatestCheatcode(); + cheatSteps.cheatWithLatestcode(); + } + + } + + @DirtiesContext(classMode = AFTER_CLASS) + public static class AnotherDirtiesContextTest extends Base { + + @Test + @Title("altering the cheatcode after unlocking would stop others from cheating, not affected by other tests (another)") + public void givenGameStageCleared_whenCheat_thenHiddenStageUnlocked() { + super.hiddenStageShouldBeUnlockedAfterCheating(); + } + } + + @DirtiesContext(classMode = AFTER_CLASS) + public static class DirtiesContextTest extends Base { + + @Test + @Title("altering the cheatcode after unlocking would stop others from cheating, not affected by other tests") + public void givenGameStageCleared_whenCheat_thenHiddenStageUnlocked() { + super.hiddenStageShouldBeUnlockedAfterCheating(); + } + } + + +} diff --git a/libraries/src/test/java/com/baeldung/serenity/spring/KonamCheatWithDirtyActionTest.java b/libraries/src/test/java/com/baeldung/serenity/spring/KonamCheatWithDirtyActionTest.java new file mode 100644 index 0000000000..213e54d557 --- /dev/null +++ b/libraries/src/test/java/com/baeldung/serenity/spring/KonamCheatWithDirtyActionTest.java @@ -0,0 +1,62 @@ +package com.baeldung.serenity.spring; + +import com.baeldung.serenity.spring.steps.KonamiCodeConstructorDependencySteps; +import net.serenitybdd.junit.runners.SerenityRunner; +import net.serenitybdd.junit.spring.integration.SpringIntegrationMethodRule; +import net.thucydides.core.annotations.Title; +import org.junit.Before; +import org.junit.FixMethodOrder; +import org.junit.Rule; +import org.junit.Test; +import org.junit.runner.RunWith; +import org.junit.runners.MethodSorters; +import org.springframework.beans.factory.annotation.Autowired; +import org.springframework.test.annotation.DirtiesContext; +import org.springframework.test.context.ContextConfiguration; + +/** + * @author aiet + */ +@RunWith(SerenityRunner.class) +@FixMethodOrder(MethodSorters.NAME_ASCENDING) +@ContextConfiguration(classes = KonamiCodeService.class) +public class KonamCheatWithDirtyActionTest { + + private KonamiCodeConstructorDependencySteps cheatSteps; + + @Autowired private KonamiCodeService codeService; + + @Before + public void init() { + cheatSteps = new KonamiCodeConstructorDependencySteps(codeService); + } + + @Test + @Title("hidden stage should be unlocked after cheating (run in service with dirty action)") + public void givenGameStageCleared_whenCheat_thenHiddenStageUnlocked() { + fetchCodeAndCheat(); + cheatSteps.aStageRemains(); + } + + @Rule public SpringIntegrationMethodRule springIntegration = new SpringIntegrationMethodRule(); + + @DirtiesContext + @Test + @Title("altering the cheatcode after unlocking would stop others from cheating") + public void givenGameStageCleared_whenCheatAndHack_thenAnotherCheatFail() { + fetchCodeAndCheat(); + cheatSteps.aStageRemains(); + + cheatSteps.letsHack(); + + fetchCodeAndCheat(); + cheatSteps.noStageRemains(); + } + + private void fetchCodeAndCheat() { + cheatSteps.gameStageCleared(); + cheatSteps.fetchLatestCheatcode(); + cheatSteps.cheatWithLatestcode(); + } + +} diff --git a/libraries/src/test/java/com/baeldung/serenity/spring/KonamCheatWithDirtyActionWithImplicitInjectionTest.java b/libraries/src/test/java/com/baeldung/serenity/spring/KonamCheatWithDirtyActionWithImplicitInjectionTest.java new file mode 100644 index 0000000000..76143156bf --- /dev/null +++ b/libraries/src/test/java/com/baeldung/serenity/spring/KonamCheatWithDirtyActionWithImplicitInjectionTest.java @@ -0,0 +1,54 @@ +package com.baeldung.serenity.spring; + +import com.baeldung.serenity.spring.steps.KonamiCodeServiceInjectionSteps; +import net.serenitybdd.junit.runners.SerenityRunner; +import net.serenitybdd.junit.spring.integration.SpringIntegrationMethodRule; +import net.thucydides.core.annotations.Steps; +import net.thucydides.core.annotations.Title; +import org.junit.FixMethodOrder; +import org.junit.Rule; +import org.junit.Test; +import org.junit.runner.RunWith; +import org.junit.runners.MethodSorters; +import org.springframework.test.annotation.DirtiesContext; +import org.springframework.test.context.ContextConfiguration; + +/** + * @author aiet + */ +@RunWith(SerenityRunner.class) +@FixMethodOrder(MethodSorters.NAME_ASCENDING) +@ContextConfiguration(classes = KonamiCodeService.class) +public class KonamCheatWithDirtyActionWithImplicitInjectionTest { + + @Steps private KonamiCodeServiceInjectionSteps cheatSteps; + + @Test + @Title("hidden stage is not unlocked after cheating (cheatcode hacked)") + public void givenGameStageCleared_whenCheat_thenCheatFail() { + fetchCodeAndCheat(); + cheatSteps.noStageRemains(); + } + + private void fetchCodeAndCheat() { + cheatSteps.gameStageCleared(); + cheatSteps.fetchLatestCheatcode(); + cheatSteps.cheatWithLatestcode(); + } + + @Rule public SpringIntegrationMethodRule springIntegration = new SpringIntegrationMethodRule(); + + @DirtiesContext + @Test + @Title("altering the cheatcode after unlocking would stop others from cheating") + public void givenGameStageCleared_whenCheatAndHack_thenAnotherCheatFail() { + fetchCodeAndCheat(); + cheatSteps.aStageRemains(); + + cheatSteps.letsHack(); + + fetchCodeAndCheat(); + cheatSteps.noStageRemains(); + } + +} diff --git a/libraries/src/test/java/com/baeldung/serenity/spring/KonamCheatWithServiceTest.java b/libraries/src/test/java/com/baeldung/serenity/spring/KonamCheatWithServiceTest.java new file mode 100644 index 0000000000..ea59931324 --- /dev/null +++ b/libraries/src/test/java/com/baeldung/serenity/spring/KonamCheatWithServiceTest.java @@ -0,0 +1,27 @@ +package com.baeldung.serenity.spring; + +import com.baeldung.serenity.spring.steps.KonamiCodeServiceInjectionSteps; +import net.serenitybdd.junit.runners.SerenityRunner; +import net.thucydides.core.annotations.Steps; +import net.thucydides.core.annotations.Title; +import org.junit.Test; +import org.junit.runner.RunWith; + +/** + * @author aiet + */ +@RunWith(SerenityRunner.class) +public class KonamCheatWithServiceTest { + + @Steps private KonamiCodeServiceInjectionSteps cheatSteps; + + @Test + @Title("hidden stage should be unlocked after cheating (mockmvc)") + public void givenGameStageCleared_whenCheat_thenHiddenStageUnlocked() { + cheatSteps.gameStageCleared(); + cheatSteps.fetchLatestCheatcode(); + cheatSteps.cheatWithLatestcode(); + cheatSteps.aStageRemains(); + } + +} diff --git a/libraries/src/test/java/com/baeldung/serenity/spring/KonamiCheatWithIntegrationMethodRulesTest.java b/libraries/src/test/java/com/baeldung/serenity/spring/KonamiCheatWithIntegrationMethodRulesTest.java new file mode 100644 index 0000000000..9d19cefba9 --- /dev/null +++ b/libraries/src/test/java/com/baeldung/serenity/spring/KonamiCheatWithIntegrationMethodRulesTest.java @@ -0,0 +1,61 @@ +package com.baeldung.serenity.spring; + +import com.baeldung.serenity.spring.steps.KonamiCheatSteps; +import net.serenitybdd.junit.runners.SerenityRunner; +import net.serenitybdd.junit.spring.integration.SpringIntegrationMethodRule; +import net.thucydides.core.annotations.Steps; +import net.thucydides.core.annotations.Title; +import org.junit.*; +import org.junit.runner.RunWith; +import org.slf4j.Logger; +import org.slf4j.LoggerFactory; +import org.springframework.beans.factory.annotation.Value; +import org.springframework.test.context.ContextConfiguration; + +/** + * Unit test for simple App. + */ +@RunWith(SerenityRunner.class) +@ContextConfiguration(locations = "classpath:konami-cheat-beans.xml") +public class KonamiCheatWithIntegrationMethodRulesTest { + + private static Logger LOG = LoggerFactory.getLogger(KonamiCheatWithIntegrationMethodRulesTest.class); + + @BeforeClass + public static void initClass() { + LOG.info("static chaincode before test class: {}", staticCheatCode); + } + + @AfterClass + public static void destroyClass() { + LOG.info("static chaincode after test class: {}", staticCheatCode); + } + + @Before + public void init() { + staticCheatCode = cheatCode; + LOG.info("cheatcode before test: {}", cheatCode); + } + + @After + public void destroy() { + LOG.info("cheatcode after test: {}", cheatCode); + } + + @Rule public SpringIntegrationMethodRule springMethodIntegration = new SpringIntegrationMethodRule(); + + @Steps private KonamiCheatSteps konamiCheatSteps; + + @Value("#{konami_props['code']}") private String cheatCode; + + private static String staticCheatCode; + + @Test + @Title("hidden stage should be unlocked after cheating (rule integration)") + public void givenGameStageCleared_whenCheat_thenHiddenStageUnlocked() { + konamiCheatSteps.gameStageCleared(); + konamiCheatSteps.cheatWith(cheatCode); + konamiCheatSteps.aStageRemains(); + } + +} diff --git a/libraries/src/test/java/com/baeldung/serenity/spring/KonamiCheatWithIntegrationRunnerTest.java b/libraries/src/test/java/com/baeldung/serenity/spring/KonamiCheatWithIntegrationRunnerTest.java new file mode 100644 index 0000000000..9aa70ddb12 --- /dev/null +++ b/libraries/src/test/java/com/baeldung/serenity/spring/KonamiCheatWithIntegrationRunnerTest.java @@ -0,0 +1,58 @@ +package com.baeldung.serenity.spring; + +import com.baeldung.serenity.spring.steps.KonamiCheatSteps; +import net.serenitybdd.junit.spring.integration.SpringIntegrationSerenityRunner; +import net.thucydides.core.annotations.Steps; +import net.thucydides.core.annotations.Title; +import org.junit.*; +import org.junit.runner.RunWith; +import org.slf4j.Logger; +import org.slf4j.LoggerFactory; +import org.springframework.beans.factory.annotation.Value; +import org.springframework.test.context.ContextConfiguration; + +/** + * Unit test for simple App. + */ +@RunWith(SpringIntegrationSerenityRunner.class) +@ContextConfiguration(locations = "classpath:konami-cheat-beans.xml") +public class KonamiCheatWithIntegrationRunnerTest { + + private static Logger LOG = LoggerFactory.getLogger(KonamiCheatWithIntegrationRunnerTest.class); + + @BeforeClass + public static void initClass() { + LOG.info("static chaincode before test class: {}", staticCheatCode); + } + + @AfterClass + public static void destroyClass() { + LOG.info("static chaincode after test class: {}", staticCheatCode); + } + + @Before + public void init() { + staticCheatCode = cheatCode; + LOG.info("cheatcode before test: {}", cheatCode); + } + + @After + public void destroy() { + LOG.info("cheatcode after test: {}", cheatCode); + } + + @Steps private KonamiCheatSteps konamiCheatSteps; + + @Value("#{konami_props['code']}") private String cheatCode; + + private static String staticCheatCode; + + @Test + @Title("hidden stage should be unlocked after cheating (with integration runner)") + public void givenGameStageCleared_whenCheat_thenHiddenStageUnlocked() { + konamiCheatSteps.gameStageCleared(); + konamiCheatSteps.cheatWith(cheatCode); + konamiCheatSteps.aStageRemains(); + } + +} diff --git a/libraries/src/test/java/com/baeldung/serenity/spring/KonamiCodeMockMvcTest.java b/libraries/src/test/java/com/baeldung/serenity/spring/KonamiCodeMockMvcTest.java new file mode 100644 index 0000000000..2ae6cdcd84 --- /dev/null +++ b/libraries/src/test/java/com/baeldung/serenity/spring/KonamiCodeMockMvcTest.java @@ -0,0 +1,31 @@ +package com.baeldung.serenity.spring; + +import com.baeldung.serenity.spring.steps.KonamiCodeRestSteps; +import io.restassured.module.mockmvc.RestAssuredMockMvc; +import net.serenitybdd.junit.runners.SerenityRunner; +import net.thucydides.core.annotations.Steps; +import org.junit.Before; +import org.junit.Test; +import org.junit.runner.RunWith; + +/** + * @author aiet + */ +@RunWith(SerenityRunner.class) +public class KonamiCodeMockMvcTest { + + @Before + public void init() { + RestAssuredMockMvc.standaloneSetup(new KonamiCodeController()); + } + + @Steps KonamiCodeRestSteps steps; + + @Test + public void givenOfficialClassicCheatcode_whenCheat_ThenTheCodeShouldDoTheTrick() throws Exception { + steps.givenClassicCheatCode(); + steps.whenCheat(); + steps.thenClassicCodeCanDoTheTrick(); + } + +} diff --git a/libraries/src/test/java/com/baeldung/serenity/spring/KonamiCodeTest.java b/libraries/src/test/java/com/baeldung/serenity/spring/KonamiCodeTest.java new file mode 100644 index 0000000000..d2e5fd30f6 --- /dev/null +++ b/libraries/src/test/java/com/baeldung/serenity/spring/KonamiCodeTest.java @@ -0,0 +1,22 @@ +package com.baeldung.serenity.spring; + +import io.restassured.module.mockmvc.RestAssuredMockMvc; +import net.serenitybdd.jbehave.SerenityStory; +import org.jbehave.core.annotations.BeforeStory; +import org.springframework.beans.factory.annotation.Autowired; +import org.springframework.test.context.ContextConfiguration; + +/** + * @author aiet + */ +@ContextConfiguration(classes = { KonamiCodeServiceInjectionController.class, KonamiCodeService.class }) +public class KonamiCodeTest extends SerenityStory { + + @Autowired private KonamiCodeService konamiCodeService; + + @BeforeStory + public void init() { + RestAssuredMockMvc.standaloneSetup(new KonamiCodeServiceInjectionController(konamiCodeService)); + } + +} diff --git a/libraries/src/test/java/com/baeldung/serenity/spring/steps/KonamiCheatSteps.java b/libraries/src/test/java/com/baeldung/serenity/spring/steps/KonamiCheatSteps.java new file mode 100644 index 0000000000..0bb408bda0 --- /dev/null +++ b/libraries/src/test/java/com/baeldung/serenity/spring/steps/KonamiCheatSteps.java @@ -0,0 +1,25 @@ +package com.baeldung.serenity.spring.steps; + +import net.thucydides.core.annotations.Step; + +import static org.junit.Assert.assertEquals; + +/** + * @author aiet + */ +public class KonamiCheatSteps { + + @Step("all stages of the game are cleared") + public void gameStageCleared() { + } + + @Step("input the classic 'Konami Code': {0} ") + public void cheatWith(String cheatcode) { + assertEquals("cheatcode wrong", "↑↑↓↓←→←→BA", cheatcode); + } + + @Step("there is still a stage left") + public void aStageRemains() { + } + +} diff --git a/libraries/src/test/java/com/baeldung/serenity/spring/steps/KonamiCodeConstructorDependencySteps.java b/libraries/src/test/java/com/baeldung/serenity/spring/steps/KonamiCodeConstructorDependencySteps.java new file mode 100644 index 0000000000..2bec25b58f --- /dev/null +++ b/libraries/src/test/java/com/baeldung/serenity/spring/steps/KonamiCodeConstructorDependencySteps.java @@ -0,0 +1,58 @@ +package com.baeldung.serenity.spring.steps; + +import com.baeldung.serenity.spring.KonamiCodeService; +import net.thucydides.core.annotations.Step; +import org.apache.commons.lang3.RandomStringUtils; + +import static org.hamcrest.core.IsEqual.equalTo; +import static org.junit.Assert.*; + +/** + * @author aiet + */ +public class KonamiCodeConstructorDependencySteps { + + private String latestCheatcode; + private boolean cheatSuccess; + + private KonamiCodeService konamiCodeService; + + public KonamiCodeConstructorDependencySteps(KonamiCodeService konamiCodeService) { + this.konamiCodeService = konamiCodeService; + } + + @Step("fetch latest cheat code") + public void fetchLatestCheatcode() { + latestCheatcode = konamiCodeService.getClassicCode(); + } + + @Step("cheat with latest code") + public void cheatWithLatestcode() { + cheatSuccess = konamiCodeService.cheatWith(latestCheatcode); + } + + @Step("all stages of the game are cleared") + public void gameStageCleared() { + konamiCodeService.clearStage(); + } + + @Step("there is still a stage left") + public void aStageRemains() { + assertTrue("cheatcode wrong", cheatSuccess); + assertThat(konamiCodeService.stageLeft(), equalTo(1)); + } + + // @Rule public SpringIntegrationMethodRule methodRule = new SpringIntegrationMethodRule(); + + // @DirtiesContext + @Step + public void letsHack() { + konamiCodeService.alterClassicCode(RandomStringUtils.random(4)); + } + + @Step("there is no stage left") + public void noStageRemains() { + assertFalse(cheatSuccess); + assertThat(konamiCodeService.stageLeft(), equalTo(0)); + } +} diff --git a/libraries/src/test/java/com/baeldung/serenity/spring/steps/KonamiCodeRestSteps.java b/libraries/src/test/java/com/baeldung/serenity/spring/steps/KonamiCodeRestSteps.java new file mode 100644 index 0000000000..3f06d42414 --- /dev/null +++ b/libraries/src/test/java/com/baeldung/serenity/spring/steps/KonamiCodeRestSteps.java @@ -0,0 +1,68 @@ +package com.baeldung.serenity.spring.steps; + +import io.restassured.module.mockmvc.response.MockMvcResponse; +import net.thucydides.core.annotations.Step; + +import java.io.UnsupportedEncodingException; + +import static io.restassured.module.mockmvc.RestAssuredMockMvc.given; +import static org.hamcrest.core.IsEqual.equalTo; + +/** + * @author aiet + */ +public class KonamiCodeRestSteps { + + MockMvcResponse mockMvcResponse; + String cheatcode; + + @Step("get the classic cheat code") + public void givenClassicCheatCode() throws UnsupportedEncodingException { + cheatcode = given() + .when() + .get("/konamicode/classic") + .mvcResult() + .getResponse() + .getContentAsString(); + } + + @Step("check if the cheat code works") + public void whenCheat() { + mockMvcResponse = given() + .queryParam("cheatcode", cheatcode) + .when() + .get("/konamicode/cheatable"); + } + + @Step("classic cheat code matches") + public void thenClassicCodeCanDoTheTrick() { + mockMvcResponse + .then() + .statusCode(200) + .body(equalTo("true")); + } + + @Step("all stage cleared") + public void stageCleared() { + given() + .queryParam("action", "clear") + .when() + .put("/konamicode/stages"); + given() + .when() + .get("/konamicode/stages") + .then() + .body(equalTo("0")); + } + + @Step("one more stage to play") + public void thenMoreStages() { + given() + .when() + .get("/konamicode/stages") + .then() + .body(equalTo("1")); + } + +} + diff --git a/libraries/src/test/java/com/baeldung/serenity/spring/steps/KonamiCodeServiceInjectionSteps.java b/libraries/src/test/java/com/baeldung/serenity/spring/steps/KonamiCodeServiceInjectionSteps.java new file mode 100644 index 0000000000..b57186ba14 --- /dev/null +++ b/libraries/src/test/java/com/baeldung/serenity/spring/steps/KonamiCodeServiceInjectionSteps.java @@ -0,0 +1,55 @@ +package com.baeldung.serenity.spring.steps; + +import com.baeldung.serenity.spring.KonamiCodeService; +import net.thucydides.core.annotations.Step; +import org.apache.commons.lang3.RandomStringUtils; +import org.springframework.beans.factory.annotation.Autowired; +import org.springframework.test.context.ContextConfiguration; + +import static org.hamcrest.core.IsEqual.equalTo; +import static org.junit.Assert.*; + +/** + * @author aiet + */ +@ContextConfiguration(classes = KonamiCodeService.class) +public class KonamiCodeServiceInjectionSteps { + + private String latestCheatcode; + private boolean cheatSuccess; + + @Autowired private KonamiCodeService konamiCodeService; + + @Step("fetch latest cheat code") + public void fetchLatestCheatcode() { + latestCheatcode = konamiCodeService.getClassicCode(); + } + + @Step("cheat with latest code") + public void cheatWithLatestcode() { + cheatSuccess = konamiCodeService.cheatWith(latestCheatcode); + } + + @Step("all stages of the game are cleared") + public void gameStageCleared() { + konamiCodeService.clearStage(); + } + + @Step("there is still a stage left") + public void aStageRemains() { + assertTrue("cheatcode wrong", cheatSuccess); + assertThat(konamiCodeService.stageLeft(), equalTo(1)); + } + + @Step("altering default cheat code") + public void letsHack() { + konamiCodeService.alterClassicCode(RandomStringUtils.random(4)); + } + + @Step("there is no stage left") + public void noStageRemains() { + assertFalse(cheatSuccess); + assertThat(konamiCodeService.stageLeft(), equalTo(0)); + } + +} diff --git a/libraries/src/test/java/com/baeldung/serenity/spring/stories/KonamiCodeStory.java b/libraries/src/test/java/com/baeldung/serenity/spring/stories/KonamiCodeStory.java new file mode 100644 index 0000000000..090eb63215 --- /dev/null +++ b/libraries/src/test/java/com/baeldung/serenity/spring/stories/KonamiCodeStory.java @@ -0,0 +1,37 @@ +package com.baeldung.serenity.spring.stories; + +import com.baeldung.serenity.spring.steps.KonamiCodeRestSteps; +import net.thucydides.core.annotations.Steps; +import org.jbehave.core.annotations.Given; +import org.jbehave.core.annotations.Then; +import org.jbehave.core.annotations.When; + +/** + * @author aiet + */ +public class KonamiCodeStory { + + @Steps KonamiCodeRestSteps restSteps; + + @Given("game stage cleared") + public void givenStageCleared(){ + restSteps.stageCleared(); + } + + @Given("KONAMI cheat code") + public void givenKONAMICheatCode() throws Exception{ + restSteps.givenClassicCheatCode(); + } + + @When("I input the cheat code") + public void whenIInputTheCheatCode() { + restSteps.whenCheat(); + } + + @Then("a hidden stage will be unlocked") + public void thenAHiddenStageWillBeUnlocked() { + restSteps.thenClassicCodeCanDoTheTrick(); + restSteps.thenMoreStages(); + } + +} diff --git a/libraries/src/test/resources/konami-cheat-beans.xml b/libraries/src/test/resources/konami-cheat-beans.xml new file mode 100644 index 0000000000..221d058337 --- /dev/null +++ b/libraries/src/test/resources/konami-cheat-beans.xml @@ -0,0 +1,13 @@ + + + + + + ↑↑↓↓←→←→BA + + + + + diff --git a/libraries/src/test/resources/stories/spring/konami_code_test.story b/libraries/src/test/resources/stories/spring/konami_code_test.story new file mode 100644 index 0000000000..bba8ad7ade --- /dev/null +++ b/libraries/src/test/resources/stories/spring/konami_code_test.story @@ -0,0 +1,12 @@ +Meta: + +Narrative: +As a KONAMI player +I want to cheat +So that I can unlock hidden stages of the game + +Scenario: A KONAMI player can use the cheatcode to unlock hidden stages +Given game stage cleared +And KONAMI cheat code +When I input the cheat code +Then a hidden stage will be unlocked \ No newline at end of file