[WIP][11.0] hotel channel connector

This commit is contained in:
QS5ELkMu
2018-09-21 02:29:57 +02:00
parent b1e76e4417
commit 1c6afa7f3a
5 changed files with 135 additions and 115 deletions

View File

@@ -1,9 +1,8 @@
# Copyright 2018 Alexandre Díaz <dev@redneboa.es> # Copyright 2018 Alexandre Díaz <dev@redneboa.es>
# License AGPL-3.0 or later (http://www.gnu.org/licenses/agpl). # License AGPL-3.0 or later (http://www.gnu.org/licenses/agpl).
import xmlrpclib import xmlrpc.client
from odoo import _ import logging
from odoo.exceptions import ValidationError
from odoo.addons.component.core import AbstractComponent from odoo.addons.component.core import AbstractComponent
from odoo.addons.queue_job.exception import RetryableJobError from odoo.addons.queue_job.exception import RetryableJobError
from odoo.tools import ( from odoo.tools import (
@@ -11,7 +10,9 @@ from odoo.tools import (
DEFAULT_SERVER_DATETIME_FORMAT) DEFAULT_SERVER_DATETIME_FORMAT)
from odoo.addons.payment.models.payment_acquirer import _partner_split_name from odoo.addons.payment.models.payment_acquirer import _partner_split_name
from odoo.addons.hotel import date_utils from odoo.addons.hotel import date_utils
from odoo import fields from odoo.addons.hotel_channel_connector.components.core import ChannelConnectorError
from odoo import fields, _
_logger = logging.getLogger(__name__)
# GLOBAL VARS # GLOBAL VARS
DEFAULT_WUBOOK_DATE_FORMAT = "%d/%m/%Y" DEFAULT_WUBOOK_DATE_FORMAT = "%d/%m/%Y"
@@ -63,9 +64,11 @@ class WuBookServer(object):
@property @property
def server(self): def server(self):
if self._server is None and self._login_data.is_valid(): if not self._login_data.is_valid():
raise ChannelConnectorError("Invalid Channel Parameters!")
if self._server is None:
try: try:
self._server = xmlrpclib.Server(self._login_data.address) self._server = xmlrpc.client.ServerProxy(self._login_data.address)
res, tok = self._server.acquire_token( res, tok = self._server.acquire_token(
self._login_data.user, self._login_data.user,
self._login_data.passwd, self._login_data.passwd,
@@ -183,7 +186,7 @@ class HotelChannelInterfaceAdapter(AbstractComponent):
channel_server = getattr(self.work, 'channel_api') channel_server = getattr(self.work, 'channel_api')
except AttributeError: except AttributeError:
raise AttributeError( raise AttributeError(
'You must provide a hotel_channel_server attribute with a ' 'You must provide a channel_api attribute with a '
'WuBookServer instance to be able to use the ' 'WuBookServer instance to be able to use the '
'Backend Adapter.' 'Backend Adapter.'
) )
@@ -192,14 +195,14 @@ class HotelChannelInterfaceAdapter(AbstractComponent):
@property @property
def _session_info(self): def _session_info(self):
try: try:
channel_server = getattr(self.work, 'hotel_channel_server') channel_server = getattr(self.work, 'channel_api')
except AttributeError: except AttributeError:
raise AttributeError( raise AttributeError(
'You must provide a hotel_channel_server attribute with a ' 'You must provide a channel_api attribute with a '
'WuBookServer instance to be able to use the ' 'WuBookServer instance to be able to use the '
'Backend Adapter.' 'Backend Adapter.'
) )
return (channel_server.session_token, channel_server.lcode) return (channel_server.session_token, channel_server._login_data.lcode)
class WuBookAdapter(AbstractComponent): class WuBookAdapter(AbstractComponent):
_name = 'wubook.adapter' _name = 'wubook.adapter'
@@ -220,7 +223,7 @@ class WuBookAdapter(AbstractComponent):
# rtype=('name' in vals and vals['name'] and 3) or 1 # rtype=('name' in vals and vals['name'] and 3) or 1
) )
if rcode != 0: if rcode != 0:
raise ValidationError(_("Can't create room in WuBook"), { raise ChannelConnectorError("Can't create room in WuBook", {
'message': results, 'message': results,
}) })
return results return results
@@ -239,7 +242,7 @@ class WuBookAdapter(AbstractComponent):
# rtype=('name' in vals and vals['name'] and 3) or 1 # rtype=('name' in vals and vals['name'] and 3) or 1
) )
if rcode != 0: if rcode != 0:
raise ValidationError(_("Can't modify room in WuBook"), { raise ChannelConnectorError("Can't modify room in WuBook", {
'message': results, 'message': results,
'channel_id': channel_room_id, 'channel_id': channel_room_id,
}) })
@@ -251,7 +254,7 @@ class WuBookAdapter(AbstractComponent):
self._session_info[1], self._session_info[1],
channel_room_id) channel_room_id)
if rcode != 0: if rcode != 0:
raise ValidationError(_("Can't delete room in WuBook"), { raise ChannelConnectorError("Can't delete room in WuBook", {
'message': results, 'message': results,
'channel_id': channel_room_id, 'channel_id': channel_room_id,
}) })
@@ -263,7 +266,7 @@ class WuBookAdapter(AbstractComponent):
self._session_info[1], self._session_info[1],
channel_room_id) channel_room_id)
if rcode != 0: if rcode != 0:
raise ValidationError(_("Can't fetch room values from WuBook"), { raise ChannelConnectorError("Can't fetch room values from WuBook", {
'message': results, 'message': results,
'channel_id': channel_room_id, 'channel_id': channel_room_id,
}) })
@@ -277,7 +280,7 @@ class WuBookAdapter(AbstractComponent):
date_utils.get_datetime(date_to).strftime(DEFAULT_WUBOOK_DATE_FORMAT), date_utils.get_datetime(date_to).strftime(DEFAULT_WUBOOK_DATE_FORMAT),
rooms) rooms)
if rcode != 0: if rcode != 0:
raise ValidationError(_("Can't fetch rooms values from WuBook"), { raise ChannelConnectorError("Can't fetch rooms values from WuBook", {
'message': results, 'message': results,
}) })
return results return results
@@ -288,7 +291,7 @@ class WuBookAdapter(AbstractComponent):
self._session_info[1], self._session_info[1],
rooms_avail) rooms_avail)
if rcode != 0: if rcode != 0:
raise ValidationError(_("Can't update rooms availability in WuBook"), { raise ChannelConnectorError("Can't update rooms availability in WuBook", {
'message': results, 'message': results,
}) })
return results return results
@@ -296,7 +299,7 @@ class WuBookAdapter(AbstractComponent):
def corporate_fetch(self): def corporate_fetch(self):
rcode, results = self._server.corporate_fetchable_properties(self.TOKEN) rcode, results = self._server.corporate_fetchable_properties(self.TOKEN)
if rcode != 0: if rcode != 0:
raise ValidationError(_("Can't call 'corporate_fetch' from WuBook"), { raise ChannelConnectorError("Can't call 'corporate_fetch' from WuBook", {
'message': results, 'message': results,
}) })
return results return results
@@ -326,7 +329,7 @@ class WuBookAdapter(AbstractComponent):
customer, customer,
adults+children) adults+children)
if rcode != 0: if rcode != 0:
raise ValidationError(_("Can't create reservations in wubook"), { raise ChannelConnectorError("Can't create reservations in wubook", {
'message': results, 'message': results,
'date_from': checkin, 'date_from': checkin,
'date_to': checkout, 'date_to': checkout,
@@ -340,7 +343,7 @@ class WuBookAdapter(AbstractComponent):
channel_reservation_id, channel_reservation_id,
reason) reason)
if rcode != 0: if rcode != 0:
raise ValidationError(_("Can't cancel reservation in WuBook"), { raise ChannelConnectorError("Can't cancel reservation in WuBook", {
'message': results, 'message': results,
'channel_reservation_id': channel_reservation_id, 'channel_reservation_id': channel_reservation_id,
}) })
@@ -353,7 +356,7 @@ class WuBookAdapter(AbstractComponent):
1, 1,
0) 0)
if rcode != 0: if rcode != 0:
raise ValidationError(_("Can't process reservations from wubook"), { raise ChannelConnectorError("Can't process reservations from wubook", {
'message': results, 'message': results,
}) })
return results return results
@@ -364,7 +367,7 @@ class WuBookAdapter(AbstractComponent):
self._session_info[1], self._session_info[1],
channel_reservation_id) channel_reservation_id)
if rcode != 0: if rcode != 0:
raise ValidationError(_("Can't process reservation from wubook"), { raise ChannelConnectorError("Can't process reservation from wubook", {
'message': results, 'message': results,
}) })
return results return results
@@ -379,7 +382,7 @@ class WuBookAdapter(AbstractComponent):
self._session_info[1], self._session_info[1],
channel_reservation_ids) channel_reservation_ids)
if rcode != 0: if rcode != 0:
raise ValidationError(_("Can't mark as readed a reservation in wubook"), { raise ChannelConnectorError("Can't mark as readed a reservation in wubook", {
'message': results, 'message': results,
'channel_reservation_ids': str(channel_reservation_ids), 'channel_reservation_ids': str(channel_reservation_ids),
}) })
@@ -393,7 +396,7 @@ class WuBookAdapter(AbstractComponent):
name, name,
daily) daily)
if rcode != 0: if rcode != 0:
raise ValidationError(_("Can't add pricing plan to wubook"), { raise ChannelConnectorError("Can't add pricing plan to wubook", {
'message': results, 'message': results,
}) })
return results return results
@@ -404,7 +407,7 @@ class WuBookAdapter(AbstractComponent):
self._session_info[1], self._session_info[1],
channel_plan_id) channel_plan_id)
if rcode != 0: if rcode != 0:
raise ValidationError(_("Can't delete pricing plan from wubook"), { raise ChannelConnectorError("Can't delete pricing plan from wubook", {
'message': results, 'message': results,
'channel_plan_id': channel_plan_id, 'channel_plan_id': channel_plan_id,
}) })
@@ -417,7 +420,7 @@ class WuBookAdapter(AbstractComponent):
channel_plan_id, channel_plan_id,
new_name) new_name)
if rcode != 0: if rcode != 0:
raise ValidationError(_("Can't update pricing plan name in wubook"), { raise ChannelConnectorError("Can't update pricing plan name in wubook", {
'message': results, 'message': results,
'channel_plan_id': channel_plan_id, 'channel_plan_id': channel_plan_id,
}) })
@@ -431,7 +434,7 @@ class WuBookAdapter(AbstractComponent):
date_utils.get_datetime(date_from).strftime(DEFAULT_WUBOOK_DATE_FORMAT), date_utils.get_datetime(date_from).strftime(DEFAULT_WUBOOK_DATE_FORMAT),
prices) prices)
if rcode != 0: if rcode != 0:
raise ValidationError(_("Can't update pricing plan in wubook"), { raise ChannelConnectorError("Can't update pricing plan in wubook", {
'message': results, 'message': results,
'channel_plan_id': channel_plan_id, 'channel_plan_id': channel_plan_id,
'date_from': date_from, 'date_from': date_from,
@@ -445,7 +448,7 @@ class WuBookAdapter(AbstractComponent):
channel_plan_id, channel_plan_id,
periods) periods)
if rcode != 0: if rcode != 0:
raise ValidationError(_("Can't update pricing plan period in wubook"), { raise ChannelConnectorError("Can't update pricing plan period in wubook", {
'message': results, 'message': results,
'channel_plan_id': channel_plan_id, 'channel_plan_id': channel_plan_id,
}) })
@@ -456,7 +459,7 @@ class WuBookAdapter(AbstractComponent):
self._session_info[0], self._session_info[0],
self._session_info[1]) self._session_info[1])
if rcode != 0: if rcode != 0:
raise ValidationError(_("Can't get pricing plans from wubook"), { raise ChannelConnectorError("Can't get pricing plans from wubook", {
'message': results, 'message': results,
}) })
return results return results
@@ -470,7 +473,7 @@ class WuBookAdapter(AbstractComponent):
date_utils(date_to).strftime(DEFAULT_WUBOOK_DATE_FORMAT), date_utils(date_to).strftime(DEFAULT_WUBOOK_DATE_FORMAT),
rooms or []) rooms or [])
if rcode != 0: if rcode != 0:
raise ValidationError(_("Can't get pricing plans from wubook"), { raise ChannelConnectorError("Can't get pricing plans from wubook", {
'message': results, 'message': results,
'channel_plan_id': channel_plan_id, 'channel_plan_id': channel_plan_id,
'date_from': date_from, 'date_from': date_from,
@@ -484,7 +487,7 @@ class WuBookAdapter(AbstractComponent):
self._session_info[0], self._session_info[0],
self._session_info[1]) self._session_info[1])
if rcode != 0: if rcode != 0:
raise ValidationError(_("Can't fetch restriction plans from wubook"), { raise ChannelConnectorError("Can't fetch restriction plans from wubook", {
'message': results, 'message': results,
}) })
return results return results
@@ -497,7 +500,7 @@ class WuBookAdapter(AbstractComponent):
date_utils(date_to).strftime(DEFAULT_WUBOOK_DATE_FORMAT), date_utils(date_to).strftime(DEFAULT_WUBOOK_DATE_FORMAT),
channel_restriction_plan_id) channel_restriction_plan_id)
if rcode != 0: if rcode != 0:
raise ValidationError(_("Can't fetch restriction plans from wubook"), { raise ChannelConnectorError("Can't fetch restriction plans from wubook", {
'message': results, 'message': results,
'channel_restriction_plan_id': channel_restriction_plan_id, 'channel_restriction_plan_id': channel_restriction_plan_id,
'date_from': date_from, 'date_from': date_from,
@@ -513,7 +516,7 @@ class WuBookAdapter(AbstractComponent):
date_utils(date_from).strftime(DEFAULT_WUBOOK_DATE_FORMAT), date_utils(date_from).strftime(DEFAULT_WUBOOK_DATE_FORMAT),
values) values)
if rcode != 0: if rcode != 0:
raise ValidationError(_("Can't update plan restrictions on wubook"), { raise ChannelConnectorError("Can't update plan restrictions on wubook", {
'message': results, 'message': results,
'channel_restriction_plan_id': channel_restriction_plan_id, 'channel_restriction_plan_id': channel_restriction_plan_id,
'date_from': date_from, 'date_from': date_from,
@@ -527,7 +530,7 @@ class WuBookAdapter(AbstractComponent):
name, name,
compact and 1 or 0) compact and 1 or 0)
if rcode != 0: if rcode != 0:
raise ValidationError(_("Can't create plan restriction in wubook"), { raise ChannelConnectorError("Can't create plan restriction in wubook", {
'message': results, 'message': results,
}) })
return results return results
@@ -539,7 +542,7 @@ class WuBookAdapter(AbstractComponent):
channel_restriction_plan_id, channel_restriction_plan_id,
new_name) new_name)
if rcode != 0: if rcode != 0:
raise ValidationError(_("Can't rename plan restriction in wubook"), { raise ChannelConnectorError("Can't rename plan restriction in wubook", {
'message': results, 'message': results,
'channel_restriction_plan_id': channel_restriction_plan_id, 'channel_restriction_plan_id': channel_restriction_plan_id,
}) })
@@ -551,7 +554,7 @@ class WuBookAdapter(AbstractComponent):
self._session_info[1], self._session_info[1],
channel_restriction_plan_id) channel_restriction_plan_id)
if rcode != 0: if rcode != 0:
raise ValidationError(_("Can't delete plan restriction on wubook"), { raise ChannelConnectorError("Can't delete plan restriction on wubook", {
'message': results, 'message': results,
'channel_restriction_plan_id': channel_restriction_plan_id, 'channel_restriction_plan_id': channel_restriction_plan_id,
}) })
@@ -560,7 +563,7 @@ class WuBookAdapter(AbstractComponent):
def get_channels_info(self): def get_channels_info(self):
results = self._server.get_channels_info(self._session_info[0]) results = self._server.get_channels_info(self._session_info[0])
if not any(results): if not any(results):
raise ValidationError(_("Can't import channels info from wubook"), { raise ChannelConnectorError("Can't import channels info from wubook", {
'message': results, 'message': results,
}) })
return results return results

