Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Fix Admin-UI management bugs #1588

Merged
merged 39 commits into from
Jan 29, 2025
Merged

Fix Admin-UI management bugs #1588

merged 39 commits into from
Jan 29, 2025

Conversation

SamuelWei
Copy link
Collaborator

@SamuelWei SamuelWei commented Nov 19, 2024

Fixes #1675
Fixes #1677
Fixes #1711
Fixes #1751

Type (Highlight the corresponding type)

  • Bugfix
  • Feature
  • Documentation
  • Refactoring (e.g. Style updates, Test implementation, etc.)
  • Other (please describe):

Checklist

  • Code updated to current develop branch head
  • Passes CI checks
  • Is a part of an issue
  • Tests added for the bugfix or newly implemented feature: part of other PR
  • Changelog is updated
  • Documentation of code and features exists

Changes

  • Close multiselect dropdowns on selection
  • Bugfix overlay reload buttons
  • Fix overlays not shown after loading error (admin view pages)
  • Fix search not disabled during loading (admin index pages)
  • Fix dialog buttons not disabled correctly during actions on admin pages
  • Fix error messages (AdminServerPoolsView, AdminRoomTypesView, AdminSettings)
  • Fix error handling (AdminUsersIndex, AdminServerPoolsView (staleError), RoomTypesDeleteButton (404 error))
  • Add missing loading retry button (Admin RoomTypesIndex)
  • Add reload button for replacement room type (RoomTypesDeleteButton)
  • Fix bbb logo image url input
  • Fix access superuser attribute
  • Fix accessing multiselect ref
  • Permissions loading behaviour (AdminRolesView)

Other information

Summary by CodeRabbit

Summary by CodeRabbit

Release Notes

  • New Features

    • Added loading retry buttons for admin index and view pages.
    • Introduced reload buttons for replacement room types.
    • Added a missing loading retry button on the room types overview page.
  • Bug Fixes

    • Improved error handling across admin views and components.
    • Fixed search and button interactions during loading states.
    • Corrected multiselect dropdown and overlay behaviors.
    • Enhanced permissions and user role management.
    • Resolved issues with form validation error messages on various pages.
  • Improvements

    • Updated form validation for settings, including handling of nullable fields.
    • Refined user interface error messaging.
    • Improved accessibility and user interaction states.
    • Enhanced the user experience with visual feedback during loading operations.
  • Performance

    • Optimized error state management in various components.

@SamuelWei SamuelWei marked this pull request as draft November 19, 2024 16:47
Copy link

codecov bot commented Nov 19, 2024

Codecov Report

Attention: Patch coverage is 11.53846% with 23 lines in your changes missing coverage. Please review.

Project coverage is 81.28%. Comparing base (9dd1542) to head (ce68db2).
Report is 1 commits behind head on develop.

Files with missing lines Patch % Lines
resources/js/views/AdminRolesView.vue 0.00% 11 Missing ⚠️
...es/js/components/SettingsRoomTypesDeleteButton.vue 0.00% 3 Missing ⚠️
resources/js/views/AdminRoomTypesIndex.vue 0.00% 3 Missing ⚠️
resources/js/views/AdminSettings.vue 0.00% 3 Missing ⚠️
resources/js/views/AdminUsersIndex.vue 0.00% 2 Missing ⚠️
resources/js/views/AdminServerPoolsView.vue 0.00% 1 Missing ⚠️
Additional details and impacted files
@@              Coverage Diff              @@
##             develop    #1588      +/-   ##
=============================================
- Coverage      81.43%   81.28%   -0.15%     
  Complexity      1410     1410              
=============================================
  Files            364      364              
  Lines           9559     9576      +17     
  Branches         874      879       +5     
=============================================
  Hits            7784     7784              
- Misses          1775     1792      +17     

☔ View full report in Codecov by Sentry.
📢 Have feedback on the report? Share it here.

Copy link

cypress bot commented Nov 19, 2024

PILOS    Run #1845

