@ -0,0 +1,48 @@ |
|||||
|
.. image:: https://img.shields.io/badge/license-LGPL--3-green.svg |
||||
|
:target: https://www.gnu.org/licenses/lgpl-3.0-standalone.html |
||||
|
:alt: License: LGPL-3 |
||||
|
|
||||
|
Import Lot from Excel |
||||
|
===================== |
||||
|
This module helps to import lots from excel sheet to stock move line. |
||||
|
|
||||
|
Configuration |
||||
|
============= |
||||
|
* No additional configuration is needed. |
||||
|
|
||||
|
Company |
||||
|
------- |
||||
|
* `Cybrosys Techno Solutions <https://cybrosys.com/>`__ |
||||
|
|
||||
|
License |
||||
|
------- |
||||
|
Lesser General Public License, Version 3 (LGPL v3). |
||||
|
(https://www.gnu.org/licenses/lgpl-3.0-standalone.html) |
||||
|
|
||||
|
Credits |
||||
|
------- |
||||
|
* Developers: (V17) Remya R, Sabeel B, |
||||
|
(V18) Aysha Shalin |
||||
|
Contact: odoo@cybrosys.com |
||||
|
|
||||
|
Contacts |
||||
|
-------- |
||||
|
* Mail Contact : odoo@cybrosys.com |
||||
|
* Website : https://cybrosys.com |
||||
|
|
||||
|
Bug Tracker |
||||
|
----------- |
||||
|
Bugs are tracked on GitHub Issues. In case of trouble, please check there if your issue has already been reported. |
||||
|
|
||||
|
Maintainer |
||||
|
========== |
||||
|
.. image:: https://cybrosys.com/images/logo.png |
||||
|
:target: https://cybrosys.com |
||||
|
|
||||
|
This module is maintained by Cybrosys Technologies. |
||||
|
|
||||
|
For support and more information, please visit `Our Website <https://cybrosys.com/>`__ |
||||
|
|
||||
|
Further information |
||||
|
=================== |
||||
|
HTML Description: `<static/description/index.html>`__ |
@ -0,0 +1,24 @@ |
|||||
|
# -*- coding: utf-8 -*- |
||||
|
############################################################################### |
||||
|
# |
||||
|
# Cybrosys Technologies Pvt. Ltd. |
||||
|
# |
||||
|
# Copyright (C) 2024-TODAY Cybrosys Technologies(<https://www.cybrosys.com>) |
||||
|
# Author: Aysha Shalin (odoo@cybrosys.com) |
||||
|
# |
||||
|
# You can modify it under the terms of the GNU LESSER |
||||
|
# GENERAL PUBLIC LICENSE (LGPL v3), Version 3. |
||||
|
# |
||||
|
# This program is distributed in the hope that it will be useful, |
||||
|
# but WITHOUT ANY WARRANTY; without even the implied warranty of |
||||
|
# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the |
||||
|
# GNU LESSER GENERAL PUBLIC LICENSE (LGPL v3) for more details. |
||||
|
# |
||||
|
# You should have received a copy of the GNU LESSER GENERAL PUBLIC |
||||
|
# LICENSE (LGPL v3) along with this program. |
||||
|
# If not, see <http://www.gnu.org/licenses/>. |
||||
|
# |
||||
|
############################################################################### |
||||
|
from . import controllers |
||||
|
from . import models |
||||
|
from . import wizard |
@ -0,0 +1,49 @@ |
|||||
|
# -*- coding: utf-8 -*- |
||||
|
############################################################################### |
||||
|
# |
||||
|
# Cybrosys Technologies Pvt. Ltd. |
||||
|
# |
||||
|
# Copyright (C) 2024-TODAY Cybrosys Technologies(<https://www.cybrosys.com>) |
||||
|
# Author: Aysha Shalin (odoo@cybrosys.com) |
||||
|
# |
||||
|
# You can modify it under the terms of the GNU LESSER |
||||
|
# GENERAL PUBLIC LICENSE (LGPL v3), Version 3. |
||||
|
# |
||||
|
# This program is distributed in the hope that it will be useful, |
||||
|
# but WITHOUT ANY WARRANTY; without even the implied warranty of |
||||
|
# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the |
||||
|
# GNU LESSER GENERAL PUBLIC LICENSE (LGPL v3) for more details. |
||||
|
# |
||||
|
# You should have received a copy of the GNU LESSER GENERAL PUBLIC |
||||
|
# LICENSE (LGPL v3) along with this program. |
||||
|
# If not, see <http://www.gnu.org/licenses/>. |
||||
|
# |
||||
|
############################################################################### |
||||
|
{ |
||||
|
'name': 'Import Lot from Excel', |
||||
|
'version': '18.0.1.0.0', |
||||
|
'category': 'Warehouse', |
||||
|
'summary': """Import/add lots while validating a purchase order picking.""", |
||||
|
'description': """This module helps to import lots and add to products in |
||||
|
purchase order line while validating stock picking.""", |
||||
|
'author': 'Cybrosys Techno Solution', |
||||
|
'company': 'Cybrosys Techno Solutions', |
||||
|
'maintainer': 'Cybrosys Techno Solution', |
||||
|
'website': 'https://www.cybrosys.com', |
||||
|
'depends': ['stock', 'purchase'], |
||||
|
'data': [ |
||||
|
'security/ir.model.access.csv', |
||||
|
'views/stock_move_views.xml', |
||||
|
'wizard/lots_attachment_view_form.xml' |
||||
|
], |
||||
|
'assets': { |
||||
|
'web.assets_backend': [ |
||||
|
'import_lots/static/src/*.js', |
||||
|
], |
||||
|
}, |
||||
|
'images': ['static/description/banner.png'], |
||||
|
'license': 'LGPL-3', |
||||
|
'installable': True, |
||||
|
'auto-install': False, |
||||
|
'application': False, |
||||
|
} |
@ -0,0 +1,22 @@ |
|||||
|
# -*- coding: utf-8 -*- |
||||
|
############################################################################### |
||||
|
# |
||||
|
# Cybrosys Technologies Pvt. Ltd. |
||||
|
# |
||||
|
# Copyright (C) 2024-TODAY Cybrosys Technologies(<https://www.cybrosys.com>) |
||||
|
# Author: Aysha Shalin (odoo@cybrosys.com) |
||||
|
# |
||||
|
# You can modify it under the terms of the GNU LESSER |
||||
|
# GENERAL PUBLIC LICENSE (LGPL v3), Version 3. |
||||
|
# |
||||
|
# This program is distributed in the hope that it will be useful, |
||||
|
# but WITHOUT ANY WARRANTY; without even the implied warranty of |
||||
|
# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the |
||||
|
# GNU LESSER GENERAL PUBLIC LICENSE (LGPL v3) for more details. |
||||
|
# |
||||
|
# You should have received a copy of the GNU LESSER GENERAL PUBLIC |
||||
|
# LICENSE (LGPL v3) along with this program. |
||||
|
# If not, see <http://www.gnu.org/licenses/>. |
||||
|
# |
||||
|
############################################################################### |
||||
|
from . import import_lots |
@ -0,0 +1,63 @@ |
|||||
|
# -*- coding: utf-8 -*- |
||||
|
############################################################################### |
||||
|
# |
||||
|
# Cybrosys Technologies Pvt. Ltd. |
||||
|
# |
||||
|
# Copyright (C) 2024-TODAY Cybrosys Technologies(<https://www.cybrosys.com>) |
||||
|
# Author: Aysha Shalin (odoo@cybrosys.com) |
||||
|
# |
||||
|
# You can modify it under the terms of the GNU LESSER |
||||
|
# GENERAL PUBLIC LICENSE (LGPL v3), Version 3. |
||||
|
# |
||||
|
# This program is distributed in the hope that it will be useful, |
||||
|
# but WITHOUT ANY WARRANTY; without even the implied warranty of |
||||
|
# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the |
||||
|
# GNU LESSER GENERAL PUBLIC LICENSE (LGPL v3) for more details. |
||||
|
# |
||||
|
# You should have received a copy of the GNU LESSER GENERAL PUBLIC LICENSE |
||||
|
# (LGPL v3) along with this program. |
||||
|
# If not, see <http://www.gnu.org/licenses/>. |
||||
|
# |
||||
|
############################################################################### |
||||
|
import base64 |
||||
|
import io |
||||
|
import openpyxl |
||||
|
from odoo import http |
||||
|
from odoo.http import request |
||||
|
try: |
||||
|
from werkzeug.utils import send_file |
||||
|
except ImportError: |
||||
|
from odoo.tools._vendor.send_file import send_file |
||||
|
|
||||
|
|
||||
|
class ImportLots(http.Controller): |
||||
|
""" Class to handle excel download """ |
||||
|
@http.route('/download/excel', type='http', auth="user") |
||||
|
def download_excel_file(self): |
||||
|
""" Download sample Excel sheet """ |
||||
|
# Create a new workbook |
||||
|
wb = openpyxl.Workbook() |
||||
|
ws = wb.active |
||||
|
# Add headers |
||||
|
ws.append(['Lots', 'Product', 'Quantity']) |
||||
|
# Add sample data |
||||
|
data = [ |
||||
|
('0000021', '[FURN_8220] Four Person Desk', 2.00), |
||||
|
('0000022', '[FURN_8220] Four Person Desk', 3.00), |
||||
|
('0000023', '[FURN_8900] Drawer Black', 6.00), |
||||
|
] |
||||
|
for row in data: |
||||
|
ws.append(row) |
||||
|
# Save the workbook to a BytesIO buffer |
||||
|
buffer = io.BytesIO() |
||||
|
wb.save(buffer) |
||||
|
buffer.seek(0) |
||||
|
# Convert the buffer content to base64 |
||||
|
file_content_base64 = base64.b64encode(buffer.getvalue()) |
||||
|
return send_file(io.BytesIO(base64.b64decode(file_content_base64)), |
||||
|
request.httprequest.environ, |
||||
|
download_name="my_excel_file.xlsx", |
||||
|
as_attachment=True, |
||||
|
mimetype= |
||||
|
'application/vnd.openxmlformats-officedocument.' |
||||
|
'spreadsheetml.sheet') |
@ -0,0 +1,6 @@ |
|||||
|
## Module <import_lots> |
||||
|
|
||||
|
#### 15.10.2024 |
||||
|
#### Version 18.0.1.0.0 |
||||
|
##### ADD |
||||
|
- Initial commit for Import Lot from Excel |
@ -0,0 +1,22 @@ |
|||||
|
# -*- coding: utf-8 -*- |
||||
|
############################################################################### |
||||
|
# |
||||
|
# Cybrosys Technologies Pvt. Ltd. |
||||
|
# |
||||
|
# Copyright (C) 2024-TODAY Cybrosys Technologies(<https://www.cybrosys.com>) |
||||
|
# Author: Aysha Shalin (odoo@cybrosys.com) |
||||
|
# |
||||
|
# You can modify it under the terms of the GNU LESSER |
||||
|
# GENERAL PUBLIC LICENSE (LGPL v3), Version 3. |
||||
|
# |
||||
|
# This program is distributed in the hope that it will be useful, |
||||
|
# but WITHOUT ANY WARRANTY; without even the implied warranty of |
||||
|
# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the |
||||
|
# GNU LESSER GENERAL PUBLIC LICENSE (LGPL v3) for more details. |
||||
|
# |
||||
|
# You should have received a copy of the GNU LESSER GENERAL PUBLIC |
||||
|
# LICENSE (LGPL v3) along with this program. |
||||
|
# If not, see <http://www.gnu.org/licenses/>. |
||||
|
# |
||||
|
############################################################################### |
||||
|
from . import stock_move |
@ -0,0 +1,54 @@ |
|||||
|
# -*- coding: utf-8 -*- |
||||
|
############################################################################### |
||||
|
# |
||||
|
# Cybrosys Technologies Pvt. Ltd. |
||||
|
# |
||||
|
# Copyright (C) 2024-TODAY Cybrosys Technologies(<https://www.cybrosys.com>) |
||||
|
# Author: Aysha Shalin (odoo@cybrosys.com) |
||||
|
# |
||||
|
# You can modify it under the terms of the GNU LESSER |
||||
|
# GENERAL PUBLIC LICENSE (LGPL v3), Version 3. |
||||
|
# |
||||
|
# This program is distributed in the hope that it will be useful, |
||||
|
# but WITHOUT ANY WARRANTY; without even the implied warranty of |
||||
|
# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the |
||||
|
# GNU LESSER GENERAL PUBLIC LICENSE (LGPL v3) for more details. |
||||
|
# |
||||
|
# You should have received a copy of the GNU LESSER GENERAL PUBLIC |
||||
|
# LICENSE (LGPL v3) along with this program. |
||||
|
# If not, see <http://www.gnu.org/licenses/>. |
||||
|
# |
||||
|
############################################################################### |
||||
|
from odoo import fields, models |
||||
|
import base64 |
||||
|
import openpyxl |
||||
|
from io import BytesIO |
||||
|
|
||||
|
|
||||
|
class StockMove(models.Model): |
||||
|
""" Inheriting stock_move to add additional new field and function """ |
||||
|
_inherit = 'stock.move' |
||||
|
|
||||
|
attachment = fields.Binary(string="Upload") |
||||
|
|
||||
|
def action_import_lot(self): |
||||
|
""" Import and write lots to stock_move_line """ |
||||
|
vals_list = [] |
||||
|
wb = openpyxl.load_workbook( |
||||
|
filename=BytesIO(base64.b64decode(self.attachment)), |
||||
|
read_only=True) |
||||
|
ws = wb.active |
||||
|
for record in ws.iter_rows(min_row=2, max_row=None, |
||||
|
min_col=None, |
||||
|
max_col=None, values_only=True): |
||||
|
if record[1] == self.product_id.display_name: |
||||
|
vals_list.append((0, 0, { |
||||
|
'lot_name': record[0], |
||||
|
'quantity': record[2], |
||||
|
'product_id': self.product_id.id |
||||
|
})) |
||||
|
continue |
||||
|
self.move_line_ids.unlink() |
||||
|
self.write({ |
||||
|
'move_line_ids': vals_list |
||||
|
}) |
|
After Width: | Height: | Size: 2.2 KiB |
After Width: | Height: | Size: 28 KiB |
After Width: | Height: | Size: 628 KiB |
After Width: | Height: | Size: 1.1 KiB |
After Width: | Height: | Size: 210 KiB |
After Width: | Height: | Size: 209 KiB |
After Width: | Height: | Size: 109 KiB |
After Width: | Height: | Size: 495 B |
After Width: | Height: | Size: 1.0 KiB |
After Width: | Height: | Size: 624 B |
After Width: | Height: | Size: 136 KiB |
After Width: | Height: | Size: 214 KiB |
After Width: | Height: | Size: 36 KiB |
After Width: | Height: | Size: 3.6 KiB |
After Width: | Height: | Size: 310 B |
After Width: | Height: | Size: 929 B |
After Width: | Height: | Size: 1.3 KiB |
After Width: | Height: | Size: 3.3 KiB |
After Width: | Height: | Size: 1.4 KiB |
After Width: | Height: | Size: 17 KiB |
After Width: | Height: | Size: 542 B |
After Width: | Height: | Size: 576 B |
After Width: | Height: | Size: 733 B |
After Width: | Height: | Size: 4.3 KiB |
After Width: | Height: | Size: 1.2 KiB |
After Width: | Height: | Size: 4.0 KiB |
After Width: | Height: | Size: 1.7 KiB |
After Width: | Height: | Size: 2.2 KiB |
After Width: | Height: | Size: 911 B |
After Width: | Height: | Size: 1.1 KiB |
After Width: | Height: | Size: 1.2 KiB |
After Width: | Height: | Size: 1.2 KiB |
After Width: | Height: | Size: 600 B |
After Width: | Height: | Size: 673 B |
After Width: | Height: | Size: 2.0 KiB |
After Width: | Height: | Size: 462 B |
After Width: | Height: | Size: 2.1 KiB |
After Width: | Height: | Size: 926 B |
After Width: | Height: | Size: 9.0 KiB |
After Width: | Height: | Size: 23 KiB |
After Width: | Height: | Size: 7.0 KiB |
After Width: | Height: | Size: 878 B |
After Width: | Height: | Size: 1.2 KiB |
After Width: | Height: | Size: 653 B |
After Width: | Height: | Size: 800 B |
After Width: | Height: | Size: 905 B |
After Width: | Height: | Size: 189 KiB |
After Width: | Height: | Size: 4.3 KiB |
After Width: | Height: | Size: 839 B |
After Width: | Height: | Size: 1.7 KiB |
After Width: | Height: | Size: 5.9 KiB |
After Width: | Height: | Size: 1.6 KiB |
After Width: | Height: | Size: 34 KiB |
After Width: | Height: | Size: 26 KiB |
After Width: | Height: | Size: 3.8 KiB |
After Width: | Height: | Size: 23 KiB |
After Width: | Height: | Size: 1.9 KiB |
After Width: | Height: | Size: 2.3 KiB |
After Width: | Height: | Size: 427 B |
After Width: | Height: | Size: 627 B |
After Width: | Height: | Size: 1.1 KiB |
After Width: | Height: | Size: 1.2 KiB |
After Width: | Height: | Size: 988 B |
After Width: | Height: | Size: 3.7 KiB |
After Width: | Height: | Size: 5.0 KiB |
After Width: | Height: | Size: 875 B |
After Width: | Height: | Size: 1.2 KiB |
After Width: | Height: | Size: 86 KiB |
After Width: | Height: | Size: 92 KiB |
After Width: | Height: | Size: 89 KiB |
After Width: | Height: | Size: 141 KiB |
After Width: | Height: | Size: 92 KiB |
After Width: | Height: | Size: 88 KiB |
After Width: | Height: | Size: 114 KiB |
After Width: | Height: | Size: 134 KiB |
After Width: | Height: | Size: 66 KiB |
After Width: | Height: | Size: 75 KiB |
After Width: | Height: | Size: 79 KiB |
After Width: | Height: | Size: 71 KiB |
After Width: | Height: | Size: 22 KiB |
After Width: | Height: | Size: 69 KiB |
After Width: | Height: | Size: 75 KiB |
After Width: | Height: | Size: 260 KiB |
After Width: | Height: | Size: 880 KiB |
After Width: | Height: | Size: 87 KiB |
After Width: | Height: | Size: 11 KiB |
@ -0,0 +1,38 @@ |
|||||
|
/** @odoo-module **/ |
||||
|
import { Dialog } from '@web/core/dialog/dialog'; |
||||
|
import { useService } from "@web/core/utils/hooks"; |
||||
|
import { registry } from "@web/core/registry"; |
||||
|
import { Component, xml } from "@odoo/owl"; |
||||
|
|
||||
|
/** |
||||
|
* Extended and added new widget to the registry |
||||
|
*/ |
||||
|
class ImportLots extends Component { |
||||
|
static template = xml`<button class="btn btn-link" t-if="this.isVisible" t-on-click="openDialog">Import Lots from Sheet</button>`; |
||||
|
setup(){ |
||||
|
this.action = useService("action"); |
||||
|
this.orm = useService("orm"); |
||||
|
} |
||||
|
get isVisible() { |
||||
|
return this.props.record.data.state !== 'done'; |
||||
|
} |
||||
|
openDialog(ev){ |
||||
|
this.action.doAction({ |
||||
|
type: 'ir.actions.act_window', |
||||
|
name: 'Import Lots', |
||||
|
res_model: 'lot.attachment', |
||||
|
view_mode: 'form', |
||||
|
views: [ |
||||
|
[false, 'form'] |
||||
|
], |
||||
|
target: 'new', |
||||
|
context:{ |
||||
|
default_product_id: this.props.record.data.product_id[0], |
||||
|
default_demanded_quantity: this.props.record.data.product_uom_qty, |
||||
|
default_picking_id: this.props.record.data.picking_id[0], |
||||
|
default_move_id: this.props.record.data.move_line_ids._config.context.default_move_id |
||||
|
} |
||||
|
}) |
||||
|
} |
||||
|
} |
||||
|
registry.category("view_widgets").add("import_lot", {component: ImportLots}); |
@ -0,0 +1,14 @@ |
|||||
|
<?xml version="1.0" encoding="utf-8"?> |
||||
|
<odoo> |
||||
|
<!-- Inherited stock_move to add a button for importing lot --> |
||||
|
<record id="view_stock_move_operations" model="ir.ui.view"> |
||||
|
<field name="name">stock.move.view.form.inherit.import.lot</field> |
||||
|
<field name="model">stock.move</field> |
||||
|
<field name="inherit_id" ref="stock.view_stock_move_operations"/> |
||||
|
<field name="arch" type="xml"> |
||||
|
<xpath expr="//widget[@name='import_lots']" position="after"> |
||||
|
<widget class="btn btn-link btn-group" name="import_lot"/> |
||||
|
</xpath> |
||||
|
</field> |
||||
|
</record> |
||||
|
</odoo> |
@ -0,0 +1,22 @@ |
|||||
|
# -*- coding: utf-8 -*- |
||||
|
############################################################################### |
||||
|
# |
||||
|
# Cybrosys Technologies Pvt. Ltd. |
||||
|
# |
||||
|
# Copyright (C) 2024-TODAY Cybrosys Technologies(<https://www.cybrosys.com>) |
||||
|
# Author: Aysha Shalin (odoo@cybrosys.com) |
||||
|
# |
||||
|
# You can modify it under the terms of the GNU LESSER |
||||
|
# GENERAL PUBLIC LICENSE (LGPL v3), Version 3. |
||||
|
# |
||||
|
# This program is distributed in the hope that it will be useful, |
||||
|
# but WITHOUT ANY WARRANTY; without even the implied warranty of |
||||
|
# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the |
||||
|
# GNU LESSER GENERAL PUBLIC LICENSE (LGPL v3) for more details. |
||||
|
# |
||||
|
# You should have received a copy of the GNU LESSER GENERAL PUBLIC |
||||
|
# LICENSE (LGPL v3) along with this program. |
||||
|
# If not, see <http://www.gnu.org/licenses/>. |
||||
|
# |
||||
|
############################################################################### |
||||
|
from . import lots_attachment |
@ -0,0 +1,112 @@ |
|||||
|
# -*- coding: utf-8 -*- |
||||
|
############################################################################### |
||||
|
# |
||||
|
# Cybrosys Technologies Pvt. Ltd. |
||||
|
# |
||||
|
# Copyright (C) 2024-TODAY Cybrosys Technologies(<https://www.cybrosys.com>) |
||||
|
# Author: Aysha Shalin (odoo@cybrosys.com) |
||||
|
# |
||||
|
# You can modify it under the terms of the GNU LESSER |
||||
|
# GENERAL PUBLIC LICENSE (LGPL v3), Version 3. |
||||
|
# |
||||
|
# This program is distributed in the hope that it will be useful, |
||||
|
# but WITHOUT ANY WARRANTY; without even the implied warranty of |
||||
|
# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the |
||||
|
# GNU LESSER GENERAL PUBLIC LICENSE (LGPL v3) for more details. |
||||
|
# |
||||
|
# You should have received a copy of the GNU LESSER GENERAL PUBLIC |
||||
|
# LICENSE (LGPL v3) along with this program. |
||||
|
# If not, see <http://www.gnu.org/licenses/>. |
||||
|
# |
||||
|
############################################################################### |
||||
|
from odoo import fields, models, _ |
||||
|
from odoo.exceptions import UserError, ValidationError |
||||
|
import base64 |
||||
|
import openpyxl |
||||
|
from io import BytesIO |
||||
|
|
||||
|
|
||||
|
class LotsAttachment(models.TransientModel): |
||||
|
""" Class for lots wizard """ |
||||
|
_name = 'lot.attachment' |
||||
|
_description = "Lots Attachment" |
||||
|
|
||||
|
picking_id = fields.Many2one('stock.picking', |
||||
|
string="Stock Picking", |
||||
|
help="Parent picking") |
||||
|
product_id = fields.Many2one('product.product', |
||||
|
string="Product", |
||||
|
help="Current product") |
||||
|
demanded_quantity = fields.Float(string="Quantity", |
||||
|
help="Product quantity demanded") |
||||
|
type = fields.Selection(string="Lots Type", |
||||
|
selection=[('lot', 'Lot'), ('serial', 'Serial')], |
||||
|
help="Choose a lot/serial") |
||||
|
move_id = fields.Many2one('stock.move') |
||||
|
attachment = fields.Binary(string="Upload", attachment=True) |
||||
|
attachment_name = fields.Char(string="Attachment Name", |
||||
|
help="Attachment file name") |
||||
|
|
||||
|
def action_import_lot(self): |
||||
|
""" Importing lots """ |
||||
|
current_move_id = self.env['stock.move'].browse(self.move_id.id) |
||||
|
if self.attachment: |
||||
|
wb = openpyxl.load_workbook( |
||||
|
filename=BytesIO(base64.b64decode(self.attachment)), |
||||
|
read_only=True) if self.attachment else "" |
||||
|
ws = wb.active |
||||
|
# Check if product exists in the sheet |
||||
|
product_found = any( |
||||
|
record[1] == current_move_id.product_id.display_name for |
||||
|
record in ws.iter_rows(min_row=2, values_only=True)) |
||||
|
if not product_found: |
||||
|
raise UserError( |
||||
|
_('The product "%s" does not exist in the sheet.') % |
||||
|
current_move_id.product_id.display_name) |
||||
|
# Check if lot name already exists in move line ids |
||||
|
if (current_move_id.move_line_ids and |
||||
|
any(record[0] in set(current_move_id.move_line_ids.mapped('lot_name')) for |
||||
|
record in ws.iter_rows(min_row=2, values_only=True))): |
||||
|
raise UserError( |
||||
|
_('This Lot name already exists in the move line.')) |
||||
|
# Calculate total sheet quantity for the product |
||||
|
total_sheet_quantity = sum( |
||||
|
record[2] for record in ws.iter_rows |
||||
|
(min_row=2, values_only=True) if |
||||
|
record[1] == current_move_id.product_id.display_name) |
||||
|
# Check if total sheet quantity exceeds demand quantity of the |
||||
|
# product |
||||
|
if total_sheet_quantity > current_move_id.product_uom_qty: |
||||
|
raise UserError( |
||||
|
_('Total quantity in the sheet exceeds the demand ' |
||||
|
'quantity of the product. Please adjust the quantities ' |
||||
|
'in the sheet.')) |
||||
|
# Prepare move line values to be written |
||||
|
vals_list = [] |
||||
|
for record in ws.iter_rows(min_row=2, values_only=True): |
||||
|
lot_name, product_name, quantity = record |
||||
|
if product_name == current_move_id.product_id.display_name: |
||||
|
vals_list.append((0, 0, { |
||||
|
'lot_name': lot_name, |
||||
|
'quantity': min(quantity, current_move_id.product_qty), |
||||
|
'move_id': current_move_id.id, |
||||
|
})) |
||||
|
# Write move line values |
||||
|
current_move_id.move_line_ids.unlink() |
||||
|
current_move_id.write({'move_line_ids': vals_list}) |
||||
|
return { |
||||
|
'type': 'ir.actions.client', |
||||
|
'tag': 'reload', |
||||
|
} |
||||
|
else: |
||||
|
raise ValidationError( |
||||
|
_('Check whether you upload the document')) |
||||
|
|
||||
|
def action_download_sample(self): |
||||
|
""" For downloading a sample excel file """ |
||||
|
return { |
||||
|
'type': 'ir.actions.act_url', |
||||
|
'url': '/download/excel', |
||||
|
'target': 'self', |
||||
|
'file_name': 'my_excel_file.xlsx' |
||||
|
} |