Browse Source
feat(order): 添加国际化支持并优化权限控制
feat(order): 添加国际化支持并优化权限控制
- 在多个组件中添加locale属性支持中英文切换 - 实现表格列标题的国际化显示 - 为首页代办功能添加菜单权限控制 - 移除菜单管理中不必要的"菜单"文字重复显示 - 禁止菜单路由字段在编辑时被修改 - 限制菜单删除功能仅对非一级菜单生效 - 新增英文版PO订单查询页面支持国际化显示master
8 changed files with 1107 additions and 28 deletions
-
12src/views/common/home.vue
-
37src/views/modules/order/com_inspectionDetailList.vue
-
19src/views/modules/order/com_logisticsPoList.vue
-
87src/views/modules/order/com_poOrderDetail.vue
-
14src/views/modules/order/com_poPartAttribute.vue
-
960src/views/modules/order/poOrder_search_en.vue
-
2src/views/modules/sys/menu-add-or-update.vue
-
4src/views/modules/sys/menu.vue
@ -0,0 +1,960 @@ |
|||||
|
<template> |
||||
|
<div class="mod-config"> |
||||
|
<com-po-order-customer-picker |
||||
|
:site="searchData.site" |
||||
|
v-model="searchData.customer" |
||||
|
@change="onSessionCustomerChange" /> |
||||
|
<!-- Search Conditions --> |
||||
|
<el-form :inline="true" label-position="top" :model="searchData"> |
||||
|
<el-form-item label="PO No"> |
||||
|
<el-input v-model="searchData.poNo" clearable style="width: 140px" @keyup.enter.native="handleSearch"></el-input> |
||||
|
</el-form-item> |
||||
|
<el-form-item label="Order Type"> |
||||
|
<el-select v-model="searchData.orderType" placeholder="Please select" style="width: 120px" clearable> |
||||
|
<el-option |
||||
|
v-for="item in poOrderTypeSearchOptions" |
||||
|
:key="item.value" |
||||
|
:label="item.label" |
||||
|
:value="item.value" /> |
||||
|
</el-select> |
||||
|
</el-form-item> |
||||
|
<el-form-item> |
||||
|
<span style="cursor: pointer" slot="label" @click="openSearchBaseList(2017)"><a href="javascript:void(0)">Part No</a></span> |
||||
|
<el-input v-model="searchData.partNo" clearable style="width: 120px" @keyup.enter.native="handleSearch"></el-input> |
||||
|
</el-form-item> |
||||
|
<el-form-item> |
||||
|
<span style="cursor: pointer" slot="label" @click="openSearchBaseList(520)"><a href="javascript:void(0)">Supplier Code</a></span> |
||||
|
<el-input v-model="searchData.supplierNo" clearable style="width: 120px" @keyup.enter.native="handleSearch"></el-input> |
||||
|
</el-form-item> |
||||
|
<el-form-item label="SKU"> |
||||
|
<el-input v-model="searchData.sku" clearable style="width: 120px" @keyup.enter.native="handleSearch"></el-input> |
||||
|
</el-form-item> |
||||
|
<el-form-item label="Status"> |
||||
|
<el-select v-model="searchData.status" placeholder="Please select" style="width:100px" clearable> |
||||
|
<el-option label="All" value=""></el-option> |
||||
|
<el-option |
||||
|
v-for="item in poOrderStatusOptions" |
||||
|
:key="item.value" |
||||
|
:label="item.label" |
||||
|
:value="item.value" /> |
||||
|
</el-select> |
||||
|
</el-form-item> |
||||
|
</el-form> |
||||
|
|
||||
|
<el-form :inline="true" label-position="top" style="margin-top:10px"> |
||||
|
<el-form-item> |
||||
|
<el-button type="primary" @click="handleSearch" :disabled="!searchData.customer">Search</el-button> |
||||
|
<el-button type="primary" @click="exportExcel" style="margin-left: 2px">Export</el-button> |
||||
|
<el-button @click="resetSearch">Reset</el-button> |
||||
|
<el-button type="warning" plain @click="advancedQueryVisible = true" style="margin-left: 2px">Advanced Query</el-button> |
||||
|
</el-form-item> |
||||
|
</el-form> |
||||
|
|
||||
|
<!-- Data Table --> |
||||
|
<el-table |
||||
|
ref="poTable" |
||||
|
:height="height" |
||||
|
:data="dataList" |
||||
|
border |
||||
|
highlight-current-row |
||||
|
v-loading="loading" |
||||
|
@row-click="changeData" |
||||
|
style="width: 100%;"> |
||||
|
<el-table-column |
||||
|
v-for="(item, index) in visibleColumns" |
||||
|
:key="item.serialNumber || index" |
||||
|
:sortable="item.columnSortable" |
||||
|
:prop="item.columnProp" |
||||
|
:header-align="item.headerAlign" |
||||
|
:show-overflow-tooltip="item.showOverflowTooltip" |
||||
|
:align="item.align" |
||||
|
:fixed="item.fixed === '' ? false : item.fixed" |
||||
|
:min-width="item.columnWidth" |
||||
|
:label="item.columnLabel"> |
||||
|
<template slot-scope="scope"> |
||||
|
<span>{{ formatColumnCell(scope.row, item) }}</span> |
||||
|
</template> |
||||
|
</el-table-column> |
||||
|
</el-table> |
||||
|
|
||||
|
<!-- Pagination --> |
||||
|
<el-pagination |
||||
|
@size-change="sizeChangeHandle" |
||||
|
@current-change="currentChangeHandle" |
||||
|
:current-page="pageIndex" |
||||
|
:page-sizes="[20, 50, 100, 200, 500]" |
||||
|
:page-size="pageSize" |
||||
|
:total="totalPage" |
||||
|
layout="total, sizes, prev, pager, next, jumper"> |
||||
|
</el-pagination> |
||||
|
|
||||
|
<!-- Detail Tabs --> |
||||
|
<el-tabs v-model="activeTab" style="margin-top: 0px; width: 99%;" @tab-click="handleTabClick" class="customer-tab" type="border-card"> |
||||
|
<!-- Order Detail --> |
||||
|
<el-tab-pane label="Order Detail" name="orderDetail"> |
||||
|
<po-order-detail |
||||
|
:detail-data="currentRow" |
||||
|
:schema-fields="fieldSchemaFields" |
||||
|
locale="en" /> |
||||
|
</el-tab-pane> |
||||
|
<!-- Logistics --> |
||||
|
<el-tab-pane label="Logistics" name="logistics"> |
||||
|
<logistics-po-list ref="logisticsPoList" locale="en" /> |
||||
|
</el-tab-pane> |
||||
|
<!-- Inspection Detail --> |
||||
|
<el-tab-pane label="Inspection Detail" name="inspectionDetail"> |
||||
|
<inspection-detail-list ref="inspectionDetailList" locale="en" /> |
||||
|
</el-tab-pane> |
||||
|
<!-- Part Attribute (Read Only) --> |
||||
|
<el-tab-pane label="Part Attribute" name="partAttribute"> |
||||
|
<po-part-attribute ref="partAttributeTab" locale="en" /> |
||||
|
</el-tab-pane> |
||||
|
</el-tabs> |
||||
|
|
||||
|
<po-order-advanced-query |
||||
|
:visible.sync="advancedQueryVisible" |
||||
|
:advanced-query-data="advancedQueryData" |
||||
|
@query="handleSearch" /> |
||||
|
|
||||
|
<ChooselistEam ref="eamList" @getBaseData="getEamData" /> |
||||
|
</div> |
||||
|
</template> |
||||
|
|
||||
|
<script> |
||||
|
import { searchPoDetailPage, searchPoDetailAdvancedPage, getPoFieldSchema } from '@/api/order/poOrder.js' |
||||
|
import { |
||||
|
createAdvancedQueryData, |
||||
|
createAdvancedQueryDataFromSchema, |
||||
|
buildPoOrderQueryParams |
||||
|
} from './poOrderAdvancedQueryHelper.js' |
||||
|
import { |
||||
|
applyFieldSchemaToColumns, |
||||
|
getAdvancedQueryFieldsFromSchema, |
||||
|
normalizeSchemaRowValues |
||||
|
} from './poOrderFieldSchemaHelper.js' |
||||
|
import excel from '@/utils/excel-util.js' |
||||
|
import LogisticsPoList from './com_logisticsPoList.vue' |
||||
|
import InspectionDetailList from './com_inspectionDetailList.vue' |
||||
|
import PoPartAttribute from './com_poPartAttribute.vue' |
||||
|
import PoOrderDetail from './com_poOrderDetail.vue' |
||||
|
import PoOrderAdvancedQuery from './com_poOrderAdvancedQuery.vue' |
||||
|
import ChooselistEam from '@/views/modules/common/Chooselist_eam.vue' |
||||
|
import ComPoOrderCustomerPicker from './com_poOrder_CustomerPicker.vue' |
||||
|
import { PO_ORDER_STATUS_OPTIONS } from './poOrderStatusOptions.js' |
||||
|
import { PO_ORDER_TYPE_OPTIONS, formatPoOrderTypeLabel } from './poOrderTypeOptions.js' |
||||
|
import { searchPartInfo } from '@/api/part/partInfo.js' |
||||
|
|
||||
|
export default { |
||||
|
components: { |
||||
|
LogisticsPoList, |
||||
|
InspectionDetailList, |
||||
|
PoPartAttribute, |
||||
|
PoOrderDetail, |
||||
|
PoOrderAdvancedQuery, |
||||
|
ChooselistEam, |
||||
|
ComPoOrderCustomerPicker |
||||
|
}, |
||||
|
name: 'PoOrderQueryEn', |
||||
|
data() { |
||||
|
return { |
||||
|
loading: false, |
||||
|
exportLoading: false, |
||||
|
height: 400, |
||||
|
activeTab: 'orderDetail', |
||||
|
pageIndex: 1, |
||||
|
pageSize: 20, |
||||
|
totalPage: 0, |
||||
|
dataList: [], |
||||
|
currentRow: {}, |
||||
|
advancedQueryVisible: false, |
||||
|
eamTagNo: '', |
||||
|
poOrderTypeSearchOptions: [{ label: 'All', value: '' }, ...PO_ORDER_TYPE_OPTIONS], |
||||
|
/** Advanced query object (read by search/export; only reset in dialog) */ |
||||
|
advancedQueryData: createAdvancedQueryData(), |
||||
|
fieldSchemaFields: [], |
||||
|
baseColumnList: null, |
||||
|
poOrderStatusOptions: PO_ORDER_STATUS_OPTIONS, |
||||
|
searchData: { |
||||
|
site: this.$store.state.user.site, |
||||
|
customer: '', |
||||
|
buyer: '', |
||||
|
poNo: '', |
||||
|
orderType: '', |
||||
|
partNo: '', |
||||
|
supplierNo: '', |
||||
|
sku: '', |
||||
|
status: '', |
||||
|
supplierName: '', |
||||
|
feeDateStart: '', |
||||
|
feeDateEnd: '' |
||||
|
}, |
||||
|
// Column config (consistent with original page, hides edit related columns) |
||||
|
columnList: [ |
||||
|
{ |
||||
|
columnProp: 'poNo', |
||||
|
columnLabel: 'PO No', |
||||
|
align: 'center', |
||||
|
columnWidth: 120, |
||||
|
showOverflowTooltip: true, |
||||
|
headerAlign: 'center' |
||||
|
}, |
||||
|
{ |
||||
|
columnProp: 'orderType', |
||||
|
columnLabel: 'Order Type', |
||||
|
align: 'center', |
||||
|
columnWidth: 100, |
||||
|
showOverflowTooltip: true, |
||||
|
headerAlign: 'center' |
||||
|
}, |
||||
|
{ |
||||
|
columnProp: 'customer', |
||||
|
columnLabel: 'Customer', |
||||
|
align: 'center', |
||||
|
columnWidth: 180, |
||||
|
showOverflowTooltip: true, |
||||
|
headerAlign: 'center' |
||||
|
}, |
||||
|
{ |
||||
|
columnProp: 'buyer', |
||||
|
columnLabel: 'Buyer', |
||||
|
align: 'center', |
||||
|
columnWidth: 90, |
||||
|
showOverflowTooltip: true, |
||||
|
headerAlign: 'center' |
||||
|
}, |
||||
|
{ |
||||
|
columnProp: 'supplierName', |
||||
|
columnLabel: 'Vendor Name', |
||||
|
align: 'center', |
||||
|
columnWidth: 180, |
||||
|
showOverflowTooltip: true, |
||||
|
headerAlign: 'center' |
||||
|
}, |
||||
|
{ |
||||
|
columnProp: 'shortOffice', |
||||
|
columnLabel: 'V_Short_Office', |
||||
|
align: 'center', |
||||
|
columnWidth: 110, |
||||
|
showOverflowTooltip: true, |
||||
|
headerAlign: 'center' |
||||
|
}, |
||||
|
{ |
||||
|
columnProp: 'shortNpc', |
||||
|
columnLabel: 'V_Short_NPC', |
||||
|
align: 'center', |
||||
|
columnWidth: 100, |
||||
|
showOverflowTooltip: true, |
||||
|
headerAlign: 'center' |
||||
|
}, |
||||
|
{ |
||||
|
columnProp: 'partNo', |
||||
|
columnLabel: 'Part No', |
||||
|
align: 'center', |
||||
|
columnWidth: 120, |
||||
|
showOverflowTooltip: true, |
||||
|
headerAlign: 'center' |
||||
|
}, |
||||
|
{ |
||||
|
columnProp: 'item', |
||||
|
columnLabel: 'Item', |
||||
|
align: 'center', |
||||
|
columnWidth: 120, |
||||
|
showOverflowTooltip: true, |
||||
|
headerAlign: 'center' |
||||
|
}, |
||||
|
{ |
||||
|
columnProp: 'categoryName', |
||||
|
columnLabel: 'Category', |
||||
|
align: 'center', |
||||
|
columnWidth: 90, |
||||
|
showOverflowTooltip: true, |
||||
|
headerAlign: 'center' |
||||
|
}, |
||||
|
{ |
||||
|
columnProp: 'sku', |
||||
|
columnLabel: 'SKU', |
||||
|
align: 'center', |
||||
|
columnWidth: 100, |
||||
|
showOverflowTooltip: true, |
||||
|
headerAlign: 'center' |
||||
|
}, |
||||
|
{ |
||||
|
columnProp: 'price', |
||||
|
columnLabel: 'Unit Price', |
||||
|
align: 'center', |
||||
|
columnWidth: 90, |
||||
|
showOverflowTooltip: true, |
||||
|
headerAlign: 'center' |
||||
|
}, |
||||
|
{ |
||||
|
columnProp: 'qty', |
||||
|
columnLabel: 'PO Qty', |
||||
|
align: 'center', |
||||
|
columnWidth: 80, |
||||
|
showOverflowTooltip: true, |
||||
|
headerAlign: 'center' |
||||
|
}, |
||||
|
{ |
||||
|
columnProp: 'value', |
||||
|
columnLabel: 'PO Value', |
||||
|
align: 'center', |
||||
|
columnWidth: 90, |
||||
|
showOverflowTooltip: true, |
||||
|
headerAlign: 'center' |
||||
|
}, |
||||
|
{ |
||||
|
columnProp: 'shipQty', |
||||
|
columnLabel: 'A-Qty', |
||||
|
align: 'center', |
||||
|
columnWidth: 80, |
||||
|
showOverflowTooltip: true, |
||||
|
headerAlign: 'center' |
||||
|
}, |
||||
|
{ |
||||
|
columnProp: 'sumPrice', |
||||
|
columnLabel: 'A-Value', |
||||
|
align: 'center', |
||||
|
columnWidth: 90, |
||||
|
showOverflowTooltip: true, |
||||
|
headerAlign: 'center' |
||||
|
}, |
||||
|
{ |
||||
|
columnProp: 'departure', |
||||
|
columnLabel: 'Departure Port', |
||||
|
align: 'center', |
||||
|
columnWidth: 100, |
||||
|
showOverflowTooltip: true, |
||||
|
headerAlign: 'center' |
||||
|
}, |
||||
|
{ |
||||
|
columnProp: 'destination', |
||||
|
columnLabel: 'Destination Port', |
||||
|
align: 'center', |
||||
|
columnWidth: 110, |
||||
|
showOverflowTooltip: true, |
||||
|
headerAlign: 'center' |
||||
|
}, |
||||
|
{ |
||||
|
columnProp: 'shipVia', |
||||
|
columnLabel: 'Method', |
||||
|
align: 'center', |
||||
|
columnWidth: 90, |
||||
|
showOverflowTooltip: true, |
||||
|
headerAlign: 'center' |
||||
|
}, |
||||
|
{ |
||||
|
columnProp: 'orderDate', |
||||
|
columnLabel: 'Buyer Release Date', |
||||
|
align: 'center', |
||||
|
columnWidth: 130, |
||||
|
showOverflowTooltip: true, |
||||
|
headerAlign: 'center' |
||||
|
}, |
||||
|
{ |
||||
|
columnProp: 'enquiry', |
||||
|
columnLabel: 'Planner Release Date', |
||||
|
align: 'center', |
||||
|
columnWidth: 140, |
||||
|
showOverflowTooltip: true, |
||||
|
headerAlign: 'center' |
||||
|
}, |
||||
|
{ |
||||
|
columnProp: 'status', |
||||
|
columnLabel: 'Status', |
||||
|
align: 'center', |
||||
|
columnWidth: 80, |
||||
|
showOverflowTooltip: true, |
||||
|
headerAlign: 'center' |
||||
|
}, |
||||
|
{ |
||||
|
columnProp: 'confirmed', |
||||
|
columnLabel: 'PI Confirmed Date', |
||||
|
align: 'center', |
||||
|
columnWidth: 120, |
||||
|
showOverflowTooltip: true, |
||||
|
headerAlign: 'center' |
||||
|
}, |
||||
|
{ |
||||
|
columnProp: 'wantReceiveDate', |
||||
|
columnLabel: 'Original Arrival Date', |
||||
|
align: 'center', |
||||
|
columnWidth: 130, |
||||
|
showOverflowTooltip: true, |
||||
|
headerAlign: 'center' |
||||
|
}, |
||||
|
{ |
||||
|
columnProp: 'narrival', |
||||
|
columnLabel: 'Final Confirmed Arrival Date', |
||||
|
align: 'center', |
||||
|
columnWidth: 110, |
||||
|
showOverflowTooltip: true, |
||||
|
headerAlign: 'center' |
||||
|
}, |
||||
|
{ |
||||
|
columnProp: 'crd', |
||||
|
columnLabel: 'PI Confirmed CRD', |
||||
|
align: 'center', |
||||
|
columnWidth: 120, |
||||
|
showOverflowTooltip: true, |
||||
|
headerAlign: 'center' |
||||
|
}, |
||||
|
{ |
||||
|
columnProp: 'crdOri', |
||||
|
columnLabel: 'Original CRD', |
||||
|
align: 'center', |
||||
|
columnWidth: 120, |
||||
|
showOverflowTooltip: true, |
||||
|
headerAlign: 'center' |
||||
|
}, |
||||
|
{ |
||||
|
columnProp: 'inspection', |
||||
|
columnLabel: 'Inspection Date', |
||||
|
align: 'center', |
||||
|
columnWidth: 100, |
||||
|
showOverflowTooltip: true, |
||||
|
headerAlign: 'center' |
||||
|
}, |
||||
|
{ |
||||
|
columnProp: 'realCrd', |
||||
|
columnLabel: 'Actual Completion Date', |
||||
|
align: 'center', |
||||
|
columnWidth: 150, |
||||
|
showOverflowTooltip: true, |
||||
|
headerAlign: 'center' |
||||
|
}, |
||||
|
{ |
||||
|
columnProp: 'eta', |
||||
|
columnLabel: 'ETA', |
||||
|
align: 'center', |
||||
|
columnWidth: 100, |
||||
|
showOverflowTooltip: true, |
||||
|
headerAlign: 'center' |
||||
|
}, |
||||
|
{ |
||||
|
columnProp: 'flexid', |
||||
|
columnLabel: 'Flexport Id', |
||||
|
align: 'center', |
||||
|
columnWidth: 90, |
||||
|
showOverflowTooltip: true, |
||||
|
headerAlign: 'center' |
||||
|
}, |
||||
|
{ |
||||
|
columnProp: 'obd', |
||||
|
columnLabel: 'On Board Date', |
||||
|
align: 'center', |
||||
|
columnWidth: 100, |
||||
|
showOverflowTooltip: true, |
||||
|
headerAlign: 'center' |
||||
|
}, |
||||
|
{ |
||||
|
columnProp: 'docSent', |
||||
|
columnLabel: 'Doc Sent', |
||||
|
align: 'center', |
||||
|
columnWidth: 90, |
||||
|
showOverflowTooltip: true, |
||||
|
headerAlign: 'center' |
||||
|
}, |
||||
|
{ |
||||
|
columnProp: 'telexRelease', |
||||
|
columnLabel: 'Telex Release', |
||||
|
align: 'center', |
||||
|
columnWidth: 100, |
||||
|
showOverflowTooltip: true, |
||||
|
headerAlign: 'center' |
||||
|
}, |
||||
|
{ |
||||
|
columnProp: 'advancePayment', |
||||
|
columnLabel: 'Advance Payment', |
||||
|
align: 'center', |
||||
|
columnWidth: 120, |
||||
|
showOverflowTooltip: true, |
||||
|
headerAlign: 'center' |
||||
|
}, |
||||
|
{ |
||||
|
columnProp: 'advancePaid', |
||||
|
columnLabel: 'Advanc Paid', |
||||
|
align: 'center', |
||||
|
columnWidth: 100, |
||||
|
showOverflowTooltip: true, |
||||
|
headerAlign: 'center' |
||||
|
}, |
||||
|
{ |
||||
|
columnProp: 'createTime', |
||||
|
columnLabel: 'Create Date', |
||||
|
align: 'center', |
||||
|
columnWidth: 100, |
||||
|
showOverflowTooltip: true, |
||||
|
headerAlign: 'center' |
||||
|
}, |
||||
|
{ |
||||
|
columnProp: 'planner', |
||||
|
columnLabel: 'M-Planner', |
||||
|
align: 'center', |
||||
|
columnWidth: 100, |
||||
|
showOverflowTooltip: true, |
||||
|
headerAlign: 'center' |
||||
|
}, |
||||
|
{ |
||||
|
columnProp: 'edit', |
||||
|
columnLabel: 'Edit Date', |
||||
|
align: 'center', |
||||
|
columnWidth: 100, |
||||
|
showOverflowTooltip: true, |
||||
|
headerAlign: 'center' |
||||
|
}, |
||||
|
{ |
||||
|
columnProp: 'endPlanner', |
||||
|
columnLabel: 'Last Editor', |
||||
|
align: 'center', |
||||
|
columnWidth: 100, |
||||
|
showOverflowTooltip: true, |
||||
|
headerAlign: 'center' |
||||
|
}, |
||||
|
{ |
||||
|
columnProp: 'remarkDelay', |
||||
|
columnLabel: 'Remark Delay', |
||||
|
align: 'center', |
||||
|
columnWidth: 110, |
||||
|
showOverflowTooltip: true, |
||||
|
headerAlign: 'center' |
||||
|
}, |
||||
|
{ |
||||
|
columnProp: 'remark', |
||||
|
columnLabel: 'Comments', |
||||
|
align: 'center', |
||||
|
columnWidth: 180, |
||||
|
showOverflowTooltip: true, |
||||
|
headerAlign: 'center' |
||||
|
}, |
||||
|
{ |
||||
|
columnProp: 'inspectionCompletedQty', |
||||
|
columnLabel: 'Inspection Completed Qty', |
||||
|
align: 'center', |
||||
|
columnWidth: 140, |
||||
|
showOverflowTooltip: true, |
||||
|
headerAlign: 'center' |
||||
|
} |
||||
|
] |
||||
|
} |
||||
|
}, |
||||
|
computed: { |
||||
|
visibleColumns() { |
||||
|
const source = this.baseColumnList || this.columnList |
||||
|
const applied = applyFieldSchemaToColumns(source, this.fieldSchemaFields) |
||||
|
return applied.filter(c => !c.columnHidden) |
||||
|
} |
||||
|
}, |
||||
|
created() { |
||||
|
this.baseColumnList = JSON.parse(JSON.stringify(this.columnList)) |
||||
|
}, |
||||
|
mounted() { |
||||
|
this.updateTableHeight() |
||||
|
window.addEventListener('resize', this.onWindowResize) |
||||
|
}, |
||||
|
activated () { |
||||
|
this.updateTableHeight() |
||||
|
this.refreshTableLayout() |
||||
|
}, |
||||
|
deactivated () { |
||||
|
this.refreshTableLayout() |
||||
|
}, |
||||
|
beforeDestroy () { |
||||
|
window.removeEventListener('resize', this.onWindowResize) |
||||
|
}, |
||||
|
methods: { |
||||
|
onWindowResize () { |
||||
|
this.updateTableHeight() |
||||
|
}, |
||||
|
updateTableHeight () { |
||||
|
const calculatedHeight = (window.innerHeight - 220) / 2 |
||||
|
this.height = calculatedHeight > 220 ? calculatedHeight : 220 |
||||
|
this.refreshTableLayout() |
||||
|
}, |
||||
|
refreshTableLayout () { |
||||
|
this.$nextTick(() => { |
||||
|
if (this.$refs.poTable && this.$refs.poTable.doLayout) { |
||||
|
this.$refs.poTable.doLayout() |
||||
|
} |
||||
|
}) |
||||
|
}, |
||||
|
formatColumnCell (row, item) { |
||||
|
if (item.columnProp === 'orderType') { |
||||
|
return formatPoOrderTypeLabel(row.orderType) |
||||
|
} |
||||
|
const prop = item && item.columnProp |
||||
|
if (!prop || !row) { |
||||
|
return '' |
||||
|
} |
||||
|
if (row[prop] !== undefined && row[prop] !== null) { |
||||
|
return row[prop] |
||||
|
} |
||||
|
if (row.extValues && typeof row.extValues === 'object' && |
||||
|
Object.prototype.hasOwnProperty.call(row.extValues, prop)) { |
||||
|
return row.extValues[prop] |
||||
|
} |
||||
|
return '' |
||||
|
}, |
||||
|
|
||||
|
buildQueryRequest() { |
||||
|
return buildPoOrderQueryParams({ |
||||
|
searchData: this.searchData, |
||||
|
advancedQueryData: this.advancedQueryData, |
||||
|
page: this.pageIndex, |
||||
|
limit: this.pageSize |
||||
|
}) |
||||
|
}, |
||||
|
|
||||
|
handleSearch() { |
||||
|
if (!this.searchData.customer) { |
||||
|
this.$message.warning('Please select Customer first') |
||||
|
return |
||||
|
} |
||||
|
this.pageIndex = 1 |
||||
|
this.getDataList() |
||||
|
}, |
||||
|
|
||||
|
onSessionCustomerChange (customer) { |
||||
|
this.searchData.customer = customer |
||||
|
this.advancedQueryData.rows = [] |
||||
|
this.pageIndex = 1 |
||||
|
this.dataList = [] |
||||
|
this.totalPage = 0 |
||||
|
this.currentRow = {} |
||||
|
this.clearDetailTabs() |
||||
|
if (!customer) { |
||||
|
this.fieldSchemaFields = [] |
||||
|
this.advancedQueryData.rows = [] |
||||
|
this.refreshTableLayout() |
||||
|
return |
||||
|
} |
||||
|
this.loadFieldSchema(customer).then(() => { |
||||
|
this.getDataList() |
||||
|
}) |
||||
|
}, |
||||
|
|
||||
|
loadFieldSchema (customer) { |
||||
|
return getPoFieldSchema({ |
||||
|
site: this.searchData.site, |
||||
|
customer, |
||||
|
scene: 'list' |
||||
|
}).then(({ data }) => { |
||||
|
if (data && data.code === 0 && data.data) { |
||||
|
this.fieldSchemaFields = data.data.fields || [] |
||||
|
const queryFields = getAdvancedQueryFieldsFromSchema(this.fieldSchemaFields) |
||||
|
this.advancedQueryData.rows = createAdvancedQueryDataFromSchema(queryFields).rows |
||||
|
} else { |
||||
|
this.fieldSchemaFields = [] |
||||
|
this.advancedQueryData.rows = [] |
||||
|
this.$message.error((data && data.msg) || 'Failed to load field permissions') |
||||
|
} |
||||
|
this.refreshTableLayout() |
||||
|
}).catch(() => { |
||||
|
this.fieldSchemaFields = [] |
||||
|
this.advancedQueryData.rows = [] |
||||
|
this.$message.error('Failed to load field permissions') |
||||
|
this.refreshTableLayout() |
||||
|
}) |
||||
|
}, |
||||
|
|
||||
|
handleListResponse(data) { |
||||
|
if (data.code === 0) { |
||||
|
this.dataList = ((data.page && data.page.list) || []).map(row => normalizeSchemaRowValues(row)) |
||||
|
this.pageIndex = data.page.currPage |
||||
|
this.pageSize = data.page.pageSize |
||||
|
this.totalPage = data.page.totalCount |
||||
|
|
||||
|
if (this.dataList.length > 0) { |
||||
|
this.$nextTick(() => { |
||||
|
if (this.$refs.poTable) { |
||||
|
this.$refs.poTable.setCurrentRow(this.dataList[0]) |
||||
|
} |
||||
|
this.changeData(this.dataList[0]) |
||||
|
}) |
||||
|
} else { |
||||
|
this.currentRow = {} |
||||
|
this.clearDetailTabs() |
||||
|
} |
||||
|
} else { |
||||
|
this.$message.error((data && data.msg) || 'Failed to get list') |
||||
|
} |
||||
|
}, |
||||
|
|
||||
|
getDataList() { |
||||
|
if (!this.searchData.customer) { |
||||
|
this.loading = false |
||||
|
this.dataList = [] |
||||
|
this.totalPage = 0 |
||||
|
this.currentRow = {} |
||||
|
this.clearDetailTabs() |
||||
|
this.refreshTableLayout() |
||||
|
return |
||||
|
} |
||||
|
this.loading = true |
||||
|
const { params, useAdvanced } = this.buildQueryRequest() |
||||
|
const request = useAdvanced ? searchPoDetailAdvancedPage(params) : searchPoDetailPage(params) |
||||
|
request.then(({ data }) => { |
||||
|
this.handleListResponse(data) |
||||
|
this.loading = false |
||||
|
this.refreshTableLayout() |
||||
|
}).catch(() => { |
||||
|
this.loading = false |
||||
|
this.$message.error('Request failed') |
||||
|
this.refreshTableLayout() |
||||
|
}) |
||||
|
}, |
||||
|
|
||||
|
/** External reset: only clears top basic conditions, not advancedQueryData */ |
||||
|
resetSearch() { |
||||
|
const currentCustomer = this.searchData.customer |
||||
|
this.searchData = { |
||||
|
site: this.$store.state.user.site, |
||||
|
customer: currentCustomer, |
||||
|
buyer: '', |
||||
|
poNo: '', |
||||
|
orderType: '', |
||||
|
partNo: '', |
||||
|
supplierNo: '', |
||||
|
sku: '', |
||||
|
status: '', |
||||
|
supplierName: '', |
||||
|
feeDateStart: '', |
||||
|
feeDateEnd: '' |
||||
|
} |
||||
|
this.pageIndex = 1 |
||||
|
this.getDataList() |
||||
|
}, |
||||
|
|
||||
|
openSearchBaseList (val) { |
||||
|
this.eamTagNo = val |
||||
|
let strVal = '' |
||||
|
let conSql = '' |
||||
|
if (val === 520) { |
||||
|
strVal = this.searchData.supplierNo || '' |
||||
|
conSql = " and supplier_no <> '' " |
||||
|
} else if (val === 2017) { |
||||
|
strVal = this.searchData.partNo || '' |
||||
|
conSql = " and part_no <> '' " |
||||
|
} |
||||
|
this.$nextTick(() => { |
||||
|
this.$refs.eamList.init(val, strVal, conSql) |
||||
|
}) |
||||
|
}, |
||||
|
|
||||
|
getEamData (val) { |
||||
|
if (this.eamTagNo === 520) { |
||||
|
this.searchData.supplierNo = val.supplier_no || val.code || '' |
||||
|
this.searchData.supplierName = val.supplier_name || val.name || '' |
||||
|
} else if (this.eamTagNo === 2017) { |
||||
|
this.searchData.partNo = val.part_no || val.code || '' |
||||
|
} |
||||
|
this.eamTagNo = '' |
||||
|
}, |
||||
|
// Export |
||||
|
exportExcel () { |
||||
|
if (!this.searchData.customer) { |
||||
|
this.$message.warning('Please select Customer first') |
||||
|
return |
||||
|
} |
||||
|
const now = new Date() |
||||
|
const year = now.getFullYear() |
||||
|
const month = String(now.getMonth() + 1).padStart(2, '0') |
||||
|
const day = String(now.getDate()).padStart(2, '0') |
||||
|
const hour = String(now.getHours()).padStart(2, '0') |
||||
|
const minute = String(now.getMinutes()).padStart(2, '0') |
||||
|
const second = String(now.getSeconds()).padStart(2, '0') |
||||
|
const exportName = `PO Order List ${year}${month}${day}${hour}${minute}${second}` |
||||
|
|
||||
|
const { params, useAdvanced } = buildPoOrderQueryParams({ |
||||
|
searchData: this.searchData, |
||||
|
advancedQueryData: this.advancedQueryData, |
||||
|
page: 1, |
||||
|
limit: 99999 |
||||
|
}) |
||||
|
|
||||
|
try { |
||||
|
excel.exportTable({ |
||||
|
url: useAdvanced ? 'pODetail/advancedPage' : 'pODetail/page', |
||||
|
columnMapping: this.visibleColumns, |
||||
|
mergeSetting: [], |
||||
|
params, |
||||
|
fileName: exportName + '.xlsx', |
||||
|
rowFetcher: res => { |
||||
|
const page = res.data && res.data.page |
||||
|
const rows = ((page && page.list) || []).map(row => normalizeSchemaRowValues(row)) |
||||
|
return { rows } |
||||
|
}, |
||||
|
columnFormatter: [], |
||||
|
dropColumns: [] |
||||
|
}) |
||||
|
} catch (error) { |
||||
|
this.$message.error('Export failed: ' + error.message) |
||||
|
} |
||||
|
}, |
||||
|
|
||||
|
// Page size |
||||
|
sizeChangeHandle(val) { |
||||
|
this.pageSize = val |
||||
|
this.pageIndex = 1 |
||||
|
this.getDataList() |
||||
|
}, |
||||
|
|
||||
|
// Current page |
||||
|
currentChangeHandle(val) { |
||||
|
this.pageIndex = val |
||||
|
this.getDataList() |
||||
|
}, |
||||
|
|
||||
|
// Row click event (similar to supplierList.vue changeData pattern) |
||||
|
changeData(row) { |
||||
|
if (!row) { |
||||
|
this.currentRow = {} |
||||
|
this.clearDetailTabs() |
||||
|
return |
||||
|
} |
||||
|
this.currentRow = JSON.parse(JSON.stringify(row)) |
||||
|
this.refreshCurrentTabTable() |
||||
|
}, |
||||
|
|
||||
|
// Refresh current tab table data (similar to supplierList.vue refreshCurrentTabTable) |
||||
|
refreshCurrentTabTable() { |
||||
|
if (!this.hasCurrentRowData()) { |
||||
|
this.clearDetailTabs() |
||||
|
return |
||||
|
} |
||||
|
if (this.activeTab === 'orderDetail') { |
||||
|
// Order detail does not need refresh, display currentRow directly |
||||
|
} |
||||
|
if (this.activeTab === 'logistics') { |
||||
|
this.refreshLogisticsTable() |
||||
|
} |
||||
|
if (this.activeTab === 'inspectionDetail') { |
||||
|
this.refreshInspectionTable() |
||||
|
} |
||||
|
if (this.activeTab === 'partAttribute') { |
||||
|
this.refreshPartAttribute() |
||||
|
} |
||||
|
}, |
||||
|
getDetailTabHeight () { |
||||
|
return Number(this.height) - 20 |
||||
|
}, |
||||
|
hasCurrentRowData () { |
||||
|
return !!(this.currentRow && typeof this.currentRow === 'object' && Object.keys(this.currentRow).length > 0) |
||||
|
}, |
||||
|
clearDetailTabs () { |
||||
|
const site = this.searchData.site || this.$store.state.user.site |
||||
|
const height = this.getDetailTabHeight() |
||||
|
if (this.$refs.logisticsPoList && this.$refs.logisticsPoList.init) { |
||||
|
this.$refs.logisticsPoList.init({ |
||||
|
flexId: '', |
||||
|
supplierNo: '', |
||||
|
site, |
||||
|
height |
||||
|
}) |
||||
|
} |
||||
|
if (this.$refs.inspectionDetailList && this.$refs.inspectionDetailList.init) { |
||||
|
this.$refs.inspectionDetailList.init({ |
||||
|
site, |
||||
|
orderNo: '', |
||||
|
itemNo: null, |
||||
|
height |
||||
|
}) |
||||
|
} |
||||
|
if (this.$refs.partAttributeTab && this.$refs.partAttributeTab.init) { |
||||
|
this.$refs.partAttributeTab.init({ |
||||
|
site, |
||||
|
partNo: '', |
||||
|
codeNo: '', |
||||
|
functionType: 'P', |
||||
|
height |
||||
|
}) |
||||
|
} |
||||
|
}, |
||||
|
|
||||
|
// Refresh logistics tab table (similar to supplierList.vue refreshShareTable) |
||||
|
refreshLogisticsTable() { |
||||
|
if (!this.hasCurrentRowData()) { |
||||
|
this.clearDetailTabs() |
||||
|
return |
||||
|
} |
||||
|
let inData = { |
||||
|
flexId: this.currentRow.flexid, |
||||
|
supplierNo: this.currentRow.supplierNo, |
||||
|
site: this.$store.state.user.site, |
||||
|
height: this.getDetailTabHeight() |
||||
|
} |
||||
|
this.$refs.logisticsPoList.init(inData) |
||||
|
}, |
||||
|
|
||||
|
// Refresh inspection detail tab table |
||||
|
refreshInspectionTable() { |
||||
|
if (!this.hasCurrentRowData()) { |
||||
|
this.clearDetailTabs() |
||||
|
return |
||||
|
} |
||||
|
let inData = { |
||||
|
site: this.$store.state.user.site, |
||||
|
orderNo: this.currentRow.orderNo || '', |
||||
|
itemNo: this.currentRow.itemNo || null, |
||||
|
height: this.getDetailTabHeight() |
||||
|
} |
||||
|
this.$refs.inspectionDetailList.init(inData) |
||||
|
}, |
||||
|
refreshPartAttribute () { |
||||
|
if (!this.hasCurrentRowData()) { |
||||
|
this.clearDetailTabs() |
||||
|
return |
||||
|
} |
||||
|
const site = this.currentRow.site || this.$store.state.user.site |
||||
|
const partNo = this.currentRow.partNo || '' |
||||
|
const inData = { |
||||
|
site, |
||||
|
partNo, |
||||
|
codeNo: this.currentRow.codeNo || '', |
||||
|
functionType: 'P', |
||||
|
height: this.getDetailTabHeight() |
||||
|
} |
||||
|
if (!partNo) { |
||||
|
this.initPartAttributeTab(inData) |
||||
|
return |
||||
|
} |
||||
|
if (inData.codeNo) { |
||||
|
this.initPartAttributeTab(inData) |
||||
|
return |
||||
|
} |
||||
|
searchPartInfo({ site, partNo }).then(({ data }) => { |
||||
|
const codeNo = (data && data.code === 0 && data.data) |
||||
|
? (data.data.codeNo || data.data.code_no || '') |
||||
|
: '' |
||||
|
this.$set(this.currentRow, 'codeNo', codeNo) |
||||
|
this.initPartAttributeTab({ |
||||
|
...inData, |
||||
|
codeNo |
||||
|
}) |
||||
|
}).catch(() => { |
||||
|
this.initPartAttributeTab(inData) |
||||
|
}) |
||||
|
}, |
||||
|
initPartAttributeTab (inData) { |
||||
|
if (this.$refs.partAttributeTab && this.$refs.partAttributeTab.init) { |
||||
|
this.$refs.partAttributeTab.init(inData) |
||||
|
} |
||||
|
}, |
||||
|
|
||||
|
// Tab click event (similar to supplierList.vue tabClick) |
||||
|
handleTabClick(tab, event) { |
||||
|
this.refreshCurrentTabTable() |
||||
|
} |
||||
|
} |
||||
|
} |
||||
|
</script> |
||||
|
|
||||
|
<style scoped lang="scss"> |
||||
|
.el-table /deep/ .cell { |
||||
|
height: auto; |
||||
|
line-height: 1.5; |
||||
|
} |
||||
|
|
||||
|
/deep/ .customer-tab .el-tabs__content { |
||||
|
padding: 5px !important; |
||||
|
} |
||||
|
</style> |
||||
Write
Preview
Loading…
Cancel
Save
Reference in new issue