Files
test/sf_maintenance/models/sf_maintenance.py
2023-10-07 17:26:09 +08:00

624 lines
31 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.

# -*- coding: utf-8 -*-
import base64
from odoo import api, fields, models, SUPERUSER_ID, _
from odoo.exceptions import UserError
import logging
from datetime import date, datetime, timedelta
import requests
import json
from odoo.addons.sf_base.commons.common import Common
class SfMaintenanceEquipmentCategory(models.Model):
_inherit = 'maintenance.equipment.category'
_description = '设备类别'
equipment_type = fields.Selection([('机床', '机床'), ('机器人', '机器人'), ('AGV小车', 'AGV小车'), ('检测设备', '检测设备')], string='类型', default='机床')
class SfMaintenanceEquipment(models.Model):
_inherit = 'maintenance.equipment'
_description = '设备'
crea_url = "/api/machine_tool/create"
def get_no(self):
partner = self.env['maintenance.equipment'].sudo().search(
[('MTcode', '!=', '')],
limit=1,
order="id desc")
if not partner:
num = "%04d" % 1
else:
m = int(partner.MTcode) + 1
num = "%04d" % m
return num
equipment_maintenance_standards_ids = fields.Many2many('equipment.maintenance.standards',
'sf_maintenance_equipment_ids', string='设备维保标准')
eq_maintenance_id = fields.Many2one('equipment.maintenance.standards', string='设备保养标准',
domain="[('maintenance_type','=','保养')]")
overhaul_date = fields.Date(string='下次预防检修')
overhaul_period = fields.Integer(string='预防检修频次')
overhaul_duration = fields.Float(string='检修时长')
overhaul_id = fields.Many2one('equipment.maintenance.standards', string='设备检修标准',
domain="[('maintenance_type','=','检修')]")
@api.onchange('eq_maintenance_id', 'overhaul_id')
def _compute_equipment_maintenance_standards_ids(self):
for record in self:
if record.eq_maintenance_id and record.overhaul_id:
record.equipment_maintenance_standards_ids = [
(6, 0, [record.eq_maintenance_id.id, record.overhaul_id.id])]
break
if record.eq_maintenance_id:
record.equipment_maintenance_standards_ids = [(6, 0, [record.eq_maintenance_id.id])]
break
if record.overhaul_id:
record.equipment_maintenance_standards_ids = [(6, 0, [record.overhaul_id.id])]
break
else:
record.equipment_maintenance_standards_ids = False
MTcode = fields.Char("编码", default=get_no)
created_user = fields.Many2one('res.users', string='创建人', default=lambda self: self.env.user)
equipment_type = fields.Selection([('机床', '机床'), ('机器人', '机器人'), ('AGV小车', 'AGV小车'), ('检测设备', '检测设备')], compute='_compute_category_id')
@api.depends('category_id')
def _compute_category_id(self):
for record in self:
if record:
record.equipment_type = record.category_id.equipment_type
code = fields.Char('机台号')
name = fields.Char('名称')
knife_type = fields.Selection(
[("BT40", "BT40"), ("BT30", "BT30"), ("BT50", "BT50")],
default="", string="刀把类型")
number_of_knife_library = fields.Integer('刀库数量(把)')
rotate_speed = fields.Integer('转速')
number_of_axles = fields.Selection(
[("三轴", "三轴"), ("四轴", "四轴"), ("五轴", "五轴")],
default="", string="轴数")
# 加工进程
x_axis = fields.Integer('X轴')
y_axis = fields.Integer('Y轴')
z_axis = fields.Integer('Z轴')
b_axis = fields.Integer('B轴')
c_axis = fields.Integer('C轴')
remark = fields.Char('备注')
is_binding = fields.Boolean('是否绑定机床', default=False)
precision_min = fields.Float('X轴定位精度min(mm)', digits=(12, 3))
precision_max = fields.Float('X轴定位精度max(mm)', digits=(12, 3))
control_system_id = fields.Many2one('sf.machine.control_system',
string="控制系统")
# 多个机床型号对应一个机床
brand_id = fields.Many2one('sf.machine.brand', string='品牌')
type_id = fields.Many2one('sf.machine_tool.type', '型号')
state = fields.Selection(
[("正常", "正常"), ("故障", "故障"), ("不可用", "不可用")],
default='正常', string="机床状态")
# 0606新增字段
machine_tool_picture = fields.Binary('图片')
heightened_way = fields.Selection([
('sifudianji', '伺服电机驱动'),
('youyagang', '油压缸驱动'),
('chilunjia', '齿轮架驱动')
], string="主轴加高方式", default='sifudianji')
workpiece_load = fields.Char('工件最大负载(kg)')
lead_screw = fields.Char('丝杆')
workbench_L = fields.Char('工作台长度(mm)')
workbench_W = fields.Char('工作台宽度(mm)')
guide_rail = fields.Char('导轨')
machine_tool_L = fields.Char('机床长度(mm)')
machine_tool_W = fields.Char('机床宽度(mm)')
machine_tool_H = fields.Char('机床高度(mm)')
feed_speed = fields.Char('进给速度(mm/min)')
tool_speed = fields.Char('刀具速度(m/min)')
distance_min = fields.Char('主轴端面至工作台面距离MIN(mm)')
distance_max = fields.Char('主轴端面至工作台面距离MAX(mm)')
taper = fields.Char('主轴锥度(°)')
torque = fields.Char('主轴电机扭矩(n/m)')
motor_power = fields.Char('主轴电机功率(kw)')
tool_quality_max = fields.Char('刀具最大质量(kg)')
tool_long_max = fields.Char('刀具最大长度(mm)')
tool_diameter_max = fields.Char('刀具刀径max(mm)')
tool_diameter_min = fields.Char('刀具刀径min(mm)')
machine_tool_category = fields.Many2one('sf.machine_tool.category', string='机床类型')
# 一个机床对应一個加工工厂,一个加工工厂对应多个机床
factory_id = fields.Many2one('res.partner', string='所属工厂',
domain="[('is_factory', '=', True)]")
# 一个机床对应一个供应商,一个供应商对应多个机床
supplier_id = fields.Many2one('res.partner', string='制造商',
domain="[('is_vendor', '=', True)]")
registration_date = fields.Date('注册日期')
state_zc = fields.Selection([("已注册", "已注册"), ("未注册", "未注册")], string="注册状态", default='未注册',
tracking=True)
active = fields.Boolean('有效', default=True)
# 多个型号对应一个机床
machine_tool_id = fields.Many2one('sf.machine_tool', '机床')
sf_maintenance_logs_ids = fields.One2many('sf.maintenance.logs', 'maintenance_equipment_id', '设备故障日志')
def name_get(self):
result = []
for parameter in self:
if parameter.code:
name = parameter.name + '-' + parameter.code
else:
name = parameter.name
result.append((parameter.id, name))
return result
@api.constrains('rotate_speed')
def _check_rotate_speed(self):
if self.rotate_speed <= 0:
raise UserError("转速不能为0")
@api.constrains('precision')
def _check_precision(self):
if self.precision <= 0.00:
raise UserError("加工精度不能为0")
@api.constrains('number_of_knife_library')
def _check_number_of_knife_library(self):
if self.number_of_knife_library <= 0:
raise UserError("刀库数量不能为0")
@api.constrains('x_axis')
def _check_x_axis(self):
if self.x_axis <= 0:
raise UserError("加工行程里x轴不能为0")
@api.constrains('y_axis')
def _check_y_axis(self):
if self.y_axis <= 0:
raise UserError("加工行程里y轴不能为0")
@api.constrains('z_axis')
def _check_z_axis(self):
if self.z_axis <= 0:
raise UserError("加工行程里z轴不能为0")
@api.constrains('b_axis')
def _check_b_axis(self):
if self.number_of_axles == '四轴':
print(self.number_of_axles)
if self.b_axis <= 0:
raise UserError("加工行程里b轴不能为0")
@api.constrains('c_axis')
def _check_c_axis(self):
if self.number_of_axles == '五轴':
if self.c_axis <= 0:
raise UserError("加工行程里c轴不能为0")
@api.onchange('type_id')
def get_type_info(self):
for item in self:
item.knife_type = item.type_id.knife_type
item.number_of_knife_library = item.type_id.number_of_knife_library
item.number_of_axles = item.type_id.number_of_axles
item.rotate_speed = item.type_id.rotate_speed
item.precision_min = item.type_id.precision_min
item.precision_max = item.type_id.precision_max
item.control_system_id = item.type_id.control_system_id
item.x_axis = item.type_id.x_axis
item.y_axis = item.type_id.y_axis
item.z_axis = item.type_id.z_axis
item.b_axis = item.type_id.b_axis
item.c_axis = item.type_id.c_axis
item.machine_tool_picture = item.type_id.machine_tool_picture
item.heightened_way = item.type_id.heightened_way
item.workpiece_load = item.type_id.workpiece_load
item.lead_screw = item.type_id.lead_screw
item.workbench_L = item.type_id.workbench_L
item.workbench_W = item.type_id.workbench_W
item.guide_rail = item.type_id.guide_rail
item.machine_tool_L = item.type_id.machine_tool_L
item.machine_tool_W = item.type_id.machine_tool_W
item.machine_tool_H = item.type_id.machine_tool_H
item.feed_speed = item.type_id.feed_speed
item.tool_speed = item.type_id.tool_speed
item.distance_min = item.type_id.distance_min
item.distance_max = item.type_id.distance_max
item.taper = item.type_id.taper
item.torque = item.type_id.torque
item.motor_power = item.type_id.motor_power
item.tool_quality_max = item.type_id.tool_quality_max
item.tool_long_max = item.type_id.tool_long_max
item.tool_diameter_max = item.type_id.tool_diameter_max
item.tool_diameter_min = item.type_id.tool_diameter_min
item.machine_tool_category = item.type_id.machine_tool_category.id
item.brand_id = item.type_id.brand_id.id
# AGV小车设备参数
AGV_L = fields.Char('设备尺寸(长)')
AGV_W = fields.Char('设备尺寸(宽)')
AGV_H = fields.Char('设备尺寸(高)')
AGV_goods_L = fields.Char('载货尺寸(长)')
AGV_goods_W = fields.Char('载货尺寸(宽)')
AGV_goods_H = fields.Char('载货尺寸(高)')
AGV_velocity = fields.Char('标准速度')
AGV_velocity_min = fields.Char('标准速度(最小)')
AGV_velocity_max = fields.Char('标准速度(最大)')
AGV_Lifting_height = fields.Char('升降高度(max)')
AGV_ground_clearance = fields.Char('最小离地高度')
AGV_turning_radius = fields.Char('最小转弯半径')
AGV_gradeability_max = fields.Integer('最大爬坡度')
AGV_parking_accuracy = fields.Char('停车精度')
AGV_load_weight_max = fields.Char('最大负载重量')
AGV_weight = fields.Char('本体总重量')
AGV_job_duration = fields.Char('连续作业时长')
AGV_transfer_mode = fields.Char('移载方式')
AGV_drive_motor_power = fields.Char('驱动电机功率')
AGV_hoist_motor_power = fields.Char('提升电机功率')
AGV_drive_motor_speed_ratio = fields.Char('驱动电机速比')
AGV_veer_motor_power = fields.Char('转向电机功率')
AGV_veer_motor_speed_ratio = fields.Char('转向电机速比')
AGV_move_motor_power = fields.Char('前移电机功率')
AGV_move_motor_speed_ratio = fields.Char('前移电机速比')
AGV_drive_mode = fields.Char('驱动方式')
AGV_navigation_mode = fields.Char('导航方式')
AGV_communication_mode = fields.Char('通讯方式')
AGV_direction_travel = fields.Char('行走方向')
AGV_power_requirements = fields.Char('电源要求')
AGV_charge_mode = fields.Selection([('手动', '手动'), ('自动', '自动')], string='充电方式')
AGV_security = fields.Char('安全防护')
AGV_operating_temperature = fields.Char('环境温度')
AGV_operating_humidity = fields.Char('环境湿度')
# 三元检测设备参数
detect_L = fields.Char('设备尺寸(长)')
detect_W = fields.Char('设备尺寸(宽)')
detect_H = fields.Char('设备尺寸(高)')
detect_x_axis = fields.Char('X轴')
detect_y_axis = fields.Char('Y轴')
detect_z_axis = fields.Char('Z轴')
detect_precision = fields.Char('测量精度')
detect_measurement_mode = fields.Selection([('光栅尺', '光栅尺'), ('容栅', '容栅'), ('磁栅', '磁栅'), ('激光干涉仪', '激光干涉仪')], string='测量方式')
detect_resolution = fields.Char('分辨率')
detect_load_weight_max = fields.Char('最大负载重量')
detect_weight = fields.Char('本体总重量')
detect_measurement_length = fields.Char('深孔测量长度(max)')
detect_control_mode = fields.Char('控制方式')
detect_balance_mode_for_Z = fields.Char('Z轴平衡方式')
detect_zoom_objective_magnification = fields.Char('变焦物镜倍率')
detect_magnification = fields.Char('放大倍率')
detect_working_distance = fields.Char('工作距离')
detect_locking_mode = fields.Char('锁紧方式')
detect_pressurized_air = fields.Char('压缩空气')
detect_object_field_of_view_max = fields.Char('物方视场(最大)')
detect_object_field_of_view_min = fields.Char('物方视场(最小)')
detect_power_requirements = fields.Char('电源要求')
detect_operating_temperature = fields.Char('环境温度')
detect_operating_humidity = fields.Char('环境湿度')
# 机器人设备参数
robot_gripping_of_workpieces_L = fields.Char('可抓取工件(长)')
robot_gripping_of_workpieces_W = fields.Char('可抓取工件(宽)')
robot_gripping_of_workpieces_H = fields.Char('可抓取工件(高)')
robot_radius_of_the_boom = fields.Char('展臂半径')
robot_load_weight_max = fields.Char('最大负载重量')
robot_weight = fields.Char('本体总重量')
robot_repeatable_positioning_accuracy = fields.Char('重复定位精度')
robot_axis_num = fields.Selection([('2轴', '2轴'), ('3轴', '3轴'), ('4轴', '4轴'), ('5轴', '5轴'), ('6轴', '6轴'), ('7轴', '7轴'), ('8轴', '8轴')], string='轴数')
axis_ids = fields.One2many('sf.robot.axis.num', 'equipment_id', string='动作范围')
robot_track_dimensions_L = fields.Char('轨道尺寸(长)')
robot_track_dimensions_W = fields.Char('轨道尺寸(宽)')
robot_track_dimensions_H = fields.Char('轨道尺寸(高)')
robot_drive_mode = fields.Char('驱动方式')
robot_installation_method = fields.Selection([('置地式', '置地式'), ('壁挂式', '壁挂式'), ('倒挂式', '倒挂式')], string='安装方式')
robot_operating_temperature = fields.Char('环境温度')
robot_operating_humidity = fields.Char('环境湿度')
# 注册同步机床
def enroll_machine_tool(self):
sf_sync_config = self.env['res.config.settings'].get_values()
token = sf_sync_config['token']
sf_secret_key = sf_sync_config['sf_secret_key']
headers = Common.get_headers(self, token, sf_secret_key)
strurl = sf_sync_config['sf_url'] + self.crea_url
objs_all = self.env['maintenance.equipment'].search([('MTcode', '=', self.MTcode)])
machine_tool_list = []
if objs_all:
for item in objs_all:
if item.machine_tool_picture != False:
image = base64.b64encode(item.machine_tool_picture).decode('utf-8')
else:
image = False
val = {
'MTcode': item.MTcode,
'factory_token': token,
'id': item.id,
'name': item.name,
'code': item.code,
'precision': item.precision,
'knife_type': item.knife_type,
'number_of_knife_library': item.number_of_knife_library,
'rotate_speed': item.rotate_speed,
'number_of_axles': item.number_of_axles,
'control_system_id': self.env['sf.machine.control_system'].search(
[('id', '=', item.control_system_id.id)]).code,
'type_id': self.env['sf.machine_tool.type'].search([('id', '=', item.type_id.id)]).code,
'brand_id': self.env['sf.machine.brand'].search([('id', '=', item.brand_id.id)]).code,
'supplier_id': item.supplier_id.id,
'x_axis': item.x_axis,
'y_axis': item.y_axis,
'z_axis': item.z_axis,
'b_axis': item.b_axis,
'c_axis': item.c_axis,
'state': item.state,
'active': item.active,
'machine_tool_picture': image,
'heightened_way': item.heightened_way,
'workpiece_load': item.workpiece_load,
'lead_screw': item.lead_screw,
'workbench_L': item.workbench_L,
'workbench_W': item.workbench_W,
'guide_rail': item.guide_rail,
'machine_tool_L': item.machine_tool_L,
'machine_tool_W': item.machine_tool_W,
'machine_tool_H': item.machine_tool_H,
'feed_speed': item.feed_speed,
'tool_speed': item.tool_speed,
'distance': item.distance,
'taper': item.taper,
'torque': item.torque,
'motor_power': item.motor_power,
'tool_quality_max': item.tool_quality_max,
'tool_long_max': item.tool_long_max,
'tool_diameter_max': item.tool_diameter_max,
'machine_tool_category': item.machine_tool_category.code,
}
machine_tool_list.append(val)
# kw = machine_tool_list
kw = json.dumps(machine_tool_list, ensure_ascii=False)
r = requests.post(strurl, json={}, data={'kw': kw, 'token': token}, headers=headers)
ret = r.json()
self.code = ret['message']
self.state_zc = "已注册"
if r == 200:
return "机床注册成功"
else:
raise UserError("没有注册机床信息")
# 修改原生方法,生成维保日期
@api.depends('effective_date', 'period', 'maintenance_ids.request_date', 'maintenance_ids.close_date',
'overhaul_period')
def _compute_next_maintenance(self):
date_now = fields.Date.context_today(self)
equipments = self.filtered(lambda x: x.period > 0)
if equipments:
for equipment in equipments:
next_maintenance_todo = self.env['maintenance.request'].search([
('equipment_id', '=', equipment.id),
('sf_maintenance_type', '=', '保养'),
('stage_id.done', '!=', True),
('close_date', '=', False)], order="request_date asc", limit=1)
last_maintenance_done = self.env['maintenance.request'].search([
('equipment_id', '=', equipment.id),
('sf_maintenance_type', '=', '保养'),
('stage_id.done', '=', True),
('close_date', '!=', False)], order="close_date desc", limit=1)
if next_maintenance_todo and last_maintenance_done:
next_date = next_maintenance_todo.request_date
date_gap = next_maintenance_todo.request_date - last_maintenance_done.close_date
# If the gap between the last_maintenance_done and the next_maintenance_todo one is bigger than 2 times the period and next request is in the future
# We use 2 times the period to avoid creation too closed request from a manually one created
if date_gap > timedelta(0) and date_gap > timedelta(
days=equipment.period) * 2 and next_maintenance_todo.request_date > date_now:
# If the new date still in the past, we set it for today
if last_maintenance_done.close_date + timedelta(days=equipment.period) < date_now:
next_date = date_now
else:
next_date = last_maintenance_done.close_date + timedelta(days=equipment.period)
elif next_maintenance_todo:
next_date = next_maintenance_todo.request_date
date_gap = next_maintenance_todo.request_date - date_now
# If next maintenance to do is in the future, and in more than 2 times the period, we insert an new request
# We use 2 times the period to avoid creation too closed request from a manually one created
if date_gap > timedelta(0) and date_gap > timedelta(days=equipment.period) * 2:
next_date = date_now + timedelta(days=equipment.period)
elif last_maintenance_done:
next_date = last_maintenance_done.close_date + timedelta(days=equipment.period)
# If when we add the period to the last maintenance done and we still in past, we plan it for today
if next_date < date_now:
next_date = date_now
else:
next_date = equipment.effective_date + timedelta(days=equipment.period)
equipment.next_action_date = next_date
else:
self.next_action_date = False
overhaul_equipments = self.filtered(lambda x: x.overhaul_period > 0)
if overhaul_equipments:
for equipment in overhaul_equipments:
next_maintenance_todo = self.env['maintenance.request'].search([
('equipment_id', '=', equipment.id),
('sf_maintenance_type', '=', '检修'),
('stage_id.done', '!=', True),
('close_date', '=', False)], order="request_date asc", limit=1)
last_maintenance_done = self.env['maintenance.request'].search([
('equipment_id', '=', equipment.id),
('sf_maintenance_type', '=', '检修'),
('stage_id.done', '=', True),
('close_date', '!=', False)], order="close_date desc", limit=1)
if next_maintenance_todo and last_maintenance_done:
next_date = next_maintenance_todo.request_date
date_gap = next_maintenance_todo.request_date - last_maintenance_done.close_date
# If the gap between the last_maintenance_done and the next_maintenance_todo one is bigger than 2 times the period and next request is in the future
# We use 2 times the period to avoid creation too closed request from a manually one created
if date_gap > timedelta(0) and date_gap > timedelta(
days=equipment.overhaul_period) * 2 and next_maintenance_todo.request_date > date_now:
# If the new date still in the past, we set it for today
if last_maintenance_done.close_date + timedelta(days=equipment.overhaul_period) < date_now:
next_date = date_now
else:
next_date = last_maintenance_done.close_date + timedelta(days=equipment.overhaul_period)
elif next_maintenance_todo:
next_date = next_maintenance_todo.request_date
date_gap = next_maintenance_todo.request_date - date_now
# If next maintenance to do is in the future, and in more than 2 times the period, we insert an new request
# We use 2 times the period to avoid creation too closed request from a manually one created
if date_gap > timedelta(0) and date_gap > timedelta(days=equipment.overhaul_period) * 2:
next_date = date_now + timedelta(days=equipment.overhaul_period)
elif last_maintenance_done:
next_date = last_maintenance_done.close_date + timedelta(days=equipment.overhaul_period)
# If when we add the period to the last maintenance done and we still in past, we plan it for today
if next_date < date_now:
next_date = date_now
else:
next_date = equipment.effective_date + timedelta(days=equipment.overhaul_period)
equipment.overhaul_date = next_date
else:
self.overhaul_date = False
# 拼接维保请求字符串
def _prepare_maintenance_request_vals(self, date):
self.ensure_one()
return {
'name': _('Preventive Maintenance - %s', self.name),
'request_date': date,
'schedule_date': date,
'category_id': self.category_id.id,
'equipment_id': self.id,
'maintenance_type': 'preventive',
'owner_user_id': self.owner_user_id.id,
'user_id': self.technician_user_id.id,
'maintenance_team_id': self.maintenance_team_id.id,
'duration': self.maintenance_duration,
'company_id': self.company_id.id or self.env.company.id,
'equipment_maintenance_id': self.eq_maintenance_id.id,
'sf_maintenance_type': '保养'
}
# 拼接维保请求字符串
def _prepare_maintenance_request_vals1(self, date):
self.ensure_one()
return {
'name': _('Preventive Maintenance - %s', self.name),
'request_date': date,
'schedule_date': date,
'category_id': self.category_id.id,
'equipment_id': self.id,
'maintenance_type': 'preventive',
'owner_user_id': self.owner_user_id.id,
'user_id': self.technician_user_id.id,
'maintenance_team_id': self.maintenance_team_id.id,
'duration': self.overhaul_duration,
'company_id': self.company_id.id or self.env.company.id,
'equipment_maintenance_id': self.overhaul_id.id,
'sf_maintenance_type': '检修'
}
# 创建维保请求
def _create_new_request(self, date):
self.ensure_one()
vals = self._prepare_maintenance_request_vals(date)
maintenance_requests = self.env['maintenance.request'].create(vals)
return maintenance_requests
def _create_new_request1(self, date):
self.ensure_one()
vals = self._prepare_maintenance_request_vals1(date)
maintenance_requests = self.env['maintenance.request'].create(vals)
return maintenance_requests
# 生成维保请求定时器
@api.model
def _cron_generate_requests(self):
"""
Generates maintenance request on the next_action_date or today if none exists
"""
for equipment in self.search([('period', '>', 0)]):
next_requests = self.env['maintenance.request'].search([('stage_id.done', '=', False),
('equipment_id', '=', equipment.id),
('maintenance_type', '=', 'preventive'),
('request_date', '=', equipment.next_action_date),
('sf_maintenance_type', '=', '保养')])
if not next_requests:
equipment._create_new_request(equipment.next_action_date)
for equipment in self.search([('overhaul_period', '>', 0)]):
next_requests = self.env['maintenance.request'].search([('stage_id.done', '=', False),
('equipment_id', '=', equipment.id),
('maintenance_type', '=', 'preventive'),
('request_date', '=', equipment.overhaul_date),
('sf_maintenance_type', '=', '检修')])
if not next_requests:
equipment._create_new_request1(equipment.overhaul_date)
image_id = fields.Many2many('maintenance.equipment.image', 'equipment_id', string='设备图文')
class MaintenanceStandardImage(models.Model):
_name = 'maintenance.equipment.image'
_description = '能力特征库'
active = fields.Boolean('有效', default=True)
name = fields.Char('名称')
image = fields.Binary(string='图文')
type = fields.Selection(
[('加工能力', '加工能力'), ('刀尖特征', '刀尖特征'), ('柄部类型', '柄部类型'), ('走刀方向', '走刀方向'), ('冷却液', '冷却液')],
string='特征')
equipment_id = fields.Many2many('maintenance.equipment', 'image_id', string='设备')
@api.model
def name_search(self, name='', args=None, operator='ilike', limit=100):
# 调用父类的name_search方法获取原始的结果列表
res = super().name_search(name, args, operator, limit)
# 定义一个空字典用来存储id和name的映射关系
name_dict = {}
# 遍历结果列表将id和name存入字典中
for item in res:
id = item[0]
name = item[1]
name_dict[id] = name
# 根据id列表搜索符合条件的记录
records = self.browse(name_dict.keys())
# 定义一个新的结果列表用来存储修改后的结果
new_res = []
# 遍历每条记录
for record in records:
# 获取记录的idname和image属性
id = record.id
name = name_dict[id]
image = record.image
# 如果image不为空将其转换为data URI scheme
if image:
data_uri = f"data:image/png;base64,{image.decode('utf-8')}"
else:
data_uri = ""
# 将这三个属性组成一个数组,并添加到结果列表中 result.append([id, name, data_uri]) # 返回结果列表 return result
new_res.append([id, name, data_uri])
# 返回新的结果列表
return new_res
class SfRobotAxisNum(models.Model):
_name = 'sf.robot.axis.num'
_description = '机器人轴参数'
name = fields.Char('*轴')
angle_min = fields.Char('最小角度-(°)')
angle_max = fields.Char('最大角度+(°)')
velocity = fields.Char('最大速度(°/s)')
weight = fields.Char('最大负载(kg)')
permissible_load_torque = fields.Char('允许负载扭矩(N-m)')
permissible_inertial_torque = fields.Char('允许惯性扭矩(kg-m²)')
equipment_id = fields.Many2one('maintenance.equipment', string='机器人', domain="[('equipment_type', '=', '机器人')]")