Run Properties:  status check passed Passed #1845  •  git commit 4f2f2982ec: Fix Admin-UI management bugs (#1588)
Project PILOS
Branch Review develop
Run status status check passed Passed #1845
Run duration 09m 00s
Commit git commit 4f2f2982ec: Fix Admin-UI management bugs (#1588)
Committer Samuel Weirich
View all properties for this run ↗︎

Test results
Tests that failed  Failures 0
Tests that were flaky  Flaky 0
Tests that did not run due to a developer annotating a test with .skip  Pending 0
Tests that did not run due to a failure in a mocha hook  Skipped 0
Tests that passed  Passing 240
View all changes introduced in this branch ↗︎

@SamuelWei SamuelWei changed the title Fix Admin-UI user management bugs Fix Admin-UI management bugs Nov 20, 2024
@Sabr1n4W Sabr1n4W linked an issue Dec 16, 2024 that may be closed by this pull request
@Sabr1n4W Sabr1n4W linked an issue Jan 9, 2025 that may be closed by this pull request
Copy link

coderabbitai bot commented Jan 27, 2025

Walkthrough

This pull request introduces comprehensive improvements across various components in the application, focusing on error handling, loading states, and user interface interactions. The changes span multiple files, addressing issues with search functionality during loading, overlay display after errors, dialog button states, and form validation. Key modifications include disabling search inputs during data loading, showing reload buttons after loading errors, and ensuring dialog buttons are correctly disabled during actions.

Changes

File Change Summary
app/Http/Requests/UpdateSettings.php Made bbb_logo field nullable in validation rules
resources/js/components/RoleSelect.vue Updated template ref and import for multiselect component
resources/js/components/Settings*DeleteButton.vue Added :disabled="isBusy" to "No" buttons in delete dialogs
resources/js/views/Admin*Index.vue Added :disabled="isBusy" to search inputs and buttons
resources/js/views/Admin*View.vue Enhanced error handling and overlay display for loading states
resources/js/views/AdminSettings.vue Updated form data handling for logo and style settings
tests/Backend/Feature/api/v1/SettingsTest.php Adjusted tests to use empty strings for clearing settings instead of null

Assessment against linked issues

Objective Addressed Explanation
Search disabled during loading [#1675]
Overlay shown after loading error [#1677]
Dialog buttons disabled during actions [#1711]
BBB logo input clearing [#1751]

Possibly related PRs

  • Fix room limit radio on edit roles page not reset on stale error #1825: Changes in the main PR include updates to the permissions loading behavior on the view/edit page of roles, which may relate to the fix for the room limit radio button not resetting on stale errors in the retrieved PR. Both PRs address user interface behavior in the context of roles and error handling.

Suggested reviewers

  • Sabr1n4W

🪧 Tips

Chat

There are 3 ways to chat with CodeRabbit:

  • Review comments: Directly reply to a review comment made by CodeRabbit. Example:
    • I pushed a fix in commit <commit_id>, please review it.
    • Generate unit testing code for this file.
    • Open a follow-up GitHub issue for this discussion.
  • Files and specific lines of code (under the "Files changed" tab): Tag @coderabbitai in a new review comment at the desired location with your query. Examples:
    • @coderabbitai generate unit testing code for this file.
    • @coderabbitai modularize this function.
  • PR comments: Tag @coderabbitai in a new PR comment to ask questions about the PR branch. For the best results, please provide a very specific query, as very limited context is provided in this mode. Examples:
    • @coderabbitai gather interesting stats about this repository and render them as a table. Additionally, render a pie chart showing the language distribution in the codebase.
    • @coderabbitai read src/utils.ts and generate unit testing code.
    • @coderabbitai read the files in the src/scheduler package and generate a class diagram using mermaid and a README in the markdown format.
    • @coderabbitai help me debug CodeRabbit configuration file.

Note: Be mindful of the bot's finite context window. It's strongly recommended to break down tasks such as reading entire modules into smaller chunks. For a focused discussion, use review comments to chat about specific files and their changes, instead of using the PR comments.

CodeRabbit Commands (Invoked using PR comments)

  • @coderabbitai pause to pause the reviews on a PR.
  • @coderabbitai resume to resume the paused reviews.
  • @coderabbitai review to trigger an incremental review. This is useful when automatic reviews are disabled for the repository.
  • @coderabbitai full review to do a full review from scratch and review all the files again.
  • @coderabbitai summary to regenerate the summary of the PR.
  • @coderabbitai generate docstrings to generate docstrings for this PR. (Beta)
  • @coderabbitai resolve resolve all the CodeRabbit review comments.
  • @coderabbitai configuration to show the current CodeRabbit configuration for the repository.
  • @coderabbitai help to get help.

Other keywords and placeholders

  • Add @coderabbitai ignore anywhere in the PR description to prevent this PR from being reviewed.
  • Add @coderabbitai summary to generate the high-level summary at a specific location in the PR description.
  • Add @coderabbitai anywhere in the PR title to generate the title automatically.

CodeRabbit Configuration File (.coderabbit.yaml)

  • You can programmatically configure CodeRabbit by adding a .coderabbit.yaml file to the root of your repository.
  • Please see the configuration documentation for more information.
  • If your editor has YAML language server enabled, you can add the path at the top of this file to enable auto-completion and validation: # yaml-language-server: $schema=https://coderabbit.ai/integrations/schema.v2.json

Documentation and Community

  • Visit our Documentation for detailed information on how to use CodeRabbit.
  • Join our Discord Community to get help, request features, and share feedback.
  • Follow us on X/Twitter for updates and announcements.

…ui-user-management

# Conflicts:
#	resources/js/components/SettingsRoomTypesDeleteButton.vue
@SamuelWei SamuelWei force-pushed the fix-admin-ui-user-management branch from 0a44ed5 to 1530eed Compare January 27, 2025 08:59
@SamuelWei SamuelWei marked this pull request as ready for review January 29, 2025 15:55
Copy link

@coderabbitai coderabbitai bot left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Actionable comments posted: 0

🔭 Outside diff range comments (1)
resources/js/views/AdminServersIndex.vue (1)

Line range hint 191-227: Remove disabled state from router links.

The :disabled="isBusy" binding on router links (as="router-link") is unnecessary and might impact user experience. Users should be able to navigate away during data loading operations.

 <Button
   v-if="userPermissions.can('view', slotProps.data)"
   v-tooltip="$t('admin.servers.view', { name: slotProps.data.name })"
   as="router-link"
-  :disabled="isBusy"
   :aria-label="$t('admin.servers.view', { name: slotProps.data.name })"
   :to="{ name: 'admin.servers.view', params: { id: slotProps.data.id } }"
   icon="fa-solid fa-eye"
 />
 <Button
   v-if="userPermissions.can('update', slotProps.data)"
   v-tooltip="$t('admin.servers.edit', { name: slotProps.data.name })"
   as="router-link"
-  :disabled="isBusy"
   :aria-label="$t('admin.servers.edit', { name: slotProps.data.name })"
   :to="{ name: 'admin.servers.edit', params: { id: slotProps.data.id } }"
   severity="info"
   icon="fa-solid fa-edit"
 />
🧹 Nitpick comments (14)
app/Http/Requests/UpdateSettings.php (1)

80-80: LGTM! Consider adding a comment to document the nullable field.

The change to make bbb_logo nullable is correct and aligns with the ability to clear the logo in the UI.

-            'bbb_logo' => ['nullable', 'string', 'max:255'],
+            'bbb_logo' => ['nullable', 'string', 'max:255'], // Nullable to allow clearing the logo
resources/js/views/AdminServersIndex.vue (1)

8-8: LGTM! Consider adding a loading indicator.

The disabled states correctly prevent duplicate API calls during loading. Consider adding a loading spinner to provide better visual feedback.

 <InputText
   v-model="filter"
   :disabled="isBusy"
+  :loading="isBusy"
   :placeholder="$t('app.search')"
   @keyup.enter="loadData(1, false)"
 />

Also applies to: 14-14

resources/js/views/AdminServerPoolsView.vue (3)

33-34: LGTM! Consider enhancing error state accessibility.

The overlay implementation with retry functionality aligns well with the PR objectives to fix overlay reload buttons. The form's aria-hidden attribute during error states is a good accessibility practice.

Consider adding an aria-live region to announce loading errors to screen readers:

 <OverlayComponent :show="isBusy || modelLoadingError">
   <template #overlay>
-    <LoadingRetryButton
+    <LoadingRetryButton
+      aria-live="polite"
       :error="modelLoadingError"
       @reload="load"
     ></LoadingRetryButton>
   </template>

384-384: Add defensive programming for stale error handling.

While the property path correction is good, consider adding null checks to prevent potential runtime errors.

-      name.value = staleError.new_model.name;
+      name.value = staleError?.new_model?.name ?? model.value.name;

Line range hint 33-182: Consider enhancing error state feedback.

While the loading and error states are handled well, consider improving the user experience during server loading errors:

  1. Add a toast notification when server loading fails
  2. Show an inline error message explaining why the servers couldn't be loaded
 function loadServers(page = 1) {
   serversLoading.value = true;
+  const toast = useToast();

   const config = {
     params: {
       page,
     },
   };

   api
     .call("servers", config)
     .then((response) => {
       serversLoadingError.value = false;
       servers.value = response.data.data;
       serversCurrentPage.value = page;
       serversHasNextPage.value = page < response.data.meta.last_page;
     })
     .catch((error) => {
       serversMultiselectRef.value.deactivate();
       serversLoadingError.value = true;
+      toast.add({
+        severity: 'error',
+        summary: t('app.errors.loading_failed'),
+        detail: t('admin.servers.loading_failed'),
+        life: 3000
+      });
       api.error(error);
     })
     .finally(() => {
       serversLoading.value = false;
     });
 }
resources/js/components/UserTabSecurityRolesAndPermissionsSection.vue (3)

19-19: Good use of optional chaining operator!

The addition of the optional chaining operator (?.) is a good defensive programming practice that prevents potential runtime errors when currentUser is null/undefined.

Consider adding a computed property for better reusability and testing:

+ const canManageSuperuser = computed(() => authStore.currentUser?.superuser)
- :disable-superuser="!authStore.currentUser?.superuser"
+ :disable-superuser="!canManageSuperuser"

Line range hint 27-31: Consider adding a retry mechanism for role loading errors.

While the error handling is comprehensive, users have no way to retry when role loading fails. This aligns with the PR objectives of improving error handling across admin views.

Consider adding a retry button when rolesLoadingError is true:

  <div class="flex justify-end">
+   <Button
+     v-if="rolesLoadingError"
+     @click="$emit('retry-roles-loading')"
+     :label="$t('app.retry')"
+     icon="fa-solid fa-sync"
+     class="mr-2"
+   />
    <Button
      v-if="!viewOnly && userPermissions.can('editUserRole', model)"
      :disabled="isBusy || rolesLoadingError || rolesLoading"
      type="submit"
      :loading="isBusy"
      :label="$t('app.save')"
      icon="fa-solid fa-save"
    />
  </div>

Line range hint 108-142: Enhance error handling in the save function.

While the error handling is comprehensive, consider adding timeout handling and a retry mechanism for network failures to improve reliability.

Consider these improvements:

 function save(event) {
   if (event) {
     event.preventDefault();
   }
   isBusy.value = true;
   formErrors.clear();
 
   api
     .call("users/" + model.value.id, {
       method: "put",
+      timeout: 5000, // 5 second timeout
       data: {
         roles: model.value.roles.map((role) => role.id),
         updated_at: model.value.updated_at,
       },
     })
     .then((response) => {
       emit("updateUser", response.data.data);
     })
     .catch((error) => {
+      if (error.code === 'ECONNABORTED') {
+        api.error(new Error('Request timed out. Please try again.'));
+        return;
+      }
       if (error.response && error.response.status === env.HTTP_NOT_FOUND) {
         emit("notFoundError", error);
       } else if (
         error.response &&
         error.response.status === env.HTTP_UNPROCESSABLE_ENTITY
       ) {
         formErrors.set(error.response.data.errors);
       } else if (
         error.response &&
         error.response.status === env.HTTP_STALE_MODEL
       ) {
         emit("staleError", error.response.data);
       } else {
         api.error(error);
       }
     })
     .finally(() => {
       isBusy.value = false;
     });
 }
resources/js/components/UserTabEmail.vue (3)

124-124: LGTM! Consider additional defensive checks.

The optional chaining operator is a good addition that prevents runtime errors when currentUser is undefined. However, consider adding a complete null check for both sides of the comparison for maximum robustness.

-  return authStore.currentUser?.id === props.user.id;
+  return authStore.currentUser?.id != null && props.user?.id != null && authStore.currentUser.id === props.user.id;

Line range hint 1-194: Consider enhancing security feedback and validation.

While the core security measures are solid (password verification, API throttling, email validation), consider these security enhancements:

  1. Add a visual indicator for remaining email change attempts before throttling
  2. Implement client-side password strength validation
  3. Add rate limiting information in the error message

Example implementation for attempt counter:

 <div class="flex justify-end">
+  <small v-if="remainingAttempts" class="text-gray-500 mr-2 self-center">
+    {{ $t('auth.remaining_attempts', { count: remainingAttempts }) }}
+  </small>
   <Button
     v-if="!viewOnly && userPermissions.can('updateAttributes', user)"
     :disabled="isBusy"

Line range hint 134-194: Enhance error handling and loading state feedback.

While the current error handling is good, consider these improvements:

  1. Add loading state feedback:
 function save(event) {
   if (event) {
     event.preventDefault();
   }

   isBusy.value = true;
+  const loadingToast = toast.info(t('common.saving'), { timeout: false });
   formErrors.clear();
   validationRequiredEmail.value = null;

   // ... existing code ...

   .finally(() => {
     currentPassword.value = null;
     isBusy.value = false;
+    loadingToast.dismiss();
   });
 }
  1. Add explicit network error handling:
     } else if (error.response.status === env.HTTP_EMAIL_CHANGE_THROTTLE) {
       toast.error(t("auth.throttle_email"));
+    } else if (!error.response) {
+      toast.error(t("errors.network"));
     } else {
       api.error(error);
     }
  1. Add cleanup on component unmount:
+import { computed, onBeforeMount, onBeforeUnmount, ref } from 'vue';
+
+// ... existing code ...
+
+onBeforeUnmount(() => {
+  formErrors.clear();
+  isBusy.value = false;
+});
resources/js/components/SettingsUsersResetPasswordButton.vue (1)

45-45: LGTM! Consider enhancing error feedback.

The addition of :disabled="isBusy" is correct and consistent. However, there's an opportunity to improve error handling.

Consider adding specific error toast messages to match the success case:

 .catch((error) => {
-  api.error(error);
+  toast.error(
+    t("admin.users.password_reset_error", { mail: props.email })
+  );
+  api.error(error);
 })
resources/js/components/SettingsServerPoolsDeleteButton.vue (1)

45-45: LGTM! Consider improving error state UX.

The addition of :disabled="isBusy" is correct and consistent. However, there's an opportunity to improve the error state handling.

Consider showing a "Retry" button when room types are affected:

-<template v-if="deleteFailedRoomTypes == null" #footer>
+<template #footer>
   <Button
     :label="$t('app.no')"
     :disabled="isBusy"
     severity="secondary"
-    @click="modalVisible = false"
+    @click="handleClose"
   />
-  <Button
+  <Button v-if="deleteFailedRoomTypes == null"
     :label="$t('app.yes')"
     :loading="isBusy"
     severity="danger"
     @click="deleteServerPool"
   />
+  <Button v-else
+    :label="$t('app.retry')"
+    severity="secondary"
+    @click="retryDelete"
+  />
 </template>

Add the following methods:

function handleClose() {
  deleteFailedRoomTypes.value = null;
  modalVisible.value = false;
}

function retryDelete() {
  deleteFailedRoomTypes.value = null;
  deleteServerPool();
}
resources/js/components/SettingsRoomTypesDeleteButton.vue (1)

32-76: Improved error handling with reload capability.

The addition of InputGroup with a reload button provides better user experience when loading replacement room types fails.

Consider adding an aria-label to the reload button for better accessibility:

        <Button
          v-if="replacementRoomTypesLoadingError"
          :disabled="isBusy"
          outlined
          severity="secondary"
          icon="fa-solid fa-sync"
+         :aria-label="$t('app.reload')"
          @click="loadReplacementRoomTypes()"
        />
📜 Review details

Configuration used: CodeRabbit UI
Review profile: CHILL
Plan: Pro

📥 Commits

Reviewing files that changed from the base of the PR and between 9dd1542 and 4c87b7b.

📒 Files selected for processing (23)
  • CHANGELOG.md (4 hunks)
  • app/Http/Requests/UpdateSettings.php (1 hunks)
  • resources/js/components/RoleSelect.vue (3 hunks)
  • resources/js/components/SettingsRolesDeleteButton.vue (1 hunks)
  • resources/js/components/SettingsRoomTypesDeleteButton.vue (5 hunks)
  • resources/js/components/SettingsServerPoolsDeleteButton.vue (1 hunks)
  • resources/js/components/SettingsServersDeleteButton.vue (1 hunks)
  • resources/js/components/SettingsUsersDeleteButton.vue (1 hunks)
  • resources/js/components/SettingsUsersResetPasswordButton.vue (1 hunks)
  • resources/js/components/UserTabEmail.vue (1 hunks)
  • resources/js/components/UserTabSecurityRolesAndPermissionsSection.vue (1 hunks)
  • resources/js/views/AdminRolesIndex.vue (1 hunks)
  • resources/js/views/AdminRolesView.vue (12 hunks)
  • resources/js/views/AdminRoomTypesIndex.vue (5 hunks)
  • resources/js/views/AdminRoomTypesView.vue (3 hunks)
  • resources/js/views/AdminServerPoolsIndex.vue (1 hunks)
  • resources/js/views/AdminServerPoolsView.vue (3 hunks)
  • resources/js/views/AdminServersIndex.vue (1 hunks)
  • resources/js/views/AdminServersView.vue (1 hunks)
  • resources/js/views/AdminSettings.vue (2 hunks)
  • resources/js/views/AdminUsersIndex.vue (5 hunks)
  • resources/js/views/AdminUsersNew.vue (1 hunks)
  • tests/Backend/Feature/api/v1/SettingsTest.php (2 hunks)
⏰ Context from checks skipped due to timeout of 90000ms (8)
  • GitHub Check: Frontend Tests (5)
  • GitHub Check: Frontend Tests (4)
  • GitHub Check: Frontend Tests (3)
  • GitHub Check: Frontend Tests (2)
  • GitHub Check: Frontend Tests (1)
  • GitHub Check: System Tests
  • GitHub Check: Visual Tests
  • GitHub Check: Backend
🔇 Additional comments (29)
tests/Backend/Feature/api/v1/SettingsTest.php (2)

907-907: Fix indentation.

The indentation was incorrect.


990-990: LGTM! Test case aligns with validation rules.

The test case correctly verifies that setting bbb_logo to an empty string clears the logo, which aligns with the nullable validation rule.

resources/js/views/AdminSettings.vue (2)

131-133: LGTM! Fixed error field name mismatch.

The error field name now correctly matches the form field name general_pagination_page_size, fixing the validation error display.


1290-1292: LGTM! Improved BBB logo form data handling.

The logic for handling the BBB logo in form data has been improved:

  1. Properly handles logo deletion by setting an empty string
  2. Added null check before appending existing logo
resources/js/views/AdminServersIndex.vue (1)

Line range hint 71-77: LGTM! Error handling implementation is robust.

The error handling implementation correctly:

  • Displays errors with retry functionality
  • Reverts pagination state on error
  • Provides visual feedback
resources/js/views/AdminServerPoolsView.vue (1)

162-162: LGTM! Error message positioning improved.

Moving the FormError component after the multiselect input improves the visual flow and helps users better understand validation errors.

resources/js/components/SettingsRolesDeleteButton.vue (1)

28-28: LGTM! Consistent handling of busy state.

The addition of :disabled="isBusy" to the "No" button aligns with the existing busy state handling in the dialog, preventing unintended user interactions during deletion operations.

resources/js/components/SettingsServersDeleteButton.vue (1)

26-26: LGTM! Consistent implementation.

The addition of :disabled="isBusy" to the "No" button maintains consistency with other components and properly prevents user interaction during server deletion operations.

resources/js/components/SettingsRoomTypesDeleteButton.vue (2)

85-85: Enhanced user interaction control.

Adding :disabled="isBusy" to the "No" button prevents user interaction during busy states.


126-126: Improved error state management.

The addition of replacementRoomTypesLoadingError ref and its management in the loadReplacementRoomTypes function enhances error handling.

Also applies to: 141-142, 158-158

resources/js/components/RoleSelect.vue (1)

4-4: Improved template ref implementation.

The change from using ref to useTemplateRef with kebab-case template ref name follows Vue.js best practices for template refs.

Let's verify if this pattern is consistently used across other components:

Also applies to: 97-97, 142-142

resources/js/views/AdminRolesIndex.vue (1)

8-8: Enhanced loading state handling.

Disabling search input and button during busy states prevents concurrent API calls and improves user experience.

Also applies to: 14-14

resources/js/views/AdminServerPoolsIndex.vue (1)

8-8: Consistent loading state handling.

The implementation matches AdminRolesIndex.vue, maintaining consistency in how loading states are handled across the application.

Let's verify if this pattern is consistently implemented across all admin index views:

Also applies to: 14-14

✅ Verification successful

Loading state handling is consistently implemented across admin views

The :disabled="isBusy" pattern is uniformly applied across all active admin index views (Roles, RoomTypes, ServerPools, Servers, Users) for search inputs, buttons, and navigation elements, maintaining a consistent user experience.

🏁 Scripts executed

The following scripts were executed for the analysis:

Script:

#!/bin/bash
# Search for other admin index views to ensure consistent loading state handling
rg -l 'Admin.*Index\.vue$' --type vue | xargs rg -l ':disabled="isBusy"'

Length of output: 1398


Script:

#!/bin/bash
# Find all admin index views and check their loading state implementation
fd -e vue | rg "Admin.*Index\.vue$" | while read -r file; do
  echo "=== $file ==="
  rg -A 1 -B 1 ':disabled="isBusy"' "$file" || echo "No matches found"
  echo
done

Length of output: 3391

resources/js/views/AdminUsersNew.vue (1)

106-106: LGTM! Good use of optional chaining.

The addition of optional chaining (?.) when accessing authStore.currentUser.superuser prevents potential null reference errors.

resources/js/views/AdminUsersIndex.vue (3)

25-25: Improved multiselect behavior.

The changes enhance the user experience by:

  1. Using a consistent ref attribute naming convention.
  2. Automatically closing the dropdown upon selection.

Also applies to: 34-34


251-251: LGTM! Good modernization of template refs.

Using useTemplateRef is a more modern and maintainable approach for handling template references.

Also applies to: 287-287


324-324: LGTM! Improved error handling.

The error handling is now more consistent with the rest of the application.

resources/js/views/AdminServersView.vue (1)

Line range hint 32-37: Enhanced error handling and user feedback.

The changes improve the user experience by:

  1. Showing the overlay during loading errors
  2. Providing a retry button when loading fails
resources/js/views/AdminRolesView.vue (4)

4-7: Improved conditional rendering.

Good addition of permissionsLoaded check to prevent premature rendering of UI elements.


35-46: Enhanced error handling with better user feedback.

The overlay now properly handles both model and permissions loading errors, with a retry button for recovery.


401-408: Good DRY implementation with computed property.

The formFieldsDisabled computed property centralizes the disable logic, making it more maintainable and consistent.


363-364: Improved permissions loading state management.

The changes properly track permissions loading state and errors, ensuring better error handling and user feedback.

Also applies to: 465-465, 536-539

resources/js/views/AdminRoomTypesView.vue (2)

32-35: LGTM! Enhanced error handling with LoadingRetryButton.

The addition of LoadingRetryButton improves error recovery by allowing users to retry loading when errors occur.


138-138: LGTM! Improved dropdown behavior.

Setting close-on-select to true provides better UX by automatically closing the dropdown after selection.

resources/js/components/SettingsUsersDeleteButton.vue (1)

42-42: LGTM! Improved dialog button state management.

Disabling the "No" button during busy states prevents potential race conditions and provides better user feedback.

resources/js/views/AdminRoomTypesIndex.vue (3)

8-8: LGTM! Improved search interaction during loading.

Disabling search input and button during loading prevents concurrent requests and provides better user feedback.

Also applies to: 14-14


41-41: LGTM! Enhanced error handling with retry mechanism.

The DataTable now properly shows loading state during errors and provides a retry button for recovery.

Also applies to: 69-71


165-165: LGTM! Proper error state management.

The loadingError state is properly initialized, cleared before loading, and set on error, ensuring accurate UI feedback.

Also applies to: 181-182, 190-190

CHANGELOG.md (1)

12-13: LGTM! Comprehensive changelog updates.

The changelog entries accurately document all changes and improvements made in PR #1588, including:

  • Added loading retry buttons
  • Changed multiselect dropdown behavior
  • Fixed search functionality, overlay display, dialog buttons, and error handling

Also applies to: 26-27, 33-42, 348-348, 360-361, 366-366, 370-370

@SamuelWei SamuelWei requested a review from Sabr1n4W January 29, 2025 16:46
Copy link

@coderabbitai coderabbitai bot left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Actionable comments posted: 0

🧹 Nitpick comments (3)
resources/js/components/TimezoneSelect.vue (3)

28-28: LGTM! Consider enhancing accessibility further.

The addition of the aria-label improves accessibility for screen readers. To make it even better, consider adding aria-busy when loading and aria-pressed attributes.

 <Button
   v-if="loadingError"
   :disabled="loading"
   outlined
   severity="secondary"
   icon="fa-solid fa-sync"
   :aria-label="$t('app.reload')"
+  :aria-busy="loading"
+  :aria-pressed="false"
   data-test="timezone-reload-button"
   @click="loadTimezones()"
 />

Line range hint 34-57: Consider adopting TypeScript for better type safety.

The props are well-defined, but using TypeScript would provide better type safety and developer experience.

interface TimezoneSelectProps {
  placeholder: string | null
  invalid: boolean | null
  disabled: boolean
  required: boolean
  ariaLabelledby: string | null
}

Line range hint 89-94: Enhance error handling with specific error types.

The error handling could be more specific to help users understand and resolve issues better.

     })
     .catch((error) => {
       loadingError.value = true;
-      api.error(error);
+      if (error.response?.status === 404) {
+        api.error(new Error($t('errors.timezone_not_found')));
+      } else if (error.response?.status === 403) {
+        api.error(new Error($t('errors.timezone_access_denied')));
+      } else {
+        api.error(error);
+      }
     })
📜 Review details

Configuration used: CodeRabbit UI
Review profile: CHILL
Plan: Pro

📥 Commits

Reviewing files that changed from the base of the PR and between d48de63 and ce68db2.

📒 Files selected for processing (7)
  • resources/js/components/RoleSelect.vue (3 hunks)
  • resources/js/components/SettingsRoomTypesDeleteButton.vue (6 hunks)
  • resources/js/components/TimezoneSelect.vue (1 hunks)
  • resources/js/views/AdminRoomTypesView.vue (4 hunks)
  • resources/js/views/AdminServerPoolsView.vue (3 hunks)
  • resources/js/views/AdminUsersIndex.vue (6 hunks)
  • resources/js/views/RoomsIndex.vue (1 hunks)
✅ Files skipped from review due to trivial changes (1)
  • resources/js/views/RoomsIndex.vue
🚧 Files skipped from review as they are similar to previous changes (5)
  • resources/js/components/SettingsRoomTypesDeleteButton.vue
  • resources/js/views/AdminRoomTypesView.vue
  • resources/js/views/AdminUsersIndex.vue
  • resources/js/components/RoleSelect.vue
  • resources/js/views/AdminServerPoolsView.vue
⏰ Context from checks skipped due to timeout of 90000ms (2)
  • GitHub Check: Docker Build
  • GitHub Check: Backend

@Sabr1n4W Sabr1n4W merged commit 4f2f298 into develop Jan 29, 2025
16 checks passed
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
2 participants