博客和组合商品接口对接
parent
2b0fff4cd7
commit
b0f6021915
|
|
@ -6,4 +6,6 @@ NODE_ENV='dev'
|
|||
VITE_APP_TITLE = 'shopxo'
|
||||
VITE_APP_PORT = 3000
|
||||
VITE_APP_BASE_API = '/dev-api'
|
||||
VITE_APP_BASE_API_URL = 'http://shopxo.com/admin.php/'
|
||||
VITE_APP_BASE_API_URL = 'http://shopxo.com/admin.php/'
|
||||
VITE_APP_BASE_API_PHP = '/dev-php'
|
||||
VITE_APP_BASE_API_PHP_URL = 'http://shopxo.com/api.php'
|
||||
|
|
@ -0,0 +1,20 @@
|
|||
import api_request from '@/utils/api-request';
|
||||
|
||||
class BlogAPI {
|
||||
/** 博客自动数据 */
|
||||
static getAutoList(data: any) {
|
||||
return api_request({
|
||||
url: `?s=plugins/index/pluginsname/binding/pluginscontrol/diybinding/pluginsaction/index.html`,
|
||||
method: 'post',
|
||||
data,
|
||||
});
|
||||
}
|
||||
}
|
||||
|
||||
export default BlogAPI;
|
||||
|
||||
// 分类树结构
|
||||
export interface Tree {
|
||||
/** 主键 */
|
||||
id: string;
|
||||
}
|
||||
|
|
@ -1,32 +1,17 @@
|
|||
import request from '@/utils/request';
|
||||
import api_request from '@/utils/api-request';
|
||||
|
||||
class ArticleAPI {
|
||||
/** 链接初始化接口 */
|
||||
static getInit() {
|
||||
return request({
|
||||
url: `diyapi/linkinit`,
|
||||
method: 'post',
|
||||
});
|
||||
}
|
||||
/** 文章指定数据 */
|
||||
static getAppointList(data: any) {
|
||||
return request({
|
||||
url: `diyapi/articleappointdata`,
|
||||
method: 'post',
|
||||
data,
|
||||
});
|
||||
}
|
||||
/** 文章自动数据 */
|
||||
class BlogAPI {
|
||||
/** 博客自动数据 */
|
||||
static getAutoList(data: any) {
|
||||
return request({
|
||||
url: `diyapi/articleautodata`,
|
||||
return api_request({
|
||||
url: `?s=plugins/index/pluginsname/blog/pluginscontrol/diyblog/pluginsaction/autobloglist`,
|
||||
method: 'post',
|
||||
data,
|
||||
});
|
||||
}
|
||||
}
|
||||
|
||||
export default ArticleAPI;
|
||||
export default BlogAPI;
|
||||
|
||||
// 分类树结构
|
||||
export interface Tree {
|
||||
|
|
|
|||
|
|
@ -16,7 +16,14 @@ class ShopAPI {
|
|||
data,
|
||||
});
|
||||
}
|
||||
|
||||
// 获取多商户的数据
|
||||
static getShopList(data: any) {
|
||||
return request({
|
||||
url: `plugins/index/pluginsname/shop/pluginscontrol/diyshop/pluginsaction/index`,
|
||||
method: 'post',
|
||||
data,
|
||||
});
|
||||
}
|
||||
}
|
||||
|
||||
export default ShopAPI;
|
||||
|
|
|
|||
|
|
@ -1,4 +1,5 @@
|
|||
import request from '@/utils/request';
|
||||
import api_request from '@/utils/api-request';
|
||||
|
||||
class UrlValueAPI {
|
||||
/** 获取商品列表 */
|
||||
|
|
@ -58,6 +59,23 @@ class UrlValueAPI {
|
|||
data,
|
||||
});
|
||||
}
|
||||
|
||||
/** 博客指定数据 */
|
||||
static getblogList(data: any) {
|
||||
return api_request({
|
||||
url: `?s=plugins/index/pluginsname/blog/pluginscontrol/diyblog/pluginsaction/index.html`,
|
||||
method: 'post',
|
||||
data,
|
||||
});
|
||||
}
|
||||
/** 组合搭配指定数据 */
|
||||
static getBindingList(data: any) {
|
||||
return api_request({
|
||||
url: `?s=plugins/index/pluginsname/binding/pluginscontrol/diybinding/pluginsaction/autobindinglist.html`,
|
||||
method: 'post',
|
||||
data,
|
||||
});
|
||||
}
|
||||
}
|
||||
|
||||
export default UrlValueAPI;
|
||||
|
|
|
|||
|
|
@ -1,14 +1,15 @@
|
|||
<template>
|
||||
<el-form-item label="读取方式">
|
||||
<el-radio-group v-model="form.data_type">
|
||||
<el-radio v-for="item in option_list" :key="item.value" :value="item.value">{{ item.name }}</el-radio>
|
||||
</el-radio-group>
|
||||
</el-form-item>
|
||||
<div v-show="form.data_type === '0'" class="nav-list">
|
||||
<drag-group :list="drag_list" :img-params="img_params" @onsort="data_list_sort" @remove="data_list_remove" @replace="data_list_replace"></drag-group>
|
||||
<el-button class="mt-20 w" @click="add">+添加</el-button>
|
||||
</div>
|
||||
<!-- 商品 -->
|
||||
<template v-if="type === 'goods'">
|
||||
<el-form-item label="读取方式">
|
||||
<el-radio-group v-model="form.data_type">
|
||||
<el-radio v-for="item in baseList.product_list" :key="item.value" :value="item.value">{{ item.name }}</el-radio>
|
||||
</el-radio-group>
|
||||
</el-form-item>
|
||||
<div v-show="form.data_type === '0'" class="nav-list">
|
||||
<drag-group :list="drag_list" img-params="images" @onsort="data_list_sort" @remove="data_list_remove" @replace="data_list_replace"></drag-group>
|
||||
<el-button class="mt-20 w" @click="add">+添加</el-button>
|
||||
</div>
|
||||
<div v-show="form.data_type === '1'" class="w h">
|
||||
<el-form-item label="关键字">
|
||||
<el-input v-model="keywords" placeholder="请输入商品关键字" clearable @blur="keyword_blur"></el-input>
|
||||
|
|
@ -38,22 +39,14 @@
|
|||
</el-form-item>
|
||||
</div>
|
||||
</template>
|
||||
<template v-else-if="type === 'article' || type === 'blog'">
|
||||
<el-form-item label="读取方式">
|
||||
<el-radio-group v-model="form.data_type">
|
||||
<el-radio v-for="item in baseList.data_type_list" :key="item.value" :value="item.value">{{ item.name }}</el-radio>
|
||||
</el-radio-group>
|
||||
</el-form-item>
|
||||
<div v-show="form.data_type === '0'" class="nav-list">
|
||||
<drag-group :list="drag_list" img-params="cover" @onsort="data_list_sort" @remove="data_list_remove" @replace="data_list_replace"></drag-group>
|
||||
<el-button class="mtb-20 w" @click="add">+添加</el-button>
|
||||
</div>
|
||||
<!-- 文章 博客 博客选项卡-->
|
||||
<template v-else-if="type === 'article' || ['blog', 'blog-tabs'].includes(type)">
|
||||
<div v-show="form.data_type === '1'" class="w h">
|
||||
<el-form-item label="关键字">
|
||||
<el-input v-model="keywords" placeholder="请输入文章关键字" clearable @blur="keyword_blur"></el-input>
|
||||
</el-form-item>
|
||||
<el-form-item :label="`${ type === 'article' ? '文章' : '博客' }分类`">
|
||||
<el-select v-model="form.category_ids" multiple collapse-tags filterable placeholder="请选择文章分类">
|
||||
<el-select v-model="form.category_ids" multiple collapse-tags filterable :placeholder="`请选择${ type === 'article' ? '文章' : '博客' }分类`">
|
||||
<template v-if="type === 'article'">
|
||||
<el-option v-for="item in common_store.common.article_category" :key="item.id" :label="item.name" :value="item.id" />
|
||||
</template>
|
||||
|
|
@ -83,18 +76,46 @@
|
|||
<el-form-item label="封面图片">
|
||||
<el-switch v-model="form.is_cover" active-value="1" inactive-value="0" />
|
||||
</el-form-item>
|
||||
<template v-if="['blog', 'blog-tabs'].includes(type)">
|
||||
<el-form-item label="是否推荐">
|
||||
<el-switch v-model="form.is_recommended" active-value="1" inactive-value="0" />
|
||||
</el-form-item>
|
||||
<el-form-item label="是否热门">
|
||||
<el-switch v-model="form.is_hot" active-value="1" inactive-value="0" />
|
||||
</el-form-item>
|
||||
</template>
|
||||
</div>
|
||||
</template>
|
||||
<!-- 组合搭配 -->
|
||||
<template v-else-if="type == 'binding'">
|
||||
<div v-show="form.data_type === '1'" class="w h">
|
||||
<el-form-item label="关键字">
|
||||
<el-input v-model="keywords" placeholder="请输入组合搭配关键字" clearable @blur="keyword_blur"></el-input>
|
||||
</el-form-item>
|
||||
<el-form-item label="类型">
|
||||
<el-select v-model="form.binding_type" multiple collapse-tags filterable placeholder="请选择类型">
|
||||
<el-option v-for="item in common_store.common.brand_list" :key="item.id" :label="item.name" :value="item.id" />
|
||||
</el-select>
|
||||
</el-form-item>
|
||||
<el-form-item label="显示数量">
|
||||
<el-input-number v-model="form.number" :min="1" :max="50" type="number" placeholder="请输入显示数量" value-on-clear="min" class="w number-show" controls-position="right"></el-input-number>
|
||||
</el-form-item>
|
||||
<el-form-item label="排序类型">
|
||||
<el-radio-group v-model="form.order_by_type">
|
||||
<el-radio v-for="item in common_store.common.brand_order_by_type_list" :key="item.index" :value="item.index">{{ item.name }}</el-radio>
|
||||
</el-radio-group>
|
||||
</el-form-item>
|
||||
<el-form-item label="排序规则">
|
||||
<el-radio-group v-model="form.order_by_rule">
|
||||
<el-radio v-for="item in common_store.common.data_order_by_rule_list" :key="item.index" :value="item.index">{{ item.name }}</el-radio>
|
||||
</el-radio-group>
|
||||
</el-form-item>
|
||||
<el-form-item label="是否推荐">
|
||||
<el-switch v-model="form.is_recommended" active-value="1" inactive-value="0" />
|
||||
</el-form-item>
|
||||
</div>
|
||||
</template>
|
||||
<template v-else>
|
||||
<el-form-item label="读取方式">
|
||||
<el-radio-group v-model="form.data_type">
|
||||
<el-radio v-for="item in baseList.brand_data_type_list" :key="item.value" :value="item.value">{{ item.name }}</el-radio>
|
||||
</el-radio-group>
|
||||
</el-form-item>
|
||||
<div v-show="form.data_type === '0'" class="nav-list">
|
||||
<drag-group :list="drag_list" img-params="logo" @onsort="data_list_sort" @remove="data_list_remove" @replace="data_list_replace"></drag-group>
|
||||
<el-button class="mt-20 w" @click="add">+添加</el-button>
|
||||
</div>
|
||||
<div v-show="form.data_type === '1'" class="w h">
|
||||
<el-form-item label="关键字">
|
||||
<el-input v-model="keywords" placeholder="请输入品牌关键字" clearable @blur="keyword_blur"></el-input>
|
||||
|
|
@ -146,8 +167,28 @@
|
|||
const keywords = ref(props.value.keywords);
|
||||
const form = ref(props.value);
|
||||
const drag_list = ref(props.list);
|
||||
type option = {
|
||||
name: string,
|
||||
value: string,
|
||||
}
|
||||
const option_list = ref<option[]>([]);
|
||||
const img_params = ref('logo');
|
||||
// 更新数据,避免子组件数据不刷新
|
||||
watchEffect(() => {
|
||||
if (props.type === 'goods') {
|
||||
option_list.value = props.baseList.product_list;
|
||||
img_params.value = 'images';
|
||||
} else if (props.type === 'article' || ['blog', 'blog-tabs'].includes(props.type)) {
|
||||
option_list.value = props.baseList.data_type_list;
|
||||
img_params.value = 'cover';
|
||||
} else if (props.type === 'binding') {
|
||||
option_list.value = props.baseList.data_type_list;
|
||||
img_params.value = 'images';
|
||||
} else {
|
||||
option_list.value = props.baseList.brand_data_type_list;
|
||||
img_params.value = 'logo';
|
||||
}
|
||||
// 关键字信息
|
||||
keywords.value = props.value.keywords;
|
||||
form.value = props.value;
|
||||
// 历史数据转成数字类型
|
||||
|
|
|
|||
|
|
@ -0,0 +1,171 @@
|
|||
<template>
|
||||
<!-- 商品分类 -->
|
||||
<div class="container">
|
||||
<div class="flex-row jc-e gap-20 mb-20">
|
||||
<el-select v-model="binding_type" class="search-w" placeholder="请选择组合搭配类型" filterable clearable @change="handle_search">
|
||||
<el-option v-for="item in article_category_list" :key="item.id" :label="item.name" :value="item.id" />
|
||||
</el-select>
|
||||
<el-input v-model="search_value" placeholder="请输入搜索内容" class="search-w" @change="handle_search">
|
||||
<template #suffix>
|
||||
<icon name="search" size="16" color="9" class="c-pointer" @click="handle_search"></icon>
|
||||
</template>
|
||||
</el-input>
|
||||
</div>
|
||||
<div class="content">
|
||||
<el-table v-loading="loading" :data="tableData" class="w" :header-cell-style="{ background: '#f7f7f7' }" row-key="id" height="438" fixed @row-click="row_click" @select="handle_select" @select-all="handle_select">
|
||||
<el-table-column v-if="multiple" type="selection" width="60" />
|
||||
<el-table-column v-else label="#" width="60" type="">
|
||||
<template #default="scope">
|
||||
<el-radio v-model="template_selection" :label="scope.$index + ''"> </el-radio>
|
||||
</template>
|
||||
</el-table-column>
|
||||
<el-table-column prop="id" label="ID" width="80" type="" />
|
||||
<el-table-column prop="images" label="封面">
|
||||
<template #default="scope">
|
||||
<div class="flex-row align-c gap-10">
|
||||
<image-empty v-if="scope.row.images" v-model="scope.row.images" class="img"></image-empty>
|
||||
<!-- <div class="flex-1">{{ scope.row.title }}</div> -->
|
||||
</div>
|
||||
</template>
|
||||
</el-table-column>
|
||||
<el-table-column prop="title" label="标题"></el-table-column>
|
||||
<el-table-column prop="describe" label="描述"></el-table-column>
|
||||
<el-table-column prop="type_name" label="类型"></el-table-column>
|
||||
<template #empty>
|
||||
<no-data></no-data>
|
||||
</template>
|
||||
</el-table>
|
||||
<div class="mt-10 flex-row jc-e">
|
||||
<el-pagination :current-page="page" background :page-size="page_size" :pager-count="5" layout="prev, pager, next" :total="data_total" @current-change="get_list" />
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
</template>
|
||||
<script lang="ts" setup>
|
||||
import UrlValueAPI from '@/api/url-value';
|
||||
import { commonStore } from '@/store';
|
||||
const common_store = commonStore();
|
||||
const props = defineProps({
|
||||
// 重置
|
||||
reset: {
|
||||
type: Boolean,
|
||||
default: () => false,
|
||||
},
|
||||
multiple: {
|
||||
type: Boolean,
|
||||
default: () => false,
|
||||
},
|
||||
// 判断是否返回链接地址
|
||||
selectIsUrl: {
|
||||
type: Boolean,
|
||||
default: false,
|
||||
},
|
||||
});
|
||||
watch(
|
||||
() => props.reset,
|
||||
(val) => {
|
||||
if (val) {
|
||||
init();
|
||||
}
|
||||
}
|
||||
);
|
||||
onMounted(() => {
|
||||
init();
|
||||
});
|
||||
const modelValue = defineModel({ type: Object, default: {} });
|
||||
const tableData = ref<pageLinkList[]>([]);
|
||||
const search_value = ref('');
|
||||
const loading = ref(false);
|
||||
const init = () => {
|
||||
template_selection.value = '';
|
||||
binding_type.value = '';
|
||||
search_value.value = '';
|
||||
article_category_list.value = common_store.common.article_category;
|
||||
get_list(1);
|
||||
};
|
||||
const handle_search = () => {
|
||||
get_list(1);
|
||||
};
|
||||
const binding_type = ref('');
|
||||
interface articleCategory {
|
||||
id: string;
|
||||
name: string;
|
||||
url: string;
|
||||
}
|
||||
const article_category_list = ref<articleCategory[]>([]);
|
||||
const template_selection = ref('');
|
||||
//#region 分页 -----------------------------------------------start
|
||||
// 当前页
|
||||
const page = ref(1);
|
||||
// 每页数量
|
||||
const page_size = ref(30);
|
||||
// 总数量
|
||||
const data_total = ref(0);
|
||||
// 查询文件
|
||||
const get_list = (new_page: number) => {
|
||||
let new_data = {
|
||||
page: new_page,
|
||||
keywords: search_value.value,
|
||||
type: binding_type.value,
|
||||
page_size: page_size.value,
|
||||
};
|
||||
loading.value = true;
|
||||
UrlValueAPI.getBindingList(new_data).then((res: any) => {
|
||||
tableData.value = res.data;
|
||||
data_total.value = res.data.length - 1;
|
||||
page.value = new_page;
|
||||
setTimeout(() => {
|
||||
loading.value = false;
|
||||
}, 500);
|
||||
});
|
||||
};
|
||||
//#region 分页 -----------------------------------------------end
|
||||
const row_click = (row: any) => {
|
||||
if (!props.multiple) {
|
||||
const new_table_data = JSON.parse(JSON.stringify(tableData.value));
|
||||
template_selection.value = new_table_data.findIndex((item: pageLinkList) => item.id == row.id).toString();
|
||||
if (props.selectIsUrl) {
|
||||
const page = '/pages/plugins/binding/detail/detail?id=' + row.id;
|
||||
const new_row = {
|
||||
id: row.id,
|
||||
name: row.name || row.title || page,
|
||||
page: page,
|
||||
};
|
||||
modelValue.value = [new_row];
|
||||
} else {
|
||||
modelValue.value = [row];
|
||||
}
|
||||
}
|
||||
};
|
||||
const handle_select = (selection: any) => {
|
||||
if (props.selectIsUrl) {
|
||||
// 遍历数组selection
|
||||
const new_selection = selection.map((item: any) => {
|
||||
const page = '/pages/plugins/binding/detail/detail?id=' + item.id;
|
||||
return {
|
||||
id: item.id,
|
||||
name: item.name || item.title || page,
|
||||
page: page,
|
||||
};
|
||||
});
|
||||
modelValue.value = new_selection;
|
||||
} else {
|
||||
modelValue.value = selection;
|
||||
}
|
||||
};
|
||||
</script>
|
||||
<style lang="scss" scoped>
|
||||
.container {
|
||||
.search-w {
|
||||
width: 22.5rem;
|
||||
}
|
||||
.content {
|
||||
:deep(.el-table__inner-wrapper:before) {
|
||||
background-color: transparent;
|
||||
}
|
||||
.img {
|
||||
width: 3.6rem;
|
||||
}
|
||||
}
|
||||
}
|
||||
</style>
|
||||
|
|
@ -2,7 +2,7 @@
|
|||
<!-- 商品分类 -->
|
||||
<div class="container">
|
||||
<div class="flex-row jc-e gap-20 mb-20">
|
||||
<el-select v-model="category_ids" class="search-w" placeholder="请选择" filterable clearable @change="handle_search">
|
||||
<el-select v-model="category_ids" class="search-w" placeholder="请选择博客分类" filterable clearable @change="handle_search">
|
||||
<el-option v-for="item in article_category_list" :key="item.id" :label="item.name" :value="item.id" />
|
||||
</el-select>
|
||||
<el-input v-model="search_value" placeholder="请输入搜索内容" class="search-w" @change="handle_search">
|
||||
|
|
@ -95,7 +95,7 @@ const template_selection = ref('');
|
|||
// 当前页
|
||||
const page = ref(1);
|
||||
// 每页数量
|
||||
const page_size = ref(30);
|
||||
const page_size = ref(10);
|
||||
// 总数量
|
||||
const data_total = ref(0);
|
||||
// 查询文件
|
||||
|
|
@ -107,7 +107,7 @@ const get_list = (new_page: number) => {
|
|||
page_size: page_size.value,
|
||||
};
|
||||
loading.value = true;
|
||||
UrlValueAPI.getArticleList(new_data).then((res: any) => {
|
||||
UrlValueAPI.getblogList(new_data).then((res: any) => {
|
||||
tableData.value = res.data.data_list;
|
||||
data_total.value = res.data.data_total;
|
||||
page.value = res.data.page;
|
||||
|
|
@ -122,7 +122,7 @@ const row_click = (row: any) => {
|
|||
const new_table_data = JSON.parse(JSON.stringify(tableData.value));
|
||||
template_selection.value = new_table_data.findIndex((item: pageLinkList) => item.id == row.id).toString();
|
||||
if (props.selectIsUrl) {
|
||||
const page = '/pages/article-detail/article-detail?id=' + row.id;
|
||||
const page = '/pages/plugins/blog/detail/detail?id=' + row.id;
|
||||
const new_row = {
|
||||
id: row.id,
|
||||
name: row.name || row.title || page,
|
||||
|
|
@ -138,7 +138,7 @@ const handle_select = (selection: any) => {
|
|||
if (props.selectIsUrl) {
|
||||
// 遍历数组selection
|
||||
const new_selection = selection.map((item: any) => {
|
||||
const page = '/pages/article-detail/article-detail?id=' + item.id;
|
||||
const page = '/pages/plugins/blog/detail/detail?id=' + item.id;
|
||||
return {
|
||||
id: item.id,
|
||||
name: item.name || item.title || page,
|
||||
|
|
|
|||
|
|
@ -76,8 +76,8 @@ const init = () => {
|
|||
template_selection.value = '';
|
||||
type.value = '';
|
||||
search_value.value = '';
|
||||
if (!is_obj_empty(common_store.common.plugins) && !is_obj_empty(common_store.common.plugins.coupon) && common_store.common.plugins.coupon.coupon_type_list.length > 0) {
|
||||
coupon_type_list.value = common_store.common.plugins.coupon.coupon_type_list;
|
||||
if (!is_obj_empty(common_store.common.plugins) && !is_obj_empty(common_store.common.plugins.coupon) && common_store.common.plugins.coupon.type_list.length > 0) {
|
||||
coupon_type_list.value = common_store.common.plugins.coupon.type_list;
|
||||
}
|
||||
get_list(1);
|
||||
};
|
||||
|
|
|
|||
|
|
@ -54,6 +54,10 @@
|
|||
<template v-else-if="link_select == 'coupon'">
|
||||
<link-coupon v-model="link_value" :multiple="multiple" :reset="reset_compontent"></link-coupon>
|
||||
</template>
|
||||
<!-- 组合搭配 -->
|
||||
<template v-else-if="link_select == 'binding'">
|
||||
<link-binding v-model="link_value" :multiple="multiple" :reset="reset_compontent"></link-binding>
|
||||
</template>
|
||||
</div>
|
||||
</div>
|
||||
<template #footer>
|
||||
|
|
|
|||
|
|
@ -24,14 +24,14 @@
|
|||
<div class="flex-row align-c jc-sb">
|
||||
<div class="flex-col gap-6">
|
||||
<div class="flex-row align-c">
|
||||
<span :style="trends_config('price_symbol', 'data')">{{ match_item.price_symbol }}</span>
|
||||
<span :style="trends_config('price', 'data')">{{ match_item.price }}</span>
|
||||
<span :style="trends_config('price_symbol', 'data')">¥</span>
|
||||
<span :style="trends_config('price', 'data')">{{ match_item.estimate_price }}</span>
|
||||
</div>
|
||||
<div class="flex-row align-c gap-3">
|
||||
<img-or-icon-or-text :value="props.value" type="data_discounts" />
|
||||
<div>
|
||||
<span :style="trends_config('save_price_symbol', 'data')">{{ match_item.price_symbol }}</span>
|
||||
<span :style="trends_config('save_price', 'data')">{{ match_item.price }}</span>
|
||||
<span :style="trends_config('save_price_symbol', 'data')">¥</span>
|
||||
<span :style="trends_config('save_price', 'data')">{{ match_item.estimate_discount_price || 0 }}</span>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
|
|
@ -49,14 +49,14 @@
|
|||
<div class="flex-row align-c jc-sb">
|
||||
<div class="flex-col gap-6">
|
||||
<div class="flex-row align-c">
|
||||
<span :style="trends_config('price_symbol', 'data')">{{ match_item.price_symbol }}</span>
|
||||
<span :style="trends_config('price', 'data')">{{ match_item.price }}</span>
|
||||
<span :style="trends_config('price_symbol', 'data')">¥</span>
|
||||
<span :style="trends_config('price', 'data')">{{ match_item.estimate_price }}</span>
|
||||
</div>
|
||||
<div class="flex-row align-c gap-3">
|
||||
<img-or-icon-or-text :value="props.value" type="data_discounts" />
|
||||
<div>
|
||||
<span :style="trends_config('save_price_symbol', 'data')">{{ match_item.price_symbol }}</span>
|
||||
<span :style="trends_config('save_price', 'data')">{{ match_item.price }}</span>
|
||||
<span :style="trends_config('save_price_symbol', 'data')">¥</span>
|
||||
<span :style="trends_config('save_price', 'data')">{{ match_item.estimate_discount_price || 0 }}</span>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
|
|
@ -70,7 +70,7 @@
|
|||
<div :style="goods_content_img_style">
|
||||
<div :class="outer_class" :style="onter_style">
|
||||
<template v-if="!['3'].includes(theme)">
|
||||
<div v-for="(item, index) in match_item.good_list" :key="index" class="re oh" :class="layout_type" :style="layout_style">
|
||||
<div v-for="(item, index) in match_item.goods" :key="index" class="re oh" :class="layout_type" :style="layout_style">
|
||||
<div :class="['oh w h', ['0' , '2'].includes(theme) ? 'flex-row' : 'flex-col' ]" :style="layout_img_style">
|
||||
<template v-if="!isEmpty(item) && is_show('goods_img')">
|
||||
<div class="oh re" :class="`flex-img${theme}`">
|
||||
|
|
@ -83,14 +83,14 @@
|
|||
{{ item.title }}
|
||||
</div>
|
||||
<div v-if="is_show('price')" class="flex-row align-c text-line-1">
|
||||
<span :style="trends_config('price_symbol', 'goods')">{{ match_item.price_symbol }}</span>
|
||||
<span :style="trends_config('price', 'goods')">{{ match_item.price }}</span>
|
||||
<span :style="trends_config('price_symbol', 'goods')">{{ item.show_price_symbol }}</span>
|
||||
<span :style="trends_config('price', 'goods')">{{ item.price }}</span>
|
||||
</div>
|
||||
<div v-if="is_show('save_price')" class="flex-row align-c gap-3">
|
||||
<img-or-icon-or-text :value="props.value" type="goods_discounts" />
|
||||
<div class="flex-1 text-line-1">
|
||||
<span :style="trends_config('save_price_symbol', 'goods')">{{ match_item.price_symbol }}</span>
|
||||
<span :style="trends_config('save_price', 'goods')">{{ match_item.price }}</span>
|
||||
<span :style="trends_config('save_price_symbol', 'goods')">{{ item.show_price_symbol }}</span>
|
||||
<span :style="trends_config('save_price', 'goods')">{{ item.discount_price || 0 }}</span>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
|
|
@ -100,7 +100,7 @@
|
|||
</template>
|
||||
<template v-else>
|
||||
<swiper :key="carouselKey" class="w flex" direction="horizontal" :loop="true" :autoplay="autoplay" :slides-per-view="form.carousel_col" :slides-per-group="slides_per_group" :allow-touch-move="false" :space-between="goods_content_outer_spacing" :pause-on-mouse-enter="true" :modules="modules">
|
||||
<swiper-slide v-for="(item, index) in match_item.good_list" :key="index">
|
||||
<swiper-slide v-for="(item, index) in match_item.goods" :key="index">
|
||||
<div :class="layout_type" :style="layout_style">
|
||||
<div :class="['oh w h', ['0', '2'].includes(theme) ? 'flex-row' : 'flex-col' ]" :style="layout_img_style">
|
||||
<template v-if="!isEmpty(item) && is_show('goods_img')">
|
||||
|
|
@ -114,14 +114,14 @@
|
|||
{{ item.title }}
|
||||
</div>
|
||||
<div v-if="is_show('price')" class="flex-row align-c text-line-1">
|
||||
<span :style="trends_config('price_symbol', 'goods')">{{ match_item.price_symbol }}</span>
|
||||
<span :style="trends_config('price', 'goods')">{{ match_item.price }}</span>
|
||||
<span :style="trends_config('price_symbol', 'goods')">{{ item.show_price_symbol }}</span>
|
||||
<span :style="trends_config('price', 'goods')">{{ item.price }}</span>
|
||||
</div>
|
||||
<div v-if="is_show('save_price')" class="flex-row align-c gap-3">
|
||||
<img-or-icon-or-text :value="props.value" type="goods_discounts" />
|
||||
<div class="flex-1 text-line-1">
|
||||
<span :style="trends_config('save_price_symbol', 'goods')">{{ match_item.price_symbol }}</span>
|
||||
<span :style="trends_config('save_price', 'goods')">{{ match_item.price }}</span>
|
||||
<span :style="trends_config('save_price_symbol', 'goods')">{{ item.show_price_symbol }}</span>
|
||||
<span :style="trends_config('save_price', 'goods')">{{ item.discount_price || 0 }}</span>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
|
|
@ -137,7 +137,7 @@
|
|||
<!-- 底部展开收起按钮区域 -->
|
||||
<div :style="bottom_button_style">
|
||||
<div class="flex-row align-c jc-sb" :style="bottom_button_img_style">
|
||||
<span :style="trends_config('button', 'bottom')">{{ form.is_default_show_goods == '1' ? '收起' : '展开'}}组合商品</span>
|
||||
<span :style="trends_config('button', 'bottom')">{{ form.is_default_show_goods == '1' ? '收起' : '展开'}}{{ match_item.type_name }}商品</span>
|
||||
<icon :name="form.is_default_show_goods == '1' ? 'arrow-top' : 'arrow-bottom'" :color="new_style.bottom_button_icon_color" :size="new_style.bottom_button_icon_size + ''"></icon>
|
||||
</div>
|
||||
</div>
|
||||
|
|
@ -153,7 +153,7 @@
|
|||
import { common_styles_computer, common_img_computer, get_math, gradient_handle, margin_computer, border_computer, box_shadow_computer, radius_computer, background_computer, padding_computer } from '@/utils';
|
||||
import { old_margin } from "@/utils/common";
|
||||
import { isEmpty, cloneDeep } from 'lodash';
|
||||
import ShopAPI from '@/api/shop';
|
||||
import BindingAPI from '@/api/binding';
|
||||
import { Swiper, SwiperSlide } from 'swiper/vue';
|
||||
import { Autoplay } from 'swiper/modules';
|
||||
const modules = [Autoplay];
|
||||
|
|
@ -177,57 +177,51 @@ const new_style = computed(() => props.value?.style || {});
|
|||
//#region 列表数据
|
||||
type goods_list = {
|
||||
title: string,
|
||||
min_original_price: string,
|
||||
discount_price: string,
|
||||
show_original_price_symbol: string,
|
||||
min_price: string,
|
||||
price: string,
|
||||
show_price_symbol: string,
|
||||
sales_count: string,
|
||||
images: string,
|
||||
}
|
||||
type data_list = {
|
||||
title: string,
|
||||
price_symbol: string;
|
||||
price: string,
|
||||
save_price_symbol: string,
|
||||
save_pice: string,
|
||||
estimate_price: string,
|
||||
estimate_discount_price: string,
|
||||
images: string,
|
||||
type_name: string;
|
||||
new_cover: string[],
|
||||
good_list: goods_list[]
|
||||
goods: goods_list[]
|
||||
}
|
||||
const default_list = {
|
||||
title: '测试组合搭配标题',
|
||||
price_symbol: '¥',
|
||||
price: '8970.00-9200.00',
|
||||
save_price_symbol: '¥',
|
||||
save_pice: '8970.00-9200.00',
|
||||
estimate_price: '8970.00-9200.00',
|
||||
estimate_discount_price: '8970.00-9200.00',
|
||||
type_name: '组合',
|
||||
images: '',
|
||||
new_cover: [],
|
||||
good_list: [
|
||||
goods: [
|
||||
{
|
||||
title: '测试商品标题',
|
||||
min_original_price: '41.2',
|
||||
discount_price: '41.2',
|
||||
show_original_price_symbol: '¥',
|
||||
min_price: '51',
|
||||
price: '51',
|
||||
show_price_symbol: '¥',
|
||||
sales_count: '1000',
|
||||
images: '',
|
||||
},
|
||||
{
|
||||
title: '测试商品标题',
|
||||
min_original_price: '41.2',
|
||||
discount_price: '41.2',
|
||||
show_original_price_symbol: '¥',
|
||||
min_price: '51',
|
||||
price: '51',
|
||||
show_price_symbol: '¥',
|
||||
sales_count: '1000',
|
||||
images: '',
|
||||
},
|
||||
{
|
||||
title: '测试商品标题',
|
||||
min_original_price: '41.2',
|
||||
discount_price: '41.2',
|
||||
show_original_price_symbol: '¥',
|
||||
min_price: '51',
|
||||
price: '51',
|
||||
show_price_symbol: '¥',
|
||||
sales_count: '1000',
|
||||
images: '',
|
||||
}
|
||||
]
|
||||
|
|
@ -250,30 +244,30 @@ onMounted(() => {
|
|||
}
|
||||
});
|
||||
|
||||
const get_products = () => {
|
||||
const { category_ids, brand_ids, number, order_by_type, order_by_rule, keywords } = form.value;
|
||||
const get_binding = () => {
|
||||
const { keywords, binding_type, number, order_by_type, order_by_rule, is_home_show } = form.value;
|
||||
const params = {
|
||||
goods_keywords: keywords,
|
||||
goods_category_ids: category_ids,
|
||||
goods_brand_ids: brand_ids,
|
||||
goods_order_by_type: order_by_type,
|
||||
goods_order_by_rule: order_by_rule,
|
||||
goods_number: number,
|
||||
binding_keywords: keywords,
|
||||
binding_type: binding_type,
|
||||
binding_order_by_type: order_by_type,
|
||||
binding_order_by_rule: order_by_rule,
|
||||
binding_number: number,
|
||||
binding_is_home_show: is_home_show,
|
||||
};
|
||||
list.value = Array(4).fill(default_list);
|
||||
// 获取商品列表
|
||||
// ShopAPI.getShopLists(params).then((res: any) => {
|
||||
// if (!isEmpty(res.data)) {
|
||||
// list.value = res.data;
|
||||
// } else {
|
||||
// list.value = Array(4).fill(default_list);
|
||||
// }
|
||||
// });
|
||||
//获取商品列表
|
||||
BindingAPI.getAutoList(params).then((res: any) => {
|
||||
if (!isEmpty(res.data.data_list)) {
|
||||
list.value = res.data.data_list;
|
||||
} else {
|
||||
list.value = Array(4).fill(default_list);
|
||||
}
|
||||
});
|
||||
};
|
||||
// 取出监听的数据
|
||||
const watch_data = computed(() => {
|
||||
const { category_ids, brand_ids, number, order_by_type, order_by_rule, data_type, data_list, keywords } = form.value;
|
||||
return { category_ids: category_ids, brand_ids: brand_ids, number: number, order_by_type: order_by_type, order_by_rule: order_by_rule, data_type: data_type, data_list: data_list, keyword: keywords };
|
||||
const { keywords, binding_type, number, order_by_type, order_by_rule, is_home_show, data_type, data_list } = form.value;
|
||||
return { keywords, binding_type, number, order_by_type, order_by_rule, is_home_show, data_type, data_list };
|
||||
})
|
||||
// 初始化的时候不执行, 监听数据变化
|
||||
watch(() => watch_data.value, (val, oldVal) => {
|
||||
|
|
@ -290,7 +284,7 @@ watch(() => watch_data.value, (val, oldVal) => {
|
|||
list.value = Array(4).fill(default_list);
|
||||
}
|
||||
} else {
|
||||
get_products();
|
||||
get_binding();
|
||||
}
|
||||
}
|
||||
}, { deep: true });
|
||||
|
|
|
|||
|
|
@ -56,7 +56,7 @@
|
|||
</el-tabs>
|
||||
</card-container>
|
||||
</el-form>
|
||||
<url-value-dialog v-model:dialog-visible="url_value_dialog_visible" :type="['realstore']" :multiple="url_value_multiple_bool" @update:model-value="url_value_dialog_call_back"></url-value-dialog>
|
||||
<url-value-dialog v-model:dialog-visible="url_value_dialog_visible" :type="['binding']" :multiple="url_value_multiple_bool" @update:model-value="url_value_dialog_call_back"></url-value-dialog>
|
||||
</div>
|
||||
</template>
|
||||
<script setup lang="ts">
|
||||
|
|
|
|||
|
|
@ -157,7 +157,7 @@ const new_content = computed(() => props.value?.content || {});
|
|||
const new_style = computed(() => props.value?.style || {});
|
||||
// 获取自动数据
|
||||
const get_auto_data_list = async () => {
|
||||
const { category_ids, number, order_by_type, order_by_rule, is_cover, keywords } = new_content.value;
|
||||
const { category_ids, number, order_by_type, order_by_rule, is_cover, keywords, is_recommended, is_hot } = new_content.value;
|
||||
const new_data = {
|
||||
blog_keywords: keywords,
|
||||
blog_category_ids: category_ids.join(','),
|
||||
|
|
@ -165,6 +165,8 @@ const get_auto_data_list = async () => {
|
|||
blog_order_by_rule: order_by_rule,
|
||||
blog_number: number,
|
||||
blog_is_cover: is_cover,
|
||||
blog_is_recommended: is_recommended,
|
||||
blog_is_hot: is_hot,
|
||||
};
|
||||
const res = await blogAPI.getAutoList(new_data);
|
||||
new_content.value.data_auto_list = [];
|
||||
|
|
@ -207,8 +209,8 @@ onMounted(() => {
|
|||
});
|
||||
// 监听new_content指定的数据变化
|
||||
const data_list_computer = computed(() => {
|
||||
const { data_type, category_ids, number, order_by_type, order_by_rule, is_cover, data_list, keywords } = new_content.value;
|
||||
return { data_type, category_ids, number, order_by_type, order_by_rule, is_cover, data_list, keywords };
|
||||
const { data_type, category_ids, number, order_by_type, order_by_rule, is_cover, data_list, keywords, is_recommended, is_hot } = new_content.value;
|
||||
return { data_type, category_ids, number, order_by_type, order_by_rule, is_cover, data_list, keywords, is_recommended, is_hot };
|
||||
});
|
||||
// 监听new_content指定的数据的变化,来获取最新数据
|
||||
watch(
|
||||
|
|
|
|||
|
|
@ -32,7 +32,7 @@
|
|||
<template v-else>
|
||||
<el-form-item label="类型">
|
||||
<el-select v-model="form.type" multiple collapse-tags filterable placeholder="请选择优惠券类型">
|
||||
<el-option v-for="item in base_list.coupon_type_list" :key="item.value" :label="item.name" :value="item.value" />
|
||||
<el-option v-for="item in base_list.type_list" :key="item.value" :label="item.name" :value="item.value" />
|
||||
</el-select>
|
||||
</el-form-item>
|
||||
<el-form-item label="展示数量">
|
||||
|
|
@ -89,7 +89,7 @@ const base_list = reactive({
|
|||
name: `风格${index + 1}`,
|
||||
url: `${new_url.value}theme-${index + 1}.png`,
|
||||
})),
|
||||
coupon_type_list: [] as select_2[],
|
||||
type_list: [] as select_2[],
|
||||
});
|
||||
onMounted(async () => {
|
||||
// 获取图片地址
|
||||
|
|
@ -100,8 +100,8 @@ onMounted(async () => {
|
|||
});
|
||||
nextTick(() => {
|
||||
// 定时获取common_store.common.article_category的数据,直到拿到值或者关闭页面为止
|
||||
if (!is_obj_empty(common_store.common.plugins) && !is_obj_empty(common_store.common.plugins.coupon) && common_store.common.plugins.coupon.coupon_type_list.length > 0) {
|
||||
base_list.coupon_type_list = common_store.common.plugins.coupon.coupon_type_list;
|
||||
if (!is_obj_empty(common_store.common.plugins) && !is_obj_empty(common_store.common.plugins.coupon) && common_store.common.plugins.coupon.type_list.length > 0) {
|
||||
base_list.type_list = common_store.common.plugins.coupon.type_list;
|
||||
}
|
||||
});
|
||||
});
|
||||
|
|
|
|||
|
|
@ -16,7 +16,9 @@
|
|||
<div :style="topic_style" class="pl-6 pr-6 radius-sm">{{ form.title }}</div>
|
||||
</template>
|
||||
<el-carousel :key="carouselKey" class="flex-1" indicator-position="none" :interval="interval_time" arrow="never" :direction="direction_type" :autoplay="true">
|
||||
<el-carousel-item v-for="(item, index) in notice_list" :key="index" class="text-line-1" :style="`${news_style} color: ${new_style.news_color}`">{{ item.notice_title }}</el-carousel-item>
|
||||
<el-carousel-item v-for="(item, index) in notice_list" :key="index" class="flex-row align-c">
|
||||
<div class="text-line-1" :style="`${news_style} color: ${new_style.news_color}`">{{ item.notice_title }}</div>
|
||||
</el-carousel-item>
|
||||
</el-carousel>
|
||||
<div v-if="form.is_right_button == '1'" :style="`color: ${new_style.right_button_color}; font-size: ${ new_style.right_button_size }px`">{{ form.right_title }}<icon name="arrow-right" :color="new_style.right_button_color || '#999'"></icon></div>
|
||||
</div>
|
||||
|
|
|
|||
|
|
@ -25,7 +25,7 @@
|
|||
<upload v-model="form.img_src" v-model:icon-value="form.icon_class" is-icon :limit="1" size="50"></upload>
|
||||
</el-form-item>
|
||||
<el-form-item v-if="is_text" label="标题文字">
|
||||
<el-input v-model="form.title" placeholder="请输入标题" maxlength="4" show-word-limit clearable></el-input>
|
||||
<el-input v-model="form.title" placeholder="请输入标题" maxlength="30" clearable></el-input>
|
||||
</el-form-item>
|
||||
<template v-if="!is_card">
|
||||
<el-form-item label="滚动方式">
|
||||
|
|
@ -61,7 +61,7 @@
|
|||
<template #default="scoped">
|
||||
<div class="flex-col align-c jc-s gap-20 flex-1">
|
||||
<el-form-item label="标题" class="w mb-0" label-width="40">
|
||||
<el-input v-model="scoped.row.notice_title" placeholder="请输入标题" maxlength="20" show-word-limit clearable></el-input>
|
||||
<el-input v-model="scoped.row.notice_title" placeholder="请输入标题" maxlength="100" clearable></el-input>
|
||||
</el-form-item>
|
||||
<el-form-item label="链接" class="w mb-0" label-width="40">
|
||||
<url-value v-model="scoped.row.notice_link"></url-value>
|
||||
|
|
|
|||
|
|
@ -171,13 +171,13 @@ const get_products = () => {
|
|||
};
|
||||
list.value = Array(4).fill(default_list);
|
||||
// 获取商品列表
|
||||
// ShopAPI.getShopLists(params).then((res: any) => {
|
||||
// if (!isEmpty(res.data)) {
|
||||
// list.value = res.data;
|
||||
// } else {
|
||||
// list.value = Array(4).fill(default_list);
|
||||
// }
|
||||
// });
|
||||
ShopAPI.getShopList(params).then((res: any) => {
|
||||
if (!isEmpty(res.data)) {
|
||||
list.value = res.data;
|
||||
} else {
|
||||
list.value = Array(4).fill(default_list);
|
||||
}
|
||||
});
|
||||
};
|
||||
// 取出监听的数据
|
||||
const watch_data = computed(() => {
|
||||
|
|
|
|||
|
|
@ -58,7 +58,15 @@ interface defaultRealstore {
|
|||
carousel_col: number;
|
||||
goods_save_price: string;
|
||||
goods_save_price_row: string;
|
||||
data_type: string;
|
||||
data_list: string[];
|
||||
data_auto_list: string[],
|
||||
keywords: string,
|
||||
binding_type: string[],
|
||||
number: number,
|
||||
order_by_type: string,
|
||||
order_by_rule: string,
|
||||
is_home_show: string,
|
||||
is_goods_show: string[];
|
||||
is_default_show_goods: string;
|
||||
is_details_show: string;
|
||||
|
|
@ -169,7 +177,15 @@ const defaultRealstore: defaultRealstore = {
|
|||
carousel_col: 1,
|
||||
goods_save_price: '1',
|
||||
goods_save_price_row: '1',
|
||||
data_type: '0',
|
||||
data_list: [],
|
||||
data_auto_list: [],
|
||||
keywords: '',
|
||||
binding_type: [],
|
||||
number: 4,
|
||||
order_by_type: '',
|
||||
order_by_rule: '',
|
||||
is_home_show: '',
|
||||
is_goods_show: ['title', 'goods_img', 'price', 'save_price'],
|
||||
is_default_show_goods: '1',
|
||||
is_details_show: '1',
|
||||
|
|
|
|||
|
|
@ -27,6 +27,8 @@ interface DefaultBlogList {
|
|||
field_show: string[];
|
||||
field_desc_row: string,
|
||||
is_cover: string;
|
||||
is_recommended: string;
|
||||
is_hot: string;
|
||||
seckill_subscript_show: string;
|
||||
subscript_type: string;
|
||||
subscript_img_src: uploadList[];
|
||||
|
|
@ -101,6 +103,8 @@ const defaultBlogList: DefaultBlogList = {
|
|||
field_show: ['0', '1', '3'],
|
||||
field_desc_row: '1',
|
||||
is_cover: defaultSetting.is_cover,
|
||||
is_recommended: '0',
|
||||
is_hot: '0',
|
||||
// 角标配置
|
||||
seckill_subscript_show: '0',
|
||||
subscript_type: 'text',
|
||||
|
|
|
|||
|
|
@ -0,0 +1,114 @@
|
|||
import axios, { InternalAxiosRequestConfig, AxiosResponse } from 'axios';
|
||||
import { ElMessage, ElMessageBox, type MessageHandler } from 'element-plus';
|
||||
import { get_cookie } from './index';
|
||||
|
||||
// 提示拦截
|
||||
|
||||
let messageInstance: MessageHandler;
|
||||
const message_error = (info: string) => {
|
||||
if (messageInstance) {
|
||||
messageInstance.close();
|
||||
}
|
||||
messageInstance = ElMessage.error({
|
||||
type: 'error',
|
||||
message: info,
|
||||
duration: 30000,
|
||||
showClose: true,
|
||||
});
|
||||
};
|
||||
|
||||
// 创建一个状态变量来跟踪是否已经弹出了退出登录的弹窗
|
||||
const isLogoutModalShown = ref(true);
|
||||
|
||||
// 用于存储每个请求的CancelToken
|
||||
const pendingRequests = new Map();
|
||||
// 不需要认证的接口
|
||||
const release_url = ['diyapi/attachmentupload'];
|
||||
// 创建 axios 实例
|
||||
const index = window.location.href.lastIndexOf('?s=');
|
||||
const new_data = window.location.href.substring(0, index);
|
||||
const new_index = new_data.lastIndexOf('/');
|
||||
const pro_url = window.location.href.substring(0, new_index);
|
||||
const service = axios.create({
|
||||
baseURL: import.meta.env.VITE_APP_BASE_API_PHP == '/dev-php' ? import.meta.env.VITE_APP_BASE_API_PHP : pro_url + '/api.php',
|
||||
timeout: 60000,
|
||||
headers: { 'Content-Type': 'application/json;charset=utf-8', 'X-Requested-With': 'XMLHttpRequest' },
|
||||
});
|
||||
/** @ts-ignore */
|
||||
// 请求拦截器
|
||||
service.interceptors.request.use(
|
||||
async (config: InternalAxiosRequestConfig) => {
|
||||
// 如果是本地则使用静态tonken如果是线上则使用cookie的token
|
||||
const cookie = get_cookie('admin_info') || '';
|
||||
const symbol = config.url?.includes('?') ? '&' : '?';
|
||||
if (import.meta.env.VITE_APP_BASE_API_PHP == '/dev-php') {
|
||||
let temp_data = await import(import.meta.env.VITE_APP_BASE_API_PHP == '/dev-php' ? '../../temp.d' : '../../temp_pro.d');
|
||||
config.url = config.url + symbol + 'token=' + temp_data.default.temp_token;
|
||||
} else {
|
||||
if (cookie && cookie !== null && cookie !== 'null') {
|
||||
config.url = config.url + '&token=' + (JSON.parse(cookie) !== 'null' ? JSON.parse(cookie)?.token : '');
|
||||
}
|
||||
}
|
||||
// 判断是否是包含不需要认证的接口
|
||||
const release_list = release_url.filter(item => config.url?.includes(item));
|
||||
if (release_list.length === 0) {
|
||||
// 检查是否有相同请求正在进行,如果有则取消, 防止重复请求导致返回数据有误
|
||||
if (pendingRequests.has(config.url)) {
|
||||
const cancelToken = pendingRequests.get(config.url);
|
||||
cancelToken.cancel('canceled');
|
||||
pendingRequests.delete(config.url);
|
||||
}
|
||||
// 创建一个新的 CancelToken
|
||||
const source = axios.CancelToken.source();
|
||||
config.cancelToken = source.token;
|
||||
pendingRequests.set(config.url, source);
|
||||
}
|
||||
return config;
|
||||
},
|
||||
(error: any) => {
|
||||
return Promise.reject(error);
|
||||
}
|
||||
);
|
||||
// 响应拦截器
|
||||
service.interceptors.response.use(
|
||||
(response: AxiosResponse) => {
|
||||
// 请求完成后,从pendingRequests中移除
|
||||
pendingRequests.delete(response.config.url);
|
||||
|
||||
const { code, msg, message, data } = response.data;
|
||||
if (code == 0) {
|
||||
return response.data;
|
||||
} else if (code == -400) {
|
||||
if (isLogoutModalShown.value) {
|
||||
isLogoutModalShown.value = false;
|
||||
ElMessageBox.alert(msg, '温馨提示', {
|
||||
confirmButtonText: '确定',
|
||||
showClose: false,
|
||||
type: 'warning',
|
||||
}).then(() => {
|
||||
localStorage.clear(); // @vueuse/core 自动导入
|
||||
window.location.href = data.logout;
|
||||
});
|
||||
}
|
||||
} else {
|
||||
message_error(msg || message || '系统出错');
|
||||
return Promise.reject('Error');
|
||||
// return Promise.reject(new Error(msg || 'Error'));
|
||||
}
|
||||
},
|
||||
(error: any) => {
|
||||
if (error.response && error.response.data) {
|
||||
const { msg, message } = error.response.data;
|
||||
message_error(msg || message || '系统出错');
|
||||
} else if (error.message == 'canceled') {
|
||||
console.log('请求已取消');
|
||||
} else {
|
||||
message_error(error.message);
|
||||
}
|
||||
|
||||
return Promise.reject(error.message);
|
||||
}
|
||||
);
|
||||
|
||||
// 导出 axios 实例
|
||||
export default service;
|
||||
|
|
@ -527,19 +527,6 @@ onMounted(async () => {
|
|||
const interval = setInterval(() => {
|
||||
// 获取分类
|
||||
if (common_store.common.module_list.length > 0) {
|
||||
common_store.common.module_list.forEach((item) => {
|
||||
if (item.key == 'plugins') {
|
||||
const data = [
|
||||
{ key: "blog", name: "博客" },
|
||||
{ key: "blog-tabs", name: "博客选项卡" },
|
||||
{ key: "binding", name: "组合搭配" },
|
||||
{ key: "realstore", name: "多门店" },
|
||||
{ key: "shop", name: "多商户" },
|
||||
{ key: "salerecords", name: "销售记录" },
|
||||
]
|
||||
item.data = item.data.concat(data);
|
||||
}
|
||||
});
|
||||
components.value = common_store.common.module_list;
|
||||
clearInterval(interval);
|
||||
}
|
||||
|
|
|
|||
|
|
@ -39,6 +39,12 @@ export default defineConfig(({ mode }: ConfigEnv): UserConfig => {
|
|||
changeOrigin: true,
|
||||
rewrite: (path) => path.replace(new RegExp('^' + env.VITE_APP_BASE_API), ''), // 替换 /dev-api 为 target 接口地址
|
||||
},
|
||||
// 反向代理解决跨域
|
||||
[env.VITE_APP_BASE_API_PHP]: {
|
||||
target: env.VITE_APP_BASE_API_PHP_URL, // 接口地址
|
||||
changeOrigin: true,
|
||||
rewrite: (path) => path.replace(new RegExp('^' + env.VITE_APP_BASE_API_PHP), ''), // 替换 /dev-api 为 target 接口地址
|
||||
},
|
||||
},
|
||||
},
|
||||
plugins: [
|
||||
|
|
|
|||
Loading…
Reference in New Issue