Merge branch 'master' of git:~/gitrepos/cam-template
commit
2e5e5328ff
|
|
@ -127,3 +127,14 @@ class mail_notification(osv.Model):
|
|||
# c.update({'display_default_code': False})
|
||||
# return super(product_product, self).name_get(cr, user, ids, context=c)
|
||||
|
||||
class sale_order_line(models.Model):
|
||||
_inherit = 'sale.order.line'
|
||||
|
||||
@api.onchange('name')
|
||||
def onchange_name(self):
|
||||
if self.name != False and self.product_id.id == False:
|
||||
ir_values = self.pool.get('ir.values')
|
||||
company = self.env['res.company'].search([], limit=1)
|
||||
taxes_id = ir_values.get_default(self._cr, self._uid, 'product.template', 'taxes_id', company_id=company.id)
|
||||
at = self.env['account.tax'].search([('id','=',isinstance(taxes_id, list) and taxes_id[0] or taxes_id)])
|
||||
self.tax_id = at
|
||||
|
|
|
|||
|
|
@ -0,0 +1,19 @@
|
|||
# -*- coding: utf-8 -*-
|
||||
##############################################################################
|
||||
#
|
||||
# This program is free software: you can redistribute it and/or modify
|
||||
# it under the terms of the GNU Affero General Public License as
|
||||
# published by the Free Software Foundation, either version 3 of the
|
||||
# License, or (at your option) any later version.
|
||||
#
|
||||
# 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 Affero General Public License for more details.
|
||||
#
|
||||
# You should have received a copy of the GNU Affero General Public License
|
||||
# along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
#
|
||||
##############################################################################
|
||||
|
||||
import sale_order_optional
|
||||
|
|
@ -0,0 +1,39 @@
|
|||
# -*- coding: utf-8 -*-
|
||||
##############################################################################
|
||||
#
|
||||
# This program is free software: you can redistribute it and/or modify
|
||||
# it under the terms of the GNU Affero General Public License as
|
||||
# published by the Free Software Foundation, either version 3 of the
|
||||
# License, or (at your option) any later version.
|
||||
#
|
||||
# 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 Affero General Public License for more details.
|
||||
#
|
||||
# You should have received a copy of the GNU Affero General Public License
|
||||
# along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
#
|
||||
##############################################################################
|
||||
|
||||
{
|
||||
'name': "Optional Lines for Sale Orders",
|
||||
'version': "1.0",
|
||||
'category': "Sales",
|
||||
'description': """
|
||||
This addon adds optional sale order lines.
|
||||
""",
|
||||
'author': "Camadeus GmbH",
|
||||
'website': "http://www.camadeus.at",
|
||||
'css': [],
|
||||
'images': [],
|
||||
'depends': ['sale'],
|
||||
'data': ['sale_order_optional_view.xml',
|
||||
'sale_order_optional_data.xml',
|
||||
],
|
||||
'installable': True,
|
||||
'auto_install': False,
|
||||
'application': False,
|
||||
}
|
||||
|
||||
# vim:expandtab:smartindent:tabstop=4:softtabstop=4:shiftwidth=4:
|
||||
|
|
@ -0,0 +1,135 @@
|
|||
# -*- encoding: utf-8 -*-
|
||||
##############################################################################
|
||||
#
|
||||
# OpenERP, Open Source Management Solution
|
||||
# Copyright (C) 2004-2009 Tiny SPRL (<http://tiny.be>). All Rights Reserved
|
||||
# $Id$
|
||||
#
|
||||
# This program is free software: you can redistribute it and/or modify
|
||||
# it under the terms of the GNU General Public License as published by
|
||||
# the Free Software Foundation, either version 3 of the License, or
|
||||
# (at your option) any later version.
|
||||
#
|
||||
# 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 General Public License for more details.
|
||||
#
|
||||
# You should have received a copy of the GNU General Public License
|
||||
# along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
#
|
||||
##############################################################################
|
||||
|
||||
from openerp.osv import fields, osv
|
||||
import openerp.addons.decimal_precision as dp
|
||||
|
||||
class sale_order(osv.osv):
|
||||
_inherit = "sale.order"
|
||||
|
||||
def _amount_line_tax(self, cr, uid, line, context=None):
|
||||
val = 0.0
|
||||
if not line.optional:
|
||||
for c in self.pool.get('account.tax').compute_all(cr, uid, line.tax_id, line.price_unit * (1-(line.discount or 0.0)/100.0), line.product_uom_qty, line.product_id, line.order_id.partner_id)['taxes']:
|
||||
val += c.get('amount', 0.0)
|
||||
return val
|
||||
|
||||
def _amount_all(self, cr, uid, ids, field_name, arg, context=None):
|
||||
cur_obj = self.pool.get('res.currency')
|
||||
res = {}
|
||||
for order in self.browse(cr, uid, ids, context=context):
|
||||
res[order.id] = {
|
||||
'amount_untaxed': 0.0,
|
||||
'amount_tax': 0.0,
|
||||
'amount_total': 0.0,
|
||||
}
|
||||
val = val1 = 0.0
|
||||
cur = order.pricelist_id.currency_id
|
||||
for line in order.order_line:
|
||||
val1 += line.price_subtotal
|
||||
val += self._amount_line_tax(cr, uid, line, context=context)
|
||||
res[order.id]['amount_tax'] = cur_obj.round(cr, uid, cur, val)
|
||||
res[order.id]['amount_untaxed'] = cur_obj.round(cr, uid, cur, val1)
|
||||
res[order.id]['amount_total'] = res[order.id]['amount_untaxed'] + res[order.id]['amount_tax']
|
||||
return res
|
||||
|
||||
def _amount_all_wrapper(self, cr, uid, ids, field_name, arg, context=None):
|
||||
""" Wrapper because of direct method passing as parameter for function fields """
|
||||
return self._amount_all(cr, uid, ids, field_name, arg, context=context)
|
||||
|
||||
def _get_order(self, cr, uid, ids, context=None):
|
||||
result = {}
|
||||
for line in self.pool.get('sale.order.line').browse(cr, uid, ids, context=context):
|
||||
result[line.order_id.id] = True
|
||||
return result.keys()
|
||||
|
||||
_columns = {
|
||||
'amount_untaxed': fields.function(_amount_all_wrapper, digits_compute=dp.get_precision('Account'), string='Untaxed Amount',
|
||||
store={
|
||||
'sale.order': (lambda self, cr, uid, ids, c={}: ids, ['order_line'], 10),
|
||||
'sale.order.line': (_get_order, ['price_unit', 'tax_id', 'discount', 'product_uom_qty'], 10),
|
||||
},
|
||||
multi='sums', help="The amount without tax.", track_visibility='always'),
|
||||
'amount_tax': fields.function(_amount_all_wrapper, digits_compute=dp.get_precision('Account'), string='Taxes',
|
||||
store={
|
||||
'sale.order': (lambda self, cr, uid, ids, c={}: ids, ['order_line'], 10),
|
||||
'sale.order.line': (_get_order, ['price_unit', 'tax_id', 'discount', 'product_uom_qty'], 10),
|
||||
},
|
||||
multi='sums', help="The tax amount."),
|
||||
'amount_total': fields.function(_amount_all_wrapper, digits_compute=dp.get_precision('Account'), string='Total',
|
||||
store={
|
||||
'sale.order': (lambda self, cr, uid, ids, c={}: ids, ['order_line'], 10),
|
||||
'sale.order.line': (_get_order, ['price_unit', 'tax_id', 'discount', 'product_uom_qty'], 10),
|
||||
},
|
||||
multi='sums', help="The total amount."),
|
||||
}
|
||||
|
||||
class sale_order_line(osv.osv):
|
||||
_inherit = 'sale.order.line'
|
||||
|
||||
def _fnct_line_invoiced(self, cr, uid, ids, field_name, args, context=None):
|
||||
res = dict.fromkeys(ids, False)
|
||||
for this in self.browse(cr, uid, ids, context=context):
|
||||
res[this.id] = this.invoice_lines and \
|
||||
all(iline.invoice_id.state != 'cancel' for iline in this.invoice_lines) or \
|
||||
this.optional
|
||||
return res
|
||||
|
||||
def _order_lines_from_invoice(self, cr, uid, ids, context=None):
|
||||
# direct access to the m2m table is the less convoluted way to achieve this (and is ok ACL-wise)
|
||||
cr.execute("""SELECT DISTINCT sol.id FROM sale_order_invoice_rel rel JOIN
|
||||
sale_order_line sol ON (sol.order_id = rel.order_id)
|
||||
WHERE rel.invoice_id = ANY(%s)""", (list(ids),))
|
||||
return [i[0] for i in cr.fetchall()]
|
||||
|
||||
def _amount_line(self, cr, uid, ids, field_name, arg, context=None):
|
||||
tax_obj = self.pool.get('account.tax')
|
||||
cur_obj = self.pool.get('res.currency')
|
||||
res = {}
|
||||
if context is None:
|
||||
context = {}
|
||||
for line in self.browse(cr, uid, ids, context=context):
|
||||
if not line.optional:
|
||||
price = line.price_unit * (1 - (line.discount or 0.0) / 100.0)
|
||||
taxes = tax_obj.compute_all(cr, uid, line.tax_id, price, line.product_uom_qty, line.product_id, line.order_id.partner_id)
|
||||
cur = line.order_id.pricelist_id.currency_id
|
||||
res[line.id] = cur_obj.round(cr, uid, cur, taxes['total'])
|
||||
else:
|
||||
res[line.id] = 0
|
||||
return res
|
||||
|
||||
_columns = {
|
||||
'invoiced': fields.function(_fnct_line_invoiced, string='Invoiced', type='boolean',
|
||||
store={
|
||||
'account.invoice': (_order_lines_from_invoice, ['state'], 10),
|
||||
'sale.order.line': (lambda self,cr,uid,ids,ctx=None: ids, ['invoice_lines'], 10)
|
||||
}),
|
||||
'price_subtotal': fields.function(_amount_line, string='Subtotal', digits_compute= dp.get_precision('Account')),
|
||||
'optional': fields.boolean('Optional'),
|
||||
}
|
||||
|
||||
def _prepare_order_line_invoice_line(self, cr, uid, line, account_id=False, context=None):
|
||||
if not line.optional:
|
||||
return super(sale_order_line, self)._prepare_order_line_invoice_line(cr, uid, line, account_id, context=context)
|
||||
else:
|
||||
return False
|
||||
|
||||
|
|
@ -0,0 +1,6 @@
|
|||
<?xml version="1.0" encoding='UTF-8'?>
|
||||
<openerp>
|
||||
<data>
|
||||
|
||||
</data>
|
||||
</openerp>
|
||||
|
|
@ -0,0 +1,17 @@
|
|||
<?xml version="1.0" encoding="utf-8"?>
|
||||
<openerp>
|
||||
<data>
|
||||
|
||||
<record id="view_order_form_optional" model="ir.ui.view">
|
||||
<field name="name">sale.order.form.optional</field>
|
||||
<field name="model">sale.order</field>
|
||||
<field name="inherit_id" ref="sale.view_order_form"/>
|
||||
<field name="arch" type="xml">
|
||||
<xpath expr="//tree/field[@name='price_subtotal']" position="after">
|
||||
<field name="optional"/>
|
||||
</xpath>
|
||||
</field>
|
||||
</record>
|
||||
|
||||
</data>
|
||||
</openerp>
|
||||
Binary file not shown.
|
After Width: | Height: | Size: 2.8 KiB |
|
|
@ -0,0 +1,19 @@
|
|||
# -*- coding: utf-8 -*-
|
||||
##############################################################################
|
||||
#
|
||||
# This program is free software: you can redistribute it and/or modify
|
||||
# it under the terms of the GNU Affero General Public License as
|
||||
# published by the Free Software Foundation, either version 3 of the
|
||||
# License, or (at your option) any later version.
|
||||
#
|
||||
# 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 Affero General Public License for more details.
|
||||
#
|
||||
# You should have received a copy of the GNU Affero General Public License
|
||||
# along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
#
|
||||
##############################################################################
|
||||
|
||||
import sale_order_reminder
|
||||
|
|
@ -0,0 +1,41 @@
|
|||
# -*- coding: utf-8 -*-
|
||||
##############################################################################
|
||||
#
|
||||
# This program is free software: you can redistribute it and/or modify
|
||||
# it under the terms of the GNU Affero General Public License as
|
||||
# published by the Free Software Foundation, either version 3 of the
|
||||
# License, or (at your option) any later version.
|
||||
#
|
||||
# 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 Affero General Public License for more details.
|
||||
#
|
||||
# You should have received a copy of the GNU Affero General Public License
|
||||
# along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
#
|
||||
##############################################################################
|
||||
|
||||
{
|
||||
'name': "Reminder for Sale Orders",
|
||||
'version': "1.0",
|
||||
'category': "Sales",
|
||||
'description': """
|
||||
This addon adds the field 'offer_valid_until' in the sale order. If this date is passed and the order is still in state 'draft' or 'sent', then
|
||||
a reminder email is sent to the sales person every day.
|
||||
""",
|
||||
'author': "Camadeus GmbH",
|
||||
'website': "http://www.camadeus.at",
|
||||
'css': [],
|
||||
'images': [],
|
||||
'depends': ['sale'],
|
||||
'data': ['sale_order_reminder_view.xml',
|
||||
'sale_order_reminder_data.xml',
|
||||
'email_template.xml',
|
||||
],
|
||||
'installable': True,
|
||||
'auto_install': False,
|
||||
'application': False,
|
||||
}
|
||||
|
||||
# vim:expandtab:smartindent:tabstop=4:softtabstop=4:shiftwidth=4:
|
||||
|
|
@ -0,0 +1,46 @@
|
|||
<?xml version="1.0" ?>
|
||||
<openerp>
|
||||
|
||||
<!-- Mail template is done in a NOUPDATE block
|
||||
so users can freely customize/delete them -->
|
||||
<data noupdate="1">
|
||||
|
||||
<!--Email template -->
|
||||
<record id="email_template_sale_reminder" model="email.template">
|
||||
<field name="name">Erinnerung: Angebot</field>
|
||||
<field name="email_from">${(object.user_id and object.user_id.email or '')|safe}</field>
|
||||
<field name="subject">Erinnerung: Angebot ${object.name}</field>
|
||||
<field name="partner_to">${object.user_id and object.user_id.partner_id.id}</field>
|
||||
<field name="model_id" ref="sale.model_sale_order"/>
|
||||
<field name="auto_delete" eval="True"/>
|
||||
<field name="body_html"><![CDATA[
|
||||
<div style="color:#007434; font-size:10.0pt; font-family:Arial Unicode MS sans-serif;">
|
||||
<p>Erinnerung für folgendes offenes Angebot:</p>
|
||||
|
||||
<p>
|
||||
<table style="color:#007434; font-size:10.0pt; font-family:Arial Unicode MS sans-serif;">
|
||||
<tr>
|
||||
<td style='width: 200px;'>Name:</td>
|
||||
<td><b>${object.name}</b></td>
|
||||
</tr>
|
||||
<tr>
|
||||
<td>Datum:</td>
|
||||
<td> ${object.date_order}</td>
|
||||
</tr>
|
||||
<tr>
|
||||
<td>Kunde:</td>
|
||||
<td> ${object.partner_id.display_name}</td>
|
||||
</tr>
|
||||
<tr>
|
||||
<td>Auftragsvolumen (netto):</td>
|
||||
<td> ${object.amount_untaxed}</td>
|
||||
</tr>
|
||||
</table>
|
||||
|
||||
</p>
|
||||
<br>
|
||||
</div>
|
||||
]]></field>
|
||||
</record>
|
||||
</data>
|
||||
</openerp>
|
||||
|
|
@ -0,0 +1,68 @@
|
|||
# -*- encoding: utf-8 -*-
|
||||
##############################################################################
|
||||
#
|
||||
# OpenERP, Open Source Management Solution
|
||||
# Copyright (C) 2004-2009 Tiny SPRL (<http://tiny.be>). All Rights Reserved
|
||||
# $Id$
|
||||
#
|
||||
# This program is free software: you can redistribute it and/or modify
|
||||
# it under the terms of the GNU General Public License as published by
|
||||
# the Free Software Foundation, either version 3 of the License, or
|
||||
# (at your option) any later version.
|
||||
#
|
||||
# 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 General Public License for more details.
|
||||
#
|
||||
# You should have received a copy of the GNU General Public License
|
||||
# along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
#
|
||||
##############################################################################
|
||||
|
||||
from openerp import models, fields, api, _
|
||||
from datetime import datetime, timedelta
|
||||
from openerp.tools import DEFAULT_SERVER_DATE_FORMAT as DATE_FORMAT
|
||||
|
||||
class res_company(models.Model):
|
||||
_inherit = 'res.company'
|
||||
|
||||
sale_offer_days = fields.Integer(string='Tage Gültigkeit Angebot', default=14)
|
||||
|
||||
class sale_order(models.Model):
|
||||
_inherit = 'sale.order'
|
||||
|
||||
@api.model
|
||||
def _offer_valid_until(self):
|
||||
user = self.env['res.users'].browse(self._uid)
|
||||
|
||||
now = datetime.now()
|
||||
res = now + timedelta(days=user.company_id.sale_offer_days)
|
||||
return res.strftime(DATE_FORMAT)
|
||||
|
||||
|
||||
offer_valid_until = fields.Date(string='Angebot gültig bis', index=True,
|
||||
readonly=True, states={'draft': [('readonly', False)], 'sent': [('readonly', False)]},
|
||||
default=_offer_valid_until)
|
||||
|
||||
@api.model
|
||||
def order_reminder_job(self):
|
||||
today = fields.Date.today()
|
||||
orders = self.search([('offer_valid_until','<',today),('state','in',('draft','sent')),('user_id','!=',False)])
|
||||
template_id = self.env['ir.model.data'].xmlid_to_res_id('sale_order_reminder.email_template_sale_reminder')
|
||||
context = {'append_link': True}
|
||||
for order in orders:
|
||||
res = self.pool.get('email.template').send_mail(self._cr, self._uid, template_id, order.id, True, context=context)
|
||||
return True
|
||||
|
||||
class mail_mail(models.Model):
|
||||
_inherit = 'mail.mail'
|
||||
|
||||
def create(self, cr, uid, vals, context=None):
|
||||
# notification field: set if it comes from order reminder job
|
||||
if context is None:
|
||||
context = {}
|
||||
|
||||
if context.get('append_link'):
|
||||
vals['notification'] = True
|
||||
return super(mail_mail, self).create(cr, uid, vals, context=context)
|
||||
|
|
@ -0,0 +1,16 @@
|
|||
<?xml version="1.0" encoding='UTF-8'?>
|
||||
<openerp>
|
||||
<data>
|
||||
|
||||
<record model="ir.cron" id="cron_sale_offer_reminder">
|
||||
<field name="name">Reminder for Sale Orders</field>
|
||||
<field name="interval_number">1</field>
|
||||
<field name="interval_type">days</field>
|
||||
<field name="numbercall">-1</field>
|
||||
<field name="doall" eval="False"/>
|
||||
<field name="model" eval="'sale.order'"/>
|
||||
<field name="function" eval="'order_reminder_job'"/>
|
||||
<field name="args" eval="'()'" />
|
||||
</record>
|
||||
</data>
|
||||
</openerp>
|
||||
|
|
@ -0,0 +1,31 @@
|
|||
<?xml version="1.0" encoding="utf-8"?>
|
||||
<openerp>
|
||||
<data>
|
||||
|
||||
<record id="sale_order_valid_until_form" model="ir.ui.view">
|
||||
<field name="name">sale_order_valid_until_form</field>
|
||||
<field name="model">sale.order</field>
|
||||
<field name="inherit_id" ref="sale.view_order_form"/>
|
||||
<field name="arch" type="xml">
|
||||
<field name="date_order" position="after">
|
||||
<field name="offer_valid_until"/>
|
||||
</field>
|
||||
</field>
|
||||
<field name="priority">20</field>
|
||||
</record> #
|
||||
|
||||
<record id="res_company_order_days_form" model="ir.ui.view">
|
||||
<field name="name">"res_company_order_days_form"</field>
|
||||
<field name="model">res.company</field>
|
||||
<field name="inherit_id" ref="base.view_company_form"/>
|
||||
<field name="arch" type="xml">
|
||||
<field name="sale_note" position="after">
|
||||
<group>
|
||||
<field name="sale_offer_days"/>
|
||||
</group>
|
||||
</field>
|
||||
</field>
|
||||
</record>
|
||||
|
||||
</data>
|
||||
</openerp>
|
||||
Binary file not shown.
|
After Width: | Height: | Size: 2.8 KiB |
|
|
@ -185,6 +185,8 @@ class Config():
|
|||
'sale',
|
||||
#'cam_hr_overtime',
|
||||
#'cam_hr',
|
||||
#'sale_order_optiona',
|
||||
#'sale_order_reminder',
|
||||
]
|
||||
|
||||
self.users_file = "res.users.csv"
|
||||
|
|
|
|||
Loading…
Reference in New Issue