Showing posts with label End-to-End Testing. Show all posts
Showing posts with label End-to-End Testing. Show all posts

How to Test Token based Authentication in API by Playwright




What is Token-based Authentication?

Token-based authentication is a method used to verify the identity of a user or system trying to access a protected resource (like an API or web application). Instead of repeatedly sending a username and password, the system issues a token (a unique string, often in the form of a JWT – JSON Web Token) after a successful login.


How it generally works:

  • Login: The user sends their credentials (username & password) to the authentication server.
  • Token Issuance: If valid, the server generates a token and sends it back to the client.
  • Token Usage: The client includes this token in the Authorization header (usually as Bearer <token>) for all subsequent requests.
  • Validation: The server validates the token and grants or denies access to protected resources.
  • Expiry & Refresh: Tokens often expire after some time, so refresh tokens may be used to obtain a new one without re-login.


How to Handle Token-based Authentication in Playwright Java

When automating scenarios with Playwright, token handling is key to bypass login screens or test APIs securely. Here’s how it is conceptually managed:


(1) Obtain Token Programmatically or Manually:
  • You can call the authentication API endpoint (using Java HTTP client or Playwright’s request context) with credentials and capture the token.
  • Alternatively, use a pre-generated token provided by the developer or QA team.
(2) Store Token in Test Context:
  • Keep the token in a variable or configuration file so it can be reused across requests and sessions.
(3) Attach Token to Requests:
  • Use Playwright’s APIRequestContext in Java to send API requests with headers that include the token (Authorization: Bearer <token>).
  • For browser-based flows, inject the token into browser storage:
       LocalStorage/SessionStorage: Save the token where the application expects it.
       Cookies: If the app stores the token in cookies, set them before navigating.

(4) Re-use Authenticated State:
  • Once the browser is authenticated with the token, Playwright allows saving that state (cookies, local storage).
  • This state can then be reused in subsequent tests to skip login repeatedly.
(5) Token Expiry Handling:
  • If the token expires, the automation should either:
        Request a new token before test execution, or
        Use a refresh token flow if supported.


To test token-based authentication in an API using Playwright in Java, you typically perform the following steps:











Workflow Explanation

  • Get the Authentication Token
    Send a POST (or appropriate) request to the authentication endpoint with credentials to get a token.
  • Use the Token in Headers
    For subsequent API calls, include the token in the Authorization header as a Bearer token.
  • Validate Response
    Use assertions to verify the status code and content of the protected endpoint's response.



Example Scenario

Let’s take an example of https://reqres.in/api/login which gives a token on successful login, and then use that token to call another API like https://reqres.in/api/users

https://reqres.in/api/login
















https://reqres.in/api/users














Maven Dependencies

<dependency>
    <groupId>com.microsoft.playwright</groupId>
    <artifactId>playwright</artifactId>
    <version>1.44.0</version> <!-- Use latest -->
</dependency>




Java Code: Token-based API Testing Using Playwright

import com.microsoft.playwright.*;
import com.microsoft.playwright.options.*;

import java.util.*;

public class TokenBasedAuthTest {
    public static void main(String[] args) {
        try (Playwright playwright = Playwright.create()) {
            APIRequest request = playwright.request().newContext();

            // Step 1: Login to get the token
            APIResponse loginResponse = request.post("https://reqres.in/api/login", 
                RequestOptions.create()
                    .setHeader("Content-Type", "application/json")
                    .setData("{ \"email\": \"eve.holt@reqres.in\", \"password\": \"cityslicka\" }")
            );

            if (loginResponse.status() != 200) {
                System.out.println("Login failed! Status: " + loginResponse.status());
                return;
            }

            // Extract token from response JSON
            String token = loginResponse.json().get("token").toString();
            System.out.println("Token received: " + token);

            // Step 2: Use token in Authorization header to call protected resource
            APIResponse userResponse = request.get("https://reqres.in/api/users/2", 
                RequestOptions.create()
                    .setHeader("Authorization", "Bearer " + token)
            );

            System.out.println("User API Status Code: " + userResponse.status());
            System.out.println("User API Response: " + userResponse.text());

            if (userResponse.status() == 200) {
                System.out.println("Token-based API access successful.");
            } else {
                System.out.println("Access failed.");
            }
        }
    }
}



