Fork me on GitHub

Fluent Authentication API (Recommended)


@BrxmJaxrsTest(beanPackages = {"org.example.model"})
class SecureApiTest {

    @Test
    void authenticatedUser_canAccessProtectedEndpoint(DynamicJaxrsTest brxm) {
        String response = brxm.request()
            .get("/site/api/protected")
            .asUser("john", "admin", "editor")  // username + roles
            .execute();

        assertThat(response).contains("Welcome, john");
    }

    @Test
    void adminRole_canAccessDashboard(DynamicJaxrsTest brxm) {
        String response = brxm.request()
            .get("/site/api/dashboard")
            .withRole("admin")  // role-only (no username)
            .execute();

        assertThat(response).contains("dashboard");
    }
}
        

Method Reference

Method Description
asUser(username, roles...) Sets remote user and roles
withRole(roles...) Sets roles without username

When to Use Each

Use asUser() when:

  • Your code checks request.getRemoteUser() or principal name
  • You need to identify the specific user in tests
  • Testing personalized content or user-specific features

Use withRole() when:

  • Your code only checks roles via request.isUserInRole()
  • Testing role-based access control without user identity

Testing Auth Failures


@BrxmJaxrsTest(
    beanPackages = {"org.example.model"},
    resources = {AuthResource.class}
)
class AuthResourceTest {

    @Test
    void login_fails_forInvalidUser(DynamicJaxrsTest brxm) {
        brxm.authentication().rejectUser("unknown");

        String response = brxm.request()
            .post("/site/api/auth/login")
            .withBody("{\"username\":\"unknown\",\"password\":\"any\"}")
            .execute();

        assertThat(response).contains("401");
    }

    @Test
    void login_fails_forWrongPassword(DynamicJaxrsTest brxm) {
        brxm.authentication().rejectPassword("wrongpassword");

        String response = brxm.request()
            .post("/site/api/auth/login")
            .withBody("{\"username\":\"john\",\"password\":\"wrongpassword\"}")
            .execute();

        assertThat(response).contains("Invalid credentials");
    }

    @Test
    void login_fails_forLockedAccount(DynamicJaxrsTest brxm) {
        brxm.authentication()
            .rejectUser("locked")
            .rejectUser("disabled");

        // Both users will fail authentication
    }
}
        
Method Description
rejectUser(username) Reject credentials with this username
rejectPassword(password) Reject credentials with this password

Methods are chainable and automatically reset between tests.

PageModel API Authentication


@BrxmPageModelTest(loadProjectContent = true)
class SecurePageModelTest {

    @Test
    void premiumUser_seesExclusiveContent(DynamicPageModelTest brxm) throws Exception {
        PageModelResponse pageModel = brxm.request()
            .get("/site/resourceapi/premium")
            .asUser("subscriber", "premium-tier")
            .executeAsPageModel();

        assertThat(pageModel.findComponentByName("ExclusiveContent")).isPresent();
    }
}
        

Principal-Based Authentication

For manual principal setup in component tests:


@BrxmComponentTest(beanPackages = {"com.example.beans"})
class LoginComponentTest {

    private void setLoggedInUser(String username, DynamicComponentTest brxm) {
        Principal principal = mock(Principal.class);
        when(principal.getName()).thenReturn(username);
        brxm.getHstRequest().setUserPrincipal(principal);
    }

    @Test
    void doBeforeRender_whenNotLoggedIn_setsLoggedInFalse(DynamicComponentTest brxm) {
        component.doBeforeRender(brxm.getHstRequest(), brxm.getHstResponse());

        Boolean loggedIn = brxm.getRequestAttributeValue("loggedin");
        assertThat(loggedIn).isFalse();
    }

    @Test
    void doBeforeRender_whenLoggedIn_setsLoggedInTrue(DynamicComponentTest brxm) {
        setLoggedInUser("testuser", brxm);

        component.doBeforeRender(brxm.getHstRequest(), brxm.getHstResponse());

        Boolean loggedIn = brxm.getRequestAttributeValue("loggedin");
        assertThat(loggedIn).isTrue();
    }
}
        

Session-Based Authentication


@Test
void doBeforeRender_withUserProfile_createsUserFromProfile(DynamicComponentTest brxm) {
    setLoggedInUser("john", brxm);

    UserProfile userProfile = new UserProfile();
    userProfile.setFirstname("John");
    userProfile.setLastname("Doe");
    userProfile.setGroups(Arrays.asList("everybody", "premium-tier"));

    HttpSession session = mock(HttpSession.class);
    when(session.getAttribute("user")).thenReturn(null);
    when(session.getAttribute("userProfile")).thenReturn(userProfile);
    brxm.getHstRequest().setSession(session);

    component.doBeforeRender(brxm.getHstRequest(), brxm.getHstResponse());

    UserModel userModel = brxm.getRequestAttributeValue("user");
    assertThat(userModel.getFirstname()).isEqualTo("John");
}
        

Role/Tier Helper Methods


@BrxmPageModelTest
class DashboardPageModelApiTest {

    private void authenticateUser(String username, String firstname,
                                   String lastname, List<String> groups,
                                   DynamicPageModelTest brxm) {
        Principal principal = mock(Principal.class);
        when(principal.getName()).thenReturn(username);
        brxm.getHstRequest().setUserPrincipal(principal);

        User user = new User(firstname, lastname, groups);
        HttpSession session = mock(HttpSession.class);
        when(session.getAttribute("user")).thenReturn(user);
        brxm.getHstRequest().setSession(session);
    }

    // Role-specific convenience methods
    private void authenticateAsFreeUser(DynamicPageModelTest brxm) {
        authenticateUser("freeuser", "Free", "User",
            Arrays.asList("everybody", "petbase-free"), brxm);
    }

    private void authenticateAsEssentialUser(DynamicPageModelTest brxm) {
        authenticateUser("essentialuser", "Essential", "User",
            Arrays.asList("everybody", "petbase-essential"), brxm);
    }

    @Test
    void essentialTier_userHasLocationMap(DynamicPageModelTest brxm) throws Exception {
        authenticateAsEssentialUser(brxm);

        PageModelResponse pageModel = brxm.request()
            .get("/site/resourceapi/dashboard")
            .executeAsPageModel();

        PageComponent locationMap = pageModel.findComponentByName("LocationMap").orElseThrow();
        assertThat(locationMap.getComponentClass())
            .isEqualTo("com.example.components.LocationMapComponent");
    }
}
        

Test Coverage Checklist

  • Unauthenticated state - No principal, no session
  • Principal only - Principal set, no session user
  • Session user - Full user object in session
  • User profile - External profile (e.g., from SSO/SAML)
  • Each subscription tier - Free, basic, premium, etc.
  • Role-based access - Admin, editor, viewer permissions
  • Login parameters - ?login=true, ?error=true
  • Session expiry - Invalidated or expired sessions
  • Invalid credentials - Wrong username/password
  • Locked accounts - Disabled or suspended users

Test Naming Convention


// Good: Clear authentication context
@Test void unauthenticated_dashboardRedirectsToLogin()
@Test void freeTier_userSeesUpgradeBanner()
@Test void essentialTier_userHasLocationTracking()
@Test void adventureTier_userHasAllFeatures()

// Avoid: Ambiguous about auth state
@Test void testDashboard()
@Test void dashboardWorks()
        

Related