REST Client testen met Restito Tool: Wat is Rest Client?
Wat is RUST?
REST staat voor ‘REpresentational State Transfer’, wat een nieuwe manier van communicatie is tussen twee systemen op een bepaald tijdstip. Eén van de systemen heet 'REST Client' en de andere heet 'REST Server'.
Voordat we meer te weten komen over het Restito Framework voor het testen van REST-clients, moeten we eerst een paar basisprincipes leren.
Wat is REST-client?
REST Client is een methode of hulpmiddel om een REST-service-API aan te roepen die beschikbaar is voor communicatie door elk systeem of elke serviceprovider. Bijvoorbeeld: als een API wordt blootgesteld om realtime verkeersinformatie over een route van Google te krijgen, wordt de software/tool die de Google-verkeers-API aanroept de REST-client genoemd.
Wat is REST-server?
Het is een methode of een API die door elk systeem of elke serviceprovider wordt blootgesteld aan communicatie. Google stelt bijvoorbeeld een API beschikbaar om realtime verkeersinformatie op een bepaalde route te verkrijgen.
Hier moet de Google-server actief zijn om te luisteren naar verzoeken aan de blootgestelde API van verschillende clients.
Voorbeeld:
Het is tijd om een compleet end-to-end-scenario op te stellen op basis van de bovenstaande definities.
Laten we eens kijken naar taxi-boekingsapplicaties zoals Uber, aangezien een bedrijf realtime informatie nodig heeft over de verkeerssituatie rond de routes waarop een bepaald voertuig zich bevindt.
Rust cliënt:
Hier is de client een mobiele Uber-applicatie waarop de chauffeur heeft ingelogd. Deze app stuurt een verzoek naar de REST API die door Google Maps wordt weergegeven om de realtime gegevens te verkrijgen. Bijvoorbeeld een HTTP GET-verzoek.
Rustserver:
In dit voorbeeld is Google de serviceprovider en reageert de API van Google Maps met de vereiste gegevens op het verzoek van de Uber-app.
Zowel de client als de server zijn even belangrijk in REST-communicatie.
Hier hebben we voorbeelden geïmplementeerd voor automatiseringstests van alleen de REST Client. Raadpleeg voor het testen van de REST-server https://www.guru99.com/top-6-api-testing-tool.html.
Wat is Restito?
Restito is een framework ontwikkeld door Mkotsur. Het is een lichtgewicht app om u te helpen bij het uitvoeren van elk type HTTP Request. U kunt Restito gebruiken om uw REST API's te testen en om problemen in uw applicatie of uw netwerk te zoeken.
Hoe test ik de REST-client met Restito?
Laten we de oefening opdelen in de volgende 4 stappen:
- Maak een HTTP-client en -methode om een HTTP GET-verzoek naar elk servereindpunt te verzenden. Beschouw voorlopig het eindpunt als
http://localhost:9092/getevents
.
- Start een Restito-server om te luisteren en de verzoeken vast te leggen die naar het eindpunt 'getevents' in localhost worden verzonden
http://localhost:9092/getevents
.
- Maak een testklasse om de bovenstaande client te testen. Roep de HTTP-client 'sendGETRequest'-methode aan om een GET-verzoek naar de API 'getevents' te initiëren.
- Valideer de HTTP GET-aanroep met behulp van het Restito-framework.
Laten we dieper ingaan op elk van de bovenstaande stappen.
Stap 1) Maak een HTTP-client en -methode om een HTTP GET-verzoek naar elk servereindpunt te verzenden.
========== JAVA CODE begint ===========
package com.chamlabs.restfulservices.client; import java.util.HashMap; import java.util.Map; import org.apache.http.client.HttpClient; import org.apache.http.client.methods.HttpGet; import org.apache.http.client.methods.HttpPost; import org.apache.http.entity.StringEntity; import org.apache.http.impl.client.HttpClientBuilder; import org.json.JSONObject; /** * This class creates a HTTP Client and has a method to send HTTP GET request: * sendGETRequest(..) */ public class RestClient { /** * Constructor for the class RestClient */ public RestClient() { System.out.println("Creating RestClient constructor"); } /** * Method to Send GET request to http://localhost:<<port>>/getevents * @param port * @return true if GET request is successfully sent. False, otherwise. */ public static boolean sendGETRequest(int port) { try { HttpClient client = HttpClientBuilder.create().build(); HttpGet getRequest = new HttpGet("http://localhost:" + port + "/getevents"); //HttpResponse response = client.execute(request); client.execute(getRequest); System.out.println("HTTP request is sent successfully." + "Returning True"); return true; } catch (Exception e) { e.printStackTrace(); } System.out.println("Some exception has occurred during the HTTP Client creation." + "Returning false"); return false; } }
========== JAVA CODE eindigt ===========
Stap 2) Start een Restito-server om te luisteren en de verzoeken vast te leggen die naar het eindpunt 'getevents' in localhost worden verzonden http://localhost:9092/getevents
.
========== JAVA CODE begint ===========
package com.chamlabs.restfultesting.util; import static com.xebialabs.restito.builder.stub.StubHttp.whenHttp; import static com.xebialabs.restito.semantics.Action.status; import static com.xebialabs.restito.semantics.Condition.get; import static com.xebialabs.restito.semantics.Condition.post; import java.util.List; import org.glassfish.grizzly.http.util.HttpStatus; import com.xebialabs.restito.semantics.Call; import com.xebialabs.restito.server.StubServer; /** * This utility class contains several utility methods like : * restartRestitoServerForGETRequests(..) * restartRestitoServerForPOSTRequests(..) * waitAndGetCallList(..) * * @author cham6 * @email: paperplanes.chandra@gmail.com * @fork: https://github.com/cham6/restfultesting.git * */ public class TestUtil { /** * Utility method to start restito stub server to accept GET requests * @param server * @param port * @param status */ public static void restartRestitoServerForGETRequests (StubServer server, int port, HttpStatus status) { // Kill the restito server if (server != null) { server.stop(); } // Initialize and configure a newer instance of the stub server server = new StubServer(port).run(); whenHttp(server).match(get("/getevents")).then(status(status)); } /** * Utility method to start restito stub server to accept POST requests * @param server * @param port * @param status */ public static void restartRestitoServerForPOSTRequests (StubServer server, int port, HttpStatus status) { // Kill the restito server if (server != null) { server.stop(); } // Initialize and configure a newer instance of the stub server server = new StubServer(port).run(); whenHttp(server).match(post("/postevents")).then(status(status)); } /** * For a given restito stub server, loop for the given amount of seconds and * break and return the call list from server. * * @param server * @param waitTimeInSeconds * @return * @throws InterruptedException */ public static List<Call> waitAndGetCallList (StubServer server, int waitTimeInSeconds) throws InterruptedException { int timeoutCount = 0; List<Call> callList = server.getCalls(); while (callList.isEmpty()) { Thread.sleep(1000); timeoutCount++; if (timeoutCount >= waitTimeInSeconds) { break; } callList = server.getCalls(); } // Wait for 2 seconds to get all the calls into callList to Eliminate any falkyness. Thread.sleep(2000); return server.getCalls(); } }
========== JAVA CODE eindigt ===========
Stap 3) Maak een testklasse om de bovenstaande client te testen. Roep de HTTP-client sendGETRequest-methode aan om een GET-verzoek naar de API 'getevents' te initiëren.
========== JAVA CODE begint ===========import junit.framework.TestCase; import com.chamlabs.restfulservices.client.RestClient; import com.chamlabs.restfultesting.util.TestUtil; import com.xebialabs.restito.semantics.Call; import com.xebialabs.restito.server.StubServer; import static org.glassfish.grizzly.http.util.HttpStatus.ACCEPTED_202; import org.json.JSONObject; import java.util.List; import java.util.Map; /** * This class contains several junit tests to validate the RestClient operations like: * sendRequest(..) * sendRequestWithCustomHeaders(..) * sendPOSTRequestWithJSONBody(..) * */ public class RestClientTester extends TestCase { private static final Integer PORT = 9098; private static final Integer PORT2 = 9099; private static final Integer PORT3 = 9097; public RestClientTester() { System.out.println("Starting the test RestClientTester"); } /** * Junit test to validate the GET request from RestClient * Steps: * 1) Create a stub server using Restito framework and configure it to listen on given port * 2) Invoke the sendGETRequest(..) method of RestClient * 3) Restito captures the matching GET requests sent, if any. * 4) Validate if Restito has captured any GET requests on given endpoint * Expected Behavior: * > Restito should have captured GET request and it should have captured only one GET request. * Finally: * > Stop the stub server started using restito. */ public void testGETRequestFromClient() { StubServer server = null; try { //This will start the stub server on 'PORT' and responds with HTTP 202 'ACCEPTED_202' TestUtil.restartRestitoServerForGETRequests(server, PORT, ACCEPTED_202); RestClient.sendGETRequest(PORT); List<Call> callList = TestUtil.waitAndGetCallList(server, 30); assertTrue("GET request is not received from the RestClient. Test failed.", (callList != null) && (callList.size() == 1)); } catch(Exception e) { e.printStackTrace(); fail("Test Failed due to exception : " + e); } finally { if(server != null) { server.stop(); } } }
========== JAVA CODE eindigt ===========
Stap 4) Hoe u een GET-verzoek kunt valideren met headers en POST-verzoeken met de hoofdtekst met behulp van het Restito-framework.
========== JAVA CODE begint ===========
/** * Junit test to validate the GET request with headers from RestClient * Steps: * 1) Create a stub server using Restito framework and configure it to listen on given port * 2) Invoke the sendGETRequestWithCustomHeaders(..) method of RestClient * 3) Restito captures the matching GET requests sent, if any. * 4) Validate if Restito has captured any GET requests on a given endpoint * Expected Behavior: * > Restito should have captured GET request, and it should have captured only one GET request. * > Get the headers of the captured GET request * and make sure the headers match to the ones configured. * Finally: * > Stop the stub server started using restito. */ public void testGETRequestWithHeadersFromClient() { StubServer server = null; try { //This will start the stub server on 'PORT' and responds with HTTP 202 'ACCEPTED_202' TestUtil.restartRestitoServerForGETRequests(server, PORT2, ACCEPTED_202); RestClient.sendGETRequestWithCustomHeaders(PORT2); List<Call> callList = TestUtil.waitAndGetCallList(server, 30); assertTrue("GET request is not received from the RestClient. Test failed.", (callList != null) && (callList.size() == 1)); //Validate the headers of the GET request from REST Client Map<String, List<String>> headersFromRequest = callList.get(0).getHeaders(); assertTrue("GET request contains header Accept and its value ", headersFromRequest.get("Accept").contains("text/html")); assertTrue("GET request contains header Authorization and its value ", headersFromRequest.get("Authorization").contains("Bearer 1234567890qwertyuiop")); assertTrue("GET request contains header Cache-Control and its value ", headersFromRequest.get("Cache-Control").contains("no-cache")); assertTrue("GET request contains header Connection and its value ", headersFromRequest.get("Connection").contains("keep-alive")); assertTrue("GET request contains header Content-Type and its value ", headersFromRequest.get("Content-Type").contains("application/json")); } catch(Exception e) { e.printStackTrace(); fail("Test Failed due to exception : " + e); } finally { if(server != null) { server.stop(); } } }
/** * Junit test to validate the POST request with body and headers from RestClient * Steps: * 1) Create a stub server using Restito framework and configure it to listen on given port * 2) Invoke the sendPOSTRequestWithJSONBody(..) method of RestClient * 3) Restito captures the matching POST requests sent, if any. * 4) Validate if Restito has captured any POST requests on given endpoint * Expected Behavior: * > Restito should have captured POST request and it should have captured only one POST request. * > Get the body of the captured POST request and validate the JSON values * Finally: * > Stop the stub server started using restito. */ public void testPOSTRequestWithJSONBody() { StubServer server = null; try { //This will start the stub server on 'PORT' and responds with HTTP 202 'ACCEPTED_202' TestUtil.restartRestitoServerForPOSTRequests(server, PORT3, ACCEPTED_202); RestClient.sendPOSTRequestWithJSONBody(PORT3); List<Call> callList = TestUtil.waitAndGetCallList(server, 30); assertTrue("POST request is not received from the RestClient. Test failed.", (callList != null) && (callList.size() == 1)); //Validate the headers of the GET request from REST Client String requestBody = callList.get(0).getPostBody(); JSONObject postRequestJSON = new JSONObject(requestBody); assertTrue("The timeUpdated in json is incorrect", postRequestJSON.get("timeUpdated").toString().equalsIgnoreCase("1535703838478")); assertTrue("The access_token in json is incorrect", postRequestJSON.get("access_token").toString(). equalsIgnoreCase("abf8714d-73a3-42ab-9df8-d13fcb92a1d8")); assertTrue("The refresh_token in json is incorrect", postRequestJSON.get("refresh_token").toString(). equalsIgnoreCase("d5a5ab08-c200-421d-ad46-2e89c2f566f5")); assertTrue("The token_type in json is incorrect", postRequestJSON.get("token_type").toString().equalsIgnoreCase("bearer")); assertTrue("The expires_in in json is incorrect", postRequestJSON.get("expires_in").toString().equalsIgnoreCase("1024")); assertTrue("The scope in json is incorrect", postRequestJSON.get("scope").toString().equalsIgnoreCase("")); } catch(Exception e) { e.printStackTrace(); fail("Test Failed due to exception : " + e); } finally { if(server != null) { server.stop(); } } } }
========== JAVA CODE eindigt ===========
Voordelen van het gebruik van Restito Framework voor het testen van REST-clients
Hier zijn de voor- en voordelen van Restito Framework voor het testen van ReST-clients
- We hebben niet de daadwerkelijke REST-server nodig die ontwikkeld moet worden om de REST Client te testen.
- Restito biedt krachtige en gevarieerde hulpprogramma's en methoden om verschillend gedrag van een server te simuleren. Bijvoorbeeld: om te testen hoe de REST-client zich gedraagt wanneer de server reageert met HTTP 404-fout of HTTP 503-fout.
- Restito-servers kunnen in enkele milliseconden worden opgezet en kunnen worden beëindigd nadat de tests zijn voltooid.
- Restito ondersteunt alle soorten HTTP-methode-inhoud, zoals gecomprimeerd, niet-gecomprimeerd, verenigd, applicatie/tekst, applicatie/JSON, enz.
Nadelen van het gebruik van Restito Framework voor het testen van REST-clients
Hier zijn de nadelen/nadelen van Restito Framework voor het testen van ReST-clients
- De REST-clientbron moet worden aangepast om 'localhost' als een servermachine te beschouwen.
- Het openen van de server in welke poort dan ook kan conflicteren als we een veelgebruikte poort gebruiken, zoals '8080' of '9443' enz.
- Het wordt aanbevolen om poorten zoals 9092 of 9099 te gebruiken, die niet vaak door andere tools worden gebruikt.
Samenvatting
- REST staat voor “REpresentational State Transfer”, een nieuwe standaardmanier van communicatie tussen twee systemen op een bepaald tijdstip.
- REST Client is een methode of hulpmiddel om een REST-service-API aan te roepen die wordt blootgesteld aan communicatie door een systeem of serviceprovider.
- In de RestServer-methode of een API die beschikbaar is voor communicatie door een systeem of serviceprovider.
- Restito is een lichtgewicht app waarmee u elk soort HTTP-verzoek kunt uitvoeren
- Maak een HTTP-client en -methode om een HTTP GET-verzoek naar elk servereindpunt te verzenden
- Start een Restito-server om te luisteren en de verzoeken vast te leggen die naar het eindpunt 'getevents' worden verzonden.
- Start een Restito-server om te luisteren en de verzoeken vast te leggen die naar het eindpunt 'getevents' in localhost worden verzonden
- Hier hebben we voorbeelden geïmplementeerd voor automatiseringstests van alleen de REST Client.
- We hebben niet de daadwerkelijke REST-server nodig die ontwikkeld moet worden om de REST Client te testen.
- De REST-clientbron moet worden aangepast om 'localhost' als een servermachine te beschouwen.