Code Steps:

(a) Login to get the token
(b) Extract token from response JSON
(c) Use token in Authorization header to call protected resource


Explanation

  • playwright.request().newContext() → Creates a new API context.
  • loginResponse.json().get("token") → Extracts token from login response.
  • "Authorization": "Bearer " + token → Adds the token to the headers for authentication.


Suggested Posts:

1. Automate GET API in Playwright
2. Automate POST API in Playwright
3. Automate PUT API in Playwright
4. Test Cookie Based Authentication in Playwright
5. Basic Authentication in Playwright

How to Test Lombok API by Playwright

 



1. What is Lombok API?

  • Project Lombok is a Java library (API) that helps reduce boilerplate code in Java classes.
  • Instead of writing getters, setters, constructors, toString(), equals(), and hashCode() methods manually, Lombok uses annotations like @Getter, @Setter, @Data, @Builder, etc. to auto-generate them during compilation.
  • Example: A User class with @Data annotation will automatically have getters, setters, and other utility methods without explicitly writing them.
  • Lombok improves code readability and maintainability but still produces bytecode with full methods, so other parts of the application can use it seamlessly.

2. Why Testing Lombok API is Important?
  • Lombok only generates methods at compile time, but we should validate the business logic that depends on these generated methods.
  • Testing ensures that:
         - Getter/Setter methods work as expected.
         - equals() and hashCode() generated methods behave correctly in collections.
         - toString() provides meaningful output.
         - Builder patterns (@Builder) correctly construct objects.


How to Test Lombok APIs with Playwright Java

(1) Setup Playwright Test Environment
  • Configure Playwright Java project.
  • Use Playwright’s API testing capabilities (APIRequestContext) for sending API calls.
(2) Send API Request
  • Perform GET, POST, PUT, or DELETE requests to endpoints built on Lombok-backed models.

(3) Validate Response
  • Check if Lombok-generated methods worked as intended. For example:
         - If you created a user via API (using Lombok’s builder), verify the response  contains correct details (via getter methods).
         - If you fetch a list, ensure Lombok’s equals() and hashCode() ensure no   duplicates are mishandled.

(4) Assertions
  • Validate status codes (200, 201, etc.).
  • Validate JSON structure (keys, values).
  • Validate that Lombok-driven serialization matches expected contract.

To test a Lombok-based API using Playwright with Java, you need to understand that Lombok is a Java annotation library used to reduce boilerplate code in Java classes. When we say "Lombok API", we are usually referring to a REST API that uses Lombok in its backend for DTOs or models.

From a test automation perspective using Playwright Java, it doesn’t matter if Lombok is used on the server side. Your focus will be on sending HTTP requests (GET, POST, PUT, DELETE) and validating responses (status codes, response body, etc.).










Steps to Test a Lombok-based API in Playwright Java:

  • Set up Playwright Java Project
  • Use Java’s HttpClient or OkHttp for API calls
  • Send a request to the API
  • Validate the response (status, body, etc.)


Example

Assume we have a Lombok-powered API:

Below is the API request for LOMBOK API

POST http://localhost:8080/api/users
Request Body:
{
  "name": "John Doe",
  "email": "john@example.com"
}



Response:

{
  "id": 1,
  "name": "John Doe",
  "email": "john@example.com"
}




Code to Test this API using Playwright Java + HttpClient

import com.microsoft.playwright.*;
import java.net.URI;
import java.net.http.*;
import java.net.http.HttpResponse.BodyHandlers;
import java.net.http.HttpRequest.BodyPublishers;

