phongdt #8

Merged
Ghost merged 5 commits from phongdt into main 2024-07-05 08:13:31 +00:00
3 changed files with 144 additions and 136 deletions
@@ -1,25 +1,29 @@
<script setup lang="ts"> <script setup lang="ts">
import { isEmpty } from "@/utils/lodash";
import DynamicComponent from "~/components/dynamic-page/page-component/templates/index.vue"; import DynamicComponent from "~/components/dynamic-page/page-component/templates/index.vue";
import { COLLECTION_PAGING_QUERY_DROP, getInputValue } from "@/utils/parseSQL"; import { getInputValue } from "@/utils/parseSQL";
import { enumPageComponentTemplates } from "@/definitions/enum";
const router = useRouter(); const router = useRouter();
const route = useRoute(); const route = useRoute();
// const store = reactive({ const store = reactive({
// component: usePageComponentStore(), component: useDynamicPageStore(),
// }); });
const _props = defineProps<{ const _props = defineProps<{
dataResult?: any; dataResult?: any[];
dataQuery?: string; dataQuery?: string;
component?: any; component?: any;
label?: any; label?: string;
}>(); }>();
const SETTING_OPTIONS = { const SETTING_OPTIONS = {
MAX_ELEMENT: 5, MAX_ELEMENT: 5,
TEMPLATE: "Article", TEMPLATE: "TYPE:Card",
LAYOUT: "TYPE:Card", LAYOUT: "TYPE:Card_Default",
};
const COMPONENT = {
taxonomy: enumPageComponentTemplates.ARTICLE,
}; };
const page = ref(1); const page = ref(1);
@@ -60,7 +64,7 @@ const handleRouteChange = async (query: any) => {
const param = query[`cpn_${_props.component?.id}`]; const param = query[`cpn_${_props.component?.id}`];
if (param) { if (param) {
const [_, value] = param.split(":") || []; const [_, value] = param.split(":") || [];
page.value = value; page.value = Number(value);
await loadPage(value); await loadPage(value);
} }
}; };
@@ -79,12 +83,13 @@ const loadPage = async (page: number) => {
} else { } else {
newDataQuery = _props.component?.settings?.dataQuery + ` Page[${page}]`; newDataQuery = _props.component?.settings?.dataQuery + ` Page[${page}]`;
} }
// const res = await store.component.getOverviewPageComponentById(Number(_props.component?.id), newDataQuery); const {item} = await store.component.getOverviewPageComponentById(Number(_props.component?.id), newDataQuery);
// const data = getInputValue(res?.settings?.dataResult, "OBJECT"); const data = getInputValue(item?.settings?.dataResult, "OBJECT");
// if (Object.keys(data).length > 0) {
// totals.value = data.Total; if (Object.keys(data).length > 0) {
// listArticlePaging.value = data?.Data || []; totals.value = data.Total;
// } listArticlePaging.value = data?.Data || [];
}
}; };
const handleNextPrev = (type: "+" | "-") => { const handleNextPrev = (type: "+" | "-") => {
@@ -107,28 +112,22 @@ const mapActivesToItems = (index: number) => {
</script> </script>
<template> <template>
<section> <section v-if="listArticleByCategory?.length > 0">
<div class="section-container" :class="[listArticleByCategory && listArticleByCategory?.length > 0 ? '' : 'noData']"> <div class="section-container">
<div class="section-layout" :style="designObject['div.section']"> <div class="section-layout" :style="designObject['div.section']">
<template v-if="listArticleByCategory?.length > 0"> <template v-for="(component, index) in listArticlePaging?.length > 0 ? listArticlePaging : listArticleByCategory" :key="index">
<template v-for="(component, index) in listArticlePaging?.length > 0 ? listArticlePaging : listArticleByCategory"> <DynamicComponent
<DynamicComponent :settings="{
:key="index" template: SETTING_OPTIONS.TEMPLATE,
v-if="!isEmpty(component)" layout: SETTING_OPTIONS.LAYOUT,
:settings="{ dataResult: { ...component },
template: SETTING_OPTIONS.TEMPLATE, label: mapActivesToItems(Number(index)),
layout: SETTING_OPTIONS.LAYOUT, }"
dataResult: { ...component }, :component="COMPONENT"
label: mapActivesToItems(Number(index)), />
}"
/>
</template>
</template>
<template v-else>
<div class="empty"><h6 class="px-2 text-center">Nội dung danh sách bài viết của danh mục sẽ đây</h6></div>
</template> </template>
<div class="button-page flex"> <div class="button-page flex">
<a class="btn-page prev-page" @click.stop="() => handleNextPrev('-')" v-if="page > 1"> <span class="btn-page prev-page" @click.stop="() => handleNextPrev('-')" v-if="page > 1">
<i class="el-icon"> <i class="el-icon">
<svg xmlns="http://www.w3.org/2000/svg" viewBox="0 0 1024 1024"> <svg xmlns="http://www.w3.org/2000/svg" viewBox="0 0 1024 1024">
<path <path
@@ -137,9 +136,9 @@ const mapActivesToItems = (index: number) => {
></path> ></path>
</svg> </svg>
</i> </i>
</a> </span>
<a v-if="listArticleByCategory?.length > 0" :class="['btn-page', page === index + 1 && 'active']" @click.stop="() => select(index + 1)" v-for="(_, index) in Math.ceil(totals / limit)">{{ index + 1 }}</a> <span :class="['btn-page', page === index + 1 && 'active']" @click.stop="() => select(index + 1)" v-for="(_, index) in Math.ceil(totals / limit)">{{ index + 1 }}</span>
<a class="btn-page next-page" @click.stop="() => handleNextPrev('+')" v-if="page < Math.ceil(totals / limit)"> <span class="btn-page next-page" @click.stop="() => handleNextPrev('+')" v-if="page < Math.ceil(totals / limit)">
<i class="el-icon"> <i class="el-icon">
<svg xmlns="http://www.w3.org/2000/svg" viewBox="0 0 1024 1024"> <svg xmlns="http://www.w3.org/2000/svg" viewBox="0 0 1024 1024">
<path <path
@@ -148,10 +147,11 @@ const mapActivesToItems = (index: number) => {
></path> ></path>
</svg> </svg>
</i> </i>
</a> </span>
</div> </div>
</div> </div>
</div> </div>
<div v-html="designObject.styleClasses" style="display: none" v-if="designObject.styles"></div>
</section> </section>
</template> </template>
@@ -161,35 +161,9 @@ const mapActivesToItems = (index: number) => {
display: flex; display: flex;
flex-direction: column; flex-direction: column;
/* gap: 10px; */ /* gap: 10px; */
overflow-x: scroll;
&.border-custom { &.border-custom {
border-color: #e5e5e5 !important; border-color: #e5e5e5 !important;
} }
&.borderLeft {
border-left: 1px solid;
}
&.borderRight {
border-right: 1px solid;
}
&.borderTop {
border-top: 1px solid;
}
&.borderBottom {
border-bottom: 1px solid;
}
}
.empty {
width: 100%;
height: 100%;
min-height: 50px;
background-color: #409eff;
display: flex;
white-space: normal;
justify-content: center;
align-items: center;
h6 {
color: #fff;
}
} }
.basic-article { .basic-article {
&.article { &.article {
@@ -198,9 +172,6 @@ const mapActivesToItems = (index: number) => {
pointer-events: none; pointer-events: none;
} }
} }
&.noData {
border-radius: 6px;
}
.flex { .flex {
display: flex; display: flex;
@@ -218,17 +189,21 @@ const mapActivesToItems = (index: number) => {
.btn-page { .btn-page {
width: 40px; width: 40px;
height: 40px; height: 40px;
padding: 9px 16px;
text-align: center; text-align: center;
line-height: 36px; line-height: 36px;
border: 1px solid #409eff; border-radius: 4px;
border-radius: 3px;
margin-left: 10px; margin-left: 10px;
display: flex; display: flex;
justify-content: center; justify-content: center;
align-items: center; align-items: center;
gap: 8px;
flex-shrink: 0;
background: #f2f2f2;
cursor: pointer; cursor: pointer;
color: #222222;
&.active { &.active {
background: #409eff; background: #ed1c24;
color: white; color: white;
} }
} }
+77 -62
View File
@@ -30,74 +30,74 @@ interface PageComponentSettings {
dataResult?: string; // Kết quả dữ liệu (Json) dataResult?: string; // Kết quả dữ liệu (Json)
} }
export type PageSection = { export type PageSection = {
id?: number; // Mã định danh id?: number; // Mã định danh
siteId?: number; // Mã hệ thống siteId?: number; // Mã hệ thống
pageId?: number; // Mã trang pageId?: number; // Mã trang
parentId?: number; // Mã vùng cha parentId?: number; // Mã vùng cha
title?: string; // Tiêu đề title?: string; // Tiêu đề
slug?: string; // (Anchor) slug?: string; // (Anchor)
code?: string; // Mã nhận diện code?: string; // Mã nhận diện
content?: string; // Nội dung content?: string; // Nội dung
keywords?: string; // Từ khóa keywords?: string; // Từ khóa
description?: string; // Mô tả description?: string; // Mô tả
type?: number; // Phân loại: PageSectionType type?: number; // Phân loại: PageSectionType
features?: string; // Đặc trưng: Featured (nổi bật) features?: string; // Đặc trưng: Featured (nổi bật)
taxonomy?: string; // Phân loại: Block | Module | Navigation taxonomy?: string; // Phân loại: Block | Module | Navigation
settings?: PageSectionSettings; // Thiết lập: PageSectionSettings (Json) settings?: PageSectionSettings; // Thiết lập: PageSectionSettings (Json)
isPublished?: boolean; // Đã xuất bản isPublished?: boolean; // Đã xuất bản
publishedBy?: number; // Xuất bản bởi publishedBy?: number; // Xuất bản bởi
publishedOn?: string; // Xuất bản vào lúc (string) publishedOn?: string; // Xuất bản vào lúc (string)
expiresOn?: string; // Hết hạn vào lúc (string) expiresOn?: string; // Hết hạn vào lúc (string)
order?: number; // Thứ tự sắp xếp order?: number; // Thứ tự sắp xếp
status?: number; // Trạng thái status?: number; // Trạng thái
} }
interface PageComponent extends Base { interface PageComponent extends Base {
id?: number; // Mã định danh id?: number; // Mã định danh
siteId?: number; // Mã hệ thống siteId?: number; // Mã hệ thống
pageId?: number; // Mã trang pageId?: number; // Mã trang
sectionId?: number; // Mã vùng sectionId?: number; // Mã vùng
title?: string; // Tiêu đề title?: string; // Tiêu đề
code?: string; // Mã nhận diện code?: string; // Mã nhận diện
content?: string; // Nội dung content?: string; // Nội dung
type?: number; // Phân loại: PageComponentType type?: number; // Phân loại: PageComponentType
features?: string; // Đặc trưng: Featured (nổi bật) features?: string; // Đặc trưng: Featured (nổi bật)
taxonomy?: string; // Phân loại taxonomy?: string; // Phân loại
settings?: PageComponentSettings; // Thiết lập: PageComponentSettings (Json) settings?: PageComponentSettings; // Thiết lập: PageComponentSettings (Json)
isPublished?: boolean; // Đã xuất bản isPublished?: boolean; // Đã xuất bản
publishedBy?: number; // Xuất bản bởi publishedBy?: number; // Xuất bản bởi
publishedOn?: string; // Xuất bản vào lúc (string) publishedOn?: string; // Xuất bản vào lúc (string)
expiresOn?: string; // Hết hạn vào lúc (string) expiresOn?: string; // Hết hạn vào lúc (string)
order?: number; // Thứ tự sắp xếp order?: number; // Thứ tự sắp xếp
status?: number; // Trạng thái status?: number; // Trạng thái
} }
interface Page extends Base { interface Page extends Base {
id?: number; // Mã định danh id?: number; // Mã định danh
siteId?: number; // Mã hệ thống siteId?: number; // Mã hệ thống
parentId?: number; // Mã trang cha parentId?: number; // Mã trang cha
title?: string; // Tiêu đề title?: string; // Tiêu đề
slug?: string; // Slug slug?: string; // Slug
code?: string; // Mã nhận diện code?: string; // Mã nhận diện
content?: string; // Nội dung content?: string; // Nội dung
favicon?: string; // Biểu tượng favicon?: string; // Biểu tượng
keywords?: string; // Từ khóa keywords?: string; // Từ khóa
thumbnail?: string; // Ảnh đại diện thumbnail?: string; // Ảnh đại diện
description?: string; // Mô tả description?: string; // Mô tả
type?: number; // Phân loại: PageType type?: number; // Phân loại: PageType
features?: string; // Đặc trưng: Featured (nổi bật) features?: string; // Đặc trưng: Featured (nổi bật)
taxonomy?: string; // Phân nhóm taxonomy?: string; // Phân nhóm
settings?: PageSettings; // Thiết lập: PageSettings (Json) settings?: PageSettings; // Thiết lập: PageSettings (Json)
isPublished?: boolean; // Đã xuất bản isPublished?: boolean; // Đã xuất bản
publishedBy?: number; // Đã xuất bản bởi publishedBy?: number; // Đã xuất bản bởi
publishedOn?: string; // Đã xuất bản vào lúc (string) publishedOn?: string; // Đã xuất bản vào lúc (string)
expiresOn?: string; // Đã hết hạn vào lúc (string) expiresOn?: string; // Đã hết hạn vào lúc (string)
order?: number; // Thứ tự sắp xếp order?: number; // Thứ tự sắp xếp
status?: number; // Trạng thái status?: number; // Trạng thái
components?: PageComponent[]; components?: PageComponent[];
sections?: PageSection[]; sections?: PageSection[];
} }
export const getDynamicPageByCode = async (event : any) => { export const getDynamicPageByCode = async (event: any) => {
try { try {
const { apiUrl } = useRuntimeConfig().public const { apiUrl } = useRuntimeConfig().public
const slug = event.context.params.slug; const slug = event.context.params.slug;
@@ -112,7 +112,7 @@ export const getDynamicPageByCode = async (event : any) => {
} }
} }
export const getDynamicPageById = async (event : any) => { export const getDynamicPageById = async (event: any) => {
try { try {
const { apiUrl } = useRuntimeConfig().public const { apiUrl } = useRuntimeConfig().public
const id = event.context.params.id; const id = event.context.params.id;
@@ -122,3 +122,18 @@ export const getDynamicPageById = async (event : any) => {
handleError(error); handleError(error);
} }
} }
export async function getOverviewPageComponentById(event: any) {
try {
const { apiUrl } = useRuntimeConfig().public
const { componentId, dataQuery } = getQuery(event)
return await $fetch(`${apiUrl}/cms/overview-page-component/${componentId}`, {
method: "POST",
headers: {
"Content-Type": "application/json",
},
body: dataQuery,
});
} catch (err) {
handleError(err);
}
}
+18
View File
@@ -60,6 +60,23 @@ export const useDynamicPageStore = defineStore("dynamicPageStore", () => {
} catch (error: any) {} } catch (error: any) {}
} }
async function getOverviewPageComponentById(componentId, dataQuery) {
try {
const { apiUrl } = useRuntimeConfig().public
const res = await $fetch(`${apiUrl}/cms/page-component/overview-page-component/${componentId}`, {
method: "POST",
headers: {
"Content-Type": "application/json",
},
body: JSON.stringify(dataQuery),
});
return res
} catch (err) {
throw err;
}
}
return { return {
currentPage, currentPage,
sectionPublished, sectionPublished,
@@ -69,6 +86,7 @@ export const useDynamicPageStore = defineStore("dynamicPageStore", () => {
setSectionPublished, setSectionPublished,
setComponentPublished, setComponentPublished,
setDataQuery, setDataQuery,
getOverviewPageComponentById
}; };
}); });