Einführung in Serenity BDD

1. Einleitung

In diesem Tutorial geben wir eine Einführung in Serenity BDD - ein großartiges Tool zum Anwenden von Behavior Driven Development (BDD). Dies ist eine Lösung für automatisierte Abnahmetests, die gut illustrierte Testberichte generiert.

2. Kernkonzepte

Die Konzepte hinter Serenity folgen den Konzepten hinter BDD. Wenn Sie mehr darüber lesen möchten, lesen Sie unseren Artikel über Gurke und JBehave.

2.1. Bedarf

In Serenity sind die Anforderungen in drei Ebenen unterteilt:

  1. Fähigkeiten
  2. Eigenschaften
  3. Geschichten

In der Regel implementiert ein Projekt in einem E-Commerce-Projekt Funktionen auf hoher Ebene, Ex-Order-Management und Mitgliederverwaltung. Jede Funktion besteht aus vielen Funktionen, und die Funktionen werden in User Stories ausführlich erläutert.

2.2. Schritte und Tests

Schritte enthalten eine Gruppe von Ressourcenmanipulationsvorgängen. Dies kann eine Aktion, eine Überprüfung oder eine kontextbezogene Operation sein. Das klassische Given_When_Then- Format kann in den Schritten wiedergegeben werden.

Und Tests gehen Hand in Hand mit Steps. Jeder Test erzählt eine einfache User Story, die mit einem bestimmten Schritt ausgeführt wird .

2.3. Berichte

Serenity meldet die Testergebnisse nicht nur, sondern verwendet sie auch zur Erstellung einer lebendigen Dokumentation, in der die Anforderungen und das Anwendungsverhalten beschrieben werden.

3. Testen mit SerenityBDD

Um unsere Serenity-Tests mit JUnit durchzuführen, müssen wir @RunWith the SerenityRunner , Test Runner , ausführen . SerenityRunner instrumentiert die Schrittbibliotheken und stellt sicher, dass die Testergebnisse von den Serenity-Reportern aufgezeichnet und gemeldet werden.

3.1. Maven-Abhängigkeiten

Um Serenity mit JUnit nutzen zu können, sollten wir serenity-core und serenity-junit in die pom.xml aufnehmen:

 net.serenity-bdd serenity-core 1.2.5-rc.11   net.serenity-bdd serenity-junit 1.2.5-rc.11 

Wir benötigen auch das Serenity-Maven-Plugin , um Berichte aus Testergebnissen zu aggregieren:

 net.serenity-bdd.maven.plugins serenity-maven-plugin 1.2.5-rc.6   serenity-reports post-integration-test  aggregate    

Wenn Serenity auch bei einem Testfehler Berichte erstellen soll, fügen Sie der Datei pom.xml Folgendes hinzu :

 org.apache.maven.plugins maven-surefire-plugin 2.20  true  

3.2. Ein Beispiel für Mitgliedschaftspunkte

Zunächst basieren unsere Tests auf den typischen Mitgliedschaftspunkten in einer E-Commerce-Anwendung. Ein Kunde kann dem Mitgliederprogramm beitreten. Wenn der Kunde Waren auf der Plattform kauft, erhöhen sich die Mitgliedschaftspunkte und die Mitgliedschaftsstufe des Kunden steigt entsprechend.

Schreiben wir nun einige Tests anhand der oben beschriebenen Szenarien und sehen, wie Serenity funktioniert.

Schreiben wir zunächst den Test für die Initialisierung der Mitgliedschaft und sehen, welche Schritte wir benötigen:

@RunWith(SerenityRunner.class) public class MemberStatusIntegrationTest { @Steps private MemberStatusSteps memberSteps; @Test public void membersShouldStartWithBronzeStatus() { memberSteps.aClientJoinsTheMemberProgram(); memberSteps.theMemberShouldHaveAStatusOf(Bronze); } }

Dann implementieren wir die beiden Schritte wie folgt:

public class MemberStatusSteps { private Member member; @Step("Given a member has {0} points") public void aMemberHasPointsOf(int points) { member = Member.withInitialPoints(points); } @Step("Then the member grade should be {0}") public void theMemberShouldHaveAStatusOf(MemberGrade grade) { assertThat(member.getGrade(), equalTo(grade)); } }

Jetzt können wir einen Integrationstest mit mvn clean verify durchführen . Die Berichte befinden sich unter target / site / serenity / index.html :

Aus dem Bericht geht hervor, dass wir nur einen Abnahmetest haben: "Mitglieder sollten mit dem Bronzestatus beginnen, die Fähigkeit dazu haben" und bestehen. Durch Klicken auf den Test werden die Schritte veranschaulicht:

Wie wir sehen können, gibt uns der Bericht von Serenity ein gründliches Verständnis dafür, was unsere Anwendung tut und ob sie unseren Anforderungen entspricht. Wenn wir einige Schritte implementieren müssen, können wir sie als @Pending markieren :

