From a557255b4a64bad4fc9061816bb9614b004491f6 Mon Sep 17 00:00:00 2001 From: qsh <> Date: Fri, 31 May 2024 17:38:17 +0800 Subject: [PATCH 1/2] =?UTF-8?q?=E4=B8=8A=E4=BC=A0?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- .env.base | 2 +- .env.dev | 2 +- .env.front | 2 +- .env.pro | 2 +- .env.stage | 2 +- .env.static | 2 +- .env.test | 2 +- src/api/infra/file/index.ts | 45 +++++++++ src/api/mall/product/brand.ts | 10 +- src/api/mall/product/category.ts | 10 +- src/api/mall/product/index.js | 10 +- src/components/Editor/src/Editor.vue | 62 +++++++++++- src/components/Search/src/Search.vue | 10 +- src/components/UploadFile/src/UploadImgs.vue | 98 +++++++++++-------- src/components/UploadFile/src/useUpload.ts | 93 ++++++++++++++++++ src/views/Basic/Dept/DeptForm.vue | 2 +- src/views/Clue/Order/index.vue | 55 ++++++++--- src/views/Clue/Pool/index.vue | 65 +++++++++--- src/views/Clue/Set/Comp/GeneralSet.vue | 50 ++++++++++ src/views/Clue/Set/index.vue | 6 +- src/views/MiniMall/Inventory/index.vue | 7 +- src/views/MiniMall/MallSet/Comp/BrandSet.vue | 72 ++++++++------ .../MiniMall/MallSet/Comp/CategorySet.vue | 63 ++++++------ .../MiniMall/MallSet/Comp/DialogBrand.vue | 42 ++++---- .../MiniMall/MallSet/Comp/DialogCategory.vue | 42 ++++---- src/views/MiniMall/MallSet/index.vue | 25 ++--- src/views/MiniMall/Product/add.vue | 70 +++++++------ src/views/MiniMall/Product/index.vue | 26 ++++- src/views/MiniMall/Purchase/index.vue | 58 ++++++++--- 29 files changed, 675 insertions(+), 260 deletions(-) create mode 100644 src/api/infra/file/index.ts create mode 100644 src/components/UploadFile/src/useUpload.ts create mode 100644 src/views/Clue/Set/Comp/GeneralSet.vue diff --git a/.env.base b/.env.base index fec926e..2fbe392 100644 --- a/.env.base +++ b/.env.base @@ -7,7 +7,7 @@ VITE_DEV=true VITE_BASE_URL='http://118.31.23.45:48080' # 上传路径 -VITE_UPLOAD_URL='http://localhost:48080/admin-api/infra/file/upload' +VITE_UPLOAD_URL='http://118.31.23.45:48080/admin-api/system/file/upload' # 接口前缀 VITE_API_BASEPATH=/dev-api diff --git a/.env.dev b/.env.dev index 42a9402..d5db008 100644 --- a/.env.dev +++ b/.env.dev @@ -7,7 +7,7 @@ VITE_DEV=false VITE_BASE_URL='http://localhost:48080' # 上传路径 -VITE_UPLOAD_URL='http://localhost:48080/admin-api/infra/file/upload' +VITE_UPLOAD_URL='http://118.31.23.45:48080/admin-api/system/file/upload' # 接口前缀 VITE_API_BASEPATH=/dev-api diff --git a/.env.front b/.env.front index f31cf92..31379fb 100644 --- a/.env.front +++ b/.env.front @@ -7,7 +7,7 @@ VITE_DEV=true VITE_BASE_URL='http://118.31.23.45:48080' # 上传路径 -VITE_UPLOAD_URL='http://api-dashboard.yudao.iocoder.cn/admin-api/infra/file/upload' +VITE_UPLOAD_URL='http://118.31.23.45:48080/admin-api/system/file/upload' # 接口前缀 VITE_API_BASEPATH=/dev-api diff --git a/.env.pro b/.env.pro index 6c57331..e0b3180 100644 --- a/.env.pro +++ b/.env.pro @@ -7,7 +7,7 @@ VITE_DEV=false VITE_BASE_URL='http://localhost:48080' # 上传路径 -VITE_UPLOAD_URL='http://localhost:48080/admin-api/infra/file/upload' +VITE_UPLOAD_URL='http://118.31.23.45:48080/admin-api/system/file/upload' # 接口前缀 VITE_API_BASEPATH= diff --git a/.env.stage b/.env.stage index 634a27d..ae34e48 100644 --- a/.env.stage +++ b/.env.stage @@ -7,7 +7,7 @@ VITE_DEV=false VITE_BASE_URL='http://api-dashboard.yudao.iocoder.cn' # 上传路径 -VITE_UPLOAD_URL='http://api-dashboard.yudao.iocoder.cn/admin-api/infra/file/upload' +VITE_UPLOAD_URL='http://118.31.23.45:48080/admin-api/system/file/upload' # 接口前缀 VITE_API_BASEPATH= diff --git a/.env.static b/.env.static index a00ddf8..c0cc560 100644 --- a/.env.static +++ b/.env.static @@ -7,7 +7,7 @@ VITE_DEV=false VITE_BASE_URL='http://localhost:48080' # 上传路径 -VITE_UPLOAD_URL='http://localhost:48080/admin-api/infra/file/upload' +VITE_UPLOAD_URL='http://118.31.23.45:48080/admin-api/system/file/upload' # 接口前缀 VITE_API_BASEPATH= diff --git a/.env.test b/.env.test index 3e4b3e5..7af3d84 100644 --- a/.env.test +++ b/.env.test @@ -7,7 +7,7 @@ VITE_DEV=false VITE_BASE_URL='http://localhost:48080' # 上传路径 -VITE_UPLOAD_URL='http://localhost:48080/admin-api/infra/file/upload' +VITE_UPLOAD_URL='http://118.31.23.45:48080/admin-api/system/file/upload' # 接口前缀 VITE_API_BASEPATH= diff --git a/src/api/infra/file/index.ts b/src/api/infra/file/index.ts new file mode 100644 index 0000000..52a3723 --- /dev/null +++ b/src/api/infra/file/index.ts @@ -0,0 +1,45 @@ +import request from '@/config/axios' + +export interface FilePageReqVO extends PageParam { + path?: string + type?: string + createTime?: Date[] +} + +// 文件预签名地址 Response VO +export interface FilePresignedUrlRespVO { + // 文件配置编号 + configId: number + // 文件上传 URL + uploadUrl: string + // 文件 URL + url: string +} + +// 查询文件列表 +export const getFilePage = (params: FilePageReqVO) => { + return request.get({ url: '/infra/file/page', params }) +} + +// 删除文件 +export const deleteFile = (id: number) => { + return request.delete({ url: '/infra/file/delete?id=' + id }) +} + +// 获取文件预签名地址 +export const getFilePresignedUrl = (path: string) => { + return request.get({ + url: '/infra/file/presigned-url', + params: { path } + }) +} + +// 创建文件 +export const createFile = (data: any) => { + return request.post({ url: '/infra/file/create', data }) +} + +// 上传文件 +export const updateFile = (data: any) => { + return request.upload({ url: '/admin-api/system/file/upload', data }) +} diff --git a/src/api/mall/product/brand.ts b/src/api/mall/product/brand.ts index 94d5370..d4a58c1 100644 --- a/src/api/mall/product/brand.ts +++ b/src/api/mall/product/brand.ts @@ -32,27 +32,27 @@ export interface BrandVO { // 创建商品品牌 export const createBrand = (data: BrandVO) => { - return request.post({ url: '/product/brand/create', data }) + return request.post({ url: '/admin-api/crm/erp-product-brand/create', data }) } // 更新商品品牌 export const updateBrand = (data: BrandVO) => { - return request.put({ url: '/product/brand/update', data }) + return request.put({ url: '/admin-api/crm/erp-product-brand/update', data }) } // 删除商品品牌 export const deleteBrand = (id: number) => { - return request.delete({ url: `/product/brand/delete?id=${id}` }) + return request.delete({ url: `/admin-api/crm/erp-product-brand/delete?id=${id}` }) } // 获得商品品牌 export const getBrand = (id: number) => { - return request.get({ url: `/product/brand/get?id=${id}` }) + return request.get({ url: `/admin-api/crm/erp-product-brand/get?id=${id}` }) } // 获得商品品牌列表 export const getBrandParam = (params: PageParam) => { - return request.get({ url: '/product/brand/page', params }) + return request.get({ url: '/admin-api/crm/erp-product-brand/page', params }) } // 获得商品品牌精简信息列表 diff --git a/src/api/mall/product/category.ts b/src/api/mall/product/category.ts index 8158fc0..61a61fb 100644 --- a/src/api/mall/product/category.ts +++ b/src/api/mall/product/category.ts @@ -36,25 +36,25 @@ export interface CategoryVO { // 创建商品分类 export const createCategory = (data: CategoryVO) => { - return request.post({ url: '/product/category/create', data }) + return request.post({ url: '/admin-api/crm/erp-product-category/create', data }) } // 更新商品分类 export const updateCategory = (data: CategoryVO) => { - return request.put({ url: '/product/category/update', data }) + return request.put({ url: '/admin-api/crm/erp-product-category/update', data }) } // 删除商品分类 export const deleteCategory = (id: number) => { - return request.delete({ url: `/product/category/delete?id=${id}` }) + return request.delete({ url: `/admin-api/crm/erp-product-category/delete?id=${id}` }) } // 获得商品分类 export const getCategory = (id: number) => { - return request.get({ url: `/product/category/get?id=${id}` }) + return request.get({ url: `/admin-api/crm/erp-product-category/get?id=${id}` }) } // 获得商品分类列表 export const getCategoryList = (params: any) => { - return request.get({ url: '/product/category/list', params }) + return request.get({ url: '/admin-api/crm/erp-product-category/page', params }) } diff --git a/src/api/mall/product/index.js b/src/api/mall/product/index.js index 23f25a4..b4afa64 100644 --- a/src/api/mall/product/index.js +++ b/src/api/mall/product/index.js @@ -1,25 +1,25 @@ import request from '@/config/axios' // 查询列表 export const getProductPage = async (params) => { - return await request.get({ url: '/admin-api/crm/erp-product//page', params }) + return await request.get({ url: '/admin-api/crm/erp-product/page', params }) } // 查询详情 export const getProduct = async (id) => { - return await request.get({ url: '/admin-api/crm/erp-product//get?id=' + id }) + return await request.get({ url: '/admin-api/crm/erp-product/get?id=' + id }) } // 新增 export const createProduct = async (data) => { - return await request.post({ url: '/admin-api/crm/erp-product//create', data: data }) + return await request.post({ url: '/admin-api/crm/erp-product/create', data: data }) } // 修改 export const updateProduct = async (params) => { - return await request.put({ url: '/admin-api/crm/erp-product//update', data: params }) + return await request.put({ url: '/admin-api/crm/erp-product/update', data: params }) } // 删除 export const deleteProduct = async (id) => { - return await request.delete({ url: '/admin-api/crm/erp-product//delete?id=' + id }) + return await request.delete({ url: '/admin-api/crm/erp-product/delete?id=' + id }) } diff --git a/src/components/Editor/src/Editor.vue b/src/components/Editor/src/Editor.vue index b2efe7b..a75ef4a 100644 --- a/src/components/Editor/src/Editor.vue +++ b/src/components/Editor/src/Editor.vue @@ -6,7 +6,7 @@ import { propTypes } from '@/utils/propTypes' import { isNumber } from '@/utils/is' import { ElMessage } from 'element-plus' import { useLocaleStore } from '@/store/modules/locale' -import { getAccessToken, getTenantId } from '@/utils/auth' +import { getAccessToken, getTenantId, getAppId } from '@/utils/auth' type InsertFnType = (url: string, alt: string, href: string) => void @@ -103,7 +103,8 @@ const editorConfig = computed((): IEditorConfig => { headers: { Accept: '*', Authorization: 'Bearer ' + getAccessToken(), - 'tenant-id': getTenantId() + 'tenant-id': getTenantId(), + 'instance-id': getAppId() }, // 跨域是否传递 cookie ,默认为 false @@ -140,6 +141,63 @@ const editorConfig = computed((): IEditorConfig => { customInsert(res: any, insertFn: InsertFnType) { insertFn(res.data, 'image', res.data) } + }, + ['uploadVideo']: { + server: import.meta.env.VITE_UPLOAD_URL, + // 单个文件的最大体积限制,默认为 2M + maxFileSize: 100 * 1024 * 1024, + // 最多可上传几个文件,默认为 100 + maxNumberOfFiles: 10, + // 选择文件时的类型限制,默认为 ['image/*'] 。如不想限制,则设置为 [] + allowedFileTypes: ['video/*'], + + // 自定义上传参数,例如传递验证的 token 等。参数会被添加到 formData 中,一起上传到服务端。 + meta: { updateSupport: 0 }, + // 将 meta 拼接到 url 参数中,默认 false + metaWithUrl: true, + + // 自定义增加 http header + headers: { + Accept: '*', + Authorization: 'Bearer ' + getAccessToken(), + 'tenant-id': getTenantId(), + 'instance-id': getAppId() + }, + + // 跨域是否传递 cookie ,默认为 false + withCredentials: true, + + // 超时时间,默认为 10 秒 + timeout: 10 * 1000, // 5 秒 + + // form-data fieldName,后端接口参数名称,默认值wangeditor-uploaded-image + fieldName: 'file', + + // 上传之前触发 + onBeforeUpload(file: File) { + console.log(file) + return file + }, + // 上传进度的回调函数 + onProgress(progress: number) { + // progress 是 0-100 的数字 + console.log('progress', progress) + }, + onSuccess(file: File, res: any) { + console.log('onSuccess', file, res) + }, + onFailed(file: File, res: any) { + alert(res.message) + console.log('onFailed', file, res) + }, + onError(file: File, err: any, res: any) { + alert(err.message) + console.error('onError', file, err, res) + }, + // 自定义插入图片 + customInsert(res: any, insertFn: InsertFnType) { + insertFn(res.data, 'video', res.data) + } } }, uploadImgShowBase64: true diff --git a/src/components/Search/src/Search.vue b/src/components/Search/src/Search.vue index ccd3746..c41c66e 100644 --- a/src/components/Search/src/Search.vue +++ b/src/components/Search/src/Search.vue @@ -33,8 +33,8 @@ const props = defineProps({ .validate((v: string) => ['left', 'center', 'right'].includes(v)) .def('center'), showLabel: propTypes.bool.def(false), - showSearch: propTypes.bool.def(true), - showReset: propTypes.bool.def(true), + showSearch: propTypes.bool.def(false), + showReset: propTypes.bool.def(false), // 是否显示伸缩 expand: propTypes.bool.def(false), // 伸缩的界限字段 @@ -199,10 +199,10 @@ initSearch() - + - + + --> - + + diff --git a/src/views/Clue/Set/index.vue b/src/views/Clue/Set/index.vue index 8f5ee5b..f50f702 100644 --- a/src/views/Clue/Set/index.vue +++ b/src/views/Clue/Set/index.vue @@ -16,7 +16,10 @@ - + + + + @@ -30,6 +33,7 @@ import ClueSource from './Comp/ClueSource.vue' import ClueGet from './Comp/ClueGet.vue' import ClueSend from './Comp/ClueSend.vue' import MsgSend from './Comp/MsgSend.vue' +import GeneralSet from './Comp/GeneralSet.vue' const tabIndex = ref(0) diff --git a/src/views/MiniMall/Inventory/index.vue b/src/views/MiniMall/Inventory/index.vue index 88c5539..a0bfbe0 100644 --- a/src/views/MiniMall/Inventory/index.vue +++ b/src/views/MiniMall/Inventory/index.vue @@ -1,12 +1,12 @@ diff --git a/src/views/MiniMall/MallSet/Comp/DialogBrand.vue b/src/views/MiniMall/MallSet/Comp/DialogBrand.vue index bcb7703..19bfaee 100644 --- a/src/views/MiniMall/MallSet/Comp/DialogBrand.vue +++ b/src/views/MiniMall/MallSet/Comp/DialogBrand.vue @@ -1,5 +1,5 @@ diff --git a/src/views/MiniMall/Product/add.vue b/src/views/MiniMall/Product/add.vue index 5447064..a3b45b3 100644 --- a/src/views/MiniMall/Product/add.vue +++ b/src/views/MiniMall/Product/add.vue @@ -16,6 +16,7 @@ placeholder="请选择分类" filterable show-all-levels + style="width: 100%" /> @@ -44,15 +45,15 @@ - - + + - - + + @@ -60,7 +61,7 @@ 添加规格 - +
属性名: - + - + diff --git a/src/views/Basic/Library/Comp/DialogResource.vue b/src/views/Basic/Library/Comp/DialogResource.vue index aca33c4..36019a9 100644 --- a/src/views/Basic/Library/Comp/DialogResource.vue +++ b/src/views/Basic/Library/Comp/DialogResource.vue @@ -1,6 +1,6 @@ - diff --git a/src/views/Basic/Library/Comp/ImagePreview.vue b/src/views/Basic/Library/Comp/ImagePreview.vue index 1ca05fb..d184dd1 100644 --- a/src/views/Basic/Library/Comp/ImagePreview.vue +++ b/src/views/Basic/Library/Comp/ImagePreview.vue @@ -1,7 +1,6 @@ - - - {{ info.title }} - - - {{ info.fileName }} - - - {{ - item - }} - - - {{ info.remark }} - - +
+
+
标题:
+
{{ info.title }}
+
+
+
文件名称:
+
{{ + info.files + }}
+
+
+
标签:
+
+ + {{ getDictLabel('knowledge_tags', item) }} + +
+
+
+
备注:
+
{{ info.remark }}
+
+
- +
{{ imgIndex + 1 }} / {{ imgList.length }}
diff --git a/src/views/MiniMall/MallSet/Comp/CategorySet.vue b/src/views/MiniMall/MallSet/Comp/CategorySet.vue index a8f753d..6a312fc 100644 --- a/src/views/MiniMall/MallSet/Comp/CategorySet.vue +++ b/src/views/MiniMall/MallSet/Comp/CategorySet.vue @@ -16,10 +16,10 @@
- - + + - + @@ -33,16 +33,16 @@ diff --git a/src/views/MiniMall/MallSet/Comp/DialogCategory.vue b/src/views/MiniMall/MallSet/Comp/DialogCategory.vue index 0468e14..f2362f5 100644 --- a/src/views/MiniMall/MallSet/Comp/DialogCategory.vue +++ b/src/views/MiniMall/MallSet/Comp/DialogCategory.vue @@ -7,7 +7,7 @@ :rules="formRules" label-width="80px" > - + @@ -71,12 +71,14 @@ const open = async (type, info) => { if (type == 'update') { formData.value = await ProductCategoryApi.getCategory(info.id) } else { - formData.value.level = info.level + 1 formData.value.parentCategory = info.name + formData.value.parentId = info.id } } finally { formLoading.value = false } + } else { + formData.value.parentId = 0 } } defineExpose({ open }) // 提供 open 方法,用于打开弹窗 @@ -91,12 +93,12 @@ const submitForm = async () => { // 提交请求 formLoading.value = true try { - if (formType.value === 'create') { + if (formType.value === 'update') { + await ProductCategoryApi.updateCategory(formData.value) + message.success(t('common.updateSuccess')) + } else { await ProductCategoryApi.createCategory(formData.value) message.success(t('common.createSuccess')) - } else { - await ProductCategoryApi.updateCategory(data) - message.success(t('common.updateSuccess')) } dialogVisible.value = false // 发送操作成功的事件 diff --git a/src/views/MiniMall/MallSet/Comp/DialogSupplier.vue b/src/views/MiniMall/MallSet/Comp/DialogSupplier.vue index 423d1ae..0581691 100644 --- a/src/views/MiniMall/MallSet/Comp/DialogSupplier.vue +++ b/src/views/MiniMall/MallSet/Comp/DialogSupplier.vue @@ -7,11 +7,11 @@ :rules="formRules" label-width="80px" > - - + + - - + + diff --git a/src/views/MiniMall/Product/Comp/ProductAttributesAddForm.vue b/src/views/MiniMall/Product/Comp/ProductAttributesAddForm.vue index 9ab56aa..e596cd2 100644 --- a/src/views/MiniMall/Product/Comp/ProductAttributesAddForm.vue +++ b/src/views/MiniMall/Product/Comp/ProductAttributesAddForm.vue @@ -6,6 +6,7 @@ :model="formData" :rules="formRules" label-width="80px" + @submit.prevent > @@ -33,7 +34,7 @@ const formRules = reactive({ name: [{ required: true, message: '名称不能为空', trigger: 'blur' }] }) const formRef = ref() // 表单 Ref -const attributeList = ref([]) // 商品属性列表 +const attributeList = ref([]) // 商品属性列表 const props = defineProps({ propertyList: { type: Array, @@ -69,17 +70,13 @@ const submitForm = async () => { formLoading.value = true try { const data = formData.value as PropertyApi.PropertyVO - // 检查属性是否已存在,如果有则返回属性和其下属性值 - const res = await PropertyApi.getPropertyListAndValue({ name: data.name }) - if (res.length === 0) { - const propertyId = await PropertyApi.createProperty(data) - attributeList.value.push({ id: propertyId, ...formData.value, values: [] }) - } else { - if (res[0].values === null) { - res[0].values = [] - } - attributeList.value.push(res[0]) // 因为只用一个 - } + const propertyId = await PropertyApi.createProperty(data) + // 添加到属性列表 + attributeList.value.push({ + id: propertyId + '', + ...formData.value, + values: [] + }) message.success(t('common.createSuccess')) dialogVisible.value = false } finally { @@ -90,8 +87,7 @@ const submitForm = async () => { /** 重置表单 */ const resetForm = () => { formData.value = { - name: '', - remark: '' + name: '' } formRef.value?.resetFields() } diff --git a/src/views/MiniMall/Product/Comp/SkuList.vue b/src/views/MiniMall/Product/Comp/SkuList.vue deleted file mode 100644 index 527f658..0000000 --- a/src/views/MiniMall/Product/Comp/SkuList.vue +++ /dev/null @@ -1,317 +0,0 @@ - - diff --git a/src/views/MiniMall/Product/add.vue b/src/views/MiniMall/Product/add.vue index a3b45b3..10a16e6 100644 --- a/src/views/MiniMall/Product/add.vue +++ b/src/views/MiniMall/Product/add.vue @@ -1,5 +1,5 @@ + > + + diff --git a/src/views/MiniMall/Product/index.vue b/src/views/MiniMall/Product/index.vue index 739bb2c..a006c7a 100644 --- a/src/views/MiniMall/Product/index.vue +++ b/src/views/MiniMall/Product/index.vue @@ -20,9 +20,9 @@ > @@ -33,6 +33,7 @@ placeholder="请选择分类" clearable filterable + :props="{ label: 'name', value: 'id', checkStrictly: true }" show-all-levels @change="handleQuery" /> @@ -40,7 +41,7 @@ 搜索 重置 - + 新增 @@ -53,6 +54,16 @@
+ + + + @@ -105,6 +116,9 @@ import { dateFormatter } from '@/utils/formatTime' import { createImageViewer } from '@/components/ImageViewer' import * as ProductApi from '@/api/mall/product' +import * as BrandApi from '@/api/mall/product/brand' +import * as CategoryApi from '@/api/mall/product/category' +import { handleTree } from '@/utils/tree' const { currentRoute, push } = useRouter() const message = useMessage() // 消息弹窗 @@ -143,8 +157,18 @@ async function handleDelete(id) { async function getList() { loading.value = true try { - const data = await ProductApi.getProductPage(queryParams.value) - tableList.value = data.list + const params = { ...queryParams.value } + if (params.productCategory && params.productCategory.length) { + params.productCategory = params.productCategory.at(-1) + } + const data = await ProductApi.getProductPage(params) + tableList.value = data.list.map((prod) => ({ + ...prod, + properties: prod.productSpecList[0].properties.map((item) => ({ + propertyId: item.propertyId, + label: item.propertyName + })) + })) total.value = data.total } finally { loading.value = false @@ -163,6 +187,15 @@ function handleQuery() { getList() } +async function getOptions() { + BrandApi.getSimpleBrandList().then((data) => { + opts.value.brand = data || [] + }) + CategoryApi.getCategorySimpleList().then((data) => { + opts.value.productCategory = handleTree(data || []) + }) +} + /** 重置按钮操作 */ function resetQuery() { queryParams.value = { @@ -182,7 +215,7 @@ function resetQuery() { */ function openForm(id) { // 修改 - if (typeof id == 'number') { + if (id) { push({ path: '/miniMall/productEdit', query: { id } @@ -201,6 +234,10 @@ watch( ) handleQuery() + +onMounted(() => { + getOptions() +})