mirror of
https://github.com/rnvm9wjdtj-bot/myaps_api.git
synced 2026-06-02 05:54:40 +00:00
mds页面整合
This commit is contained in:
@@ -368,6 +368,105 @@ INTERNAL_FIELDS = {'memo', 'sys_user', 'sys_date', 'sys_stamp'}
|
||||
EXCLUDE_FIELDS = ['_createtime', '_updatetime', 'sys_date', 'sys_stamp']
|
||||
|
||||
|
||||
def extract_all_fields(schema_class, model_class) -> List[Dict[str, Any]]:
|
||||
"""
|
||||
从Schema和Model提取完整的字段元数据
|
||||
|
||||
Args:
|
||||
schema_class: Pydantic Schema类
|
||||
model_class: Tortoise Model类
|
||||
|
||||
Returns:
|
||||
字段元数据列表
|
||||
"""
|
||||
fields = []
|
||||
|
||||
if not schema_class or not model_class:
|
||||
return fields
|
||||
|
||||
# 获取字段映射
|
||||
field_map = get_field_map(model_class)
|
||||
|
||||
for field_name, field_info in schema_class.model_fields.items():
|
||||
if field_name.startswith('_'):
|
||||
continue
|
||||
|
||||
# 判断字段类型
|
||||
annotation = field_info.annotation
|
||||
data_type = 'string'
|
||||
|
||||
# 判断数据类型
|
||||
if isinstance(annotation, type):
|
||||
if issubclass(annotation, (int, float)):
|
||||
data_type = 'number'
|
||||
elif issubclass(annotation, Enum):
|
||||
data_type = 'enum'
|
||||
|
||||
# 获取枚举选项
|
||||
enum_options = None
|
||||
if data_type == 'enum' and hasattr(annotation, 'get_options'):
|
||||
enum_options = annotation.get_options()
|
||||
|
||||
# 判断是否必填
|
||||
is_required = field_info.is_required()
|
||||
|
||||
# 获取范围约束
|
||||
ge = getattr(field_info, 'ge', None)
|
||||
gt = getattr(field_info, 'gt', None)
|
||||
le = getattr(field_info, 'le', None)
|
||||
lt = getattr(field_info, 'lt', None)
|
||||
|
||||
# 获取最大长度
|
||||
max_length = getattr(field_info, 'max_length', None)
|
||||
|
||||
# 获取描述
|
||||
description = field_info.description or field_name
|
||||
|
||||
# 构建字段元数据
|
||||
field_meta = {
|
||||
"field": field_name,
|
||||
"title": description,
|
||||
"description": description,
|
||||
"data_type": data_type,
|
||||
"is_required": is_required,
|
||||
"is_internal": False,
|
||||
"enum_options": enum_options,
|
||||
"range": {
|
||||
"ge": ge,
|
||||
"gt": gt,
|
||||
"le": le,
|
||||
"lt": lt
|
||||
},
|
||||
"max_length": max_length
|
||||
}
|
||||
|
||||
fields.append(field_meta)
|
||||
|
||||
# 添加内部字段
|
||||
internal_fields_config = {
|
||||
'_staging_id', '_source_system', '_source_id', '_status',
|
||||
'_error_msg', '_transform_rules', '_retry_count',
|
||||
'_createtime', '_updatetime', '_synced_id', '_synced_time'
|
||||
}
|
||||
|
||||
for field_name in internal_fields_config:
|
||||
if field_name in model_class._meta.fields_map:
|
||||
field = model_class._meta.fields_map[field_name]
|
||||
fields.append({
|
||||
"field": field_name,
|
||||
"title": field.description or field_name,
|
||||
"description": field.description or field_name,
|
||||
"data_type": 'string',
|
||||
"is_required": False,
|
||||
"is_internal": True,
|
||||
"enum_options": None,
|
||||
"range": None,
|
||||
"max_length": None
|
||||
})
|
||||
|
||||
return fields
|
||||
|
||||
|
||||
def generate_validation_rules_doc(table_key: str, config: Dict) -> Dict[str, Any]:
|
||||
"""
|
||||
生成完整的校验规则文档
|
||||
@@ -386,6 +485,7 @@ def generate_validation_rules_doc(table_key: str, config: Dict) -> Dict[str, Any
|
||||
doc = {
|
||||
"table_name": extract_display_name_from_model(model_class),
|
||||
"table_key": table_key,
|
||||
"fields": [],
|
||||
|
||||
"required_fields": [],
|
||||
"enum_fields": [],
|
||||
@@ -396,6 +496,10 @@ def generate_validation_rules_doc(table_key: str, config: Dict) -> Dict[str, Any
|
||||
"business_keys": []
|
||||
}
|
||||
|
||||
# 完整字段元数据
|
||||
if schema_class and model_class:
|
||||
doc["fields"] = extract_all_fields(schema_class, model_class)
|
||||
|
||||
# 必填字段
|
||||
if schema_class:
|
||||
required_fields = extract_required_fields(schema_class)
|
||||
|
||||
+72
-21
@@ -9,6 +9,71 @@ import os
|
||||
|
||||
BASE_DIR = os.path.dirname(os.path.dirname(os.path.abspath(__file__)))
|
||||
|
||||
# MDS 页面配置字典
|
||||
MDS_PAGE_CONFIG = {
|
||||
"material": {
|
||||
"page_title": "物料数据清洗管理",
|
||||
"keyword_placeholder": "搜索物料号或描述...",
|
||||
"config_file": "material.config.js"
|
||||
},
|
||||
"workcenter": {
|
||||
"page_title": "工作中心数据清洗管理",
|
||||
"keyword_placeholder": "搜索工作中心或描述...",
|
||||
"config_file": "workcenter.config.js"
|
||||
},
|
||||
"mat-ver": {
|
||||
"page_title": "产线版本数据清洗管理",
|
||||
"keyword_placeholder": "搜索物料号或版本号...",
|
||||
"config_file": "mat-ver.config.js"
|
||||
},
|
||||
"mat-wc": {
|
||||
"page_title": "工艺路线数据清洗管理",
|
||||
"keyword_placeholder": "搜索物料号或工作中心...",
|
||||
"config_file": "mat-wc.config.js"
|
||||
},
|
||||
"mat-wc-bom": {
|
||||
"page_title": "BOM数据清洗管理",
|
||||
"keyword_placeholder": "搜索父件或子件料号...",
|
||||
"config_file": "mat-wc-bom.config.js"
|
||||
},
|
||||
"mold": {
|
||||
"page_title": "模具数据清洗管理",
|
||||
"keyword_placeholder": "搜索模具编号或描述...",
|
||||
"config_file": "mold.config.js"
|
||||
},
|
||||
"mat-wc-mold": {
|
||||
"page_title": "机台模具数据清洗管理",
|
||||
"keyword_placeholder": "搜索物料号或模具编号...",
|
||||
"config_file": "mat-wc-mold.config.js"
|
||||
}
|
||||
}
|
||||
|
||||
def render_mds_page(page_key):
|
||||
"""使用模板渲染MDS页面"""
|
||||
template_path = os.path.join(BASE_DIR, "static", "mds", "pages", "template.html")
|
||||
with open(template_path, "r", encoding="utf-8") as f:
|
||||
template = f.read()
|
||||
|
||||
config = MDS_PAGE_CONFIG[page_key]
|
||||
|
||||
# 准备替换变量
|
||||
replacements = {
|
||||
"{page_title}": config["page_title"],
|
||||
"{keyword_placeholder}": config["keyword_placeholder"],
|
||||
"{config_file}": config["config_file"]
|
||||
}
|
||||
|
||||
# 设置导航栏高亮
|
||||
for key in MDS_PAGE_CONFIG.keys():
|
||||
replacements[f"{{{key.replace('-', '_')}_active}}"] = "active" if key == page_key else ""
|
||||
|
||||
# 执行替换
|
||||
html = template
|
||||
for old, new in replacements.items():
|
||||
html = html.replace(old, new)
|
||||
|
||||
return html
|
||||
|
||||
|
||||
router = APIRouter()
|
||||
|
||||
@@ -55,42 +120,28 @@ def register_routes(app):
|
||||
|
||||
@app.get("/mds/material", response_class=HTMLResponse, include_in_schema=False)
|
||||
async def mds_material():
|
||||
file_path = os.path.join(BASE_DIR, "static", "mds", "pages", "material.html")
|
||||
with open(file_path, "r", encoding="utf-8") as f:
|
||||
return f.read()
|
||||
return render_mds_page("material")
|
||||
|
||||
@app.get("/mds/workcenter", response_class=HTMLResponse, include_in_schema=False)
|
||||
async def mds_workcenter():
|
||||
file_path = os.path.join(BASE_DIR, "static", "mds", "pages", "workcenter.html")
|
||||
with open(file_path, "r", encoding="utf-8") as f:
|
||||
return f.read()
|
||||
return render_mds_page("workcenter")
|
||||
|
||||
@app.get("/mds/mat-ver", response_class=HTMLResponse, include_in_schema=False)
|
||||
async def mds_mat_ver():
|
||||
file_path = os.path.join(BASE_DIR, "static", "mds", "pages", "mat-ver.html")
|
||||
with open(file_path, "r", encoding="utf-8") as f:
|
||||
return f.read()
|
||||
return render_mds_page("mat-ver")
|
||||
|
||||
@app.get("/mds/mat-wc", response_class=HTMLResponse, include_in_schema=False)
|
||||
async def mds_mat_wc():
|
||||
file_path = os.path.join(BASE_DIR, "static", "mds", "pages", "mat-wc.html")
|
||||
with open(file_path, "r", encoding="utf-8") as f:
|
||||
return f.read()
|
||||
return render_mds_page("mat-wc")
|
||||
|
||||
@app.get("/mds/mat-wc-bom", response_class=HTMLResponse, include_in_schema=False)
|
||||
async def mds_mat_wc_bom():
|
||||
file_path = os.path.join(BASE_DIR, "static", "mds", "pages", "mat-wc-bom.html")
|
||||
with open(file_path, "r", encoding="utf-8") as f:
|
||||
return f.read()
|
||||
return render_mds_page("mat-wc-bom")
|
||||
|
||||
@app.get("/mds/mold", response_class=HTMLResponse, include_in_schema=False)
|
||||
async def mds_mold():
|
||||
file_path = os.path.join(BASE_DIR, "static", "mds", "pages", "mold.html")
|
||||
with open(file_path, "r", encoding="utf-8") as f:
|
||||
return f.read()
|
||||
return render_mds_page("mold")
|
||||
|
||||
@app.get("/mds/mat-wc-mold", response_class=HTMLResponse, include_in_schema=False)
|
||||
async def mds_mat_wc_mold():
|
||||
file_path = os.path.join(BASE_DIR, "static", "mds", "pages", "mat-wc-mold.html")
|
||||
with open(file_path, "r", encoding="utf-8") as f:
|
||||
return f.read()
|
||||
return render_mds_page("mat-wc-mold")
|
||||
|
||||
+207
-1
@@ -1094,6 +1094,7 @@ async def batch_update_staging(request: Request, table_name: str, data: dict = B
|
||||
| 2026-05-13 | v2.5 | 重大更新:多账套同步支持、前端内存泄漏修复、None值累加全面修复、错误信息格式统一、刷新同步逻辑优化 |
|
||||
| 2026-05-14 | v3.0 | **架构级重构**:校验逻辑从硬编码转为配置驱动,通过Pydantic Schema自动提取校验规则,大幅提升可维护性和扩展性 |
|
||||
| 2026-05-15 | v3.1 | **两阶段校验增强**:新增合规性校验、关联校验分阶段处理,新增校验规则文档化API,完善前端通用组件库 |
|
||||
| 2026-05-15 | v3.2 | **前端架构重构**:通用控制器 + 配置驱动,所有表共用同一套代码,新增表只需编写配置文件 |
|
||||
|
||||
---
|
||||
|
||||
@@ -1841,7 +1842,212 @@ stats["rejected"] = stats.get("compliance_error", 0) + stats.get("relation_error
|
||||
|
||||
---
|
||||
|
||||
## 十二、v2.3版本更新详情
|
||||
## 十二、v3.2版本更新详情
|
||||
|
||||
### 12.1 前端架构重构概览
|
||||
|
||||
**核心设计理念**:所有表共用同一套代码,新增表只需编写配置文件。
|
||||
|
||||
**架构演进**:
|
||||
|
||||
| 阶段 | 实现方式 | 新增表成本 |
|
||||
|------|----------|------------|
|
||||
| v2.5- | 每个表单独编写JS + HTML | 数百行代码 |
|
||||
| v3.0 | 配置驱动后端校验 | 数行配置 |
|
||||
| v3.2 | 配置驱动前后端 | 仅需配置文件 |
|
||||
|
||||
### 12.2 配置文件设计
|
||||
|
||||
**新增配置目录**:`static/mds/configs/`
|
||||
|
||||
**配置文件结构**:
|
||||
|
||||
```javascript
|
||||
// material.config.js
|
||||
const MDS_PAGE_CONFIG = {
|
||||
tableKey: 't_material',
|
||||
tableDisplayName: '物料',
|
||||
|
||||
display: {
|
||||
columns: [
|
||||
{ field: '_status', title: '状态', width: '80px' },
|
||||
{ field: '_createtime', title: '创建时间', width: '180px', sortable: true },
|
||||
{ field: 'materialno', title: '物料号', width: '100px', sortable: true },
|
||||
{ field: 'description', title: '物料描述', width: '150px' },
|
||||
// ... 更多字段
|
||||
],
|
||||
defaultSortField: '_createtime',
|
||||
defaultSortDir: 'desc',
|
||||
|
||||
advancedFilterCategories: {
|
||||
stringFields: [...],
|
||||
enumFields: [...],
|
||||
dateFields: [...]
|
||||
}
|
||||
},
|
||||
|
||||
edit: {
|
||||
fields: [...]
|
||||
}
|
||||
};
|
||||
```
|
||||
|
||||
**配置文件清单**:
|
||||
|
||||
| 配置文件 | 对应表 |
|
||||
|----------|--------|
|
||||
| `material.config.js` | t_material |
|
||||
| `workcenter.config.js` | t_workcenter |
|
||||
| `mat-ver.config.js` | t_mat_ver |
|
||||
| `mat-wc.config.js` | t_mat_wc |
|
||||
| `mat-wc-bom.config.js` | t_mat_wc_bom |
|
||||
| `mold.config.js` | t_mold |
|
||||
| `mat-wc-mold.config.js` | t_mat_wc_mold |
|
||||
|
||||
### 12.3 通用页面控制器
|
||||
|
||||
**新增核心文件**:`mds-page-controller.js`(1219行)
|
||||
|
||||
**控制器架构**:
|
||||
|
||||
```javascript
|
||||
class MDSPageController {
|
||||
constructor(config) {
|
||||
this.config = config;
|
||||
this.tableKey = config.tableKey;
|
||||
this.tableDisplayName = config.tableDisplayName;
|
||||
|
||||
this.tableMeta = null;
|
||||
this.dataTable = null;
|
||||
this.statusCard = null;
|
||||
|
||||
this.fieldValues = {};
|
||||
this.nullFields = new Set();
|
||||
|
||||
this.init();
|
||||
}
|
||||
|
||||
async init() {
|
||||
await this.loadTableMeta();
|
||||
this.initStatusCard();
|
||||
this.initDataTable();
|
||||
this.bindEvents();
|
||||
}
|
||||
|
||||
// 从 /rules/{tableKey} API 加载校验规则元数据
|
||||
async loadTableMeta() {
|
||||
const response = await callApi(`/rules/${this.tableKey}`);
|
||||
if (response.success === 1) {
|
||||
this.tableMeta = response.data;
|
||||
}
|
||||
}
|
||||
|
||||
// 动态获取字段信息(从API元数据或配置文件)
|
||||
getFieldLabel(fieldName) { ... }
|
||||
getFieldType(fieldName) { ... }
|
||||
getEnumOptions(fieldName) { ... }
|
||||
isRequiredField(fieldName) { ... }
|
||||
|
||||
// 核心功能
|
||||
loadData() { ... }
|
||||
validateData() { ... }
|
||||
approveData() { ... }
|
||||
syncToProduction() { ... }
|
||||
}
|
||||
```
|
||||
|
||||
**核心特性**:
|
||||
|
||||
1. **元数据驱动**:从 `/rules/{tableKey}` API 动态加载字段信息、枚举选项、必填字段
|
||||
2. **配置驱动**:表特定配置(列定义、排序、筛选等)完全外部化
|
||||
3. **完整功能**:数据加载、校验、审批、同步、编辑、删除等所有功能通用化
|
||||
4. **模板页面**:`template.html` 作为所有表的统一入口
|
||||
|
||||
### 12.4 页面模板化
|
||||
|
||||
**文件变更**:
|
||||
|
||||
| 变更 | 说明 |
|
||||
|------|------|
|
||||
| 重命名 | `material.html` → `template.html` |
|
||||
| 删除 | mat-ver.html、mat-wc-bom.html、mat-wc-mold.html、mat-wc.html、mold.html、workcenter.html |
|
||||
|
||||
**模板页面使用**:
|
||||
|
||||
```html
|
||||
<!-- template.html -->
|
||||
<!DOCTYPE html>
|
||||
<html>
|
||||
<head>
|
||||
<title>MDS - {{config.tableDisplayName}}</title>
|
||||
<!-- 通用资源引用 -->
|
||||
<script src="../configs/{{tableKey}}.config.js"></script>
|
||||
<script src="../js/mds-page-controller.js"></script>
|
||||
</head>
|
||||
<body>
|
||||
<!-- 通用模板结构 -->
|
||||
</body>
|
||||
</html>
|
||||
```
|
||||
|
||||
### 12.5 后端配合更新
|
||||
|
||||
**新增路由**:
|
||||
|
||||
```python
|
||||
# routes_register.py
|
||||
# 新增表的API路由注册
|
||||
```
|
||||
|
||||
**全局常量更新**:
|
||||
|
||||
```python
|
||||
# globalconst.py
|
||||
# 表配置更新
|
||||
```
|
||||
|
||||
### 12.6 新增表开发流程(v3.2版本)
|
||||
|
||||
**新增表只需3步**:
|
||||
|
||||
```
|
||||
1. 后端:定义Schema + 配置 STAGING_TABLE_CONFIG
|
||||
↓
|
||||
2. 前端:编写 {tableKey}.config.js 配置文件
|
||||
↓
|
||||
3. 完成!
|
||||
```
|
||||
|
||||
**对比v2.5版本**:
|
||||
|
||||
| 阶段 | v2.5及之前 | v3.2 |
|
||||
|------|------------|------|
|
||||
| 后端 | 100+行代码 | Schema + 配置 |
|
||||
| 前端 | 500+行代码 | 仅配置文件 |
|
||||
| 总计 | >600行代码 | <100行配置 |
|
||||
|
||||
### 12.7 修改文件清单
|
||||
|
||||
| 文件 | 变更类型 | 核心改动 |
|
||||
|------|----------|----------|
|
||||
| `_base.py` | 优化 | 配合前端重构 |
|
||||
| `routes_register.py` | 优化 | 新增路由注册 |
|
||||
| `globalconst.py` | 优化 | 全局常量更新 |
|
||||
| `mds-page-controller.js` | **新增** | 通用页面控制器(1219行) |
|
||||
| `material.config.js` | **新增** | 物料表配置 |
|
||||
| `workcenter.config.js` | **新增** | 工作中心表配置 |
|
||||
| `mat-ver.config.js` | **新增** | 产线版本表配置 |
|
||||
| `mat-wc.config.js` | **新增** | 工艺路线表配置 |
|
||||
| `mat-wc-bom.config.js` | **新增** | 物料清单表配置 |
|
||||
| `mold.config.js` | **新增** | 模具表配置 |
|
||||
| `mat-wc-mold.config.js` | **新增** | 机台模具关联表配置 |
|
||||
| `material.js` | 优化 | 简化为配置驱动 |
|
||||
| `template.html` | **重命名** | `material.html` → `template.html` |
|
||||
| 5个旧页面文件 | **删除** | 不再需要单独的页面文件 |
|
||||
|
||||
---
|
||||
|
||||
## 十三、v2.3版本更新详情
|
||||
|
||||
### 9.1 校验错误详情展示
|
||||
|
||||
|
||||
@@ -10,6 +10,13 @@ NONE_AND_EMPTY = {None, ""}
|
||||
class YesNoEnum(str, Enum):
|
||||
YES = "Y"
|
||||
NO = "N"
|
||||
|
||||
@classmethod
|
||||
def get_options(cls):
|
||||
return [
|
||||
{"value": "Y", "label": "是(Y)"},
|
||||
{"value": "N", "label": "否(N)"}
|
||||
]
|
||||
|
||||
|
||||
class LotSizeEnum(str, Enum):
|
||||
@@ -29,11 +36,39 @@ class LotSizeEnum(str, Enum):
|
||||
M1 = "M1" # 按1月合并
|
||||
M2 = "M2" # 按2月合并
|
||||
M3 = "M3" # 按3月合并
|
||||
|
||||
@classmethod
|
||||
def get_options(cls):
|
||||
return [
|
||||
{"value": "EX", "label": "一对一(EX)"},
|
||||
{"value": "FX", "label": "固定批(FX)"},
|
||||
{"value": "VB", "label": "重订货点(VB)"},
|
||||
{"value": "D1", "label": "按1天合并(D1)"},
|
||||
{"value": "D2", "label": "按2天合并(D2)"},
|
||||
{"value": "D3", "label": "按3天合并(D3)"},
|
||||
{"value": "D4", "label": "按4天合并(D4)"},
|
||||
{"value": "D5", "label": "按5天合并(D5)"},
|
||||
{"value": "D6", "label": "按6天合并(D6)"},
|
||||
{"value": "W1", "label": "按1周合并(W1)"},
|
||||
{"value": "W2", "label": "按2周合并(W2)"},
|
||||
{"value": "W3", "label": "按3周合并(W3)"},
|
||||
{"value": "W4", "label": "按4周合并(W4)"},
|
||||
{"value": "M1", "label": "按1月合并(M1)"},
|
||||
{"value": "M2", "label": "按2月合并(M2)"},
|
||||
{"value": "M3", "label": "按3月合并(M3)"}
|
||||
]
|
||||
|
||||
|
||||
class ProductCategoryEnum(str, Enum):
|
||||
MTO = "MTO" # MTO
|
||||
MTS = "MTS" # MTS
|
||||
|
||||
@classmethod
|
||||
def get_options(cls):
|
||||
return [
|
||||
{"value": "MTO", "label": "按订单生产(MTO)"},
|
||||
{"value": "MTS", "label": "按库存生产(MTS)"}
|
||||
]
|
||||
|
||||
|
||||
class SupplyTypeEnum(str, Enum):
|
||||
@@ -67,16 +102,38 @@ class AbcEnum(str, Enum):
|
||||
A = "A"
|
||||
B = "B"
|
||||
C = "C"
|
||||
|
||||
@classmethod
|
||||
def get_options(cls):
|
||||
return [
|
||||
{"value": "A", "label": "A类"},
|
||||
{"value": "B", "label": "B类"},
|
||||
{"value": "C", "label": "C类"}
|
||||
]
|
||||
|
||||
|
||||
class EfEnum(str, Enum):
|
||||
E = "E"
|
||||
F = "F"
|
||||
|
||||
@classmethod
|
||||
def get_options(cls):
|
||||
return [
|
||||
{"value": "E", "label": "自制件(E)"},
|
||||
{"value": "F", "label": "采购件(F)"}
|
||||
]
|
||||
|
||||
|
||||
class SfEnum(str, Enum):
|
||||
S = "S"
|
||||
F = "F"
|
||||
|
||||
@classmethod
|
||||
def get_options(cls):
|
||||
return [
|
||||
{"value": "S", "label": "S"},
|
||||
{"value": "F", "label": "F"}
|
||||
]
|
||||
|
||||
|
||||
class StaticString(str, Enum):
|
||||
|
||||
@@ -0,0 +1,39 @@
|
||||
const MDS_PAGE_CONFIG = {
|
||||
tableKey: 't_mat_ver',
|
||||
tableDisplayName: '产线版本',
|
||||
|
||||
display: {
|
||||
columns: [
|
||||
{ field: '_status', title: '状态', width: '80px' },
|
||||
{ field: '_createtime', title: '创建时间', width: '180px', sortable: true },
|
||||
{ field: 'materialno', title: '物料号', width: '120px', sortable: true },
|
||||
{ field: 'matver', title: '版本号', width: '80px', sortable: true },
|
||||
{ field: 'description', title: '描述', width: '200px' },
|
||||
{ field: 'active', title: '激活', width: '80px' },
|
||||
{ field: 'lotfrom', title: '批量下限', width: '100px' },
|
||||
{ field: 'lotto', title: '批量上限', width: '100px' },
|
||||
{ field: '_source_system', title: '来源', width: '80px' }
|
||||
],
|
||||
|
||||
defaultSortField: '_createtime',
|
||||
defaultSortDir: 'desc',
|
||||
|
||||
advancedFilterCategories: {
|
||||
stringFields: [
|
||||
{ value: 'MaterialNo', label: '物料号' },
|
||||
{ value: 'MatVer', label: '版本号' },
|
||||
{ value: 'Description', label: '描述' }
|
||||
],
|
||||
numberFields: [
|
||||
{ value: 'LotFrom', label: '批量下限' },
|
||||
{ value: 'LotTo', label: '批量上限' }
|
||||
],
|
||||
enumFields: [
|
||||
{ value: 'Active', label: '激活', options: [
|
||||
{ value: 'Y', label: '是' },
|
||||
{ value: 'N', label: '否' }
|
||||
]}
|
||||
]
|
||||
}
|
||||
}
|
||||
};
|
||||
@@ -0,0 +1,46 @@
|
||||
const MDS_PAGE_CONFIG = {
|
||||
tableKey: 't_mat_wc_bom',
|
||||
tableDisplayName: 'BOM',
|
||||
|
||||
display: {
|
||||
columns: [
|
||||
{ field: '_status', title: '状态', width: '80px' },
|
||||
{ field: '_createtime', title: '创建时间', width: '180px', sortable: true },
|
||||
{ field: 'productno', title: '父件料号', width: '120px', sortable: true },
|
||||
{ field: 'matver', title: '版本号', width: '80px' },
|
||||
{ field: 'itemno', title: '工序号', width: '80px' },
|
||||
{ field: 'materialno', title: '子件料号', width: '120px' },
|
||||
{ field: 'qty', title: '用量', width: '100px' },
|
||||
{ field: 'scrap', title: '损耗率', width: '80px' },
|
||||
{ field: 'mto', title: 'MTO', width: '80px' },
|
||||
{ field: 'alt', title: '替代料', width: '80px' },
|
||||
{ field: '_source_system', title: '来源', width: '80px' }
|
||||
],
|
||||
|
||||
defaultSortField: '_createtime',
|
||||
defaultSortDir: 'desc',
|
||||
|
||||
advancedFilterCategories: {
|
||||
stringFields: [
|
||||
{ value: 'ProductNo', label: '父件料号' },
|
||||
{ value: 'MatVer', label: '版本号' },
|
||||
{ value: 'ItemNo', label: '工序号' },
|
||||
{ value: 'MaterialNo', label: '子件料号' }
|
||||
],
|
||||
numberFields: [
|
||||
{ value: 'Qty', label: '用量' },
|
||||
{ value: 'Scrap', label: '损耗率' }
|
||||
],
|
||||
enumFields: [
|
||||
{ value: 'MTO', label: 'MTO', options: [
|
||||
{ value: 'Y', label: '是' },
|
||||
{ value: 'N', label: '否' }
|
||||
]},
|
||||
{ value: 'Alt', label: '替代料', options: [
|
||||
{ value: 'Y', label: '是' },
|
||||
{ value: 'N', label: '否' }
|
||||
]}
|
||||
]
|
||||
}
|
||||
}
|
||||
};
|
||||
@@ -0,0 +1,35 @@
|
||||
const MDS_PAGE_CONFIG = {
|
||||
tableKey: 't_mat_wc_mold',
|
||||
tableDisplayName: '机台模具',
|
||||
|
||||
display: {
|
||||
columns: [
|
||||
{ field: '_status', title: '状态', width: '80px' },
|
||||
{ field: '_createtime', title: '创建时间', width: '180px', sortable: true },
|
||||
{ field: 'materialno', title: '物料号', width: '120px', sortable: true },
|
||||
{ field: 'workcenter', title: '工作中心', width: '100px' },
|
||||
{ field: 'itemno', title: '工序号', width: '80px' },
|
||||
{ field: 'moldno', title: '模具编号', width: '120px' },
|
||||
{ field: 'basesec', title: 'UPH', width: '100px' },
|
||||
{ field: 'priority', title: '优先级', width: '80px' },
|
||||
{ field: '_source_system', title: '来源', width: '80px' }
|
||||
],
|
||||
|
||||
defaultSortField: '_createtime',
|
||||
defaultSortDir: 'desc',
|
||||
|
||||
advancedFilterCategories: {
|
||||
stringFields: [
|
||||
{ value: 'MaterialNo', label: '物料号' },
|
||||
{ value: 'WorkCenter', label: '工作中心' },
|
||||
{ value: 'ItemNo', label: '工序号' },
|
||||
{ value: 'MoldNo', label: '模具编号' }
|
||||
],
|
||||
numberFields: [
|
||||
{ value: 'BaseSec', label: 'UPH' },
|
||||
{ value: 'Priority', label: '优先级' }
|
||||
],
|
||||
enumFields: []
|
||||
}
|
||||
}
|
||||
};
|
||||
@@ -0,0 +1,41 @@
|
||||
const MDS_PAGE_CONFIG = {
|
||||
tableKey: 't_mat_wc',
|
||||
tableDisplayName: '工艺路线',
|
||||
|
||||
display: {
|
||||
columns: [
|
||||
{ field: '_status', title: '状态', width: '80px' },
|
||||
{ field: '_createtime', title: '创建时间', width: '180px', sortable: true },
|
||||
{ field: 'materialno', title: '物料号', width: '120px', sortable: true },
|
||||
{ field: 'matver', title: '版本号', width: '80px' },
|
||||
{ field: 'itemno', title: '工序号', width: '80px' },
|
||||
{ field: 'workcenter', title: '工作中心', width: '100px' },
|
||||
{ field: 'sf', title: '串并行', width: '80px' },
|
||||
{ field: 'basesec', title: '基础工时', width: '100px' },
|
||||
{ field: 'sortno', title: '排序', width: '80px' },
|
||||
{ field: '_source_system', title: '来源', width: '80px' }
|
||||
],
|
||||
|
||||
defaultSortField: '_createtime',
|
||||
defaultSortDir: 'desc',
|
||||
|
||||
advancedFilterCategories: {
|
||||
stringFields: [
|
||||
{ value: 'MaterialNo', label: '物料号' },
|
||||
{ value: 'MatVer', label: '版本号' },
|
||||
{ value: 'ItemNo', label: '工序号' },
|
||||
{ value: 'WorkCenter', label: '工作中心' }
|
||||
],
|
||||
numberFields: [
|
||||
{ value: 'BaseSec', label: '基础工时' },
|
||||
{ value: 'SortNo', label: '排序' }
|
||||
],
|
||||
enumFields: [
|
||||
{ value: 'SF', label: '串并行', options: [
|
||||
{ value: 'S', label: '串行' },
|
||||
{ value: 'P', label: '并行' }
|
||||
]}
|
||||
]
|
||||
}
|
||||
}
|
||||
};
|
||||
@@ -0,0 +1,111 @@
|
||||
const MDS_PAGE_CONFIG = {
|
||||
tableKey: 't_material',
|
||||
tableDisplayName: '物料',
|
||||
|
||||
display: {
|
||||
columns: [
|
||||
{ field: '_status', title: '状态', width: '80px' },
|
||||
{ field: '_createtime', title: '创建时间', width: '180px', sortable: true },
|
||||
{ field: 'materialno', title: '物料号', width: '100px', sortable: true },
|
||||
{ field: 'description', title: '物料描述', width: '150px' },
|
||||
{ field: 'size', title: '规格' },
|
||||
{ field: 'plant', title: '工厂', width: '70px' },
|
||||
{ field: 'planner', title: '计划员' },
|
||||
{ field: 'fifo', title: 'FIFO', width: '50px' },
|
||||
{ field: 'leadday', title: '提前期', width: '60px' },
|
||||
{ field: 'expday', title: '保质期', width: '60px' },
|
||||
{ field: 'grday', title: '质检期', width: '60px' },
|
||||
{ field: 'abc', title: 'ABC', width: '50px' },
|
||||
{ field: 'unit', title: '单位', width: '50px' },
|
||||
{ field: 'price', title: '价格', width: '80px' },
|
||||
{ field: 'groupno', title: '型号' },
|
||||
{ field: 'type', title: '类型', width: '50px' },
|
||||
{ field: 'phantom', title: '虚拟件', width: '60px' },
|
||||
{ field: 'phantommin', title: '虚拟时间', width: '70px' },
|
||||
{ field: 'firmday', title: '固定天数', width: '60px' },
|
||||
{ field: 'daygap', title: '拆分天数', width: '60px' },
|
||||
{ field: 'candelay', title: '可延迟', width: '60px' },
|
||||
{ field: 'lotsize', title: '批量策略', width: '70px' },
|
||||
{ field: 'lotfix', title: '固定批', width: '60px' },
|
||||
{ field: 'lotmin', title: '最小批', width: '60px' },
|
||||
{ field: 'lotmax', title: '最大批', width: '60px' },
|
||||
{ field: 'lotround', title: '取整值', width: '60px' },
|
||||
{ field: 'lotss', title: '安全库存', width: '60px' },
|
||||
{ field: 'lotpoint', title: '订货点', width: '60px' },
|
||||
{ field: 'lottop', title: '最大库存', width: '60px' },
|
||||
{ field: 'planitem', title: '产品组' },
|
||||
{ field: 'preday', title: '向前冲销', width: '60px' },
|
||||
{ field: 'subday', title: '向后冲销', width: '60px' },
|
||||
{ field: 'free1', title: '自定义1' },
|
||||
{ field: 'free2', title: '自定义2' },
|
||||
{ field: 'free3', title: '自定义3' },
|
||||
{ field: '_source_system', title: '来源', width: '80px' }
|
||||
],
|
||||
|
||||
defaultSortField: '_createtime',
|
||||
defaultSortDir: 'desc',
|
||||
|
||||
advancedFilterCategories: {
|
||||
stringFields: [
|
||||
{ value: 'MaterialNo', label: '物料号' },
|
||||
{ value: 'Description', label: '物料描述' },
|
||||
{ value: 'Plant', label: '工厂' },
|
||||
{ value: 'Planner', label: '计划员' },
|
||||
{ value: 'Unit', label: '单位' }
|
||||
],
|
||||
numberFields: [
|
||||
{ value: 'LeadDay', label: '提前期' },
|
||||
{ value: 'ExpDay', label: '保质期' },
|
||||
{ value: 'GRDay', label: '质检期' },
|
||||
{ value: 'Price', label: '价格' },
|
||||
{ value: 'PhantomMin', label: '虚拟时间' },
|
||||
{ value: 'FirmDay', label: '固定天' },
|
||||
{ value: 'DayGap', label: '拆分天' },
|
||||
{ value: 'LotFix', label: '固定批' },
|
||||
{ value: 'LotMin', label: '最小批' },
|
||||
{ value: 'LotMax', label: '最大批' }
|
||||
],
|
||||
enumFields: [
|
||||
{ value: 'ABC', label: 'ABC分类', options: [
|
||||
{ value: 'A', label: 'A类' },
|
||||
{ value: 'B', label: 'B类' },
|
||||
{ value: 'C', label: 'C类' }
|
||||
]},
|
||||
{ value: 'Type', label: '类型', options: [
|
||||
{ value: 'E', label: '自制件(E)' },
|
||||
{ value: 'F', label: '采购件(F)' }
|
||||
]},
|
||||
{ value: 'Phantom', label: '虚拟件', options: [
|
||||
{ value: 'Y', label: '是(Y)' },
|
||||
{ value: 'N', label: '否(N)' }
|
||||
]},
|
||||
{ value: 'CanDelay', label: '可延迟', options: [
|
||||
{ value: 'Y', label: '是(Y)' },
|
||||
{ value: 'N', label: '否(N)' }
|
||||
]},
|
||||
{ value: 'LotSize', label: '批量策略', options: [
|
||||
{ value: 'EX', label: '一对一(EX)' },
|
||||
{ value: 'FX', label: '固定批(FX)' },
|
||||
{ value: 'VB', label: '重订货点(VB)' },
|
||||
{ value: 'D1', label: '按1天合并(D1)' },
|
||||
{ value: 'D2', label: '按2天合并(D2)' },
|
||||
{ value: 'D3', label: '按3天合并(D3)' },
|
||||
{ value: 'D4', label: '按4天合并(D4)' },
|
||||
{ value: 'D5', label: '按5天合并(D5)' },
|
||||
{ value: 'D6', label: '按6天合并(D6)' },
|
||||
{ value: 'W1', label: '按1周合并(W1)' },
|
||||
{ value: 'W2', label: '按2周合并(W2)' },
|
||||
{ value: 'W3', label: '按3周合并(W3)' },
|
||||
{ value: 'W4', label: '按4周合并(W4)' },
|
||||
{ value: 'M1', label: '按1月合并(M1)' },
|
||||
{ value: 'M2', label: '按2月合并(M2)' },
|
||||
{ value: 'M3', label: '按3月合并(M3)' }
|
||||
]},
|
||||
{ value: 'FIFO', label: 'FIFO', options: [
|
||||
{ value: '0', label: '最近原则' },
|
||||
{ value: '1', label: 'FIFO' }
|
||||
]}
|
||||
]
|
||||
}
|
||||
}
|
||||
};
|
||||
@@ -0,0 +1,46 @@
|
||||
const MDS_PAGE_CONFIG = {
|
||||
tableKey: 't_mold',
|
||||
tableDisplayName: '模具',
|
||||
|
||||
display: {
|
||||
columns: [
|
||||
{ field: '_status', title: '状态', width: '80px' },
|
||||
{ field: '_createtime', title: '创建时间', width: '180px', sortable: true },
|
||||
{ field: 'moldno', title: '模具编号', width: '120px', sortable: true },
|
||||
{ field: 'moldname', title: '描述', width: '200px' },
|
||||
{ field: 'type', title: '类型', width: '100px' },
|
||||
{ field: 'status', title: '状态', width: '100px' },
|
||||
{ field: 'moldnum', title: '穴数', width: '80px' },
|
||||
{ field: 'qty', title: '台数', width: '80px' },
|
||||
{ field: '_source_system', title: '来源', width: '80px' }
|
||||
],
|
||||
|
||||
defaultSortField: '_createtime',
|
||||
defaultSortDir: 'desc',
|
||||
|
||||
advancedFilterCategories: {
|
||||
stringFields: [
|
||||
{ value: 'MoldNo', label: '模具编号' },
|
||||
{ value: 'MoldName', label: '描述' }
|
||||
],
|
||||
numberFields: [
|
||||
{ value: 'MoldNum', label: '穴数' },
|
||||
{ value: 'Qty', label: '台数' }
|
||||
],
|
||||
enumFields: [
|
||||
{ value: 'Type', label: '类型', options: [
|
||||
{ value: '注塑', label: '注塑' },
|
||||
{ value: '冲压', label: '冲压' },
|
||||
{ value: '压铸', label: '压铸' },
|
||||
{ value: '夹具', label: '夹具' }
|
||||
]},
|
||||
{ value: 'Status', label: '状态', options: [
|
||||
{ value: '空闲', label: '空闲' },
|
||||
{ value: '生产中', label: '生产中' },
|
||||
{ value: '维修中', label: '维修中' },
|
||||
{ value: '报废', label: '报废' }
|
||||
]}
|
||||
]
|
||||
}
|
||||
}
|
||||
};
|
||||
@@ -0,0 +1,40 @@
|
||||
const MDS_PAGE_CONFIG = {
|
||||
tableKey: 't_workcenter',
|
||||
tableDisplayName: '工作中心',
|
||||
|
||||
display: {
|
||||
columns: [
|
||||
{ field: '_status', title: '状态', width: '80px' },
|
||||
{ field: '_createtime', title: '创建时间', width: '180px', sortable: true },
|
||||
{ field: 'workcenter', title: '工作中心', width: '120px', sortable: true },
|
||||
{ field: 'description', title: '描述', width: '200px' },
|
||||
{ field: 'bottleneck', title: '瓶颈', width: '80px' },
|
||||
{ field: 'finite', title: '有限产能', width: '100px' },
|
||||
{ field: 'capacity', title: '产能', width: '100px' },
|
||||
{ field: '_source_system', title: '来源', width: '80px' }
|
||||
],
|
||||
|
||||
defaultSortField: '_createtime',
|
||||
defaultSortDir: 'desc',
|
||||
|
||||
advancedFilterCategories: {
|
||||
stringFields: [
|
||||
{ value: 'WorkCenter', label: '工作中心' },
|
||||
{ value: 'Description', label: '描述' }
|
||||
],
|
||||
numberFields: [
|
||||
{ value: 'Capacity', label: '产能' }
|
||||
],
|
||||
enumFields: [
|
||||
{ value: 'Bottleneck', label: '瓶颈', options: [
|
||||
{ value: 'Y', label: '是' },
|
||||
{ value: 'N', label: '否' }
|
||||
]},
|
||||
{ value: 'Finite', label: '有限产能', options: [
|
||||
{ value: 'Y', label: '是' },
|
||||
{ value: 'N', label: '否' }
|
||||
]}
|
||||
]
|
||||
}
|
||||
}
|
||||
};
|
||||
+22
-23
@@ -374,18 +374,17 @@ async function syncData() {
|
||||
}
|
||||
|
||||
const stats = response.data;
|
||||
const validatedCount = stats.validated || 0;
|
||||
const validatedCount = stats.relation_pass || stats.validated || 0;
|
||||
const retryExceeded = stats.retry_exceeded || 0;
|
||||
|
||||
if (validatedCount === 0) {
|
||||
showMessage('没有校验通过的记录可同步', 'warning');
|
||||
return;
|
||||
showMessage('没有外键通过的记录可推送', 'warning');
|
||||
}
|
||||
|
||||
// 如果有超过重试次数的记录,询问是否重置
|
||||
let resetRetry = false;
|
||||
if (retryExceeded > 0) {
|
||||
resetRetry = confirm(`有${retryExceeded}条记录的重试次数已达上限,是否重置重试次数后同步?\n\n点击"确定"重置并同步,点击"取消"跳过这些记录`);
|
||||
resetRetry = confirm(`有${retryExceeded}条记录的重试次数已达上限,是否重置重试次数后推送?\n\n点击"确定"重置并推送,点击"取消"跳过这些记录`);
|
||||
}
|
||||
|
||||
const { mode, targetDbs } = await showSyncModeDialog(validatedCount);
|
||||
@@ -394,7 +393,7 @@ async function syncData() {
|
||||
const targetDbParam = targetDbs.join(',');
|
||||
const totalCount = validatedCount * targetDbs.length;
|
||||
|
||||
showProgress(mode === 'incremental' ? '增量同步中' : '刷新同步中', totalCount);
|
||||
showProgress(mode === 'incremental' ? '增量推送中' : '刷新推送中', totalCount);
|
||||
|
||||
let totalSynced = 0;
|
||||
let totalFailed = 0;
|
||||
@@ -405,14 +404,14 @@ async function syncData() {
|
||||
|
||||
// 刷新模式只调用一次,增量模式循环调用
|
||||
if (mode === 'refresh') {
|
||||
// 刷新模式:一次性同步
|
||||
// 刷新模式:一次性推送
|
||||
setProgressIndeterminate(true);
|
||||
const syncResponse = await callApi(baseUrl, 'POST');
|
||||
setProgressIndeterminate(false);
|
||||
|
||||
if (syncResponse.success !== 1) {
|
||||
hideProgress();
|
||||
showMessage(syncResponse.message || '同步失败', 'danger');
|
||||
showMessage(syncResponse.message || '推送失败', 'danger');
|
||||
} else {
|
||||
const syncStats = syncResponse.data;
|
||||
totalSynced = syncStats.total_synced || 0;
|
||||
@@ -421,9 +420,9 @@ async function syncData() {
|
||||
|
||||
// 根据成功/失败显示不同消息
|
||||
if (totalFailed > 0) {
|
||||
showMessage(`同步完成: ${targetDbs.length}个账套, 成功${totalSynced}条, 失败${totalFailed}条(部分记录缺少必填字段)`, 'warning');
|
||||
showMessage(`推送完成: ${targetDbs.length}个账套, 成功${totalSynced}条, 失败${totalFailed}条(部分记录缺少必填字段)`, 'warning');
|
||||
} else {
|
||||
showMessage(`同步完成: ${targetDbs.length}个账套, 成功${totalSynced}条`, 'success');
|
||||
showMessage(`推送完成: ${targetDbs.length}个账套, 成功${totalSynced}条`, 'success');
|
||||
}
|
||||
}
|
||||
} else {
|
||||
@@ -438,7 +437,7 @@ async function syncData() {
|
||||
|
||||
if (syncResponse.success !== 1) {
|
||||
hideProgress();
|
||||
showMessage(syncResponse.message || '同步失败', 'danger');
|
||||
showMessage(syncResponse.message || '推送失败', 'danger');
|
||||
break;
|
||||
}
|
||||
|
||||
@@ -463,9 +462,9 @@ async function syncData() {
|
||||
|
||||
// 根据成功/失败显示不同消息
|
||||
if (totalFailed > 0) {
|
||||
showMessage(`同步完成: ${targetDbs.length}个账套, 成功${totalSynced}条, 失败${totalFailed}条(部分记录缺少必填字段)`, 'warning');
|
||||
showMessage(`推送完成: ${targetDbs.length}个账套, 成功${totalSynced}条, 失败${totalFailed}条(部分记录缺少必填字段)`, 'warning');
|
||||
} else {
|
||||
showMessage(`同步完成: ${targetDbs.length}个账套, 成功${totalSynced}条`, 'success');
|
||||
showMessage(`推送完成: ${targetDbs.length}个账套, 成功${totalSynced}条`, 'success');
|
||||
}
|
||||
}
|
||||
|
||||
@@ -486,7 +485,7 @@ async function showSyncModeDialog(validatedCount) {
|
||||
<div class="modal-dialog modal-dialog-centered">
|
||||
<div class="modal-content">
|
||||
<div class="modal-header">
|
||||
<h5 class="modal-title">选择同步模式</h5>
|
||||
<h5 class="modal-title">选择推送模式</h5>
|
||||
<button type="button" class="btn-close" data-bs-dismiss="modal"></button>
|
||||
</div>
|
||||
<div class="modal-body">
|
||||
@@ -500,35 +499,35 @@ async function showSyncModeDialog(validatedCount) {
|
||||
</div>
|
||||
`).join('')}
|
||||
</div>
|
||||
<div class="form-text">默认全选,可取消勾选排除不需要同步的账套</div>
|
||||
<div class="form-text">默认全选,可取消勾选排除不需要推送的账套</div>
|
||||
</div>
|
||||
<hr>
|
||||
<div class="mb-3">
|
||||
<label class="form-label fw-bold">同步模式</label>
|
||||
<label class="form-label fw-bold">推送模式</label>
|
||||
<div class="form-check">
|
||||
<input class="form-check-input" type="radio" name="syncMode" id="modeIncremental" value="incremental" checked>
|
||||
<label class="form-check-label" for="modeIncremental">
|
||||
<strong>增量同步</strong> <span class="badge bg-primary">${validatedCount}条</span>
|
||||
<strong>增量推送</strong> <span class="badge bg-primary">${validatedCount}条</span>
|
||||
</label>
|
||||
<div class="text-muted small mt-1">仅同步校验通过的新数据,保留正式表现有数据</div>
|
||||
<div class="text-muted small mt-1">仅推送校验通过的新数据,保留正式表现有数据</div>
|
||||
</div>
|
||||
</div>
|
||||
<div class="mb-3">
|
||||
<div class="form-check">
|
||||
<input class="form-check-input" type="radio" name="syncMode" id="modeRefresh" value="refresh">
|
||||
<label class="form-check-label" for="modeRefresh">
|
||||
<strong>刷新同步</strong> <span class="badge bg-warning text-dark">${validatedCount}条</span>
|
||||
<strong>刷新推送</strong> <span class="badge bg-warning text-dark">${validatedCount}条</span>
|
||||
</label>
|
||||
<div class="text-muted small mt-1">清空正式表后,重新同步校验通过的数据</div>
|
||||
<div class="text-muted small mt-1">清空正式表后,重新推送校验通过的数据</div>
|
||||
</div>
|
||||
</div>
|
||||
<div class="alert alert-warning small mb-0">
|
||||
<i class="bi bi-exclamation-triangle"></i> 刷新同步将<strong>删除正式表所有数据</strong>,请谨慎操作!
|
||||
<i class="bi bi-exclamation-triangle"></i> 刷新推送将<strong>删除正式表所有数据</strong>,请谨慎操作!
|
||||
</div>
|
||||
</div>
|
||||
<div class="modal-footer">
|
||||
<button type="button" class="btn btn-secondary" data-bs-dismiss="modal">取消</button>
|
||||
<button type="button" class="btn btn-primary" id="confirmSyncBtn">开始同步</button>
|
||||
<button type="button" class="btn btn-primary" id="confirmSyncBtn">开始推送</button>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
@@ -562,7 +561,7 @@ async function showSyncModeDialog(validatedCount) {
|
||||
}
|
||||
|
||||
async function syncAllData() {
|
||||
if (!confirm('确定要同步所有校验通过的数据吗?')) return;
|
||||
if (!confirm('确定要推送所有校验通过的数据吗?')) return;
|
||||
|
||||
showLoading();
|
||||
|
||||
@@ -571,7 +570,7 @@ async function syncAllData() {
|
||||
hideLoading();
|
||||
|
||||
handleResponse(response, (data) => {
|
||||
showMessage('所有表同步完成', 'success');
|
||||
showMessage('所有表推送完成', 'success');
|
||||
dataTable.refresh();
|
||||
statusCard.refresh();
|
||||
});
|
||||
|
||||
File diff suppressed because it is too large
Load Diff
@@ -1,51 +0,0 @@
|
||||
<!DOCTYPE html>
|
||||
<html lang="zh-CN">
|
||||
<head>
|
||||
<meta charset="UTF-8">
|
||||
<meta name="viewport" content="width=device-width, initial-scale=1.0">
|
||||
<title>产线版本数据清洗管理</title>
|
||||
<link href="/static/mds/css/bootstrap.min.css" rel="stylesheet">
|
||||
<script src="/static/mds/js/bootstrap.bundle.min.js"></script>
|
||||
</head>
|
||||
<body>
|
||||
<nav class="navbar navbar-expand-lg navbar-dark bg-primary mb-2">
|
||||
<div class="container-fluid">
|
||||
<a class="navbar-brand" href="/mds">📊 数据清洗管理系统</a>
|
||||
<button class="navbar-toggler" type="button" data-bs-toggle="collapse" data-bs-target="#navbarNav">
|
||||
<span class="navbar-toggler-icon"></span>
|
||||
</button>
|
||||
<div class="collapse navbar-collapse" id="navbarNav">
|
||||
<ul class="navbar-nav me-auto">
|
||||
<li class="nav-item">
|
||||
<a class="nav-link" href="/mds/material">📦 物料</a>
|
||||
</li>
|
||||
<li class="nav-item">
|
||||
<a class="nav-link" href="/mds/workcenter">🏭 工作中心</a>
|
||||
</li>
|
||||
<li class="nav-item">
|
||||
<a class="nav-link active" href="/mds/mat-ver">📋 产线版本</a>
|
||||
</li>
|
||||
<li class="nav-item">
|
||||
<a class="nav-link" href="/mds/mat-wc">🛠️ 工艺路线</a>
|
||||
</li>
|
||||
<li class="nav-item">
|
||||
<a class="nav-link" href="/mds/mat-wc-bom">📐 BOM</a>
|
||||
</li>
|
||||
<li class="nav-item">
|
||||
<a class="nav-link" href="/mds/mold">🔧 模具</a>
|
||||
</li>
|
||||
<li class="nav-item">
|
||||
<a class="nav-link" href="/mds/mat-wc-mold">🔩 机台模具</a>
|
||||
</li>
|
||||
</ul>
|
||||
</div>
|
||||
</div>
|
||||
</nav>
|
||||
<div class="container">
|
||||
<div class="alert alert-info text-center py-5">
|
||||
<h3>产线版本数据清洗管理</h3>
|
||||
<p class="mb-0">功能开发中,敬请期待...</p>
|
||||
</div>
|
||||
</div>
|
||||
</body>
|
||||
</html>
|
||||
@@ -1,51 +0,0 @@
|
||||
<!DOCTYPE html>
|
||||
<html lang="zh-CN">
|
||||
<head>
|
||||
<meta charset="UTF-8">
|
||||
<meta name="viewport" content="width=device-width, initial-scale=1.0">
|
||||
<title>BOM数据清洗管理</title>
|
||||
<link href="/static/mds/css/bootstrap.min.css" rel="stylesheet">
|
||||
<script src="/static/mds/js/bootstrap.bundle.min.js"></script>
|
||||
</head>
|
||||
<body>
|
||||
<nav class="navbar navbar-expand-lg navbar-dark bg-primary mb-2">
|
||||
<div class="container-fluid">
|
||||
<a class="navbar-brand" href="/mds">📊 数据清洗管理系统</a>
|
||||
<button class="navbar-toggler" type="button" data-bs-toggle="collapse" data-bs-target="#navbarNav">
|
||||
<span class="navbar-toggler-icon"></span>
|
||||
</button>
|
||||
<div class="collapse navbar-collapse" id="navbarNav">
|
||||
<ul class="navbar-nav me-auto">
|
||||
<li class="nav-item">
|
||||
<a class="nav-link" href="/mds/material">📦 物料</a>
|
||||
</li>
|
||||
<li class="nav-item">
|
||||
<a class="nav-link" href="/mds/workcenter">🏭 工作中心</a>
|
||||
</li>
|
||||
<li class="nav-item">
|
||||
<a class="nav-link" href="/mds/mat-ver">📋 产线版本</a>
|
||||
</li>
|
||||
<li class="nav-item">
|
||||
<a class="nav-link" href="/mds/mat-wc">🛠️ 工艺路线</a>
|
||||
</li>
|
||||
<li class="nav-item">
|
||||
<a class="nav-link active" href="/mds/mat-wc-bom">📐 BOM</a>
|
||||
</li>
|
||||
<li class="nav-item">
|
||||
<a class="nav-link" href="/mds/mold">🔧 模具</a>
|
||||
</li>
|
||||
<li class="nav-item">
|
||||
<a class="nav-link" href="/mds/mat-wc-mold">🔩 机台模具</a>
|
||||
</li>
|
||||
</ul>
|
||||
</div>
|
||||
</div>
|
||||
</nav>
|
||||
<div class="container">
|
||||
<div class="alert alert-info text-center py-5">
|
||||
<h3>BOM数据清洗管理</h3>
|
||||
<p class="mb-0">功能开发中,敬请期待...</p>
|
||||
</div>
|
||||
</div>
|
||||
</body>
|
||||
</html>
|
||||
@@ -1,51 +0,0 @@
|
||||
<!DOCTYPE html>
|
||||
<html lang="zh-CN">
|
||||
<head>
|
||||
<meta charset="UTF-8">
|
||||
<meta name="viewport" content="width=device-width, initial-scale=1.0">
|
||||
<title>机台模具关联数据清洗管理</title>
|
||||
<link href="/static/mds/css/bootstrap.min.css" rel="stylesheet">
|
||||
<script src="/static/mds/js/bootstrap.bundle.min.js"></script>
|
||||
</head>
|
||||
<body>
|
||||
<nav class="navbar navbar-expand-lg navbar-dark bg-primary mb-2">
|
||||
<div class="container-fluid">
|
||||
<a class="navbar-brand" href="/mds">📊 数据清洗管理系统</a>
|
||||
<button class="navbar-toggler" type="button" data-bs-toggle="collapse" data-bs-target="#navbarNav">
|
||||
<span class="navbar-toggler-icon"></span>
|
||||
</button>
|
||||
<div class="collapse navbar-collapse" id="navbarNav">
|
||||
<ul class="navbar-nav me-auto">
|
||||
<li class="nav-item">
|
||||
<a class="nav-link" href="/mds/material">📦 物料</a>
|
||||
</li>
|
||||
<li class="nav-item">
|
||||
<a class="nav-link" href="/mds/workcenter">🏭 工作中心</a>
|
||||
</li>
|
||||
<li class="nav-item">
|
||||
<a class="nav-link" href="/mds/mat-ver">📋 产线版本</a>
|
||||
</li>
|
||||
<li class="nav-item">
|
||||
<a class="nav-link" href="/mds/mat-wc">🛠️ 工艺路线</a>
|
||||
</li>
|
||||
<li class="nav-item">
|
||||
<a class="nav-link" href="/mds/mat-wc-bom">📐 BOM</a>
|
||||
</li>
|
||||
<li class="nav-item">
|
||||
<a class="nav-link" href="/mds/mold">🔧 模具</a>
|
||||
</li>
|
||||
<li class="nav-item">
|
||||
<a class="nav-link active" href="/mds/mat-wc-mold">🔩 机台模具</a>
|
||||
</li>
|
||||
</ul>
|
||||
</div>
|
||||
</div>
|
||||
</nav>
|
||||
<div class="container">
|
||||
<div class="alert alert-info text-center py-5">
|
||||
<h3>机台模具关联数据清洗管理</h3>
|
||||
<p class="mb-0">功能开发中,敬请期待...</p>
|
||||
</div>
|
||||
</div>
|
||||
</body>
|
||||
</html>
|
||||
@@ -1,51 +0,0 @@
|
||||
<!DOCTYPE html>
|
||||
<html lang="zh-CN">
|
||||
<head>
|
||||
<meta charset="UTF-8">
|
||||
<meta name="viewport" content="width=device-width, initial-scale=1.0">
|
||||
<title>工艺路线数据清洗管理</title>
|
||||
<link href="/static/mds/css/bootstrap.min.css" rel="stylesheet">
|
||||
<script src="/static/mds/js/bootstrap.bundle.min.js"></script>
|
||||
</head>
|
||||
<body>
|
||||
<nav class="navbar navbar-expand-lg navbar-dark bg-primary mb-2">
|
||||
<div class="container-fluid">
|
||||
<a class="navbar-brand" href="/mds">📊 数据清洗管理系统</a>
|
||||
<button class="navbar-toggler" type="button" data-bs-toggle="collapse" data-bs-target="#navbarNav">
|
||||
<span class="navbar-toggler-icon"></span>
|
||||
</button>
|
||||
<div class="collapse navbar-collapse" id="navbarNav">
|
||||
<ul class="navbar-nav me-auto">
|
||||
<li class="nav-item">
|
||||
<a class="nav-link" href="/mds/material">📦 物料</a>
|
||||
</li>
|
||||
<li class="nav-item">
|
||||
<a class="nav-link" href="/mds/workcenter">🏭 工作中心</a>
|
||||
</li>
|
||||
<li class="nav-item">
|
||||
<a class="nav-link" href="/mds/mat-ver">📋 产线版本</a>
|
||||
</li>
|
||||
<li class="nav-item">
|
||||
<a class="nav-link active" href="/mds/mat-wc">🛠️ 工艺路线</a>
|
||||
</li>
|
||||
<li class="nav-item">
|
||||
<a class="nav-link" href="/mds/mat-wc-bom">📐 BOM</a>
|
||||
</li>
|
||||
<li class="nav-item">
|
||||
<a class="nav-link" href="/mds/mold">🔧 模具</a>
|
||||
</li>
|
||||
<li class="nav-item">
|
||||
<a class="nav-link" href="/mds/mat-wc-mold">🔩 机台模具</a>
|
||||
</li>
|
||||
</ul>
|
||||
</div>
|
||||
</div>
|
||||
</nav>
|
||||
<div class="container">
|
||||
<div class="alert alert-info text-center py-5">
|
||||
<h3>工艺路线数据清洗管理</h3>
|
||||
<p class="mb-0">功能开发中,敬请期待...</p>
|
||||
</div>
|
||||
</div>
|
||||
</body>
|
||||
</html>
|
||||
@@ -1,51 +0,0 @@
|
||||
<!DOCTYPE html>
|
||||
<html lang="zh-CN">
|
||||
<head>
|
||||
<meta charset="UTF-8">
|
||||
<meta name="viewport" content="width=device-width, initial-scale=1.0">
|
||||
<title>模具数据清洗管理</title>
|
||||
<link href="/static/mds/css/bootstrap.min.css" rel="stylesheet">
|
||||
<script src="/static/mds/js/bootstrap.bundle.min.js"></script>
|
||||
</head>
|
||||
<body>
|
||||
<nav class="navbar navbar-expand-lg navbar-dark bg-primary mb-2">
|
||||
<div class="container-fluid">
|
||||
<a class="navbar-brand" href="/mds">📊 数据清洗管理系统</a>
|
||||
<button class="navbar-toggler" type="button" data-bs-toggle="collapse" data-bs-target="#navbarNav">
|
||||
<span class="navbar-toggler-icon"></span>
|
||||
</button>
|
||||
<div class="collapse navbar-collapse" id="navbarNav">
|
||||
<ul class="navbar-nav me-auto">
|
||||
<li class="nav-item">
|
||||
<a class="nav-link" href="/mds/material">📦 物料</a>
|
||||
</li>
|
||||
<li class="nav-item">
|
||||
<a class="nav-link" href="/mds/workcenter">🏭 工作中心</a>
|
||||
</li>
|
||||
<li class="nav-item">
|
||||
<a class="nav-link" href="/mds/mat-ver">📋 产线版本</a>
|
||||
</li>
|
||||
<li class="nav-item">
|
||||
<a class="nav-link" href="/mds/mat-wc">🛠️ 工艺路线</a>
|
||||
</li>
|
||||
<li class="nav-item">
|
||||
<a class="nav-link" href="/mds/mat-wc-bom">📐 BOM</a>
|
||||
</li>
|
||||
<li class="nav-item">
|
||||
<a class="nav-link active" href="/mds/mold">🔧 模具</a>
|
||||
</li>
|
||||
<li class="nav-item">
|
||||
<a class="nav-link" href="/mds/mat-wc-mold">🔩 机台模具</a>
|
||||
</li>
|
||||
</ul>
|
||||
</div>
|
||||
</div>
|
||||
</nav>
|
||||
<div class="container">
|
||||
<div class="alert alert-info text-center py-5">
|
||||
<h3>模具数据清洗管理</h3>
|
||||
<p class="mb-0">功能开发中,敬请期待...</p>
|
||||
</div>
|
||||
</div>
|
||||
</body>
|
||||
</html>
|
||||
@@ -3,12 +3,11 @@
|
||||
<head>
|
||||
<meta charset="UTF-8">
|
||||
<meta name="viewport" content="width=device-width, initial-scale=1.0">
|
||||
<title>物料数据清洗管理</title>
|
||||
<title>{page_title}</title>
|
||||
<link href="/static/mds/css/bootstrap.min.css" rel="stylesheet">
|
||||
<link rel="stylesheet" href="/static/mds/css/custom.css">
|
||||
</head>
|
||||
<body>
|
||||
<!-- 导航栏 -->
|
||||
<nav class="navbar navbar-expand-lg navbar-dark bg-primary mb-2">
|
||||
<div class="container-fluid">
|
||||
<a class="navbar-brand" href="/mds">📊 数据清洗管理系统</a>
|
||||
@@ -18,57 +17,58 @@
|
||||
<div class="collapse navbar-collapse" id="navbarNav">
|
||||
<ul class="navbar-nav me-auto">
|
||||
<li class="nav-item">
|
||||
<a class="nav-link active" href="/mds/material">📦 物料</a>
|
||||
<a class="nav-link {material_active}" href="/mds/material">📦 物料</a>
|
||||
</li>
|
||||
<li class="nav-item">
|
||||
<a class="nav-link" href="/mds/workcenter">🏭 工作中心</a>
|
||||
<a class="nav-link {workcenter_active}" href="/mds/workcenter">🏭 工作中心</a>
|
||||
</li>
|
||||
<li class="nav-item">
|
||||
<a class="nav-link" href="/mds/mat-ver">📋 产线版本</a>
|
||||
<a class="nav-link {mat_ver_active}" href="/mds/mat-ver">📋 产线版本</a>
|
||||
</li>
|
||||
<li class="nav-item">
|
||||
<a class="nav-link" href="/mds/mat-wc">🛠️ 工艺路线</a>
|
||||
<a class="nav-link {mat_wc_active}" href="/mds/mat-wc">🛠️ 工艺路线</a>
|
||||
</li>
|
||||
<li class="nav-item">
|
||||
<a class="nav-link" href="/mds/mat-wc-bom">📐 BOM</a>
|
||||
<a class="nav-link {mat_wc_bom_active}" href="/mds/mat-wc-bom">📐 BOM</a>
|
||||
</li>
|
||||
<li class="nav-item">
|
||||
<a class="nav-link" href="/mds/mold">🔧 模具</a>
|
||||
<a class="nav-link {mold_active}" href="/mds/mold">🔧 模具</a>
|
||||
</li>
|
||||
<li class="nav-item">
|
||||
<a class="nav-link" href="/mds/mat-wc-mold">🔩 机台模具</a>
|
||||
<a class="nav-link {mat_wc_mold_active}" href="/mds/mat-wc-mold">🔩 机台模具</a>
|
||||
</li>
|
||||
</ul>
|
||||
<div class="d-flex gap-2">
|
||||
<button class="btn btn-outline-light btn-sm" style="width:100px" id="validateAllBtn">校验全部</button>
|
||||
<button class="btn btn-outline-light btn-sm" style="width:100px" id="syncAllBtn">同步全部</button>
|
||||
<button class="btn btn-outline-light btn-sm" style="width:100px" id="syncAllBtn">推送全部</button>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
</nav>
|
||||
|
||||
<div class="container-fluid py-2">
|
||||
<!-- 状态统计卡片 -->
|
||||
<div class="row mb-2">
|
||||
<div class="col-12" id="statusCardContainer"></div>
|
||||
</div>
|
||||
|
||||
<!-- 操作按钮 + 筛选区域 -->
|
||||
<div class="filter-bar mb-2">
|
||||
<div class="row g-2 align-items-center">
|
||||
<div class="col-auto">
|
||||
<button class="btn btn-primary btn-sm" style="width:100px" data-bs-toggle="modal" data-bs-target="#uploadModal">导入</button>
|
||||
<button class="btn btn-success btn-sm" style="width:100px" id="validateBtn">校验</button>
|
||||
<button class="btn btn-info btn-sm" style="width:100px" id="syncBtn">同步</button>
|
||||
<button class="btn btn-info btn-sm" style="width:100px" id="syncBtn">推送</button>
|
||||
<button class="btn btn-outline-warning btn-sm" style="width:100px" id="rulesBtn">校验规则</button>
|
||||
</div>
|
||||
<div class="col-auto ms-auto">
|
||||
<button class="btn btn-outline-info btn-sm" style="width:100px" id="downloadTemplateBtn">下载模板</button>
|
||||
</div>
|
||||
<div class="col-auto">
|
||||
<select class="form-select form-select-sm" id="statusFilter" style="width:100px">
|
||||
<option value="">全部状态</option>
|
||||
<option value="pending">待处理</option>
|
||||
<option value="validated">校验通过</option>
|
||||
<option value="rejected">校验失败</option>
|
||||
<option value="synced">已同步</option>
|
||||
<option value="synced">已推送</option>
|
||||
</select>
|
||||
</div>
|
||||
<div class="col-auto">
|
||||
@@ -81,7 +81,7 @@
|
||||
</select>
|
||||
</div>
|
||||
<div class="col-auto flex-grow-1">
|
||||
<input type="text" class="form-control form-control-sm" id="keywordInput" placeholder="搜索物料号或描述...">
|
||||
<input type="text" class="form-control form-control-sm" id="keywordInput" placeholder="{keyword_placeholder}">
|
||||
</div>
|
||||
<div class="col-auto">
|
||||
<button class="btn btn-primary btn-sm" id="searchBtn">查询</button>
|
||||
@@ -91,11 +91,9 @@
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<!-- 数据列表区域 -->
|
||||
<div class="data-table-container" id="tableContainer"></div>
|
||||
</div>
|
||||
|
||||
<!-- 上传弹窗 -->
|
||||
<div class="modal fade" id="uploadModal" tabindex="-1">
|
||||
<div class="modal-dialog">
|
||||
<div class="modal-content">
|
||||
@@ -125,7 +123,6 @@
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<!-- 精准筛选弹窗 -->
|
||||
<div class="modal fade" id="advancedFilterModal" tabindex="-1">
|
||||
<div class="modal-dialog modal-lg">
|
||||
<div class="modal-content">
|
||||
@@ -177,7 +174,6 @@
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<!-- 批量编辑弹窗 -->
|
||||
<div class="modal fade" id="batchEditModal" tabindex="-1">
|
||||
<div class="modal-dialog modal-lg">
|
||||
<div class="modal-content">
|
||||
@@ -203,7 +199,6 @@
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<!-- 编辑弹窗 -->
|
||||
<div class="modal fade" id="editModal" tabindex="-1">
|
||||
<div class="modal-dialog modal-xl">
|
||||
<div class="modal-content">
|
||||
@@ -228,6 +223,12 @@
|
||||
<script src="/static/mds/js/api-client.js"></script>
|
||||
<script src="/static/mds/js/data-table.js"></script>
|
||||
<script src="/static/mds/js/status-card.js"></script>
|
||||
<script src="/static/mds/js/material.js"></script>
|
||||
<script src="/static/mds/configs/{config_file}"></script>
|
||||
<script src="/static/mds/js/mds-page-controller.js"></script>
|
||||
<script>
|
||||
document.addEventListener('DOMContentLoaded', () => {
|
||||
new MDSPageController(MDS_PAGE_CONFIG);
|
||||
});
|
||||
</script>
|
||||
</body>
|
||||
</html>
|
||||
@@ -1,51 +0,0 @@
|
||||
<!DOCTYPE html>
|
||||
<html lang="zh-CN">
|
||||
<head>
|
||||
<meta charset="UTF-8">
|
||||
<meta name="viewport" content="width=device-width, initial-scale=1.0">
|
||||
<title>工作中心数据清洗管理</title>
|
||||
<link href="/static/mds/css/bootstrap.min.css" rel="stylesheet">
|
||||
<script src="/static/mds/js/bootstrap.bundle.min.js"></script>
|
||||
</head>
|
||||
<body>
|
||||
<nav class="navbar navbar-expand-lg navbar-dark bg-primary mb-2">
|
||||
<div class="container-fluid">
|
||||
<a class="navbar-brand" href="/mds">📊 数据清洗管理系统</a>
|
||||
<button class="navbar-toggler" type="button" data-bs-toggle="collapse" data-bs-target="#navbarNav">
|
||||
<span class="navbar-toggler-icon"></span>
|
||||
</button>
|
||||
<div class="collapse navbar-collapse" id="navbarNav">
|
||||
<ul class="navbar-nav me-auto">
|
||||
<li class="nav-item">
|
||||
<a class="nav-link" href="/mds/material">📦 物料</a>
|
||||
</li>
|
||||
<li class="nav-item">
|
||||
<a class="nav-link active" href="/mds/workcenter">🏭 工作中心</a>
|
||||
</li>
|
||||
<li class="nav-item">
|
||||
<a class="nav-link" href="/mds/mat-ver">📋 产线版本</a>
|
||||
</li>
|
||||
<li class="nav-item">
|
||||
<a class="nav-link" href="/mds/mat-wc">🛠️ 工艺路线</a>
|
||||
</li>
|
||||
<li class="nav-item">
|
||||
<a class="nav-link" href="/mds/mat-wc-bom">📐 BOM</a>
|
||||
</li>
|
||||
<li class="nav-item">
|
||||
<a class="nav-link" href="/mds/mold">🔧 模具</a>
|
||||
</li>
|
||||
<li class="nav-item">
|
||||
<a class="nav-link" href="/mds/mat-wc-mold">🔩 机台模具</a>
|
||||
</li>
|
||||
</ul>
|
||||
</div>
|
||||
</div>
|
||||
</nav>
|
||||
<div class="container">
|
||||
<div class="alert alert-info text-center py-5">
|
||||
<h3>工作中心数据清洗管理</h3>
|
||||
<p class="mb-0">功能开发中,敬请期待...</p>
|
||||
</div>
|
||||
</div>
|
||||
</body>
|
||||
</html>
|
||||
Reference in New Issue
Block a user