public class LombokApiTest {
    public static void main(String[] args) throws Exception {
        // Start Playwright (in case you want to verify UI after API test)
        try (Playwright playwright = Playwright.create()) {
            Browser browser = playwright.chromium().launch(new BrowserType.LaunchOptions().setHeadless(true));
            BrowserContext context = browser.newContext();
            Page page = context.newPage();

            // Send API request using Java HttpClient
            HttpClient client = HttpClient.newHttpClient();

            // Sample JSON payload
            String jsonBody = """
                    {
                      "name": "John Doe",
                      "email": "john@example.com"
                    }
                    """;

            HttpRequest request = HttpRequest.newBuilder()
                    .uri(URI.create("http://localhost:8080/api/users"))
                    .header("Content-Type", "application/json")
                    .POST(BodyPublishers.ofString(jsonBody))
                    .build();

            HttpResponse<String> response = client.send(request, BodyHandlers.ofString());

            // Print and assert
            System.out.println("Status Code: " + response.statusCode());
            System.out.println("Response Body: " + response.body());

            if (response.statusCode() == 200 || response.statusCode() == 201) {
                System.out.println("API Test Passed");
            } else {
                System.out.println("API Test Failed");
            }

            // Optionally, use Playwright to navigate to a UI and verify the new user
            // page.navigate("http://localhost:8080/users");
            // page.locator("text=John Doe").waitFor(); // if user is listed
        }
    }
}



Code explanation:

(a) Create Playwright and Page object
(b) Send API request using Java HttpClient
(c) Define input JSON request
(d) Create HttpRequest object and send the request by send()
(e) The response that we got is printed and asserted.


Tools Used

  • Java HttpClient: To test the REST API.
  • Playwright Java: To optionally validate frontend after API call.
  • Lombok: Present in the backend API but irrelevant to test logic.


Maven Dependency for Playwright

<dependency>
  <groupId>com.microsoft.playwright</groupId>
  <artifactId>playwright</artifactId>
  <version>1.43.0</version> <!-- or latest -->
</dependency>


Selenium vs Playwright

 



Below is the detailed comparison of Playwright and Selenium which are two popular open-source web automation tools.


Selenium

Selenium is one of the oldest and most widely used web automation frameworks. It supports multiple programming languages such as Java, Python, C#, Ruby, and JavaScript, and works across many browsers. Selenium operates using the WebDriver protocol, which communicates with browsers to perform actions like clicking, typing, or navigating. 

It has a large community, strong ecosystem, and compatibility with many third-party tools like TestNG, JUnit, or Maven. However, Selenium often requires explicit waits to handle dynamic content, and test execution can sometimes be slower compared to modern frameworks. 

Its biggest advantage is its maturity, stability, and wide industry adoption.


Playwright

Playwright is a relatively newer automation framework developed by Microsoft. It supports JavaScript/TypeScript, Python, Java, and .NET. Unlike Selenium, Playwright does not rely on WebDriver; it directly communicates with browsers using native DevTools protocols, which makes it faster and more reliable. Playwright provides built-in auto-waiting mechanisms, making it easier to handle dynamic web applications without adding many explicit waits. 

It also has advanced features like intercepting network requests, handling multiple browser contexts, working with iframes, and supporting modern browsers including Chromium, Firefox, and WebKit. 

Additionally, Playwright supports parallel execution and cross-browser testing out of the box. Its modern design makes it well-suited for today’s single-page applications.










FeaturePlaywrightSelenium
ArchitectureModern, browser automation through WebSocket protocolTraditional, uses WebDriver protocol
Languages SupportedJavaScript, TypeScript, Python, C#, JavaJava, Python, C#, Ruby, JavaScript, Kotlin, etc.
Browsers SupportedChromium, Firefox, WebKit (Safari engine)Chrome, Firefox, Safari, IE, Edge
Cross-browser TestingYes (via single API)Yes (via WebDriver, requires separate drivers)
Headless ModeBuilt-in for all browsersSupported but configuration-heavy
Mobile EmulationBuilt-in (Android/iOS simulation)Supported via Chrome DevTools or Appium
Multi-tab/Context SupportExcellent (isolated browser contexts)Limited (each tab requires handling in a new driver instance)
Auto-wait for ElementsYes (automatic waiting for DOM/state readiness)Manual waits often needed (e.g., WebDriverWait)
Screenshots/VideosBuilt-in support for screenshots, videos, and tracesScreenshots supported, video needs external integration
Debugging ToolsBuilt-in tracing, time-travel debuggingBasic logs, stack traces, external tools needed for deep debug
Execution SpeedFaster (uses WebSocket and optimized browser contexts)Slower (uses HTTP/WebDriver protocol)
Parallel ExecutionBuilt-in support (workers, test sharding)Needs external config (e.g., Selenium Grid, TestNG parallel)
Ease of SetupEasy, single binary for all supported browsersComplex, needs drivers for each browser
CI/CD IntegrationGood support (GitHub Actions, Jenkins, etc.)Excellent support and maturity



