odoo/ext/3rd-party-addons/sales_commission_external_user/models/sales_commission.py

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: