script[setup]: modules/content (#18442)

This commit is contained in:
Rijk van Zanten
2023-05-03 11:32:35 -04:00
committed by GitHub
parent b9213304d1
commit e5897177bf
7 changed files with 404 additions and 566 deletions

View File

@@ -5,27 +5,17 @@
<v-list-item-content><v-text-overflow :text="name" :highlight="search" /></v-list-item-content>
</template>
<script lang="ts">
import { defineComponent } from 'vue';
export default defineComponent({
props: {
icon: {
type: String,
default: 'label',
},
color: {
type: String,
default: 'var(--foreground-normal)',
},
name: {
type: String,
required: true,
},
search: {
type: String,
default: null,
},
},
});
<script setup lang="ts">
withDefaults(
defineProps<{
name: string;
search?: string;
icon?: string;
color?: string;
}>(),
{
icon: 'label',
color: 'var(--foreground-normal)',
}
);
</script>

View File

@@ -57,8 +57,8 @@
</v-menu>
</template>
<script lang="ts">
import { defineComponent, PropType, computed } from 'vue';
<script setup lang="ts">
import { computed } from 'vue';
import { Collection } from '@/types/collections';
import { Preset } from '@directus/types';
import { useUserStore } from '@/stores/user';
@@ -69,95 +69,70 @@ import NavigationBookmark from './navigation-bookmark.vue';
import { useI18n } from 'vue-i18n';
import { orderBy } from 'lodash';
export default defineComponent({
name: 'NavigationItem',
components: { NavigationItemContent, NavigationBookmark },
props: {
collection: {
type: Object as PropType<Collection>,
required: true,
},
showHidden: {
type: Boolean,
default: false,
},
search: {
type: String,
default: null,
},
},
setup(props) {
const { t } = useI18n();
const props = defineProps<{
collection: Collection;
showHidden?: boolean;
search?: string;
}>();
const { isAdmin } = useUserStore();
const collectionsStore = useCollectionsStore();
const presetsStore = usePresetsStore();
const { t } = useI18n();
const childCollections = computed(() => getChildCollections(props.collection));
const { isAdmin } = useUserStore();
const collectionsStore = useCollectionsStore();
const presetsStore = usePresetsStore();
const childBookmarks = computed(() => getChildBookmarks(props.collection));
const childCollections = computed(() => getChildCollections(props.collection));
const isGroup = computed(() => childCollections.value.length > 0 || childBookmarks.value.length > 0);
const childBookmarks = computed(() => getChildBookmarks(props.collection));
const to = computed(() => (props.collection.schema ? `/content/${props.collection.collection}` : ''));
const isGroup = computed(() => childCollections.value.length > 0 || childBookmarks.value.length > 0);
const matchesSearch = computed(() => {
if (!props.search || props.search.length < 3) return true;
const to = computed(() => (props.collection.schema ? `/content/${props.collection.collection}` : ''));
const searchQuery = props.search.toLowerCase();
const matchesSearch = computed(() => {
if (!props.search || props.search.length < 3) return true;
return matchesSearch(props.collection) || childrenMatchSearch(childCollections.value, childBookmarks.value);
const searchQuery = props.search.toLowerCase();
function childrenMatchSearch(collections: Collection[], bookmarks: Preset[]): boolean {
return (
collections.some((collection) => {
const childCollections = getChildCollections(collection);
const childBookmarks = getChildBookmarks(collection);
return matchesSearch(props.collection) || childrenMatchSearch(childCollections.value, childBookmarks.value);
return matchesSearch(collection) || childrenMatchSearch(childCollections, childBookmarks);
}) || bookmarks.some((bookmark) => bookmarkMatchesSearch(bookmark))
);
}
function childrenMatchSearch(collections: Collection[], bookmarks: Preset[]): boolean {
return (
collections.some((collection) => {
const childCollections = getChildCollections(collection);
const childBookmarks = getChildBookmarks(collection);
function matchesSearch(collection: Collection) {
return collection.collection.includes(searchQuery) || collection.name.toLowerCase().includes(searchQuery);
}
return matchesSearch(collection) || childrenMatchSearch(childCollections, childBookmarks);
}) || bookmarks.some((bookmark) => bookmarkMatchesSearch(bookmark))
);
}
function bookmarkMatchesSearch(bookmark: Preset) {
return bookmark.bookmark?.toLowerCase().includes(searchQuery);
}
});
function matchesSearch(collection: Collection) {
return collection.collection.includes(searchQuery) || collection.name.toLowerCase().includes(searchQuery);
}
const hasContextMenu = computed(() => isAdmin && props.collection.type === 'table');
return {
childCollections,
childBookmarks,
isGroup,
to,
matchesSearch,
isAdmin,
t,
hasContextMenu,
};
function getChildCollections(collection: Collection) {
let collections = collectionsStore.collections.filter(
(childCollection) => childCollection.meta?.group === collection.collection
);
if (props.showHidden === false) {
collections = collections.filter((collection) => collection.meta?.hidden !== true);
}
return orderBy(collections, ['meta.sort', 'collection']);
}
function getChildBookmarks(collection: Collection) {
return presetsStore.bookmarks.filter((bookmark) => bookmark.collection === collection.collection);
}
},
function bookmarkMatchesSearch(bookmark: Preset) {
return bookmark.bookmark?.toLowerCase().includes(searchQuery);
}
});
const hasContextMenu = computed(() => isAdmin && props.collection.type === 'table');
function getChildCollections(collection: Collection) {
let collections = collectionsStore.collections.filter(
(childCollection) => childCollection.meta?.group === collection.collection
);
if (props.showHidden === false) {
collections = collections.filter((collection) => collection.meta?.hidden !== true);
}
return orderBy(collections, ['meta.sort', 'collection']);
}
function getChildBookmarks(collection: Collection) {
return presetsStore.bookmarks.filter((bookmark) => bookmark.collection === collection.collection);
}
</script>
<style scoped>

View File

@@ -36,60 +36,42 @@
</div>
</template>
<script lang="ts">
import { useI18n } from 'vue-i18n';
import { defineComponent, computed, ref, toRefs } from 'vue';
import { useNavigation } from '../composables/use-navigation';
<script setup lang="ts">
import { useCollectionsStore } from '@/stores/collections';
import { orderBy, isNil } from 'lodash';
import { isNil, orderBy } from 'lodash';
import { computed, ref, toRefs } from 'vue';
import { useI18n } from 'vue-i18n';
import { useNavigation } from '../composables/use-navigation';
import NavigationItem from './navigation-item.vue';
export default defineComponent({
components: { NavigationItem },
props: {
currentCollection: {
type: String,
default: null,
},
},
setup(props) {
const { t } = useI18n();
const { currentCollection } = toRefs(props);
const { activeGroups, showHidden } = useNavigation(currentCollection);
const props = defineProps<{
currentCollection?: string;
}>();
const search = ref('');
const { t } = useI18n();
const { currentCollection } = toRefs(props);
const { activeGroups, showHidden } = useNavigation(currentCollection);
const collectionsStore = useCollectionsStore();
const search = ref('');
const rootItems = computed(() => {
const shownCollections = showHidden.value ? collectionsStore.allCollections : collectionsStore.visibleCollections;
return orderBy(
shownCollections.filter((collection) => {
return isNil(collection?.meta?.group);
}),
['meta.sort', 'collection']
);
});
const collectionsStore = useCollectionsStore();
const dense = computed(() => collectionsStore.visibleCollections.length > 5);
const showSearch = computed(() => collectionsStore.visibleCollections.length > 20);
const hasHiddenCollections = computed(
() => collectionsStore.allCollections.length > collectionsStore.visibleCollections.length
);
return {
t,
activeGroups,
showHidden,
rootItems,
dense,
search,
showSearch,
hasHiddenCollections,
};
},
const rootItems = computed(() => {
const shownCollections = showHidden.value ? collectionsStore.allCollections : collectionsStore.visibleCollections;
return orderBy(
shownCollections.filter((collection) => {
return isNil(collection?.meta?.group);
}),
['meta.sort', 'collection']
);
});
const dense = computed(() => collectionsStore.visibleCollections.length > 5);
const showSearch = computed(() => collectionsStore.visibleCollections.length > 20);
const hasHiddenCollections = computed(
() => collectionsStore.allCollections.length > collectionsStore.visibleCollections.length
);
</script>
<style lang="scss" scoped>

View File

@@ -1,6 +1,6 @@
<template>
<component
:is="isSingleton ? 'item-route' : 'collection-route'"
:is="isSingleton ? ItemRoute : CollectionRoute"
:collection="collection"
:bookmark="bookmark"
:archive="archive"
@@ -8,56 +8,38 @@
/>
</template>
<script lang="ts">
import { defineComponent, computed, watch } from 'vue';
<script setup lang="ts">
import { computed, watch } from 'vue';
import CollectionRoute from './collection.vue';
import ItemRoute from './item.vue';
import { useCollectionsStore } from '@/stores/collections';
import { useRoute } from 'vue-router';
import { useLocalStorage } from '@/composables/use-local-storage';
export default defineComponent({
components: {
CollectionRoute,
ItemRoute,
},
props: {
collection: {
type: String,
required: true,
},
bookmark: {
type: String,
default: null,
},
archive: {
type: String,
default: null,
},
},
setup(props) {
const route = useRoute();
const props = defineProps<{
collection: string;
bookmark?: string;
archive?: string;
}>();
const { data } = useLocalStorage('last-accessed-collection');
const route = useRoute();
const collectionsStore = useCollectionsStore();
const { data } = useLocalStorage('last-accessed-collection');
const isSingleton = computed(() => {
const collectionInfo = collectionsStore.getCollection(props.collection);
return !!collectionInfo?.meta?.singleton === true;
});
const collectionsStore = useCollectionsStore();
watch(
() => route.params,
(newParams) => {
if (newParams.collection && data.value !== newParams.collection) {
data.value = newParams.collection;
}
},
{ immediate: true }
);
return { isSingleton };
},
const isSingleton = computed(() => {
const collectionInfo = collectionsStore.getCollection(props.collection);
return !!collectionInfo?.meta?.singleton === true;
});
watch(
() => route.params,
(newParams) => {
if (newParams.collection && data.value !== newParams.collection) {
data.value = newParams.collection;
}
},
{ immediate: true }
);
</script>

View File

@@ -270,410 +270,337 @@
</component>
</template>
<script lang="ts">
import { useI18n } from 'vue-i18n';
import { defineComponent, computed, ref, watch, toRefs } from 'vue';
import ContentNavigation from '../components/navigation.vue';
<script setup lang="ts">
import api from '@/api';
import ContentNotFound from './not-found.vue';
import { useCollection, useLayout } from '@directus/composables';
import { useExtension } from '@/composables/use-extension';
import { usePreset } from '@/composables/use-preset';
import LayoutSidebarDetail from '@/views/private/components/layout-sidebar-detail.vue';
import ArchiveSidebarDetail from '@/views/private/components/archive-sidebar-detail.vue';
import RefreshSidebarDetail from '@/views/private/components/refresh-sidebar-detail.vue';
import ExportSidebarDetail from '@/views/private/components/export-sidebar-detail.vue';
import FlowSidebarDetail from '@/views/private/components/flow-sidebar-detail.vue';
import SearchInput from '@/views/private/components/search-input.vue';
import BookmarkAdd from '@/views/private/components/bookmark-add.vue';
import { useRouter } from 'vue-router';
import { usePermissionsStore } from '@/stores/permissions';
import { useUserStore } from '@/stores/user';
import DrawerBatch from '@/views/private/components/drawer-batch.vue';
import { unexpectedError } from '@/utils/unexpected-error';
import { mergeFilters } from '@directus/utils';
import ArchiveSidebarDetail from '@/views/private/components/archive-sidebar-detail.vue';
import BookmarkAdd from '@/views/private/components/bookmark-add.vue';
import DrawerBatch from '@/views/private/components/drawer-batch.vue';
import ExportSidebarDetail from '@/views/private/components/export-sidebar-detail.vue';
import FlowSidebarDetail from '@/views/private/components/flow-sidebar-detail.vue';
import LayoutSidebarDetail from '@/views/private/components/layout-sidebar-detail.vue';
import RefreshSidebarDetail from '@/views/private/components/refresh-sidebar-detail.vue';
import SearchInput from '@/views/private/components/search-input.vue';
import { useCollection, useLayout } from '@directus/composables';
import { Filter } from '@directus/types';
import { useExtension } from '@/composables/use-extension';
import { mergeFilters } from '@directus/utils';
import { computed, ref, toRefs, watch } from 'vue';
import { useI18n } from 'vue-i18n';
import { useRouter } from 'vue-router';
import ContentNavigation from '../components/navigation.vue';
import ContentNotFound from './not-found.vue';
type Item = {
[field: string]: any;
};
export default defineComponent({
name: 'ContentCollection',
components: {
ContentNavigation,
ContentNotFound,
LayoutSidebarDetail,
SearchInput,
BookmarkAdd,
DrawerBatch,
ArchiveSidebarDetail,
RefreshSidebarDetail,
ExportSidebarDetail,
FlowSidebarDetail,
const props = defineProps<{
collection: string;
bookmark?: string;
archive?: string;
}>();
const { t } = useI18n();
const router = useRouter();
const userStore = useUserStore();
const permissionsStore = usePermissionsStore();
const layoutRef = ref();
const { collection } = toRefs(props);
const bookmarkID = computed(() => (props.bookmark ? +props.bookmark : null));
const { selection } = useSelection();
const { info: currentCollection } = useCollection(collection);
const { addNewLink, currentCollectionLink } = useLinks();
const { breadcrumb } = useBreadcrumb();
const {
layout,
layoutOptions,
layoutQuery,
filter,
search,
savePreset,
bookmarkExists,
saveCurrentAsBookmark,
bookmarkTitle,
resetPreset,
bookmarkSaved,
bookmarkIsMine,
refreshInterval,
busy: bookmarkSaving,
clearLocalSave,
} = usePreset(collection, bookmarkID);
const { layoutWrapper } = useLayout(layout);
const {
confirmDelete,
deleting,
batchDelete,
confirmArchive,
archiveItems,
archiving,
error: deleteError,
batchEditActive,
} = useBatch();
const { bookmarkDialogActive, creatingBookmark, createBookmark } = useBookmarks();
const currentLayout = useExtension('layout', layout);
watch(
collection,
() => {
if (layout.value === null) {
layout.value = 'tabular';
}
},
props: {
collection: {
type: String,
required: true,
},
bookmark: {
type: String,
default: null,
},
archive: {
type: String,
default: null,
},
},
setup(props) {
const { t } = useI18n();
{ immediate: true }
);
const router = useRouter();
const { batchEditAllowed, batchArchiveAllowed, batchDeleteAllowed, createAllowed } = usePermissions();
const userStore = useUserStore();
const permissionsStore = usePermissionsStore();
const layoutRef = ref();
const hasArchive = computed(
() =>
currentCollection.value &&
currentCollection.value.meta?.archive_field &&
currentCollection.value.meta?.archive_app_filter
);
const { collection } = toRefs(props);
const bookmarkID = computed(() => (props.bookmark ? +props.bookmark : null));
const archiveFilter = computed<Filter | null>(() => {
if (!currentCollection.value?.meta) return null;
if (!currentCollection.value?.meta?.archive_app_filter) return null;
const { selection } = useSelection();
const { info: currentCollection } = useCollection(collection);
const { addNewLink, currentCollectionLink } = useLinks();
const { breadcrumb } = useBreadcrumb();
const field = currentCollection.value.meta.archive_field;
const {
layout,
layoutOptions,
layoutQuery,
filter,
search,
savePreset,
bookmarkExists,
saveCurrentAsBookmark,
bookmarkTitle,
resetPreset,
bookmarkSaved,
bookmarkIsMine,
refreshInterval,
busy: bookmarkSaving,
clearLocalSave,
} = usePreset(collection, bookmarkID);
if (!field) return null;
const { layoutWrapper } = useLayout(layout);
const {
confirmDelete,
deleting,
batchDelete,
confirmArchive,
archiveItems,
archiving,
error: deleteError,
batchEditActive,
} = useBatch();
const { bookmarkDialogActive, creatingBookmark, createBookmark } = useBookmarks();
const currentLayout = useExtension('layout', layout);
watch(
collection,
() => {
if (layout.value === null) {
layout.value = 'tabular';
}
},
{ immediate: true }
);
const { batchEditAllowed, batchArchiveAllowed, batchDeleteAllowed, createAllowed } = usePermissions();
const hasArchive = computed(
() =>
currentCollection.value &&
currentCollection.value.meta?.archive_field &&
currentCollection.value.meta?.archive_app_filter
);
const archiveFilter = computed<Filter | null>(() => {
if (!currentCollection.value?.meta) return null;
if (!currentCollection.value?.meta?.archive_app_filter) return null;
const field = currentCollection.value.meta.archive_field;
if (!field) return null;
let archiveValue: any = currentCollection.value.meta.archive_value;
if (archiveValue === 'true') archiveValue = true;
if (archiveValue === 'false') archiveValue = false;
if (props.archive === 'all') {
return null;
} else if (props.archive === 'archived') {
return {
[field]: {
_eq: archiveValue,
},
};
} else {
return {
[field]: {
_neq: archiveValue,
},
};
}
});
let archiveValue: any = currentCollection.value.meta.archive_value;
if (archiveValue === 'true') archiveValue = true;
if (archiveValue === 'false') archiveValue = false;
if (props.archive === 'all') {
return null;
} else if (props.archive === 'archived') {
return {
t,
addNewLink,
batchDelete,
batchEditActive,
confirmDelete,
currentCollection,
deleting,
filter,
layoutRef,
layoutWrapper,
selection,
layoutOptions,
layoutQuery,
layout,
search,
savePreset,
bookmarkExists,
currentCollectionLink,
bookmarkDialogActive,
creatingBookmark,
createBookmark,
bookmarkTitle,
breadcrumb,
clearFilters,
confirmArchive,
archiveItems,
archiving,
batchEditAllowed,
batchArchiveAllowed,
batchDeleteAllowed,
deleteError,
createAllowed,
resetPreset,
bookmarkSaved,
bookmarkIsMine,
bookmarkSaving,
clearLocalSave,
batchRefresh,
refresh,
refreshInterval,
currentLayout,
hasArchive,
archiveFilter,
mergeFilters,
download,
[field]: {
_eq: archiveValue,
},
};
} else {
return {
[field]: {
_neq: archiveValue,
},
};
}
});
async function refresh() {
await layoutRef.value?.state?.refresh?.();
}
async function refresh() {
await layoutRef.value?.state?.refresh?.();
}
async function download() {
await layoutRef.value?.state?.download?.();
}
async function download() {
await layoutRef.value?.state?.download?.();
}
async function batchRefresh() {
selection.value = [];
await refresh();
}
function useBreadcrumb() {
const breadcrumb = computed(() => [
{
name: currentCollection.value?.name,
to: `/content/${props.collection}`,
},
]);
return { breadcrumb };
}
function useSelection() {
const selection = ref<Item[]>([]);
// Whenever the collection we're working on changes, we have to clear the selection
watch(
() => props.collection,
() => (selection.value = [])
);
return { selection };
}
function useBatch() {
const confirmDelete = ref(false);
const deleting = ref(false);
const batchEditActive = ref(false);
const confirmArchive = ref(false);
const archiving = ref(false);
const error = ref<any>(null);
return { batchEditActive, confirmDelete, deleting, batchDelete, confirmArchive, archiving, archiveItems, error };
async function batchDelete() {
deleting.value = true;
const batchPrimaryKeys = selection.value;
try {
await api.delete(`/items/${props.collection}`, {
data: batchPrimaryKeys,
});
async function batchRefresh() {
selection.value = [];
await refresh();
}
function useBreadcrumb() {
const breadcrumb = computed(() => [
{
name: currentCollection.value?.name,
to: `/content/${props.collection}`,
confirmDelete.value = false;
} catch (err: any) {
error.value = err;
} finally {
deleting.value = false;
}
}
async function archiveItems() {
if (!currentCollection.value?.meta?.archive_field) return;
archiving.value = true;
let archiveValue: any = currentCollection.value.meta.archive_value;
if (archiveValue === 'true') archiveValue = true;
if (archiveValue === 'false') archiveValue = false;
try {
await api.patch(`/items/${props.collection}`, {
keys: selection.value,
data: {
[currentCollection.value.meta.archive_field]: archiveValue,
},
]);
return { breadcrumb };
}
function useSelection() {
const selection = ref<Item[]>([]);
// Whenever the collection we're working on changes, we have to clear the selection
watch(
() => props.collection,
() => (selection.value = [])
);
return { selection };
}
function useBatch() {
const confirmDelete = ref(false);
const deleting = ref(false);
const batchEditActive = ref(false);
const confirmArchive = ref(false);
const archiving = ref(false);
const error = ref<any>(null);
return { batchEditActive, confirmDelete, deleting, batchDelete, confirmArchive, archiving, archiveItems, error };
async function batchDelete() {
deleting.value = true;
const batchPrimaryKeys = selection.value;
try {
await api.delete(`/items/${props.collection}`, {
data: batchPrimaryKeys,
});
selection.value = [];
await refresh();
confirmDelete.value = false;
} catch (err: any) {
error.value = err;
} finally {
deleting.value = false;
}
}
async function archiveItems() {
if (!currentCollection.value?.meta?.archive_field) return;
archiving.value = true;
let archiveValue: any = currentCollection.value.meta.archive_value;
if (archiveValue === 'true') archiveValue = true;
if (archiveValue === 'false') archiveValue = false;
try {
await api.patch(`/items/${props.collection}`, {
keys: selection.value,
data: {
[currentCollection.value.meta.archive_field]: archiveValue,
},
});
selection.value = [];
await refresh();
confirmArchive.value = false;
} catch (err: any) {
error.value = err;
} finally {
archiving.value = false;
}
}
}
function useLinks() {
const addNewLink = computed<string>(() => {
return `/content/${props.collection}/+`;
});
const currentCollectionLink = computed<string>(() => {
return `/content/${props.collection}`;
});
selection.value = [];
await refresh();
return { addNewLink, currentCollectionLink };
confirmArchive.value = false;
} catch (err: any) {
error.value = err;
} finally {
archiving.value = false;
}
}
}
function useBookmarks() {
const bookmarkDialogActive = ref(false);
const creatingBookmark = ref(false);
function useLinks() {
const addNewLink = computed<string>(() => {
return `/content/${props.collection}/+`;
});
return {
bookmarkDialogActive,
creatingBookmark,
createBookmark,
};
const currentCollectionLink = computed<string>(() => {
return `/content/${props.collection}`;
});
async function createBookmark(bookmark: any) {
creatingBookmark.value = true;
return { addNewLink, currentCollectionLink };
}
try {
const newBookmark = await saveCurrentAsBookmark({
bookmark: bookmark.name,
icon: bookmark.icon,
color: bookmark.color,
});
function useBookmarks() {
const bookmarkDialogActive = ref(false);
const creatingBookmark = ref(false);
router.push(`/content/${newBookmark.collection}?bookmark=${newBookmark.id}`);
return {
bookmarkDialogActive,
creatingBookmark,
createBookmark,
};
bookmarkDialogActive.value = false;
} catch (err: any) {
unexpectedError(err);
} finally {
creatingBookmark.value = false;
}
}
async function createBookmark(bookmark: any) {
creatingBookmark.value = true;
try {
const newBookmark = await saveCurrentAsBookmark({
bookmark: bookmark.name,
icon: bookmark.icon,
color: bookmark.color,
});
router.push(`/content/${newBookmark.collection}?bookmark=${newBookmark.id}`);
bookmarkDialogActive.value = false;
} catch (err: any) {
unexpectedError(err);
} finally {
creatingBookmark.value = false;
}
}
}
function clearFilters() {
filter.value = null;
search.value = null;
}
function clearFilters() {
filter.value = null;
search.value = null;
}
function usePermissions() {
const batchEditAllowed = computed(() => {
const admin = userStore?.currentUser?.role.admin_access === true;
if (admin) return true;
function usePermissions() {
const batchEditAllowed = computed(() => {
const admin = userStore?.currentUser?.role.admin_access === true;
if (admin) return true;
const updatePermissions = permissionsStore.permissions.find(
(permission) => permission.action === 'update' && permission.collection === collection.value
);
const updatePermissions = permissionsStore.permissions.find(
(permission) => permission.action === 'update' && permission.collection === collection.value
);
return !!updatePermissions;
});
return !!updatePermissions;
});
const batchArchiveAllowed = computed(() => {
if (!currentCollection.value?.meta?.archive_field) return false;
const admin = userStore?.currentUser?.role.admin_access === true;
if (admin) return true;
const batchArchiveAllowed = computed(() => {
if (!currentCollection.value?.meta?.archive_field) return false;
const admin = userStore?.currentUser?.role.admin_access === true;
if (admin) return true;
const updatePermissions = permissionsStore.permissions.find(
(permission) => permission.action === 'update' && permission.collection === collection.value
);
const updatePermissions = permissionsStore.permissions.find(
(permission) => permission.action === 'update' && permission.collection === collection.value
);
if (!updatePermissions) return false;
if (!updatePermissions.fields) return false;
if (updatePermissions.fields.includes('*')) return true;
return updatePermissions.fields.includes(currentCollection.value.meta.archive_field);
});
if (!updatePermissions) return false;
if (!updatePermissions.fields) return false;
if (updatePermissions.fields.includes('*')) return true;
return updatePermissions.fields.includes(currentCollection.value.meta.archive_field);
});
const batchDeleteAllowed = computed(() => {
const admin = userStore?.currentUser?.role.admin_access === true;
if (admin) return true;
const batchDeleteAllowed = computed(() => {
const admin = userStore?.currentUser?.role.admin_access === true;
if (admin) return true;
const deletePermissions = permissionsStore.permissions.find(
(permission) => permission.action === 'delete' && permission.collection === collection.value
);
const deletePermissions = permissionsStore.permissions.find(
(permission) => permission.action === 'delete' && permission.collection === collection.value
);
return !!deletePermissions;
});
return !!deletePermissions;
});
const createAllowed = computed(() => {
const admin = userStore?.currentUser?.role.admin_access === true;
if (admin) return true;
const createAllowed = computed(() => {
const admin = userStore?.currentUser?.role.admin_access === true;
if (admin) return true;
const createPermissions = permissionsStore.permissions.find(
(permission) => permission.action === 'create' && permission.collection === collection.value
);
const createPermissions = permissionsStore.permissions.find(
(permission) => permission.action === 'create' && permission.collection === collection.value
);
return !!createPermissions;
});
return !!createPermissions;
});
return { batchEditAllowed, batchArchiveAllowed, batchDeleteAllowed, createAllowed };
}
},
});
return { batchEditAllowed, batchArchiveAllowed, batchDeleteAllowed, createAllowed };
}
</script>
<style lang="scss" scoped>

View File

@@ -32,28 +32,17 @@
</private-view>
</template>
<script lang="ts">
import { useI18n } from 'vue-i18n';
import { defineComponent, computed } from 'vue';
import ContentNavigation from '../components/navigation.vue';
<script setup lang="ts">
import { useUserStore } from '@/stores/user';
import { computed } from 'vue';
import { useI18n } from 'vue-i18n';
import ContentNavigation from '../components/navigation.vue';
export default defineComponent({
name: 'ContentOverview',
components: {
ContentNavigation,
},
props: {},
setup() {
const { t } = useI18n();
const { t } = useI18n();
const userStore = useUserStore();
const userStore = useUserStore();
const isAdmin = computed(() => userStore.currentUser?.role.admin_access === true);
return { t, isAdmin };
},
});
const isAdmin = computed(() => userStore.currentUser?.role.admin_access === true);
</script>
<style lang="scss" scoped>

View File

@@ -12,18 +12,11 @@
</private-view>
</template>
<script lang="ts">
<script setup lang="ts">
import { useI18n } from 'vue-i18n';
import { defineComponent } from 'vue';
import ContentNavigation from '../components/navigation.vue';
export default defineComponent({
components: { ContentNavigation },
setup() {
const { t } = useI18n();
return { t };
},
});
const { t } = useI18n();
</script>
<style lang="scss" scoped>