Final Take:

Use Playwright for modern, high-speed automation with features like auto-wait, parallel testing, and browser context isolation.

Use Selenium for broad browser compatibility (example: legacy IE), or if you already have a mature Selenium-based infrastructure.


Suggested Posts:

1. First Script in Playwright
2. Automate GET API in Playwright
3. Comma Selectors in Playwright
4. Handle Alerts in Playwright
5. Find Web Elements by XPath in Playwright

How to Automate a Login Page by Playwright Java




When automating a login page with Playwright in Java, the process involves simulating the exact steps a real user would perform when logging into a web application. Here’s the conceptual flow:

1. Test Preparation

  • Launch Browser: Use Playwright to start a browser instance (Chrome, Firefox, WebKit).
  • Create Context and Page: A browser context is like a fresh user session, and a page represents a single browser tab. These are required to isolate the login test.

2. Navigating to the Login Page
  • Direct the browser to the application’s login URL.
  • Ensure the page is fully loaded before proceeding (Playwright automatically waits for the page to be ready, but explicit waits can be used for synchronization).
3. Interacting with Input Fields
  • Locate Username Field: Identify the username/email input box using a selector (ID, name, placeholder, or CSS).
  • Locate Password Field: Similarly, find the password input field.
  • Enter Credentials: Simulate typing the username and password into their respective fields.
4. Clicking the Login Button
  • Identify the login/submit button on the page.
  • Simulate a user click on the button. Playwright ensures the element is ready for interaction before performing the click.
5. Handling Synchronization
  • After clicking login, the application might redirect to another page (like a dashboard).
  • Playwright automatically waits for navigation, but you may also wait for a specific element on the home/dashboard page to confirm successful login.
6. Validation of Login
  • Positive Scenario: Verify that a unique element on the home page (e.g., a profile icon, welcome message, or logout button) is visible, confirming login success.
  • Negative Scenario: Check for error messages (example: “Invalid username or password”) when wrong credentials are entered.
7. Security & Session Handling
  • Playwright allows capturing and storing cookies or session tokens. This can be reused in future tests to avoid repeated logins.
  • Browser Context ensures each test runs in isolation, preventing session overlap.
8. Tear Down
  • After test execution, close the page, context, and browser to free up resources.
  • This ensures test environments remain clean and consistent.












Website to be automated: 

https://opensource-demo.orangehrmlive.com/web/index.php/auth/login






Add maven dependency in pom.xml:

<dependencies>
    <dependency>
        <groupId>com.microsoft.playwright</groupId>
        <artifactId>playwright</artifactId>
        <version>1.44.0</version>
    </dependency>
</dependencies>

Java Code to Automate Login


import com.microsoft.playwright.*;

public class OrangeHRMLoginTest {
    public static void main(String[] args) {
        // Step 1: Launch Playwright
        try (Playwright playwright = Playwright.create()) {

            // Step 2: Launch a browser (Chromium)
            Browser browser = playwright.chromium().launch(new BrowserType.LaunchOptions().setHeadless(false));

            // Step 3: Create a new browser context
            BrowserContext context = browser.newContext();

            // Step 4: Open a new page
            Page page = context.newPage();

            // Step 5: Navigate to the login page
            page.navigate("https://opensource-demo.orangehrmlive.com/web/index.php/auth/login");

            // Step 6: Wait for username input field to be visible
            page.waitForSelector("input[name='username']");

            // Step 7: Fill in the login credentials
            page.fill("input[name='username']", "Admin");
            page.fill("input[name='password']", "admin123");

            // Step 8: Click the login button
            page.click("button[type='submit']");

            // Step 9: Print login success message
            System.out.println("Login successful!");

            // Optional: Close browser after verification
            browser.close();
        }
    }
}

