1+ import { expect , test } from "@playwright/test" ;
2+ import { UserRole , verifyUserRow } from "./utils/admin" ;
3+
4+
5+ test . describe ( 'Admin Page' , ( ) => {
6+ test . beforeEach ( async ( { page } ) => {
7+ await test . step ( "Open the admin page" , async ( ) => {
8+ await page . goto ( "/admin" )
9+ } )
10+ } ) ;
11+
12+ test ( "Admin tab table should be visible" , async ( { page } ) => {
13+ await test . step ( 'Check elements visibility' , async ( ) => {
14+ await expect ( page . getByRole ( 'heading' , { name : 'Users' , level : 1 } ) ) . toBeVisible ( ) ;
15+ await expect ( page . getByText ( 'Manage user accounts and permissions' ) ) . toBeVisible ( ) ;
16+ await expect ( page . getByRole ( 'button' , { name : 'Add User' } ) ) . toBeVisible ( ) ;
17+ await expect ( page . locator ( 'th[data-slot="table-head"]' ) ) . toHaveText ( [
18+ 'Full Name' ,
19+ 'Email' ,
20+ 'Role' ,
21+ 'Status' ,
22+ 'Actions'
23+ ] )
24+ } ) ;
25+
26+ await test . step ( 'Check the user table' , async ( ) => {
27+ await verifyUserRow ( page , 'N/A' , 'admin@example.com' , UserRole . SUPERUSER , 'Active' , true ) ;
28+ } ) ;
29+ } )
30+
31+
32+ test ( 'User Dialog should have all fields visible' , async ( { page } ) => {
33+ const addUserBtn = page . getByRole ( 'button' , { name : 'Add User' } ) ;
34+
35+ await test . step ( "Open the Dialog" , async ( ) => {
36+ await expect ( addUserBtn ) . toBeVisible ( ) ;
37+ await addUserBtn . click ( ) ;
38+ } ) ;
39+
40+ const dialog = page . getByRole ( 'dialog' , { name : 'Add User' } ) ;
41+
42+ await test . step ( "Fill Inputs" , async ( ) => {
43+ await expect ( dialog ) . toBeVisible ( ) ;
44+ await expect ( page . getByRole ( 'heading' , { name : 'Add User' , level : 2 } ) ) . toBeVisible ( ) ;
45+ await expect ( dialog . getByText ( 'Fill in the form below to add a new user' ) ) . toBeVisible ( ) ;
46+
47+ const fields = [ 'Email' , 'Full Name' , 'Set Password' , 'Confirm Password' ] ;
48+ for ( const field of fields ) {
49+ await expect ( dialog . getByLabel ( field ) ) . toBeVisible ( ) ;
50+ await expect ( dialog . locator ( 'label[data-slot="form-label"]' ) . filter ( { hasText : field } ) )
51+ . toBeVisible ( ) ;
52+ }
53+
54+ // Checkboxes
55+ await expect ( dialog . getByRole ( 'checkbox' , { name : 'Is superuser?' } ) ) . toBeVisible ( ) ;
56+ await expect ( dialog . getByRole ( 'checkbox' , { name : 'Is active?' } ) ) . toBeVisible ( ) ;
57+ } ) ;
58+
59+ await test . step ( "Close the Dialog" , async ( ) => {
60+ // Footer Buttons
61+ const cancelBtn = dialog . getByRole ( 'button' , { name : 'Cancel' } ) ;
62+ await expect ( cancelBtn ) . toBeVisible ( ) ;
63+ await expect ( dialog . getByRole ( 'button' , { name : 'Save' } ) ) . toBeVisible ( ) ;
64+
65+ // Close the dialog
66+ await cancelBtn . click ( ) ;
67+ // Check if Add User button is visible after closing the dialog
68+ await expect ( addUserBtn ) . toBeVisible ( ) ;
69+ } ) ;
70+ } ) ;
71+
72+
73+ test ( 'User Dialog should have all error fields visible' , async ( { page } ) => {
74+ const addUserBtn = page . getByRole ( 'button' , { name : 'Add User' } ) ;
75+
76+ await test . step ( "Open the Dialog" , async ( ) => {
77+ await expect ( addUserBtn ) . toBeVisible ( ) ;
78+ await addUserBtn . click ( ) ;
79+ } ) ;
80+
81+ const dialog = page . getByRole ( 'dialog' , { name : 'Add User' } ) ;
82+
83+ await test . step ( "Trigger error messages" , async ( ) => {
84+ await expect ( dialog ) . toBeVisible ( ) ;
85+
86+ // Trigger error messages by clicking on input field
87+ await dialog . getByLabel ( 'Email' ) . click ( ) ;
88+ await dialog . getByLabel ( 'Set Password' ) . click ( ) ;
89+ await dialog . getByLabel ( 'Confirm Password' ) . click ( ) ;
90+
91+ // Click Save to trigger error message on 'Confirm Password' field
92+ const saveBtn = dialog . getByRole ( 'button' , { name : 'Save' } ) ;
93+ await saveBtn . click ( ) ;
94+
95+ // Check the error messages
96+ await expect ( dialog . getByText ( 'Invalid email address' ) ) . toBeVisible ( ) ;
97+ await expect ( dialog . getByText ( 'Password is required' ) ) . toBeVisible ( ) ;
98+ await expect ( dialog . getByText ( 'Please confirm your password' ) ) . toBeVisible ( ) ;
99+ } ) ;
100+
101+ await test . step ( "Close the Dialog" , async ( ) => {
102+ const cancelBtn = dialog . getByRole ( 'button' , { name : 'Cancel' } ) ;
103+ await cancelBtn . click ( ) ;
104+ // Check if Add User button is visible after closing the dialog
105+ await expect ( dialog ) . toBeHidden ( ) ;
106+ await expect ( addUserBtn ) . toBeVisible ( ) ;
107+ } ) ;
108+ } ) ;
109+
110+
111+ test ( 'Admin should fill out the Add User form, save then delete it' , async ( { page } ) => {
112+ const email = 'becebal.burebista@example.com' ;
113+ const fullName = 'Decebal Burebista' ;
114+ const password = 'SecurePass123!' ;
115+
116+ const addUserBtn = page . getByRole ( 'button' , { name : 'Add User' } ) ;
117+ await expect ( addUserBtn ) . toBeVisible ( ) ;
118+ await addUserBtn . click ( ) ;
119+
120+ const dialog = page . getByRole ( 'dialog' , { name : 'Add User' } ) ;
121+ await expect ( dialog ) . toBeVisible ( ) ;
122+
123+ await test . step ( "Fill out text and password fields" , async ( ) => {
124+ await dialog . getByLabel ( 'Email' ) . fill ( email ) ;
125+ await dialog . getByLabel ( 'Full Name' ) . fill ( fullName ) ;
126+ await dialog . locator ( 'input[name="password"]' ) . fill ( password ) ;
127+ await dialog . locator ( 'input[name="confirm_password"]' ) . fill ( password ) ;
128+
129+ // Toggle Checkboxes
130+ const superuserCheckbox = dialog . getByRole ( 'checkbox' , { name : 'Is superuser?' } ) ;
131+ const activeCheckbox = dialog . getByRole ( 'checkbox' , { name : 'Is active?' } ) ;
132+
133+ await superuserCheckbox . check ( ) ;
134+ await activeCheckbox . check ( ) ;
135+
136+ // Verify the data was entered correctly before saving
137+ await expect ( dialog . getByLabel ( 'Email' ) ) . toHaveValue ( email ) ;
138+ await expect ( dialog . getByLabel ( 'Full Name' ) ) . toHaveValue ( fullName ) ;
139+ await expect ( dialog . getByLabel ( 'Set Password' ) ) . toHaveValue ( password ) ;
140+ await expect ( dialog . getByLabel ( 'Confirm Password' ) ) . toHaveValue ( password ) ;
141+ await expect ( superuserCheckbox ) . toBeChecked ( ) ;
142+ await expect ( activeCheckbox ) . toBeChecked ( ) ;
143+ } ) ;
144+
145+ await test . step ( "Save the User" , async ( ) => {
146+ const saveButton = dialog . getByRole ( 'button' , { name : 'Save' } ) ;
147+ await saveButton . click ( ) ;
148+
149+ // Verify the dialog closes
150+ await expect ( dialog ) . toBeHidden ( ) ;
151+ await expect ( addUserBtn ) . toBeVisible ( ) ;
152+ } ) ;
153+
154+ await test . step ( "Check the new user in the user table" , async ( ) => {
155+ await verifyUserRow ( page , fullName , email , UserRole . SUPERUSER , 'Active' ) ;
156+ } ) ;
157+
158+ await test . step ( "Cleanup" , async ( ) => {
159+ const userRow = page . getByRole ( 'row' ) . filter ( { hasText : email } ) ;
160+
161+ // Click the "ellipsis" trigger inside that row
162+ await userRow . getByRole ( 'button' , { name : 'menu' } ) . or ( userRow . locator ( '[data-slot="dropdown-menu-trigger"]' ) ) . click ( ) ;
163+
164+ // Click "Delete User" from the menu that appears globally
165+ await page . getByRole ( 'menuitem' , { name : 'Delete User' } ) . click ( ) ;
166+
167+ // Confirm the deletion in the resulting dialog
168+ const confirmDialog = page . getByRole ( 'dialog' ) ;
169+ await confirmDialog . getByRole ( 'button' , { name : 'Delete' } ) . click ( ) ;
170+ } ) ;
171+ } ) ;
172+ } ) ;
0 commit comments