需求:根据列表数据生成查询条件,并实现查询功能

libs/util.js 文件中

/**
 *
 * @param {Object} condition
 * @description 查询条件,是一个对象
 *
 * @param {Array} data
 * @description 需要筛选的数据源
 */
// 纯前端实现列表查询
export function filterData(condition, data) {
    let filter = (condition, data) => {
        return data.filter(item => {
            return Object.keys(condition).every(key => {
                if (condition[key] == '') {
                    return true
                } 
                // 精准查询
                else {
                    return item[key] === condition[key]
                }
                // 模糊查询
                // 这里是为了进行某个(或多个)条件的模糊查询做出的业务判断,key是对应的值。
                // let diff =
                //     key == 'gdsNm1' || 'gdsNm2'
                //         ? String(item[key]).toLowerCase().indexOf(String(condition[key]).trim().toLowerCase()) !== -1
                //         : String(item[key]).toLowerCase() == String(condition[key]).trim().toLowerCase()
                // return diff
            })
        })
    }
    return filter(condition, data)
}

.vue 文件中

<template>
    <div>
        <el-dialog title="组合SKU" :visible.sync="dialogVisible" width="80%" @close="closeHandle">
            <div class="warn-box">
                <img class="warn-img" src="~@/assets/warn.png" alt="" />
                SKU进行组合时,多规格的情况下,至少有一个规格的属性值不同,其他规格属性值相同才能进行组合。
            </div>
            <!-- 查询 -->
            <el-form :model="formInline" :inline="true">
                <div v-for="(data, dataIndex) in specsOptions" :key="data.value" class="searchform-wrap">
                    <el-form-item :label="data.label" v-if="data.options.length">
                        <el-select v-model="formInline[data.value]" placeholder="请选择" filterable>
                            <el-option label="全部" value=""></el-option>
                            <el-option :label="item.label" :value="item.value" v-for="item in specsOptions[dataIndex].options" :key="item.value"></el-option>
                        </el-select>
                    </el-form-item>
                </div>
                <el-form-item>
                    <el-button type="primary" @click="handleSearch">查询</el-button>
                    <el-button @click="reset">重置</el-button>
                </el-form-item>
            </el-form>
            <!-- 表格内容 -->
            <el-table ref="skuTable" :data="tableData" height="400" tooltip-effect="dark" border style="width: 100%" @selection-change="handleSelectionChange">
                <el-table-column type="selection" width="50" align="center"></el-table-column>
                <el-table-column prop="skuName" show-overflow-tooltip label="商品名称" minWidth="140"></el-table-column>

                <el-table-column v-if="showColumn('模块')" prop="module" show-overflow-tooltip label="模块" minWidth="110"></el-table-column>
                <el-table-column v-if="showColumn('批次')" prop="batch" show-overflow-tooltip label="批次" minWidth="110"></el-table-column>
                <el-table-column v-if="showColumn('地方版')" prop="localVersion" show-overflow-tooltip label="地方版" minWidth="110"></el-table-column>
                <el-table-column v-if="showColumn('学期')" prop="semester" show-overflow-tooltip label="学期" minWidth="110"></el-table-column>
                <el-table-column v-if="showColumn('科目')" prop="subject" show-overflow-tooltip label="科目" minWidth="110"></el-table-column>
                <el-table-column v-if="showColumn('版本')" prop="version" show-overflow-tooltip label="版本" minWidth="110"></el-table-column>
                <el-table-column v-if="showColumn('使用类型')" prop="useType" show-overflow-tooltip label="使用类型" minWidth="110"></el-table-column>
                <el-table-column v-if="showColumn('年级')" prop="grade" show-overflow-tooltip label="年级" minWidth="110"></el-table-column>

                <el-table-column prop="skuCode" show-overflow-tooltip label="SKU编号" minWidth="140"></el-table-column>
            </el-table>
            <span slot="footer" class="dialog-footer">
                <el-button @click="closeHandle">取 消</el-button>
                <el-button type="primary" :disabled="disabled" :loading="confirmLoading" @click="confirmHandle(1)">提交</el-button>
                <el-button type="primary" :disabled="disabled" :loading="confirmLoading" @click="confirmHandle(0)">提交并继续</el-button>
            </span>
        </el-dialog>
    </div>
</template>

<script>
import { skuGroup } from '@/api/goods'
import { unique, filterData } from '@/libs/util'

