2013-12-16 05:24:51 +00:00
|
|
|
# -*- coding: utf-8 -*-
|
|
|
|
##############################################################################
|
|
|
|
#
|
|
|
|
# OpenERP, Open Source Management Solution
|
|
|
|
# Copyright (C) 2013-Today OpenERP SA (<http://www.openerp.com>).
|
|
|
|
#
|
|
|
|
# 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/>.
|
|
|
|
#
|
|
|
|
##############################################################################
|
2013-12-02 12:34:37 +00:00
|
|
|
|
|
|
|
from openerp import SUPERUSER_ID
|
|
|
|
from openerp.addons.web import http
|
|
|
|
from openerp.addons.web.http import request
|
2014-01-03 07:04:49 +00:00
|
|
|
import werkzeug
|
2014-01-22 12:18:56 +00:00
|
|
|
import datetime
|
2014-01-25 22:10:59 +00:00
|
|
|
import time
|
2013-12-16 05:24:51 +00:00
|
|
|
|
2014-01-25 12:37:58 +00:00
|
|
|
from openerp.tools.translate import _
|
|
|
|
|
2013-12-02 12:34:37 +00:00
|
|
|
class sale_quote(http.Controller):
|
2014-01-23 10:23:37 +00:00
|
|
|
@http.route([
|
|
|
|
"/quote/<int:order_id>",
|
|
|
|
"/quote/<int:order_id>/<token>"
|
|
|
|
], type='http', auth="public", website=True)
|
|
|
|
def view(self, order_id, token=None, message=False, **post):
|
2013-12-20 05:46:36 +00:00
|
|
|
# use SUPERUSER_ID allow to access/view order for public user
|
2014-01-25 16:12:03 +00:00
|
|
|
# only if he knows the private token
|
2015-04-14 14:58:39 +00:00
|
|
|
order = request.registry.get('sale.order').browse(request.cr, token and SUPERUSER_ID or request.uid, order_id, request.context)
|
2014-01-25 22:40:01 +00:00
|
|
|
now = time.strftime('%Y-%m-%d')
|
2014-01-25 22:10:59 +00:00
|
|
|
if token:
|
2014-01-25 22:52:33 +00:00
|
|
|
if token != order.access_token:
|
|
|
|
return request.website.render('website.404')
|
2014-01-25 22:40:01 +00:00
|
|
|
# Log only once a day
|
2014-02-25 09:05:06 +00:00
|
|
|
if request.session.get('view_quote',False)!=now:
|
|
|
|
request.session['view_quote'] = now
|
2014-01-25 22:10:59 +00:00
|
|
|
body=_('Quotation viewed by customer')
|
|
|
|
self.__message_post(body, order_id, type='comment')
|
2014-01-25 17:24:55 +00:00
|
|
|
days = 0
|
|
|
|
if order.validity_date:
|
2014-01-25 18:27:19 +00:00
|
|
|
days = (datetime.datetime.strptime(order.validity_date, '%Y-%m-%d') - datetime.datetime.now()).days + 1
|
2014-01-01 15:47:54 +00:00
|
|
|
values = {
|
2013-12-16 08:49:35 +00:00
|
|
|
'quotation': order,
|
2014-01-25 22:10:59 +00:00
|
|
|
'message': message and int(message) or False,
|
2014-01-25 16:12:03 +00:00
|
|
|
'option': bool(filter(lambda x: not x.line_id, order.options)),
|
2014-01-25 22:40:01 +00:00
|
|
|
'order_valid': (not order.validity_date) or (now <= order.validity_date),
|
2015-04-16 14:15:08 +00:00
|
|
|
'days_valid': days,
|
2014-01-01 15:47:54 +00:00
|
|
|
}
|
2014-01-25 23:08:47 +00:00
|
|
|
return request.website.render('website_quote.so_quotation', values)
|
2013-12-02 12:34:37 +00:00
|
|
|
|
2014-01-20 20:52:29 +00:00
|
|
|
@http.route(['/quote/accept'], type='json', auth="public", website=True)
|
2014-05-11 11:52:31 +00:00
|
|
|
def accept(self, order_id, token=None, signer=None, sign=None, **post):
|
2014-01-18 10:46:34 +00:00
|
|
|
order_obj = request.registry.get('sale.order')
|
|
|
|
order = order_obj.browse(request.cr, SUPERUSER_ID, order_id)
|
2014-01-25 22:52:33 +00:00
|
|
|
if token != order.access_token:
|
|
|
|
return request.website.render('website.404')
|
2015-10-09 14:50:23 +00:00
|
|
|
if order.state != 'sent':
|
|
|
|
return False
|
2014-05-16 14:47:29 +00:00
|
|
|
attachments=sign and [('signature.png', sign.decode('base64'))] or []
|
2014-07-07 09:50:30 +00:00
|
|
|
order_obj.signal_workflow(request.cr, SUPERUSER_ID, [order_id], 'order_confirm', context=request.context)
|
2014-01-25 19:25:53 +00:00
|
|
|
message = _('Order signed by %s') % (signer,)
|
|
|
|
self.__message_post(message, order_id, type='comment', subtype='mt_comment', attachments=attachments)
|
|
|
|
return True
|
2013-12-02 12:34:37 +00:00
|
|
|
|
2014-01-20 20:52:29 +00:00
|
|
|
@http.route(['/quote/<int:order_id>/<token>/decline'], type='http', auth="public", website=True)
|
2014-01-03 07:04:49 +00:00
|
|
|
def decline(self, order_id, token, **post):
|
2014-01-25 16:12:03 +00:00
|
|
|
order_obj = request.registry.get('sale.order')
|
|
|
|
order = order_obj.browse(request.cr, SUPERUSER_ID, order_id)
|
2014-01-25 22:52:33 +00:00
|
|
|
if token != order.access_token:
|
|
|
|
return request.website.render('website.404')
|
2015-10-09 14:50:23 +00:00
|
|
|
if order.state != 'sent':
|
|
|
|
return werkzeug.utils.redirect("/quote/%s/%s?message=4" % (order_id, token))
|
2014-01-25 16:12:03 +00:00
|
|
|
request.registry.get('sale.order').action_cancel(request.cr, SUPERUSER_ID, [order_id])
|
2014-01-03 07:04:49 +00:00
|
|
|
message = post.get('decline_message')
|
|
|
|
if message:
|
2014-01-25 16:12:03 +00:00
|
|
|
self.__message_post(message, order_id, type='comment', subtype='mt_comment')
|
2014-01-20 22:22:28 +00:00
|
|
|
return werkzeug.utils.redirect("/quote/%s/%s?message=2" % (order_id, token))
|
2013-12-02 12:34:37 +00:00
|
|
|
|
2014-01-20 20:52:29 +00:00
|
|
|
@http.route(['/quote/<int:order_id>/<token>/post'], type='http', auth="public", website=True)
|
2014-01-01 19:21:21 +00:00
|
|
|
def post(self, order_id, token, **post):
|
2014-01-01 15:47:54 +00:00
|
|
|
# use SUPERUSER_ID allow to access/view order for public user
|
2014-01-17 10:07:46 +00:00
|
|
|
order_obj = request.registry.get('sale.order')
|
|
|
|
order = order_obj.browse(request.cr, SUPERUSER_ID, order_id)
|
2014-01-03 09:11:18 +00:00
|
|
|
message = post.get('comment')
|
2014-01-25 22:52:33 +00:00
|
|
|
if token != order.access_token:
|
|
|
|
return request.website.render('website.404')
|
2014-01-03 07:04:49 +00:00
|
|
|
if message:
|
2014-01-25 16:12:03 +00:00
|
|
|
self.__message_post(message, order_id, type='comment', subtype='mt_comment')
|
2014-01-20 22:22:28 +00:00
|
|
|
return werkzeug.utils.redirect("/quote/%s/%s?message=1" % (order_id, token))
|
2014-01-01 15:47:54 +00:00
|
|
|
|
2014-01-25 16:12:03 +00:00
|
|
|
def __message_post(self, message, order_id, type='comment', subtype=False, attachments=[]):
|
2014-01-03 07:04:49 +00:00
|
|
|
request.session.body = message
|
|
|
|
cr, uid, context = request.cr, request.uid, request.context
|
2014-01-24 06:33:10 +00:00
|
|
|
user = request.registry['res.users'].browse(cr, SUPERUSER_ID, uid, context=context)
|
2013-12-02 12:34:37 +00:00
|
|
|
if 'body' in request.session and request.session.body:
|
2014-01-24 06:33:10 +00:00
|
|
|
request.registry.get('sale.order').message_post(cr, SUPERUSER_ID, order_id,
|
2013-12-02 12:34:37 +00:00
|
|
|
body=request.session.body,
|
2014-01-23 10:23:37 +00:00
|
|
|
type=type,
|
2014-01-23 14:01:28 +00:00
|
|
|
subtype=subtype,
|
2014-01-24 06:33:10 +00:00
|
|
|
author_id=user.partner_id.id,
|
2014-01-03 07:04:49 +00:00
|
|
|
context=context,
|
2014-01-25 16:12:03 +00:00
|
|
|
attachments=attachments
|
2013-12-02 12:34:37 +00:00
|
|
|
)
|
|
|
|
request.session.body = False
|
2014-01-03 07:04:49 +00:00
|
|
|
return True
|
2013-12-02 12:34:37 +00:00
|
|
|
|
2014-01-20 20:52:29 +00:00
|
|
|
@http.route(['/quote/update_line'], type='json', auth="public", website=True)
|
2014-05-11 11:52:31 +00:00
|
|
|
def update(self, line_id, remove=False, unlink=False, order_id=None, token=None, **post):
|
2014-01-03 15:54:45 +00:00
|
|
|
order = request.registry.get('sale.order').browse(request.cr, SUPERUSER_ID, int(order_id))
|
2014-01-25 22:52:33 +00:00
|
|
|
if token != order.access_token:
|
|
|
|
return request.website.render('website.404')
|
2014-01-25 20:30:52 +00:00
|
|
|
if order.state not in ('draft','sent'):
|
|
|
|
return False
|
2014-01-25 20:41:07 +00:00
|
|
|
line_id=int(line_id)
|
2013-12-09 13:10:15 +00:00
|
|
|
if unlink:
|
2014-01-25 20:41:07 +00:00
|
|
|
request.registry.get('sale.order.line').unlink(request.cr, SUPERUSER_ID, [line_id], context=request.context)
|
2014-01-03 15:54:45 +00:00
|
|
|
return False
|
2014-01-25 16:12:03 +00:00
|
|
|
number=(remove and -1 or 1)
|
2013-12-12 11:50:25 +00:00
|
|
|
|
2013-12-10 10:44:42 +00:00
|
|
|
order_line_obj = request.registry.get('sale.order.line')
|
2013-12-20 05:46:36 +00:00
|
|
|
order_line_val = order_line_obj.read(request.cr, SUPERUSER_ID, [line_id], [], context=request.context)[0]
|
2013-12-10 10:44:42 +00:00
|
|
|
quantity = order_line_val['product_uom_qty'] + number
|
2013-12-20 05:46:36 +00:00
|
|
|
order_line_obj.write(request.cr, SUPERUSER_ID, [line_id], {'product_uom_qty': (quantity)}, context=request.context)
|
2014-01-25 16:12:03 +00:00
|
|
|
return [str(quantity), str(order.amount_total)]
|
2014-01-01 15:47:54 +00:00
|
|
|
|
2014-05-13 09:35:45 +00:00
|
|
|
@http.route(["/quote/template/<model('sale.quote.template'):quote>"], type='http', auth="user", website=True)
|
2014-01-03 15:54:45 +00:00
|
|
|
def template_view(self, quote, **post):
|
2014-01-25 16:12:03 +00:00
|
|
|
values = { 'template': quote }
|
2014-01-25 23:08:47 +00:00
|
|
|
return request.website.render('website_quote.so_template', values)
|
2014-01-20 20:52:29 +00:00
|
|
|
|
|
|
|
@http.route(["/quote/add_line/<int:option_id>/<int:order_id>/<token>"], type='http', auth="public", website=True)
|
2014-01-03 15:54:45 +00:00
|
|
|
def add(self, option_id, order_id, token, **post):
|
2014-01-02 15:22:25 +00:00
|
|
|
vals = {}
|
2014-01-03 15:54:45 +00:00
|
|
|
order = request.registry.get('sale.order').browse(request.cr, SUPERUSER_ID, order_id)
|
2014-01-25 22:52:33 +00:00
|
|
|
if token != order.access_token:
|
|
|
|
return request.website.render('website.404')
|
2015-02-12 13:09:49 +00:00
|
|
|
if order.state not in ['draft', 'sent']:
|
|
|
|
return request.website.render('website.http_error', {'status_code': 'Forbidden', 'status_message': _('You cannot add options to a confirmed order.')})
|
2014-01-25 17:24:55 +00:00
|
|
|
option_obj = request.registry.get('sale.order.option')
|
2014-01-03 15:54:45 +00:00
|
|
|
option = option_obj.browse(request.cr, SUPERUSER_ID, option_id)
|
2014-01-25 22:10:59 +00:00
|
|
|
|
|
|
|
res = request.registry.get('sale.order.line').product_id_change(request.cr, SUPERUSER_ID, order_id,
|
|
|
|
False, option.product_id.id, option.quantity, option.uom_id.id, option.quantity, option.uom_id.id,
|
|
|
|
option.name, order.partner_id.id, False, True, time.strftime('%Y-%m-%d'),
|
2015-08-25 12:52:20 +00:00
|
|
|
False, order.fiscal_position.id, True, dict(request.context or {}, company_id=order.company_id.id))
|
2014-01-25 22:10:59 +00:00
|
|
|
vals = res.get('value', {})
|
|
|
|
if 'tax_id' in vals:
|
|
|
|
vals['tax_id'] = [(6, 0, vals['tax_id'])]
|
|
|
|
|
2014-01-02 15:22:25 +00:00
|
|
|
vals.update({
|
2014-01-17 10:07:46 +00:00
|
|
|
'price_unit': option.price_unit,
|
|
|
|
'website_description': option.website_description,
|
|
|
|
'name': option.name,
|
2014-01-03 15:54:45 +00:00
|
|
|
'order_id': order.id,
|
|
|
|
'product_id' : option.product_id.id,
|
2014-01-25 22:10:59 +00:00
|
|
|
'product_uos_qty': option.quantity,
|
|
|
|
'product_uos': option.uom_id.id,
|
2014-01-03 15:54:45 +00:00
|
|
|
'product_uom_qty': option.quantity,
|
2014-01-25 22:10:59 +00:00
|
|
|
'product_uom': option.uom_id.id,
|
2014-01-03 15:54:45 +00:00
|
|
|
'discount': option.discount,
|
2014-01-02 15:22:25 +00:00
|
|
|
})
|
2014-01-03 15:54:45 +00:00
|
|
|
line = request.registry.get('sale.order.line').create(request.cr, SUPERUSER_ID, vals, context=request.context)
|
|
|
|
option_obj.write(request.cr, SUPERUSER_ID, [option.id], {'line_id': line}, context=request.context)
|
2014-01-21 12:53:14 +00:00
|
|
|
return werkzeug.utils.redirect("/quote/%s/%s#pricing" % (order.id, token))
|
2014-01-03 15:54:45 +00:00
|
|
|
|
2014-01-02 15:22:25 +00:00
|
|
|
|