View File

@@ -20,3 +20,8 @@ class BaseHotelChannelConnectorComponent(AbstractComponent):
'date_start': dfrom, 'date_start': dfrom,
'date_end': dto, 'date_end': dto,
}) })
class ChannelConnectorError(Exception):
def __init__(self, message, data):
super().__init__(message)
self.data = data

View File

@@ -7,6 +7,7 @@ import json
from datetime import timedelta from datetime import timedelta
from odoo.exceptions import ValidationError from odoo.exceptions import ValidationError
from odoo.addons.component.core import AbstractComponent, Component from odoo.addons.component.core import AbstractComponent, Component
from odoo.addons.hotel_channel_connector.components.core import ChannelConnectorError
from odoo.addons.hotel import date_utils from odoo.addons.hotel import date_utils
from odoo import _ from odoo import _
from odoo.tools import ( from odoo.tools import (
@@ -130,7 +131,7 @@ class HotelChannelConnectorImporter(AbstractComponent):
@api.model @api.model
def _generate_booking_vals(self, broom, checkin_str, checkout_str, def _generate_booking_vals(self, broom, checkin_str, checkout_str,
is_cancellation, wchannel_info, wstatus, crcode, is_cancellation, channel_info, wstatus, crcode,
rcode, room_type, split_booking, dates_checkin, rcode, room_type, split_booking, dates_checkin,
dates_checkout, book): dates_checkout, book):
# Generate Reservation Day Lines # Generate Reservation Day Lines
@@ -154,24 +155,27 @@ class HotelChannelConnectorImporter(AbstractComponent):
persons = room_type.wcapacity persons = room_type.wcapacity
if 'ancillary' in broom and 'guests' in broom['ancillary']: if 'ancillary' in broom and 'guests' in broom['ancillary']:
persons = broom['ancillary']['guests'] persons = broom['ancillary']['guests']
vals = { vals = {
'checkin': checkin_str, 'channel_reservation_id': rcode,
'checkout': checkout_str, 'ota_id': channel_info and channel_info.id,
'adults': persons, 'ota_reservation_id': crcode,
'children': book['children'], 'channel_raw_data': json.dumps(book),
'reservation_line_ids': reservation_line_ids,
'price_unit': tprice,
'to_assign': True,
'wrid': rcode,
'wchannel_id': wchannel_info and wchannel_info.id,
'wchannel_reservation_code': crcode,
'wstatus': wstatus, 'wstatus': wstatus,
'to_read': True, 'wmodified': book['was_modified'],
'state': is_cancellation and 'cancelled' or 'draft', 'odoo_id': [0, False, {
'room_type_id': room_type.id, 'checkin': checkin_str,
'splitted': split_booking, 'checkout': checkout_str,
'wbook_json': json.dumps(book), 'adults': persons,
'wmodified': book['was_modified'] 'children': book['children'],
'reservation_line_ids': reservation_line_ids,
'price_unit': tprice,
'to_assign': True,
'to_read': True,
'state': is_cancellation and 'cancelled' or 'draft',
'room_type_id': room_type.id,
'splitted': split_booking,
}],
} }
_logger.info("===== CONTRUCT RESERV") _logger.info("===== CONTRUCT RESERV")
_logger.info(vals) _logger.info(vals)
@@ -210,8 +214,10 @@ class HotelChannelConnectorImporter(AbstractComponent):
tz_hotel = self.env['ir.default'].sudo().get( tz_hotel = self.env['ir.default'].sudo().get(
'res.config.settings', 'tz_hotel') 'res.config.settings', 'tz_hotel')
res_partner_obj = self.env['res.partner'] res_partner_obj = self.env['res.partner']
channel_reserv_obj = self.env['channel.hotel.reservation']
hotel_reserv_obj = self.env['hotel.reservation'] hotel_reserv_obj = self.env['hotel.reservation']
hotel_folio_obj = self.env['hotel.folio'] hotel_folio_obj = self.env['hotel.folio']
channel_room_type_obj = self.env['channel.hotel.room.type']
hotel_room_type_obj = self.env['hotel.room.type'] hotel_room_type_obj = self.env['hotel.room.type']
# Space for store some data for construct folios # Space for store some data for construct folios
processed_rids = [] processed_rids = []
@@ -231,10 +237,10 @@ class HotelChannelConnectorImporter(AbstractComponent):
# (for example set a invalid new reservation and receive in # (for example set a invalid new reservation and receive in
# the same transaction an cancellation) # the same transaction an cancellation)
if crcode in failed_reservations: if crcode in failed_reservations:
self.create_channel_connector_issue( self.create_issue(
'reservation', 'reservation',
"Can't process a reservation that previusly failed!", "Can't process a reservation that previusly failed!",
'', wid=book['reservation_code']) '', channel_object_id=book['reservation_code'])
continue continue
# Get dates for the reservation (GMT->UTC) # Get dates for the reservation (GMT->UTC)
@@ -260,34 +266,37 @@ class HotelChannelConnectorImporter(AbstractComponent):
# Search Folio. If exists. # Search Folio. If exists.
folio_id = False folio_id = False
if crcode != 'undefined': if crcode != 'undefined':
reserv_folio = hotel_reserv_obj.search([ reserv_folio = channel_reserv_obj.search([
('wchannel_reservation_code', '=', crcode) ('ota_reservation_id', '=', crcode)
], limit=1) ], limit=1)
if reserv_folio: if reserv_folio:
folio_id = reserv_folio.folio_id folio_id = reserv_folio.odoo_id.folio_id
else: else:
reserv_folio = hotel_reserv_obj.search([ reserv_folio = channel_reserv_obj.search([
('wrid', '=', rcode) ('channel_reservation_id', '=', rcode)
], limit=1) ], limit=1)
if reserv_folio: if reserv_folio:
folio_id = reserv_folio.folio_id folio_id = reserv_folio.odoo_id.folio_id
# Need update reservations? # Need update reservations?
sreservs = hotel_reserv_obj.search([('wrid', '=', rcode)]) sreservs = channel_reserv_obj.search([('channel_reservation_id', '=', rcode)])
reservs = folio_id.room_lines if folio_id else sreservs reservs = folio_id.room_lines if folio_id else sreservs.mapped(lambda x: x.odoo_id)
reservs_processed = False reservs_processed = False
if any(reservs): if any(reservs):
folio_id = reservs[0].folio_id folio_id = reservs[0].folio_id
for reserv in reservs: for reserv in reservs:
if reserv.wrid == rcode: if reserv.channel_reservation_id == rcode:
reserv.with_context({'wubook_action': False}).write({ binding_id = reserv.channel_bind_ids[0]
binding_id.write({
'channel_raw_data': json.dumps(book),
'wstatus': str(book['status']), 'wstatus': str(book['status']),
'wstatus_reason': book.get('status_reason', ''), 'wstatus_reason': book.get('status_reason', ''),
})
reserv.with_context({'wubook_action': False}).write({
'to_read': True, 'to_read': True,
'to_assign': True, 'to_assign': True,
'price_unit': book['amount'], 'price_unit': book['amount'],
'wcustomer_notes': book['customer_notes'], 'customer_notes': book['customer_notes'],
'wbook_json': json.dumps(book),
}) })
if reserv.partner_id.unconfirmed: if reserv.partner_id.unconfirmed:
reserv.partner_id.write( reserv.partner_id.write(
@@ -321,22 +330,22 @@ class HotelChannelConnectorImporter(AbstractComponent):
partner_id = res_partner_obj.create(self._generate_partner_vals(book)) partner_id = res_partner_obj.create(self._generate_partner_vals(book))
# Search Wubook Channel Info # Search Wubook Channel Info
wchannel_info = self.env['wubook.channel.info'].search( channel_info = self.env['hotel.channel.connector.ota.info'].search(
[('wid', '=', str(book['id_channel']))], limit=1) [('ota_id', '=', str(book['id_channel']))], limit=1)
reservations = [] reservations = []
used_rooms = [] used_rooms = []
# Iterate booked rooms # Iterate booked rooms
for broom in book['booked_rooms']: for broom in book['booked_rooms']:
room_type = hotel_room_type_obj.search([ room_type = channel_room_type_obj.search([
('wrid', '=', broom['room_id']) ('channel_room_id', '=', broom['room_id'])
], limit=1) ], limit=1)
if not room_type: if not room_type:
self.create_channel_connector_issue( self.create_issue(
'reservation', 'reservation',
"Can't found any room type associated to '%s' \ "Can't found any room type associated to '%s' \
in this hotel" % book['rooms'], in this hotel" % book['rooms'],
'', wid=book['reservation_code']) '', channel_object_id=book['reservation_code'])
failed_reservations.append(crcode) failed_reservations.append(crcode)
continue continue
@@ -355,26 +364,26 @@ class HotelChannelConnectorImporter(AbstractComponent):
checkin_str, checkin_str,
checkout_str, checkout_str,
is_cancellation, is_cancellation,
wchannel_info, channel_info,
bstatus, bstatus,
crcode, crcode,
rcode, rcode,
room_type, room_type.odoo_id,
split_booking, split_booking,
dates_checkin, dates_checkin,
dates_checkout, dates_checkout,
book, book,
) )
if vals['price_unit'] != book['amount']: if vals['price_unit'] != book['amount']:
self.create_channel_connector_issue( self.create_issue(
'reservation', 'reservation',
"Invalid reservation total price! %.2f != %.2f" % (vals['price_unit'], book['amount']), "Invalid reservation total price! %.2f != %.2f" % (vals['price_unit'], book['amount']),
'', wid=book['reservation_code']) '', channel_object_id=book['reservation_code'])
free_rooms = hotel_room_type_obj.check_availability_room( free_rooms = room_type.odoo_id.check_availability_room(
checkin_str, checkin_str,
checkout_str, checkout_str,
room_type_id=room_type.id, room_type_id=room_type.odoo_id.id,
notthis=used_rooms) notthis=used_rooms)
if any(free_rooms): if any(free_rooms):
vals.update({ vals.update({
@@ -412,11 +421,11 @@ class HotelChannelConnectorImporter(AbstractComponent):
checkin_utc_dt, checkin_utc_dt,
checkout_utc_dt, checkout_utc_dt,
is_cancellation, is_cancellation,
wchannel_info, channel_info,
bstatus, bstatus,
crcode, crcode,
rcode, rcode,
room_type, room_type.odoo_id,
False, False,
(checkin_utc_dt, False), (checkin_utc_dt, False),
(checkout_utc_dt, False), (checkout_utc_dt, False),
@@ -424,15 +433,15 @@ class HotelChannelConnectorImporter(AbstractComponent):
) )
vals.update({ vals.update({
'product_id': 'product_id':
room_type.room_ids[0].product_id.id, room_type.odoo_id.room_ids[0].product_id.id,
'name': room_type.name, 'name': room_type.odoo_id.name,
'overbooking': True, 'overbooking': True,
}) })
reservations.append((0, False, vals)) reservations.append((0, False, vals))
self.create_channel_connector_issue( self.create_issue(
'reservation', 'reservation',
"Reservation imported with overbooking state", "Reservation imported with overbooking state",
'', wid=rcode) '', channel_object_id=rcode)
dates_checkin = [False, False] dates_checkin = [False, False]
dates_checkout = [False, False] dates_checkout = [False, False]
split_booking = False split_booking = False
@@ -448,10 +457,10 @@ class HotelChannelConnectorImporter(AbstractComponent):
] ]
if split_booking: if split_booking:
self.create_channel_connector_issue( self.create_issue(
'reservation', 'reservation',
"Reservation Splitted", "Reservation Splitted",
'', wid=rcode) '', channel_object_id=rcode)
# Create Folio # Create Folio
if not any(failed_reservations) and any(reservations): if not any(failed_reservations) and any(reservations):
@@ -487,11 +496,11 @@ class HotelChannelConnectorImporter(AbstractComponent):
creserv.parent_reservation = preserv.id creserv.parent_reservation = preserv.id
processed_rids.append(rcode) processed_rids.append(rcode)
except Exception as e_msg: except ChannelConnectorError as err:
self.create_channel_connector_issue( self.create_issue(
'reservation', 'reservation',
e_msg[0], err.data['message'],
'', wid=rcode) '', channel_object_id=rcode)
failed_reservations.append(crcode) failed_reservations.append(crcode)
return (processed_rids, any(failed_reservations), return (processed_rids, any(failed_reservations),
checkin_utc_dt, checkout_utc_dt) checkin_utc_dt, checkout_utc_dt)
@@ -698,8 +707,8 @@ class HotelChannelConnectorImporter(AbstractComponent):
room_type.with_context({'wubook_action': False}).write(vals) room_type.with_context({'wubook_action': False}).write(vals)
else: else:
room_type_obj.with_context({'wubook_action': False}).create(vals) room_type_obj.with_context({'wubook_action': False}).create(vals)
except ValidationError: except ChannelConnectorError as err:
self.create_issue('room', _("Can't import rooms from WuBook"), results) self.create_issue('room', _("Can't import rooms from WuBook"), err.data['message'])
return count return count
@@ -725,10 +734,10 @@ class HotelChannelConnectorImporter(AbstractComponent):
dto_dt.strftime(DEFAULT_WUBOOK_DATE_FORMAT), dto_dt.strftime(DEFAULT_WUBOOK_DATE_FORMAT),
rooms) rooms)
self._generate_room_values(dfrom, dto, results, self._generate_room_values(dfrom, dto, results,
set_max_avail=set_max_avail) set_max_avail=set_max_avail)
except ValidationError: except ChannelConnectorError as err:
self.create_issue('room', _("Can't fetch rooms values from WuBook"), self.create_issue('room', _("Can't fetch rooms values from WuBook"),
results, dfrom=dfrom, dto=dto) err.data['message'], dfrom=dfrom, dto=dto)
return False return False
return True return True
@@ -746,11 +755,11 @@ class HotelChannelConnectorImporter(AbstractComponent):
self.backend_adapter.fetch_rooms_values( self.backend_adapter.fetch_rooms_values(
checkin_utc_dt.strftime(DEFAULT_SERVER_DATE_FORMAT), checkin_utc_dt.strftime(DEFAULT_SERVER_DATE_FORMAT),
checkout_utc_dt.strftime(DEFAULT_SERVER_DATE_FORMAT)) checkout_utc_dt.strftime(DEFAULT_SERVER_DATE_FORMAT))
except ValidationError: except ChannelConnectorError as err:
self.create_channel_connector_issue( self.create_issue(
'reservation', 'reservation',
_("Can't process reservations from wubook"), _("Can't process reservations from wubook"),
results, channel_object_id=channel_reservation_id) err.data['message'], channel_object_id=channel_reservation_id)
return False return False
return True return True
@@ -759,11 +768,11 @@ class HotelChannelConnectorImporter(AbstractComponent):
try: try:
results = self.backend_adapter.get_pricing_plans() results = self.backend_adapter.get_pricing_plans()
count = self._generate_pricelists(results) count = self._generate_pricelists(results)
except ValidationError: except ChannelConnectorError as err:
self.create_issue( self.create_issue(
'plan', 'plan',
_("Can't get pricing plans from wubook"), _("Can't get pricing plans from wubook"),
results) err.data['message'])
return 0 return 0
return count return count
@@ -776,11 +785,11 @@ class HotelChannelConnectorImporter(AbstractComponent):
date_to, date_to,
rooms) rooms)
self._generate_pricelist_items(channel_plan_id, date_from, date_to, results) self._generate_pricelist_items(channel_plan_id, date_from, date_to, results)
except ValidationError: except ChannelConnectorError as err:
self.create_issue( self.create_issue(
'plan', 'plan',
_("Can't fetch plan prices from wubook"), _("Can't fetch plan prices from wubook"),
results) err.data['message'])
return False return False
return True return True
@@ -799,11 +808,12 @@ class HotelChannelConnectorImporter(AbstractComponent):
date_to, date_to,
rooms) rooms)
self._generate_pricelist_items(channel_plan_id, date_from, date_to, results) self._generate_pricelist_items(channel_plan_id, date_from, date_to, results)
except ValidationError: except ChannelConnectorError as err:
self.create_issue( self.create_issue(
'plan', 'plan',
"Can't fetch all plan prices from wubook!", "Can't fetch all plan prices from wubook!",
results, wid=channel_plan_id, dfrom=date_from, dto=date_to) err.data['message'],
channel_object_id=channel_plan_id, dfrom=date_from, dto=date_to)
return False return False
return no_errors return no_errors
@@ -812,11 +822,11 @@ class HotelChannelConnectorImporter(AbstractComponent):
try: try:
results = self.backend_adapter.rplan_rplans() results = self.backend_adapter.rplan_rplans()
count = self._generate_restrictions(results) count = self._generate_restrictions(results)
except ValidationError: except ChannelConnectorError as err:
self.create_issue( self.create_issue(
'rplan', 'rplan',
_("Can't fetch restriction plans from wubook"), _("Can't fetch restriction plans from wubook"),
results) err.data['message'])
return 0 return 0
return count return count
@@ -829,12 +839,12 @@ class HotelChannelConnectorImporter(AbstractComponent):
int(channel_restriction_plan_id)) int(channel_restriction_plan_id))
if any(results): if any(results):
self._generate_restriction_items(results) self._generate_restriction_items(results)
except ValidationError: except ChannelConnectorError as err:
self.create_issue( self.create_issue(
'rplan', 'rplan',
_("Can't fetch plan restrictions from wubook"), _("Can't fetch plan restrictions from wubook"),
results, err.data['message'],
wid=channel_restriction_plan_id, channel_object_id=channel_restriction_plan_id,
dfrom=date_from, dto=date_to) dfrom=date_from, dto=date_to)
return False return False
return True return True
@@ -844,10 +854,10 @@ class HotelChannelConnectorImporter(AbstractComponent):
try: try:
results = self.backend_adapter.get_channels_info() results = self.backend_adapter.get_channels_info()
count = self._generate_wubook_channel_info(results) count = self._generate_wubook_channel_info(results)
except ValidationError: except ChannelConnectorError as err:
self.create_issue( self.create_issue(
'channel', 'channel',
_("Can't import channels info from wubook"), _("Can't import channels info from wubook"),
results) err.data['message'])
return 0 return 0
return count return count

