+
+
+
@@ -877,12 +990,15 @@
-
+
- from
- to
+ from
+
+ to
+
@@ -895,95 +1011,96 @@
- No quality control point found
-
- Quality control points define the quality checks which should be
- performed at each operation, for your different products.
+ No quality control point found
+
+
+ Quality control points define the quality checks which should be
+ performed at each operation, for your different products.
+ id="menu_quality_root"
+ name="Quality"
+ web_icon="quality_control,static/description/icon.svg"
+ sequence="150"
+ groups="quality.group_quality_user"/>
+ id="menu_quality_dashboard"
+ name="Overview"
+ action="quality_alert_team_action"
+ parent="menu_quality_root"
+ sequence="5"/>
+ id="menu_quality_control"
+ name="Quality Control"
+ parent="menu_quality_root"
+ sequence="15"/>
+ id="menu_quality_control_points"
+ name="Control Points"
+ parent="menu_quality_control"
+ action="quality_point_action"
+ groups="quality.group_quality_manager"
+ sequence="17"/>
+ id="menu_quality_checks"
+ name="Quality Checks"
+ action="quality_check_action_main"
+ parent="menu_quality_control"
+ sequence="18"/>
+ id="menu_quality_alert"
+ name="Quality Alerts"
+ action="quality_alert_action_check"
+ parent="menu_quality_control"
+ sequence="20"/>
+ id="menu_quality_configuration"
+ name="Configuration"
+ groups="quality.group_quality_manager"
+ parent="menu_quality_root"
+ sequence="25"/>
+ id="menu_quality_config_alert_team"
+ name="Quality Teams"
+ action="quality_alert_team_action_config"
+ parent="menu_quality_configuration"
+ sequence="5"/>
+ id="menu_quality_config_alert_stage"
+ name="Quality Alert Stages"
+ action="quality_alert_stage_action"
+ parent="menu_quality_configuration"
+ groups="base.group_no_one"
+ sequence="15"/>
+ id="menu_config_quality_tags"
+ name="Quality Tags"
+ groups="base.group_no_one"
+ action="quality_tag_action"
+ parent="menu_quality_configuration"
+ sequence="25"/>
+ id="menu_quality_reporting"
+ name="Reporting"
+ groups="quality.group_quality_manager"
+ parent="menu_quality_root"
+ sequence="20"/>
+ id="menu_quality_alert_report"
+ action="quality_alert_action_report"
+ parent="menu_quality_reporting"
+ sequence="6"/>
+ id="menu_quality_check_report"
+ action="quality_check_action_report"
+ parent="menu_quality_reporting"
+ sequence="5"/>
diff --git a/sf_base/security/ir.model.access.csv b/sf_base/security/ir.model.access.csv
index 0a319f34..e33fd23d 100644
--- a/sf_base/security/ir.model.access.csv
+++ b/sf_base/security/ir.model.access.csv
@@ -72,6 +72,7 @@ access_sf_cutting_speed_group_plan_director,sf_cutting_speed_group_plan_director
access_sf_feed_per_tooth_group_purchase_director,sf_feed_per_tooth_group_purchase_director,model_sf_feed_per_tooth,sf_base.group_purchase_director,1,1,0,0
access_sf_feed_per_tooth_group_sale_director,sf_feed_per_tooth_group_sale_director,model_sf_feed_per_tooth,sf_base.group_sale_director,1,1,0,0
access_sf_feed_per_tooth_group_plan_director,sf_feed_per_tooth_group_plan_director,model_sf_feed_per_tooth,sf_base.group_plan_director,1,1,0,0
+access_sf_feed_per_tooth_group_sale_salemanager,sf_feed_per_tooth_group_sale_salemanager,model_sf_feed_per_tooth,sf_base.group_sale_salemanager,1,0,0,0
access_sf_feed_per_tooth,sf_feed_per_tooth,model_sf_feed_per_tooth,base.group_user,1,1,1,0
access_sf_feed_per_tooth_admin,sf_feed_per_tooth_admin,model_sf_feed_per_tooth,base.group_system,1,1,1,0
access_sf_ramping_angle,sf_ramping_angle,model_sf_ramping_angle,base.group_user,1,1,1,1
diff --git a/sf_manufacturing/controllers/controllers.py b/sf_manufacturing/controllers/controllers.py
index d62de74f..3a192e82 100644
--- a/sf_manufacturing/controllers/controllers.py
+++ b/sf_manufacturing/controllers/controllers.py
@@ -228,7 +228,7 @@ class Manufacturing_Connect(http.Controller):
"""
logging.info('PartQualityInspect:%s' % kw)
try:
- res = {'Succeed': True, 'Datas': []}
+ res = {'Succeed': True}
datas = request.httprequest.data
ret = json.loads(datas)
production_id = ret['BillId']
@@ -236,17 +236,40 @@ class Manufacturing_Connect(http.Controller):
workorder = request.env['mrp.workorder'].sudo().search(
[('production_id', '=', production_id), ('routing_type', '=', routing_type)], limit=1)
if workorder:
+ workorder.test_result = ret['Quality']
+ logging.info('制造订单:%s' % workorder.production_id.name)
if 'ReportPaht' in ret:
download_state = request.env['mrp.workorder'].with_user(
request.env.ref("base.user_admin")).download_reportfile_tmp(workorder,
ret['ReportPaht'])
- if download_state is not False:
- request.env['mrp.workorder'].with_user(
+ if download_state == 1:
+ detection_ret = request.env['mrp.workorder'].with_user(
request.env.ref("base.user_admin")).get_detection_file(workorder, ret['ReportPaht'])
+ if detection_ret is True:
+ stock_picking_type = request.env['stock.picking.type'].sudo().search(
+ [('sequence_code', '=', 'SFP')])
+ if stock_picking_type:
+ stock_picking = request.env['stock.picking'].sudo().search(
+ [('product_id', '=', workorder.product_id.id),
+ ('origin', '=', workorder.production_id.origin),
+ ('picking_type_id', '=', stock_picking_type.id)])
+ if stock_picking:
+ quality_check = request.env['quality.check'].sudo().search(
+ [('product_id', '=', workorder.product_id.id),
+ ('picking_id', '=', stock_picking.id)])
+ if quality_check:
+ logging.info('质检单:%s' % quality_check.name)
+ quality_check.write({'report_pdf': workorder.detection_report,
+ 'report_result': workorder.test_result})
+ elif download_state == 2:
+ res = {'Succeed': False, 'ErrorCode': 205,
+ 'Error': 'ReportPaht中的工件号与制造订单%s不匹配,请检查ReportPaht是否正确' % workorder.production_id.name}
else:
res = {'Succeed': False, 'ErrorCode': 204, 'Error': '检测报告文件从FTP拉取失败'}
else:
res = {'Succeed': False, 'ErrorCode': 203, 'Error': '未传ReportPaht字段'}
+ else:
+ res = {'Succeed': False, 'ErrorCode': 206, 'Error': '未查询到工单'}
except Exception as e:
res = {'Succeed': False, 'ErrorCode': 202, 'Error': e}
logging.info('PartQualityInspect error:%s' % e)
diff --git a/sf_manufacturing/models/mrp_workorder.py b/sf_manufacturing/models/mrp_workorder.py
index 11c0c2d8..751a3dd9 100644
--- a/sf_manufacturing/models/mrp_workorder.py
+++ b/sf_manufacturing/models/mrp_workorder.py
@@ -95,8 +95,7 @@ class ResMrpWorkOrder(models.Model):
Y10_axis = fields.Float(default=0)
Z10_axis = fields.Float(default=0)
X_deviation_angle = fields.Integer(string="X轴偏差度", default=0)
- test_results = fields.Selection([("合格", "合格"), ("返工", "返工"), ("报废", "报废")], default='合格',
- string="检测结果")
+ test_result = fields.Char("检测结果")
cnc_ids = fields.One2many("sf.cnc.processing", 'workorder_id', string="CNC加工程序")
cmm_ids = fields.One2many("sf.cmm.program", 'workorder_id', string="CMM程序")
tray_code = fields.Char(string="托盘编码")
@@ -432,7 +431,7 @@ class ResMrpWorkOrder(models.Model):
"""
重新生成制造订单或者重新生成工单
"""
- if self.test_results == '报废':
+ if self.test_result == '报废':
values = self.env['mrp.production'].create_production1_values(self.production_id)
productions = self.env['mrp.production'].with_user(SUPERUSER_ID).sudo().with_company(
self.production_id.company_id).create(
@@ -464,7 +463,7 @@ class ResMrpWorkOrder(models.Model):
'mail.message_origin_link',
values={'self': production, 'origin': origin_production},
subtype_id=self.env.ref('mail.mt_note').id)
- if self.test_results == '返工':
+ if self.test_result == '返工':
productions = self.production_id
# self.env['stock.move'].sudo().create(productions._get_moves_raw_values())
# self.env['stock.move'].sudo().create(productions._get_moves_finished_values())
@@ -631,33 +630,34 @@ class ResMrpWorkOrder(models.Model):
# 将FTP的检测报告文件下载到临时目录
def download_reportfile_tmp(self, workorder, reportpath):
+ logging.info('reportpath:%s' % reportpath)
production_no = workorder.production_id.name.replace('/', '_')
+ # ftp地址
remotepath = os.path.join('/', production_no, 'detection')
- serverdir = os.path.join('/tmp', production_no, 'detection')
- ftp_resconfig = self.env['res.config.settings'].get_values()
- ftp = FtpController(str(ftp_resconfig['ftp_host']), int(ftp_resconfig['ftp_port']),
- ftp_resconfig['ftp_user'],
- ftp_resconfig['ftp_password'])
- download_state = ftp.download_reportfile_tree(remotepath, serverdir, reportpath)
- logging.info('download_state:%s' % download_state)
+ logging.info('ftp地址:%s' % remotepath)
+ if remotepath in reportpath:
+ # 服务器内临时地址
+ serverdir = os.path.join('/tmp', production_no, 'detection')
+ ftp_resconfig = self.env['res.config.settings'].get_values()
+ ftp = FtpController(str(ftp_resconfig['ftp_host']), int(ftp_resconfig['ftp_port']),
+ ftp_resconfig['ftp_user'],
+ ftp_resconfig['ftp_password'])
+ download_state = ftp.download_reportfile_tree(remotepath, serverdir, reportpath)
+ logging.info('download_state:%s' % download_state)
+ else:
+ download_state = 2
return download_state
# 根据中控系统提供的检测文件地址去ftp里对应的制造订单里获取
def get_detection_file(self, workorder, reportPath):
- logging.info('workorder:%s' % workorder.name)
- logging.info('制造订单:%s' % workorder.production_id.name)
- logging.info('reportPath:%s' % reportPath)
serverdir = os.path.join('/tmp', reportPath).replace('//', '/')
- logging.info('serverdir:%s' % serverdir)
+ logging.info('get_detection_file-serverdir:%s' % serverdir)
for root, dirs, files in os.walk(serverdir):
for f in files:
- logging.info('f:%s' % f)
- if os.path.splitext(f)[1] == ".pdf":
- full_path = os.path.join(serverdir, root, f)
- logging.info('检测文件路径:%s' % full_path)
- if full_path is not False:
- workorder.detection_report = base64.b64encode(
- open(full_path, 'rb').read())
+ if f in reportPath:
+ workorder.detection_report = base64.b64encode(
+ open(serverdir, 'rb').read())
+ return True
class CNCprocessing(models.Model):
@@ -686,15 +686,11 @@ class CNCprocessing(models.Model):
# mrs下发编程单创建CNC加工
def cnc_processing_create(self, cnc_workorder, ret, program_path, program_path_tmp):
- logging.info('ret:%s' % ret)
- logging.info('program_path_tmp:%s' % program_path_tmp)
- logging.info('program_path:%s' % program_path)
for obj in ret['programming_list']:
workorder = self.env['mrp.workorder'].search([('production_id.name', '=', ret['production_order_no']),
('processing_panel', '=', obj['processing_panel']),
('routing_type', '=', 'CNC加工')])
logging.info('workorder:%s' % workorder.id)
- logging.info('obj:%s' % obj)
if obj['program_name'] in program_path:
logging.info('obj:%s' % obj['program_name'])
cnc_processing = self.env['sf.cnc.processing'].create({
@@ -739,9 +735,6 @@ class CNCprocessing(models.Model):
if f in program_path:
# if cnc_processing.program_name == f.split('.')[0]:
cnc_file_path = os.path.join(serverdir, root, f)
- logging.info('cnc_file_path:%s' % cnc_file_path)
- logging.info('program_path:%s' % program_path)
- logging.info('f:%s' % f)
self.write_file(cnc_file_path, cnc_processing)
# 创建附件(nc文件)
diff --git a/sf_manufacturing/security/ir.model.access.csv b/sf_manufacturing/security/ir.model.access.csv
index c3fceb02..a54f6bf5 100644
--- a/sf_manufacturing/security/ir.model.access.csv
+++ b/sf_manufacturing/security/ir.model.access.csv
@@ -4,6 +4,7 @@ access_sf_cnc_processing_manager,sf_cnc_processing,model_sf_cnc_processing,sf_ba
access_sf_cmm_program_group_sf_mrp_user,sf_cmm_program_group_sf_mrp_user,model_sf_cmm_program,sf_base.group_sf_mrp_user,1,0,0,0
access_sf_cmm_program_group_sf_mrp_manager,sf_cmm_program_group_sf_mrp_manager,model_sf_cmm_program,sf_base.group_sf_mrp_manager,1,0,0,0
access_sf_model_type,sf_model_type,model_sf_model_type,sf_base.group_sf_mrp_user,1,0,0,0
+access_sf_model_type_admin,sf_model_type_admin,model_sf_model_type,base.group_system,1,1,1,0
access_sf_model_type_manager,sf_model_type,model_sf_model_type,sf_base.group_sf_mrp_manager,1,1,1,0
access_sf_model_type_group_sale_director,sf_model_type_group_sale_director,model_sf_model_type,sf_base.group_sale_director,1,0,0,0
access_sf_model_type_group_purchase_director,sf_model_type_group_purchase_director,model_sf_model_type,sf_base.group_purchase_director,1,0,0,0
diff --git a/sf_manufacturing/views/mrp_workorder_view.xml b/sf_manufacturing/views/mrp_workorder_view.xml
index ee1eb751..5a09969e 100644
--- a/sf_manufacturing/views/mrp_workorder_view.xml
+++ b/sf_manufacturing/views/mrp_workorder_view.xml
@@ -143,10 +143,10 @@
-
+
-
+
计划加工时间
@@ -434,9 +434,10 @@
-
+
-
+