java-mall-admin/src/views/product/productList/index.vue
2025-06-28 18:56:10 +08:00

570 lines
16 KiB
Vue

<template>
<div class="department-management-container">
<vab-query-form>
<vab-query-form-left-panel :span="4">
<el-button type="primary" @click="showImport">
{{ __('批量导入') }}
</el-button>
<el-button
v-show="selectRows.length > 0"
icon="el-icon-check"
type="primary"
@click="expPrint()"
>
{{ __('导出打印') }}
</el-button>
<el-button
v-show="selectRows.length > 0"
icon="el-icon-top"
type="primary"
@click="review(1001)"
>
{{ __('上架') }}
</el-button>
<el-button
v-show="selectRows.length > 0"
icon="el-icon-bottom"
type="primary"
@click="review(1002)"
>
{{ __('下架') }}
</el-button>
</vab-query-form-left-panel>
<vab-query-form-right-panel :span="20">
<el-form :inline="true" :model="queryForm" @submit.native.prevent>
<el-form-item prop="product_state_id">
<el-radio-group v-model="queryForm.product_state_id" @change="queryData">
<el-radio-button v-for="item in stateOptions" :key="item.value" :label="item.value" >{{item.label}}</el-radio-button>
</el-radio-group>
</el-form-item>
<el-form-item v-if="configs.config.supplier_market_enable && 1 == configs.store_type" prop="product_src">
<el-radio-group v-model="queryForm.product_src" @change="queryData">
<el-radio-button v-for="item in stateSrc" :key="item.value" :label="item.value" >{{item.label}}</el-radio-button>
</el-radio-group>
</el-form-item>
<el-form-item>
<el-input
v-model.trim="queryForm.product_name"
clearable
:placeholder="__('请输入商品名称')"
style="width: 150px;"
/>
</el-form-item>
<el-form-item>
<el-input
v-model.trim="queryForm.product_id"
clearable
:placeholder="__('SPU编号')"
style="width: 120px;"
/>
</el-form-item>
<el-form-item>
<el-input
v-model.trim="queryForm.product_number"
clearable
:placeholder="__('商品货号')"
style="width: 120px;"
/>
</el-form-item>
<el-form-item>
<tree-select
ref="treeSelect"
:checked-keys="defaultCheckedKeys"
clearable
:data="productDataList"
:default-props="defaultProps"
:height="300"
:node-key="nodeKey"
size="small"
style="width: 120px"
:width="220"
@change="change"
/>
</el-form-item>
<el-form-item>
<el-button icon="el-icon-search" type="primary" @click="queryData">
{{ __('查询') }}
</el-button>
</el-form-item>
</el-form>
</vab-query-form-right-panel>
</vab-query-form>
<el-table
ref="table"
v-loading="listLoading"
border
:data="list"
:height="tableConfig.height"
@selection-change="setSelectRows"
>
<el-table-column
align="center"
fixed
show-overflow-tooltip
type="selection"
/>
<el-table-column align="center"
fixed="left" :label="__('操作')" width="185">
<template #default="{ row }">
<el-button type="text" @click="handleAdd(row)">
{{ __('编辑') }}
</el-button>
<el-button
v-if="row.product_state_id === 1002"
type="text"
@click="reviewOne(row, 1001)"
>
{{ __('上架') }}
</el-button>
<el-button
v-if="row.product_state_id === 1001"
type="text"
@click="reviewOne(row, 1002)"
>
{{ __('下架') }}
</el-button>
<el-button type="text" @click="handleEdit(row)">
{{ __('SKU') }}
</el-button>
<el-button type="text" @click="handleDelete(row)">
{{ __('删除') }}
</el-button>
</template>
</el-table-column>
<el-table-column
align="center"
fixed="left"
:label="__('产品SPU')"
prop="product_id"
show-overflow-tooltip
/>
<el-table-column
align="center"
fixed="left"
:label="__('主图')"
prop="product_image"
show-overflow-tooltip
width="80"
>
<template slot-scope="scope">
<el-image
v-if="scope.row.product_image"
:preview-src-list="[scope.row.product_image]"
:src="scope.row.product_image"
style="width: 35px; height: 35px"
/>
</template>
</el-table-column>
<el-table-column
align="center"
:label="__('产品名称')"
show-overflow-tooltip
width="260px"
>
<template #default="{ row }">
<el-link @click="showPreview(row)">
{{ row.product_name }}
</el-link>
</template>
</el-table-column>
<el-table-column
v-if="configs.config.supplier_market_enable && 1 == configs.store_type"
align="center"
:label="__('供应价格')"
prop="product_cost_price"
show-overflow-tooltip
/>
<el-table-column
align="center"
:label="__('市场价')"
prop="product_market_price"
show-overflow-tooltip
/>
<el-table-column
align="center"
:label="__('商品单价')"
prop="product_unit_price"
show-overflow-tooltip
/>
<el-table-column
align="center"
:formatter="formatId"
:label="__('商品审核')"
prop="product_verify_id"
show-overflow-tooltip
/>
<el-table-column
align="center"
:label="__('商品状态')"
prop="product_state_id"
show-overflow-tooltip
width="100"
>
<template slot-scope="scope">
<el-button
v-if="scope.row.product_state_id === 1002"
type="info"
size="mini"
plain
@click="changeState(scope.row.product_id, 1001)"
>
{{ __('仓库中') }}
</el-button>
<el-button
v-if="scope.row.product_state_id === 1001"
type="success"
size="mini"
plain
@click="changeState(scope.row.product_id, 1002)"
>
{{ __('销售中') }}
</el-button>
<span v-if="scope.row.product_state_id === 1000">
{{ __('违规禁售') }}
</span>
<span v-if="scope.row.product_state_id === 1003">
未分配商品
</span>
</template>
</el-table-column>
<el-table-column
align="center"
:label="__('分销商品编号')"
prop="product_src_id"
show-overflow-tooltip
width="120"
/>
<el-table-column
align="center"
:label="__('商品货号')"
prop="product_number"
show-overflow-tooltip
width="100"
/>
<el-table-column
align="center"
:formatter="formatTime"
:label="__('上架时间')"
prop="product_sale_time"
show-overflow-tooltip
width="180"
/>
</el-table>
<el-pagination
background
:current-page="queryForm.pageNum"
:layout="layout"
:page-size="queryForm.pageSize"
:total="total"
@current-change="handleCurrentChange"
@size-change="handleSizeChange"
/>
<edit ref="edit" @fetch-data="fetchData" />
<add ref="add" @fetch-data="fetchData" />
<excelExe-import ref="excelExeImport" @fetch-data="fetchData" />
<el-dialog
:append-to-body="true"
custom-class="center-dialog"
height="50%"
title="商品预览"
top="0vh"
:visible.sync="dialogVisible"
width="90%"
>
<iframe
frameborder="0"
height="700px"
:src="pc_url"
width="100%"
></iframe>
</el-dialog>
</div>
</template>
<script>
import { doDelete, editState, getList, exportFile } from '@/api/product/base'
import { translateTitle as __ } from '@/utils/i18n'
import { renderTime } from '@/utils/date'
import Edit from './components/productListEdit'
import Add from './components/addProductEdit'
import { getToken } from '@/utils/token'
import excelExeImport from './components/ExcelImport'
import {mapGetters} from "vuex";
import TreeSelect from '@/components/treeSelect'
import { getTree } from '@/api/base/product/category'
export default {
name: 'ProductList',
components: { Edit, Add, excelExeImport,TreeSelect },
beforeRouteEnter(to, form, next) {
next((vm) => vm.queryData())
},
data() {
return {
tableConfig: {
height: window.innerHeight - 220 - 90,
},
dialogVisible: false,
pc_url: '',
params: {
authorization: '',
},
list: [],
listLoading: true,
layout: 'total, sizes, prev, pager, next, jumper',
total: 0,
selectRows: '',
queryForm: {
pageNum: 1,
pageSize: 20,
kind_id: '1201,1202,1203', //实物及虚拟
product_state_id: null,
product_src: false,
},
verifyOptions: [
{
value: null,
label: this.__('全部'),
},
{
value: 3002,
label: this.__('待审核'),
},
{
value: 3000,
label: this.__('拒绝'),
},
{
value: 3001,
label: this.__('通过'),
},
],
stateOptions: [
{
value: null,
label: this.__('全部'),
},
{
// 1001-正常;1002-下架仓库中;1000-违规禁售
value: 1001,
label: this.__('销售中'),
},
{
value: 1002,
label: this.__('仓库中'),
},
{
value: 1000,
label: this.__('违规禁售'),
},
{
value:1003,
label:"未分配商品"
}
],
stateSrc: [
{
value: false,
label: this.__('全部'),
},
{
value: true,
label: this.__('供应商产品'),
},
],
defaultCheckedKeys: [],
nodeKey: 'id',
defaultProps: {
children: 'children',
label: 'label',
},
productDataList: [], // 产品规格数据
}
},
computed: {
...mapGetters({
configs: 'routes/configs',
}),
...mapGetters({
rid: 'user/rid',
}),
},
created() {
let query = this.$route.query
if (query.product_state_id) {
this.queryForm.product_state_id = Number(query.product_state_id)
}
this.params.authorization = getToken()
this.fetchData()
this.getTree()
},
methods: {
__,
showImport() {
this.$refs.excelExeImport.showEdit()
},
async changeState(product_id, state) {
this.$baseConfirm(this.__('请确认是否更改状态?'), null, async () => {
const { msg, status } = await editState({
product_state_id: state,
product_id: product_id,
})
if (status == 200) {
this.$baseMessage(msg, 'success', false, 'vab-hey-message-success')
} else {
this.$baseMessage(msg, 'error')
}
await this.fetchData()
})
},
async getTree() {
const { data } = await getTree()
this.productDataList = data
},
handleSuccess(response, file, fileList) {
let status = response.status
let msg = response.msg
if (status === 200) {
if (200 == status) {
this.$baseMessage(msg, 'success')
} else {
this.$baseMessage(msg, 'error')
}
this.$emit('fetch-data')
this.close()
} else {
this.$refs.upload.clearFiles()
this.$baseMessage(msg, 'error')
}
},
formatId(row) {
return row.product_verify_id === 3001
? this.__('审核通过')
: row.product_verify_id === 3002
? this.__('审核中')
: this.__('审核未通过')
},
formatTime(row) {
const product_sale_time = row.product_sale_time
return product_sale_time ? renderTime(product_sale_time) : ''
},
inquire(product_state_id) {
if (product_state_id) {
this.queryForm.product_state_id = product_state_id
} else {
this.queryForm.product_state_id = ''
}
this.queryForm.pageNum = 1
this.queryForm.pageSize = 10
this.fetchData()
},
__,
setSelectRows(val) {
this.selectRows = val
},
handleEdit(row) {
this.$refs['edit'].showEdit(row)
},
handleAdd(row) {
this.$refs['add'].showEdit(row)
},
handleSizeChange(val) {
this.queryForm.pageSize = val
this.fetchData()
},
handleCurrentChange(val) {
this.queryForm.pageNum = val
this.fetchData()
},
queryData() {
this.queryForm.pageNum = 1
this.fetchData()
},
showPreview(row) {
this.pc_url =
process.env.VUE_APP_BASE_URL +
'/product/detail?item_id=' +
row.item_id
this.dialogVisible = true
},
async reviewOne(row, product_state_id) {
this.$baseConfirm(this.__('请确认是否更改状态?'), null, async () => {
const { msg, status } = await editState({
product_state_id: product_state_id,
product_id: row.product_id,
})
if (status == 200) {
this.$baseMessage(msg, 'success', false, 'vab-hey-message-success')
} else {
this.$baseMessage(msg, 'error')
}
await this.fetchData()
})
},
expPrint() {
const rows = this.$refs.table.selection
if (!rows || rows.length <= 0) {
this.$baseMessage('没有选中的数据!', 'error')
return
}
let product_ids = rows.map((item) => item.product_id)
exportFile({ product_ids: product_ids.toString() }).then((data) => {
const blob = new Blob([data])
const downloadElement = document.createElement('a')
const href = window.URL.createObjectURL(blob) //创建下载的链接
downloadElement.href = href
downloadElement.download = decodeURIComponent('商品数据.csv') //下载后文件名
document.body.appendChild(downloadElement)
downloadElement.click() //点击下载
document.body.removeChild(downloadElement) //下载完成移除元素
window.URL.revokeObjectURL(href) //释放掉blob对象
})
},
async review(product_state_id) {
let product_id = this.selectRows.map((item) => item.product_id)
const { msg, status } = await editState({
product_state_id: product_state_id,
product_id: product_id.toString(),
})
if (200 == status) {
this.$baseMessage(msg, 'success')
} else {
this.$baseMessage(msg, 'error')
}
await this.fetchData()
},
handleDelete(row) {
this.$baseConfirm(this.__('你确定要删除当前项吗'), null, async () => {
const { msg, status } = await doDelete({ product_id: row.product_id })
if (200 == status) {
this.$baseMessage(msg, 'success')
} else {
this.$baseMessage(msg, 'error')
}
await this.fetchData()
})
},
async fetchData() {
this.listLoading = true
const { data } = await getList(this.queryForm)
this.list = data.items
this.total = data.records
this.listLoading = false
},
change(id) {
this.queryForm.category_id = id
},
},
}
</script>