mirror of
https://github.com/OCA/manufacture.git
synced 2025-01-28 16:37:15 +02:00
[IMP] quality_control_issue: add scrap feature.
This commit is contained in:
committed by
Jordi Ballester Alomar
parent
e16506f189
commit
4075ce1ffe
@@ -2,3 +2,4 @@
|
||||
# Add a repository url and branch if you need a forked version
|
||||
product-attribute
|
||||
stock-logistics-warehouse
|
||||
stock-logistics-workflow
|
||||
|
||||
@@ -6,17 +6,59 @@
|
||||
Quality Control Issue
|
||||
=====================
|
||||
|
||||
WIP
|
||||
|
||||
This module extends the functionality of quality Control to allow you to
|
||||
report and manage quality control issues.
|
||||
|
||||
Configuration
|
||||
=============
|
||||
|
||||
To configure this module in order to take advantage of the kanban views you
|
||||
need to create the stages for *issues* and *problems*. To **create** stages in
|
||||
any kanban view click on *Add New Column*. Then you can **reorder** the stages
|
||||
just dragging them.
|
||||
|
||||
In created stages you can **configure** them clicking on the gear button that
|
||||
appears at the right of the stage name and clicking on *Edit*. Note the
|
||||
following behaviors:
|
||||
|
||||
* You can set a *Quality Control Team*.
|
||||
|
||||
- Stages with no team set will be shared by all teams.
|
||||
- Stages with a team associated will be only available for that specific
|
||||
team.
|
||||
|
||||
* In Issue Stages you can also relate a *QC State* to the stage.
|
||||
|
||||
- When you move to a different stage an issue with *QC state* defined the
|
||||
state of the issue will also change according to it.
|
||||
- The other way around, if you change the state, the system will look for
|
||||
an appropriate stage and if existing the issue will be move to that stage.
|
||||
- If you change the *QC team* of an issue, the system will get the default
|
||||
stage for that team and apply it to the issue.
|
||||
|
||||
Usage
|
||||
=====
|
||||
|
||||
To use this module, you need to:
|
||||
To use Quality Control Issues, you need to:
|
||||
|
||||
#. Go to *Quality Control > Issues > QC Issues*.
|
||||
#. Go to *Quality Control > Issues > QC Issues* or to *Quality Control >
|
||||
Dashboard* and click on *Issues* in any of your teams.
|
||||
#. Click on create to report an issue.
|
||||
#. Select the product and quantity for the issue. Optionally you can specify
|
||||
a location and relate the issue to some *Problem*.
|
||||
|
||||
To manage your Quality Control Problems, you have to:
|
||||
|
||||
#. Go to *Quality Control > Problem Tracking > Problems* or to *Quality
|
||||
Control > Dashboard* and click on *Problems* in any of your teams.
|
||||
|
||||
Issue Dispositions:
|
||||
-------------------
|
||||
|
||||
You can perform the following actions in quality control issues 'in progress':
|
||||
|
||||
* Scrap: Click on *Scrap Products* button.
|
||||
* Create RMA: Install `rma_quality_control_issue` and see instructions there.
|
||||
|
||||
.. image:: https://odoo-community.org/website/image/ir.attachment/5784_f2813bd/datas
|
||||
:alt: Try me on Runbot
|
||||
@@ -28,9 +70,7 @@ Known issues / Roadmap
|
||||
Todo:
|
||||
-----
|
||||
|
||||
* Add Dispositions: RMA, scrap, rework...
|
||||
* reference to PO, MO, QC...
|
||||
* Link to Problem tracking...
|
||||
* Add more dispositions: repair, refurbish...
|
||||
|
||||
Bug Tracker
|
||||
===========
|
||||
@@ -52,6 +92,7 @@ Contributors
|
||||
------------
|
||||
|
||||
* Lois Rilo <lois.rilo@eficent.com>
|
||||
* Jordi Ballester Alomar <jordi.ballester@eficent.com>
|
||||
|
||||
Maintainer
|
||||
----------
|
||||
|
||||
@@ -11,7 +11,12 @@
|
||||
"license": "AGPL-3",
|
||||
"application": False,
|
||||
"installable": True,
|
||||
"depends": ["quality_control", "quality_control_team", "stock"],
|
||||
"depends": [
|
||||
"quality_control",
|
||||
"quality_control_team",
|
||||
"stock",
|
||||
"stock_scrap",
|
||||
],
|
||||
"data": [
|
||||
"security/ir.model.access.csv",
|
||||
"security/quality_control_issue_security.xml",
|
||||
@@ -21,5 +26,6 @@
|
||||
"views/qc_problem_view.xml",
|
||||
"views/qc_problem_group_view.xml",
|
||||
"views/qc_team_dashboard_view.xml",
|
||||
"views/stock_scrap_view.xml",
|
||||
],
|
||||
}
|
||||
|
||||
@@ -1,6 +1,8 @@
|
||||
# -*- coding: utf-8 -*-
|
||||
# Copyright 2017 Eficent Business and IT Consulting Services S.L.
|
||||
# License AGPL-3.0 or later (http://www.gnu.org/licenses/agpl).
|
||||
|
||||
from . import stock_scrap
|
||||
from . import qc_stage
|
||||
from . import qc_problem
|
||||
from . import qc_problem_group
|
||||
|
||||
@@ -2,7 +2,8 @@
|
||||
# Copyright 2017 Eficent Business and IT Consulting Services S.L.
|
||||
# License AGPL-3.0 or later (http://www.gnu.org/licenses/agpl).
|
||||
|
||||
from openerp import api, fields, models
|
||||
from openerp import api, fields, models, _
|
||||
from openerp.exceptions import UserError
|
||||
import openerp.addons.decimal_precision as dp
|
||||
|
||||
|
||||
@@ -11,6 +12,12 @@ class QualityControlIssue(models.Model):
|
||||
_description = "Quality Control Issue"
|
||||
_inherit = "mail.thread"
|
||||
|
||||
@api.multi
|
||||
def _compute_stock_scrap_qty(self):
|
||||
for rec in self:
|
||||
rec.stock_scrap_qty = sum(
|
||||
self.stock_scrap_ids.mapped('scrap_qty'))
|
||||
|
||||
@api.model
|
||||
def create(self, vals):
|
||||
vals['name'] = self.env['ir.sequence'].next_by_code(
|
||||
@@ -61,7 +68,7 @@ class QualityControlIssue(models.Model):
|
||||
("progress", "In Progress"),
|
||||
("done", "Done"),
|
||||
("cancel", "Cancel")], default="new",
|
||||
track_visibility='onchange')
|
||||
track_visibility='onchange', readonly=True)
|
||||
product_id = fields.Many2one(
|
||||
comodel_name="product.product", string="Product",
|
||||
readonly=True, states={"new": [("readonly", False)]}, required=True)
|
||||
@@ -111,6 +118,10 @@ class QualityControlIssue(models.Model):
|
||||
company_id = fields.Many2one(
|
||||
comodel_name='res.company', string='Company', required=True,
|
||||
default=lambda self: self.env.user.company_id)
|
||||
stock_scrap_ids = fields.One2many(
|
||||
comodel_name='stock.scrap', string='Scraps',
|
||||
inverse_name='qc_issue_id')
|
||||
stock_scrap_qty = fields.Integer(compute=_compute_stock_scrap_qty)
|
||||
|
||||
_group_by_full = {
|
||||
'stage_id': _read_group_stage_ids
|
||||
@@ -131,18 +142,47 @@ class QualityControlIssue(models.Model):
|
||||
team_ids.add(issue.team_id.id)
|
||||
search_domain = []
|
||||
if team_ids:
|
||||
search_domain += [('|')] * (len(team_ids) - 1)
|
||||
search_domain += [('|')] * (len(team_ids))
|
||||
search_domain.append(('qc_team_id', '=', False))
|
||||
for team_id in team_ids:
|
||||
search_domain.append(('qc_team_id', '=', team_id))
|
||||
else:
|
||||
search_domain.append(('qc_team_id', '=', False))
|
||||
search_domain += list(domain)
|
||||
# perform search, return the first found
|
||||
stage = self.env['qc.issue.stage'].search(
|
||||
search_domain, order=order, limit=1)
|
||||
return stage
|
||||
|
||||
@api.multi
|
||||
def write(self, vals):
|
||||
stage_obj = self.env['qc.issue.stage']
|
||||
state = vals.get('state')
|
||||
if state:
|
||||
if len(self.mapped('qc_team_id')) > 1:
|
||||
raise UserError(_(
|
||||
"Every issue must have the same QC team to perform this "
|
||||
"action."))
|
||||
team = self[0].qc_team_id
|
||||
stage = self.issue_stage_find([], team, [('state', '=', state)])
|
||||
if stage:
|
||||
vals.update({'stage_id': stage.id})
|
||||
return super(QualityControlIssue, self).write(vals)
|
||||
team_id = vals.get('qc_team_id')
|
||||
if team_id is not None:
|
||||
team = self.env['qc.team'].browse(team_id)
|
||||
stage = self.issue_stage_find([], team, [('fold', '=', False)])
|
||||
if stage:
|
||||
vals.update({'stage_id': stage.id})
|
||||
stage_id = vals.get('stage_id')
|
||||
if stage_id:
|
||||
state = stage_obj.browse(stage_id).state
|
||||
if state:
|
||||
vals.update({'state': state})
|
||||
return super(QualityControlIssue, self).write(vals)
|
||||
|
||||
@api.multi
|
||||
def action_confirm(self):
|
||||
self._check_required_fields()
|
||||
self.write({'state': 'progress'})
|
||||
|
||||
@api.multi
|
||||
@@ -170,7 +210,38 @@ class QualityControlIssue(models.Model):
|
||||
self.product_id = product
|
||||
self.product_uom = product.product_tmpl_id.uom_id
|
||||
|
||||
@api.onchange("stage_id")
|
||||
def _onchange_stage_id(self):
|
||||
if self.stage_id.state:
|
||||
self.state = self.stage_id.state
|
||||
@api.multi
|
||||
def scrap_products(self):
|
||||
self.ensure_one()
|
||||
return {
|
||||
'name': _('Scrap'),
|
||||
'view_type': 'form',
|
||||
'view_mode': 'form',
|
||||
'res_model': 'stock.scrap',
|
||||
'view_id': self.env.ref('stock_scrap.stock_scrap_form_view2').id,
|
||||
'type': 'ir.actions.act_window',
|
||||
'context': {
|
||||
'default_qc_issue_id': self.id,
|
||||
'default_location_id': self.location_id.id,
|
||||
'default_product_id': self.product_id.id,
|
||||
'default_scrap_qty': self.product_qty,
|
||||
'default_product_uom_id': self.product_uom.id,
|
||||
'default_lot_id': self.lot_id.id,
|
||||
},
|
||||
'target': 'new',
|
||||
}
|
||||
|
||||
@api.multi
|
||||
def action_view_stock_scrap(self):
|
||||
action = self.env.ref('stock_scrap.action_stock_scrap')
|
||||
result = action.read()[0]
|
||||
lines = self.stock_scrap_ids
|
||||
# choose the view_mode accordingly
|
||||
if len(lines) != 1:
|
||||
result['domain'] = "[('id', 'in', " + \
|
||||
str(lines.ids) + ")]"
|
||||
elif len(lines) == 1:
|
||||
res = self.env.ref('stock_scrap.stock_scrap_form_view', False)
|
||||
result['views'] = [(res and res.id or False, 'form')]
|
||||
result['res_id'] = lines.id
|
||||
return result
|
||||
|
||||
@@ -40,5 +40,5 @@ class QualityControlIssueStage(models.Model):
|
||||
help='This stage is folded in the kanban view when there are no '
|
||||
'records in that stage to display.')
|
||||
state = fields.Selection(
|
||||
string="QC Status",
|
||||
string="QC State",
|
||||
selection=lambda self: self.env['qc.issue']._fields['state'].selection)
|
||||
|
||||
@@ -101,9 +101,12 @@ class QcProblem(models.Model):
|
||||
team_ids.add(problem.team_id.id)
|
||||
search_domain = []
|
||||
if team_ids:
|
||||
search_domain += [('|')] * (len(team_ids) - 1)
|
||||
search_domain += [('|')] * (len(team_ids))
|
||||
search_domain.append(('qc_team_id', '=', False))
|
||||
for team_id in team_ids:
|
||||
search_domain.append(('qc_team_id', '=', team_id))
|
||||
else:
|
||||
search_domain.append(('qc_team_id', '=', False))
|
||||
search_domain += list(domain)
|
||||
# perform search, return the first found
|
||||
stage = self.env['qc.stage'].search(
|
||||
|
||||
12
quality_control_issue/models/stock_scrap.py
Normal file
12
quality_control_issue/models/stock_scrap.py
Normal file
@@ -0,0 +1,12 @@
|
||||
# -*- coding: utf-8 -*-
|
||||
# Copyright 2017 Eficent Business and IT Consulting Services S.L.
|
||||
# License AGPL-3.0 or later (http://www.gnu.org/licenses/agpl).
|
||||
|
||||
from openerp import fields, models
|
||||
|
||||
|
||||
class QualityControlIssueStage(models.Model):
|
||||
_inherit = "stock.scrap"
|
||||
|
||||
qc_issue_id = fields.Many2one(
|
||||
comodel_name="qc.issue", string="Quality Control Issue")
|
||||
@@ -30,6 +30,9 @@
|
||||
<button name="action_done"
|
||||
type="object" states="progress"
|
||||
string="Set to Done" class="oe_highlight"/>
|
||||
<button name="scrap_products"
|
||||
string="Scrap Products" type="object"
|
||||
states="progress"/>
|
||||
<button name="action_cancel"
|
||||
type="object" states="new,progress"
|
||||
string="Cancel"/>
|
||||
@@ -39,7 +42,14 @@
|
||||
</header>
|
||||
<sheet>
|
||||
<div class="oe_button_box" name="button_box">
|
||||
<!--To be inhereted by other modules.-->
|
||||
<button type="object" name="action_view_stock_scrap"
|
||||
class="oe_stat_button"
|
||||
icon="fa-recycle"
|
||||
context="{'default_qc_issue_id': active_id}">
|
||||
<field name="stock_scrap_qty"
|
||||
widget="statinfo"
|
||||
string="Scrapped products"/>
|
||||
</button>
|
||||
</div>
|
||||
<div class="oe_title">
|
||||
<label string="Quality Control Issue"/>
|
||||
|
||||
29
quality_control_issue/views/stock_scrap_view.xml
Normal file
29
quality_control_issue/views/stock_scrap_view.xml
Normal file
@@ -0,0 +1,29 @@
|
||||
<?xml version="1.0" encoding="utf-8"?>
|
||||
<!-- Copyright 2017 Eficent Business and IT Consulting Services S.L.
|
||||
License AGPL-3.0 or later (http://www.gnu.org/licenses/agpl). -->
|
||||
|
||||
<odoo>
|
||||
|
||||
<record id="stock_scrap_form_view" model="ir.ui.view">
|
||||
<field name="name">stock.scrap.form - quality_control_issue</field>
|
||||
<field name="model">stock.scrap</field>
|
||||
<field name="inherit_id" ref="stock_scrap.stock_scrap_form_view"/>
|
||||
<field name="arch" type="xml">
|
||||
<field name="owner_id" position="after">
|
||||
<field name="qc_issue_id" attrs="{'invisible': [('qc_issue_id', '=', False)]}"/>
|
||||
</field>
|
||||
</field>
|
||||
</record>
|
||||
|
||||
<record id="stock_scrap_form_view2" model="ir.ui.view">
|
||||
<field name="name">stock.scrap.form2 - quality_control_issue</field>
|
||||
<field name="model">stock.scrap</field>
|
||||
<field name="inherit_id" ref="stock_scrap.stock_scrap_form_view2"/>
|
||||
<field name="arch" type="xml">
|
||||
<field name="owner_id" position="after">
|
||||
<field name="qc_issue_id" attrs="{'invisible': [('qc_issue_id', '=', False)]}"/>
|
||||
</field>
|
||||
</field>
|
||||
</record>
|
||||
|
||||
</odoo>
|
||||
Reference in New Issue
Block a user