View File

@@ -3,6 +3,7 @@
from odoo.exceptions import ValidationError from odoo.exceptions import ValidationError
from odoo.addons.component.core import Component from odoo.addons.component.core import Component
from odoo.addons.hotel_channel_connector.components.core import ChannelConnectorError
from odoo import fields, api, _ from odoo import fields, api, _
from odoo.tools import ( from odoo.tools import (
DEFAULT_SERVER_DATE_FORMAT, DEFAULT_SERVER_DATE_FORMAT,
@@ -34,10 +35,10 @@ class HotelReservationImporter(Component):
self.backend_adapter.fetch_rooms_values( self.backend_adapter.fetch_rooms_values(
checkin_utc_dt.strftime(DEFAULT_SERVER_DATE_FORMAT), checkin_utc_dt.strftime(DEFAULT_SERVER_DATE_FORMAT),
checkout_utc_dt.strftime(DEFAULT_SERVER_DATE_FORMAT)) checkout_utc_dt.strftime(DEFAULT_SERVER_DATE_FORMAT))
except ValidationError: except ChannelConnectorError as err:
self.create_issue( self.create_issue(
'reservation', 'reservation',
_("Can't process reservations from wubook"), _("Can't process reservations from wubook"),
results) err.data['message'])
return False return False
return True return True

View File

@@ -21,9 +21,10 @@
<notebook> <notebook>
<page string="API" name="api"> <page string="API" name="api">
<group colspan="4" col="4"> <group colspan="4" col="4">
<field name="version" colspan="4"/> <field name="version" colspan="2"/>
<field name="server" colspan="2"/> <field name="server" colspan="2"/>
<field name="lcode" colspan="2"/> <field name="lcode" colspan="2"/>
<field name="pkey" colspan="2"/>
<field name="username" colspan="2"/> <field name="username" colspan="2"/>
<field name="passwd" password="1" colspan="2"/> <field name="passwd" password="1" colspan="2"/>
</group> </group>