Log in as a user from the worldParameters.users registry in cucumber.js, by its handle rather than by typing credentials into the feature file:
users: {
admin: { username: 'admin', password: process.env.DRUPAL_ADMIN_PASS || 'admin' },
editor: { username: 'editor', password: process.env.DRUPAL_EDITOR_PASS || 'editor' },
}
Opens /user/login, fills #edit-name and #edit-pass and submits by dispatching the submit button's click inside the page, with the navigation wait armed in the same Promise.all, then settles the landing page. The in-page submit is what keeps the login reliable under a sticky bar, a chat widget or a cookie banner that covers the button and would otherwise turn a pointer click into an actionability timeout.
For suites that log in often, pair it once with webship-js's "I save the auth state to" step and restore that state in the other scenarios.
Examples
Given I am a logged in user with the "admin" user
Given I am a logged in user with the username "editor"
Given we are a logged in user with "admin"
Given a logged in user with the "editor" user
And I am a logged in user with the "content editor" user
Pattern
Given(/^(I am |we are )*a logged in user with( the)*( username)* "([^"]*)?"( user)*$/, …)
Part of @webship-js/drupal-core-steps (github.com/webship/drupal-core-steps), a step pack for Webship-js 2.0.x.