@Pending @Step("When the member exchange {}") public void aMemberExchangeA(Commodity commodity){ //TODO }

Der Bericht würde uns daran erinnern, was als nächstes zu tun ist. Und falls ein Test fehlschlägt, kann er auch im Bericht eingesehen werden:

Jeder fehlgeschlagene, ignorierte oder übersprungene Schritt wird aufgelistet:

4. Integration mit JBehave

Serenity kann auch in vorhandene BDD-Frameworks wie JBehave integriert werden.

4.1. Maven-Abhängigkeiten

To integrate with JBehave, one more dependency serenity-jbehave is needed in the POM:

 net.serenity-bdd serenity-jbehave 1.24.0 

4.2. JBehave Github REST API Test Continued

As we have introduced how to do REST API testing with JBehave, we can continue with our JBehave REST API test and see how it fits in Serenity.

Our story was:

Scenario: Github user's profile should have a login payload same as username Given github user profile api When I look for eugenp via the api Then github's response contains a 'login' payload same as eugenp

The Given_When_Then steps can be migrated to as @Steps without any changes:

public class GithubRestUserAPISteps { private String api; private GitHubUser resource; @Step("Given the github REST API for user profile") public void withUserProfileAPIEndpoint() { api = "//api.github.com/users/%s"; } @Step("When looking for {0} via the api") public void getProfileOfUser(String username) throws IOException { HttpResponse httpResponse = getGithubUserProfile(api, username); resource = retrieveResourceFromResponse(httpResponse, GitHubUser.class); } @Step("Then there should be a login field with value {0} in payload of user {0}") public void profilePayloadShouldContainLoginValue(String username) { assertThat(username, Matchers.is(resource.getLogin())); } }

To make JBehave's story-to-code mapping work as expected, we need to implement JBehave's step definition using @Steps:

public class GithubUserProfilePayloadStepDefinitions { @Steps GithubRestUserAPISteps userAPISteps; @Given("github user profile api") public void givenGithubUserProfileApi() { userAPISteps.withUserProfileAPIEndpoint(); } @When("looking for $user via the api") public void whenLookingForProfileOf(String user) throws IOException { userAPISteps.getProfileOfUser(user); } @Then("github's response contains a 'login' payload same as $user") public void thenGithubsResponseContainsAloginPayloadSameAs(String user) { userAPISteps.profilePayloadShouldContainLoginValue(user); } }

With SerenityStories, we can run JBehave tests both from within our IDE and in the build process:

import net.serenitybdd.jbehave.SerenityStory; public class GithubUserProfilePayload extends SerenityStory {}

After the verify build finished, we can see our test report:

Compared to plain text report of JBehave, the rich report by Serenity gives us a more eye-pleasing and live overview of our story and the test result.

5. Integration With REST-assured

It is noteworthy that Serenity supports integration with REST-assured. To have a review of REST-assured, take a look at the guide to REST-assured.

5.1. Maven Dependencies

To make use of REST-assured with Serenity, the serenity-rest-assured dependency should be included:

 net.serenity-bdd serenity-rest-assured 1.2.5-rc.11 

5.2. Use REST-assured in Github REST API Test

Now we can replace our web client with REST-assured utilities:

import static net.serenitybdd.rest.SerenityRest.rest; import static net.serenitybdd.rest.SerenityRest.then; public class GithubRestAssuredUserAPISteps { private String api; @Step("Given the github REST API for user profile") public void withUserProfileAPIEndpoint() { api = "//api.github.com/users/{username}"; } @Step("When looking for {0} via the api") public void getProfileOfUser(String username) throws IOException { rest().get(api, username); } @Step("Then there should be a login field with value {0} in payload of user {0}") public void profilePayloadShouldContainLoginValue(String username) { then().body("login", Matchers.equalTo(username)); } }

After replacing the implementation of userAPISteps in the StepDefition, we can re-run the verify build:

public class GithubUserProfilePayloadStepDefinitions { @Steps GithubRestAssuredUserAPISteps userAPISteps; //... }

In the report, we can see the actual API invoked during the test, and by clicking on the REST Query button, the details of request and response will be presented:

6. Integration With JIRA

As of now, we already have a great test report describing details and status of our requirements with Serenity framework. But for an agile team, issue tracking systems such as JIRA are often used to keep track of requirements. It would be better if we could use them seamlessly.

Luckily, Serenity already supports integration with JIRA.

6.1. Maven Dependencies

To integrate with JIRA, we need another dependency: serenity-jira-requirements-provider.

 net.serenity-bdd serenity-jira-requirements-provider 1.1.3-rc.5 

6.2. One-way Integration

To add JIRA links in the story, we can add the JIRA issue using story's meta tag:

Meta: @issue #BDDTEST-1

Außerdem sollten das JIRA-Konto und die Links in der Datei serenity.properties im Stammverzeichnis des Projekts angegeben werden:

jira.url= jira.project= jira.username= jira.password=

Dann würde ein JIRA-Link im Bericht angehängt:

Serenity unterstützt auch die bidirektionale Integration mit JIRA. Weitere Informationen finden Sie in der offiziellen Dokumentation.

7. Zusammenfassung

In diesem Artikel haben wir Serenity BDD und mehrere Integrationen mit anderen Testframeworks und Anforderungsmanagementsystemen vorgestellt.

Obwohl wir das meiste behandelt haben, was Serenity kann, kann es sicherlich mehr. In unserem nächsten Artikel werden wir uns damit befassen, wie Serenity mit WebDriver-Unterstützung es uns ermöglichen kann, Webanwendungsseiten mithilfe des Drehbuchs zu automatisieren.

Wie immer finden Sie den vollständigen Implementierungscode im GitHub-Projekt.