476 lines
16 KiB
Python
476 lines
16 KiB
Python
# -*- coding: utf-8 -*-
|
|
|
|
from openerp import models, fields, api, _
|
|
from openerp.exceptions import UserError, ValidationError, Warning
|
|
|
|
class SalesCommission(models.Model):
|
|
_name = "sales.commission"
|
|
_deacription = "Sales Commission"
|
|
_order = 'id desc'
|
|
_rec_name = 'name'
|
|
# _inherit = ['mail.thread', 'ir.needaction_mixin']
|
|
_inherit = ['mail.thread', 'mail.activity.mixin', 'portal.mixin'] #odoo11
|
|
|
|
@api.multi
|
|
@api.depends('sales_commission_line', 'sales_commission_line.state')
|
|
def _get_amount_total(self):
|
|
for rec in self:
|
|
total_amount = []
|
|
for line in rec.sales_commission_line:
|
|
if line.state not in ['cancel', 'exception']:
|
|
total_amount.append(line.amount_company_currency)#multi currency supported
|
|
rec.amount = sum(total_amount)
|
|
|
|
@api.model
|
|
def create(self, vals):
|
|
vals['name'] = self.env['ir.sequence'].next_by_code('sales.commission')
|
|
return super(SalesCommission, self).create(vals)
|
|
|
|
@api.multi
|
|
@api.depends('invoice_id','invoice_id.state')
|
|
def _is_paid_invoice(self):
|
|
for rec in self:
|
|
if rec.invoice_id.state == 'paid':
|
|
rec.is_paid = True
|
|
rec.state = 'paid'
|
|
|
|
name = fields.Char(
|
|
string="Name",
|
|
readonly=True,
|
|
)
|
|
state = fields.Selection([
|
|
('draft', 'Draft'),
|
|
('invoice', 'Invoiced'),
|
|
('paid', 'Paid'),
|
|
('cancel', 'Cancelled')],
|
|
default='draft',
|
|
track_visibility='onchange',
|
|
copy=False, string="Status"
|
|
)
|
|
start_date = fields.Datetime(
|
|
string='Start Date',
|
|
readonly=True, states={'draft': [('readonly', False)]},
|
|
)
|
|
end_date = fields.Datetime(
|
|
string='End Date',
|
|
readonly=True, states={'draft': [('readonly', False)]},
|
|
)
|
|
commission_user_id = fields.Many2one(
|
|
'res.partner',
|
|
string='Sales Member',
|
|
required=True,
|
|
readonly=True, states={'draft': [('readonly', False)]},
|
|
)
|
|
sales_commission_line = fields.One2many(
|
|
'sales.commission.line',
|
|
'sales_commission_id',
|
|
string="Commission Line",
|
|
readonly=True, states={'draft': [('readonly', False)]},
|
|
)
|
|
notes = fields.Text(string="Internal Notes")
|
|
company_id = fields.Many2one(
|
|
'res.company',
|
|
default=lambda self: self.env.user.company_id,
|
|
string='Company',
|
|
readonly=True
|
|
)
|
|
product_id = fields.Many2one(
|
|
'product.product',
|
|
domain=[('is_commission_product','=',True)],
|
|
string='Commision Product For Invoice',
|
|
readonly=True, states={'draft': [('readonly', False)]},
|
|
)
|
|
amount = fields.Float(
|
|
string='Total Commision Amount (Company Currency)',
|
|
compute="_get_amount_total",
|
|
store=True,
|
|
readonly=True, states={'draft': [('readonly', False)]},
|
|
)
|
|
invoice_id = fields.Many2one(
|
|
'account.invoice',
|
|
string='Commission Invoice',
|
|
readonly=True, states={'draft': [('readonly', False)]},
|
|
)
|
|
is_paid = fields.Boolean(
|
|
string="Is Commission Paid",
|
|
compute="_is_paid_invoice",
|
|
store=True,
|
|
readonly=True, states={'draft': [('readonly', False)]},
|
|
)
|
|
currency_id = fields.Many2one(
|
|
'res.currency',
|
|
related='company_id.currency_id',
|
|
string='Currency',
|
|
readonly=True, states={'draft': [('readonly', False)]}
|
|
)
|
|
|
|
@api.multi
|
|
def _write(self, vals):
|
|
for rec in self:
|
|
if 'is_paid' in vals:
|
|
if vals['is_paid'] == True:
|
|
vals['state'] = 'paid'
|
|
return super(SalesCommission, self)._write(vals)
|
|
|
|
@api.multi
|
|
def _prepare_invoice_line(self, invoice_id):
|
|
"""
|
|
Prepare the dict of values to create the new invoice line for a sales order line.
|
|
:param qty: float quantity to invoice
|
|
"""
|
|
res = {}
|
|
for rec in self:
|
|
product = rec.product_id
|
|
account = product.property_account_expense_id or product.categ_id.property_account_expense_categ_id
|
|
if not account:
|
|
raise UserError(_('Please define expense account for this product: "%s" (id:%d) - or for its category: "%s".') % \
|
|
(product.name, product.id, product.categ_id.name))
|
|
fpos = invoice_id.partner_id.property_account_position_id
|
|
if fpos:
|
|
account = fpos.map_account(account)
|
|
#for title service
|
|
res = {
|
|
'name': product.name,
|
|
'origin': invoice_id.origin,
|
|
'account_id': account.id,
|
|
'price_unit': rec.amount,#To do
|
|
'quantity': 1,
|
|
'uom_id': product.uom_id.id,
|
|
'product_id': product.id or False,
|
|
}
|
|
return res
|
|
|
|
@api.multi
|
|
def unlink(self):
|
|
for rec in self:
|
|
if rec.state != 'draft':
|
|
raise UserError(_('Sorry! You can not delete non-draft sales commission!'))
|
|
return super(SalesCommission, self).unlink()
|
|
|
|
@api.multi
|
|
def invoice_line_create(self, invoice_id):
|
|
precision = self.env['decimal.precision'].precision_get('Product Unit of Measure')
|
|
for rec in self:
|
|
vals = rec._prepare_invoice_line(invoice_id=invoice_id)
|
|
vals.update({'invoice_id': invoice_id.id})
|
|
self.env['account.invoice.line'].create(vals)
|
|
|
|
@api.multi
|
|
def _prepare_invoice(self):
|
|
"""
|
|
Prepare the dict of values to create the new invoice . This method may be
|
|
overridden to implement custom invoice generation (making sure to call super() to establish
|
|
a clean extension chain).
|
|
"""
|
|
self.ensure_one()
|
|
|
|
#find Applicant as a invoice related
|
|
partner = self.commission_user_id
|
|
#applicant = self.applicant_ids.search([('applicant_based_on_invoice','=',True)],limit=1)
|
|
if not partner.property_product_pricelist:
|
|
raise Warning(_('Please set pricelist.'))
|
|
|
|
domain = [
|
|
('type', '=', 'purchase'),
|
|
('company_id', '=', self.company_id.id),]
|
|
journal_id = self.env['account.journal'].search(domain, limit=1)
|
|
if not journal_id:
|
|
raise UserError(_('Please configure an accounting sale journal for this company.'))
|
|
|
|
invoice_vals = {
|
|
'name': self.name or '',
|
|
'origin': self.name,
|
|
'type': 'in_invoice',
|
|
'account_id': partner.property_account_receivable_id.id,
|
|
'partner_id': partner.id,
|
|
'journal_id': journal_id.id,
|
|
'currency_id': partner.property_product_pricelist.currency_id.id,
|
|
'comment': partner.name,
|
|
'payment_term_id': partner.property_payment_term_id.id,
|
|
'fiscal_position_id': partner.property_account_position_id.id,
|
|
'company_id': self.company_id.id,
|
|
'user_id': self.env.user.id,
|
|
'sale_commission_id': self.id,
|
|
}
|
|
return invoice_vals
|
|
|
|
@api.multi
|
|
def action_create_invoice(self):
|
|
inv_obj = self.env['account.invoice']
|
|
inv_line_obj = self.env['account.invoice.line']
|
|
for rec in self:
|
|
#invoice create
|
|
inv_data = rec._prepare_invoice()
|
|
invoice = inv_obj.create(inv_data)
|
|
# #invoice line create
|
|
rec.invoice_line_create(invoice)
|
|
rec.invoice_id = invoice.id
|
|
rec.state = 'invoice'
|
|
for line in rec.sales_commission_line:
|
|
if line.state not in ['cancel', 'exception']:
|
|
line.state = 'invoice'
|
|
|
|
@api.multi
|
|
def action_cancel(self):
|
|
for rec in self:
|
|
rec.state = 'cancel'
|
|
|
|
@api.multi
|
|
def action_draft(self):
|
|
for rec in self:
|
|
rec.state = 'draft'
|
|
|
|
class SalesCommissionLine(models.Model):
|
|
_name = "sales.commission.line"
|
|
_deacription = "Sales Commission"
|
|
_order = 'id desc'
|
|
_rec_name = 'sales_commission_id'
|
|
# _inherit = ['mail.thread', 'ir.needaction_mixin']
|
|
_inherit = ['mail.thread', 'mail.activity.mixin', 'portal.mixin'] #odoo11
|
|
|
|
@api.model
|
|
def create(self, vals):
|
|
vals['name'] = self.env['ir.sequence'].next_by_code('sales.commission.line')
|
|
return super(SalesCommissionLine, self).create(vals)
|
|
|
|
@api.multi
|
|
@api.depends('amount','currency_id', 'src_order_id', 'src_invoice_id', 'src_payment_id')
|
|
def _compute_amount_company_currency(self):
|
|
for rec in self:
|
|
if rec.src_order_id:
|
|
rec.amount_company_currency = rec.src_order_id.currency_id.compute(rec.amount, rec.currency_id)
|
|
if rec.src_invoice_id:
|
|
rec.amount_company_currency = rec.src_invoice_id.currency_id.compute(rec.amount, rec.currency_id)
|
|
if rec.src_payment_id:
|
|
rec.amount_company_currency = rec.src_payment_id.currency_id.compute(rec.amount, rec.currency_id)
|
|
@api.multi
|
|
@api.depends('amount','currency_id', 'src_order_id', 'src_invoice_id', 'src_payment_id')
|
|
def _compute_source_currency(self):
|
|
for rec in self:
|
|
if rec.src_order_id:
|
|
rec.source_currency = rec.src_order_id.currency_id.id
|
|
if rec.src_invoice_id:
|
|
rec.source_currency = rec.src_invoice_id.currency_id.id
|
|
if rec.src_payment_id:
|
|
rec.source_currency = rec.src_payment_id.currency_id.id
|
|
|
|
sales_commission_id = fields.Many2one(
|
|
'sales.commission',
|
|
string="Sales Commission",
|
|
)
|
|
name = fields.Char(
|
|
string="Name",
|
|
readonly=True,
|
|
copy=False,
|
|
)
|
|
# name_origin = fields.Char(
|
|
# string = "Origin"
|
|
# )
|
|
sales_team_id = fields.Many2one(
|
|
'crm.team',
|
|
string='Sales Team',
|
|
reqired=True
|
|
)
|
|
commission_user_id = fields.Many2one(
|
|
'res.partner',
|
|
string='Sales Member',
|
|
related='sales_commission_id.commission_user_id',
|
|
)
|
|
amount = fields.Float(
|
|
string='Amount',
|
|
copy=False,
|
|
)
|
|
source_currency = fields.Many2one(
|
|
'res.currency',
|
|
string='Source Currency',
|
|
compute='_compute_source_currency',
|
|
store=True,
|
|
)
|
|
company_id = fields.Many2one(
|
|
'res.company',
|
|
default=lambda self: self.env.user.company_id,
|
|
string='Company',
|
|
readonly=True
|
|
)
|
|
origin = fields.Char(string='Source Document', copy=False)
|
|
notes = fields.Text(string="Internal Notes")
|
|
|
|
state = fields.Selection([
|
|
('draft', 'Draft'),
|
|
('invoice', 'Invoiced'),
|
|
('paid', 'Paid'),
|
|
('exception','Exception'),
|
|
('cancel', 'Cancelled'),
|
|
],
|
|
default='draft',
|
|
track_visibility='onchange',
|
|
copy=False,
|
|
string="Status"
|
|
)
|
|
product_id = fields.Many2one(
|
|
'product.product',
|
|
domain=[('is_commission_product','=',True)],
|
|
string='Product',
|
|
copy=False,
|
|
)
|
|
type = fields.Selection(
|
|
[('sales_person', 'Sales Person'),
|
|
('sales_manager', 'Sales Manager')],
|
|
copy=False,
|
|
string="User Type",
|
|
)
|
|
invoice_id = fields.Many2one(
|
|
'account.invoice',
|
|
string='Account Invoice',
|
|
copy=False,
|
|
)
|
|
date = fields.Datetime(
|
|
string='Commission Date',
|
|
copy=False,
|
|
)
|
|
amount_company_currency = fields.Float(
|
|
string='Amount in Company Currency',
|
|
compute='_compute_amount_company_currency',
|
|
store=True,
|
|
)
|
|
currency_id = fields.Many2one(
|
|
'res.currency',
|
|
default=lambda self: self.env.user.company_id.currency_id.id,
|
|
string='Currency',
|
|
)
|
|
src_invoice_id = fields.Many2one(
|
|
'account.invoice',
|
|
string='Source Invoice',
|
|
copy=False,
|
|
)
|
|
src_order_id = fields.Many2one(
|
|
'sale.order',
|
|
string='Source Sale Order',
|
|
copy=False,
|
|
)
|
|
src_payment_id = fields.Many2one(
|
|
'account.payment',
|
|
string='Source Payment',
|
|
copy=False,
|
|
)
|
|
is_paid = fields.Boolean(
|
|
string="Is Commision Line Paid",
|
|
related="sales_commission_id.is_paid",
|
|
store=True,
|
|
)
|
|
# user_id = fields.Many2one(
|
|
# 'res.users',
|
|
# string="User"
|
|
# )
|
|
|
|
@api.multi
|
|
def _write(self, vals):
|
|
for line in self:
|
|
if 'is_paid' in vals:
|
|
if vals['is_paid'] == True:
|
|
vals['state'] = 'paid'
|
|
return super(SalesCommissionLine, self)._write(vals)
|
|
|
|
|
|
@api.multi
|
|
def unlink(self):
|
|
for rec in self:
|
|
if rec.state != 'draft':
|
|
raise UserError(_('Sorry! You can not delete non-draft sales commission lines!'))
|
|
return super(SalesCommissionLine, self).unlink()
|
|
|
|
# @api.multi
|
|
# def _prepare_invoice_line(self, invoice_id):
|
|
# """
|
|
# Prepare the dict of values to create the new invoice line for a sales order line.
|
|
# :param qty: float quantity to invoice
|
|
# """
|
|
# res = {}
|
|
# for rec in self:
|
|
# product = rec.product_id
|
|
# account = product.property_account_income_id or product.categ_id.property_account_income_categ_id
|
|
# if not account:
|
|
# raise UserError(_('Please define income account for this product: "%s" (id:%d) - or for its category: "%s".') % \
|
|
# (product.name, product.id, product.categ_id.name))
|
|
# fpos = invoice_id.partner_id.property_account_position_id
|
|
# if fpos:
|
|
# account = fpos.map_account(account)
|
|
# #for title service
|
|
# res = {
|
|
# 'name': invoice_id.origin,
|
|
# 'origin': invoice_id.origin,
|
|
# 'account_id': account.id,
|
|
# 'price_unit': rec.amount,#To do
|
|
# 'quantity': 1,
|
|
# 'uom_id': product.uom_id.id,
|
|
# 'product_id': product.id or False,
|
|
# }
|
|
# return res
|
|
|
|
# @api.multi
|
|
# def invoice_line_create(self, invoice_id):
|
|
# precision = self.env['decimal.precision'].precision_get('Product Unit of Measure')
|
|
# for rec in self:
|
|
# vals = rec._prepare_invoice_line(invoice_id=invoice_id)
|
|
# vals.update({'invoice_id': invoice_id.id})
|
|
# self.env['account.invoice.line'].create(vals)
|
|
|
|
# @api.multi
|
|
# def _prepare_invoice(self):
|
|
# """
|
|
# Prepare the dict of values to create the new invoice . This method may be
|
|
# overridden to implement custom invoice generation (making sure to call super() to establish
|
|
# a clean extension chain).
|
|
# """
|
|
# self.ensure_one()
|
|
#
|
|
# #find Applicant as a invoice related
|
|
# partner = self.commission_user_id.partner_id
|
|
# #applicant = self.applicant_ids.search([('applicant_based_on_invoice','=',True)],limit=1)
|
|
# if not partner.property_product_pricelist:
|
|
# raise Warning(_('Please set pricelist.'))
|
|
|
|
# domain = [
|
|
# ('type', '=', 'sale'),
|
|
# ('company_id', '=', self.company_id.id),]
|
|
# journal_id = self.env['account.journal'].search(domain, limit=1)
|
|
# if not journal_id:
|
|
# raise UserError(_('Please configure an accounting sale journal for this company.'))
|
|
#
|
|
# invoice_vals = {
|
|
# 'name': self.name or '',
|
|
# 'origin': self.name,
|
|
# 'type': 'in_invoice',
|
|
# 'account_id': partner.property_account_receivable_id.id,
|
|
# 'partner_id': partner.id,
|
|
# 'journal_id': journal_id.id,
|
|
# 'currency_id': partner.property_product_pricelist.currency_id.id,
|
|
# 'comment': partner.name,
|
|
# 'payment_term_id': partner.property_payment_term_id.id,
|
|
# 'fiscal_position_id': partner.property_account_position_id.id,
|
|
# 'company_id': self.company_id.id,
|
|
# 'user_id': self.commission_user_id and self.commission_user_id.id,
|
|
# 'sale_commission_id': self.id,
|
|
# }
|
|
# return invoice_vals
|
|
|
|
# @api.multi
|
|
# def action_create_invoice(self):
|
|
# inv_obj = self.env['account.invoice']
|
|
# inv_line_obj = self.env['account.invoice.line']
|
|
# for rec in self:
|
|
# #invoice create
|
|
# inv_data = rec._prepare_invoice()
|
|
# invoice = inv_obj.create(inv_data)
|
|
## #invoice line create
|
|
# rec.invoice_line_create(invoice)
|
|
# rec.invoice_id = invoice.id
|
|
# rec.state = 'invoice'
|
|
|
|
@api.multi
|
|
def action_cancel(self):
|
|
self.state = 'cancel'
|
|
|
|
|
|
# vim:expandtab:smartindent:tabstop=4:softtabstop=4:shiftwidth=4:
|