test
This commit is contained in:
@@ -3,7 +3,7 @@ import { onMounted, ref, shallowRef, watch } from "vue";
|
|||||||
import { useDisplay } from "vuetify";
|
import { useDisplay } from "vuetify";
|
||||||
import sidebarItems from "~/components/layout/full/vertical-sidebar/sidebarItem";
|
import sidebarItems from "~/components/layout/full/vertical-sidebar/sidebarItem";
|
||||||
import { Menu2Icon } from "vue-tabler-icons";
|
import { Menu2Icon } from "vue-tabler-icons";
|
||||||
import { useCustomizerStore } from "~/store/customizer";
|
import { useCustomizerStore } from "~/stores/customizer";
|
||||||
const sidebarMenu = shallowRef(sidebarItems);
|
const sidebarMenu = shallowRef(sidebarItems);
|
||||||
const customizer = useCustomizerStore();
|
const customizer = useCustomizerStore();
|
||||||
const { mdAndDown } = useDisplay();
|
const { mdAndDown } = useDisplay();
|
||||||
@@ -14,6 +14,9 @@ onMounted(() => {
|
|||||||
watch(mdAndDown, (val) => {
|
watch(mdAndDown, (val) => {
|
||||||
sDrawer.value = !val;
|
sDrawer.value = !val;
|
||||||
});
|
});
|
||||||
|
|
||||||
|
// console.log("sidebarMenu", sidebarMenu.value);
|
||||||
|
// console.log("sidebarMenu", sidebarItems.map((item) => item.children));
|
||||||
</script>
|
</script>
|
||||||
|
|
||||||
<template>
|
<template>
|
||||||
@@ -26,7 +29,7 @@ watch(mdAndDown, (val) => {
|
|||||||
customizer.actTheme,
|
customizer.actTheme,
|
||||||
customizer.mini_sidebar ? 'mini-sidebar' : '',
|
customizer.mini_sidebar ? 'mini-sidebar' : '',
|
||||||
customizer.setHorizontalLayout ? 'horizontalLayout' : 'verticalLayout',
|
customizer.setHorizontalLayout ? 'horizontalLayout' : 'verticalLayout',
|
||||||
customizer.setBorderCard ? 'cardBordered' : ''
|
customizer.setBorderCard ? 'cardBordered' : '',
|
||||||
]"
|
]"
|
||||||
>
|
>
|
||||||
<!---Customizer location left side--->
|
<!---Customizer location left side--->
|
||||||
|
|||||||
@@ -1,7 +1,7 @@
|
|||||||
<script setup lang="ts">
|
<script setup lang="ts">
|
||||||
import { ref } from 'vue';
|
import { ref } from 'vue';
|
||||||
import { useTheme } from 'vuetify';
|
import { useTheme } from 'vuetify';
|
||||||
import { useCustomizerStore } from '~/store/customizer';
|
import { useCustomizerStore } from '~/stores/customizer';
|
||||||
import {
|
import {
|
||||||
CheckIcon,
|
CheckIcon,
|
||||||
LayoutColumnsIcon,
|
LayoutColumnsIcon,
|
||||||
|
|||||||
@@ -1,6 +1,6 @@
|
|||||||
<script setup>
|
<script setup>
|
||||||
import { computed } from 'vue';
|
import { computed } from 'vue';
|
||||||
import { useCustomizerStore } from '~/store/customizer';
|
import { useCustomizerStore } from '~/stores/customizer';
|
||||||
|
|
||||||
const customizer = useCustomizerStore();
|
const customizer = useCustomizerStore();
|
||||||
|
|
||||||
|
|||||||
@@ -1,7 +1,7 @@
|
|||||||
<script setup lang="ts">
|
<script setup lang="ts">
|
||||||
import { ref } from 'vue';
|
import { ref } from 'vue';
|
||||||
import { useTheme } from 'vuetify';
|
import { useTheme } from 'vuetify';
|
||||||
import { useCustomizerStore } from '~/store/customizer';
|
import { useCustomizerStore } from '~/stores/customizer';
|
||||||
import { Icon } from '@iconify/vue';
|
import { Icon } from '@iconify/vue';
|
||||||
|
|
||||||
const theme = useTheme();
|
const theme = useTheme();
|
||||||
|
|||||||
@@ -1,6 +1,6 @@
|
|||||||
<script setup lang="ts">
|
<script setup lang="ts">
|
||||||
import { ref, watch, computed } from 'vue';
|
import { ref, watch, computed } from 'vue';
|
||||||
import { useCustomizerStore } from '~/store/customizer';
|
import { useCustomizerStore } from '~/stores/customizer';
|
||||||
// import { useEcomStore } from '@/stores/apps/eCommerce';
|
// import { useEcomStore } from '@/stores/apps/eCommerce';
|
||||||
// import LanguageDD from './LanguageDD.vue';
|
// import LanguageDD from './LanguageDD.vue';
|
||||||
import NotificationDD from './NotificationDD.vue';
|
import NotificationDD from './NotificationDD.vue';
|
||||||
|
|||||||
@@ -1,12 +1,15 @@
|
|||||||
<script setup lang="ts">
|
<script setup lang="ts">
|
||||||
import { ref, shallowRef } from 'vue';
|
import { ref, shallowRef } from 'vue';
|
||||||
import { useCustomizerStore } from '~/store/customizer';
|
import { useCustomizerStore } from '~/stores/customizer';
|
||||||
import sidebarItems from './sidebarItem';
|
import sidebarItems from './sidebarItem'; //sidebar static dari template
|
||||||
import Logo from '../logo/Logo.vue';
|
import Logo from '../logo/Logo.vue';
|
||||||
import { Icon } from '@iconify/vue';
|
import { Icon } from '@iconify/vue';
|
||||||
import { useRoute } from 'vue-router';
|
import { useRoute } from 'vue-router';
|
||||||
// MiniSidebar Icons
|
// MiniSidebar Icons
|
||||||
import MiniSideIcons from './MinIconItems';
|
import MiniSideIcons from './MinIconItems';
|
||||||
|
//import { useSidebarAccess } from '~/composables/useSidebarAccess'
|
||||||
|
import { mergeSidebar, mergeSidebarIcon } from '~/composables/sidebarMenu/mergeSidebar';
|
||||||
|
import sidebarRole from "@/stores/rolePages"; // data dummy
|
||||||
|
|
||||||
const route = useRoute();
|
const route = useRoute();
|
||||||
|
|
||||||
@@ -36,7 +39,25 @@ const findTitleByPath = (items: any, path: any) => {
|
|||||||
|
|
||||||
return title;
|
return title;
|
||||||
};
|
};
|
||||||
const foundId = findTitleByPath(sidebarItems, route.path);
|
|
||||||
|
const customizer = useCustomizerStore();
|
||||||
|
const sidebarMenu = shallowRef(sidebarItems);
|
||||||
|
|
||||||
|
//Merge Sidebar dari user api
|
||||||
|
//sidebarItems dari static sidebar
|
||||||
|
//sidebarRole dari role user api
|
||||||
|
const userRole = "admin";
|
||||||
|
const roleSidebarItems = sidebarRole.filter(item => item.role === userRole);
|
||||||
|
//filter menu untuk userRole admin
|
||||||
|
//mergeSidebar (menu awal, menu role user)
|
||||||
|
const mergedPages = mergeSidebar(sidebarMenu.value, roleSidebarItems[0].pages)
|
||||||
|
console.log('sidebarMenu', sidebarMenu.value);
|
||||||
|
console.log('roleSidebarItems', roleSidebarItems[0].pages);
|
||||||
|
console.log('mergedSidebarMenu', mergedPages);
|
||||||
|
sidebarMenu.value = mergedPages
|
||||||
|
|
||||||
|
|
||||||
|
const foundId = findTitleByPath(mergedPages, route.path);
|
||||||
const getCurrent = foundId ? foundId : 1;
|
const getCurrent = foundId ? foundId : 1;
|
||||||
const currentMenu = ref<any>(getCurrent);
|
const currentMenu = ref<any>(getCurrent);
|
||||||
function showData(data: any) {
|
function showData(data: any) {
|
||||||
@@ -44,10 +65,19 @@ function showData(data: any) {
|
|||||||
//customizer.SET_MINI_SIDEBAR(!customizer.mini_sidebar)
|
//customizer.SET_MINI_SIDEBAR(!customizer.mini_sidebar)
|
||||||
}
|
}
|
||||||
|
|
||||||
// MiniSidebar Icons End
|
|
||||||
const customizer = useCustomizerStore();
|
|
||||||
const sidebarMenu = shallowRef(sidebarItems);
|
|
||||||
|
|
||||||
|
|
||||||
|
//Merge Icon dari sidebarMenu api
|
||||||
|
const sidebarMiniSideIcons = shallowRef(MiniSideIcons);
|
||||||
|
if (mergedPages !== null) {
|
||||||
|
sidebarMiniSideIcons.value = mergedPages
|
||||||
|
const mergedIcon = mergeSidebarIcon(MiniSideIcons, sidebarMiniSideIcons.value)
|
||||||
|
//console.log('sidebarIcon', MiniSideIcons);
|
||||||
|
console.log('mergedsidebarIcon', mergedIcon);
|
||||||
|
sidebarMiniSideIcons.value = mergedIcon
|
||||||
|
}
|
||||||
|
|
||||||
|
// MiniSidebar Icons End
|
||||||
</script>
|
</script>
|
||||||
|
|
||||||
<template>
|
<template>
|
||||||
@@ -74,7 +104,7 @@ const sidebarMenu = shallowRef(sidebarItems);
|
|||||||
<div class="miniicons mt-lg-0 mt-4">
|
<div class="miniicons mt-lg-0 mt-4">
|
||||||
<!-- MiniSidebar Icons -->
|
<!-- MiniSidebar Icons -->
|
||||||
<div class="d-flex flex-column gap-2">
|
<div class="d-flex flex-column gap-2">
|
||||||
<div class="miniicons-list px-4" v-for="menu in MiniSideIcons" :key="menu.icon">
|
<div class="miniicons-list px-4" v-for="menu in sidebarMiniSideIcons" :key="menu.icon">
|
||||||
<v-btn
|
<v-btn
|
||||||
rounded="md"
|
rounded="md"
|
||||||
flat
|
flat
|
||||||
|
|||||||
@@ -14,21 +14,28 @@ export interface menu {
|
|||||||
disabled?: boolean;
|
disabled?: boolean;
|
||||||
type?: string;
|
type?: string;
|
||||||
subCaption?: string;
|
subCaption?: string;
|
||||||
|
role?: string[];
|
||||||
|
permission?: string[];
|
||||||
}
|
}
|
||||||
const sidebarItem: menu[] = [
|
const sidebarItem: menu[] = [
|
||||||
{
|
{
|
||||||
header: 'dashboards',
|
header: "dashboards",
|
||||||
id: 1,
|
id: 1,
|
||||||
children: [
|
|
||||||
|
children: [
|
||||||
{
|
{
|
||||||
title: 'Dashboard1',
|
title: 'Dashboard1',
|
||||||
icon: 'widget-add-line-duotone',
|
icon: 'widget-add-line-duotone',
|
||||||
to: '/dashboards/dashboard1'
|
to: '/dashboards/dashboard1',
|
||||||
|
// role: ['admin'],
|
||||||
|
//permission: ['view', 'update', 'create', 'delete'],
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
title: 'Dashboard2',
|
title: 'Dashboard2',
|
||||||
icon: 'chart-line-duotone',
|
icon: 'chart-line-duotone',
|
||||||
to: '/dashboards/dashboard2'
|
to: '/dashboards/dashboard2',
|
||||||
|
// role: ['admin','user'],
|
||||||
|
//permission: ['view', 'update', 'create', 'delete'],
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
title: 'Dashboard3',
|
title: 'Dashboard3',
|
||||||
@@ -42,11 +49,15 @@ const sidebarItem: menu[] = [
|
|||||||
children: [
|
children: [
|
||||||
{
|
{
|
||||||
title: 'Homepage',
|
title: 'Homepage',
|
||||||
to: '/front-page/homepage'
|
to: '/front-page/homepage',
|
||||||
|
//role: ['admin','user'],
|
||||||
|
//permission: ['view', 'update', 'create', 'delete'],
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
title: 'About Us',
|
title: 'About Us',
|
||||||
to: '/front-page/about-us'
|
to: '/front-page/about-us',
|
||||||
|
//role: ['admin','user'],
|
||||||
|
//permission: ['view', 'update', 'create', 'delete'],
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
title: 'Blog',
|
title: 'Blog',
|
||||||
|
|||||||
64
composables/sidebarMenu/mergeSidebar.ts
Normal file
64
composables/sidebarMenu/mergeSidebar.ts
Normal file
@@ -0,0 +1,64 @@
|
|||||||
|
|
||||||
|
import type { SidebarItem } from '~/types/menuAkses/sidebar'
|
||||||
|
import type { PageAccess } from '~/types/menuAkses/access'
|
||||||
|
interface SidebarItemWithPermissions extends SidebarItem {
|
||||||
|
permissions: string[];
|
||||||
|
}
|
||||||
|
|
||||||
|
export function mergeSidebar(menuItems: SidebarItem[], allowedPages: PageAccess[]): SidebarItem[] {
|
||||||
|
const result: SidebarItem[] = []
|
||||||
|
|
||||||
|
for (const item of menuItems) {
|
||||||
|
// Jika punya anak (children)
|
||||||
|
//console.log('item', item);
|
||||||
|
//console.log('allowedPages', allowedPages);
|
||||||
|
if (Array.isArray(item.children)) {
|
||||||
|
const filteredChildren = mergeSidebar(item.children, allowedPages)
|
||||||
|
//console.log('ada array item', item);
|
||||||
|
|
||||||
|
// console.log('filteredChildren', filteredChildren);
|
||||||
|
if (filteredChildren.length > 0) {
|
||||||
|
result.push({
|
||||||
|
...item,
|
||||||
|
children: filteredChildren
|
||||||
|
})
|
||||||
|
}
|
||||||
|
//console.log('result', result);
|
||||||
|
}
|
||||||
|
|
||||||
|
// Jika punya path, cocokkan dengan json dummy / backend
|
||||||
|
else if (item.to) {
|
||||||
|
const matchPage = allowedPages.find(page => page.title === item.title && page.path === item.to) //cocokkan title dan path link halaman
|
||||||
|
|
||||||
|
//console.log('match', matchPage,matchPage?.permissions);
|
||||||
|
if (matchPage && matchPage.permissions?.includes('view')) {
|
||||||
|
result.push({
|
||||||
|
...item,
|
||||||
|
permissions: matchPage?.permissions,
|
||||||
|
|
||||||
|
} as SidebarItemWithPermissions)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
return result
|
||||||
|
}
|
||||||
|
|
||||||
|
export function mergeSidebarIcon(staticIcon: any[], IconAccess: any[]) {
|
||||||
|
const result : any[] = []
|
||||||
|
|
||||||
|
for (const item of staticIcon) {
|
||||||
|
const matchIcon = IconAccess.find(icon => icon.id === item.id)
|
||||||
|
//console.log('matchIcon', matchIcon);
|
||||||
|
if (matchIcon) {
|
||||||
|
result.push({
|
||||||
|
...item,
|
||||||
|
|
||||||
|
})
|
||||||
|
}
|
||||||
|
|
||||||
|
}
|
||||||
|
|
||||||
|
return result
|
||||||
|
}
|
||||||
|
|
||||||
47
composables/sidebarMenu/useSidebarAkses.ts
Normal file
47
composables/sidebarMenu/useSidebarAkses.ts
Normal file
@@ -0,0 +1,47 @@
|
|||||||
|
import { useHakAksesStore } from '@/stores/sidebarMenuAkses/useMenuAksesStore'
|
||||||
|
import { mergeSidebar, mergeSidebarIcon } from '~/composables/sidebarMenu/mergeSidebar';
|
||||||
|
import sidebarRole from "@/stores/rolePages"; // data dummy
|
||||||
|
import sidebarItems from '~/components/layout/full/vertical-sidebar/sidebarItem'; //sidebar static dari template
|
||||||
|
import MiniSideIcons from '~/components/layout/full/vertical-sidebar/MinIconItems';
|
||||||
|
|
||||||
|
|
||||||
|
export function useSidebarAccess(data: any) {
|
||||||
|
const sidebarMenu = shallowRef(sidebarItems);
|
||||||
|
const sidebarMiniSideIcons = shallowRef(MiniSideIcons);
|
||||||
|
|
||||||
|
const userRole = "admin";
|
||||||
|
const roleSidebarItems = sidebarRole.filter(item => item.role === userRole);
|
||||||
|
const mergedPages = mergeSidebar(sidebarMenu.value, roleSidebarItems[0].pages)
|
||||||
|
data = mergeSidebarIcon(sidebarMiniSideIcons.value, roleSidebarItems[0].pages)
|
||||||
|
console.log('mergedPages useSidebarAccess', mergedPages);
|
||||||
|
|
||||||
|
return data
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
// export function useAccess() {
|
||||||
|
|
||||||
|
// const store = useHakAksesStore()
|
||||||
|
// const getRole = () => store.role
|
||||||
|
// const getPages = () => store.pageAccess
|
||||||
|
|
||||||
|
// const getPermissionsByPath = (path: string): string[] => {
|
||||||
|
// const match = store.pageAccess.find(p => p.path === path)
|
||||||
|
// return match?.permissions || []
|
||||||
|
// }
|
||||||
|
|
||||||
|
// return {
|
||||||
|
// getRole,
|
||||||
|
// getPages,
|
||||||
|
// getPermissionsByPath
|
||||||
|
// }
|
||||||
|
// }
|
||||||
10
composables/useAccess.ts
Normal file
10
composables/useAccess.ts
Normal file
@@ -0,0 +1,10 @@
|
|||||||
|
//import { sidebarMeta } from '@/components/layout/sidebar'
|
||||||
|
import { mergeSidebar } from '~/composables/sidebarMenu/mergeSidebar'
|
||||||
|
import { useSidebarAccess } from '~/composables/sidebarMenu/useSidebarAkses'
|
||||||
|
|
||||||
|
export const useAccess = () => {
|
||||||
|
const result = useSidebarAccess("tes")
|
||||||
|
|
||||||
|
|
||||||
|
return result
|
||||||
|
}
|
||||||
25
composables/useAuth123.ts
Normal file
25
composables/useAuth123.ts
Normal file
@@ -0,0 +1,25 @@
|
|||||||
|
// // composables/useAuth.ts
|
||||||
|
// import { useCookie } from '#app'
|
||||||
|
|
||||||
|
// export const useAuth = () => {
|
||||||
|
// const user = useState('auth_user', () => null)
|
||||||
|
// const token = useCookie('auth_token')
|
||||||
|
|
||||||
|
// const setUser = (data: any, tokenValue: string) => {
|
||||||
|
// user.value = data
|
||||||
|
// token.value = tokenValue
|
||||||
|
// }
|
||||||
|
|
||||||
|
// const logout = () => {
|
||||||
|
// user.value = null
|
||||||
|
// token.value = null
|
||||||
|
// }
|
||||||
|
|
||||||
|
// return {
|
||||||
|
// user,
|
||||||
|
// token,
|
||||||
|
// setUser,
|
||||||
|
// logout,
|
||||||
|
// isLoggedIn: computed(() => !!user.value)
|
||||||
|
// }
|
||||||
|
// }
|
||||||
34
middleware/auth-menu.global.ts.123
Normal file
34
middleware/auth-menu.global.ts.123
Normal file
@@ -0,0 +1,34 @@
|
|||||||
|
export default defineNuxtRouteMiddleware((to) => {
|
||||||
|
// const auth = useAuthStore()
|
||||||
|
// const requiredPermission = to.meta.permission
|
||||||
|
// console.log('requiredPermission', auth)
|
||||||
|
// const userRole = auth.user?.role
|
||||||
|
|
||||||
|
// if (!auth.user) {
|
||||||
|
// return navigateTo('/login')
|
||||||
|
// }
|
||||||
|
|
||||||
|
// if (requiredPermission && !auth.hasPermission(requiredPermission)) {
|
||||||
|
// return navigateTo('/unauthorized')
|
||||||
|
// }
|
||||||
|
|
||||||
|
// // Kalau kamu mau batasi halaman berdasar role:
|
||||||
|
// const allowedRoles = to.meta.roles
|
||||||
|
// if (allowedRoles && !allowedRoles.includes(userRole)) {
|
||||||
|
// return navigateTo('/unauthorized')
|
||||||
|
// }
|
||||||
|
const { status, data: session } = useAuth();
|
||||||
|
if (status.value === "unauthenticated") {
|
||||||
|
console.log("status:", status.value);
|
||||||
|
} else {
|
||||||
|
console.log("status:", status.value);
|
||||||
|
}
|
||||||
|
console.log('masuk middeleware auth-menu')
|
||||||
|
|
||||||
|
|
||||||
|
console.log('route:', to.fullPath)
|
||||||
|
|
||||||
|
|
||||||
|
return navigateTo('/sample-page-copy')
|
||||||
|
})
|
||||||
|
|
||||||
40
middleware/auth-menu.ts
Normal file
40
middleware/auth-menu.ts
Normal file
@@ -0,0 +1,40 @@
|
|||||||
|
|
||||||
|
// middleware/auth.ts
|
||||||
|
|
||||||
|
import { useAccess } from '~/composables/useAccess'
|
||||||
|
export default defineNuxtRouteMiddleware((to) => {
|
||||||
|
const { getRole, getPermissionsByPath } = useAccess()
|
||||||
|
const role = useAccess()
|
||||||
|
// const perms = getPermissionsByPath(to.path)
|
||||||
|
|
||||||
|
// const meta = to.meta
|
||||||
|
|
||||||
|
// Jika belum login, redirect ke halaman login
|
||||||
|
const isLoggedIn = !!role // role
|
||||||
|
if (!isLoggedIn) {
|
||||||
|
console.log('[ NOT LOGGED IN]', { path: to.path })
|
||||||
|
//return navigateTo('/login') //
|
||||||
|
}
|
||||||
|
|
||||||
|
// // Validasi permission
|
||||||
|
// const rolePass = !meta.role || meta.role.includes(role)
|
||||||
|
// const permissionPass = !meta.permission || meta.permission.every(p => perms.includes(p))
|
||||||
|
|
||||||
|
// if (!rolePass || !permissionPass) {
|
||||||
|
// console.log('[ ACCESS DENIED]', {
|
||||||
|
// path: to.path,
|
||||||
|
// role,
|
||||||
|
// requiredRole: meta.role,
|
||||||
|
// permissions: perms,
|
||||||
|
// requiredPermission: meta.permission
|
||||||
|
// })
|
||||||
|
// return navigateTo('/403') // Halaman tidak punya akses
|
||||||
|
// }
|
||||||
|
return navigateTo('/sample-page-copy')
|
||||||
|
// Semua valid, lanjut ke halaman
|
||||||
|
// console.log('[ACCESS GRANTED]', {
|
||||||
|
// path: to.path,
|
||||||
|
// role,
|
||||||
|
// permissions
|
||||||
|
// })
|
||||||
|
})
|
||||||
19
pages/Sample-Page-copy.vue
Normal file
19
pages/Sample-Page-copy.vue
Normal file
@@ -0,0 +1,19 @@
|
|||||||
|
<script setup lang="ts">
|
||||||
|
import { ref } from "vue";
|
||||||
|
import UiParentCard from "@/components/shared/UiParentCard.vue";
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
</script>
|
||||||
|
<template>
|
||||||
|
<v-row>
|
||||||
|
<v-col cols="12" md="12">
|
||||||
|
<v-card elevation="10">
|
||||||
|
<v-card-item>
|
||||||
|
<h5 class="text-h5 mb-3">Sample Page Copy</h5>
|
||||||
|
<p class="text-body-1">This is a sample page</p>
|
||||||
|
</v-card-item>
|
||||||
|
</v-card>
|
||||||
|
</v-col>
|
||||||
|
</v-row>
|
||||||
|
</template>
|
||||||
@@ -1,6 +1,20 @@
|
|||||||
<script setup lang="ts">
|
<script setup lang="ts">
|
||||||
import { ref } from "vue";
|
import { ref } from "vue";
|
||||||
import UiParentCard from "@/components/shared/UiParentCard.vue";
|
import UiParentCard from "@/components/shared/UiParentCard.vue";
|
||||||
|
|
||||||
|
definePageMeta({
|
||||||
|
middleware: ["auth-menu"],
|
||||||
|
//middleware : ['sidebase-auth']
|
||||||
|
});
|
||||||
|
|
||||||
|
const { status, data: session } = useAuth();
|
||||||
|
if (status.value === "unauthenticated") {
|
||||||
|
console.log("status", status.value);
|
||||||
|
} else {
|
||||||
|
console.log("status", status.value);
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
</script>
|
</script>
|
||||||
<template>
|
<template>
|
||||||
<v-row>
|
<v-row>
|
||||||
|
|||||||
@@ -1,22 +1,34 @@
|
|||||||
<script setup lang="ts">
|
<script setup lang="ts">
|
||||||
/*Call Components*/
|
/*Call Components*/
|
||||||
import RevenueCard from '@/components/dashboard/RevenueCard.vue';
|
import RevenueCard from "@/components/dashboard/RevenueCard.vue";
|
||||||
import NewCustomer from '@/components/dashboard/NewCustomer.vue';
|
import NewCustomer from "@/components/dashboard/NewCustomer.vue";
|
||||||
import Totalincome from '@/components/dashboard/TotalIncome.vue';
|
import Totalincome from "@/components/dashboard/TotalIncome.vue";
|
||||||
import RevenueProduct from '@/components/dashboard/RevenueProducts.vue';
|
import RevenueProduct from "@/components/dashboard/RevenueProducts.vue";
|
||||||
import DailyActivities from '@/components/dashboard/DailyActivities.vue';
|
import DailyActivities from "@/components/dashboard/DailyActivities.vue";
|
||||||
import BlogCards from '@/components/dashboard/BlogCards.vue';
|
import BlogCards from "@/components/dashboard/BlogCards.vue";
|
||||||
|
|
||||||
|
definePageMeta({
|
||||||
|
middleware: ["auth-menu"],
|
||||||
|
//middleware : ['sidebase-auth']
|
||||||
|
});
|
||||||
|
|
||||||
|
// const { status } = useAuth();
|
||||||
|
// if (status.value === "unauthenticated") {
|
||||||
|
// console.log("status", status.value);
|
||||||
|
// } else {
|
||||||
|
// console.log("status", status.value);
|
||||||
|
// }
|
||||||
</script>
|
</script>
|
||||||
|
|
||||||
<template>
|
<template>
|
||||||
<v-row>
|
<v-row>
|
||||||
<v-col cols="12" lg="8"><RevenueCard /></v-col>
|
<v-col cols="12" lg="8"><RevenueCard /></v-col>
|
||||||
<v-col cols="12" lg="4"
|
<v-col cols="12" lg="4"
|
||||||
><NewCustomer class="mb-6" />
|
><NewCustomer class="mb-6" />
|
||||||
<Totalincome />
|
<Totalincome />
|
||||||
</v-col>
|
</v-col>
|
||||||
<v-col cols="12" lg="8"><RevenueProduct/></v-col>
|
<v-col cols="12" lg="8"><RevenueProduct /></v-col>
|
||||||
<v-col cols="12" lg="4"><DailyActivities/> </v-col>
|
<v-col cols="12" lg="4"><DailyActivities /> </v-col>
|
||||||
<v-col cols="12"><BlogCards/></v-col>
|
<v-col cols="12"><BlogCards /></v-col>
|
||||||
</v-row>
|
</v-row>
|
||||||
</template>
|
</template>
|
||||||
|
|||||||
0
store/customizer.ts → stores/customizer.ts
Executable file → Normal file
0
store/customizer.ts → stores/customizer.ts
Executable file → Normal file
112
stores/rolePages.json
Normal file
112
stores/rolePages.json
Normal file
@@ -0,0 +1,112 @@
|
|||||||
|
[
|
||||||
|
{
|
||||||
|
"id_user": 1,
|
||||||
|
"username": "Super Admin",
|
||||||
|
"email": "admin@company.com",
|
||||||
|
"password": "123456",
|
||||||
|
"full_name": "System Administrator",
|
||||||
|
"role": "admin",
|
||||||
|
"role_description": "Administrative access with most permissions",
|
||||||
|
"roleMenu": [
|
||||||
|
{
|
||||||
|
"header": "dashboards",
|
||||||
|
"id": "1",
|
||||||
|
"children": [
|
||||||
|
{
|
||||||
|
"title": "Dashboard1",
|
||||||
|
"link": "/dashboards/dashboard1",
|
||||||
|
"create": "true",
|
||||||
|
"update": "false",
|
||||||
|
"delete": "false",
|
||||||
|
"view": "false"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"title": "Dashboard2",
|
||||||
|
"link": "/dashboards/dashboard1",
|
||||||
|
"create": "true",
|
||||||
|
"update": "false",
|
||||||
|
"delete": "false",
|
||||||
|
"view": "false"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"title": "Front Pages",
|
||||||
|
"link": "/",
|
||||||
|
"children": [
|
||||||
|
{
|
||||||
|
"title": "Homepage",
|
||||||
|
"to": "/front-page/homepage",
|
||||||
|
"create": "true",
|
||||||
|
"update": "false",
|
||||||
|
"delete": "false",
|
||||||
|
"view": "false"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"title": "About Us",
|
||||||
|
"to": "/front-page/about-us",
|
||||||
|
"create": "true",
|
||||||
|
"update": "false",
|
||||||
|
"delete": "false",
|
||||||
|
"view": "false"
|
||||||
|
}
|
||||||
|
]
|
||||||
|
}
|
||||||
|
]
|
||||||
|
}
|
||||||
|
]
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"id_user": 2,
|
||||||
|
"username": "user",
|
||||||
|
"email": "manager1@company.com",
|
||||||
|
"password": "234567",
|
||||||
|
"full_name": "John Manager",
|
||||||
|
"role": "user",
|
||||||
|
"role_description": "User level access for operational tasks",
|
||||||
|
"roleMenu": [
|
||||||
|
{
|
||||||
|
"header": "dashboards",
|
||||||
|
"id": "1",
|
||||||
|
"children": [
|
||||||
|
{
|
||||||
|
"title": "Dashboard1",
|
||||||
|
"link": "/dashboards/dashboard1",
|
||||||
|
"create": "false",
|
||||||
|
"update": "false",
|
||||||
|
"delete": "false",
|
||||||
|
"view": "false"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"title": "Dashboard2",
|
||||||
|
"link": "/dashboards/dashboard1",
|
||||||
|
"create": "false",
|
||||||
|
"update": "false",
|
||||||
|
"delete": "false",
|
||||||
|
"view": "false"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"title": "Front Pages",
|
||||||
|
"link": "/",
|
||||||
|
"children": [
|
||||||
|
{
|
||||||
|
"title": "Homepage",
|
||||||
|
"to": "/front-page/homepage",
|
||||||
|
"create": "false",
|
||||||
|
"update": "false",
|
||||||
|
"delete": "false",
|
||||||
|
"view": "false"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"title": "About Us",
|
||||||
|
"to": "/front-page/about-us",
|
||||||
|
"create": "false",
|
||||||
|
"update": "false",
|
||||||
|
"delete": "false",
|
||||||
|
"view": "false"
|
||||||
|
}
|
||||||
|
]
|
||||||
|
}
|
||||||
|
]
|
||||||
|
}
|
||||||
|
]
|
||||||
|
}
|
||||||
|
]
|
||||||
97
stores/rolePages.ts
Normal file
97
stores/rolePages.ts
Normal file
@@ -0,0 +1,97 @@
|
|||||||
|
const rolePages = [
|
||||||
|
{
|
||||||
|
id_user: 1,
|
||||||
|
username: "Super Admin",
|
||||||
|
email: "admin@company.com",
|
||||||
|
password: "123456",
|
||||||
|
full_name: "System Administrator",
|
||||||
|
role: "admin",
|
||||||
|
role_description: "Administrative access with most permissions",
|
||||||
|
pages: [
|
||||||
|
{
|
||||||
|
title: "Dashboard1",
|
||||||
|
path: "/dashboards/dashboard1",
|
||||||
|
permissions: ["create", "view", "update", "delete"],
|
||||||
|
},
|
||||||
|
{
|
||||||
|
title: "Dashboard3",
|
||||||
|
path: "/dashboards/dashboard3",
|
||||||
|
permissions: ["create", "view", "update", "delete"],
|
||||||
|
},
|
||||||
|
{
|
||||||
|
title: "Homepage",
|
||||||
|
path: "/front-page/homepage",
|
||||||
|
permissions: ["create", "view", "update", "delete"],
|
||||||
|
},
|
||||||
|
{
|
||||||
|
title: "About Us",
|
||||||
|
path: "/front-page/about-us",
|
||||||
|
permissions: ["create", "view", "update", "delete"],
|
||||||
|
},
|
||||||
|
{
|
||||||
|
title: "Error",
|
||||||
|
path: "/auth/404",
|
||||||
|
permissions: ["view"],
|
||||||
|
},
|
||||||
|
{
|
||||||
|
title: "Side Login",
|
||||||
|
path: "/auth/login",
|
||||||
|
permissions: ["view"],
|
||||||
|
},
|
||||||
|
{
|
||||||
|
title: "Shop",
|
||||||
|
path: "/ecommerce/products",
|
||||||
|
permissions: ["view"],
|
||||||
|
},
|
||||||
|
{
|
||||||
|
title: "Detail",
|
||||||
|
path: "/ecommerce/product/detail/1",
|
||||||
|
permissions: ["view"],
|
||||||
|
},
|
||||||
|
{
|
||||||
|
title: "Autocomplete",
|
||||||
|
path: "/forms/form-elements/autocomplete",
|
||||||
|
permissions: ["view"],
|
||||||
|
},
|
||||||
|
{
|
||||||
|
title: "Combobox",
|
||||||
|
path: "/forms/form-elements/combobox",
|
||||||
|
permissions: ["view"],
|
||||||
|
},
|
||||||
|
],
|
||||||
|
},
|
||||||
|
|
||||||
|
{
|
||||||
|
id_user: 2,
|
||||||
|
username: "user",
|
||||||
|
email: "manager1@company.com",
|
||||||
|
password: "234567",
|
||||||
|
full_name: "John Manager",
|
||||||
|
role: "user",
|
||||||
|
role_description: "User level access for operational tasks",
|
||||||
|
pages: [
|
||||||
|
{
|
||||||
|
title: "Dashboard1",
|
||||||
|
path: "/dashboards/dashboard1",
|
||||||
|
permissions: ["view"],
|
||||||
|
},
|
||||||
|
{
|
||||||
|
title: "Dashboard2",
|
||||||
|
path: "/dashboards/dashboard1",
|
||||||
|
permissions: ["view"],
|
||||||
|
},
|
||||||
|
{
|
||||||
|
title: "Homepage",
|
||||||
|
path: "/front-page/homepage",
|
||||||
|
permissions: ["view"],
|
||||||
|
},
|
||||||
|
{
|
||||||
|
title: "About Us",
|
||||||
|
path: "/front-page/about-us",
|
||||||
|
permissions: ["view"],
|
||||||
|
},
|
||||||
|
],
|
||||||
|
},
|
||||||
|
];
|
||||||
|
|
||||||
|
export default rolePages;
|
||||||
28
stores/sidebarMenuAkses/useMenuAksesStore.ts
Normal file
28
stores/sidebarMenuAkses/useMenuAksesStore.ts
Normal file
@@ -0,0 +1,28 @@
|
|||||||
|
import { defineStore } from 'pinia'
|
||||||
|
import type { PageAccess } from '@/types/menuAkses/access'
|
||||||
|
|
||||||
|
export const useHakAksesStore = defineStore('hakAksesMenu', {
|
||||||
|
state: () => ({
|
||||||
|
role: '',
|
||||||
|
pageAccess: [] as PageAccess[], //Array halaman dengan permissions
|
||||||
|
mergedSidebar: []
|
||||||
|
}),
|
||||||
|
|
||||||
|
actions: {
|
||||||
|
setAccess(payload: { role: string; pages: PageAccess[] }) {
|
||||||
|
this.role = payload.role
|
||||||
|
this.pageAccess = payload.pages
|
||||||
|
},
|
||||||
|
|
||||||
|
resetAccess() {
|
||||||
|
this.role = ''
|
||||||
|
this.pageAccess = []
|
||||||
|
},
|
||||||
|
|
||||||
|
setMergedSidebar(data: any) {
|
||||||
|
this.mergedSidebar = data
|
||||||
|
}
|
||||||
|
}
|
||||||
|
})
|
||||||
|
|
||||||
|
|
||||||
10
types/menuAkses/access.ts
Normal file
10
types/menuAkses/access.ts
Normal file
@@ -0,0 +1,10 @@
|
|||||||
|
export interface PageAccess {
|
||||||
|
path?: string
|
||||||
|
permissions?: string[]
|
||||||
|
title?: string;
|
||||||
|
}
|
||||||
|
|
||||||
|
export interface RoleAccess {
|
||||||
|
role?: string
|
||||||
|
pages?: PageAccess[]
|
||||||
|
}
|
||||||
40
types/menuAkses/sidebar.ts
Normal file
40
types/menuAkses/sidebar.ts
Normal file
@@ -0,0 +1,40 @@
|
|||||||
|
// types/sidebar.ts
|
||||||
|
|
||||||
|
export interface SidebarItem {
|
||||||
|
header?: string;
|
||||||
|
title?: string;
|
||||||
|
icon?: any;
|
||||||
|
id?: number;
|
||||||
|
to?: string;
|
||||||
|
chip?: string;
|
||||||
|
BgColor?: string;
|
||||||
|
chipBgColor?: string;
|
||||||
|
chipColor?: string;
|
||||||
|
chipVariant?: string;
|
||||||
|
chipIcon?: string;
|
||||||
|
children?: menu[];
|
||||||
|
disabled?: boolean;
|
||||||
|
type?: string;
|
||||||
|
subCaption?: string;
|
||||||
|
role?: string[];
|
||||||
|
permission?: string[];
|
||||||
|
}
|
||||||
|
export interface menu {
|
||||||
|
header?: string;
|
||||||
|
title?: string;
|
||||||
|
icon?: any;
|
||||||
|
id?: number;
|
||||||
|
to?: string;
|
||||||
|
chip?: string;
|
||||||
|
BgColor?: string;
|
||||||
|
chipBgColor?: string;
|
||||||
|
chipColor?: string;
|
||||||
|
chipVariant?: string;
|
||||||
|
chipIcon?: string;
|
||||||
|
children?: menu[];
|
||||||
|
disabled?: boolean;
|
||||||
|
type?: string;
|
||||||
|
subCaption?: string;
|
||||||
|
role?: string[];
|
||||||
|
permission?: string[];
|
||||||
|
}
|
||||||
Reference in New Issue
Block a user