hms_bak/hotel_management/models/hotel_management.py
2024-10-08 01:17:38 +04:00

3017 lines
135 KiB
Python

# -*- encoding: utf-8 -*-
import time
from dateutil.relativedelta import relativedelta
import datetime
from datetime import date
from odoo import api, fields, models, tools, _, SUPERUSER_ID
from odoo.exceptions import ValidationError, UserError
from odoo.exceptions import UserError
from odoo.tools import config
# import odoo.addons.decimal_precision as dp
from odoo.tools.translate import _
from odoo.tools import format_amount
import calendar
from datetime import datetime, timedelta, timezone
import logging
_logger = logging.getLogger(__name__)
from dateutil.parser import *
import pytz
import math
utc_time = datetime.utcnow()
from odoo.tools import DEFAULT_SERVER_DATETIME_FORMAT
# @api.multi
def get_price(self, pricelist_ids, price):
price_amt = 0.0
pricelist_item_ids = []
if self._context is None:
self._context = {}
date = time.strftime('%Y-%m-%d')
if 'date' in self._context:
date = self._context['date']
currency_obj = self.env['res.currency']
product_pricelist_version_obj = self.env['product.pricelist.item']
user_browse = self.env['res.users']
company_obj = self.env['res.company']
company_id = company_obj.browse(user_browse.company_id.id)
pricelist_obj = self.env[
'product.pricelist'].browse(pricelist_ids)
if pricelist_ids:
pricelist_item_ids.append(pricelist_ids)
pricelist_obj = self.env[
'product.pricelist'].browse(pricelist_ids)
pricelist_item_ids = list(set(pricelist_item_ids))
plversions_search_args = [
('pricelist_id', 'in', pricelist_item_ids),
'|',
('date_start', '=', False),
('date_start', '<=', date),
'|',
('date_end', '=', False),
('date_end', '>=', date),
]
plversion_ids = product_pricelist_version_obj.search(
plversions_search_args)
if not plversion_ids:
msg = "At least one pricelist item has not declared !\nPlease create pricelist item."
raise UserError(_('Warning !'), _(msg))
self._cr.execute(
'SELECT i.* '
'FROM product_pricelist_item AS i '
'WHERE id = ' + str(plversion_ids[0].id) + '')
res1 = self._cr.dictfetchall()
if pricelist_obj:
price = currency_obj.compute(
price, pricelist_obj.currency_id.id, round=False)
for res in res1:
if res:
price_limit = price
x = (1.0 + (res['price_discount'] or 0.0))
price = price * (1.0 + (res['price_discount'] or 0.0))
price += (res['price_surcharge'] or 0.0)
if res['price_min_margin']:
price = max(price, price_limit + res['price_min_margin'])
if res['price_max_margin']:
price = min(price, price_limit + res['price_max_margin'])
break
price_amt = price
return price_amt
# Class creation for ID Master
class id_master(models.Model):
_name = 'id.master'
_description = 'Clients ID details'
name = fields.Char('ID Name', required=True)
id_code = fields.Char('ID Code', required=True)
class checkout_configuration(models.Model):
_name = 'checkout.configuration'
_description = 'Checkout Configuration'
name = fields.Selection([('custom', 'Custom'), ('24hour', '24 Hours')],
'Checkout Time', default='24hour', required=True)
time = fields.Selection([
('01', '1 AM'), ('02', '2 AM'), ('03', '3 AM'), ('04', '4 AM'), ('05', '5 AM'), (
'06', '6 AM'), ('07', '7 AM'), ('08', '8 AM'), ('09', '9 AM'), ('10', '10 AM'),
('11', '11 AM'), ('12', '12 Noon'), ('13', '1 PM'), ('14', '2 PM'), ('15', '3 PM'), (
'16', '4 PM'), ('17', '5 PM'), ('18', '6 PM'), ('19', '7 PM'), ('20', '8 PM'),
('21', '9 PM'), ('22', '10 PM'), ('23',
'11 PM'), ('24', '12 Mid Night')
], 'Time', default='10')
shop_id = fields.Many2one('sale.shop', 'Hotel', domain="[('company_id', '=', [current_company_id])]",
required=True,
help="Will show list of shop that belongs to allowed companies of logged-in user. \n -Assign a shop to configure shop-wise check out policy.")
company_id = fields.Many2one(
'res.company', related='shop_id.company_id', string='Company', store=True)
# _sql_constraints = [
# ('shop_id_uniq', 'unique(shop_id)', 'Shop must be unique !'),
# ]
class sale_order(models.Model):
_inherit = "sale.order"
_description = "Sale Order Inherit "
def _amount_line_tax(self, line):
val = 0.0
if line.product_uom_qty == 0:
num_of_days = 1
else:
num_of_days = line.product_uom_qty
taxes = line.tax_id.compute_all(
line.price_unit * (1 - (line.discount or 0.0) / 100.0), quantity=num_of_days)
val = taxes['total_included'] - taxes['total_excluded']
return val
# def _amount_all(self):
# for order in self:
# order.update({
# '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(line)
# if cur:
# total = cur.round(val1) + cur.round(val)
# order.update({
# 'amount_untaxed': cur.round(val1),
# 'amount_tax': cur.round(val),
# 'amount_total': total,
# })
# state = fields.Selection(selection_add=[
# ('draft', 'Quotation'),
# ('sent', 'Quotation Sent'),
# ('sale', 'To Invoice'),
# ('progress', 'In Progress'),
# ('check_out', 'CheckOut'),
# ('done', 'Done'),
# ('cancel', 'Cancelled')
# ], string='Order State', readonly=True, index=True)
# amount_untaxed = fields.Monetary(string='Untaxed Amount', store=True, readonly=True, compute='_amount_all',
# tracking=5)
# amount_tax = fields.Monetary(
# string='Taxes', store=True, readonly=True, compute='_amount_all')
# amount_total = fields.Monetary(
# string='Total', store=True, readonly=True, compute='_amount_all')
transfer_invoice_ids = fields.Many2many('account.move', 'sale_transfer_account_invoice_rel', 'sale_id',
'invoice_id', "Transfer Invoice Details")
class hotel_reservation(models.Model):
_name = "hotel.reservation"
_description = "Reservation"
_inherit = ['mail.thread', 'mail.activity.mixin', 'portal.mixin']
def unlink(self):
for record in self:
if record.state in ['confirm', 'done']:
raise UserError(
"Reservation could not be Deleted once it is Confirm")
else:
for hotel_id in record:
hotel_id.reservation_line.unlink()
return super(hotel_reservation, self).unlink()
def hotel_reservation_web_unlink(self):
hotel_reservation_ids = self.search(
[('state', '=', 'draft')])
remove_web_draft = self.env['ir.config_parameter'].get_param('remove_draft_web_reservation')
time_diff = 0
for reservation in hotel_reservation_ids:
current_datetime = fields.Datetime.now()
reservation_line = self.env['hotel.reservation.line'].search([('line_id', '=', reservation.id)], limit=1)
if reservation_line.checkin:
diff = current_datetime - reservation_line.checkin
time_diff = int(diff.seconds // 60)
if remove_web_draft:
if time_diff > int(remove_web_draft):
reservation.cancel_reservation()
# @api.multi
def state_scheduler(self):
room_ids = self.env['hotel.room'].search([])
current_date = fields.Datetime.now()
for room_id in room_ids:
room_folio_ids = self.env['hotel.room.booking.history'].search(
[('history_id', '=', room_id.id)])
for room_folio_id in room_folio_ids:
# print(room_folio_id.check_out.strftime('%Y-%m-%d'))
# print(current_date.strftime('%Y-%m-%d'))
if room_folio_id.check_out.strftime('%Y-%m-%d') < current_date.strftime('%Y-%m-%d') and room_folio_id.booking_id.state in ['draft', 'confirm']:
room_folio_id.booking_id.write({
'state': 'cancel'
})
def _get_report_base_filename(self):
return "Hotel-Report"
def action_set_to_dirty(self):
self.write({'state': 'draft'})
return True
@api.depends('total_cost1', )
def _get_advance_payment(self):
sum = 0.00
remaining = 0.00
for obj in self:
obj.update({
'total_advance': 0.0,
'remaining_amt': 0.0,
})
sum = 0
for line in obj.account_move_ids:
move_lines = self.env['account.move.line'].search(
[('move_id', '=', line.id)])
if move_lines:
for mv in move_lines:
sum = sum + mv.debit
obj.update({
'total_advance': sum,
'remaining_amt': obj.total_cost1 - sum
})
def advance_payment(self):
reservation = self
res_id = reservation.id
value = {}
data_id = self.env['ir.model.data']._xmlid_to_res_id('hotel_management.advance_payment_wizard1')
if self._context is None:
self._context = {}
ctx = dict(self._context)
ctx['active_ids'] = [reservation]
ctx['reservation_id'] = res_id
if data_id:
view_id1 = data_id
value = {
'name': _('Deposit amount entry'),
'view_type': 'form',
'view_mode': 'form',
'res_model': 'advance.payment.wizard',
'view_id': view_id1,
'context': ctx,
'views': [(view_id1, 'form')],
'type': 'ir.actions.act_window',
'target': 'new',
}
return value
def update_resevation(self):
for reservation in self:
room_his_id_search = self.env['hotel.room.booking.history'].search(
[('booking_id', '=', reservation.id)])
room_his_id_search.unlink()
if not reservation.reservation_line:
raise ValidationError("Reservation line Details are missing.")
for line in reservation.reservation_line:
room_line_id = self.env['hotel.room'].search(
[('product_id', '=', line.room_number.id)])
###############################################by pornima######
housekeeping_room = self.env['hotel.housekeeping'].search([
('room_no', '=', room_line_id.product_id.id), ('state', '=', 'dirty')])
if housekeeping_room:
for house1 in housekeeping_room:
# house = self.env['hotel.housekeeping'].browse(house1)
house = house1
house_current_date = (datetime.strptime(
str(house.current_date), '%Y-%m-%d')).date()
house_end_date = (datetime.strptime(
str(house.end_date), '%Y-%m-%d')).date()
start_reser = datetime.strptime(
str(line.checkin), '%Y-%m-%d %H:%M:%S').date()
end_reser = datetime.strptime(
str(line.checkout), '%Y-%m-%d %H:%M:%S').date()
if (house_current_date <= start_reser <= house_end_date) or (
house_current_date <= end_reser <= house_end_date) or (
(start_reser < house_current_date) and (end_reser > house_end_date)):
# if (((start_reser < house_current_date) and (end_reser > house_end_date)) or (house_current_date <= start_reser < house_end_date) or (house_current_date < end_reser <= house_end_date)) and (house.state == 'dirty'):
# print "i am in if loop--------------"
raise ValidationError(
"Room %s is not clean for reservation period !" % (room_line_id.name))
###############################################
if room_line_id.room_folio_ids:
for history in room_line_id.room_folio_ids:
if history.state == 'done':
history_start_date = history.check_in
history_end_date = history.check_out
reservation_start_date = datetime.strptime(
str(line.checkin), '%Y-%m-%d %H:%M:%S')
reservation_end_date = datetime.strptime(
str(line.checkout), '%Y-%m-%d %H:%M:%S')
if (history_start_date <= reservation_start_date < history_end_date) or (
history_start_date < reservation_end_date <= history_end_date) or (
(reservation_start_date < history_start_date) and (
reservation_end_date > history_end_date)):
# print "Already Reserved......."
if not (reservation.id == history.booking_id.id):
raise UserError("Room %s is booked in this reservation period !" % (
room_line_id.name,))
for line in reservation.reservation_line:
# print reservation,"reservation"
room_line_id = self.env['hotel.room'].search(
[('product_id', '=', line.room_number.id)])
room_his_id = self.env['hotel.room.booking.history'].create({
'partner_id': reservation.partner_id.id,
'check_in': line.checkin,
'check_out': line.checkout,
'history_id': room_line_id.id,
'product_id': line.room_number.id,
'booking_id': reservation.id,
'state': 'done',
'category_id': room_line_id.categ_id.id,
'name': line.room_number.name,
'check_in_date': (line.checkin).date(),
'check_out_date': (line.checkout).date(),
})
def write(self, vals):
ret = super(hotel_reservation, self).write(vals)
for res in self:
if res:
no_of_adults_room = 0
no_of_child_room = 0
if res.reservation_line:
for line in res.reservation_line:
if line:
no_of_adults_room += line.room_number.max_adult
no_of_child_room += line.room_number.max_child
_logger.info('\n\n\n{}\n{}\n{}\n\n\n'.format(res.name, res.adults, vals))
# if res.adults <= 0:
# raise ValidationError('Please set no of adults for reservation')
#
# if res.adults > no_of_adults_room:
# raise ValidationError('You can not exceed the number of adults than the set limit on '
# 'individual room.')
#
# if res.childs > no_of_child_room:
# raise ValidationError('You can not exceed the number of children than the set limit on '
# 'individual room.')
return ret
@api.model_create_multi
def create(self, vals):
for val in vals:
val['name'] = self.env['ir.sequence'].next_by_code(
'hotel.reservation') or _('New')
val['reservation_no'] = val['name']
res = super(hotel_reservation, self).create(val)
res.compute()
if res:
no_of_adults_room = 0
no_of_child_room = 0
if res.reservation_line:
for line in res.reservation_line:
if line:
no_of_adults_room += line.room_number.max_adult
no_of_child_room += line.room_number.max_child
# if res.adults <= 0:
# raise ValidationError('Please set no of adults for reservation')
#
# if res.adults > no_of_adults_room:
# raise ValidationError('You can not exceed the number of adults than the set limit on '
# 'individual room.')
#
# if res.childs > no_of_child_room:
# raise ValidationError('You can not exceed the number of children than the set limit on '
# 'individual room.')
return res
# @api.multi
def _count_total_rooms(self):
for order in self:
count = 0
for line in order.reservation_line:
count += 1
order.update({
'number_of_rooms': count,
})
@api.onchange('pricelist_id')
def onchange_pricelist_id(self):
self.show_update_pricelist = True
if 'checkin' in self._context and 'checkout' in self._context:
room_obj = self.env['product.product']
room_brw = room_obj.search(
[('id', '=', self._context['hotel_resource'])])
pricelist = self.env['sale.shop'].browse(
int(self._context['shop_id'])).pricelist_id.id
if pricelist == False:
raise UserError(
('Please set the Pricelist on the shop %s to proceed further') % room_brw.shop_id.name)
ctx = self._context and self._context.copy() or {}
ctx.update({'date': self._context['checkin']})
from dateutil import parser
day_count1 = parser.isoparse(self._context['checkout']) - parser.isoparse(self._context['checkin'])
day_count2 = day_count1.total_seconds()
_logger.info("DIFF SECONDS===>>>>>>>>>{}".format(day_count2))
day_count2 = day_count2 / 86400
day_count2 = "{:.2f}".format(day_count2)
day_count2 = math.ceil(float(day_count2))
_logger.info("SELF CONTEXT====>>>>>{}".format(self._context['checkin']))
res_line = {
'categ_id': room_brw.categ_id.id,
'room_number': room_brw.id,
'checkin': parser.isoparse(self._context['checkin']),
'checkout': parser.isoparse(self._context['checkout']),
'number_of_days': int(day_count2),
'price': self.env['product.pricelist'].with_context(ctx)._price_get(room_brw, 1)[pricelist]
}
if self.reservation_line:
self.reservation_line.write(res_line)
else:
_logger.info("RES LINE===>>>>>>>>>>>>>>>{}".format(res_line))
self.reservation_line = [[0, 0, res_line]]
if not self.pricelist_id:
return {}
if not self.reservation_line:
return {}
if len(self.reservation_line) != 1:
warning = {
'title': _('Pricelist Warning!'),
'message': _(
'If you change the pricelist of this order (and eventually the currency), prices of existing order lines will not be updated.')
}
return {'warning': warning}
def update_prices(self):
lines_to_update = []
for line in self.reservation_line:
product = line.room_number.with_context(
quantity=line.number_of_days,
date=line.checkin,
pricelist=self.pricelist_id.id,
)
price_unit = self.env['account.tax']._fix_tax_included_price_company(
line._get_display_price(product), line.room_number.taxes_id, line.taxes_id, line.company_id)
if self.pricelist_id.discount_policy == 'without_discount' and price_unit:
discount = max(0, (price_unit - product.price)
* 100 / price_unit)
else:
discount = 0
lines_to_update.append(
(1, line.id, {'price': price_unit, 'discount': discount}))
self.update({'reservation_line': lines_to_update})
self.show_update_pricelist = False
self.message_post(body=_(
"Product prices have been recomputed according to pricelist <b>%s<b> " %self.pricelist_id.display_name))
def _amount_line_tax(self, line):
val = 0.0
taxes = line.taxes_id.compute_all(
line.price * (1 - (line.discount or 0.0) / 100.0), quantity=line.number_of_days)
val = taxes['total_included'] - taxes['total_excluded']
return val
# @api.multi
def _get_subtotal_amount(self):
total = 0.0
if self:
for obj in self:
if obj.id:
for line in obj.reservation_line:
total += line.sub_total1
print('------obj.pricelist_id', obj.pricelist_id)
print('------obj.pricelist_id.currency_id', obj.pricelist_id.currency_id)
obj.update({
'untaxed_amt': obj.pricelist_id.currency_id.round(total),
})
else:
obj.update({
'untaxed_amt': 0,
})
# @api.multi
def _get_total_tax(self):
# get total tax on the room
val1 = 0.0
total1 = 0.0
for obj in self:
for line in obj.reservation_line:
total1 += line.sub_total1
val1 += self._amount_line_tax(line)
if obj.pricelist_id:
obj.update({
'total_tax': obj.pricelist_id.currency_id.round(val1),
})
@api.depends('reservation_line')
def _get_total_rental_cost(self):
# total amount after deduction by tax
for order in self:
order.update({
'total_cost1': 0.0,
})
total1 = val1 = 0.0
cur = order.pricelist_id.currency_id
for line in order.reservation_line:
total1 += line.sub_total1
val1 += self._amount_line_tax(line)
if cur:
sum = cur.round(total1) + cur.round(val1)
order.update({
'total_cost1': sum,
})
# @api.multi
@api.depends('adv_amount')
def _get_advance_cost(self):
total = 0
for obj in self:
total = 0
if obj.adv_amount:
total = obj.adv_amount
obj.update({
'deposit_cost2': total,
})
# @api.multi
def _get_default_shop(self):
user = self.env['res.users'].browse(self._uid)
company_id = user.company_id.id
shop_ids = self.env['sale.shop'].search(
[('company_id', '=', company_id)])
if not shop_ids:
raise UserError(
'There is no default shop for the current user\'s company!')
return shop_ids[0]
@api.onchange('shop_id')
def onchange_shop(self):
if self.shop_id:
shop = self.shop_id
if shop.pricelist_id:
self.pricelist_id = shop.pricelist_id.id
@api.onchange('partner_id')
def onchange_patner(self):
if self.partner_id:
partner = self.partner_id
if partner.property_product_pricelist:
self.pricelist_id = partner.property_product_pricelist.id
print('-------------commits', self.pricelist_id)
# self.env.cr.commit()
name = fields.Char('Event type', default=lambda self: _('New'))
gds_id = fields.Char('GDS ID', readonly=True)
reservation_no = fields.Char(
'Reservation No', readonly=True, index=True)
date_order = fields.Datetime('Date Ordered', required=True, default=datetime.today(), readonly=True)
shop_id = fields.Many2one('sale.shop', 'Hotel', required=True,
domain="[('company_id', '=', [current_company_id])]",
default=_get_default_shop, readonly=True)
partner_id = fields.Many2one(
'res.partner', 'Guest Name', required=True)
pricelist_id = fields.Many2one(
'product.pricelist', 'Pricelist')
# 'checkin': fields.datetime('Expected-Date-Arrival',required=True,readonly=True, states={'draft':[('readonly',False)],'confirm':[('readonly',False)]}),
# 'checkout': fields.datetime('Expected-Date-Departure',required=True, readonly=True, states={'draft':[('readonly',False)],'confirm':[('readonly',False)]}),
adults = fields.Integer('Adults', )
childs = fields.Integer('Children',)
reservation_line = fields.One2many(
'hotel.reservation.line', 'line_id', 'Reservation Line', readonly=False)
state = fields.Selection([('draft', 'Draft'), ('confirm', 'Confirm'), (
'done', 'Done'), ('cancel', 'Cancelled')], 'State', default='draft', readonly=True)
folio_id = fields.Many2many(
'hotel.folio', 'hotel_folio_reservation_rel', 'order_id', 'invoice_id', 'Folio')
folio_state = fields.Selection(
string="Status",
readonly=True, copy=False, index=True,
tracking=3,
related='hotel_folio_id.state')
hotel_folio_id = fields.Many2one('hotel.folio', string = "Hotel Folio", compute = "_compute_folio_state", store=True)
dummy = fields.Datetime('Dummy')
source = fields.Selection([('internal_reservation', 'Internal Reservation'), ('through_web', 'Through Web'), (
'through_gds', 'Through GDS')], 'Source', default='internal_reservation', index=True, readonly=True)
number_of_rooms = fields.Integer(
compute="_count_total_rooms", string="Number Of Rooms")
untaxed_amt = fields.Float(
compute="_get_subtotal_amount", string="Untaxed Amount")
total_tax = fields.Float(string="Reservation Tax",store = True,
compute="_get_total_tax")
deposit_cost1 = fields.Float(string="deposit cost", )
total_cost1 = fields.Float(
string="Total Reservation cost", compute="_get_total_rental_cost", readonly=True)
company_id = fields.Many2one(
'res.company', related='shop_id.company_id', string='Company', store=True)
id_line_ids = fields.One2many('hotel.resv.id.details', 'reservation_id',
'ID Line', readonly=False)
via = fields.Selection([('direct', 'Direct'), ('agent', 'Agent')], "Via",
readonly=True, default='direct')
agent_id = fields.Many2one('res.partner', 'Agent', readonly=True)
invoiced = fields.Boolean('Invoiced', default=False)
adv_amount = fields.Float("Advance Amount")
deposit_recv_acc = fields.Many2one(
'account.account', string="Deposit Account", required=False)
deposit_cost2 = fields.Float(
compute="_get_advance_cost", string="Advance Payment", store=True)
agent_comm = fields.Float("Commision")
currency_id = fields.Many2one('res.currency', 'Currency', required=True, related='company_id.currency_id',
default=lambda self: self.env.user.company_id.currency_id.id)
note = fields.Text(string='Note')
account_move_ids = fields.Many2many('account.move', 'reservation_account_move_rel', 'reservation_id', 'move_id',
"Payment Details")
total_advance = fields.Float(
compute="_get_advance_payment", string="Total Advance Payment", )
remaining_amt = fields.Float(
compute="_get_advance_payment", string="Total Remaining Amount", )
show_update_pricelist = fields.Boolean(string='Has Pricelist Changed')
folio_count = fields.Integer(
compute="_compute_folio", string='Folio Count', copy=False, default=0, readonly=True)
folio_ids = fields.Many2many('hotel.folio', compute="_compute_folio", string='Invoices', copy=False,
readonly=True)
reference = fields.Char('Rederence')
@api.depends('name')
def _compute_folio_state(self):
for record in self:
hotel_folio = self.env['hotel.folio'].sudo().search([('reservation_id', '=', record.id)])
if hotel_folio:
record.hotel_folio_id = hotel_folio.id
else:
record.hotel_folio_id = ''
def _compute_folio(self):
for order in self:
folio = self.env['hotel.folio'].search(
[('reservation_id', '=', order.id)])
order.folio_ids = folio
order.folio_count = len(folio)
def action_view_folio(self):
folio = self.mapped('folio_ids')
action = self.env.ref('hotel.open_hotel_folio1_form_tree').sudo().read()[0]
if len(folio) > 1:
action['domain'] = [('id', 'in', folio.ids)]
elif len(folio) == 1:
form_view = [
(self.env.ref('hotel.view_hotel_folio1_form').id, 'form')]
if 'views' in action:
action['views'] = form_view + \
[(state, view)
for state, view in action['views'] if view != 'form']
else:
action['views'] = form_view
action['res_id'] = folio.id
else:
action = {'type': 'ir.actions.act_window_close'}
return action
# @api.multi
def compute(self):
total = 0
val = 0
for obj in self:
for line in obj.reservation_line:
# line.count_price()
total += line.sub_total1
val += self._amount_line_tax(line)
if self.pricelist_id:
self.total_tax = self.pricelist_id.currency_id.round(val)
self.untaxed_amt = self.pricelist_id.currency_id.round(total)
else:
self.total_tax = val
self.untaxed_amt = total
sum = self.total_tax + self.untaxed_amt
self.total_cost1 = sum
return True
# @api.multi
def onchange_partner_id(self, cr, uid, ids, part):
if not part:
return {'value': {'partner_invoice_id': False, 'partner_shipping_id': False, }}
addr = self.pool.get('res.partner').address_get(
cr, uid, [part], ['delivery', 'invoice', 'contact'])
result = {}
warning = {}
title = False
message = False
partner = self.pool.get('res.partner').browse(cr, uid, part)
if partner.reservation_warn != 'no-message':
if partner.reservation_warn == 'block':
raise UserError(
_('Alert for %s!') % (partner.name), partner.reservation_msg)
title = _("Warning for %s") % partner.name
message = partner.reservation_msg
warning = {
'title': title,
'message': message
}
if result.get('warning', False):
warning['title'] = title and title + ' & ' + \
result['warning']['title'] or result['warning']['title']
warning['message'] = message and message + ' ' + \
result['warning']['message'] or result['warning']['message']
return {'value': {'partner_invoice_id': addr['invoice'], 'partner_shipping_id': addr['delivery'],
'value1': result.get('value', {}), },
'warning': warning}
@api.onchange('adv_amount')
def onchange_adv_amount(self):
if self.adv_amount:
self.deposite = self.adv_amount
# @api.multi
def cancel_reservation(self):
for reservation in self:
if reservation.state in ['draft', 'confirm']:
room_his_id_search = self.env['hotel.room.booking.history'].search(
[('booking_id', '=', reservation.id)])
room_his_id_search.unlink()
self.status = 'cancelled'
self.write({'state': 'cancel'})
def back_to_dashboard(self):
return {
'type': 'ir.actions.act_url',
'url': 'localhost:3000/dashboards',
'target': 'current'
}
# @api.multi
def confirmed_reservation(self):
for reservation in self:
if reservation.source == 'internal_reservation':
if not reservation.reservation_line:
raise UserError(_('Please Select Room'))
if reservation.total_cost1 < reservation.deposit_cost2:
raise ValidationError(
"Advance Amount Should not be greater than Total Reservation Cost.")
if not reservation.reservation_line:
raise ValidationError("Reservation line Details are missing.")
for line in reservation.reservation_line:
room_line_id = self.env['hotel.room'].search(
[('product_id', '=', line.room_number.id)])
###############################################by pornima######
housekeeping_room = self.env['hotel.housekeeping'].search([
('room_no', '=', room_line_id.product_id.id), ('state', '=', 'dirty')])
if housekeeping_room:
for house1 in housekeeping_room:
house_brw = self.env[
'hotel.housekeeping'].browse(house1)
house = house_brw.id
house_current_date = (datetime.strptime(
str(house.current_date), '%Y-%m-%d')).date()
house_end_date = (datetime.strptime(
str(house.end_date), '%Y-%m-%d')).date()
start_reser = datetime.strptime(
str(line.checkin), '%Y-%m-%d %H:%M:%S').date()
end_reser = datetime.strptime(
str(line.checkout), '%Y-%m-%d %H:%M:%S').date()
if (house_current_date <= start_reser <= house_end_date) or (
house_current_date <= end_reser <= house_end_date) or (
(start_reser < house_current_date) and (end_reser > house_end_date)):
raise ValidationError(
"Room %s is not clean for reservation period !" % (room_line_id.name))
#
###############################################
if room_line_id.room_folio_ids:
for history in room_line_id.room_folio_ids:
if history.state == 'done':
history_start_date = history.check_in
history_end_date = history.check_out
reservation_start_date = line.checkin
reservation_end_date = line.checkout
if (history_start_date <= reservation_start_date < history_end_date) or (
history_start_date < reservation_end_date <= history_end_date) or (
(reservation_start_date < history_start_date) and (
reservation_end_date >= history_end_date)):
if not (reservation.id == history.booking_id.id):
raise UserError("Room %s is booked in this reservation period !" % (
room_line_id.name))
for line in reservation.reservation_line:
room_line_id = self.env['hotel.room'].search(
[('product_id', '=', line.room_number.id)])
room_his_id = self.env['hotel.room.booking.history'].create({
'partner_id': reservation.partner_id.id,
'check_in': line.checkin,
'check_out': line.checkout,
'history_id': room_line_id.id,
'product_id': line.room_number.id,
'booking_id': reservation.id,
'state': 'done',
'category_id': room_line_id.categ_id.id,
'name': line.room_number.name,
'check_in_date': line.checkin,
'check_out_date': line.checkout
})
self.status = 'confirmed'
self.write({'state': 'confirm'})
return True
def update_history(self):
for reservation in self:
room_his_id_search = self.env['hotel.room.booking.history'].search(
[('booking_id', '=', reservation.id)])
room_his_id_search.unlink()
if not reservation.reservation_line:
raise ValidationError("Reservation line Details are missing.")
for line in reservation.reservation_line:
room_line_id = self.env['hotel.room'].search(
[('product_id', '=', line.room_number.id)])
###############################################by pornima######
housekeeping_room = self.env['hotel.housekeeping'].search([
('room_no', '=', room_line_id.product_id.id), ('state', '=', 'dirty')])
if housekeeping_room:
for house1 in housekeeping_room:
# house = self.env['hotel.housekeeping'].browse(house1)
house = house1
house_current_date = (datetime.strptime(
str(house.current_date), '%Y-%m-%d')).date()
house_end_date = (datetime.strptime(
str(house.end_date), '%Y-%m-%d')).date()
start_reser = datetime.strptime(
str(line.checkin), '%Y-%m-%d %H:%M:%S').date()
end_reser = datetime.strptime(
str(line.checkout), '%Y-%m-%d %H:%M:%S').date()
if (house_current_date <= start_reser <= house_end_date) or (
house_current_date <= end_reser <= house_end_date) or (
(start_reser < house_current_date) and (end_reser > house_end_date)):
# if (((start_reser < house_current_date) and (end_reser > house_end_date)) or (house_current_date <= start_reser < house_end_date) or (house_current_date < end_reser <= house_end_date)) and (house.state == 'dirty'):
# print "i am in if loop--------------"
raise ValidationError("Room %s is not clean for reservation period !") % (
room_line_id.name)
###############################################
if room_line_id.room_folio_ids:
for history in room_line_id.room_folio_ids:
if history.state == 'done':
history_start_date = history.check_in
history_end_date = history.check_out
reservation_start_date = datetime.strptime(
str(line.checkin), '%Y-%m-%d %H:%M:%S')
reservation_end_date = datetime.strptime(
str(line.checkout), '%Y-%m-%d %H:%M:%S')
if (history_start_date <= reservation_start_date < history_end_date) or (
history_start_date < reservation_end_date <= history_end_date) or (
(reservation_start_date < history_start_date) and (
reservation_end_date > history_end_date)):
# print "Already Reserved......."
if not (reservation.id == history.booking_id.id):
raise UserError("Room %s is booked in this reservation period !" % (
room_line_id.name,))
for line in reservation.reservation_line:
# print reservation,"reservation"
room_line_id = self.env['hotel.room'].search(
[('product_id', '=', line.room_number.id)])
room_his_id = self.env['hotel.room.booking.history'].create({
'partner_id': reservation.partner_id.id,
'check_in': line.checkin,
'check_out': line.checkout,
'history_id': room_line_id.id,
'product_id': line.room_number.id,
'booking_id': reservation.id,
'state': 'done',
'category_id': room_line_id.categ_id.id,
'name': line.room_number.name,
'check_in_date': (line.checkin).date(),
'check_out_date': (line.checkout).date(),
})
return True
def create_folio(self):
for reservation in self:
room_his_id_search = self.env['hotel.room.booking.history'].search(
[('booking_id', '=', reservation.id)])
room_his_id_search.unlink()
if not reservation.reservation_line:
raise ValidationError("Reservation line Details are missing.")
for line in reservation.reservation_line:
room_line_id = self.env['hotel.room'].search(
[('product_id', '=', line.room_number.id)])
###############################################by pornima######
housekeeping_room = self.env['hotel.housekeeping'].search(
[('room_no', '=', room_line_id.product_id.id), ('state', '=', 'dirty')])
# "housekeeping_room--------------------------------------------------------------------",housekeeping_room
if housekeeping_room:
for house1 in housekeeping_room:
house_brw = self.env[
'hotel.housekeeping'].browse(house1)
house = house_brw.id
house_current_date = (
datetime.strptime(str(house.current_date), '%Y-%m-%d')).date()
house_end_date = (
datetime.strptime(str(house.end_date), '%Y-%m-%d')).date()
start_reser = datetime.strptime(
str(line.checkin), '%Y-%m-%d %H:%M:%S').date()
end_reser = datetime.strptime(
str(line.checkout), '%Y-%m-%d %H:%M:%S').date()
if (house_current_date <= start_reser <= house_end_date) or (
house_current_date <= end_reser <= house_end_date) or (
(start_reser < house_current_date) and (end_reser > house_end_date)):
# if (((start_reser < house_current_date) and (end_reser > house_end_date)) or (house_current_date <= start_reser < house_end_date) or (house_current_date < end_reser <= house_end_date)) :
# print "i am in if loop--------------\n\n\n\n\n"
raise ValidationError("Room %s is not clean for reservation period !" % (
room_line_id.name))
###############################################
if room_line_id.room_folio_ids:
for history in room_line_id.room_folio_ids:
if history.state == 'done':
history_start_date = history.check_in
history_end_date = history.check_out
reservation_start_date = line.checkin
reservation_end_date = line.checkout
if (history_start_date <= reservation_start_date < history_end_date) or (
history_start_date < reservation_end_date <= history_end_date) or (
(reservation_start_date < history_start_date) and (
reservation_end_date > history_end_date)):
if not (reservation.id == history.booking_id.id):
raise UserError("Room %s is booked in this reservation period !" % (
room_line_id.name,))
line = reservation.reservation_line
folio = self.env['hotel.folio'].create({
'date_order': reservation.date_order,
'shop_id': reservation.shop_id.id,
'partner_id': reservation.partner_id.id,
'pricelist_id': reservation.pricelist_id.id,
'partner_invoice_id': reservation.partner_id.id,
'partner_shipping_id': reservation.partner_id.id,
# 'checkin_date': line.checkin,
# 'checkout_date': line.checkout,
'reservation_id': reservation.id,
# 'duration': line1.number_of_days,
'note': reservation.note,
# 'service_lines': reservation.other_items_ids,
})
for line in reservation.reservation_line:
room_line_id = self.env['hotel.room'].search(
[('product_id', '=', line.room_number.id)])
room_his_id = self.env['hotel.room.booking.history'].create({
'partner_id': reservation.partner_id.id,
'check_in': line.checkin,
'check_out': line.checkout,
'history_id': room_line_id.id,
'product_id': line.room_number.id,
'booking_id': reservation.id,
'state': 'done',
'category_id': line.room_number.categ_id.id, # room_line_id.categ_id.id,
'name': line.room_number.name,
'check_in_date': line.checkin,
'check_out_date': line.checkout,
})
tax_ids = []
for tax_line in line.taxes_id:
tax_ids.append(tax_line.id)
vals = {
'folio_id': folio.id,
'product_id': line.room_number.id,
'name': line.room_number.name,
'product_uom': line.room_number.uom_id.id,
'price_unit': line.price,
'product_uom_qty': line.number_of_days,
# 'checkin_date': datetime.now(),
'checkin_date': line.checkin,
'checkout_date': line.checkout,
'discount': line.discount,
'tax_id': [(6, 0, tax_ids)],
'categ_id': line.room_number.categ_id.id, # room_line_id.categ_id.id,
'hotel_reservation_line_id': line.id
}
self.env["hotel_folio.line"].create(vals)
# for service_line in reservation.other_items_ids:
# product_id = self.env['product.product'].search(
# [('id', '=', service_line.product_id.id)])
# vals = {
# 'folio_id': folio.id,
# 'product_id': product_id.id,
# 'name': product_id.name,
# 'product_uom': service_line.product_uom.id,
# 'product_uom_qty': service_line.product_uom_qty,
# 'price_unit': service_line.price_unit,
#
# }
# self.env["hotel_service.line"].create(vals)
for rec_id in reservation.id_line_ids:
rec_id.write({'folio_id': folio.id})
for mv in reservation.account_move_ids:
self._cr.execute('insert into sale_account_move_rel(sale_id, move_id) values (%s,%s)',
(folio.id, mv.id))
reservation.reservation_line.write({
'checkin': line.checkin,
})
reservation.status = 'checkin'
reservation.write(
{'state': 'done', 'agent_comm': reservation.total_cost1, })
return True
def done(self):
active_id = self._context.get('active_ids')
for reservation in self:
# print "reservation.deposit_cost2=======================",
# reservation.total_cost1
if reservation.deposit_cost2:
data_obj = self.env['ir.model.data']
data_id = data_obj._get_id(
'hotel_management', 'deposit_journal_entry_wizard1')
# print data_id,"data_id=------------------------"
view_id1 = False
if self._context is None:
self_context = {}
ctx = dict(self._context)
ctx['active_ids'] = [reservation.id]
ctx['booking_id'] = reservation.id
if data_id:
view_id1 = data_obj.browse(data_id).res_id
value = {
'name': _('Advance Payment Entry'),
'view_type': 'form',
'view_mode': 'form',
'res_model': 'deposit_journal_entry.wizard1',
'view_id': False,
'context': ctx,
'views': [(view_id1, 'form')],
'type': 'ir.actions.act_window',
'target': 'new',
'nodestroy': True
}
return value
else:
so = self.create_folio()
return so
def _send_order_confirmation_mail(self):
if self.env.su:
# sending mail in sudo was meant for it being sent from superuser
self = self.with_user(SUPERUSER_ID)
# template_id = self._find_mail_template(force_confirmation_template=True)
# if template_id:
# for order in self:
# order.with_context(force_send=True).message_post_with_template(template_id, composition_mode='comment', email_layout_xmlid="mail.mail_notification_paynow")
class hotel_reservation_line(models.Model):
_name = "hotel.reservation.line"
_description = "Reservation Line"
def write(self, vals):
res = super(hotel_reservation_line, self).write(vals)
for ret in self:
if 'checkin' in vals or 'checkout' in vals:
ret.onchange_date_count_total_days()
return res
@api.model_create_multi
def create(self, vals):
for val in vals:
checkin = val['checkin']
checkout = val['checkout']
if checkout and checkin > checkout:
raise UserError(
'Error! Departure date must be greater than Arrival Date')
so = super(hotel_reservation_line, self).create(val)
return so
@api.onchange('checkin', 'checkout')
# @api.depends('line_id.shop_id')
def onchange_date_count_total_days(self):
shop_id = None
if not self.checkin:
return False
if not self.checkout:
return False
current_date = datetime.today().date()
date_object = (self.checkout, '%Y-%m-%d %H:%M:%S')
if current_date != date_object:
if self.checkin >= self.checkout:
checkout = self.checkin
checkout += timedelta(days=1)
self.checkout = checkout
_logger.info("TYPE==>>>>%s", checkout)
if self.line_id:
shop_id = self.line_id.shop_id.id
_logger.info("SHOP ID===>>>>>>>>>>>>{}".format(shop_id))
if not shop_id:
raise UserError('Shop must be set before selection of room.')
policy_obj = self.env['checkout.configuration'].sudo().search(
[('shop_id', '=', shop_id)])
_logger.info("Policy OBJ===>>>>>>>>>>>>>>>>>>{}".format(policy_obj))
if not policy_obj:
raise UserError('Checkout policy is not define for selected Hotel.')
check_in = self.checkin
check_out = self.checkout
_logger.info("DAY COUNT====>>>>%s", check_in)
_logger.info("DAY COUNT====>>>>%s", check_out)
day_count1 = check_out - check_in
day_count2 = day_count1.total_seconds()
day_count2 = day_count2 / 86400
day_count2 = "{:.2f}".format(day_count2)
_logger.info("DIFFERENCE==>>>>>>>>>{}".format(day_count2))
day_count2 = math.ceil(float(day_count2))
_logger.info("DAY COUNT22===>>>>>>>>>>>>>>>>{}".format(day_count2))
self.number_of_days = day_count2
@api.onchange('room_number', 'checkin', 'checkout')
@api.depends('checkin', 'checkout', 'banquet_id.pricelist_id', 'banquet_id', 'line_id.partner_id', 'number_of_days',
'banquet_id.source')
def onchange_room_id(self):
v = {}
res_list = []
warning = ''
if self.room_number:
product_browse = self.room_number
product_id = product_browse.id
price = product_browse.lst_price
if price is False:
raise ValidationError("Couldn't find a pricelist line matching this product!")
pricelist = self.line_id.pricelist_id.id
ctx = self._context and self._context.copy() or {}
ctx.update({'date': self.checkin})
if pricelist:
price = self.env['product.pricelist'].with_context(ctx)._price_get(
self.room_number, self.number_of_days)[pricelist]
# price = self.env['product.pricelist'].with_context(ctx).price_get(
# self.room_number.id, self.number_of_days, {
# 'uom': product_browse.uom_id.id,
# 'date': self.checkin,
# })[pricelist]
v['price'] = price
tax_ids = []
for tax_line in product_browse.taxes_id:
tax_ids.append(tax_line.id)
v['taxes_id'] = [(6, 0, tax_ids)]
v['checkin'] = self.checkin
v['checkout'] = self.checkout
reservation_start_date = self.checkin
reservation_end_date = self.checkout
check_config = self.env['ir.model'].search([('model', '=', 'hotel.reservation.through.gds.configuration')])
if check_config:
config_id = self.env['hotel.reservation.through.gds.configuration'].search([])
config_browse = config_id
if config_browse and self.line_id.source != 'through_gds':
for record in config_browse:
config_start_date = record.name
config_end_date = record.to_date
config_start_date = datetime.strptime(str(config_start_date), '%Y-%m-%d %H:%M:%S')
config_end_date = datetime.strptime(str(config_end_date), '%Y-%m-%d %H:%M:%S')
if (config_start_date <= reservation_start_date < config_end_date) or (
config_start_date < reservation_end_date <= config_end_date) or (
(reservation_start_date < config_start_date) and (
reservation_end_date > config_end_date)):
for line in record.line_ids:
room_list = []
for room in line.room_number:
room_list.append(room.id)
if self.room_number.id in room_list:
raise UserError("Room is reserved in this period for GDS reservation!")
room_line_id = self.env['hotel.room'].search([('product_id', '=', product_id)])
housekeeping_room = self.env['hotel.housekeeping'].search([('room_no', '=', room_line_id.product_id.id)])
if housekeeping_room:
for house1 in housekeeping_room:
house = house1
house_current_date = house.current_date
house_current_date = datetime.combine(house_current_date, datetime.min.time())
house_current_date = datetime.strptime(str(house_current_date), '%Y-%m-%d %H:%M:%S')
house_end_date = house.end_date
house_end_date = datetime.combine(house_end_date, datetime.min.time())
house_end_date = datetime.strptime(str(house_end_date), '%Y-%m-%d %H:%M:%S')
start_reser = self.checkin
end_reser = self.checkout
if (((start_reser < house_current_date) and (end_reser > house_end_date)) or (
house_current_date <= start_reser < house_end_date) or (
house_current_date < end_reser <= house_end_date)) and (house.state == 'dirty'):
raise UserError("Warning! Room %s is not clean for reservation period !" % (room_line_id.name))
if room_line_id.room_folio_ids:
for history in room_line_id.room_folio_ids:
if history.state == 'done':
history_start_date = history.check_in
history_end_date = history.check_out
room_line_id = self.env['hotel.room'].search([('product_id', '=', product_id)])
housekeeping_room = self.env['hotel.housekeeping'].search([
('room_no', '=', room_line_id.product_id.id), ('state', '=', 'dirty')])
if housekeeping_room:
for house1 in housekeeping_room:
house = house1
house_current_date = (datetime.strptime(str(house.current_date), '%Y-%m-%d')).date()
house_end_date = (datetime.strptime(str(house.end_date), '%Y-%m-%d')).date()
start_reser = datetime.strptime(str(self.checkin), '%Y-%m-%d %H:%M:%S').date()
end_reser = datetime.strptime(str(self.checkout), '%Y-%m-%d %H:%M:%S').date()
if (house_current_date <= start_reser <= house_end_date) or (
house_current_date <= end_reser <= house_end_date) or (
(start_reser < house_current_date) and (end_reser > house_end_date)):
raise UserError("Room %s is not clean for reservation period !" % (
room_line_id.name))
if (history_start_date <= reservation_start_date < history_end_date) or (
history_start_date < reservation_end_date <= history_end_date) or (
(reservation_start_date < history_start_date) and (
reservation_end_date > history_end_date)):
if not (self.line_id.id == history.booking_id.id):
raise UserError("Room %s is booked in this reservation period !" % (room_line_id.name))
return {'value': v, 'warning': warning}
@api.depends('number_of_days', 'discount', 'price', 'taxes_id')
def count_sub_total1(self):
for line in self:
tax_amount = 0
price = line.price * (1 - (line.discount or 0.0) / 100.0)
taxes = line.taxes_id.compute_all(price, line.line_id.currency_id, line.number_of_days,
product=line.room_number,
partner=line.line_id.partner_id)
for tax in taxes['taxes']:
tax_amount = tax_amount + tax['amount']
line.update({
'sub_total1': taxes['total_excluded'],
})
currency_id = fields.Many2one(
related='line_id.currency_id', store=True, string='Currency', readonly=True)
line_id = fields.Many2one('hotel.reservation')
room_number = fields.Many2one('product.product', 'Room Number',
domain="[('isroom','=',True),('categ_id','=',categ_id)]",
help="Will list out all the rooms that belong to selected shop.", required=True)
categ_id = fields.Many2one('product.category', 'Room Type', required=True, )
price = fields.Float("Price")
discount = fields.Float('Discount (%)', digits=(16, 2))
number_of_days = fields.Integer(string="Number Of Days", default=1)
sub_total1 = fields.Float(
string='Sub Total', store=True, readonly=True, compute='count_sub_total1', compute_sudo=False)
taxes_id = fields.Many2many('account.tax', 'reservation_taxes_rel', 'prod_id', 'tax_id', 'Taxes', domain=[
('type_tax_use', 'in', ['sale', 'all'])])
checkin = fields.Datetime('Checkin Date', required=True, default=lambda self: fields.Datetime.now())
checkout = fields.Datetime('Checkout Date', required=True, )
company_id = fields.Many2one(related='line_id.company_id', comodel_name='res.company', string='Company', store=True)
@api.model
def default_get(self, default_fields):
# _logger.info("USER===>>>>>>>>>>>{}".format(self.env.user))
_logger.info("\n\n\n\nSELF CONTEXT===>>>>>>>>>>>>>{}".format(self._context))
if self.env.user.id == 4:
user_id = self.env['res.users'].search([('id', '=', 2)])
else:
user_id = self.env.user
# _logger.info("TZ===>>>>>>>>>>>>>>>{}".format(user_id.tz))
tz = pytz.timezone(user_id.tz)
time_difference = tz.utcoffset(utc_time).total_seconds()
# _logger.info("TIME DIFFERENCE===>>>>>>>>>>>>>>>>>>{}".format(time_difference))
vals = super(hotel_reservation_line, self).default_get(default_fields)
# _logger.info("VALS===>>>>>>>>>>>>>>>>{}".format(self.room_number))
tax_ids = []
if self.room_number:
for tax_line in self.room_number.taxes_id:
tax_ids.append(tax_line.id)
_logger.info("TAXES ID===>>>>>>>>>>>>>>{}".format(tax_ids))
if self._context.get('shop_id'):
sale_shop_id = self.env['sale.shop'].search([('id', '=', self._context.get('shop_id'))])
_logger.info("SALE SHOP===>>>>>{}".format(sale_shop_id))
checkout_policy_id = self.env['checkout.configuration'].search(
[('shop_id', '=', self._context.get('shop_id'))])
if len(checkout_policy_id) > 1:
raise ValidationError('It looks like you have setup multiple checkout policy for one shop.\nPlease check the configuration.')
# _logger.info("Checkout Policy===>>>{}".format(checkout_policy_id))
if checkout_policy_id.name == 'custom':
time = int(checkout_policy_id.time)
if vals.get('checkin'):
checkin = vals.get('checkin')
checkin = datetime(checkin.year, checkin.month, checkin.day)
checkout_date = checkin + timedelta(days=1)
checkout = checkout_date + timedelta(hours=00, minutes=00, seconds=00)
to_string = fields.Datetime.to_string(checkout)
# _logger.info("TO STRING====>>>>{}".format(to_string))
from_string = fields.Datetime.from_string(to_string)
# _logger.info("FROM STRING====>>>>{}".format(from_string))
checkout = from_string
checkout = checkout + timedelta(hours=time)
checkout = checkout - timedelta(seconds=time_difference)
# _logger.info("\n\n\n\n\nVALS=====>>>>>>>>>>>>>>>>>>{}".format(checkout))
vals.update({'checkout': checkout})
elif self._context.get('checkin'):
checkin = self._context.get('checkin')
check_in_from_string = fields.Datetime.from_string(self._context.get('checkin'))
checkin = datetime(check_in_from_string.year, check_in_from_string.month, check_in_from_string.day)
checkin = checkin + timedelta(hours=int(time))
checkout = self._context.get('checkout')
checkout_from_string = fields.Datetime.from_string(self._context.get('checkout'))
checkout = datetime(checkout_from_string.year, checkout_from_string.month, checkout_from_string.day)
checkout = checkout + timedelta(hours=int(time))
checkout = checkout - timedelta(seconds=time_difference)
checkin = checkin - timedelta(seconds=time_difference)
vals.update({'checkout': checkout, 'checkin': checkin})
else:
if vals.get('checkin'):
checkin = vals.get('checkin')
checkout_date = checkin + timedelta(days=1)
checkout = checkout_date
_logger.info("CHECKOUT ====>>>>>>>>>>>{}".format(checkout_date))
vals.update({'checkout': checkout, })
if tax_ids:
vals.update({'taxes_id': [(6, 0, tax_ids)]})
_logger.info("\n\n\n\n\n\n\n\nVals====>>>>>>>>>>>>>>>>>>>>{}".format(vals))
return vals
def _get_display_price(self, product):
# TO DO: move me in master/saas-16 on sale.order
# awa: don't know if it's still the case since we need the "product_no_variant_attribute_value_ids" field now
# to be able to compute the full price
# it is possible that a no_variant attribute is still in a variant if
# the type of the attribute has been changed after creation.
# no_variant_attributes_price_extra = [
# ptav.price_extra for ptav in self.product_no_variant_attribute_value_ids.filtered(
# lambda ptav:
# ptav.price_extra and
# ptav not in product.product_template_attribute_value_ids
# )
# ]
# if no_variant_attributes_price_extra:
# product = product.with_context(
# no_variant_attributes_price_extra=tuple(
# no_variant_attributes_price_extra)
# )
if self.line_id.pricelist_id.discount_policy == 'with_discount':
return product.with_context(pricelist=self.line_id.pricelist_id.id).price
product_context = dict(self.env.context, partner_id=self.line_id.partner_id.id,
date=self.line_id.date_order)
final_price, rule_id = self.line_id.pricelist_id.with_context(product_context).get_product_price_rule(
product or self.product_id, self.product_uom_qty or 1.0, self.line_id.partner_id)
base_price, currency = self.with_context(product_context)._get_real_price_currency(
product, rule_id, self.product_uom_qty, self.line_id.pricelist_id.id)
if currency != self.line_id.pricelist_id.currency_id:
base_price = currency._convert(
base_price, self.line_id.pricelist_id.currency_id,
self.line_id.company_id or self.env.company, self.line_id.date_order or fields.Date.today())
# negative discounts (= surcharge) are included in the display price
return max(base_price, final_price)
class hotel_room(models.Model):
_inherit = "hotel.room"
_description = "room Inherit "
room_folio_ids = fields.One2many(
"hotel.room.booking.history", "history_id", "Room Rental History", copy=False)
@api.onchange('shop_id')
def on_change_shop_id(self):
if not self.shop_id:
return {'value': {}}
temp = self.shop_id
self.company_id = temp.company_id.id
class hotel_room_booking_history(models.Model):
_name = "hotel.room.booking.history"
_description = "Hotel Room Booking History"
product_id = fields.Integer("Product ID", readonly=True)
history_id = fields.Many2one("hotel.room", "Room No", readonly=True)
name = fields.Char('Product Name', readonly=True, required=True)
category_id = fields.Many2one(
"product.category", "room category", readonly=True)
check_in = fields.Datetime('CheckIn Date', readonly=True)
check_out = fields.Datetime('CheckOut Date', readonly=True)
check_in_date = fields.Date('Check In Date', readonly=True)
check_out_date = fields.Date('Check Out Date', readonly=True)
partner_id = fields.Many2one('res.partner', "Partner Name", readonly=True)
booking_id = fields.Many2one(
'hotel.reservation', "Booking Ref", readonly=True)
state = fields.Selection([('draft', 'Draft'), ('confirm', 'Confirm'),
('cancle', 'Cancel'), ('done', 'Done')], 'State', readonly=True)
company_id = fields.Many2one(
'res.company', string='Company', default=lambda self: self.env.user.company_id)
class hotel_food_line(models.Model):
_name = 'hotel_food.line'
_description = 'hotel Food line'
_inherits = {'sale.order.line': 'food_line_id'}
food_line_id = fields.Many2one(
'sale.order.line', 'food_line_id', required=True, ondelete='cascade')
folio_id = fields.Many2one('hotel.folio', 'folio_id', ondelete='cascade')
source_origin = fields.Char('Source Origin')
@api.model_create_multi
def create(self, vals_list):
_logger.info("VALS====>>>>>>>{}".format(vals_list))
for rec in vals_list:
folio = self.env["hotel.folio"].browse([rec['folio_id']])
# if "product_id" in vals.keys():
# self.env["product.product"].browse(
# vals['product_id']).write({'state': 'sellable'})
rec.update({'order_id': folio.order_id.id})
res = super(hotel_food_line, self).create(vals_list)
return res
@api.onchange('product_id')
def product_id_change(self):
if self.product_id:
self.product_uom = self.product_id.uom_id
self.price_unit = self.product_id.lst_price
self.name = self.product_id.description_sale
class hotel_folio(models.Model):
_inherit = "hotel.folio"
_description = "Hotel Folio"
state = fields.Selection(
selection=[
('draft', "Quotation"),
('sent', "Quotation Sent"),
('sale', "Sales Order"),
('progress', "Progress"),
('check_out', 'Check Out'),
('done', "Locked"),
('cancel', "Cancelled"),
],
string="Status",
readonly=True, copy=False, index=True,
tracking=3,
default='draft')
def unlink(self):
for rec in self:
if rec.state not in ['sale', 'done']:
res = super(hotel_folio, rec).unlink()
else:
raise UserError("Folio Cannot be Deleted once it is Confirm")
return res
@api.depends('amount_total', )
def _get_advance_payment(self):
sum = 0.00
remaining = 0.00
for obj in self:
obj.update({
'total_advance': 0.0,
'remaining_amt': 0.0,
})
sum = 0
for line in obj.account_move_ids:
move_lines = self.env['account.move.line'].search(
[('move_id', '=', line.id)])
if move_lines:
for mv in move_lines:
sum = sum + mv.debit
obj.update({
'total_advance': sum,
'remaining_amt': obj.amount_total - sum
})
total_advance = fields.Float(
compute="_get_advance_payment", string="Total Advance Payment", )
remaining_amt = fields.Float(
compute="_get_advance_payment", string="Total Remaining Amount", )
account_move_ids = fields.Many2many('account.move', 'sale_account_move_rel', 'sale_id', 'move_id',
"Payment Details")
is_agent_commission_created = fields.Boolean('Is Agent Commission Created')
def _rooms_reference(self):
for order in self:
order_ref = ''
for line in order.room_lines:
if line.product_id:
order_ref += line.product_id.name + ','
if order_ref and order_ref[-1] == ',':
order.update({
'rooms_ref': order_ref[:-1],
'rooms_ref1': order_ref[:-1],
})
else:
order.update({
'rooms_ref': order_ref,
'rooms_ref1': order_ref,
})
transport_line_ids = fields.One2many(
'hotel_folio_transport.line', 'folio_id')
laundry_line_ids = fields.One2many(
'hotel_folio_laundry.line', 'folio_id', 'Folio Ref')
reservation_id = fields.Many2one('hotel.reservation', 'Reservation Ref')
laundry_invoice_ids = fields.Many2many(
'account.move', 'laundry_folio_invoice_rel', 'folio_id', 'invoice_id', 'Laundry Related Invoices',
readonly=True)
transport_invoice_ids = fields.Many2many(
'account.move', 'transport_folio_invoice_rel', 'folio_id', 'invoice_id', 'Transport Related Invoices',
readonly=True)
id_line_ids = fields.One2many(
'hotel.resv.id.details', 'folio_id', 'ID Line')
food_lines = fields.One2many('hotel_food.line', 'folio_id')
rooms_ref = fields.Char(compute="_rooms_reference", string="Room No", compute_sudo=False)
rooms_ref1 = fields.Char(compute="_rooms_reference", compute_sudo=False,
string="Room Number")
def advance_payment(self):
reservation = self
res_id = reservation.reservation_id
data_obj = self.env['ir.model.data'].sudo().search([('name', '=', 'advance_payment_wizard1')])
data_id = data_obj.id
view_id1 = False
if self._context is None:
self._context = {}
ctx = dict(self._context)
ctx['active_ids'] = [reservation.id]
ctx['reservation_id'] = res_id.id
if data_id:
view_id1 = data_obj.browse(data_id).res_id
value = {
'name': _('Deposit amount entry'),
'view_type': 'form',
'view_mode': 'form',
'res_model': 'advance.payment.wizard',
'view_id': False,
'context': ctx,
'views': [(view_id1, 'form')],
'type': 'ir.actions.act_window',
'target': 'new',
'nodestroy': True
}
return value
# @api.multi
def action_checkout(self):
folio = self.browse(self._ids)[0]
for room in folio.room_lines:
sdate = room.checkout_date
housekeeping_id = self.env['hotel.housekeeping'].create({
'current_date': sdate,
'end_date': (sdate + timedelta(1)).date(),
'clean_type': 'checkout',
'room_no': room.product_id.id,
'inspector': self._uid,
'inspect_date_time': sdate + timedelta(1),
'state': 'dirty',
'quality': 'clean',
})
self.reservation_id.status = 'checkout'
self.write({'state': 'check_out'})
return True
# @api.multi
def action_done(self):
for line in self:
# for invoice in line.invoice_ids:
# if (invoice.partner_id.id == line.partner_id.id) and invoice.payment_state not in ['paid',
# 'in_payment']:
# raise UserError('Invoice is not paid !')
for invoice in line.transfer_invoice_ids:
if invoice.payment_state != 'paid':
raise UserError('Transfer Invoice is not paid !')
self.write({'state': 'done'})
return True
# @api.multi
def action_cancel(self):
today = time.strftime('%Y-%m-%d %H:%M:%S')
today = datetime.strptime(str(today), '%Y-%m-%d %H:%M:%S')
for obj in self:
for room_id in obj.room_lines:
if room_id.checkin_date <= today:
if obj.order_reserve_invoice_ids:
raise UserError(
'Error ! Invoice has been created, so You can not delete this record!')
if obj.table_order_invoice_ids:
raise UserError(
'Error ! Invoice has been created, so You can not delete this record!')
if obj.invoice_ids:
raise UserError(
'Error ! Invoice has been created, so You can not delete this record!')
if obj.picking_ids:
raise UserError(
'Error !', 'Invoice has been created, so You can not delete this record!')
so = super(hotel_folio, self).action_cancel()
for room in obj.room_lines:
room_line_id = self.env['hotel.room'].search(
[('product_id', '=', room.product_id.id)])
history_obj = self.env['hotel.room.booking.history'].search([
('history_id', '=', room_line_id.id), ('booking_id', '=', obj.reservation_id.id)])
if history_obj:
history_browse = history_obj
history_browse.unlink()
return so
# @api.multi
def action_wait(self, cr, uid, ids, context=None):
for obj in self.browse(cr, uid, ids, context):
if (not obj.invoice_ids):
self.write(cr, uid, [obj.id], {'state': 'manual'})
else:
self.write(cr, uid, [obj.id], {'state': 'progress'})
today = time.strftime('%Y-%m-%d')
if obj.reservation_id.id:
self.pool.get('hotel.reservation').compute(
cr, uid, [obj.reservation_id.id])
for room in obj.room_lines:
room_line_id = self.pool.get('hotel.room').search(
cr, uid, [('product_id', '=', room.product_id.id)])
room_line_browse = self.pool.get(
'hotel.room').browse(cr, uid, room_line_id)
history_obj = self.pool.get('hotel.room.booking.history').search(cr, uid, [
('history_id', '=', room_line_browse[0].id), ('booking_id', '=', obj.reservation_id.id)])
if history_obj:
history_browse = self.pool.get(
'hotel.room.booking.history').browse(cr, uid, history_obj)
self.pool.get('hotel.room.booking.history').write(cr, uid, history_browse[0].id, {
'check_in': room.checkin_date, 'check_out': room.checkout_date,
'check_in_date': room.checkin_date[0:10],
'check_out_date': room.checkout_date[0:10]})
return {}
# @api.multi
def print_relatedinvoice(self, cr, uid, ids, context=None):
'''
This function prints the sales order and mark it as sent, so that we can see more easily the next step of the workflow
'''
id_list = []
assert len(
ids) == 1, 'This option should only be used for a single id at a time'
for obj in self.browse(cr, uid, ids, context={}):
if obj.invoice_ids:
for invoice_id in obj.invoice_ids:
id_list.append(invoice_id.id)
if obj.laundry_invoice_ids:
for invoice_id in obj.laundry_invoice_ids:
id_list.append(invoice_id.id)
if obj.transport_invoice_ids:
for invoice_id in obj.transport_invoice_ids:
id_list.append(invoice_id.id)
if obj.order_reserve_invoice_ids:
for invoice_id in obj.order_reserve_invoice_ids:
id_list.append(invoice_id.id)
if obj.table_order_invoice_ids:
for invoice_id in obj.table_order_invoice_ids:
id_list.append(invoice_id.id)
datas = {
'model': 'account.move',
'ids': id_list,
'form': self.pool.get('account.move').read(cr, uid, id_list, context=context),
}
return {'type': 'ir.actions.report.xml', 'report_name': 'account.move', 'datas': datas, 'nodestroy': True}
# @api.multi
def update_folio_history(self):
tax_ids = []
folio = self
if not folio.room_lines:
raise ValidationError("Rooms line Details are missing.")
book_search = self.env['hotel.room.booking.history'].search(
[('booking_id', '=', folio.reservation_id.id)])
if book_search:
# self.env['hotel.room.booking.history'].unlink(book_search)
book_search.unlink()
if folio.reservation_id.reservation_line:
# print
# "folio.reservation_id.reservation_line=======================================",folio.reservation_id.reservation_line
for res_line in folio.reservation_id.reservation_line:
res_line.unlink()
for folio_line in folio.room_lines:
#
for tax_line in folio_line.tax_id:
tax_ids.append(tax_line.id)
res_line_id = self.env['hotel.reservation.line'].create({
'checkin': folio_line.checkin_date,
'checkout': folio_line.checkout_date,
'categ_id': folio_line.categ_id.id,
'room_number': folio_line.product_id.id,
'line_id': folio.reservation_id.id,
'shop_id': folio.shop_id.id,
'price': folio_line.price_unit,
'discount': folio_line.discount,
'taxes_id': [(6, 0, tax_ids)],
'number_of_days': folio_line.product_uom_qty,
})
tax_ids = []
room_line_id = self.env['hotel.room'].search(
[('product_id', '=', folio_line.product_id.id)])
room_his_id = self.env['hotel.room.booking.history'].create({
'partner_id': folio.partner_id.id,
'check_in': folio_line.checkin_date,
'check_out': folio_line.checkout_date,
'history_id': room_line_id.id,
'product_id': folio_line.product_id.id,
'booking_id': folio.reservation_id.id,
'state': 'done',
'category_id': folio_line.categ_id.id,
'name': folio_line.product_id.name,
'check_in_date': str(folio_line.checkin_date)[0:10],
'check_out_date': str(folio_line.checkout_date)[0:10],
})
return True
def write(self, vals):
res = super(hotel_folio, self).write(vals)
if 'state' in vals and vals['state'] == 'sale':
if self.room_lines:
for rec in self.room_lines:
rec.on_change_checkout()
return res
class hotel_folio_line(models.Model):
_inherit = 'hotel_folio.line'
_description = 'hotel folio1 room line'
_s = {'sale.order.line': 'order_line_id'}
hotel_reservation_line_id = fields.Many2one(
'hotel.reservation.line', 'hotel reservation line id=')
state = fields.Selection(
selection=[
('draft', "Quotation"),
('sent', "Quotation Sent"),
('sale', "Sales Order"),
('progress', "Progress"),
('check_out', 'Check Out'),
('done', "Locked"),
('cancel', "Cancelled"),
],
string="Status",
readonly=True, copy=False, index=True,
tracking=3,
default='draft')
@api.model_create_multi
def create(self, vals):
for val in vals:
checkin = val['checkin_date']
checkout = val['checkout_date']
if checkout and checkin > checkout:
raise UserError(
'Error! Departure date must be greater than Arrival Date')
return super(hotel_folio_line, self).create(val)
@api.onchange('product_id', 'checkin_date', 'checkout_date')
@api.depends('folio_id.pricelist_id', 'checkin_date', 'checkout_date', 'folio_id.partner_id', 'product_uom_qty',
'parent_id')
def onchange_product_id(self):
if self.checkout_date and self.checkin_date > self.checkout_date:
return {'warning': {'title': "Error", 'message': "Departure date must be greater than Arrival Date"}, }
v = {}
warning = ''
if not self.folio_id.pricelist_id:
raise ValidationError("PriceList is not Selected !")
# if not (self.checkin_date and self.checkout_date):
# raise UserError(
# "Please Select Expected-Date-Arrival and Expected-Date-Departure before selecting room number!")
date = str(self.checkin_date)[0:10]
if self.product_id:
product_browse = self.product_id
price = product_browse.lst_price
if price is False:
raise ValidationError(
"Couldn't find a pricelist line matching this product!2")
v['price'] = price
tax_ids = []
for tax_line in product_browse.taxes_id:
tax_ids.append(tax_line.id)
v['taxes_id'] = [(6, 0, tax_ids)]
v['checkin'] = self.checkin_date
v['checkout'] = self.checkout_date
room_line_id = self.env['hotel.room'].search(
[('product_id', '=', self.product_id.id)])
#############################Added by Pornima######################
housekeeping_room = self.env['hotel.housekeeping'].search([
('room_no', '=', room_line_id.product_id.id), ('state', '=', 'dirty')])
# print
# "housekeeping_room--------------------------------------------------------------------",housekeeping_room
if housekeeping_room:
for house1 in housekeeping_room:
house = house1
house_current_date = (datetime.strptime(
str(house.current_date), '%Y-%m-%d')).date()
house_end_date = (datetime.strptime(
str(house.end_date), '%Y-%m-%d')).date()
start_reser = datetime.strptime(
str(self.checkin_date), '%Y-%m-%d %H:%M:%S').date()
end_reser = datetime.strptime(
str(self.checkout_date), '%Y-%m-%d %H:%M:%S').date()
if (house_current_date <= start_reser <= house_end_date) or (
house_current_date <= end_reser <= house_end_date) or (
(start_reser < house_current_date) and (end_reser > house_end_date)):
raise UserError("Room %s is not clean for reservation period !" % (
room_line_id.name))
###################################################################
if room_line_id.room_folio_ids:
for history in room_line_id.room_folio_ids:
if history.state == 'done' and history.booking_id.id != self.folio_id.reservation_id.id:
history_start_date = history.check_in
history_end_date = history.check_out
reservation_start_date = self.checkin_date
reservation_end_date = self.checkout_date
if (history_start_date <= reservation_start_date < history_end_date) or (
history_start_date < reservation_end_date <= history_end_date) or (
(reservation_start_date < history_start_date) and (
reservation_end_date > history_end_date)):
# self.folio_id, history.booking_id.id)
if not (self.folio_id.id == history.booking_id.id):
raise UserError(
"Room %s is booked in this reservation period !" % (room_line_id.name,))
v['product_uom'] = product_browse.uom_id.id
v['name'] = product_browse.name
v['price_unit'] = product_browse.list_price
return {'value': v}
def unlink(self):
booking_history_obj = self.env['hotel.room.booking.history']
for categ in self:
room_id = self.env['hotel.room'].search(
[('product_id', '=', categ.product_id.id)])
reservation_line = categ.hotel_reservation_line_id
booking_history_id = booking_history_obj.search([('booking_id', '=', reservation_line.line_id.id),
('hostory_id', '=', room_id.id)])
booking_history_id.unlink()
reservation_line.unlink()
categ.order_line_id.unlink()
return super(hotel_folio_line, self).unlink()
def write(self, vals):
room_book_history_obj = self.env['hotel.room.booking.history']
for folio_line in self:
room_id = self.env['hotel.room'].search(
[('product_id', '=', folio_line.product_id.id)])
booking_history_rec = room_book_history_obj.search(
[('booking_id', '=', folio_line.folio_id.reservation_id.id),
('history_id', '=', room_id.id)])
history_vals = {
'partner_id': folio_line.folio_id.reservation_id.partner_id.id,
'check_in': folio_line.checkin_date,
'check_out': folio_line.checkout_date,
'product_id': folio_line.product_id.id,
'booking_id': folio_line.folio_id.reservation_id.id,
'state': 'done',
'check_in_date': folio_line.checkin_date,
'check_out_date': folio_line.checkout_date,
}
history_vals.update({'history_id': room_id.id,
'category_id': room_id.categ_id.id, # room_line_id.categ_id.id,
'name': room_id.name, })
if not booking_history_rec:
room_book_history_obj.create(history_vals)
else:
booking_history_rec.write(history_vals)
return super(hotel_folio_line, self).write(vals)
class hotel_service_line(models.Model):
_inherit = 'hotel_service.line'
_description = 'hotel Service line'
_s = {'sale.order.line': 'service_line_id'}
@api.onchange('product_id')
def onchange_product_id(self):
v = {}
if self.product_id:
date = time.strftime('%Y-%m-%d')
self.product_uom = self.product_id.uom_id.id
self.name = self.product_id.name if not self.product_id.description_sale else self.product_id.description_sale
_logger.info('------------- {} {}'.format(self.name, self.product_id.name))
tax_ids = []
for tax_line in self.product_id.taxes_id:
tax_ids.append(tax_line.id)
self.tax_id = [(6, 0, tax_ids)]
self.product_uom_qty = 1
self.price_unit = self.product_id.lst_price
# return {'value': v}
class hotel_restaurant_tables(models.Model):
_inherit = "hotel.restaurant.tables"
_description = "Includes Hotel Restaurant Table"
name = fields.Char('Table number', required=True)
capacity = fields.Integer('Capacity')
shop_id = fields.Many2one('sale.shop', 'Hotel',domain="[('company_id', '=', [current_company_id])]",
help="Will show list of shop that belongs to allowed companies of logged-in user. \n -Assigning shop name to which this table no belongs to.")
avl_state = fields.Selection([('available', 'Available'), ('book', 'Booked')], 'Availability Status',
default='available', index=True, required=True)
state = fields.Selection(selection_add=[('draft', 'Draft'), ('edit', 'Edit'), ('confirmed', 'Confirmed'), (
'canceled', 'Cancel')], string='State', required=True, readonly=True,
ondelete={'draft': 'set default', 'edit': 'set default', 'confirmed': 'set default',
'canceled': 'set default'})
company_id = fields.Many2one(
'res.company', related='shop_id.company_id', string='Company', store=True)
def confirm(self):
self.write({'state': 'confirmed'})
return True
def cancel_supplier(self):
self.write({'state': 'cancel'})
return True
def update_record(self):
self.write({'state': 'edit'})
return True
class hotel_restaurant_order(models.Model):
_inherit = "hotel.restaurant.order"
_description = "Includes Hotel Restaurant Order"
def domain_change(self):
new_ids = []
room_lines = self.env['hotel.folio'].search([('state', '=', 'draft')]).mapped('room_lines')
for rec in room_lines:
if rec.product_id:
room_id = self.env['hotel.room'].search([('product_id', '=', rec.product_id.id)])
if room_id:
new_ids.append(room_id.id)
return [('id', 'in', new_ids)]
@api.depends('order_list', 'order_list.tax_id', 'order_list.item_rate', 'order_list.item_qty')
def _amount_tax(self):
# print " In amount :::::: Tax"
val = 0.00
for line in self.order_list:
taxes = line.tax_id.compute_all(
line.item_rate, None, int(line.item_qty))
val += taxes['total_included'] - taxes['total_excluded']
if self.pricelist_id:
self.amount_tax = self.pricelist_id.currency_id.round(val)
else:
self.amount_tax = val
@api.depends('order_list')
def _sub_total(self):
# print "Sub Total :::::: Tax"
val = 0.00
for line in self.order_list:
val += line.price_subtotal
# print "SubTotal ::::::", val
if self.pricelist_id:
self.amount_subtotal = self.pricelist_id.currency_id.round(val)
else:
self.amount_subtotal = val
def _amount_untaxed(self):
for line in self:
total = sum(order.price_subtotal for order in line.order_list)
# total += sum(fee.price_subtotal for fee in line.fees_lines)
line.amount_untaxed = line.pricelist_id.currency_id.round(total)
def _total(self):
val = val1 = 0.0
for line in self.order_list:
taxes = line.tax_id.compute_all(
line.item_rate, None, int(line.item_qty))
val1 += line.price_subtotal
# print "SubTotal -------", val1
val += taxes['total_included'] - taxes['total_excluded']
# print "Tax ------", val
if self.pricelist_id:
self.amount_tax = self.pricelist_id.currency_id.round(val)
self.amount_untaxed = self.pricelist_id.currency_id.round(val1)
else:
self.amount_tax = val
self.amount_untaxed = val1
# print "subtotal ------ ", self.amount_untaxed
self.amount_total = self.amount_untaxed + self.amount_tax
def _get_default_shop(self):
company_id = self.env['res.users'].browse(self.env.uid).company_id.id
shop_ids = self.env['sale.shop'].search(
[('company_id', '=', company_id)]).ids
if not shop_ids:
raise UserError(
'There is no default shop for the current user\'s company!')
return shop_ids[0]
@api.onchange('shop_id')
def onchange_shop_id(self):
v = {}
if self.shop_id:
shop = self.env['sale.shop'].browse(self.shop_id.id)
if shop.pricelist_id:
v['pricelist_id'] = shop.pricelist_id.id
v['company_id'] = shop.company_id.id
return {'value': v}
waiter_name1 = fields.Many2one('res.users', 'Waiter User Name')
partner_id = fields.Many2one('res.partner', 'Customer', required=True,
help="Will show customer name corresponding to selected room no.")
room_no = fields.Many2one(
'hotel.room', 'Room No', domain=domain_change,help="Will show list of currently occupied room no that belongs to selected shop.")
pricelist_id = fields.Many2one(
'product.pricelist', 'Pricelist',
domain="[('company_id', '=', [current_company_id])]",
required=True, readonly=True)
shop_id = fields.Many2one('sale.shop', 'Hotel', default=_get_default_shop, required=True, readonly=True,
help="Will show list of shop that belongs to allowed companies of logged-in user.")
company_id = fields.Many2one(
'res.company', related='shop_id.company_id', string='Company', store=True)
state = fields.Selection(selection_add=[('draft', 'Draft'), ('confirm', 'Confirmed'), ('order', 'Order Done'), (
'done', 'Done'), ('cancel', 'Cancelled')], string='State', index=True, required=True, readonly=True)
flag = fields.Boolean("Flag", default=False)
amount_subtotal = fields.Float(
compute="_sub_total", string='SubTotal', compute_sudo=False)
amount_tax = fields.Float(compute="_amount_tax", string='Tax')
amount_total = fields.Float(compute="_total", string='Total')
amount_untaxed = fields.Float(
'Untaxed Amount', compute='_amount_untaxed', store=True)
def confirm_order(self):
for obj in self:
for line in obj.table_no:
line.write({'avl_state': 'book'})
self.write({'state': 'confirm'})
return True
# @api.multi
@api.onchange('pricelist_id')
def onchange_pricelist_id(self):
if not self.pricelist_id:
return {}
if not self.order_list or self.order_list == [(6, 0, [])]:
return {}
if len(self.order_list) != 1:
warning = {
'title': _('Pricelist Warning!'),
'message': _(
'If you change the pricelist of this order (and eventually the currency), prices of existing order lines will not be updated.')
}
return {'warning': warning}
@api.onchange('o_date')
def onchange_odate(self):
new_ids = []
# Old Logic
# main_obj_ids = self.env['hotel.room.booking.history'].search([
# ('check_in', '<=', self.o_date), ('check_out', '>=', self.o_date), ('state', '=', 'done')])
# for dest_line in main_obj_ids:
# new_ids.append(dest_line.history_id.id)
# New Logic
room_lines = self.env['hotel.folio'].search([('state', '=', 'draft')]).mapped('room_lines')
for rec in room_lines:
if rec.product_id:
room_id = self.env['hotel.room'].search([('product_id', '=', rec.product_id.id)])
if room_id:
new_ids.append(room_id.id)
return {
'domain': {
'room_no': [('id', 'in', new_ids)],
}}
@api.depends('o_date')
@api.onchange('room_no')
def onchange_room_no(self):
res = {}
booking_id = 0
# history_obj = self.env["hotel.room.booking.history"]
if not self.room_no:
return {'value': {'partner_id': False}}
# for folio_hsry_id in history_obj.search([('history_id', '=', self.room_no.id), ('state', '=', 'done')]):
# hstry_line_id = folio_hsry_id
# start_dt = hstry_line_id.check_in
# end_dt = hstry_line_id.check_out
# if (start_dt <= self.o_date) and (end_dt >= self.o_date):
# booking_id = hstry_line_id.booking_id.id
# folio_obj_id = self.env["hotel.folio"].search(
# [('reservation_id', '=', booking_id)])
# if not folio_obj_id:
# raise UserError(
# 'Please create folio for selected room first.')
# res['folio_id'] = folio_obj_id[0].id
# res['partner_id'] = hstry_line_id.partner_id.id
# new logic updated on 13-June-2022
room_lines = self.env['hotel.folio'].search([('state', '=', 'draft')]).mapped('room_lines')
for rec in room_lines:
if rec.product_id.id == self.room_no.product_id.id:
folio_id = rec.folio_id
if folio_id:
res['folio_id'] = folio_id.id
res['partner_id'] = folio_id.partner_id.id
break
return {'value': res}
# @api.multi
class hotel_restaurant_reservation(models.Model):
_inherit = "hotel.restaurant.reservation"
_description = "Includes Hotel Restaurant Reservation"
def _get_default_shop(self):
company_id = self.env['res.users'].browse(self.env.uid).company_id.id
shop_ids = self.env['sale.shop'].search(
[('company_id', '=', company_id)]).ids
if not shop_ids:
raise UserError(
'There is no default shop for the current user\'s company!')
return shop_ids[0]
@api.onchange('shop_id')
def onchange_shop_id(self):
v = {}
if self.shop_id:
shop = self.env['sale.shop'].browse(self.shop_id.id)
if shop.pricelist_id:
v['pricelist_id'] = shop.pricelist_id.id
return {'value': v}
cname = fields.Many2one('res.partner', 'Customer Name', required=True,
help="Will show customer name corresponding to selected room no.")
room_no = fields.Many2one('hotel.room', 'Room No',
help="Will show list of currently occupied room no that belongs to selected shop.")
pricelist_id = fields.Many2one(
'product.pricelist', 'Pricelist', required=True)
shop_id = fields.Many2one('sale.shop', 'Hotel', default=_get_default_shop, required=True,
help="Will show list of shop that belongs to allowed companies of logged-in user.")
company_id = fields.Many2one(
'res.company', related='shop_id.company_id', string='Company', store=True)
@api.onchange('pricelist_id')
def onchange_pricelist_id(self):
if not self.pricelist_id:
return {}
if not self.order_list_ids or self.order_list_ids == [(6, 0, [])]:
return {}
if len(self.order_list_ids) != 1:
warning = {
'title': _('Pricelist Warning!'),
'message': _(
'If you change the pricelist of this order (and eventually the currency), prices of existing order lines will not be updated.')
}
return {'warning': warning}
@api.onchange('start_date', 'end_date')
def onchange_date(self):
new_ids = []
main_obj_ids = self.env['hotel.room.booking.history'].search(
[('check_in', '<=', self.start_date), ('check_out', '>=', self.end_date), ('state', '!=', 'cancel')])
for dest_line in main_obj_ids:
new_ids.append(dest_line.history_id.id)
return {
'domain': {
'room_no': [('id', 'in', new_ids)],
}}
@api.onchange('room_no', 'start_date', 'end_date')
def onchange_room_no(self):
res = {}
booking_id = 0
history_obj = self.env["hotel.room.booking.history"]
folio_obj = self.env["hotel.folio"]
if not self.room_no:
return {'value': {'partner_id': False}}
for folio_hsry_id in history_obj.search([('history_id', '=', self.room_no.id), ('state', '=', 'done')]):
history_start_date = folio_hsry_id.check_in
history_end_date = folio_hsry_id.check_out
if (history_start_date <= self.start_date < history_end_date) or (
history_start_date < self.end_date <= history_end_date) or (
(self.start_date < history_start_date) and (self.end_date >= history_end_date)):
booking_id = folio_hsry_id.booking_id.id
folio_obj_id = folio_obj.search(
[('reservation_id', '=', booking_id)])
res['folio_id'] = folio_obj_id
res['cname'] = folio_obj_id.partner_id.id
return {'value': res}
def create_order(self):
for i in self:
table_ids = [x.id for x in i.tableno]
order_list_ids = [x.id for x in i.order_list_ids]
kot_data = self.env['hotel.reservation.order'].create({
'reservation_id': i.id,
'date1': i.start_date,
'partner_id': i.cname.id,
'room_no': i.room_no.id,
'folio_id': i.folio_id.id,
'table_no': [(6, 0, table_ids)],
# 'order_list_ids': [(6, 0, order_list_ids)],
'pricelist_id': i.pricelist_id.id,
'shop_id': i.shop_id.id,
})
for line in i.order_list_ids:
line.write({'o_l': kot_data.id})
kot_browse = self.env[
'hotel.reservation.order'].browse(kot_data.id)
self.write({'state': 'order'})
return True
def table_reserved(self):
for reservation in self:
self.write({'state': 'confirm'})
return True
class hotel_reservation_order(models.Model):
_inherit = "hotel.reservation.order"
_description = "Includes Hotel Reservation order"
def _sub_total(self):
# print "In reservation order Sub_total"
val = 0.00
for line in self.order_list:
val += line.price_subtotal
# print "SubTotal ::::::", val
self.amount_subtotal = self.pricelist_id.currency_id.round(val)
# print " Subtotal", self.amount_subtotal
def _amount_tax(self):
val = 0.00
for line in self.order_list:
taxes = line.tax_id.compute_all(
line.item_rate, None, int(line.item_qty), line.product_id.product_id, False)
val += taxes['total_included'] - taxes['total_excluded']
self.amount_tax = self.pricelist_id.currency_id.round(val)
def _amount_untaxed(self):
for line in self:
total = sum(order.price_subtotal for order in line.order_list)
# total += sum(fee.price_subtotal for fee in line.fees_lines)
line.amount_untaxed = line.pricelist_id.currency_id.round(total)
def _total(self):
val = val1 = 0.0
for line in self.order_list:
taxes = line.tax_id.compute_all(
line.item_rate, None, int(line.item_qty))
val1 += line.price_subtotal
# print "SubTotal -------", val1
val += taxes['total_included'] - taxes['total_excluded']
# print "Tax ------", val
self.amount_tax = self.pricelist_id.currency_id.round(val)
# print "amount Tax ------ ", self.amount_tax
self.amount_untaxed = self.pricelist_id.currency_id.round(val1)
# print "subtotal ------ ", self.amount_untaxed
self.amount_total = self.amount_untaxed + self.amount_tax
# print "Total ------ ", self.amount_subtotal
def _get_default_shop(self):
company_id = self.env['res.users'].browse(self.env.uid).company_id.id
shop_ids = self.env['sale.shop'].search(
[('company_id', '=', company_id)]).ids
if not shop_ids:
raise UserError(
'There is no default shop for the current user\'s company!')
return shop_ids[0]
@api.onchange('shop_id')
def onchange_shop_id(self):
v = {}
if self.shop_id:
shop = self.env['sale.shop'].browse(self.shop_id.id)
if shop.pricelist_id:
v['pricelist_id'] = shop.pricelist_id.id
return {'value': v}
waitername1 = fields.Many2one('res.users', 'Waiter User Name')
pricelist_id = fields.Many2one(
'product.pricelist', 'Pricelist', required=True)
shop_id = fields.Many2one('sale.shop', 'Hotel', required=True, default=_get_default_shop)
company_id = fields.Many2one(
'res.company', related='shop_id.company_id', string='Company', store=True)
flag1 = fields.Boolean("Flag", default=False)
amount_subtotal = fields.Float(compute="_sub_total", string='Subtotal')
amount_tax = fields.Float(compute="_amount_tax", string='Tax')
amount_total = fields.Float(compute="_total", string='Total')
amount_untaxed = fields.Float(
'Untaxed Amount', compute='_amount_untaxed', store=True)
@api.onchange('pricelist_id')
def onchange_pricelist_id(self):
if not self.pricelist_id:
return {}
if not self.order_list or self.order_list == [(6, 0, [])]:
return {}
if len(self.order_list) != 1:
warning = {
'title': _('Pricelist Warning!'),
'message': _(
'If you change the pricelist of this order (and eventually the currency), prices of existing order lines will not be updated.')
}
return {'warning': warning}
def confirm_order(self):
for obj in self:
for line in obj.table_no:
self.env['hotel.restaurant.tables'].write(
{'avl_state': 'book'})
self.write({'state': 'confirm'})
return True
def create_invoice(self):
for obj in self:
for line in obj.table_no:
self.env['hotel.restaurant.tables'].write(
{'avl_state': 'available'})
acc_id = obj.partner_id.property_account_receivable_id.id
journal_ids = self.env['account.journal'].search(
[('type', '=', 'sale')], limit=1)
journal_id = None
if journal_ids:
journal_id = journal_ids.id
# added this id for pricing calculation for different pricelists
type = 'out_invoice'
if not obj.room_no:
inv = {
'name': obj.order_number,
'invoice_origin': obj.order_number,
'move_type': type,
'ref': "Order Invoice",
# 'account_id': acc_id,
'partner_id': obj.partner_id.id,
'currency_id': obj.pricelist_id.currency_id.id,
'journal_id': journal_id,
# 'amount_tax': obj.amount_tax,
# 'amount_untaxed': (obj.amount_total - obj.amount_tax),
# 'amount_total': obj.amount_total,
}
inv_id = self.env['account.move'].create(inv)
todo = []
for ol in obj.order_list:
todo.append(ol.id)
if ol.product_id.categ_id:
a = ol.product_id.categ_id.property_account_income_categ_id.id
if not a:
raise ValidationError(_('Error !'), _(
'There is no expense account defined for this product: "%s" (id:%d)') % (
ol.product_id.name, ol.product_id.id,))
else:
a = self.env['ir.property'].get(
'property_account_income_categ', 'product.category').id
tax_ids = []
for tax_line in ol.tax_id:
tax_ids.append(tax_line.id)
inv_id.write({
'invoice_line_ids': [(0, 0, {
'name': ol.product_id.name,
'move_id': inv_id.id,
'account_id': a,
'price_unit': ol.item_rate,
'quantity': float(ol.item_qty),
'product_id': ol.product_id.product_id.id,
# 'uos_id': False,
# 'origin': obj.order_number,
# 'move_id': inv_id.id,
# 'pay_date':obj.date1,
# 'order_amt': ol.price_subtotal,
'tax_ids': [(6, 0, tax_ids)],
})]
})
# self.env['account.move.line'].create(il)
self.write({'state': 'done'})
self.mapped('table_no').write({'avl_state': 'available'})
if self.folio_id:
for r in self.order_list:
tax_ids = []
for tax_line in r.tax_id:
tax_ids.append(tax_line.id)
so_line = {
'name': r.product_id.name,
'product_uom_qty': r.item_qty,
'product_id': r.product_id.product_id.id,
'price_unit': r.item_rate,
'product_uom': r.product_id.product_id.uom_id.id,
'order_id': self.folio_id.order_id.id,
'tax_id': [(6, 0, tax_ids)],
}
so_line_id = self.env['sale.order.line'].create(so_line)
service_line = {
'folio_id': self.folio_id.id,
'food_line_id': so_line_id.id,
'source_origin': obj.order_number,
}
service_line_id = self.env[
'hotel_food.line'].create(service_line)
return True
# @api.multi
def reservation_generate_kot(self):
kot_flag = True
bot_flag = True
kot_data = False
bot_data = False
for order in self:
table_ids = [x.id for x in order.table_no]
for order_line in order.order_list:
product_id = order_line.product_id
product_nature = product_id.product_nature
if product_nature == 'kot' and kot_flag:
order_reservation_data = {
'resno': order.order_number,
'room_no': order.room_no.name,
'kot_date': order.date1,
'w_name': order.waitername1.name,
'shop_id': order.shop_id.id,
'tableno': [(6, 0, table_ids)],
'product_nature': product_id.product_nature,
'pricelist_id': order.pricelist_id.id,
}
kot_flag = False
if product_nature == 'kot' and order_line.states == True:
current_qty = int(
order_line.item_qty) - order_line.previous_qty
if current_qty > 0:
kot_data_reserve = self.env['hotel.restaurant.kitchen.order.tickets'].create(
order_reservation_data)
o_line = {
'product_id': order_line.product_id.id,
'name': order_line.product_id.name,
'item_qty': current_qty,
'item_rate': order_line.item_rate,
'kot_order_list': kot_data_reserve,
'product_nature': product_id.product_nature,
}
self.env['hotel.restaurant.order.list'].create(o_line)
self.env['hotel.restaurant.order.list'].write(
{'previous_qty': order_line.item_qty})
if product_nature == 'kot' and order_line.states == False:
kot_data = self.env['hotel.restaurant.kitchen.order.tickets'].create(
order_reservation_data)
total_qty = int(order_line.item_qty) + \
order_line.previous_qty
o_line = {
'product_id': order_line.product_id.id,
'name': order_line.product_id.id,
'item_qty': order_line.item_qty,
'item_rate': order_line.item_rate,
'kot_order_list': kot_data.id,
'product_nature': product_id.product_nature,
# 'total_qty': total_qty,
}
self.env['hotel.restaurant.order.list'].create(o_line)
self.env['hotel.restaurant.order.list'].write(
{'states': 'True', 'previous_qty': order_line.item_qty})
if product_nature == 'bot' and bot_flag:
order_reservation_data_bot = {
'resno': order.order_number,
'room_no': order.room_no.name,
'kot_date': order.date1,
'w_name': order.waitername1.name,
'shop_id': order.shop_id.id,
'tableno': [(6, 0, table_ids)],
'product_nature': product_id.product_nature,
'pricelist_id': order.pricelist_id.id,
}
bot_flag = False
if product_nature == 'bot' and order_line.states == True:
current_qty = int(order_line.item_qty) - \
order_line.previous_qty
if current_qty > 0:
bot_data = self.env['hotel.restaurant.kitchen.order.tickets'].create(
order_reservation_data_bot)
o_line = {
'product_id': order_line.product_id.id,
'name': order_line.product_id.name,
'item_qty': current_qty,
'item_rate': order_line.item_rate,
'kot_order_list': bot_data.id,
'product_nature': product_id.product_nature,
}
self.env['hotel.restaurant.order.list'].create(o_line)
self.env['hotel.restaurant.order.list'].write(
{'states': 'True', 'previous_qty': order_line.item_qty})
if product_nature == 'bot' and order_line.states == False:
current_qty = int(order_line.item_qty) - \
order_line.previous_qty
if current_qty > 0:
bot_data = self.env['hotel.restaurant.kitchen.order.tickets'].create(
order_reservation_data_bot)
o_line = {
'product_id': order_line.product_id.id,
'name': order_line.product_id.id,
'item_qty': order_line.item_qty,
'item_rate': order_line.item_rate,
'kot_order_list': bot_data.id,
'product_nature': product_id.product_nature,
}
self.env['hotel.restaurant.order.list'].create(o_line)
self.env['hotel.restaurant.order.list'].write(
{'states': 'True', 'previous_qty': order_line.item_qty})
stock_brw = self.env['stock.picking'].search(
[('origin', '=', order.order_number)])
if stock_brw:
for order_items in order.order_list:
order_list = self.env['hotel.restaurant.order.list'].search([(
'product_id', '=', order_items.product_id.id),
('kot_order_list.resno', '=', order.order_number)])
total_qty1 = 0
for order_qty in order_list:
p_qty1 = order_qty.item_qty
total_qty1 = total_qty1 + int(p_qty1)
product_id = self.env['hotel.menucard'].browse(
order_items.product_id.id).product_id.id
if product_id:
move_id = self.env['stock.move'].search(
[('product_id', '=', product_id), ('picking_id', '=', stock_brw.id)])
if move_id:
self.env['stock.move'].write(
{'product_uom_qty': total_qty1, })
self.write({'state': 'order'})
return True
class res_partner(models.Model):
_inherit = 'res.partner'
_description = 'Partner'
agent = fields.Boolean('Agent')
commission = fields.Float('Commission Percentage')
login_password = fields.Char('Login Password')
reservation_warn = fields.Selection([
('no-message', 'No Message'),
('warning', 'Warning'),
('block', 'Blocking Message')
], 'Hotel Reservation', default='no-message', required=True)
reservation_msg = fields.Text('Message for Hotel Reservation')
@api.model_create_multi
def create(self, vals):
if ('agent' in vals) and (vals['agent']):
if not ('commission' in vals):
raise ValidationError("Commission Percentage is not define.")
if ('commission' in vals) and not vals['commission']:
raise ValidationError("Commission Percentage is not define.")
return super(res_partner, self).create(vals)
# def write(self, vals):
# """
# Overriding the write method
# """
# if ('agent' in vals) and (vals['agent']):
# if not ('commission' in vals):
# raise UserError("Commission Percentage is not define.")
# return super(res_partner, self).sudo().write(vals)
class hotel_restaurant_order_list(models.Model):
_inherit = "hotel.restaurant.order.list"
_description = "Inherits Hotel Restaurant Order"
# @api.one
@api.depends("item_qty", "item_rate")
def _sub_total(self):
cur = False
for line in self:
price = line.item_rate
taxes = line.tax_id.compute_all(
price, None, int(line.item_qty), line.product_id.product_id, False)
# print "Taxessssssssss", taxes
if line.o_list:
cur = line.o_list.pricelist_id.currency_id
# print cur, "---o_list"
if line.order_l:
cur = line.order_l.pricelist_id.currency_id
# print cur, "---order_l"
if line.o_l:
cur = line.o_l.pricelist_id.currency_id
# print cur, "---o_l"
if line.kot_order_list:
cur = line.kot_order_list.pricelist_id.currency_id
# print cur, "---kot_order_list"
if cur:
line.price_subtotal += cur.round(taxes['total_excluded'])
else:
line.price_subtotal += taxes['total_excluded']
product_id = fields.Many2one('hotel.menucard', 'Item Name')
product_qty = fields.Integer('quantity')
states = fields.Boolean('States', default=False)
previous_qty = fields.Integer('quantities')
total = fields.Integer('total')
tax_id = fields.Many2many(
'account.tax', 'restaurant_order_tax', 'order_line_id', 'tax_id', 'Taxes', )
price_subtotal = fields.Float(
compute="_sub_total", string='Subtotal')
@api.depends('order_l.pricelist_id', 'order_l.start_date', 'o_l.pricelist_id', 'o_l.date1', 'o_list.pricelist_id',
'o_list.o_date', 'product_id', 'item_qty')
@api.onchange('product_id')
def on_change_item_name(self):
# if not self.order_l.pricelist_id:
# raise UserError("Heloooo PriceList is not Selected !")
if not self.product_id:
return {'value': {}}
temp = self.product_id
taxx_id = self.product_id.taxes_id
tax_id = self.env['account.fiscal.position'].map_tax(
self.product_id.taxes_id)
price_value = 0
if self.o_l:
if not self.o_l.pricelist_id:
raise ValidationError("Orders PriceList is not Selected!")
if self.o_l.date1:
ol_date = self.o_l.date1
else:
ol_date = time.strftime('%Y-%m-%d')
elif self.o_list:
if not self.o_list.pricelist_id:
raise ValidationError("Table Order PriceList is not Selected !")
if self.o_list.o_date:
olist_date = self.o_list.o_date
else:
olist_date = time.strftime('%Y-%m-%d')
elif self.order_l:
if not self.order_l.pricelist_id:
raise ValidationError("Table Booking PriceList is not Selected !")
if self.order_l.start_date:
orderl_date = self.order_l.start_date
else:
orderl_date = time.strftime('%Y-%m-%d')
if self.item_qty:
if self.o_l:
price_value = self.o_l.pricelist_id._price_get(
temp.product_id.id, self.item_qty, uom=temp.uom_id.id, date=ol_date)[self.o_l.pricelist_id.id]
elif self.o_list:
price_value = self.o_list.pricelist_id._price_get(
temp.product_id.id, self.item_qty, uom=temp.uom_id.id,date=olist_date)[self.o_list.pricelist_id.id]
elif self.order_l:
price_value = self.order_l.pricelist_id._price_get(
temp.product_id.id, self.item_qty, uom=temp.uom_id.id, date=orderl_date)[self.order_l.pricelist_id.id]
# else:
# if price_value is False:
# raise UserError(
# "Couldn't find a pricelist line matching this product!")
else:
if self.o_l:
price_value = self.o_l.pricelist_id._price_get(temp.product_id, self.item_qty)[self.o_l.pricelist_id.id]
elif self.o_list:
price_value = self.o_list.pricelist_id._price_get(
temp.product_id, self.item_qty)[self.o_list.pricelist_id.id]
elif self.order_l:
price_value = self.order_l.pricelist_id._price_get(
temp.product_id,
temp.uom_id.id,
)[self.order_l.pricelist_id.id]
self.item_rate = price_value
self.tax_id = tax_id
class product_template(models.Model):
_inherit = "product.template"
@tools.ormcache()
def _get_default_category_id(self):
# Deletion forbidden (at least through unlink)
return self.env.ref('product.product_category_all')
shop_id = fields.Many2one('sale.shop', string='Hotel',domain="[('company_id', 'in', [current_company_id])]",
help="Will show list of shop that belongs to allowed companies of logged-in user. \n -Assigning a shop will make product exclusive for selected shop.")
product_nature = fields.Selection(
[('kot', 'KOT'), ('bot', 'BOT')], 'Product Nature')
company_id = fields.Many2one('res.company', string='Company'
, domain="[('id', 'in', [current_company_id])]")
categ_id = fields.Many2one(
'product.category', 'Product Category',
domain="[('company_id', 'in', [current_company_id])]",
change_default=True, default=_get_default_category_id, group_expand='_read_group_categ_id',
required=True, help="Select category for the current product")
@api.onchange('shop_id')
def on_change_shop_id(self):
if not self.shop_id:
return {'value': {}}
temp = self.shop_id
self.company_id = temp.company_id.id
@api.model
def _construct_tax_string(self, price):
user_id = self.env['res.users'].search([('id', '=', self._context.get('uid'))])
if self.currency_id:
currency = self.currency_id
elif user_id.currency_id:
currency = user_id.company_id.currency_id
res = self.taxes_id.compute_all(price, product=self, partner=self.env['res.partner'])
joined = []
included = res['total_included']
if currency.compare_amounts(included, price):
joined.append(_('%s Incl. Taxes', format_amount(self.env, included, currency)))
excluded = res['total_excluded']
if currency.compare_amounts(excluded, price):
joined.append(_('%s Excl. Taxes', format_amount(self.env, excluded, currency)))
if joined:
tax_string = f"(= {', '.join(joined)})"
else:
tax_string = " "
return tax_string
class hotel_restaurant_kitchen_order_tickets(models.Model):
_inherit = "hotel.restaurant.kitchen.order.tickets"
_description = "Includes Hotel Restaurant Order"
@api.model_create_multi
def create(self, vals):
for rec in vals:
product_nature = rec['product_nature']
if product_nature != 'kot':
rec['ordernobot'] = self.env['ir.sequence'].next_by_code(
'hotel.reservation.botorder')
return super(hotel_restaurant_kitchen_order_tickets, self).create(vals)
ordernobot = fields.Char('BOT Number', readonly=True)
product_nature = fields.Selection(
[('kot', 'KOT'), ('bot', 'BOT')], 'Product Nature')
shop_id = fields.Many2one('sale.shop', 'Hotel', required=True)
pricelist_id = fields.Many2one('product.pricelist', 'Pricelist', )
company_id = fields.Many2one(
'res.company', related='shop_id.company_id', string='Company', store=True)
class hotel_menucard(models.Model):
_inherit = "hotel.menucard"
_description = "Hotel menucard Inherit "
# company_id = fields.Many2one('res.company', related='shop_id.company_id', string='Company', default=lambda *a: False)
company_id = fields.Many2one(
'res.company', string='Company', default=lambda *a: False)
product_nature = fields.Selection(
[('kot', 'KOT'), ('bot', 'BOT')], 'Product Nature', default='kot')
@api.onchange('shop_id')
def on_change_shop_id(self):
if not self.shop_id:
return {'value': {}}
temp = self.shop_id
self.company_id = temp.company_id.id
@api.onchange('shop_id')
def on_change_shop_id(self):
if self.shop_id:
temp = self.shop_id
self.company_id = temp.company_id.id
else:
self.company_id = False
class database_configuration(models.Model):
_name = 'database.configuration'
_description = 'Database Configuration'
name = fields.Char('Database Name', required=True)
company_name = fields.Char('Company Name', required=True)
user_name = fields.Char('User Name', required=True)
password = fields.Char('Password', required=True)
class hotel_resv_id_details(models.Model):
_name = 'hotel.resv.id.details'
_description = 'Clients ID details during reservation'
name = fields.Char('ID Card Number')
client_id = fields.Many2one("id.master", "Document Type")
partner_name = fields.Char('Guest Name')
issuing_auth = fields.Char('Issuing Authority')
gender = fields.Selection(
[('M', 'Male'), ('F', 'Female')], 'Gender')
country_id = fields.Many2one("res.country", "Country")
date_birth = fields.Date('Date of Birth')
valid_from = fields.Date('Valid From')
valid_to = fields.Date('Valid To')
reservation_id = fields.Many2one('hotel.reservation', 'Reservation Id')
folio_id = fields.Many2one('hotel.folio', 'Folio Id')
# class for dashboard URL
class dashboard_url(models.Model):
_name = "dashboard.url"
_description = 'dashboard url'
url = fields.Char("Dashboard URL")
@api.model_create_multi
def create(self, vals):
ids = self.env['dashboard.url'].search(self._ids, [])
if ids:
# self.env['dashboard.url'].unlink(self._ids)
ids.unlink()
return super(dashboard_url, self).create(vals)
class account_invoice(models.Model):
_name = "account.move"
_inherit = "account.move"
_description = 'Invoice'
exchange_rate = fields.Float('Exchange Rate', digits=(12, 6), )
create_date = fields.Datetime('Creation Date', )
@api.onchange('currency_id')
@api.depends('journal_id')
def onchange_currency_id(self):
# on change of the journal, we need to set also the default value for
# payment_rate and payment_rate_currency_id
res = {}
if self._context is None:
self._context = {}
currency_obj = self.env['res.currency']
if not self.journal_id:
raise ValidationError('Journal is not selected.')
journal = self.env['account.journal'].browse(self.journal_id.id)
# company_id = journal.company_id.id
exchange_rate = 1.0
payment_rate_currency_id = self.currency_id
company_currency_id = journal.company_id.currency_id.id
ctx = self._context and self._context.copy() or {}
ctx.update({'date': str(time.strftime('%Y-%m-%d'))})
if payment_rate_currency_id and payment_rate_currency_id.id != company_currency_id:
tmp = currency_obj.browse(payment_rate_currency_id).rate
exchange_rate = tmp / currency_obj.browse(company_currency_id).rate
res['exchange_rate'] = exchange_rate
res['currency_id'] = payment_rate_currency_id.id
return {'value': res}
class hotel_folio_transport_line(models.Model):
_name = 'hotel_folio_transport.line'
_description = 'hotel folio transport line'
_inherits = {'sale.order.line': 'transport_line_id'}
transport_line_id = fields.Many2one(
'sale.order.line', 'food_line_id', required=True, ondelete='cascade')
folio_id = fields.Many2one('hotel.folio', 'Folio ref', ondelete='cascade')
source_origin = fields.Char('Source Origin')
@api.onchange('product_id')
def product_id_change(self):
if self.product_id:
self.product_uom = self.product_id.uom_id
self.price_unit = self.product_id.lst_price
self.name = self.product_id.description_sale
class hotel_folio_laundry_line(models.Model):
_name = 'hotel_folio_laundry.line'
_description = 'hotel folio laundry line'
_inherits = {'sale.order.line': 'laundry_line_id'}
laundry_line_id = fields.Many2one(
'sale.order.line', 'laundry ref', required=True, ondelete='cascade')
folio_id = fields.Many2one('hotel.folio', 'Folio ref', ondelete='cascade')
source_origin = fields.Char('Source Origin')
@api.onchange('product_id')
def product_id_change(self):
if self.product_id:
self.product_uom = self.product_id.uom_id
self.price_unit = self.product_id.lst_price
self.name = self.product_id.description_sale
# class StockChangeStandardPrice(models.TransientModel):
# _inherit = "stock.change.standard.price"
# _description = "Change Standard Price"
#
# def change_price(self):
# """ Changes the Standard Price of Product and creates an account move accordingly. """
# self.ensure_one()
# if self._context['active_model'] == 'product.template':
# products = self.env['product.template'].browse(self._context['active_id']).product_variant_ids
# elif self._context['active_model'] == 'product.product':
# products = self.env['product.product'].browse(self._context['active_id'])
#
# elif self._context['active_model'] == 'hotel.room':
# products = self.env['hotel.room'].browse(self._context['active_id']).product_variant_ids
#
# elif self._context['active_model'] == 'hotel.menucard':
# products = self.env['hotel.menucard'].browse(self._context['active_id']).product_variant_ids
#
# elif self._context['active_model'] == 'hotel.services':
# products = self.env['hotel.services'].browse(self._context['active_id']).product_variant_ids
#
# else:
# pass
#
# products._change_standard_price(self.new_price, counterpart_account_id=self.counterpart_account_id.id)
# return {'type': 'ir.actions.act_window_close'}