Afiq a2a81bd3bb Refactor RBAC Management and Dashboard Integration
- Removed the RBAC Management section from the navigation structure.
- Updated the dashboard page title to "RBAC Management" and modified the breadcrumb to reflect the new path.
- Simplified the dashboard component by removing unused data and integrating new tab functionalities for managing applications, groups, roles, and permissions.
- Enhanced the create group and create role pages to include application assignment and simplified form states.
- Updated user creation page to include application assignment and filtered group/role options based on the selected application.
- Deleted the obsolete rbac-permission page to streamline the project structure.
2025-05-31 17:30:11 +08:00

306 lines
11 KiB
Vue

<script setup>
definePageMeta({
title: "Create Role",
middleware: ["auth"],
requiresAuth: true,
breadcrumb: [
{ name: "Dashboard", path: "/dashboard" },
{ name: "Roles", path: "/roles" },
{ name: "Create Role", path: "/roles/create", type: "current" }
]
});
import { ref, reactive, computed, onMounted } from 'vue'
// Form state - SIMPLIFIED
const roleForm = reactive({
name: '',
description: '',
application: '',
permissions: [], // Simple list of permissions
isActive: true
})
// Available applications
const availableApplications = ref([
{ id: '1', name: 'Main Application', description: 'Primary business application' },
{ id: '2', name: 'HR System', description: 'Human Resources Management' },
{ id: '3', name: 'Finance System', description: 'Financial Management' }
])
// Simplified permissions - focused on actual system functions
const availablePermissions = ref([
// User Management
{ id: 'users_view', name: 'View Users', category: 'User Management', description: 'Can view user listings and profiles' },
{ id: 'users_create', name: 'Create Users', category: 'User Management', description: 'Can create new user accounts' },
{ id: 'users_edit', name: 'Edit Users', category: 'User Management', description: 'Can modify user information' },
{ id: 'users_delete', name: 'Delete Users', category: 'User Management', description: 'Can delete user accounts' },
// Group Management
{ id: 'groups_view', name: 'View Groups', category: 'Group Management', description: 'Can view group listings' },
{ id: 'groups_create', name: 'Create Groups', category: 'Group Management', description: 'Can create new groups' },
{ id: 'groups_edit', name: 'Edit Groups', category: 'Group Management', description: 'Can modify groups' },
{ id: 'groups_delete', name: 'Delete Groups', category: 'Group Management', description: 'Can delete groups' },
// Role Management
{ id: 'roles_view', name: 'View Roles', category: 'Role Management', description: 'Can view role listings' },
{ id: 'roles_create', name: 'Create Roles', category: 'Role Management', description: 'Can create new roles' },
{ id: 'roles_edit', name: 'Edit Roles', category: 'Role Management', description: 'Can modify roles' },
{ id: 'roles_delete', name: 'Delete Roles', category: 'Role Management', description: 'Can delete roles' },
// System Access
{ id: 'dashboard_access', name: 'Dashboard Access', category: 'System Access', description: 'Can access the dashboard' },
{ id: 'reports_view', name: 'View Reports', category: 'System Access', description: 'Can view system reports' },
{ id: 'settings_view', name: 'View Settings', category: 'System Access', description: 'Can view system settings' },
{ id: 'settings_edit', name: 'Edit Settings', category: 'System Access', description: 'Can modify system settings' }
])
// Loading state
const isLoading = ref(false)
// Computed
const isFormValid = computed(() => {
return roleForm.name &&
roleForm.description &&
roleForm.application
})
const applicationOptions = computed(() =>
availableApplications.value.map(app => ({
label: app.name,
value: app.id
}))
)
const permissionsByCategory = computed(() => {
const grouped = {}
availablePermissions.value.forEach(permission => {
if (!grouped[permission.category]) {
grouped[permission.category] = []
}
grouped[permission.category].push(permission)
})
return grouped
})
// Methods
const createRole = async () => {
if (!isFormValid.value) return
isLoading.value = true
try {
const roleData = {
name: roleForm.name,
description: roleForm.description,
application: roleForm.application,
permissions: roleForm.permissions,
isActive: roleForm.isActive
}
console.log('Creating role:', roleData)
// Simulate API call
await new Promise(resolve => setTimeout(resolve, 1500))
// Success - redirect
await navigateTo('/roles')
} catch (error) {
console.error('Failed to create role:', error)
} finally {
isLoading.value = false
}
}
const resetForm = () => {
Object.assign(roleForm, {
name: '',
description: '',
application: '',
permissions: [],
isActive: true
})
}
// Initialize
onMounted(() => {
// Load additional data if needed
})
</script>
<template>
<div>
<LayoutsBreadcrumb />
<!-- Header -->
<div class="mb-6">
<div class="flex items-center justify-between">
<div>
<h1 class="text-2xl font-bold text-gray-900 dark:text-white">Create New Role</h1>
<p class="text-gray-600 dark:text-gray-400">Roles define what users can do in the application</p>
</div>
<div class="flex space-x-3">
<rs-button @click="resetForm" variant="primary-outline">
<Icon name="ph:arrow-clockwise" class="w-4 h-4 mr-2" />
Reset Form
</rs-button>
<rs-button @click="createRole" :disabled="!isFormValid || isLoading">
<Icon name="ph:shield-plus" class="w-4 h-4 mr-2" />
{{ isLoading ? 'Creating...' : 'Create Role' }}
</rs-button>
</div>
</div>
</div>
<FormKit type="form" @submit="createRole">
<div class="grid grid-cols-1 lg:grid-cols-3 gap-6">
<!-- Main Form -->
<div class="lg:col-span-2 space-y-6">
<!-- Basic Information -->
<rs-card>
<template #header>
<h3 class="text-lg font-medium text-gray-900 dark:text-white">Basic Information</h3>
</template>
<template #body>
<div class="space-y-4">
<div class="grid grid-cols-1 md:grid-cols-2 gap-4">
<FormKit
v-model="roleForm.name"
type="text"
label="Role Name"
placeholder="e.g., Content Manager"
validation="required|length:3"
validation-visibility="dirty"
:validation-messages="{
required: 'Role name is required',
length: 'Role name must be at least 3 characters'
}"
/>
<FormKit
v-model="roleForm.application"
type="select"
label="Application"
placeholder="Select application"
:options="applicationOptions"
validation="required"
validation-visibility="dirty"
help="Which application this role applies to"
:validation-messages="{
required: 'Application is required'
}"
/>
</div>
<FormKit
v-model="roleForm.description"
type="textarea"
label="Description"
placeholder="Describe what this role can do and its responsibilities"
validation="required"
validation-visibility="dirty"
rows="3"
:validation-messages="{
required: 'Description is required'
}"
/>
<FormKit
v-model="roleForm.isActive"
type="checkbox"
label="Active Role"
help="Role can be assigned to users when active"
/>
</div>
</template>
</rs-card>
<!-- Permissions -->
<rs-card>
<template #header>
<h3 class="text-lg font-medium text-gray-900 dark:text-white">Permissions</h3>
</template>
<template #body>
<div class="space-y-6">
<p class="text-sm text-gray-600 dark:text-gray-400">
Select what actions this role can perform in the system.
</p>
<div
v-for="(permissions, category) in permissionsByCategory"
:key="category"
class="space-y-3"
>
<h4 class="text-sm font-medium text-gray-900 dark:text-white border-b border-gray-200 dark:border-gray-700 pb-2">
{{ category }}
</h4>
<div class="grid grid-cols-1 md:grid-cols-2 gap-2">
<FormKit
v-for="permission in permissions"
:key="permission.id"
v-model="roleForm.permissions"
type="checkbox"
:value="permission.id"
:label="permission.name"
:help="permission.description"
:classes="{
wrapper: 'mb-1',
label: '!text-sm',
help: '!text-xs'
}"
/>
</div>
</div>
</div>
</template>
</rs-card>
</div>
<!-- Sidebar -->
<div class="space-y-6">
<!-- Role Preview -->
<rs-card>
<template #header>
<h3 class="text-lg font-medium text-gray-900 dark:text-white">Role Preview</h3>
</template>
<template #body>
<div class="space-y-3">
<div>
<span class="text-sm font-medium text-gray-700 dark:text-gray-300">Name:</span>
<p class="text-sm text-gray-900 dark:text-white">{{ roleForm.name || 'Not set' }}</p>
</div>
<div>
<span class="text-sm font-medium text-gray-700 dark:text-gray-300">Application:</span>
<p class="text-sm text-gray-900 dark:text-white">
{{ availableApplications.find(a => a.id === roleForm.application)?.name || 'Not selected' }}
</p>
</div>
<div>
<span class="text-sm font-medium text-gray-700 dark:text-gray-300">Permissions:</span>
<rs-badge :variant="roleForm.permissions.length > 0 ? 'success' : 'secondary'">
{{ roleForm.permissions.length }} permissions
</rs-badge>
</div>
<div class="flex space-x-2">
<rs-badge :variant="roleForm.isActive ? 'success' : 'secondary'">
{{ roleForm.isActive ? 'Active' : 'Inactive' }}
</rs-badge>
</div>
</div>
</template>
</rs-card>
</div>
</div>
</FormKit>
</div>
</template>
<style scoped>
/* Custom styles */
</style>