jiateng_ws/dao/inspection_dao.py

703 lines
26 KiB
Python
Raw Blame History

This file contains ambiguous Unicode characters

This file contains Unicode characters that might be confused with other characters. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.

import json
import logging
from datetime import datetime
from utils.sql_utils import SQLUtils
class InspectionDAO:
"""检验项目配置和数据访问对象"""
def __init__(self):
"""初始化数据访问对象"""
self.db = SQLUtils('sqlite', database='db/jtDB.db')
def __del__(self):
"""析构函数,确保数据库连接关闭"""
if hasattr(self, 'db'):
self.db.close()
def get_all_inspection_configs(self, include_disabled=False):
"""获取所有检验项目配置
Args:
include_disabled: 是否包含禁用的项目
Returns:
list: 检验项目配置列表
"""
try:
if include_disabled:
sql = """
SELECT id, position, name, display_name, enabled, required,
data_type, min_value, max_value, enum_values, unit, sort_order
FROM wsbz_inspection_config
WHERE is_deleted = FALSE
ORDER BY sort_order, position
"""
params = ()
else:
sql = """
SELECT id, position, name, display_name, enabled, required,
data_type, min_value, max_value, enum_values, unit, sort_order
FROM wsbz_inspection_config
WHERE is_deleted = FALSE AND enabled = TRUE
ORDER BY sort_order, position
"""
params = ()
self.db.cursor.execute(sql, params)
results = self.db.cursor.fetchall()
configs = []
for row in results:
config = {
'id': row[0],
'position': row[1],
'name': row[2],
'display_name': row[3],
'enabled': bool(row[4]),
'required': bool(row[5]),
'data_type': row[6],
'min_value': row[7],
'max_value': row[8],
'enum_values': json.loads(row[9]) if row[9] else None,
'unit': row[10],
'sort_order': row[11]
}
configs.append(config)
return configs
except Exception as e:
logging.error(f"获取检验项目配置失败: {str(e)}")
return []
def get_enabled_inspection_configs(self):
"""获取已启用的检验项目配置
Returns:
list: 已启用的检验项目配置列表
"""
return self.get_all_inspection_configs(include_disabled=False)
def get_inspection_config_by_position(self, position):
"""根据位置获取检验项目配置
Args:
position: 位置序号 (1-6)
Returns:
dict: 检验项目配置, 未找到则返回None
"""
try:
sql = """
SELECT id, position, name, display_name, enabled, required,
data_type, min_value, max_value, enum_values, unit, sort_order
FROM wsbz_inspection_config
WHERE position = ? AND is_deleted = FALSE
"""
params = (position,)
self.db.cursor.execute(sql, params)
row = self.db.cursor.fetchone()
if row:
config = {
'id': row[0],
'position': row[1],
'name': row[2],
'display_name': row[3],
'enabled': bool(row[4]),
'required': bool(row[5]),
'data_type': row[6],
'min_value': row[7],
'max_value': row[8],
'enum_values': json.loads(row[9]) if row[9] else None,
'unit': row[10],
'sort_order': row[11]
}
return config
else:
return None
except Exception as e:
logging.error(f"获取检验项目配置失败: {str(e)}")
return None
def update_inspection_config(self, config_id, data, username='system'):
"""更新检验项目配置
Args:
config_id: 配置ID
data: 更新数据
username: 操作用户
Returns:
bool: 更新是否成功
"""
try:
current_time = datetime.now().strftime('%Y-%m-%d %H:%M:%S')
# 构建更新SQL
update_fields = []
params = []
# 可更新的字段
allowed_fields = [
'name', 'display_name', 'enabled', 'required',
'data_type', 'min_value', 'max_value', 'unit',
'sort_order', 'enum_values'
]
for field in allowed_fields:
if field in data:
# 特殊处理enum_values字段确保存储为JSON字符串
if field == 'enum_values' and data[field] is not None:
if isinstance(data[field], list):
update_fields.append(f"{field} = ?")
params.append(json.dumps(data[field]))
elif isinstance(data[field], str):
# 如果已经是字符串检查是否有效的JSON
try:
json.loads(data[field])
update_fields.append(f"{field} = ?")
params.append(data[field])
except:
logging.warning(f"无效的JSON: {data[field]}")
continue
else:
update_fields.append(f"{field} = ?")
params.append(data[field])
# 添加更新时间和更新人
update_fields.append("update_time = ?")
params.append(current_time)
update_fields.append("update_by = ?")
params.append(username)
# 添加配置ID到参数列表
params.append(config_id)
# 构建SQL
sql = f"""
UPDATE inspection_config
SET {', '.join(update_fields)}
WHERE id = ?
"""
self.db.execute_update(sql, params)
return True
except Exception as e:
logging.error(f"更新检验项目配置失败: {str(e)}")
return False
def toggle_inspection_config(self, position, enabled, username='system'):
"""启用或禁用检验项目配置
Args:
position: 位置序号 (1-6)
enabled: 是否启用
username: 操作用户
Returns:
bool: 操作是否成功
"""
try:
current_time = datetime.now().strftime('%Y-%m-%d %H:%M:%S')
sql = """
UPDATE wsbz_inspection_config
SET enabled = ?, update_time = ?, update_by = ?
WHERE position = ? AND is_deleted = FALSE
"""
params = (enabled, current_time, username, position)
self.db.execute_update(sql, params)
return True
except Exception as e:
logging.error(f"更新检验项目启用状态失败: {str(e)}")
return False
def save_order_info(self, order_id,data):
"""保存订单信息到 wsbz_order_info 表
Args:
data: 订单信息字典
Returns:
bool: 操作是否成功
"""
try:
if not data:
return False
sql = """
INSERT INTO wsbz_order_info (
data_corp, user_id, user_name, gzl_zl, ddmo, xpack,
sc_gch, qd, spack_type, mxzs, jt, ddnote, code, type,
lable, lib, gzl, maxsl, cz, size, cd, luno, qfqd,
pono, xj, ysl, dycz, zh, edit_id, remarks
) VALUES (
?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?,
?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?
)
"""
params = (
data.get("data_corp", "JT"),
data.get("user_id", ""),
data.get("user_name", ""),
data.get("zx_zl", ""),
data.get("mo", ""),
data.get("xpack", ""),
order_id if order_id else "",
data.get("qd", ""),
data.get("spack_type", ""),
data.get("mxzs", ""),
data.get("jt", ""),
data.get("note", ""),
data.get("code", ""),
data.get("type", ""),
data.get("template_name", ""),
data.get("lib", ""),
data.get("zx_code", ""),
data.get("maxsl", ""),
data.get("cz", ""),
data.get("size", ""),
data.get("cd", ""),
data.get("luno", ""),
data.get("qfqd", ""),
data.get("khno", ""),
data.get("size", ""),
data.get("ysl", ""),
data.get("dycz", ""),
data.get("zh", ""),
data.get("edit_id", ""),
data.get("remarks", ""),
)
self.db.cursor.execute(sql, params)
self.db.conn.commit()
return True
except Exception as e:
logging.error(f"保存订单信息失败: {str(e)}")
self.db.conn.rollback()
return False
def save_inspection_data(self, order_id, data, username='system'):
"""保存检验数据
Args:
order_id: 工程号
data: 检验数据列表,格式: [{'position': 1, 'config_id': 1, 'value': '合格'}, ...]
username: 操作用户
Returns:
bool: 保存是否成功
"""
try:
current_time = datetime.now().strftime('%Y-%m-%d %H:%M:%S')
self.db.begin_transaction()
for item in data:
position = item.get('position')
config_id = item.get('config_id')
value = item.get('value')
status = item.get('status', 'pass')
remark = item.get('remark', '')
tray_id = item.get('tray_id', '')
# 检查是否已存在该工程号和位置的记录
check_sql = """
SELECT id FROM wsbz_inspection_data
WHERE order_id = ? AND position = ? AND is_deleted = FALSE
"""
check_params = (order_id, position)
self.db.cursor.execute(check_sql, check_params)
existing = self.db.cursor.fetchone()
if existing:
# 更新已有记录
update_sql = """
UPDATE wsbz_inspection_data
SET config_id = ?, value = ?, status = ?, remark = ?,
update_time = ?, update_by = ?, tray_id = ?
WHERE id = ?
"""
update_params = (
config_id, value, status, remark,
current_time, username, tray_id, existing[0]
)
self.db.cursor.execute(update_sql, update_params)
else:
# 插入新记录
insert_sql = """
INSERT INTO wsbz_inspection_data (
order_id, position, config_id, value, status, remark,
create_time, create_by, is_deleted, tray_id
) VALUES (?, ?, ?, ?, ?, ?, ?, ?, FALSE, ?)
"""
insert_params = (
order_id, position, config_id, value, status, remark,
current_time, username, tray_id
)
self.db.cursor.execute(insert_sql, insert_params)
self.db.commit_transaction()
return True
except Exception as e:
self.db.rollback_transaction()
logging.error(f"保存检验数据失败: {str(e)}")
return False
def get_inspection_data_unfinished(self, tray_id):
"""获取未完成的检验数据,通过是否贴标来判断
Returns:
list: 未完成的检验数据列表
"""
try:
# 先获取所有没有贴标的工程号
sql_orders = """
SELECT DISTINCT d.order_id
FROM wsbz_inspection_data d
WHERE d.is_deleted = FALSE AND d.tray_id = ?
AND d.position = 11 AND COALESCE(d.value,'') = ''
"""
params = (tray_id,)
self.db.cursor.execute(sql_orders, params)
orders = self.db.cursor.fetchall()
if not orders:
return []
# 构建IN子句的参数
order_ids = [order[0] for order in orders]
placeholders = ','.join(['?' for _ in order_ids])
# 获取这些工程号的所有检验数据
sql = f"""
SELECT d.id, d.order_id, d.position, d.config_id, d.value, d.status, d.remark,
c.name, c.display_name, c.data_type, c.unit
FROM wsbz_inspection_data d
LEFT JOIN wsbz_inspection_config c ON d.config_id = c.id
WHERE d.is_deleted = FALSE AND d.tray_id = ?
AND d.order_id IN ({placeholders})
ORDER BY d.create_time
"""
params = [tray_id] + order_ids
self.db.cursor.execute(sql, params)
results = self.db.cursor.fetchall()
data_list = []
for row in results:
data = {
'id': row[0],
'order_id': row[1],
'position': row[2],
'config_id': row[3],
'value': row[4],
'status': row[5],
'remark': row[6],
'name': row[7],
'display_name': row[8],
'data_type': row[9],
'unit': row[10]
}
data_list.append(data)
return data_list
except Exception as e:
logging.error(f"获取未完成的检验数据失败: {str(e)}")
return []
def get_inspection_data_by_order(self, order_id, tray_id):
"""根据工程号获取检验数据
Args:
order_id: 工程号
tray_id: 托盘号
Returns:
list: 检验数据列表
"""
try:
sql = """
SELECT d.id, d.position, d.config_id, d.value, d.status, d.remark,
c.name, c.display_name, c.data_type, c.unit
FROM wsbz_inspection_data d
LEFT JOIN wsbz_inspection_config c ON d.config_id = c.id
WHERE d.order_id = ? AND d.is_deleted = FALSE AND d.tray_id = ?
ORDER BY d.create_time, d.order_id, d.position
"""
params = (order_id, tray_id)
self.db.cursor.execute(sql, params)
results = self.db.cursor.fetchall()
data_list = []
for row in results:
data = {
'id': row[0],
'position': row[1],
'config_id': row[2],
'value': row[3],
'status': row[4],
'remark': row[5],
'name': row[6],
'display_name': row[7],
'data_type': row[8],
'unit': row[9]
}
data_list.append(data)
return data_list
except Exception as e:
logging.error(f"获取检验数据失败: {str(e)}")
return []
def get_package_record(self, tray_id):
"""根据托盘号获取包装记录
Args:
tray_id: 托盘号
Returns:
list: 包装记录列表
"""
try:
sql = """
SELECT order_id,
COALESCE(material, '') as material,
COALESCE(spec, '') as spec,
tray_id,
COALESCE(axis_package_id, '') as axis_package_id,
COALESCE(weight, 0) as weight,
COALESCE(net_weight, 0) as net_weight,
STRFTIME('%Y-%m-%d %H:%M:%S', pack_time) as pack_time
FROM wsbz_inspection_pack_data
WHERE tray_id = ?
AND is_deleted = FALSE
ORDER BY pack_time DESC
"""
params = (tray_id,)
self.db.cursor.execute(sql, params)
results = self.db.cursor.fetchall()
return results
except Exception as e:
logging.error(f"获取包装记录失败: {str(e)}")
return []
def save_package_record(self, order_id, tray_id, label_value, weight_value,net_weight_value, finish_time):
"""保存包装记录
Args:
order_id: 工程号
tray_id: 托盘号
label_value: 标签值
weight_value: 重量值
finish_time: 完成时间
"""
# TODO调用接口获取到工程号对应的其他信息比如材质规格后续完成
try:
sql = """
INSERT INTO wsbz_inspection_pack_data (order_id, tray_id, axis_package_id, weight, net_weight, pack_time, create_time, create_by, update_time, update_by, is_deleted)
VALUES (?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?)
"""
params = (order_id, tray_id, label_value, weight_value, net_weight_value, finish_time, datetime.now(), 'system', datetime.now(), 'system', False)
self.db.cursor.execute(sql, params)
self.db.conn.commit()
except Exception as e:
logging.error(f"保存包装记录失败: {str(e)}")
self.db.conn.rollback()
def delete_inspection_data(self, order_id, tray_id):
"""删除检验数据
Args:
order_id: 工程号
tray_id: 托盘号
"""
try:
sql = """
UPDATE wsbz_inspection_data
SET is_deleted = TRUE
WHERE order_id = ? AND tray_id = ?
"""
params = (order_id, tray_id)
self.db.cursor.execute(sql, params)
self.db.conn.commit()
except Exception as e:
logging.error(f"删除检验数据失败: {str(e)}")
self.db.conn.rollback()
def get_axios_num_by_order_id(self, order_id):
"""获取托盘号对应的轴号"""
try:
sql = """
SELECT max(axis_package_id) as axios_num FROM wsbz_inspection_pack_data WHERE order_id = ?
AND is_deleted = FALSE
"""
params = (order_id,)
self.db.cursor.execute(sql, params)
result = self.db.cursor.fetchone()
return int(result[0]) if result else 0
except Exception as e:
logging.error(f"获取轴号失败: {str(e)}")
return 0
def get_axios_num(self, tray_id):
"""获取托盘号对应的轴号"""
try:
sql = """
SELECT max(axis_package_id) as axios_num FROM wsbz_inspection_pack_data WHERE tray_id = ?
AND is_deleted = FALSE
"""
params = (tray_id,)
self.db.cursor.execute(sql, params)
result = self.db.cursor.fetchone()
return int(result[0]) if result else 0
except Exception as e:
logging.error(f"获取轴号失败: {str(e)}")
return 0
def get_gzl_zl(self,order_id):
"""获取工字轮重量"""
try:
sql = """
SELECT gzl_zl FROM wsbz_order_info WHERE sc_gch = ?
"""
params = (order_id,)
self.db.cursor.execute(sql, params)
result = self.db.cursor.fetchone()
return result[0] if result else 0
except Exception as e:
logging.error(f"获取工字轮重量失败: {str(e)}")
return 0
def get_order_create_time(self, order_id):
"""获取工程号的最早创建时间
Args:
order_id: 工程号
Returns:
str: 创建时间,格式为'YYYY-MM-DD HH:MM:SS'如果未找到则返回None
"""
try:
sql = """
SELECT MIN(create_time) FROM wsbz_inspection_data
WHERE order_id = ? AND is_deleted = FALSE
"""
self.db.cursor.execute(sql, (order_id,))
result = self.db.cursor.fetchone()
return result[0] if result and result[0] else None
except Exception as e:
logging.error(f"获取工程号创建时间失败: {str(e)}")
return None
def get_orders_by_create_time(self, order_ids):
"""按创建时间排序工程号
Args:
order_ids: 工程号列表
Returns:
list: 按创建时间排序的工程号列表
"""
try:
if not order_ids:
return []
# 构建IN子句
placeholders = ','.join(['?' for _ in order_ids])
# 查询每个工程号的最早创建时间并排序
sql = f"""
SELECT order_id, MIN(create_time) as first_create_time
FROM wsbz_inspection_data
WHERE order_id IN ({placeholders}) AND is_deleted = FALSE
GROUP BY order_id
ORDER BY first_create_time
"""
self.db.cursor.execute(sql, order_ids)
results = self.db.cursor.fetchall()
# 提取排序后的工程号
sorted_order_ids = [row[0] for row in results]
# 确保所有传入的工程号都在结果中
for order_id in order_ids:
if order_id not in sorted_order_ids:
sorted_order_ids.append(order_id)
return sorted_order_ids
except Exception as e:
logging.error(f"按创建时间排序工程号失败: {str(e)}")
return order_ids # 出错时返回原始顺序
def get_order_info(self, order_id):
"""获取订单信息
Args:
order_id: 工程号
Returns:
dict: 订单信息字典
"""
try:
sql = """
SELECT data_corp,user_id,user_name,gzl_zl,mzl,ddmo,xpack,sc_gch,qd,spack_type,mxzs,jt,ddnote,code,
type,lable,lib,gzl,maxsl,cz,size,cd,luno,qfqd,pono,xj,ysl,dycz,zh,edit_id,remarks
FROM wsbz_order_info WHERE sc_gch = ?
"""
params = (order_id,)
self.db.cursor.execute(sql, params)
result = self.db.cursor.fetchone()
if not result:
return {}
# 获取列名
column_names = [desc[0] for desc in self.db.cursor.description]
# 转换为字典
result_dict = {}
for i, value in enumerate(result):
if i < len(column_names):
result_dict[column_names[i]] = value
return result_dict
except Exception as e:
logging.error(f"获取订单信息失败: {str(e)}")
return {}
def get_order_others_info(self, order_id, tray_id):
"""获取订单其他信息
Args:
order_id: 工程号
tray_id: 托盘号
Returns:
dict: 订单其他信息字典以name为keyvalue为值
"""
try:
sql = """
SELECT t1.order_id, CASE WHEN t1.position = 12 THEN 'mzl' ELSE name END AS name, value
FROM wsbz_inspection_data t1
LEFT JOIN main.wsbz_inspection_config wic ON t1.config_id = wic.id
WHERE order_id = ?
AND tray_id = ?
AND CASE WHEN t1.position = 12 THEN 'mzl' ELSE name END IS NOT NULL
AND COALESCE(value, '') != ''
"""
params = (order_id, tray_id)
self.db.cursor.execute(sql, params)
results = self.db.cursor.fetchall()
if not results:
return {}
# 将结果转换为字典以name为keyvalue为值
result_dict = {}
for row in results:
if len(row) >= 3: # 确保行至少有3个元素
name = row[1] # name在第二列
value = row[2] # value在第三列
result_dict[name] = value
return result_dict
except Exception as e:
logging.error(f"获取订单其他信息失败: {str(e)}")
return {}