export default {
    name: 'Combination',
    props: {
        value: {
            type: Boolean,
            default: true
        },
        skuList: {
            type: Array,
            default: () => {
                return []
            }
        },
        skuAttributes: {
            type: Array,
            default: () => {
                return []
            }
        }
    },
    computed: {
        dialogVisible: {
            get() {
                return this.value
            },
            set(val) {
                this.$emit('input', val)
            }
        }
    },
    watch: {
        skuList(newValue) {
            if (newValue) {
                let data = newValue.filter(item => item.skuCode.indexOf('ZH') == -1)
                this.beforeSearchData = data
                this.tableData = data
                this.zhList = newValue.filter(item => item.skuCode.indexOf('ZH') != -1)
                this.generateOptions()
            }
        }
    },
    data() {
        return {
            diffKey: '',
            beforeSearchData: [],
            tableData: [],
            zhList: [],
            btnLoading: false,
            confirmLoading: false,
            disabled: true,
            selectList: [],
            formInline: {
                module: '',
                batch: '',
                localVersion: '',
                semester: '',
                subject: '',
                version: '',
                useType: '',
                grade: ''
            },
            specsOptions: [
                {
                    label: '模块',
                    value: 'module',
                    options: []
                },
                {
                    label: '批次',
                    value: 'batch',
                    options: []
                },
                {
                    label: '地方版',
                    value: 'localVersion',
                    options: []
                },
                {
                    label: '学期',
                    value: 'semester',
                    options: []
                },
                {
                    label: '科目',
                    value: 'subject',
                    options: []
                },
                {
                    label: '版本',
                    value: 'version',
                    options: []
                },
                {
                    label: '使用类型',
                    value: 'useType',
                    options: []
                },
                {
                    label: '年级',
                    value: 'grade',
                    options: []
                }
            ]
        }
    },
    methods: {
        //商品表格属性头展示
        showColumn(key) {
            return this.skuAttributes.indexOf(key) > -1
        },
        // 查询条件
        generateOptions() {
            let arr = this.specsOptions.map(item => {
                if (this.skuAttributes.indexOf(item.label) > -1) {
                    return item
                }
            })
            for (const attrItem of arr) {
                if (attrItem) {
                    let options = this.beforeSearchData?.map(tableItem => {
                        return {
                            value: tableItem[attrItem.value],
                            label: tableItem[attrItem.value]
                        }
                    })
                    attrItem.options = options && options.length ? unique(options, 'label') : []
                }
            }
        },
        //表格选中
        handleSelectionChange(list) {
            this.selectList = list
            this.disabled = list.length > 1 ? false : true
            // this.disabled = this.findDiff(list)
        },
        findDiff(list) {
            let arr = this.specsOptions.filter(item => this.skuAttributes.indexOf(item.label) > -1)
            let keyList = arr.map(item => item.value)
            let diffList = []
            list.forEach(item => {
                let val = {}
                keyList.forEach(el => {
                    val[el] = item[el]
                })
                diffList.push(val)
            })
            let basic = {}
            diffList.forEach(el => {
                Object.keys(el).forEach(k => {
                    let map = basic[k]
                    if (!map) {
                        basic[k] = new Set()
                        map = basic[k]
                    }
                    map.add(el[k])
                })
            })
            let keys = Object.keys(basic).filter(k => basic[k].size > 1)
            this.diffKey = keys[0]
            return keys.length != 1
        },
        //查找组合商品是否重复
        findZHDiff(e, list) {
            if (!list || list.length < 1) {
                return false
            } else {
                let code = e.childSkuCodes.join(',')
                list.forEach(item => {
                    item.formChild = item.childSkuCodes.join(',')
                })
                let codeList = list.map(item => item.formChild)
                return codeList.indexOf(code) == -1 ? false : true
            }
        },
        // 取消
        closeHandle() {
            this.formInline = {
                module: '',
                batch: '',
                localVersion: '',
                semester: '',
                subject: '',
                version: '',
                useType: '',
                grade: ''
            }
            this.$emit('input', false)
            this.$refs.skuTable.clearSelection()
        },
        // 提交
        confirmHandle(flag) {
            this.selectList.forEach(item => {
                item.warningNum = item.warningNum ? item.warningNum : 0
            })
            let params = this.selectList
            this.confirmLoading = true
            skuGroup(params)
                .then(res => {
                    let val = res.data.data || {}
                    let repet = this.findZHDiff(val, this.zhList)
                    if (repet) {
                        this.$message.warning('该组合已存在请勿重复操作')
                        return
                    }
                    val.fluInventory = val.availableInventory
                    val.childSkuCodes = params.map(item => item.skuCode)
                    this.$emit('confirm', val, flag)
                    this.zhList.push(val)
                    this.$message.success('组合成功')
                    if (flag == 1) {
                        this.closeHandle()
                    }
                })
                .finally(res => {
                    this.confirmLoading = false
                })
        },
        // 查询
        handleSearch() {
            this.tableData = filterData(this.formInline, this.beforeSearchData)
        },
        // 重置
        reset() {
            this.formInline = {
                module: '',
                batch: '',
                localVersion: '',
                semester: '',
                subject: '',
                version: '',
                useType: '',
                grade: ''
            }
            this.tableData = this.beforeSearchData
        }
    }
}
</script>

<style lang="less">
.searchform-wrap {
    display: inline-block;
    margin-right: 6px;
}
</style>

参考文章:前端多条件查询数据处理

Logo

技术共进,成长同行——讯飞AI开发者社区

更多推荐