Code explanation:

Line/BlockExplanation
Playwright.create()Starts Playwright engine
chromium().launch(...)Launches Chromium browser (can be firefox() or webkit() too)
browser.newContext()Creates a new isolated browser context (like incognito)
context.newPage()Opens a new browser tab/page
page.navigate(url)Opens the specified URL
page.fill(selector, value)Enters value into input field (selector is a CSS locator)
page.click(selector)Clicks the element (e.g., login button)
browser.close()Closes the browser at the end

Required Credentials

For this demo:

  • Username: Admin
  • Password: admin123


Points to Consider:
  • This script assumes that the page loads fast enough, but for real-world tests, you should use explicit waits where needed.
  • You can run this from a main method or integrate it into a test framework like JUnit/TestNG for proper test cases.

Comma Selectors in Playwright

 



In Playwright Javacomma selectors refer to compound selectors that use commas , to combine multiple selectors, allowing you to target multiple elements at once — similar to how they work in CSS.


How Comma Selectors Work in Playwright

(1) Multiple Elements in One Locator

  • Instead of writing separate locators for each element type, you can combine them using commas.
  • This is useful when the elements share similar behavior but have different identifiers.

(2) Playwright Behavior

  • Playwright evaluates each selector in the group, then merges the results into a single collection of matched elements.
  • You can then perform actions (click, count, assert visibility, etc.) on those matched elements.

(3) Scenarios Where Useful

  • Different button styles: If "Submit" might be a <button> in one place but an <input> in another, you can write one combined selector.
  • Dynamic UIs: When the element can appear in multiple formats depending on conditions (e.g., mobile vs desktop view).
  • Bulk operations: Selecting multiple types of similar items (like all headings h1, h2, h3).


Key Points to Remember
  • Comma selectors follow CSS selector rules since Playwright supports CSS selectors.
  • They help reduce duplication in locators.
  • But be careful: too many comma selectors can make locators harder to maintain, so use them when elements are truly interchangeable.












What Are Comma Selectors?

comma selector allows you to select multiple elements that match any of the selectors separated by a comma.

Syntax:

Locator locator = page.locator("selector1, selector2, selector3");


Website to be automated: https://www.google.com/









Java Playwright Code:


import com.microsoft.playwright.Browser;
import com.microsoft.playwright.BrowserType;
import com.microsoft.playwright.Locator;
import com.microsoft.playwright.Page;
import com.microsoft.playwright.Playwright;

public class CommaSelectorsExample {
	
	public static void main(String[] args) {
		
	// this code will click Gmail or if instead of Gmail GoogleMail is present like or condition
	Playwright playwright = Playwright.create();
	Browser browser = playwright.chromium().launch(new BrowserType.LaunchOptions().setHeadless(false));
	Page p1 = browser.newPage();
	p1.navigate("https://www.google.co.in");
	p1.locator("a:has-text('Gmail'),a:has-text('GoogleMail') ").click();
	
	//For two links comma seperated selector code is there
	Page p2 = browser.newPage();
	p2.navigate("https://www.google.co.in");
	Locator lc = p2.locator("a:has-text('Gmail'),a:has-text('Images') ");
	System.out.println(lc.count());
	
	//click on Gmail by using xpath
	Page p3 = browser.newPage();
	p2.navigate("https://www.google.co.in");
	Locator gmailLocator = p2.locator("//a[text()='Gmail'] | //a[text()='GooleMail'] ");
	System.out.println(gmailLocator.textContent());
	gmailLocator.click();
	
	browser.close();
	playwright.close();

}
}


Code explanation:

(a) Navigate to the website by page.navigate()
(b) Locator will locate web element either by first or second locator separated by comma or by both, if both are able to find web element.


(c) In next steps also, we are finding web elements by appropriate locator, printing the count and text of the locators.


Important Points:
  • Comma selectors are useful when you want to interact with multiple possible matching elements.
  • Playwright executes them like CSS, meaning it selects all matching elements.