> Markdown version of [Set Up Browserless Tests with Quarkus](https://vaadin.com/docs/next/building-apps/testing/browserless/setup-quarkus). Section index: [llms.txt](https://vaadin.com/docs/next/building-apps/llms.txt)

# Set Up Browserless Tests with Quarkus

Use this guide for a Quarkus Flow application. Tests extend `QuarkusBrowserlessTest` and run with `@QuarkusTest`. For a Java EE application that uses Vaadin CDI and Weld, use [the separate CDI setup](https://vaadin.com/docs/next/building-apps/testing/browserless/setup-cdi.md).

## <a id="add-dependencies"></a>Add Dependencies

With the Vaadin BOM imported, add these test dependencies to your `pom.xml` file:

pom.xml

```xml
<dependency>
    <groupId>com.vaadin</groupId>
    <artifactId>browserless-test-junit6</artifactId>
    <scope>test</scope>
</dependency>
<dependency>
    <groupId>com.vaadin</groupId>
    <artifactId>browserless-test-quarkus</artifactId>
    <scope>test</scope>
</dependency>
<dependency>
    <groupId>io.quarkus</groupId>
    <artifactId>quarkus-junit</artifactId>
    <scope>test</scope>
</dependency>
```

## <a id="create-a-test"></a>Create a Test

Create this view:

`HelloWorldView.java`

```java
import com.vaadin.flow.component.button.Button;
import com.vaadin.flow.component.notification.Notification;
import com.vaadin.flow.component.orderedlayout.HorizontalLayout;
import com.vaadin.flow.component.textfield.TextField;
import com.vaadin.flow.router.Route;

@Route("")
public class HelloWorldView extends HorizontalLayout {

    TextField name;
    Button sayHello;

    public HelloWorldView() {
        name = new TextField("Your name");
        sayHello = new Button("Say hello");
        sayHello.addClickListener(e -> {
            Notification.show("Hello " + name.getValue());
        });
        add(name, sayHello);
    }
}
```

Create a test class that extends `QuarkusBrowserlessTest`, in the same Java package as the view under `src/test/java`:

`HelloWorldViewTest.java`

```java
import org.junit.jupiter.api.Assertions;
import org.junit.jupiter.api.Test;
import com.vaadin.browserless.quarkus.QuarkusBrowserlessTest;
import com.vaadin.flow.component.notification.Notification;
import io.quarkus.test.junit.QuarkusTest;

@QuarkusTest
class HelloWorldViewTest extends QuarkusBrowserlessTest {
    @Test
    public void setText_clickButton_notificationIsShown() {
        final HelloWorldView helloView = navigate(HelloWorldView.class);

        test(helloView.name).setValue("Test");
        test(helloView.sayHello).click();

        Notification notification = find(Notification.class).single();
        Assertions.assertEquals("Hello Test", test(notification).getText());
    }
}
```

See [How a Browserless Test Works](https://vaadin.com/docs/next/building-apps/testing/browserless/test-user-interactions.md#how-a-browserless-test-works) for what each line of the test does.

> **Note:** `@QuarkusTest` starts the application and its HTTP server, which browserless tests don’t use. The `QuarkusBrowserlessTest` tests still run in a mocked Vaadin environment.

## <a id="run-the-test"></a>Run the Test

Run the test from your IDE or with `mvn test`. The test passes when entering a name and clicking the button shows the expected notification.

## <a id="replace-a-service-with-a-test-profile"></a>Replace a Service with a Test Profile

Annotate a test with `@TestProfile` to run it with a specific test configuration. A test profile can, for example, override application configuration, enable bean alternatives, and provide custom test resources. See the [Quarkus Testing Profiles documentation](https://quarkus.io/guides/getting-started-testing#testing_different_profiles) for all options.

This example replaces a `GreetingService` with a test implementation. It assumes a `WelcomeView` that shows the result of `greetingService.greet("Quarkus")` in a span stored in its `greeting` field. The test implementation is a CDI bean annotated with `@Alternative`:

`MockService.java`

```java
import jakarta.enterprise.context.ApplicationScoped;
import jakarta.enterprise.inject.Alternative;

@Alternative
@ApplicationScoped
public class MockService implements GreetingService {
    @Override
    public String greet(String name) {
        return "Hello " + name + " from the mock service";
    }
}
```

The profile enables the alternative and also overrides the `app.some.config` property:

`MockServiceProfile.java`

```java
import java.util.Collections;
import java.util.Map;
import java.util.Set;
import io.quarkus.test.junit.QuarkusTestProfile;

public class MockServiceProfile implements QuarkusTestProfile {

    @Override
    public Map<String, String> getConfigOverrides() {
        return Collections.singletonMap("app.some.config","value");
    }

    @Override
    public Set<Class<?>> getEnabledAlternatives() {
        return Collections.singleton(MockService.class);
    }
}
```

A test that uses the profile gets the alternative injected into the view:

`MockServiceViewTest.java`

```java
import org.junit.jupiter.api.Assertions;
import org.junit.jupiter.api.Test;
import com.vaadin.browserless.quarkus.QuarkusBrowserlessTest;
import io.quarkus.test.junit.QuarkusTest;
import io.quarkus.test.junit.TestProfile;

@QuarkusTest
@TestProfile(MockServiceProfile.class)
class MockServiceViewTest extends QuarkusBrowserlessTest {
    @Test
    void view_usesMockService() {
        WelcomeView view = navigate(WelcomeView.class);
        Assertions.assertEquals("Hello Quarkus from the mock service",
                view.greeting.getText());
    }
}
```

## <a id="next-steps"></a>Next Steps

- [Test User Interactions](https://vaadin.com/docs/next/building-apps/testing/browserless/test-user-interactions.md) explains how the test works and how to cover more complex views.

- [Test View Access Control](https://vaadin.com/docs/next/building-apps/testing/browserless/test-view-access.md#quarkus) covers protected views with Quarkus Security.

- [Debug a Failing Browserless Test](https://vaadin.com/docs/next/building-apps/testing/browserless/debug-tests.md) helps when a test fails.

`09A26994-97AB-4877-AEB1-717BE02E348D`
