mirror of
https://github.com/OCA/pms.git
synced 2025-01-29 00:17:45 +02:00
Code review (#62)
* [REF] pms: refactor amenity type * [REF] pms: refactor amenity * [REF]Refactor amenity views and demo data * [WIP] master model 2nd day * [WIP] Master model refactor * [WIP] Refactor in tests * [WIP] Add mandatory sequence in pms_property at tests and fix create in folio, reservation and checkin * [WIP] Test refactor * [WIP]Refactor pms_room, pms_room_clousure_reason and pms_room_type * [WIP]review of guidelines in master models * [WIP]test refactor * [WIP]review guidelines in master models 2 * [WIP] fixed fields in pms_l10n_es * [WIP]Refactor product_product, product_template, res_company, res_partner and res_user * [IMP] Add common.py for tests * [WIP] Refactor fields in pms.folio and pms.reservation * [WIP] Review guidelines in pms.reservation, pms.reservation.line and rename availability models * [WIP] Rename availability models * [WIP] Refactor availability models * [WIP] Refactor availity models 2 * [WIP] Pms: add sequences creation in pms_property create * [WIP] Fix sequence creation in pmp.property * [REF] Refactor fields in res_partner and rename date_overnight * [REF] Refactoring master models tests * [FIX] Fix sequence create in pms.reservation * [REF] Refactor helps in master and availability models * [IMP] Extend test coverage in test_pms_reservation * [REF] Refactor fields in pms_reservation * [REF] Refactor fields in pms_reservation 2 * [REF] Refactor fields in service flow * [REF] Refactor pms_reservation * [REF] Refactor pms_reservation 2 * [REF] draft button removed from view * [REF] change no_show to arrival_delayed in field state of pms_reservation * [REF] Add compute_preferred_room_id in pms_reservation * [REF] Fix cache problem in test_reservation_action_checkout Co-authored-by: braisab <braisterbutalino@gmail.com> Co-authored-by: Sara Lago <saralago126@gmail.com> Co-authored-by: Brais Abeijón <>
This commit is contained in:
@@ -44,7 +44,7 @@
|
||||
"views/pms_board_service_room_type_views.xml",
|
||||
"views/pms_cancelation_rule_views.xml",
|
||||
"views/pms_checkin_partner_views.xml",
|
||||
"views/pms_floor_views.xml",
|
||||
"views/pms_ubication_views.xml",
|
||||
"views/pms_property_views.xml",
|
||||
"views/pms_reservation_views.xml",
|
||||
"views/pms_service_views.xml",
|
||||
@@ -58,8 +58,8 @@
|
||||
"views/account_bank_statement_views.xml",
|
||||
"views/res_users_views.xml",
|
||||
"views/pms_room_type_class_views.xml",
|
||||
"views/pms_room_type_availability_plan_views.xml",
|
||||
"views/pms_room_type_availability_rule_views.xml",
|
||||
"views/pms_availability_plan_views.xml",
|
||||
"views/pms_availability_plan_rule_views.xml",
|
||||
"views/pms_shared_room_views.xml",
|
||||
"views/res_partner_views.xml",
|
||||
"views/product_pricelist_views.xml",
|
||||
@@ -67,7 +67,6 @@
|
||||
"views/pms_sale_channel.xml",
|
||||
"views/product_template_views.xml",
|
||||
"views/webclient_templates.xml",
|
||||
"views/ir_sequence_views.xml",
|
||||
"views/account_journal_views.xml",
|
||||
"views/folio_portal_templates.xml",
|
||||
"views/reservation_portal_templates.xml",
|
||||
|
||||
@@ -15,7 +15,7 @@
|
||||
name="nextcall"
|
||||
eval="(DateTime.now() + timedelta(days=1)).strftime('%Y-%m-%d 09:00:00')"
|
||||
/>
|
||||
<field name="code">model.auto_no_show()</field>
|
||||
<field name="code">model.auto_arrival_delayed()</field>
|
||||
</record>
|
||||
<!-- Set reservation like No Checout if checkout is not confirmed-->
|
||||
<record model="ir.cron" id="nocheckout_reservations">
|
||||
@@ -28,7 +28,7 @@
|
||||
<field name="state">code</field>
|
||||
<field name="model_id" ref="model_pms_reservation" />
|
||||
<field name="nextcall" eval="DateTime.now()" />
|
||||
<field name="code">model.auto_no_checkout()</field>
|
||||
<field name="code">model.auto_departure_delayed()</field>
|
||||
</record>
|
||||
<!-- Scheduler For To Inform Guest About Reservation Before 24 Hours -->
|
||||
<record model="ir.cron" id="autocheckout_reservations">
|
||||
|
||||
@@ -2,10 +2,7 @@
|
||||
<odoo>
|
||||
<data noupdate="1">
|
||||
<!-- Basic pms -->
|
||||
<record
|
||||
id="main_pms_room_type_availability_plan"
|
||||
model="pms.room.type.availability.plan"
|
||||
>
|
||||
<record id="main_pms_availability_plan" model="pms.availability.plan">
|
||||
<field name="name">Availability Plan</field>
|
||||
</record>
|
||||
<record id="main_pms_property" model="pms.property">
|
||||
@@ -21,6 +18,7 @@
|
||||
<field name="website">https://www.commitsun.com</field>
|
||||
<field name="folio_sequence_id" ref="pms.seq_pms_folio" />
|
||||
<field name="checkin_sequence_id" ref="pms.seq_pms_checkin" />
|
||||
<field name="reservation_sequence_id" ref="pms.seq_pms_reservation" />
|
||||
</record>
|
||||
<!-- pms.users -->
|
||||
<record id="base.user_root" model="res.users">
|
||||
|
||||
@@ -1,7 +1,7 @@
|
||||
<?xml version="1.0" encoding="utf-8" ?>
|
||||
<odoo>
|
||||
<data noupdate="1">
|
||||
<!-- Multi pms Demo -->
|
||||
<!-- Company -->
|
||||
<record id="pms_company1" model="res.company">
|
||||
<field name="name">Alda Company</field>
|
||||
<field name="currency_id" ref="base.EUR" />
|
||||
@@ -11,26 +11,62 @@
|
||||
eval="obj()._get_default_favicon(original=True)"
|
||||
/>
|
||||
</record>
|
||||
<record
|
||||
id="demo_pms_room_type_availability"
|
||||
model="pms.room.type.availability.plan"
|
||||
>
|
||||
<!--Availability Plan -->
|
||||
<record id="demo_pms_availability" model="pms.availability.plan">
|
||||
<field name="name">Availability Plan Demo</field>
|
||||
</record>
|
||||
<!-- Sequence -->
|
||||
<record model="ir.sequence" id="seq_pms_folio2">
|
||||
<field name="name">PMS Folio 2</field>
|
||||
<field name="code">pms.folio</field>
|
||||
<field name="prefix">F/%(y)s</field>
|
||||
<field name="suffix">%(sec)s</field>
|
||||
<field name="padding">4</field>
|
||||
<field name="company_id" ref="pms_company1" />
|
||||
</record>
|
||||
|
||||
<record model="ir.sequence" id="seq_pms_reservation2">
|
||||
<field name="name">PMS Reservation 2</field>
|
||||
<field name="code">pms.reservation</field>
|
||||
<field name="prefix">R/%(y)s</field>
|
||||
<field name="suffix">%(sec)s</field>
|
||||
<field name="padding">4</field>
|
||||
<field name="company_id" ref="pms_company1" />
|
||||
</record>
|
||||
|
||||
<record model="ir.sequence" id="seq_pms_checkin2">
|
||||
<field name="name">PMS Checkin 2</field>
|
||||
<field name="code">pms.checkin.partner</field>
|
||||
<field name="prefix">C/%(y)s</field>
|
||||
<field name="suffix">%(sec)s</field>
|
||||
<field name="padding">4</field>
|
||||
<field name="company_id" ref="pms_company1" />
|
||||
</record>
|
||||
|
||||
<!--Properties-->
|
||||
<record id="demo_pms_property" model="pms.property">
|
||||
<field name="name">San Carlos</field>
|
||||
<field name="company_id" ref="base.main_company" />
|
||||
<field name="default_pricelist_id" ref="product.list0" />
|
||||
<field name="folio_sequence_id" ref="pms.seq_pms_folio" />
|
||||
<field name="checkin_sequence_id" ref="pms.seq_pms_checkin" />
|
||||
<field name="reservation_sequence_id" ref="pms.seq_pms_reservation" />
|
||||
</record>
|
||||
<record id="demo_pms_property2" model="pms.property">
|
||||
<field name="name">Agalia</field>
|
||||
<field name="company_id" ref="base.main_company" />
|
||||
<field name="default_pricelist_id" ref="product.list0" />
|
||||
<field name="folio_sequence_id" ref="pms.seq_pms_folio" />
|
||||
<field name="checkin_sequence_id" ref="pms.seq_pms_checkin" />
|
||||
<field name="reservation_sequence_id" ref="pms.seq_pms_reservation" />
|
||||
</record>
|
||||
<record id="demo_pms_property3" model="pms.property">
|
||||
<field name="name">Pilgrim Leon</field>
|
||||
<field name="company_id" ref="pms_company1" />
|
||||
<field name="default_pricelist_id" ref="product.list0" />
|
||||
<field name="folio_sequence_id" ref="pms.seq_pms_folio2" />
|
||||
<field name="checkin_sequence_id" ref="pms.seq_pms_checkin2" />
|
||||
<field name="reservation_sequence_id" ref="pms.seq_pms_reservation2" />
|
||||
</record>
|
||||
<!-- users -->
|
||||
<record id="base.user_root" model="res.users">
|
||||
@@ -76,14 +112,14 @@
|
||||
]"
|
||||
/>
|
||||
</record>
|
||||
<!-- pms.floor -->
|
||||
<record id="pms_floor_0" model="pms.floor">
|
||||
<!-- pms.ubication -->
|
||||
<record id="pms_ubication_0" model="pms.ubication">
|
||||
<field name="name">Ground Floor</field>
|
||||
</record>
|
||||
<record id="pms_floor_1" model="pms.floor">
|
||||
<record id="pms_ubication_1" model="pms.ubication">
|
||||
<field name="name">First Floor</field>
|
||||
</record>
|
||||
<record id="pms_floor_2" model="pms.floor">
|
||||
<record id="pms_ubication_2" model="pms.ubication">
|
||||
<field name="name">Second Floor</field>
|
||||
</record>
|
||||
<!-- pms.amenity.type -->
|
||||
@@ -99,31 +135,31 @@
|
||||
<!-- pms.amenity -->
|
||||
<record id="pms_amenity_0" model="pms.amenity">
|
||||
<field name="name">Shampoo and Soap</field>
|
||||
<field name="room_amenity_type_id" ref="pms_amenity_type_0" />
|
||||
<field name="pms_amenity_type_id" ref="pms_amenity_type_0" />
|
||||
</record>
|
||||
<record id="pms_amenity_1" model="pms.amenity">
|
||||
<field name="name">High-quality Shampoo and Soap Essential Herbs</field>
|
||||
<field name="room_amenity_type_id" ref="pms_amenity_type_0" />
|
||||
<field name="pms_amenity_type_id" ref="pms_amenity_type_0" />
|
||||
</record>
|
||||
<record id="pms_amenity_2" model="pms.amenity">
|
||||
<field name="name">Hair Dryer</field>
|
||||
<field name="room_amenity_type_id" ref="pms_amenity_type_0" />
|
||||
<field name="pms_amenity_type_id" ref="pms_amenity_type_0" />
|
||||
</record>
|
||||
<record id="pms_amenity_3" model="pms.amenity">
|
||||
<field name="name">High speed Wired Internet access</field>
|
||||
<field name="room_amenity_type_id" ref="pms_amenity_type_1" />
|
||||
<field name="pms_amenity_type_id" ref="pms_amenity_type_1" />
|
||||
</record>
|
||||
<record id="pms_amenity_4" model="pms.amenity">
|
||||
<field name="name">Wi-Fi</field>
|
||||
<field name="room_amenity_type_id" ref="pms_amenity_type_1" />
|
||||
<field name="pms_amenity_type_id" ref="pms_amenity_type_1" />
|
||||
</record>
|
||||
<record id="pms_amenity_5" model="pms.amenity">
|
||||
<field name="name">Microwave oven</field>
|
||||
<field name="room_amenity_type_id" ref="pms_amenity_type_2" />
|
||||
<field name="pms_amenity_type_id" ref="pms_amenity_type_2" />
|
||||
</record>
|
||||
<record id="pms_amenity_6" model="pms.amenity">
|
||||
<field name="name">Half-sized Refrigerator</field>
|
||||
<field name="room_amenity_type_id" ref="pms_amenity_type_2" />
|
||||
<field name="pms_amenity_type_id" ref="pms_amenity_type_2" />
|
||||
</record>
|
||||
<!-- pms.room.type.class -->
|
||||
<record id="pms_room_type_class_0" model="pms.room.type.class">
|
||||
@@ -137,14 +173,14 @@
|
||||
<!-- pms.room.type -->
|
||||
<record id="pms_room_type_0" model="pms.room.type">
|
||||
<field name="name">Economic</field>
|
||||
<field name="code_type">ECO</field>
|
||||
<field name="default_code">ECO</field>
|
||||
<field name="list_price">21.00</field>
|
||||
<field name="class_id" ref="pms_room_type_class_0" />
|
||||
<field name="room_amenity_ids" eval="[(4, ref('pms_amenity_0'))]" />
|
||||
</record>
|
||||
<record id="pms_room_type_1" model="pms.room.type">
|
||||
<field name="name">Single</field>
|
||||
<field name="code_type">SNG</field>
|
||||
<field name="default_code">SNG</field>
|
||||
<field name="list_price">20.00</field>
|
||||
<field name="class_id" ref="pms_room_type_class_0" />
|
||||
<field
|
||||
@@ -154,7 +190,7 @@
|
||||
</record>
|
||||
<record id="pms_room_type_2" model="pms.room.type">
|
||||
<field name="name">Double</field>
|
||||
<field name="code_type">DBL</field>
|
||||
<field name="default_code">DBL</field>
|
||||
<field name="list_price">25.00</field>
|
||||
<field name="class_id" ref="pms_room_type_class_0" />
|
||||
<field
|
||||
@@ -164,7 +200,7 @@
|
||||
</record>
|
||||
<record id="pms_room_type_3" model="pms.room.type">
|
||||
<field name="name">Triple</field>
|
||||
<field name="code_type">TRP</field>
|
||||
<field name="default_code">TRP</field>
|
||||
<field name="list_price">35.00</field>
|
||||
<field name="class_id" ref="pms_room_type_class_0" />
|
||||
<field
|
||||
@@ -174,7 +210,7 @@
|
||||
</record>
|
||||
<record id="pms_room_type_4" model="pms.room.type">
|
||||
<field name="name">Conference Room</field>
|
||||
<field name="code_type">CFR</field>
|
||||
<field name="default_code">CFR</field>
|
||||
<field name="list_price">80.00</field>
|
||||
<field name="class_id" ref="pms_room_type_class_1" />
|
||||
<field
|
||||
@@ -186,35 +222,35 @@
|
||||
<record id="pms_room_0" model="pms.room">
|
||||
<field name="name">Economic-101</field>
|
||||
<field name="room_type_id" ref="pms_room_type_0" />
|
||||
<field name="floor_id" ref="pms_floor_1" />
|
||||
<field name="ubication_id" ref="pms_ubication_1" />
|
||||
<field name="capacity">2</field>
|
||||
<field name="pms_property_id" ref="pms.main_pms_property" />
|
||||
</record>
|
||||
<record id="pms_room_1" model="pms.room">
|
||||
<field name="name">Single-101</field>
|
||||
<field name="room_type_id" ref="pms_room_type_1" />
|
||||
<field name="floor_id" ref="pms_floor_1" />
|
||||
<field name="ubication_id" ref="pms_ubication_1" />
|
||||
<field name="capacity">1</field>
|
||||
<field name="pms_property_id" ref="pms.main_pms_property" />
|
||||
</record>
|
||||
<record id="pms_room_2" model="pms.room">
|
||||
<field name="name">Single-102</field>
|
||||
<field name="room_type_id" ref="pms_room_type_1" />
|
||||
<field name="floor_id" ref="pms_floor_1" />
|
||||
<field name="ubication_id" ref="pms_ubication_1" />
|
||||
<field name="capacity">1</field>
|
||||
<field name="pms_property_id" ref="pms.main_pms_property" />
|
||||
</record>
|
||||
<record id="pms_room_3" model="pms.room">
|
||||
<field name="name">Single-103</field>
|
||||
<field name="room_type_id" ref="pms_room_type_1" />
|
||||
<field name="floor_id" ref="pms_floor_1" />
|
||||
<field name="ubication_id" ref="pms_ubication_1" />
|
||||
<field name="capacity">1</field>
|
||||
<field name="pms_property_id" ref="pms.main_pms_property" />
|
||||
</record>
|
||||
<record id="pms_room_4" model="pms.room">
|
||||
<field name="name">Double-201</field>
|
||||
<field name="room_type_id" ref="pms_room_type_2" />
|
||||
<field name="floor_id" ref="pms_floor_2" />
|
||||
<field name="ubication_id" ref="pms_ubication_2" />
|
||||
<field name="capacity">2</field>
|
||||
<field name="extra_beds_allowed">1</field>
|
||||
<field name="pms_property_id" ref="pms.main_pms_property" />
|
||||
@@ -222,21 +258,21 @@
|
||||
<record id="pms_room_5" model="pms.room">
|
||||
<field name="name">Double-202</field>
|
||||
<field name="room_type_id" ref="pms_room_type_2" />
|
||||
<field name="floor_id" ref="pms_floor_2" />
|
||||
<field name="ubication_id" ref="pms_ubication_2" />
|
||||
<field name="capacity">2</field>
|
||||
<field name="pms_property_id" ref="pms.main_pms_property" />
|
||||
</record>
|
||||
<record id="pms_room_6" model="pms.room">
|
||||
<field name="name">Triple-203</field>
|
||||
<field name="room_type_id" ref="pms_room_type_3" />
|
||||
<field name="floor_id" ref="pms_floor_2" />
|
||||
<field name="ubication_id" ref="pms_ubication_2" />
|
||||
<field name="capacity">3</field>
|
||||
<field name="pms_property_id" ref="pms.main_pms_property" />
|
||||
</record>
|
||||
<record id="pms_room_7" model="pms.room">
|
||||
<field name="name">Open Talk Away Room</field>
|
||||
<field name="room_type_id" ref="pms_room_type_4" />
|
||||
<field name="floor_id" ref="pms_floor_0" />
|
||||
<field name="ubication_id" ref="pms_ubication_0" />
|
||||
<field name="capacity">10</field>
|
||||
<field name="pms_property_id" ref="pms.main_pms_property" />
|
||||
</record>
|
||||
@@ -258,7 +294,6 @@
|
||||
<field name="per_person">False</field>
|
||||
<field name="daily_limit">1</field>
|
||||
<field name="is_extra_bed">True</field>
|
||||
<field name="show_in_calendar">True</field>
|
||||
</record>
|
||||
<record id="pms_service_3" model="product.product">
|
||||
<field name="name">Late Check-out</field>
|
||||
@@ -369,7 +404,7 @@
|
||||
<record id="demo_pms_room_type_0" model="pms.room.type">
|
||||
<field name="pms_property_ids" eval="[(4, ref('pms.demo_pms_property'))]" />
|
||||
<field name="name">Prop. Demo Suite</field>
|
||||
<field name="code_type">SUI</field>
|
||||
<field name="default_code">SUI</field>
|
||||
<field name="list_price">21.00</field>
|
||||
<field name="class_id" ref="pms_room_type_class_0" />
|
||||
<field name="room_amenity_ids" eval="[(4, ref('pms_amenity_0'))]" />
|
||||
@@ -377,7 +412,7 @@
|
||||
<record id="demo_pms_room_type_1" model="pms.room.type">
|
||||
<field name="pms_property_ids" eval="[(4, ref('pms.demo_pms_property'))]" />
|
||||
<field name="name">Prop. Demo Views</field>
|
||||
<field name="code_type">VIE</field>
|
||||
<field name="default_code">VIE</field>
|
||||
<field name="list_price">20.00</field>
|
||||
<field name="class_id" ref="pms_room_type_class_0" />
|
||||
<field
|
||||
|
||||
@@ -619,10 +619,10 @@ msgid "Arrival Hour (GMT)"
|
||||
msgstr "Hora de Llegada (GMT)"
|
||||
|
||||
#. module: pms
|
||||
#: model:ir.model.fields,help:pms.field_pms_room__floor_id
|
||||
#: model:ir.model.fields,help:pms.field_pms_shared_room__floor_id
|
||||
msgid "At which floor the room is located."
|
||||
msgstr "Piso en el que está localizada la habitación."
|
||||
#: model:ir.model.fields,help:pms.field_pms_room__ubication_id
|
||||
#: model:ir.model.fields,help:pms.field_pms_shared_room__ubication_id
|
||||
msgid "At which ubication the room is located."
|
||||
msgstr "Ubicación en la que está localizada la habitación."
|
||||
|
||||
#. module: pms
|
||||
#: model:ir.model.fields,field_description:pms.field_pms_folio__message_attachment_count
|
||||
@@ -1436,7 +1436,7 @@ msgstr "Creado por"
|
||||
#: model:ir.model.fields,field_description:pms.field_pms_board_service_room_type_line__create_uid
|
||||
#: model:ir.model.fields,field_description:pms.field_pms_cancelation_rule__create_uid
|
||||
#: model:ir.model.fields,field_description:pms.field_pms_checkin_partner__create_uid
|
||||
#: model:ir.model.fields,field_description:pms.field_pms_floor__create_uid
|
||||
#: model:ir.model.fields,field_description:pms.field_pms_ubication__create_uid
|
||||
#: model:ir.model.fields,field_description:pms.field_pms_folio__create_uid
|
||||
#: model:ir.model.fields,field_description:pms.field_pms_folio_availability_wizard__create_uid
|
||||
#: model:ir.model.fields,field_description:pms.field_pms_folio_wizard__create_uid
|
||||
@@ -1473,7 +1473,7 @@ msgstr "Creado por"
|
||||
#: model:ir.model.fields,field_description:pms.field_pms_board_service_room_type_line__create_date
|
||||
#: model:ir.model.fields,field_description:pms.field_pms_cancelation_rule__create_date
|
||||
#: model:ir.model.fields,field_description:pms.field_pms_checkin_partner__create_date
|
||||
#: model:ir.model.fields,field_description:pms.field_pms_floor__create_date
|
||||
#: model:ir.model.fields,field_description:pms.field_pms_ubication__create_date
|
||||
#: model:ir.model.fields,field_description:pms.field_pms_folio__create_date
|
||||
#: model:ir.model.fields,field_description:pms.field_pms_folio_availability_wizard__create_date
|
||||
#: model:ir.model.fields,field_description:pms.field_pms_folio_wizard__create_date
|
||||
@@ -1856,7 +1856,7 @@ msgstr "Descuento por cancelación"
|
||||
#: model:ir.model.fields,field_description:pms.field_pms_board_service_room_type_line__display_name
|
||||
#: model:ir.model.fields,field_description:pms.field_pms_cancelation_rule__display_name
|
||||
#: model:ir.model.fields,field_description:pms.field_pms_checkin_partner__display_name
|
||||
#: model:ir.model.fields,field_description:pms.field_pms_floor__display_name
|
||||
#: model:ir.model.fields,field_description:pms.field_pms_ubication__display_name
|
||||
#: model:ir.model.fields,field_description:pms.field_pms_folio__display_name
|
||||
#: model:ir.model.fields,field_description:pms.field_pms_folio_availability_wizard__display_name
|
||||
#: model:ir.model.fields,field_description:pms.field_pms_folio_wizard__display_name
|
||||
@@ -2107,7 +2107,7 @@ msgid "First Day"
|
||||
msgstr "Primer Día"
|
||||
|
||||
#. module: pms
|
||||
#: model:pms.floor,name:pms.pms_floor_1
|
||||
#: model:pms.ubication,name:pms.pms_ubication_1
|
||||
msgid "First Floor"
|
||||
msgstr "Primer Piso"
|
||||
|
||||
@@ -2124,7 +2124,7 @@ msgid "Fixed"
|
||||
msgstr "Fijo"
|
||||
|
||||
#. module: pms
|
||||
#: model:ir.actions.act_window,name:pms.open_pms_floor_form_tree
|
||||
#: model:ir.actions.act_window,name:pms.open_pms_ubication_form_tree
|
||||
msgid "Floor Structure"
|
||||
msgstr "Estructura del Piso"
|
||||
|
||||
@@ -2360,7 +2360,7 @@ msgid "Gives the different ways to package the same product."
|
||||
msgstr "Ofrece diferentes formas de empaquetar el mismo producto."
|
||||
|
||||
#. module: pms
|
||||
#: model:pms.floor,name:pms.pms_floor_0
|
||||
#: model:pms.ubication,name:pms.pms_ubication_0
|
||||
msgid "Ground Floor"
|
||||
msgstr "Planta Baja"
|
||||
|
||||
@@ -2463,7 +2463,7 @@ msgstr "Nombre del huésped"
|
||||
#: model:ir.model.fields,field_description:pms.field_pms_board_service_room_type_line__id
|
||||
#: model:ir.model.fields,field_description:pms.field_pms_cancelation_rule__id
|
||||
#: model:ir.model.fields,field_description:pms.field_pms_checkin_partner__id
|
||||
#: model:ir.model.fields,field_description:pms.field_pms_floor__id
|
||||
#: model:ir.model.fields,field_description:pms.field_pms_ubication__id
|
||||
#: model:ir.model.fields,field_description:pms.field_pms_folio__id
|
||||
#: model:ir.model.fields,field_description:pms.field_pms_folio_availability_wizard__id
|
||||
#: model:ir.model.fields,field_description:pms.field_pms_folio_wizard__id
|
||||
@@ -3020,7 +3020,7 @@ msgstr "Lenguaje"
|
||||
#: model:ir.model.fields,field_description:pms.field_pms_board_service_room_type_line____last_update
|
||||
#: model:ir.model.fields,field_description:pms.field_pms_cancelation_rule____last_update
|
||||
#: model:ir.model.fields,field_description:pms.field_pms_checkin_partner____last_update
|
||||
#: model:ir.model.fields,field_description:pms.field_pms_floor____last_update
|
||||
#: model:ir.model.fields,field_description:pms.field_pms_ubication____last_update
|
||||
#: model:ir.model.fields,field_description:pms.field_pms_folio____last_update
|
||||
#: model:ir.model.fields,field_description:pms.field_pms_folio_availability_wizard____last_update
|
||||
#: model:ir.model.fields,field_description:pms.field_pms_folio_wizard____last_update
|
||||
@@ -3064,7 +3064,7 @@ msgstr "Última modificación en"
|
||||
#: model:ir.model.fields,field_description:pms.field_pms_board_service_room_type_line__write_uid
|
||||
#: model:ir.model.fields,field_description:pms.field_pms_cancelation_rule__write_uid
|
||||
#: model:ir.model.fields,field_description:pms.field_pms_checkin_partner__write_uid
|
||||
#: model:ir.model.fields,field_description:pms.field_pms_floor__write_uid
|
||||
#: model:ir.model.fields,field_description:pms.field_pms_ubication__write_uid
|
||||
#: model:ir.model.fields,field_description:pms.field_pms_folio__write_uid
|
||||
#: model:ir.model.fields,field_description:pms.field_pms_folio_availability_wizard__write_uid
|
||||
#: model:ir.model.fields,field_description:pms.field_pms_folio_wizard__write_uid
|
||||
@@ -3101,7 +3101,7 @@ msgstr "Última Actualización por"
|
||||
#: model:ir.model.fields,field_description:pms.field_pms_board_service_room_type_line__write_date
|
||||
#: model:ir.model.fields,field_description:pms.field_pms_cancelation_rule__write_date
|
||||
#: model:ir.model.fields,field_description:pms.field_pms_checkin_partner__write_date
|
||||
#: model:ir.model.fields,field_description:pms.field_pms_floor__write_date
|
||||
#: model:ir.model.fields,field_description:pms.field_pms_ubication__write_date
|
||||
#: model:ir.model.fields,field_description:pms.field_pms_folio__write_date
|
||||
#: model:ir.model.fields,field_description:pms.field_pms_folio_availability_wizard__write_date
|
||||
#: model:ir.model.fields,field_description:pms.field_pms_folio_wizard__write_date
|
||||
@@ -4264,7 +4264,7 @@ msgstr "Prop. Demo Vistas"
|
||||
#: model:ir.model.fields,field_description:pms.field_pms_board_service_line__pms_property_ids
|
||||
#: model:ir.model.fields,field_description:pms.field_pms_board_service_room_type__pms_property_ids
|
||||
#: model:ir.model.fields,field_description:pms.field_pms_cancelation_rule__pms_property_ids
|
||||
#: model:ir.model.fields,field_description:pms.field_pms_floor__pms_property_ids
|
||||
#: model:ir.model.fields,field_description:pms.field_pms_ubication__pms_property_ids
|
||||
#: model:ir.model.fields,field_description:pms.field_pms_room_type__pms_property_ids
|
||||
#: model:ir.model.fields,field_description:pms.field_pms_room_type_availability_plan__pms_property_ids
|
||||
#: model:ir.model.fields,field_description:pms.field_pms_room_type_class__pms_property_ids
|
||||
@@ -4332,12 +4332,12 @@ msgid "Property Type Class"
|
||||
msgstr "Clase del Tipo de la propiedad"
|
||||
|
||||
#. module: pms
|
||||
#: model_terms:ir.ui.view,arch_db:pms.pms_floor_view_form
|
||||
#: model_terms:ir.ui.view,arch_db:pms.pms_ubication_view_form
|
||||
msgid "Property Ubication"
|
||||
msgstr "Ubicación de la Propiedad"
|
||||
|
||||
#. module: pms
|
||||
#: model_terms:ir.ui.view,arch_db:pms.pms_floor_view_tree
|
||||
#: model_terms:ir.ui.view,arch_db:pms.pms_ubication_view_tree
|
||||
msgid "Property Ubications"
|
||||
msgstr "Ubicaciones de la Propiedad"
|
||||
|
||||
@@ -4912,7 +4912,7 @@ msgid "Search"
|
||||
msgstr "Buscar"
|
||||
|
||||
#. module: pms
|
||||
#: model:pms.floor,name:pms.pms_floor_2
|
||||
#: model:pms.ubication,name:pms.pms_ubication_2
|
||||
msgid "Second Floor"
|
||||
msgstr "Segundo Piso"
|
||||
|
||||
@@ -4971,7 +4971,7 @@ msgstr "Self"
|
||||
#. module: pms
|
||||
#: model:ir.model,name:pms.model_ir_sequence
|
||||
#: model:ir.model.fields,field_description:pms.field_folio_sale_line__sequence
|
||||
#: model:ir.model.fields,field_description:pms.field_pms_floor__sequence
|
||||
#: model:ir.model.fields,field_description:pms.field_pms_ubication__sequence
|
||||
#: model:ir.model.fields,field_description:pms.field_pms_folio__sequence
|
||||
#: model:ir.model.fields,field_description:pms.field_pms_room__sequence
|
||||
#: model:ir.model.fields,field_description:pms.field_pms_room_type__sequence
|
||||
@@ -5874,21 +5874,21 @@ msgid "Types"
|
||||
msgstr "Tipos"
|
||||
|
||||
#. module: pms
|
||||
#: model:ir.model,name:pms.model_pms_floor
|
||||
#: model:ir.model.fields,field_description:pms.field_pms_room__floor_id
|
||||
#: model:ir.model.fields,field_description:pms.field_pms_shared_room__floor_id
|
||||
#: model:ir.model,name:pms.model_pms_ubication
|
||||
#: model:ir.model.fields,field_description:pms.field_pms_room__ubication_id
|
||||
#: model:ir.model.fields,field_description:pms.field_pms_shared_room__ubication_id
|
||||
#: model_terms:ir.ui.view,arch_db:pms.pms_room_view_form
|
||||
#: model_terms:ir.ui.view,arch_db:pms.pms_shared_room_view_form
|
||||
msgid "Ubication"
|
||||
msgstr "Ubicación"
|
||||
|
||||
#. module: pms
|
||||
#: model:ir.model.fields,field_description:pms.field_pms_floor__name
|
||||
#: model:ir.model.fields,field_description:pms.field_pms_ubication__name
|
||||
msgid "Ubication Name"
|
||||
msgstr "Nombre de la Ubicación"
|
||||
|
||||
#. module: pms
|
||||
#: model:ir.ui.menu,name:pms.menu_open_pms_floor_form_tree
|
||||
#: model:ir.ui.menu,name:pms.menu_open_pms_ubication_form_tree
|
||||
msgid "Ubications"
|
||||
msgstr "Ubicaciones"
|
||||
|
||||
|
||||
@@ -3,14 +3,13 @@
|
||||
# License AGPL-3.0 or later (http://www.gnu.org/licenses/agpl).
|
||||
|
||||
from . import ir_http
|
||||
from . import ir_sequence
|
||||
from . import ir_config_parameter
|
||||
|
||||
# from . import payment_return
|
||||
from . import pms_board_service_room_type
|
||||
from . import pms_property
|
||||
from . import res_users
|
||||
from . import pms_floor
|
||||
from . import pms_ubication
|
||||
from . import pms_folio
|
||||
from . import pms_reservation
|
||||
from . import pms_room
|
||||
@@ -24,8 +23,8 @@ from . import product_template
|
||||
from . import product_product
|
||||
from . import res_company
|
||||
from . import account_payment
|
||||
from . import pms_room_type_availability_plan
|
||||
from . import pms_room_type_availability_rule
|
||||
from . import pms_availability_plan
|
||||
from . import pms_availability_plan_rule
|
||||
from . import pms_reservation_line
|
||||
from . import pms_checkin_partner
|
||||
from . import product_pricelist
|
||||
@@ -46,4 +45,4 @@ from . import folio_sale_line
|
||||
from . import account_bank_statement_line
|
||||
from . import account_bank_statement
|
||||
from . import account_journal
|
||||
from . import pms_room_type_availability
|
||||
from . import pms_availability
|
||||
|
||||
@@ -1,26 +0,0 @@
|
||||
# Copyright 2017 Dario Lodeiros
|
||||
# License AGPL-3.0 or later (http://www.gnu.org/licenses/agpl).
|
||||
from odoo import _, api, fields, models
|
||||
|
||||
|
||||
class IrSequence(models.Model):
|
||||
_inherit = "ir.sequence"
|
||||
|
||||
pms_property_id = fields.Many2one("pms.property", string="Property")
|
||||
|
||||
@api.model
|
||||
def _next_sequence_property(self, pms_property_id, code):
|
||||
sequence = self.search(
|
||||
[
|
||||
("code", "=", code),
|
||||
("pms_property_id", "=", pms_property_id),
|
||||
]
|
||||
)
|
||||
if not sequence:
|
||||
sequence = self.search(
|
||||
[
|
||||
("code", "=", code),
|
||||
("pms_property_id", "=", False),
|
||||
]
|
||||
)
|
||||
return sequence._next_do() or _("New")
|
||||
@@ -7,56 +7,46 @@ from odoo.exceptions import ValidationError
|
||||
|
||||
class PmsRoomAmenity(models.Model):
|
||||
_name = "pms.amenity"
|
||||
_description = "Room amenities"
|
||||
_description = "Room amenity"
|
||||
|
||||
# Fields declaration
|
||||
name = fields.Char("Amenity Name", translate=True, required=True)
|
||||
pms_property_ids = fields.Many2many(
|
||||
"pms.property",
|
||||
string="Properties",
|
||||
required=False,
|
||||
ondelete="restrict",
|
||||
active = fields.Boolean(
|
||||
string="Active",
|
||||
help="Determines if amenity is active",
|
||||
default=True,
|
||||
)
|
||||
room_amenity_type_id = fields.Many2one(
|
||||
"pms.amenity.type",
|
||||
"Amenity Category",
|
||||
name = fields.Char(
|
||||
string="Amenity Name",
|
||||
help="Amenity Name",
|
||||
required=True,
|
||||
translate=True,
|
||||
)
|
||||
pms_property_ids = fields.Many2many(
|
||||
string="Properties",
|
||||
help="Properties with access to the element;"
|
||||
" if not set, all properties can access",
|
||||
comodel_name="pms.property",
|
||||
relation="pms_amenity_pms_property_rel",
|
||||
column1="amenity_type_id",
|
||||
column2="pms_property_id",
|
||||
)
|
||||
pms_amenity_type_id = fields.Many2one(
|
||||
string="Amenity Category",
|
||||
help="Segment the amenities by categories (multimedia, comfort, etc ...)",
|
||||
comodel_name="pms.amenity.type",
|
||||
domain="['|', ('pms_property_ids', '=', False),('pms_property_ids', 'in', "
|
||||
"pms_property_ids)]",
|
||||
)
|
||||
default_code = fields.Char("Internal Reference")
|
||||
active = fields.Boolean("Active", default=True)
|
||||
|
||||
# TODO: Constrain coherence pms_property_ids with amenity types pms_property_ids
|
||||
allowed_property_ids = fields.Many2many(
|
||||
"pms.property",
|
||||
"allowed_amenity_move_rel",
|
||||
"amenity_id",
|
||||
"property_id",
|
||||
string="Allowed Properties",
|
||||
store=True,
|
||||
readonly=True,
|
||||
compute="_compute_allowed_property_ids",
|
||||
default_code = fields.Char(
|
||||
string="Internal Reference", help="Internal unique identifier of the amenity"
|
||||
)
|
||||
|
||||
@api.depends(
|
||||
"room_amenity_type_id.pms_property_ids",
|
||||
)
|
||||
def _compute_allowed_property_ids(self):
|
||||
for amenity in self:
|
||||
if amenity.room_amenity_type_id.pms_property_ids:
|
||||
amenity.allowed_property_ids = (
|
||||
amenity.room_amenity_type_id.pms_property_ids
|
||||
)
|
||||
else:
|
||||
amenity.allowed_property_ids = False
|
||||
|
||||
@api.constrains(
|
||||
"allowed_property_ids",
|
||||
"pms_amenity_type_id",
|
||||
"pms_property_ids",
|
||||
)
|
||||
def _check_property_integrity(self):
|
||||
for rec in self:
|
||||
if rec.pms_property_ids and rec.allowed_property_ids:
|
||||
for prop in rec.pms_property_ids:
|
||||
if prop not in rec.allowed_property_ids:
|
||||
raise ValidationError(_("Property not allowed in amenity type"))
|
||||
if rec.pms_amenity_type_id and rec.pms_amenity_type_id.pms_property_ids:
|
||||
res = rec.pms_property_ids - rec.pms_amenity_type_id.pms_property_ids
|
||||
if res:
|
||||
raise ValidationError(_("Property not allowed"))
|
||||
|
||||
@@ -1,21 +1,48 @@
|
||||
# Copyright 2017 Alexandre Díaz
|
||||
# Copyright 2017 Dario Lodeiros
|
||||
# License AGPL-3.0 or later (http://www.gnu.org/licenses/agpl).
|
||||
from odoo import fields, models
|
||||
from odoo import _, api, fields, models
|
||||
from odoo.exceptions import ValidationError
|
||||
|
||||
|
||||
class PmsRoomAmenityType(models.Model):
|
||||
_name = "pms.amenity.type"
|
||||
_description = "Amenities Type"
|
||||
_description = "Amenity Type"
|
||||
|
||||
# Fields declaration
|
||||
name = fields.Char("Amenity Type Name", translate=True, required=True)
|
||||
active = fields.Boolean(
|
||||
string="Active",
|
||||
help="Determines if amenity type is active",
|
||||
default=True,
|
||||
)
|
||||
name = fields.Char(
|
||||
string="Amenity Type Name",
|
||||
help="Amenity Type Name",
|
||||
required=True,
|
||||
translate=True,
|
||||
)
|
||||
pms_property_ids = fields.Many2many(
|
||||
"pms.property", string="Properties", required=False, ondelete="restrict"
|
||||
string="Properties",
|
||||
help="Properties with access to the element;"
|
||||
" if not set, all properties can access",
|
||||
comodel_name="pms.property",
|
||||
relation="pms_amenity_type_pms_property_rel",
|
||||
column1="amenity_type_id",
|
||||
column2="pms_property_id",
|
||||
)
|
||||
room_amenity_ids = fields.One2many(
|
||||
"pms.amenity", "room_amenity_type_id", "Amenities in this category"
|
||||
pms_amenity_ids = fields.One2many(
|
||||
string="Amenities In This Category",
|
||||
help="Amenities included in this type",
|
||||
comodel_name="pms.amenity",
|
||||
inverse_name="pms_amenity_type_id",
|
||||
)
|
||||
active = fields.Boolean("Active", default=True)
|
||||
|
||||
# TODO: Constrain coherence pms_property_ids with amenities pms_property_ids
|
||||
@api.constrains(
|
||||
"pms_property_ids",
|
||||
"pms_amenity_ids",
|
||||
)
|
||||
def _check_property_integrity(self):
|
||||
for rec in self:
|
||||
if rec.pms_property_ids:
|
||||
res = rec.pms_amenity_ids.pms_property_ids - rec.pms_property_ids
|
||||
if res:
|
||||
raise ValidationError(_("Property not allowed"))
|
||||
|
||||
@@ -4,39 +4,46 @@ from odoo import _, api, fields, models
|
||||
from odoo.exceptions import ValidationError
|
||||
|
||||
|
||||
class PmsRoomTypeAvailability(models.Model):
|
||||
_name = "pms.room.type.availability"
|
||||
class PmsAvailability(models.Model):
|
||||
_name = "pms.availability"
|
||||
_description = "Room type availability per day"
|
||||
|
||||
room_type_id = fields.Many2one(
|
||||
comodel_name="pms.room.type",
|
||||
string="Room Type",
|
||||
required=True,
|
||||
ondelete="cascade",
|
||||
help="Room type for which availability is indicated",
|
||||
readonly=True,
|
||||
required=True,
|
||||
comodel_name="pms.room.type",
|
||||
ondelete="cascade",
|
||||
)
|
||||
date = fields.Date(
|
||||
string="Date",
|
||||
required=True,
|
||||
help="Date for which availability applies",
|
||||
readonly=True,
|
||||
required=True,
|
||||
)
|
||||
pms_property_id = fields.Many2one(
|
||||
comodel_name="pms.property",
|
||||
string="Property",
|
||||
ondelete="restrict",
|
||||
required=True,
|
||||
help="Property to which the availability is directed",
|
||||
readonly=True,
|
||||
required=True,
|
||||
comodel_name="pms.property",
|
||||
ondelete="restrict",
|
||||
)
|
||||
reservation_line_ids = fields.One2many(
|
||||
string="Reservation Lines",
|
||||
help="They are the lines of the reservation into a reservation,"
|
||||
"they corresponds to the nights",
|
||||
readonly=True,
|
||||
comodel_name="pms.reservation.line",
|
||||
inverse_name="avail_id",
|
||||
readonly=True,
|
||||
)
|
||||
real_avail = fields.Integer(
|
||||
compute="_compute_real_avail",
|
||||
string="Real Avail",
|
||||
help="",
|
||||
store=True,
|
||||
readonly=True,
|
||||
compute="_compute_real_avail",
|
||||
)
|
||||
|
||||
_sql_constraints = [
|
||||
@@ -7,47 +7,120 @@ from odoo.exceptions import ValidationError
|
||||
from odoo.tools import DEFAULT_SERVER_DATE_FORMAT
|
||||
|
||||
|
||||
class PmsRoomTypeAvailability(models.Model):
|
||||
class PmsAvailabilityPlan(models.Model):
|
||||
"""The room type availability is used as a daily availability plan for room types
|
||||
and therefore is related only with one property."""
|
||||
|
||||
_name = "pms.room.type.availability.plan"
|
||||
_name = "pms.availability.plan"
|
||||
_description = "Reservation availability plan"
|
||||
|
||||
# Default methods
|
||||
@api.model
|
||||
def _get_default_pms_property(self):
|
||||
return self.env.user.get_active_property_ids()[0] or None
|
||||
|
||||
# Fields declaration
|
||||
name = fields.Char("Availability Plan Name", required=True)
|
||||
pms_property_ids = fields.Many2many(
|
||||
comodel_name="pms.property",
|
||||
string="Properties",
|
||||
ondelete="restrict",
|
||||
name = fields.Char(
|
||||
string="Availability Plan Name", help="Name of availability plan", required=True
|
||||
)
|
||||
pms_property_ids = fields.Many2many(
|
||||
string="Properties",
|
||||
help="Properties with access to the element;"
|
||||
" if not set, all properties can access",
|
||||
comodel_name="pms.property",
|
||||
relation="pms_availability_plan_pms_property_rel",
|
||||
column1="availability_plan_id",
|
||||
column2="pms_property_id",
|
||||
)
|
||||
|
||||
pms_pricelist_ids = fields.One2many(
|
||||
string="Pricelists",
|
||||
help="Pricelists of the availability plan ",
|
||||
comodel_name="product.pricelist",
|
||||
inverse_name="availability_plan_id",
|
||||
string="Pricelists",
|
||||
required=False,
|
||||
)
|
||||
|
||||
rule_ids = fields.One2many(
|
||||
comodel_name="pms.room.type.availability.rule",
|
||||
inverse_name="availability_plan_id",
|
||||
string="Availability Rules",
|
||||
help="Rules in a availability plan",
|
||||
comodel_name="pms.availability.plan.rule",
|
||||
inverse_name="availability_plan_id",
|
||||
)
|
||||
|
||||
active = fields.Boolean(
|
||||
string="Active",
|
||||
default=True,
|
||||
help="If unchecked, it will allow you to hide the "
|
||||
"Availability plan without removing it.",
|
||||
default=True,
|
||||
)
|
||||
|
||||
# Business Methods
|
||||
@api.model
|
||||
def get_count_rooms_available(
|
||||
self,
|
||||
checkin,
|
||||
checkout,
|
||||
room_type_id,
|
||||
pms_property_id,
|
||||
current_lines=False,
|
||||
pricelist_id=False,
|
||||
):
|
||||
if current_lines and not isinstance(current_lines, list):
|
||||
current_lines = [current_lines]
|
||||
|
||||
avail = self.get_count_real_free_rooms(
|
||||
checkin, checkout, room_type_id, pms_property_id, current_lines
|
||||
)
|
||||
domain_rules = [
|
||||
("date", ">=", checkin),
|
||||
(
|
||||
"date",
|
||||
"<=",
|
||||
checkout,
|
||||
), # TODO: only closed_departure take account checkout date!
|
||||
("room_type_id", "=", room_type_id),
|
||||
("pms_property_id", "=", pms_property_id),
|
||||
]
|
||||
if pricelist_id:
|
||||
pricelist = self.env["product.pricelist"].browse(pricelist_id)
|
||||
if pricelist and pricelist.availability_plan_id:
|
||||
domain_rules.append(
|
||||
("availability_plan_id", "=", pricelist.availability_plan_id.id)
|
||||
)
|
||||
rule_items = self.env["pms.availability.plan.rule"].search(domain_rules)
|
||||
if len(rule_items) > 0:
|
||||
for item in rule_items:
|
||||
if self.any_rule_applies(checkin, checkout, item):
|
||||
return 0
|
||||
avail = min(rule_items.mapped("plan_avail"))
|
||||
return avail
|
||||
|
||||
def get_count_real_free_rooms(
|
||||
self,
|
||||
checkin,
|
||||
checkout,
|
||||
room_type_id,
|
||||
pms_property_id,
|
||||
current_lines=False,
|
||||
):
|
||||
Avail = self.env["pms.availability"]
|
||||
count_free_rooms = len(self.env["pms.room.type"].browse(room_type_id).room_ids)
|
||||
if isinstance(checkin, str):
|
||||
checkin = datetime.datetime.strptime(
|
||||
checkin, DEFAULT_SERVER_DATE_FORMAT
|
||||
).date()
|
||||
if isinstance(checkout, str):
|
||||
checkout = datetime.datetime.strptime(
|
||||
checkout, DEFAULT_SERVER_DATE_FORMAT
|
||||
).date()
|
||||
for avail in Avail.search(
|
||||
[
|
||||
("date", ">=", checkin),
|
||||
("date", "<=", checkout - datetime.timedelta(1)),
|
||||
("room_type_id", "=", room_type_id),
|
||||
("pms_property_id", "=", pms_property_id),
|
||||
]
|
||||
):
|
||||
if avail.real_avail < count_free_rooms:
|
||||
count_free_rooms = avail.real_avail
|
||||
return count_free_rooms
|
||||
|
||||
@classmethod
|
||||
def any_rule_applies(cls, checkin, checkout, item):
|
||||
reservation_len = (checkout - checkin).days
|
||||
@@ -98,9 +171,7 @@ class PmsRoomTypeAvailability(models.Model):
|
||||
domain_rules.append(
|
||||
("availability_plan_id", "=", pricelist.availability_plan_id.id)
|
||||
)
|
||||
rule_items = self.env["pms.room.type.availability.rule"].search(
|
||||
domain_rules
|
||||
)
|
||||
rule_items = self.env["pms.availability.plan.rule"].search(domain_rules)
|
||||
|
||||
if len(rule_items) > 0:
|
||||
room_types_to_remove = []
|
||||
@@ -122,7 +193,7 @@ class PmsRoomTypeAvailability(models.Model):
|
||||
current_lines=False,
|
||||
pms_property_id=False,
|
||||
):
|
||||
Avail = self.env["pms.room.type.availability"]
|
||||
Avail = self.env["pms.availability"]
|
||||
if isinstance(checkin, str):
|
||||
checkin = datetime.datetime.strptime(
|
||||
checkin, DEFAULT_SERVER_DATE_FORMAT
|
||||
@@ -153,78 +224,6 @@ class PmsRoomTypeAvailability(models.Model):
|
||||
domain_rooms.append(("room_type_id", "=", room_type_id))
|
||||
return self.env["pms.room"].search(domain_rooms)
|
||||
|
||||
@api.model
|
||||
def get_count_rooms_available(
|
||||
self,
|
||||
checkin,
|
||||
checkout,
|
||||
room_type_id,
|
||||
pms_property_id,
|
||||
current_lines=False,
|
||||
pricelist_id=False,
|
||||
):
|
||||
if current_lines and not isinstance(current_lines, list):
|
||||
current_lines = [current_lines]
|
||||
|
||||
avail = self.get_count_real_free_rooms(
|
||||
checkin, checkout, room_type_id, pms_property_id, current_lines
|
||||
)
|
||||
domain_rules = [
|
||||
("date", ">=", checkin),
|
||||
(
|
||||
"date",
|
||||
"<=",
|
||||
checkout,
|
||||
), # TODO: only closed_departure take account checkout date!
|
||||
("room_type_id", "=", room_type_id),
|
||||
("pms_property_id", "=", pms_property_id),
|
||||
]
|
||||
if pricelist_id:
|
||||
pricelist = self.env["product.pricelist"].browse(pricelist_id)
|
||||
if pricelist and pricelist.availability_plan_id:
|
||||
domain_rules.append(
|
||||
("availability_plan_id", "=", pricelist.availability_plan_id.id)
|
||||
)
|
||||
rule_items = self.env["pms.room.type.availability.rule"].search(
|
||||
domain_rules
|
||||
)
|
||||
if len(rule_items) > 0:
|
||||
for item in rule_items:
|
||||
if self.any_rule_applies(checkin, checkout, item):
|
||||
return 0
|
||||
avail = min(rule_items.mapped("plan_avail"))
|
||||
return avail
|
||||
|
||||
def get_count_real_free_rooms(
|
||||
self,
|
||||
checkin,
|
||||
checkout,
|
||||
room_type_id,
|
||||
pms_property_id,
|
||||
current_lines=False,
|
||||
):
|
||||
Avail = self.env["pms.room.type.availability"]
|
||||
count_free_rooms = len(self.env["pms.room.type"].browse(room_type_id).room_ids)
|
||||
if isinstance(checkin, str):
|
||||
checkin = datetime.datetime.strptime(
|
||||
checkin, DEFAULT_SERVER_DATE_FORMAT
|
||||
).date()
|
||||
if isinstance(checkout, str):
|
||||
checkout = datetime.datetime.strptime(
|
||||
checkout, DEFAULT_SERVER_DATE_FORMAT
|
||||
).date()
|
||||
for avail in Avail.search(
|
||||
[
|
||||
("date", ">=", checkin),
|
||||
("date", "<=", checkout - datetime.timedelta(1)),
|
||||
("room_type_id", "=", room_type_id),
|
||||
("pms_property_id", "=", pms_property_id),
|
||||
]
|
||||
):
|
||||
if avail.real_avail < count_free_rooms:
|
||||
count_free_rooms = avail.real_avail
|
||||
return count_free_rooms
|
||||
|
||||
@api.model
|
||||
def splitted_availability(
|
||||
self,
|
||||
@@ -262,7 +261,7 @@ class PmsRoomTypeAvailability(models.Model):
|
||||
@api.model
|
||||
def update_quota(self, pricelist_id, room_type_id, date, line):
|
||||
if pricelist_id and room_type_id and date:
|
||||
rule = self.env["pms.room.type.availability.rule"].search(
|
||||
rule = self.env["pms.availability.plan.rule"].search(
|
||||
[
|
||||
("availability_plan_id.pms_pricelist_ids", "=", pricelist_id.id),
|
||||
("room_type_id", "=", room_type_id.id),
|
||||
@@ -286,7 +285,7 @@ class PmsRoomTypeAvailability(models.Model):
|
||||
rule.quota -= 1
|
||||
|
||||
# check old rule item
|
||||
old_rule = self.env["pms.room.type.availability.rule"].search(
|
||||
old_rule = self.env["pms.availability.plan.rule"].search(
|
||||
[("id", "=", line.impacts_quota)]
|
||||
)
|
||||
|
||||
@@ -298,7 +297,7 @@ class PmsRoomTypeAvailability(models.Model):
|
||||
|
||||
# in any case, check old rule item
|
||||
if line.impacts_quota:
|
||||
old_rule = self.env["pms.room.type.availability.rule"].search(
|
||||
old_rule = self.env["pms.availability.plan.rule"].search(
|
||||
[("id", "=", line.impacts_quota)]
|
||||
)
|
||||
# and restore quota in old rule item
|
||||
@@ -4,93 +4,106 @@ from odoo import _, api, fields, models
|
||||
from odoo.exceptions import ValidationError
|
||||
|
||||
|
||||
class PmsRoomTypeAvailabilityRule(models.Model):
|
||||
_name = "pms.room.type.availability.rule"
|
||||
class PmsAvailabilityPlanRule(models.Model):
|
||||
_name = "pms.availability.plan.rule"
|
||||
_description = "Reservation rule by day"
|
||||
|
||||
# Field Declarations
|
||||
|
||||
availability_plan_id = fields.Many2one(
|
||||
comodel_name="pms.room.type.availability.plan",
|
||||
string="Availability Plan",
|
||||
ondelete="cascade",
|
||||
help="The availability plan that include the Availabilty Rule",
|
||||
index=True,
|
||||
comodel_name="pms.availability.plan",
|
||||
ondelete="cascade",
|
||||
)
|
||||
room_type_id = fields.Many2one(
|
||||
comodel_name="pms.room.type",
|
||||
string="Room Type",
|
||||
help="Room type for which availability rule is applied",
|
||||
required=True,
|
||||
comodel_name="pms.room.type",
|
||||
ondelete="cascade",
|
||||
)
|
||||
date = fields.Date(string="Date")
|
||||
date = fields.Date(
|
||||
string="Date",
|
||||
help="Date for which availability rule applies",
|
||||
)
|
||||
|
||||
min_stay = fields.Integer(
|
||||
string="Min. Stay",
|
||||
help="Minimum stay",
|
||||
default=0,
|
||||
)
|
||||
min_stay_arrival = fields.Integer(
|
||||
string="Min. Stay Arrival",
|
||||
help="Minimum stay if checkin is today",
|
||||
default=0,
|
||||
)
|
||||
max_stay = fields.Integer(
|
||||
string="Max. Stay",
|
||||
help="Maximum stay",
|
||||
default=0,
|
||||
)
|
||||
max_stay_arrival = fields.Integer(
|
||||
string="Max. Stay Arrival",
|
||||
help="Maximum stay if checkin is today",
|
||||
default=0,
|
||||
)
|
||||
closed = fields.Boolean(
|
||||
string="Closed",
|
||||
help="Indicate if property is closed or not",
|
||||
default=False,
|
||||
)
|
||||
closed_departure = fields.Boolean(
|
||||
string="Closed Departure",
|
||||
help="",
|
||||
default=False,
|
||||
)
|
||||
closed_arrival = fields.Boolean(
|
||||
string="Closed Arrival",
|
||||
help="",
|
||||
default=False,
|
||||
)
|
||||
quota = fields.Integer(
|
||||
string="Quota",
|
||||
store=True,
|
||||
readonly=False,
|
||||
compute="_compute_quota",
|
||||
help="Generic Quota assigned.",
|
||||
readonly=False,
|
||||
store=True,
|
||||
compute="_compute_quota",
|
||||
)
|
||||
max_avail = fields.Integer(
|
||||
string="Max. Availability",
|
||||
store=True,
|
||||
help="Maximum simultaneous availability on own Booking Engine",
|
||||
readonly=False,
|
||||
store=True,
|
||||
compute="_compute_max_avail",
|
||||
help="Maximum simultaneous availability on own Booking Engine.",
|
||||
)
|
||||
pms_property_id = fields.Many2one(
|
||||
comodel_name="pms.property",
|
||||
string="Property",
|
||||
help="Properties with access to the element",
|
||||
ondelete="restrict",
|
||||
required=True,
|
||||
comodel_name="pms.property",
|
||||
)
|
||||
allowed_property_ids = fields.Many2many(
|
||||
"pms.property",
|
||||
"allowed_availability_move_rel",
|
||||
"availability_rule_id",
|
||||
"property_id",
|
||||
string="Allowed Properties",
|
||||
help="Allowed properties for user",
|
||||
store=True,
|
||||
readonly=True,
|
||||
compute="_compute_allowed_property_ids",
|
||||
comodel_name="pms.property",
|
||||
relation="allowed_availability_move_rel",
|
||||
column1="availability_plan_rule_id",
|
||||
column2="property_id",
|
||||
)
|
||||
avail_id = fields.Many2one(
|
||||
string="Avail record",
|
||||
comodel_name="pms.room.type.availability",
|
||||
comodel_name="pms.availability",
|
||||
compute="_compute_avail_id",
|
||||
store=True,
|
||||
readonly=False,
|
||||
ondelete="restrict",
|
||||
)
|
||||
real_avail = fields.Integer(
|
||||
string="Real availability",
|
||||
related="avail_id.real_avail",
|
||||
store="True",
|
||||
)
|
||||
@@ -112,7 +125,7 @@ class PmsRoomTypeAvailabilityRule(models.Model):
|
||||
def _compute_avail_id(self):
|
||||
for record in self:
|
||||
if record.room_type_id and record.pms_property_id and record.date:
|
||||
avail = self.env["pms.room.type.availability"].search(
|
||||
avail = self.env["pms.availability"].search(
|
||||
[
|
||||
("date", "=", record.date),
|
||||
("room_type_id", "=", record.room_type_id.id),
|
||||
@@ -122,7 +135,7 @@ class PmsRoomTypeAvailabilityRule(models.Model):
|
||||
if avail:
|
||||
record.avail_id = avail.id
|
||||
else:
|
||||
record.avail_id = self.env["pms.room.type.availability"].create(
|
||||
record.avail_id = self.env["pms.availability"].create(
|
||||
{
|
||||
"date": record.date,
|
||||
"room_type_id": record.room_type_id.id,
|
||||
@@ -7,23 +7,50 @@ class PmsBoardService(models.Model):
|
||||
_name = "pms.board.service"
|
||||
_description = "Board Services"
|
||||
|
||||
# Fields declaration
|
||||
name = fields.Char("Board Name", translate=True, size=64, required=True, index=True)
|
||||
name = fields.Char(
|
||||
string="Board Service Name",
|
||||
help="Board Service Name",
|
||||
required=True,
|
||||
index=True,
|
||||
size=64,
|
||||
translate=True,
|
||||
)
|
||||
board_service_line_ids = fields.One2many(
|
||||
"pms.board.service.line", "pms_board_service_id"
|
||||
string="Board Service Lines",
|
||||
help="Services included in this Board Service",
|
||||
comodel_name="pms.board.service.line",
|
||||
inverse_name="pms_board_service_id",
|
||||
)
|
||||
pms_property_ids = fields.Many2many(
|
||||
"pms.property", string="Properties", required=False, ondelete="restrict"
|
||||
string="Properties",
|
||||
help="Properties with access to the element;"
|
||||
" if not set, all properties can access",
|
||||
required=False,
|
||||
comodel_name="pms.property",
|
||||
relation="pms_board_service_pms_property_rel",
|
||||
column1="board_service_id",
|
||||
column2="pms_property_id",
|
||||
)
|
||||
pms_board_service_room_type_ids = fields.One2many(
|
||||
"pms.board.service.room.type", "pms_board_service_id"
|
||||
string="Board Services Room Type",
|
||||
help="Board Services Room Type corresponding to this Board Service,"
|
||||
"One board service for several room types",
|
||||
comodel_name="pms.board.service.room.type",
|
||||
inverse_name="pms_board_service_id",
|
||||
)
|
||||
amount = fields.Float(
|
||||
"Amount", digits=("Product Price"), compute="_compute_board_amount", store=True
|
||||
string="Amount",
|
||||
help="Price for this Board Service. "
|
||||
"It corresponds to the sum of his board service lines",
|
||||
store=True,
|
||||
digits=("Product Price"),
|
||||
compute="_compute_board_amount",
|
||||
)
|
||||
|
||||
show_detail_report = fields.Boolean(string="Show Detail Report")
|
||||
# Compute and Search methods
|
||||
show_detail_report = fields.Boolean(
|
||||
string="Show Detail Report",
|
||||
help="True if you want that board service detail to be shown on the report",
|
||||
)
|
||||
|
||||
@api.depends("board_service_line_ids.amount")
|
||||
def _compute_board_amount(self):
|
||||
|
||||
@@ -8,24 +8,37 @@ class PmsBoardServiceLine(models.Model):
|
||||
_name = "pms.board.service.line"
|
||||
_description = "Services on Board Service included"
|
||||
|
||||
# Default methods
|
||||
pms_board_service_id = fields.Many2one(
|
||||
string="Board Service",
|
||||
help="Board Service in which this line is included",
|
||||
required=True,
|
||||
comodel_name="pms.board.service",
|
||||
ondelete="cascade",
|
||||
)
|
||||
product_id = fields.Many2one(
|
||||
string="Product",
|
||||
help="Product associated with this board service line",
|
||||
required=True,
|
||||
comodel_name="product.product",
|
||||
)
|
||||
pms_property_ids = fields.Many2many(
|
||||
string="Properties",
|
||||
help="Properties with access to the element;"
|
||||
" if not set, all properties can access",
|
||||
comodel_name="pms.property",
|
||||
related="pms_board_service_id.pms_property_ids",
|
||||
)
|
||||
amount = fields.Float(
|
||||
string="Amount",
|
||||
help="Price for this Board Service Line/Product",
|
||||
default=lambda self: self._get_default_price(),
|
||||
digits=("Product Price"),
|
||||
)
|
||||
|
||||
def _get_default_price(self):
|
||||
if self.product_id:
|
||||
return self.product_id.list_price
|
||||
|
||||
# Fields declaration
|
||||
pms_board_service_id = fields.Many2one(
|
||||
"pms.board.service", "Board Service", ondelete="cascade", required=True
|
||||
)
|
||||
product_id = fields.Many2one("product.product", string="Product", required=True)
|
||||
pms_property_ids = fields.Many2many(
|
||||
"pms.property", related="pms_board_service_id.pms_property_ids"
|
||||
)
|
||||
amount = fields.Float(
|
||||
"Amount", digits=("Product Price"), default=_get_default_price
|
||||
)
|
||||
|
||||
# Constraints and onchanges
|
||||
@api.onchange("product_id")
|
||||
def onchange_product_id(self):
|
||||
if self.product_id:
|
||||
|
||||
@@ -11,41 +11,54 @@ class PmsBoardServiceRoomType(models.Model):
|
||||
_log_access = False
|
||||
_description = "Board Service included in Room"
|
||||
|
||||
# Fields declaration
|
||||
pms_board_service_id = fields.Many2one(
|
||||
"pms.board.service",
|
||||
string="Board Service",
|
||||
index=True,
|
||||
ondelete="cascade",
|
||||
help="Board Service corresponding to this Board Service Room Type",
|
||||
required=True,
|
||||
index=True,
|
||||
comodel_name="pms.board.service",
|
||||
ondelete="cascade",
|
||||
)
|
||||
pms_property_ids = fields.Many2many(
|
||||
"pms.property",
|
||||
string="Properties",
|
||||
help="Properties with access to the element; "
|
||||
"if not set, all properties can access",
|
||||
required=False,
|
||||
comodel_name="pms.property",
|
||||
ondelete="restrict",
|
||||
)
|
||||
pms_room_type_id = fields.Many2one(
|
||||
"pms.room.type",
|
||||
string="Room Type",
|
||||
index=True,
|
||||
ondelete="cascade",
|
||||
help="Room Type for which this Board Service is available",
|
||||
required=True,
|
||||
index=True,
|
||||
comodel_name="pms.room.type",
|
||||
domain=[
|
||||
"|",
|
||||
("pms_property_ids", "=", False),
|
||||
("pms_property_ids", "in", pms_property_ids),
|
||||
],
|
||||
ondelete="cascade",
|
||||
)
|
||||
board_service_line_ids = fields.One2many(
|
||||
"pms.board.service.room.type.line", "pms_board_service_room_type_id"
|
||||
string="Board Service Lines",
|
||||
help="Services included in this Board Service",
|
||||
comodel_name="pms.board.service.room.type.line",
|
||||
inverse_name="pms_board_service_room_type_id",
|
||||
)
|
||||
amount = fields.Float(
|
||||
"Amount", digits=("Product Price"), compute="_compute_board_amount", store=True
|
||||
string="Amount",
|
||||
help="Price for this Board Service. "
|
||||
"It corresponds to the sum of his board service lines",
|
||||
store=True,
|
||||
digits=("Product Price"),
|
||||
compute="_compute_board_amount",
|
||||
)
|
||||
by_default = fields.Boolean(
|
||||
string="Apply by Default",
|
||||
help="Indicates if this board service is applied by default in the room type",
|
||||
)
|
||||
by_default = fields.Boolean("Apply by Default")
|
||||
|
||||
# Compute and Search methods
|
||||
@api.depends("board_service_line_ids.amount")
|
||||
def _compute_board_amount(self):
|
||||
for record in self:
|
||||
@@ -66,8 +79,6 @@ class PmsBoardServiceRoomType(models.Model):
|
||||
if any(default_boards.filtered(lambda l: l.id != record.id)):
|
||||
raise UserError(_("""Only can set one default board service"""))
|
||||
|
||||
# Action methods
|
||||
|
||||
def open_board_lines_form(self):
|
||||
action = (
|
||||
self.env.ref("pms.action_pms_board_service_room_type_view").sudo().read()[0]
|
||||
@@ -79,7 +90,6 @@ class PmsBoardServiceRoomType(models.Model):
|
||||
action["target"] = "new"
|
||||
return action
|
||||
|
||||
# ORM Overrides
|
||||
def init(self):
|
||||
self._cr.execute(
|
||||
"SELECT indexname FROM pg_indexes WHERE indexname = %s",
|
||||
@@ -107,7 +117,6 @@ class PmsBoardServiceRoomType(models.Model):
|
||||
)
|
||||
return super(PmsBoardServiceRoomType, self).write(vals)
|
||||
|
||||
# Business methods
|
||||
@api.model
|
||||
def prepare_board_service_reservation_ids(self, board_service_id):
|
||||
"""
|
||||
|
||||
@@ -10,19 +10,26 @@ class PmsBoardServiceRoomTypeLine(models.Model):
|
||||
|
||||
# Fields declaration
|
||||
pms_board_service_room_type_id = fields.Many2one(
|
||||
"pms.board.service.room.type",
|
||||
"Board Service Room",
|
||||
ondelete="cascade",
|
||||
string="Board Service Room",
|
||||
help="Board Service Room Type in which this line is included",
|
||||
required=True,
|
||||
comodel_name="pms.board.service.room.type",
|
||||
ondelete="cascade",
|
||||
)
|
||||
product_id = fields.Many2one(
|
||||
"product.product",
|
||||
"Product",
|
||||
required=True,
|
||||
string="Product",
|
||||
help="Product associated with this board service room type line",
|
||||
readonly=True,
|
||||
required=True,
|
||||
comodel_name="product.product",
|
||||
)
|
||||
# TODO def default_amount "amount of service"
|
||||
amount = fields.Float("Amount", digits=("Product Price"), default=0.0)
|
||||
amount = fields.Float(
|
||||
string="Amount",
|
||||
help="Price for this Board Service Room Type Line/Product",
|
||||
default=0.0,
|
||||
digits=("Product Price"),
|
||||
)
|
||||
|
||||
@api.constrains("pms_board_service_room_type_id", "product_id")
|
||||
def _check_property_integrity(self):
|
||||
|
||||
@@ -221,10 +221,13 @@ class PmsCheckinPartner(models.Model):
|
||||
)
|
||||
if len(reservation.checkin_partner_ids) < reservation.adults:
|
||||
if vals.get("identifier", _("New")) == _("New") or "identifier" not in vals:
|
||||
vals["identifier"] = self.env["ir.sequence"]._next_sequence_property(
|
||||
pms_property_id=reservation.pms_property_id.id,
|
||||
code="pms.checkin.partner",
|
||||
pms_property_id = (
|
||||
self.env.user.get_active_property_ids()[0]
|
||||
if "pms_property_id" not in vals
|
||||
else vals["pms_property_id"]
|
||||
)
|
||||
pms_property = self.env["pms.property"].browse(pms_property_id)
|
||||
vals["identifier"] = pms_property.folio_sequence_id._next_do()
|
||||
return super(PmsCheckinPartner, self).create(vals)
|
||||
if len(draft_checkins) > 0:
|
||||
draft_checkins[0].write(vals)
|
||||
@@ -291,7 +294,7 @@ class PmsCheckinPartner(models.Model):
|
||||
"arrival": fields.Datetime.now(),
|
||||
}
|
||||
record.update(vals)
|
||||
if record.reservation_id.left_for_checkin:
|
||||
if record.reservation_id.allowed_checkin:
|
||||
record.reservation_id.state = "onboard"
|
||||
|
||||
def action_done(self):
|
||||
|
||||
@@ -1,17 +0,0 @@
|
||||
# Copyright 2017 Dario Lodeiros
|
||||
# License AGPL-3.0 or later (http://www.gnu.org/licenses/agpl).
|
||||
from odoo import fields, models
|
||||
|
||||
|
||||
class PmsFloor(models.Model):
|
||||
_name = "pms.floor"
|
||||
_description = "Ubication"
|
||||
|
||||
# Fields declaration
|
||||
name = fields.Char(
|
||||
"Ubication Name", translate=True, size=64, required=True, index=True
|
||||
)
|
||||
pms_property_ids = fields.Many2many(
|
||||
"pms.property", string="Properties", required=False, ondelete="restrict"
|
||||
)
|
||||
sequence = fields.Integer("Sequence")
|
||||
@@ -123,6 +123,8 @@ class PmsFolio(models.Model):
|
||||
readonly=True,
|
||||
required=True,
|
||||
ondelete="restrict",
|
||||
# comodel_name="res.currency",
|
||||
# compute="_compute_currency_id"
|
||||
)
|
||||
pricelist_id = fields.Many2one(
|
||||
"product.pricelist",
|
||||
@@ -257,6 +259,7 @@ class PmsFolio(models.Model):
|
||||
client_order_ref = fields.Char(string="Customer Reference", copy=False)
|
||||
reservation_type = fields.Selection(
|
||||
[("normal", "Normal"), ("staff", "Staff"), ("out", "Out of Service")],
|
||||
required=True,
|
||||
string="Type",
|
||||
default=lambda *a: "normal",
|
||||
)
|
||||
@@ -510,7 +513,7 @@ class PmsFolio(models.Model):
|
||||
@api.depends("agency_id")
|
||||
def _compute_partner_id(self):
|
||||
for folio in self:
|
||||
if folio.agency_id and folio.agency_id.invoice_agency:
|
||||
if folio.agency_id and folio.agency_id.invoice_to_agency:
|
||||
folio.partner_id = folio.agency_id.id
|
||||
elif not folio.partner_id:
|
||||
folio.partner_id = False
|
||||
@@ -569,6 +572,16 @@ class PmsFolio(models.Model):
|
||||
order.move_ids = invoices
|
||||
order.invoice_count = len(invoices)
|
||||
|
||||
# @api.depends(
|
||||
# "reservation_ids",
|
||||
# "reservation_ids.currency_id"
|
||||
# )
|
||||
# def _compute_currency_id(self):
|
||||
# if len(self.reservation_ids.mapped("currency_id")) == 1:
|
||||
# self.currency_id = self.reservation_ids.mapped("currency_id")
|
||||
# else:
|
||||
# raise UserError(_("Some reservations have different currency"))
|
||||
|
||||
def _compute_access_url(self):
|
||||
super(PmsFolio, self)._compute_access_url()
|
||||
for folio in self:
|
||||
@@ -620,7 +633,6 @@ class PmsFolio(models.Model):
|
||||
other status is met.
|
||||
- to invoice: if any SO line is 'to invoice', the whole SO is 'to invoice'
|
||||
- invoiced: if all SO lines are invoiced, the SO is invoiced.
|
||||
- upselling: if all SO lines are invoiced or upselling, the status is upselling.
|
||||
"""
|
||||
unconfirmed_orders = self.filtered(lambda so: so.state in ["draft"])
|
||||
unconfirmed_orders.invoice_status = "no"
|
||||
@@ -686,7 +698,7 @@ class PmsFolio(models.Model):
|
||||
for folio in self.filtered("reservation_ids"):
|
||||
folio.count_rooms_pending_arrival = len(
|
||||
folio.reservation_ids.filtered(
|
||||
lambda c: c.state in ("draf", "confirm", "no_show")
|
||||
lambda c: c.state in ("draf", "confirm", "arrival_delayed")
|
||||
)
|
||||
)
|
||||
|
||||
@@ -869,7 +881,7 @@ class PmsFolio(models.Model):
|
||||
def action_to_arrive(self):
|
||||
self.ensure_one()
|
||||
reservations = self.reservation_ids.filtered(
|
||||
lambda c: c.state in ("draf", "confirm", "no_show")
|
||||
lambda c: c.state in ("draf", "confirm", "arrival_delayed")
|
||||
)
|
||||
action = self.env.ref("pms.open_pms_reservation_form_tree_all").read()[0]
|
||||
action["domain"] = [("id", "in", reservations.ids)]
|
||||
@@ -884,10 +896,8 @@ class PmsFolio(models.Model):
|
||||
if "pms_property_id" not in vals
|
||||
else vals["pms_property_id"]
|
||||
)
|
||||
vals["name"] = self.env["ir.sequence"]._next_sequence_property(
|
||||
pms_property_id=pms_property_id,
|
||||
code="pms.folio",
|
||||
)
|
||||
pms_property = self.env["pms.property"].browse(pms_property_id)
|
||||
vals["name"] = pms_property.folio_sequence_id._next_do()
|
||||
result = super(PmsFolio, self).create(vals)
|
||||
return result
|
||||
|
||||
|
||||
@@ -18,53 +18,77 @@ class PmsProperty(models.Model):
|
||||
_inherits = {"res.partner": "partner_id"}
|
||||
_check_company_auto = True
|
||||
|
||||
# Fields declaration
|
||||
partner_id = fields.Many2one(
|
||||
"res.partner", "Property", required=True, delegate=True, ondelete="cascade"
|
||||
string="Property",
|
||||
help="Current property",
|
||||
comodel_name="res.partner",
|
||||
required=True,
|
||||
ondelete="cascade",
|
||||
)
|
||||
company_id = fields.Many2one(
|
||||
"res.company",
|
||||
required=True,
|
||||
string="Company",
|
||||
help="The company that owns or operates this property.",
|
||||
comodel_name="res.company",
|
||||
required=True,
|
||||
)
|
||||
user_ids = fields.Many2many(
|
||||
"res.users",
|
||||
"pms_property_users_rel",
|
||||
"pms_property_id",
|
||||
"user_id",
|
||||
string="Accepted Users",
|
||||
help="Field related to res.users. Allowed users on the property",
|
||||
comodel_name="res.users",
|
||||
relation="pms_property_users_rel",
|
||||
column1="pms_property_id",
|
||||
column2="user_id",
|
||||
)
|
||||
room_ids = fields.One2many("pms.room", "pms_property_id", "Rooms")
|
||||
room_ids = fields.One2many(
|
||||
string="Rooms",
|
||||
help="Rooms that a property has.",
|
||||
comodel_name="pms.room",
|
||||
inverse_name="pms_property_id",
|
||||
)
|
||||
# TODO: establecer tarifa publica por defecto
|
||||
default_pricelist_id = fields.Many2one(
|
||||
"product.pricelist",
|
||||
string="Product Pricelist",
|
||||
required=True,
|
||||
help="The default pricelist used in this property.",
|
||||
comodel_name="product.pricelist",
|
||||
required=True,
|
||||
default=lambda self: self.env.ref("product.list0").id,
|
||||
)
|
||||
default_arrival_hour = fields.Char(
|
||||
"Arrival Hour (GMT)", help="HH:mm Format", default="14:00"
|
||||
string="Arrival Hour", help="HH:mm Format", default="14:00"
|
||||
)
|
||||
default_departure_hour = fields.Char(
|
||||
"Departure Hour (GMT)", help="HH:mm Format", default="12:00"
|
||||
string="Departure Hour", help="HH:mm Format", default="12:00"
|
||||
)
|
||||
default_cancel_policy_days = fields.Integer("Cancellation Days")
|
||||
default_cancel_policy_percent = fields.Float("Percent to pay")
|
||||
folio_sequence_id = fields.Many2one(
|
||||
"ir.sequence", "Folio Sequence", check_company=True, copy=False
|
||||
string="Folio Sequence",
|
||||
help="The sequence that formed the name of the folio.",
|
||||
check_company=True,
|
||||
copy=False,
|
||||
comodel_name="ir.sequence",
|
||||
)
|
||||
reservation_sequence_id = fields.Many2one(
|
||||
string="Reservation Sequence",
|
||||
help="The sequence that formed the name of the reservation.",
|
||||
check_company=True,
|
||||
copy=False,
|
||||
comodel_name="ir.sequence",
|
||||
)
|
||||
checkin_sequence_id = fields.Many2one(
|
||||
"ir.sequence", "Checkin Sequence", check_company=True, copy=False
|
||||
)
|
||||
tz = fields.Selection(
|
||||
_tz_get,
|
||||
string="Timezone",
|
||||
required=True,
|
||||
default=lambda self: self.env.user.tz or "UTC",
|
||||
help="This field is used in order to define \
|
||||
in which timezone the arrival/departure will work.",
|
||||
string="Checkin Sequence",
|
||||
help="Field used to create the name of the checkin partner",
|
||||
check_company=True,
|
||||
copy=False,
|
||||
comodel_name="ir.sequence",
|
||||
)
|
||||
|
||||
tz = fields.Selection(
|
||||
string="Timezone",
|
||||
help="This field is used to determine de timezone of the property.",
|
||||
required=True,
|
||||
default=lambda self: self.env.user.tz or "UTC",
|
||||
selection=_tz_get,
|
||||
)
|
||||
|
||||
# Constraints and onchanges
|
||||
@api.constrains("default_arrival_hour")
|
||||
def _check_arrival_hour(self):
|
||||
for record in self:
|
||||
@@ -93,15 +117,15 @@ class PmsProperty(models.Model):
|
||||
)
|
||||
)
|
||||
|
||||
def date_property_timezone(self, date):
|
||||
def date_property_timezone(self, dt):
|
||||
self.ensure_one()
|
||||
tz_property = self.tz
|
||||
date = pytz.timezone(tz_property).localize(date)
|
||||
date = date.replace(tzinfo=None)
|
||||
date = pytz.timezone(self.env.user.tz).localize(date)
|
||||
date = date.astimezone(pytz.utc)
|
||||
date = date.replace(tzinfo=None)
|
||||
return date
|
||||
dt = pytz.timezone(tz_property).localize(dt)
|
||||
dt = dt.replace(tzinfo=None)
|
||||
dt = pytz.timezone(self.env.user.tz).localize(dt)
|
||||
dt = dt.astimezone(pytz.utc)
|
||||
dt = dt.replace(tzinfo=None)
|
||||
return dt
|
||||
|
||||
def _get_payment_methods(self):
|
||||
self.ensure_one()
|
||||
@@ -121,3 +145,47 @@ class PmsProperty(models.Model):
|
||||
]
|
||||
)
|
||||
return payment_methods
|
||||
|
||||
@api.model
|
||||
def create(self, vals):
|
||||
name = vals.get("name")
|
||||
if "folio_sequence_id" not in vals or not vals.get("folio_sequence_id"):
|
||||
folio_sequence = self.env["ir.sequence"].create(
|
||||
{
|
||||
"name": "PMS Folio " + name,
|
||||
"code": "pms.folio",
|
||||
"prefix": "F/%(y)s",
|
||||
"suffix": "%(sec)s",
|
||||
"padding": 4,
|
||||
"company_id": vals.get("company_id"),
|
||||
}
|
||||
)
|
||||
vals.update({"folio_sequence_id": folio_sequence.id})
|
||||
if "reservation_sequence_id" not in vals or not vals.get(
|
||||
"reservation_sequence_id"
|
||||
):
|
||||
reservation_sequence = self.env["ir.sequence"].create(
|
||||
{
|
||||
"name": "PMS Reservation " + name,
|
||||
"code": "pms.reservation",
|
||||
"prefix": "R/%(y)s",
|
||||
"suffix": "%(sec)s",
|
||||
"padding": 4,
|
||||
"company_id": vals.get("company_id"),
|
||||
}
|
||||
)
|
||||
vals.update({"reservation_sequence_id": reservation_sequence.id})
|
||||
if "checkin_sequence_id" not in vals or not vals.get("checkin_sequence_id"):
|
||||
checkin_sequence = self.env["ir.sequence"].create(
|
||||
{
|
||||
"name": "PMS Checkin " + name,
|
||||
"code": "pms.checkin.partner",
|
||||
"prefix": "C/%(y)s",
|
||||
"suffix": "%(sec)s",
|
||||
"padding": 4,
|
||||
"company_id": vals.get("company_id"),
|
||||
}
|
||||
)
|
||||
vals.update({"checkin_sequence_id": checkin_sequence.id})
|
||||
record = super(PmsProperty, self).create(vals)
|
||||
return record
|
||||
|
||||
File diff suppressed because it is too large
Load Diff
@@ -15,84 +15,94 @@ class PmsReservationLine(models.Model):
|
||||
_description = "Reservations by day"
|
||||
_order = "date"
|
||||
|
||||
# Default Methods ang Gets
|
||||
|
||||
def name_get(self):
|
||||
result = []
|
||||
for res in self:
|
||||
date = fields.Date.from_string(res.date)
|
||||
name = u"{}/{}".format(date.day, date.month)
|
||||
result.append((res.id, name))
|
||||
return result
|
||||
|
||||
# Fields declaration
|
||||
reservation_id = fields.Many2one(
|
||||
"pms.reservation",
|
||||
string="Reservation",
|
||||
ondelete="cascade",
|
||||
help="It is the reservation in a reservation line",
|
||||
required=True,
|
||||
copy=False,
|
||||
comodel_name="pms.reservation",
|
||||
ondelete="cascade",
|
||||
)
|
||||
room_id = fields.Many2one(
|
||||
"pms.room",
|
||||
string="Room",
|
||||
ondelete="restrict",
|
||||
compute="_compute_room_id",
|
||||
store=True,
|
||||
help="The room of a reservation. ",
|
||||
readonly=False,
|
||||
store=True,
|
||||
compute="_compute_room_id",
|
||||
comodel_name="pms.room",
|
||||
ondelete="restrict",
|
||||
)
|
||||
|
||||
sale_line_ids = fields.Many2many(
|
||||
"folio.sale.line",
|
||||
"reservation_line_sale_line_rel",
|
||||
"reservation_line_id",
|
||||
"sale_line_id",
|
||||
string="Sales Lines",
|
||||
readonly=True,
|
||||
copy=False,
|
||||
comodel_name="folio.sale.line",
|
||||
relation="reservation_line_sale_line_rel",
|
||||
column1="reservation_line_id",
|
||||
column2="sale_line_id",
|
||||
)
|
||||
pms_property_id = fields.Many2one(
|
||||
"pms.property",
|
||||
store=True,
|
||||
string="Property",
|
||||
help="Property with access to the element;"
|
||||
" if not set, all properties can access",
|
||||
readonly=True,
|
||||
store=True,
|
||||
comodel_name="pms.property",
|
||||
related="reservation_id.pms_property_id",
|
||||
)
|
||||
date = fields.Date("Date")
|
||||
state = fields.Selection(related="reservation_id.state")
|
||||
date = fields.Date(
|
||||
string="Date",
|
||||
help="The date of the reservation in reservation line",
|
||||
)
|
||||
state = fields.Selection(
|
||||
string="State",
|
||||
help="State of the reservation line.",
|
||||
related="reservation_id.state",
|
||||
)
|
||||
price = fields.Float(
|
||||
string="Price",
|
||||
help="The price in a reservation line",
|
||||
store=True,
|
||||
digits=("Product Price"),
|
||||
compute="_compute_price",
|
||||
store=True,
|
||||
readonly=False,
|
||||
)
|
||||
cancel_discount = fields.Float(
|
||||
string="Cancelation Discount (%)",
|
||||
digits=("Discount"),
|
||||
default=0.0,
|
||||
compute="_compute_cancel_discount",
|
||||
store=True,
|
||||
help="",
|
||||
readonly=False,
|
||||
default=0.0,
|
||||
store=True,
|
||||
digits=("Discount"),
|
||||
compute="_compute_cancel_discount",
|
||||
)
|
||||
avail_id = fields.Many2one(
|
||||
string="Availability Day",
|
||||
comodel_name="pms.room.type.availability",
|
||||
help="",
|
||||
store=True,
|
||||
comodel_name="pms.availability",
|
||||
ondelete="restrict",
|
||||
compute="_compute_avail_id",
|
||||
store=True,
|
||||
)
|
||||
|
||||
discount = fields.Float(string="Discount (%)", digits=("Discount"), default=0.0)
|
||||
discount = fields.Float(
|
||||
string="Discount (%)",
|
||||
help="",
|
||||
default=0.0,
|
||||
digits=("Discount"),
|
||||
)
|
||||
occupies_availability = fields.Boolean(
|
||||
string="Occupies",
|
||||
compute="_compute_occupies_availability",
|
||||
store=True,
|
||||
help="This record is taken into account to calculate availability",
|
||||
store=True,
|
||||
compute="_compute_occupies_availability",
|
||||
)
|
||||
impacts_quota = fields.Integer(
|
||||
string="Impacts quota",
|
||||
compute="_compute_impact_quota",
|
||||
store=True,
|
||||
help="",
|
||||
readonly=False,
|
||||
store=True,
|
||||
compute="_compute_impact_quota",
|
||||
)
|
||||
|
||||
_sql_constraints = [
|
||||
@@ -104,7 +114,43 @@ class PmsReservationLine(models.Model):
|
||||
),
|
||||
]
|
||||
|
||||
# Compute and Search methods
|
||||
def name_get(self):
|
||||
result = []
|
||||
for res in self:
|
||||
date = fields.Date.from_string(res.date)
|
||||
name = u"{}/{}".format(date.day, date.month)
|
||||
result.append((res.id, name))
|
||||
return result
|
||||
|
||||
def _get_display_price(self, product):
|
||||
if self.reservation_id.pricelist_id.discount_policy == "with_discount":
|
||||
return product.with_context(
|
||||
pricelist=self.reservation_id.pricelist_id.id
|
||||
).price
|
||||
product_context = dict(
|
||||
self.env.context,
|
||||
partner_id=self.reservation_id.partner_id.id,
|
||||
date=self.date,
|
||||
uom=product.uom_id.id,
|
||||
)
|
||||
final_price, rule_id = self.reservation_id.pricelist_id.with_context(
|
||||
product_context
|
||||
).get_product_price_rule(product, 1.0, self.reservation_id.partner_id)
|
||||
base_price, currency = self.with_context(
|
||||
product_context
|
||||
)._get_real_price_currency(
|
||||
product, rule_id, 1, product.uom_id, self.reservation_id.pricelist_id.id
|
||||
)
|
||||
if currency != self.reservation_id.pricelist_id.currency_id:
|
||||
base_price = currency._convert(
|
||||
base_price,
|
||||
self.reservation_id.pricelist_id.currency_id,
|
||||
self.reservation_id.company_id or self.env.company,
|
||||
fields.Date.today(),
|
||||
)
|
||||
# negative discounts (= surcharge) are included in the display price
|
||||
return max(base_price, final_price)
|
||||
|
||||
@api.depends("reservation_id.room_type_id", "reservation_id.preferred_room_id")
|
||||
def _compute_room_id(self):
|
||||
for line in self.filtered("reservation_id.room_type_id").sorted(
|
||||
@@ -116,9 +162,7 @@ class PmsReservationLine(models.Model):
|
||||
# select room_id regardless room_type_id selected on reservation
|
||||
free_room_select = True if reservation.preferred_room_id else False
|
||||
# we get the rooms available for the entire stay
|
||||
rooms_available = self.env[
|
||||
"pms.room.type.availability.plan"
|
||||
].rooms_available(
|
||||
rooms_available = self.env["pms.availability.plan"].rooms_available(
|
||||
checkin=line.reservation_id.checkin,
|
||||
checkout=line.reservation_id.checkout,
|
||||
room_type_id=reservation.room_type_id.id
|
||||
@@ -150,9 +194,7 @@ class PmsReservationLine(models.Model):
|
||||
else:
|
||||
line.room_id = rooms_available[0]
|
||||
# check that the reservation cannot be allocated even by dividing it
|
||||
elif not self.env[
|
||||
"pms.room.type.availability.plan"
|
||||
].splitted_availability(
|
||||
elif not self.env["pms.availability.plan"].splitted_availability(
|
||||
checkin=line.reservation_id.checkin,
|
||||
checkout=line.reservation_id.checkout,
|
||||
room_type_id=line.reservation_id.room_type_id.id,
|
||||
@@ -249,9 +291,7 @@ class PmsReservationLine(models.Model):
|
||||
def _compute_impact_quota(self):
|
||||
for line in self:
|
||||
reservation = line.reservation_id
|
||||
line.impacts_quota = self.env[
|
||||
"pms.room.type.availability.plan"
|
||||
].update_quota(
|
||||
line.impacts_quota = self.env["pms.availability.plan"].update_quota(
|
||||
pricelist_id=reservation.pricelist_id,
|
||||
room_type_id=reservation.room_type_id,
|
||||
date=line.date,
|
||||
@@ -282,7 +322,7 @@ class PmsReservationLine(models.Model):
|
||||
partner=partner.id,
|
||||
quantity=1,
|
||||
date=line.reservation_id.date_order,
|
||||
date_overnight=line.date,
|
||||
consumption_date=line.date,
|
||||
pricelist=reservation.pricelist_id.id,
|
||||
uom=product.uom_id.id,
|
||||
property=reservation.pms_property_id.id,
|
||||
@@ -371,7 +411,7 @@ class PmsReservationLine(models.Model):
|
||||
and record.pms_property_id
|
||||
and record.occupies_availability
|
||||
):
|
||||
avail = self.env["pms.room.type.availability"].search(
|
||||
avail = self.env["pms.availability"].search(
|
||||
[
|
||||
("date", "=", record.date),
|
||||
("room_type_id", "=", record.room_id.room_type_id.id),
|
||||
@@ -381,7 +421,7 @@ class PmsReservationLine(models.Model):
|
||||
if avail:
|
||||
record.avail_id = avail.id
|
||||
else:
|
||||
record.avail_id = self.env["pms.room.type.availability"].create(
|
||||
record.avail_id = self.env["pms.availability"].create(
|
||||
{
|
||||
"date": record.date,
|
||||
"room_type_id": record.room_id.room_type_id.id,
|
||||
@@ -412,35 +452,6 @@ class PmsReservationLine(models.Model):
|
||||
)
|
||||
cancel_lines.day_qty = 0
|
||||
|
||||
def _get_display_price(self, product):
|
||||
if self.reservation_id.pricelist_id.discount_policy == "with_discount":
|
||||
return product.with_context(
|
||||
pricelist=self.reservation_id.pricelist_id.id
|
||||
).price
|
||||
product_context = dict(
|
||||
self.env.context,
|
||||
partner_id=self.reservation_id.partner_id.id,
|
||||
date=self.date,
|
||||
uom=product.uom_id.id,
|
||||
)
|
||||
final_price, rule_id = self.reservation_id.pricelist_id.with_context(
|
||||
product_context
|
||||
).get_product_price_rule(product, 1.0, self.reservation_id.partner_id)
|
||||
base_price, currency = self.with_context(
|
||||
product_context
|
||||
)._get_real_price_currency(
|
||||
product, rule_id, 1, product.uom_id, self.reservation_id.pricelist_id.id
|
||||
)
|
||||
if currency != self.reservation_id.pricelist_id.currency_id:
|
||||
base_price = currency._convert(
|
||||
base_price,
|
||||
self.reservation_id.pricelist_id.currency_id,
|
||||
self.reservation_id.company_id or self.env.company,
|
||||
fields.Date.today(),
|
||||
)
|
||||
# negative discounts (= surcharge) are included in the display price
|
||||
return max(base_price, final_price)
|
||||
|
||||
@api.constrains("room_id")
|
||||
def _check_adults(self):
|
||||
for record in self.filtered("room_id"):
|
||||
|
||||
@@ -16,97 +16,120 @@ class PmsRoom(models.Model):
|
||||
_description = "Property Room"
|
||||
_order = "sequence, room_type_id, name"
|
||||
|
||||
# Defaults and Gets
|
||||
name = fields.Char(
|
||||
string="Room Name",
|
||||
help="Room Name",
|
||||
required=True,
|
||||
)
|
||||
active = fields.Boolean(
|
||||
string="Active", help="Determines if room is active", default=True
|
||||
)
|
||||
sequence = fields.Integer(
|
||||
string="Sequence",
|
||||
help="Field used to change the position of the rooms in tree view."
|
||||
"Changing the position changes the sequence",
|
||||
default=0,
|
||||
)
|
||||
pms_property_id = fields.Many2one(
|
||||
string="Property",
|
||||
help="Properties with access to the element;"
|
||||
" if not set, all properties can access",
|
||||
required=True,
|
||||
default=lambda self: self.env.user.active_property_ids[0],
|
||||
comodel_name="pms.property",
|
||||
ondelete="restrict",
|
||||
)
|
||||
room_type_id = fields.Many2one(
|
||||
string="Property Room Type",
|
||||
help="Unique room type for the rooms",
|
||||
required=True,
|
||||
comodel_name="pms.room.type",
|
||||
domain=[
|
||||
"|",
|
||||
("pms_property_ids", "=", False),
|
||||
(pms_property_id, "in", "pms_property_ids"),
|
||||
],
|
||||
ondelete="restrict",
|
||||
)
|
||||
# TODO: Dario, design shared rooms
|
||||
shared_room_id = fields.Many2one(
|
||||
string="Shared Room",
|
||||
help="The room can be sold by beds",
|
||||
default=False,
|
||||
comodel_name="pms.shared.room",
|
||||
)
|
||||
ubication_id = fields.Many2one(
|
||||
string="Ubication",
|
||||
help="At which ubication the room is located.",
|
||||
comodel_name="pms.ubication",
|
||||
domain=[
|
||||
"|",
|
||||
("pms_property_ids", "=", False),
|
||||
(pms_property_id, "in", "pms_property_ids"),
|
||||
],
|
||||
)
|
||||
capacity = fields.Integer(
|
||||
string="Capacity", help="The maximum number of people that can occupy a room"
|
||||
)
|
||||
extra_beds_allowed = fields.Integer(
|
||||
string="Extra Beds Allowed",
|
||||
help="Number of extra beds allowed in room",
|
||||
required=True,
|
||||
default="0",
|
||||
)
|
||||
description_sale = fields.Text(
|
||||
string="Sale Description",
|
||||
help="A description of the Product that you want to communicate to "
|
||||
" your customers. This description will be copied to every Sales "
|
||||
" Order, Delivery Order and Customer Invoice/Credit Note",
|
||||
translate=True,
|
||||
)
|
||||
|
||||
allowed_property_ids = fields.Many2many(
|
||||
string="Allowed Properties",
|
||||
help="Allowed properties for rooms",
|
||||
store=True,
|
||||
readonly=True,
|
||||
compute="_compute_allowed_property_ids",
|
||||
comodel_name="pms.property",
|
||||
relation="room_property_rel",
|
||||
column1="room_id",
|
||||
column2="property_id",
|
||||
)
|
||||
|
||||
def name_get(self):
|
||||
result = []
|
||||
for room in self:
|
||||
name = room.name
|
||||
if room.room_type_id:
|
||||
name += " [%s]" % room.room_type_id.code_type
|
||||
name += " [%s]" % room.room_type_id.default_code
|
||||
result.append((room.id, name))
|
||||
return result
|
||||
|
||||
# Fields declaration
|
||||
name = fields.Char("Room Name", required=True)
|
||||
pms_property_id = fields.Many2one(
|
||||
"pms.property",
|
||||
required=True,
|
||||
ondelete="restrict",
|
||||
default=lambda self: self.env.user.active_property_ids[0],
|
||||
@api.depends(
|
||||
"room_type_id",
|
||||
"room_type_id.pms_property_ids",
|
||||
"ubication_id",
|
||||
"ubication_id.pms_property_ids",
|
||||
)
|
||||
room_type_id = fields.Many2one(
|
||||
"pms.room.type",
|
||||
"Property Room Type",
|
||||
required=True,
|
||||
ondelete="restrict",
|
||||
domain=[
|
||||
"|",
|
||||
("pms_property_ids", "=", False),
|
||||
(pms_property_id, "in", "pms_property_ids"),
|
||||
],
|
||||
)
|
||||
shared_room_id = fields.Many2one("pms.shared.room", "Shared Room", default=False)
|
||||
floor_id = fields.Many2one(
|
||||
"pms.floor",
|
||||
"Ubication",
|
||||
help="At which floor the room is located.",
|
||||
domain=[
|
||||
"|",
|
||||
("pms_property_ids", "=", False),
|
||||
(pms_property_id, "in", "pms_property_ids"),
|
||||
],
|
||||
)
|
||||
capacity = fields.Integer("Capacity")
|
||||
to_be_cleaned = fields.Boolean("To be Cleaned", default=False)
|
||||
extra_beds_allowed = fields.Integer(
|
||||
"Extra beds allowed", default="0", required=True
|
||||
)
|
||||
description_sale = fields.Text(
|
||||
"Sale Description",
|
||||
translate=True,
|
||||
help="A description of the Product that you want to communicate to "
|
||||
" your customers. This description will be copied to every Sales "
|
||||
" Order, Delivery Order and Customer Invoice/Credit Note",
|
||||
)
|
||||
active = fields.Boolean("Active", default=True)
|
||||
sequence = fields.Integer("Sequence", default=0)
|
||||
|
||||
allowed_property_ids = fields.Many2many(
|
||||
comodel_name="pms.property",
|
||||
relation="room_property_rel",
|
||||
column1="room_id",
|
||||
column2="property_id",
|
||||
string="Allowed properties",
|
||||
store=True,
|
||||
readonly=True,
|
||||
compute="_compute_allowed_property_ids",
|
||||
)
|
||||
|
||||
@api.depends("room_type_id.pms_property_ids", "floor_id.pms_property_ids")
|
||||
# TODO: Dario, revisar flujo de allowed properties
|
||||
def _compute_allowed_property_ids(self):
|
||||
for record in self:
|
||||
if not (
|
||||
record.room_type_id.pms_property_ids or record.floor_id.pms_property_ids
|
||||
record.room_type_id.pms_property_ids
|
||||
or record.ubication_id.pms_property_ids
|
||||
):
|
||||
record.allowed_property_ids = False
|
||||
record.allowed_property_ids = self.env["pms.property"].search([])
|
||||
elif not record.room_type_id.pms_property_ids:
|
||||
record.allowed_property_ids = record.ubication_id.pms_property_ids
|
||||
elif not record.ubication_id.pms_property_ids:
|
||||
record.allowed_property_ids = record.room_type_id.pms_property_ids
|
||||
else:
|
||||
if record.room_type_id.pms_property_ids:
|
||||
if record.floor_id.pms_property_ids:
|
||||
properties = list(
|
||||
set(record.room_type_id.pms_property_ids.ids)
|
||||
& set(record.floor_id.pms_property_ids.ids)
|
||||
)
|
||||
record.allowed_property_ids = self.env["pms.property"].search(
|
||||
[("id", "in", properties)]
|
||||
)
|
||||
else:
|
||||
record.allowed_property_ids = (
|
||||
record.room_type_id.pms_property_ids
|
||||
)
|
||||
else:
|
||||
record.allowed_property_ids = record.floor_id.pms_property_ids
|
||||
record.allowed_property_ids = (
|
||||
record.room_type_id.pms_property_ids
|
||||
& record.ubication_id.pms_property_ids
|
||||
)
|
||||
|
||||
# Constraints and onchanges
|
||||
@api.constrains("capacity")
|
||||
def _check_capacity(self):
|
||||
for record in self:
|
||||
@@ -124,15 +147,18 @@ class PmsRoom(models.Model):
|
||||
)
|
||||
def _check_property_integrity(self):
|
||||
for rec in self:
|
||||
if rec.pms_property_id and rec.allowed_property_ids:
|
||||
if rec.pms_property_id:
|
||||
if rec.pms_property_id.id not in rec.allowed_property_ids.ids:
|
||||
raise ValidationError(
|
||||
_("Property not allowed in room type or in floor")
|
||||
_("Property not allowed in room type or in ubication")
|
||||
)
|
||||
|
||||
# Business methods
|
||||
|
||||
def get_capacity(self, extra_bed=0):
|
||||
if not self.shared_room_id:
|
||||
return self.capacity + extra_bed
|
||||
return self.capacity
|
||||
for record in self:
|
||||
if not record.shared_room_id:
|
||||
if extra_bed > record.extra_beds_allowed:
|
||||
raise ValidationError(
|
||||
_("Extra beds can't be greater than allowed beds for this room")
|
||||
)
|
||||
return record.capacity + extra_bed
|
||||
return record.capacity
|
||||
|
||||
@@ -7,9 +7,24 @@ class RoomClosureReason(models.Model):
|
||||
_name = "room.closure.reason"
|
||||
_description = "Cause of out of service"
|
||||
|
||||
# Fields declaration
|
||||
name = fields.Char("Name", translate=True, required=True)
|
||||
pms_property_ids = fields.Many2many(
|
||||
"pms.property", string="Properties", required=False, ondelete="restrict"
|
||||
name = fields.Char(
|
||||
string="Name",
|
||||
help="The name that identifies the room closure reason",
|
||||
required=True,
|
||||
translate=True,
|
||||
)
|
||||
pms_property_ids = fields.Many2many(
|
||||
string="Properties",
|
||||
help="Properties with access to the element;"
|
||||
" if not set, all properties can access",
|
||||
comodel_name="pms.property",
|
||||
relation="pms_room_closure_reason_pms_property_rel",
|
||||
column1="room_closure_reason_type_id",
|
||||
column2="pms_property_id",
|
||||
ondelete="restrict",
|
||||
)
|
||||
description = fields.Text(
|
||||
string="Description",
|
||||
help="Explanation of the reason for closing a room",
|
||||
translate=True,
|
||||
)
|
||||
description = fields.Text("Description", translate=True)
|
||||
|
||||
@@ -16,17 +16,101 @@ class PmsRoomType(models.Model):
|
||||
_name = "pms.room.type"
|
||||
_description = "Room Type"
|
||||
_inherits = {"product.product": "product_id"}
|
||||
_order = "sequence, code_type, name"
|
||||
_order = "sequence,default_code,name"
|
||||
|
||||
sequence = fields.Integer(
|
||||
string="Sequence",
|
||||
help="Field used to change the position of the room types in tree view.",
|
||||
default=0,
|
||||
)
|
||||
product_id = fields.Many2one(
|
||||
string="Product Room Type",
|
||||
help="Product identifier associated with room type",
|
||||
comodel_name="product.product",
|
||||
required=True,
|
||||
delegate=True,
|
||||
ondelete="cascade",
|
||||
)
|
||||
room_ids = fields.One2many(
|
||||
string="Rooms",
|
||||
help="Rooms that belong to room type.",
|
||||
comodel_name="pms.room",
|
||||
inverse_name="room_type_id",
|
||||
domain="["
|
||||
"'|', "
|
||||
"('pms_property_id', '=', False), "
|
||||
"('pms_property_id','in', pms_property_ids)"
|
||||
"]",
|
||||
)
|
||||
class_id = fields.Many2one(
|
||||
string="Property Type Class",
|
||||
help="Class to which the room type belongs",
|
||||
comodel_name="pms.room.type.class",
|
||||
required=True,
|
||||
domain="["
|
||||
"'|', "
|
||||
"('pms_property_ids', '=', False), "
|
||||
"('pms_property_ids', 'in', pms_property_ids)"
|
||||
"]",
|
||||
)
|
||||
board_service_room_type_ids = fields.One2many(
|
||||
string="Board Services",
|
||||
help="Board Service included in room type",
|
||||
comodel_name="pms.board.service.room.type",
|
||||
inverse_name="pms_room_type_id",
|
||||
domain="['|', ('pms_property_ids', '=', False), ('pms_property_ids', 'in', "
|
||||
"pms_property_ids)]",
|
||||
)
|
||||
room_amenity_ids = fields.Many2many(
|
||||
string="Room Type Amenities",
|
||||
help="List of amenities included in room type",
|
||||
comodel_name="pms.amenity",
|
||||
relation="pms_room_type_amenity_rel",
|
||||
column1="room_type_id",
|
||||
column2="amenity_id",
|
||||
domain="["
|
||||
"'|', "
|
||||
"('pms_property_ids', '=', False), "
|
||||
"('pms_property_ids', 'in', pms_property_ids)"
|
||||
"]",
|
||||
)
|
||||
default_code = fields.Char(
|
||||
string="Code",
|
||||
help="Identification code for a room type",
|
||||
required=True,
|
||||
)
|
||||
# TODO: Session review to define shared room and "sales rooms packs"
|
||||
is_shared_room = fields.Boolean(
|
||||
string="Shared Room",
|
||||
help="This room type is reservation by beds",
|
||||
default=False,
|
||||
)
|
||||
total_rooms_count = fields.Integer(
|
||||
string="Total Rooms Count",
|
||||
help="The number of rooms in a room type",
|
||||
compute="_compute_total_rooms_count",
|
||||
store=True,
|
||||
)
|
||||
default_max_avail = fields.Integer(
|
||||
string="Default Max. Availability",
|
||||
help="Maximum simultaneous availability on own Booking Engine "
|
||||
"given no availability rules. "
|
||||
"Use `-1` for using maximum simultaneous availability.",
|
||||
default=-1,
|
||||
)
|
||||
default_quota = fields.Integer(
|
||||
string="Default Quota",
|
||||
help="Quota assigned to the own Booking Engine given no availability rules. "
|
||||
"Use `-1` for managing no quota.",
|
||||
default=-1,
|
||||
)
|
||||
|
||||
# Defaults and Gets
|
||||
def name_get(self):
|
||||
result = []
|
||||
for room_type in self:
|
||||
name = room_type.name
|
||||
if self._context.get("checkin") and self._context.get("checkout"):
|
||||
avail = self.env[
|
||||
"pms.room.type.availability.plan"
|
||||
].get_count_rooms_available(
|
||||
avail = self.env["pms.availability.plan"].get_count_rooms_available(
|
||||
checkin=self._context.get("checkin"),
|
||||
checkout=self._context.get("checkout"),
|
||||
room_type_id=room_type.id,
|
||||
@@ -37,99 +121,26 @@ class PmsRoomType(models.Model):
|
||||
result.append((room_type.id, name))
|
||||
return result
|
||||
|
||||
# Fields declaration
|
||||
product_id = fields.Many2one(
|
||||
"product.product",
|
||||
"Product Room Type",
|
||||
required=True,
|
||||
delegate=True,
|
||||
ondelete="cascade",
|
||||
)
|
||||
room_ids = fields.One2many(
|
||||
"pms.room",
|
||||
"room_type_id",
|
||||
"Rooms",
|
||||
domain="["
|
||||
"'|', "
|
||||
"('pms_property_id', '=', False), "
|
||||
"('pms_property_id','in', pms_property_ids)"
|
||||
"]",
|
||||
)
|
||||
class_id = fields.Many2one(
|
||||
"pms.room.type.class",
|
||||
"Property Type Class",
|
||||
required=True,
|
||||
domain="["
|
||||
"'|', "
|
||||
"('pms_property_ids', '=', False), "
|
||||
"('pms_property_ids', 'in', pms_property_ids)"
|
||||
"]",
|
||||
)
|
||||
board_service_room_type_ids = fields.One2many(
|
||||
"pms.board.service.room.type",
|
||||
"pms_room_type_id",
|
||||
string="Board Services",
|
||||
domain="['|', ('pms_property_ids', '=', False), ('pms_property_ids', 'in', "
|
||||
"pms_property_ids)]",
|
||||
)
|
||||
room_amenity_ids = fields.Many2many(
|
||||
"pms.amenity",
|
||||
"pms_room_type_aminity_rel",
|
||||
"room_type_ids",
|
||||
"amenity_ids",
|
||||
string="Room Type Amenities",
|
||||
help="List of Amenities.",
|
||||
domain="["
|
||||
"'|', "
|
||||
"('pms_property_ids', '=', False), "
|
||||
"('pms_property_ids', 'in', pms_property_ids)"
|
||||
"]",
|
||||
)
|
||||
code_type = fields.Char(
|
||||
"Code",
|
||||
required=True,
|
||||
)
|
||||
shared_room = fields.Boolean(
|
||||
"Shared Room", default=False, help="This room type is reservation by beds"
|
||||
)
|
||||
total_rooms_count = fields.Integer(compute="_compute_total_rooms", store=True)
|
||||
active = fields.Boolean("Active", default=True)
|
||||
sequence = fields.Integer("Sequence", default=0)
|
||||
default_max_avail = fields.Integer(
|
||||
"Max. Availability",
|
||||
default=-1,
|
||||
help="Maximum simultaneous availability on own Booking Engine "
|
||||
"given no availability rules. "
|
||||
"Use `-1` for using maximum simultaneous availability.",
|
||||
)
|
||||
default_quota = fields.Integer(
|
||||
"Default Quota",
|
||||
default=-1,
|
||||
help="Quota assigned to the own Booking Engine given no availability rules. "
|
||||
"Use `-1` for managing no quota.",
|
||||
)
|
||||
|
||||
# Constraints and onchanges
|
||||
@api.depends("room_ids", "room_ids.active")
|
||||
def _compute_total_rooms(self):
|
||||
def _compute_total_rooms_count(self):
|
||||
for record in self:
|
||||
record.total_rooms_count = len(record.room_ids)
|
||||
|
||||
@api.model
|
||||
def get_unique_by_property_code(self, pms_property_id, code_type=None):
|
||||
def get_room_types_by_property(self, pms_property_id, default_code=None):
|
||||
"""
|
||||
:param pms_property_id: property ID
|
||||
:param code_type: room type code (optional)
|
||||
:param default_code: room type code (optional)
|
||||
:return: - recordset of
|
||||
- all the pms.room.type of the pms_property_id
|
||||
if code_type not defined
|
||||
- one or 0 pms.room.type if code_type defined
|
||||
- ValidationError if more than one code_type found by
|
||||
if default_code not defined
|
||||
- one or 0 pms.room.type if default_code defined
|
||||
- ValidationError if more than one default_code found by
|
||||
the same pms_property_id
|
||||
"""
|
||||
domain = []
|
||||
if code_type:
|
||||
domain += ["&", ("code_type", "=", code_type)]
|
||||
if default_code:
|
||||
domain += ["&", ("default_code", "=", default_code)]
|
||||
company_id = self.env["pms.property"].browse(pms_property_id).company_id.id
|
||||
domain += [
|
||||
"|",
|
||||
@@ -145,18 +156,18 @@ class PmsRoomType(models.Model):
|
||||
records = self.search(domain)
|
||||
res, res_priority = {}, {}
|
||||
for rec in records:
|
||||
res_priority.setdefault(rec.code_type, -1)
|
||||
res_priority.setdefault(rec.default_code, -1)
|
||||
priority = (rec.pms_property_ids and 2) or (rec.company_id and 1 or 0)
|
||||
if priority > res_priority[rec.code_type]:
|
||||
res.setdefault(rec.code_type, rec.id)
|
||||
res[rec.code_type], res_priority[rec.code_type] = rec.id, priority
|
||||
elif priority == res_priority[rec.code_type]:
|
||||
if priority > res_priority[rec.default_code]:
|
||||
res.setdefault(rec.default_code, rec.id)
|
||||
res[rec.default_code], res_priority[rec.default_code] = rec.id, priority
|
||||
elif priority == res_priority[rec.default_code]:
|
||||
raise ValidationError(
|
||||
_(
|
||||
"Integrity error: There's multiple room types "
|
||||
"with the same code %s and properties"
|
||||
)
|
||||
% rec.code_type
|
||||
% rec.default_code
|
||||
)
|
||||
return self.browse(list(res.values()))
|
||||
|
||||
@@ -170,7 +181,7 @@ class PmsRoomType(models.Model):
|
||||
_("Property isn't allowed in Room Type Class")
|
||||
)
|
||||
|
||||
@api.constrains("code_type", "pms_property_ids", "company_id")
|
||||
@api.constrains("default_code", "pms_property_ids", "company_id")
|
||||
def _check_code_property_company_uniqueness(self):
|
||||
msg = _("Already exists another room type with the same code and properties")
|
||||
for rec in self:
|
||||
@@ -178,7 +189,7 @@ class PmsRoomType(models.Model):
|
||||
if self.search(
|
||||
[
|
||||
("id", "!=", rec.id),
|
||||
("code_type", "=", rec.code_type),
|
||||
("default_code", "=", rec.default_code),
|
||||
("pms_property_ids", "=", False),
|
||||
("company_id", "=", rec.company_id.id),
|
||||
]
|
||||
@@ -186,8 +197,8 @@ class PmsRoomType(models.Model):
|
||||
raise ValidationError(msg)
|
||||
else:
|
||||
for pms_property in rec.pms_property_ids:
|
||||
other = rec.get_unique_by_property_code(
|
||||
pms_property.id, rec.code_type
|
||||
other = rec.get_room_types_by_property(
|
||||
pms_property.id, rec.default_code
|
||||
)
|
||||
if other and other != rec:
|
||||
raise ValidationError(msg)
|
||||
@@ -226,12 +237,14 @@ class PmsRoomType(models.Model):
|
||||
)
|
||||
|
||||
# ORM Overrides
|
||||
# TODO: Review Check product fields default values to room
|
||||
@api.model
|
||||
def create(self, vals):
|
||||
""" Add room types as not purchase services. """
|
||||
vals.update(
|
||||
{
|
||||
"purchase_ok": False,
|
||||
"sale_ok": False,
|
||||
"type": "service",
|
||||
}
|
||||
)
|
||||
@@ -242,68 +255,7 @@ class PmsRoomType(models.Model):
|
||||
record.product_id.unlink()
|
||||
return super().unlink()
|
||||
|
||||
# Business methods
|
||||
|
||||
def get_capacity(self):
|
||||
self.ensure_one()
|
||||
capacities = self.room_ids.mapped("capacity")
|
||||
return min(capacities) if any(capacities) else 0
|
||||
|
||||
@api.model
|
||||
def get_rate_room_types(self, **kwargs):
|
||||
"""
|
||||
room_type_ids: Ids from room types to get rate, optional, if you
|
||||
not use this param, the method return all room_types
|
||||
from: Date from, mandatory
|
||||
days: Number of days, mandatory
|
||||
pricelist_id: Pricelist to use, optional
|
||||
partner_id: Partner, optional
|
||||
Return Dict Code Room Types: subdict with day, discount, price
|
||||
"""
|
||||
vals = {}
|
||||
# room_type_ids = kwargs.get("room_type_ids", False)
|
||||
# room_types = (
|
||||
# self.env["pms.room.type"].browse(room_type_ids)
|
||||
# if room_type_ids
|
||||
# else self.env["pms.room.type"].search([])
|
||||
# )
|
||||
date_from = kwargs.get("date_from", False)
|
||||
days = kwargs.get("days", False)
|
||||
discount = kwargs.get("discount", False)
|
||||
if not date_from or not days:
|
||||
raise ValidationError(_("Date From and days are mandatory"))
|
||||
partner_id = kwargs.get("partner_id", False)
|
||||
# partner = self.env["res.partner"].browse(partner_id)
|
||||
# pricelist_id = kwargs.get(
|
||||
# "pricelist_id",
|
||||
# partner.property_product_pricelist.id
|
||||
# and partner.property_product_pricelist.id
|
||||
# or self.env.user.pms_property_id.default_pricelist_id.id,
|
||||
# )
|
||||
vals.update(
|
||||
{
|
||||
"partner_id": partner_id if partner_id else False,
|
||||
"discount": discount,
|
||||
}
|
||||
)
|
||||
rate_vals = {}
|
||||
# TODO: Now it is computed field, We need other way to return rates
|
||||
# for room_type in room_types:
|
||||
# vals.update({"room_type_id": room_type.id})
|
||||
# room_vals = self.env["pms.reservation"].prepare_reservation_lines(
|
||||
# date_from,
|
||||
# days,
|
||||
# pricelist_id=pricelist_id,
|
||||
# vals=vals,
|
||||
# update_old_prices=False,
|
||||
# )
|
||||
# rate_vals.update(
|
||||
# {
|
||||
# room_type.id: [
|
||||
# item[2] for item in room_vals[
|
||||
# "reservation_line_ids"
|
||||
# ] if item[2]
|
||||
# ]
|
||||
# }
|
||||
# )
|
||||
return rate_vals
|
||||
|
||||
@@ -17,16 +17,41 @@ class PmsRoomTypeClass(models.Model):
|
||||
_description = "Room Type Class"
|
||||
_order = "sequence, name, code_class"
|
||||
|
||||
# Fields declaration
|
||||
name = fields.Char("Class Name", required=True, translate=True)
|
||||
# Relationship between models
|
||||
pms_property_ids = fields.Many2many(
|
||||
"pms.property", string="Properties", required=False, ondelete="restrict"
|
||||
name = fields.Char(
|
||||
string="Class Name",
|
||||
help="Name of the room type class",
|
||||
required=True,
|
||||
translate=True,
|
||||
)
|
||||
active = fields.Boolean(
|
||||
string="Active",
|
||||
help="If unchecked, it will allow you to hide the room type",
|
||||
default=True,
|
||||
)
|
||||
sequence = fields.Integer(
|
||||
string="Sequence",
|
||||
help="Field used to change the position of the room type classes in tree view.",
|
||||
default=0,
|
||||
)
|
||||
pms_property_ids = fields.Many2many(
|
||||
string="Properties",
|
||||
help="Properties with access to the element;"
|
||||
" if not set, all properties can access",
|
||||
comodel_name="pms.property",
|
||||
relation="pms_room_type_class_property_rel",
|
||||
column1="room_type_class_id",
|
||||
column2="pms_property_id",
|
||||
ondelete="restrict",
|
||||
)
|
||||
room_type_ids = fields.One2many(
|
||||
string="Types",
|
||||
help="Room Types that belong to this Room Type Class",
|
||||
comodel_name="pms.room.type",
|
||||
inverse_name="class_id",
|
||||
)
|
||||
code_class = fields.Char(
|
||||
string="Code", help="Room type class identification code", required=True
|
||||
)
|
||||
room_type_ids = fields.One2many("pms.room.type", "class_id", "Types")
|
||||
code_class = fields.Char("Code", required=True)
|
||||
active = fields.Boolean("Active", default=True)
|
||||
sequence = fields.Integer("Sequence", default=0)
|
||||
|
||||
@api.model
|
||||
def get_unique_by_property_code(self, pms_property_id, code_class=None):
|
||||
|
||||
@@ -5,10 +5,22 @@ class PmsSaleChannel(models.Model):
|
||||
_name = "pms.sale.channel"
|
||||
_description = "Sales Channel"
|
||||
|
||||
# Fields declaration
|
||||
name = fields.Text(string="Sale Channel Name")
|
||||
name = fields.Text(string="Sale Channel Name", help="The name of the sale channel")
|
||||
channel_type = fields.Selection(
|
||||
[("direct", "Direct"), ("indirect", "Indirect")], string="Sale Channel Type"
|
||||
string="Sale Channel Type",
|
||||
help="Type of sale channel; it can be 'direct'(if there is"
|
||||
"no intermediary) or 'indirect'(if there are"
|
||||
"intermediaries between partner and property",
|
||||
selection=[("direct", "Direct"), ("indirect", "Indirect")],
|
||||
)
|
||||
is_on_line = fields.Boolean(
|
||||
string="On Line", help="Indicates if the sale channel is on-line"
|
||||
)
|
||||
product_pricelist_ids = fields.Many2many(
|
||||
string="Pricelists",
|
||||
help="Pricelists for a sale channel",
|
||||
comodel_name="product.pricelist",
|
||||
relation="pms_sale_channel_product_pricelist_rel",
|
||||
column1="pms_sale_channel_id",
|
||||
column2="product_pricelist_id",
|
||||
)
|
||||
on_line = fields.Boolean("On Line")
|
||||
product_pricelist_ids = fields.Many2many("product.pricelist", string="Pricelists")
|
||||
|
||||
@@ -13,135 +13,239 @@ class PmsService(models.Model):
|
||||
_name = "pms.service"
|
||||
_description = "Services and its charges"
|
||||
|
||||
# Default methods
|
||||
|
||||
def name_get(self):
|
||||
result = []
|
||||
for rec in self:
|
||||
name = []
|
||||
name.append("{name}".format(name=rec.name))
|
||||
if rec.reservation_id.name:
|
||||
name.append("{name}".format(name=rec.reservation_id.name))
|
||||
result.append((rec.id, ", ".join(name)))
|
||||
return result
|
||||
|
||||
@api.model
|
||||
def _default_reservation_id(self):
|
||||
if self.env.context.get("reservation_ids"):
|
||||
ids = [item[1] for item in self.env.context["reservation_ids"]]
|
||||
return self.env["pms.reservation"].browse([(ids)], limit=1)
|
||||
elif self.env.context.get("default_reservation_id"):
|
||||
return self.env.context.get("default_reservation_id")
|
||||
return False
|
||||
|
||||
# Fields declaration
|
||||
name = fields.Char(
|
||||
"Service description",
|
||||
compute="_compute_name",
|
||||
store=True,
|
||||
string="Service description",
|
||||
help="Service description",
|
||||
readonly=False,
|
||||
store=True,
|
||||
compute="_compute_name",
|
||||
)
|
||||
product_id = fields.Many2one(
|
||||
"product.product", "Service", ondelete="restrict", required=True
|
||||
string="Service",
|
||||
help="Product associated with this service",
|
||||
required=True,
|
||||
comodel_name="product.product",
|
||||
ondelete="restrict",
|
||||
)
|
||||
folio_id = fields.Many2one(
|
||||
comodel_name="pms.folio",
|
||||
string="Folio",
|
||||
compute="_compute_folio_id",
|
||||
help="Folio in which the service is included",
|
||||
readonly=False,
|
||||
store=True,
|
||||
comodel_name="pms.folio",
|
||||
compute="_compute_folio_id",
|
||||
)
|
||||
sale_line_ids = fields.One2many(
|
||||
string="Sale Lines",
|
||||
help="",
|
||||
copy=False,
|
||||
comodel_name="folio.sale.line",
|
||||
inverse_name="service_id",
|
||||
string="Sale Lines",
|
||||
copy=False,
|
||||
)
|
||||
reservation_id = fields.Many2one(
|
||||
"pms.reservation",
|
||||
"Room",
|
||||
default=_default_reservation_id,
|
||||
string="Room",
|
||||
help="Reservation in which the service is included",
|
||||
default=lambda self: self._default_reservation_id(),
|
||||
comodel_name="pms.reservation",
|
||||
ondelete="cascade",
|
||||
)
|
||||
service_line_ids = fields.One2many(
|
||||
"pms.service.line",
|
||||
"service_id",
|
||||
compute="_compute_service_line_ids",
|
||||
store=True,
|
||||
string="Service Lines",
|
||||
help="Subservices included in this service",
|
||||
readonly=False,
|
||||
store=True,
|
||||
comodel_name="pms.service.line",
|
||||
inverse_name="service_id",
|
||||
compute="_compute_service_line_ids",
|
||||
)
|
||||
company_id = fields.Many2one(
|
||||
related="folio_id.company_id", string="Company", store=True, readonly=True
|
||||
string="Company",
|
||||
help="Company to which the service belongs",
|
||||
readonly=True,
|
||||
store=True,
|
||||
related="folio_id.company_id",
|
||||
)
|
||||
pms_property_id = fields.Many2one(
|
||||
comodel_name="pms.property",
|
||||
store=True,
|
||||
string="Property",
|
||||
help="Property to which the service belongs",
|
||||
readonly=True,
|
||||
store=True,
|
||||
comodel_name="pms.property",
|
||||
related="folio_id.pms_property_id",
|
||||
)
|
||||
tax_ids = fields.Many2many(
|
||||
"account.tax",
|
||||
string="Taxes",
|
||||
compute="_compute_tax_ids",
|
||||
store=True,
|
||||
help="Taxes applied in the service",
|
||||
readonly=False,
|
||||
store=True,
|
||||
comodel_name="account.tax",
|
||||
domain=["|", ("active", "=", False), ("active", "=", True)],
|
||||
compute="_compute_tax_ids",
|
||||
)
|
||||
analytic_tag_ids = fields.Many2many(
|
||||
string="Analytic Tags",
|
||||
help="",
|
||||
comodel_name="account.analytic.tag",
|
||||
)
|
||||
analytic_tag_ids = fields.Many2many("account.analytic.tag", string="Analytic Tags")
|
||||
currency_id = fields.Many2one(
|
||||
related="folio_id.currency_id", store=True, string="Currency", readonly=True
|
||||
)
|
||||
sequence = fields.Integer(string="Sequence", default=10)
|
||||
state = fields.Selection(related="folio_id.state")
|
||||
per_day = fields.Boolean(related="product_id.per_day", related_sudo=True)
|
||||
product_qty = fields.Integer(
|
||||
"Quantity",
|
||||
compute="_compute_product_qty",
|
||||
string="Currency",
|
||||
help="The currency used in relation to the folio",
|
||||
readonly=True,
|
||||
store=True,
|
||||
readonly=False,
|
||||
related="folio_id.currency_id",
|
||||
)
|
||||
sequence = fields.Integer(string="Sequence", help="", default=10)
|
||||
state = fields.Selection(
|
||||
string="State",
|
||||
help="Service status, it corresponds with folio status",
|
||||
related="folio_id.state",
|
||||
)
|
||||
per_day = fields.Boolean(
|
||||
string="Per Day",
|
||||
help="Indicates if service is sold by days",
|
||||
related="product_id.per_day",
|
||||
related_sudo=True,
|
||||
)
|
||||
product_qty = fields.Integer(
|
||||
string="Quantity",
|
||||
help="Number of services that were sold",
|
||||
readonly=False,
|
||||
store=True,
|
||||
compute="_compute_product_qty",
|
||||
)
|
||||
is_board_service = fields.Boolean(
|
||||
string="Is Board Service",
|
||||
help="Indicates if the service is part of a board service",
|
||||
)
|
||||
is_board_service = fields.Boolean()
|
||||
# Non-stored related field to allow portal user to
|
||||
# see the image of the product he has ordered
|
||||
product_image = fields.Binary(
|
||||
"Product Image", related="product_id.image_1024", store=False, related_sudo=True
|
||||
string="Product Image",
|
||||
help="Image of the service",
|
||||
store=False,
|
||||
related="product_id.image_1024",
|
||||
related_sudo=True,
|
||||
)
|
||||
invoice_status = fields.Selection(
|
||||
[
|
||||
string="Invoice Status",
|
||||
help="State in which the service is with respect to invoices."
|
||||
"It can be 'invoiced', 'to_invoice' or 'no'",
|
||||
readonly=True,
|
||||
default="no",
|
||||
store=True,
|
||||
compute="_compute_invoice_status",
|
||||
selection=[
|
||||
("invoiced", "Fully Invoiced"),
|
||||
("to invoice", "To Invoice"),
|
||||
("no", "Nothing to Invoice"),
|
||||
],
|
||||
string="Invoice Status",
|
||||
compute="_compute_invoice_status",
|
||||
store=True,
|
||||
readonly=True,
|
||||
default="no",
|
||||
)
|
||||
channel_type = fields.Selection(
|
||||
[
|
||||
string="Sales Channel",
|
||||
help="sales channel through which the service was sold."
|
||||
"It can be 'door', 'mail', 'phone', 'call' or 'web'",
|
||||
selection=[
|
||||
("door", "Door"),
|
||||
("mail", "Mail"),
|
||||
("phone", "Phone"),
|
||||
("call", "Call Center"),
|
||||
("web", "Web"),
|
||||
],
|
||||
string="Sales Channel",
|
||||
)
|
||||
price_subtotal = fields.Monetary(
|
||||
string="Subtotal", readonly=True, store=True, compute="_compute_amount_service"
|
||||
string="Subtotal",
|
||||
help="Subtotal price without taxes",
|
||||
readonly=True,
|
||||
store=True,
|
||||
compute="_compute_amount_service",
|
||||
)
|
||||
price_total = fields.Monetary(
|
||||
string="Total", readonly=True, store=True, compute="_compute_amount_service"
|
||||
string="Total",
|
||||
help="Total price without taxes",
|
||||
readonly=True,
|
||||
store=True,
|
||||
compute="_compute_amount_service",
|
||||
)
|
||||
price_tax = fields.Float(
|
||||
string="Taxes Amount",
|
||||
help="Total of taxes in service",
|
||||
readonly=True,
|
||||
store=True,
|
||||
compute="_compute_amount_service",
|
||||
)
|
||||
|
||||
# Compute and Search methods
|
||||
@api.depends("product_id")
|
||||
def _compute_tax_ids(self):
|
||||
for service in self:
|
||||
service.tax_ids = service.product_id.taxes_id.filtered(
|
||||
lambda r: not service.company_id or r.company_id == service.company_id
|
||||
)
|
||||
|
||||
@api.depends("service_line_ids", "service_line_ids.day_qty")
|
||||
def _compute_product_qty(self):
|
||||
self.product_qty = 0
|
||||
for service in self.filtered("service_line_ids"):
|
||||
qty = sum(service.service_line_ids.mapped("day_qty"))
|
||||
service.product_qty = qty
|
||||
|
||||
@api.depends("reservation_id", "reservation_id.folio_id")
|
||||
def _compute_folio_id(self):
|
||||
for record in self:
|
||||
if record.reservation_id:
|
||||
record.folio_id = record.reservation_id.folio_id
|
||||
elif not record.folio_id:
|
||||
record.folio_id = False
|
||||
|
||||
@api.depends(
|
||||
"sale_line_ids",
|
||||
"sale_line_ids.invoice_status",
|
||||
)
|
||||
def _compute_invoice_status(self):
|
||||
"""
|
||||
Compute the invoice status of a Reservation. Possible statuses:
|
||||
Base on folio sale line invoice status
|
||||
"""
|
||||
for line in self:
|
||||
states = list(set(line.sale_line_ids.mapped("invoice_status")))
|
||||
if len(states) == 1:
|
||||
line.invoice_status = states[0]
|
||||
elif len(states) >= 1:
|
||||
if "to_invoice" in states:
|
||||
line.invoice_status = "to_invoice"
|
||||
elif "invoiced" in states:
|
||||
line.invoice_status = "invoiced"
|
||||
else:
|
||||
line.invoice_status = "no"
|
||||
else:
|
||||
line.invoice_status = "no"
|
||||
|
||||
@api.depends("service_line_ids.price_day_total")
|
||||
def _compute_amount_service(self):
|
||||
for service in self:
|
||||
if service.service_line_ids:
|
||||
service.update(
|
||||
{
|
||||
"price_tax": sum(
|
||||
service.service_line_ids.mapped("price_day_tax")
|
||||
),
|
||||
"price_total": sum(
|
||||
service.service_line_ids.mapped("price_day_total")
|
||||
),
|
||||
"price_subtotal": sum(
|
||||
service.service_line_ids.mapped("price_day_subtotal")
|
||||
),
|
||||
}
|
||||
)
|
||||
else:
|
||||
service.update(
|
||||
{
|
||||
"price_tax": 0,
|
||||
"price_total": 0,
|
||||
"price_subtotal": 0,
|
||||
}
|
||||
)
|
||||
|
||||
@api.depends("product_id")
|
||||
def _compute_name(self):
|
||||
self.name = False
|
||||
@@ -268,76 +372,26 @@ class PmsService(models.Model):
|
||||
return old_line
|
||||
return False
|
||||
|
||||
@api.depends("product_id")
|
||||
def _compute_tax_ids(self):
|
||||
for service in self:
|
||||
service.tax_ids = service.product_id.taxes_id.filtered(
|
||||
lambda r: not service.company_id or r.company_id == service.company_id
|
||||
)
|
||||
# Default methods
|
||||
|
||||
@api.depends("service_line_ids", "service_line_ids.day_qty")
|
||||
def _compute_product_qty(self):
|
||||
self.product_qty = 0
|
||||
for service in self.filtered("service_line_ids"):
|
||||
qty = sum(service.service_line_ids.mapped("day_qty"))
|
||||
service.product_qty = qty
|
||||
def name_get(self):
|
||||
result = []
|
||||
for rec in self:
|
||||
name = []
|
||||
name.append("{name}".format(name=rec.name))
|
||||
if rec.reservation_id.name:
|
||||
name.append("{name}".format(name=rec.reservation_id.name))
|
||||
result.append((rec.id, ", ".join(name)))
|
||||
return result
|
||||
|
||||
@api.depends("reservation_id", "reservation_id.folio_id")
|
||||
def _compute_folio_id(self):
|
||||
for record in self:
|
||||
if record.reservation_id:
|
||||
record.folio_id = record.reservation_id.folio_id
|
||||
elif not record.folio_id:
|
||||
record.folio_id = False
|
||||
|
||||
@api.depends(
|
||||
"sale_line_ids",
|
||||
"sale_line_ids.invoice_status",
|
||||
)
|
||||
def _compute_invoice_status(self):
|
||||
"""
|
||||
Compute the invoice status of a Reservation. Possible statuses:
|
||||
Base on folio sale line invoice status
|
||||
"""
|
||||
for line in self:
|
||||
states = list(set(line.sale_line_ids.mapped("invoice_status")))
|
||||
if len(states) == 1:
|
||||
line.invoice_status = states[0]
|
||||
elif len(states) >= 1:
|
||||
if "to_invoice" in states:
|
||||
line.invoice_status = "to_invoice"
|
||||
elif "invoiced" in states:
|
||||
line.invoice_status = "invoiced"
|
||||
else:
|
||||
line.invoice_status = "no"
|
||||
else:
|
||||
line.invoice_status = "no"
|
||||
|
||||
@api.depends("service_line_ids.price_day_total")
|
||||
def _compute_amount_service(self):
|
||||
for service in self:
|
||||
if service.service_line_ids:
|
||||
service.update(
|
||||
{
|
||||
"price_tax": sum(
|
||||
service.service_line_ids.mapped("price_day_tax")
|
||||
),
|
||||
"price_total": sum(
|
||||
service.service_line_ids.mapped("price_day_total")
|
||||
),
|
||||
"price_subtotal": sum(
|
||||
service.service_line_ids.mapped("price_day_subtotal")
|
||||
),
|
||||
}
|
||||
)
|
||||
else:
|
||||
service.update(
|
||||
{
|
||||
"price_tax": 0,
|
||||
"price_total": 0,
|
||||
"price_subtotal": 0,
|
||||
}
|
||||
)
|
||||
@api.model
|
||||
def _default_reservation_id(self):
|
||||
if self.env.context.get("reservation_ids"):
|
||||
ids = [item[1] for item in self.env.context["reservation_ids"]]
|
||||
return self.env["pms.reservation"].browse([(ids)], limit=1)
|
||||
elif self.env.context.get("default_reservation_id"):
|
||||
return self.env.context.get("default_reservation_id")
|
||||
return False
|
||||
|
||||
# Action methods
|
||||
def open_service_ids(self):
|
||||
|
||||
@@ -11,59 +11,100 @@ class PmsServiceLine(models.Model):
|
||||
_order = "date"
|
||||
_rec_name = "service_id"
|
||||
|
||||
# Fields declaration
|
||||
service_id = fields.Many2one(
|
||||
"pms.service",
|
||||
string="Service Room",
|
||||
ondelete="cascade",
|
||||
help="Service identifier",
|
||||
required=True,
|
||||
copy=False,
|
||||
comodel_name="pms.service",
|
||||
ondelete="cascade",
|
||||
)
|
||||
is_board_service = fields.Boolean(
|
||||
string="Is Board Service",
|
||||
help="Indicates if the service line is part of a board service",
|
||||
store=True,
|
||||
related="service_id.is_board_service",
|
||||
)
|
||||
product_id = fields.Many2one(
|
||||
string="Product",
|
||||
help="Product associated with this service line",
|
||||
store=True,
|
||||
related="service_id.product_id",
|
||||
)
|
||||
is_board_service = fields.Boolean(related="service_id.is_board_service", store=True)
|
||||
product_id = fields.Many2one(related="service_id.product_id", store=True)
|
||||
tax_ids = fields.Many2many(
|
||||
"account.tax", string="Taxes", related="service_id.tax_ids", readonly="True"
|
||||
string="Taxes",
|
||||
help="Taxes applied in the service line",
|
||||
readonly="True",
|
||||
comodel_name="account.tax",
|
||||
related="service_id.tax_ids",
|
||||
)
|
||||
pms_property_id = fields.Many2one(
|
||||
"pms.property", store=True, readonly=True, related="service_id.pms_property_id"
|
||||
string="Property",
|
||||
help="Property to which the service belongs",
|
||||
readonly=True,
|
||||
store=True,
|
||||
comodel_name="pms.property",
|
||||
related="service_id.pms_property_id",
|
||||
)
|
||||
date = fields.Date(
|
||||
string="Date",
|
||||
help="Sate on which the product is to be consumed",
|
||||
)
|
||||
day_qty = fields.Integer(
|
||||
string="Units",
|
||||
help="Amount to be consumed per day",
|
||||
)
|
||||
date = fields.Date("Date")
|
||||
day_qty = fields.Integer("Units")
|
||||
price_unit = fields.Float(
|
||||
"Unit Price",
|
||||
string="Unit Price",
|
||||
help="Price per unit of service",
|
||||
digits=("Product Price"),
|
||||
)
|
||||
price_day_subtotal = fields.Monetary(
|
||||
string="Subtotal",
|
||||
help="Subtotal price without taxes",
|
||||
readonly=True,
|
||||
store=True,
|
||||
compute="_compute_day_amount_service",
|
||||
)
|
||||
price_day_total = fields.Monetary(
|
||||
string="Total", readonly=True, store=True, compute="_compute_day_amount_service"
|
||||
string="Total",
|
||||
help="Total price without taxes",
|
||||
readonly=True,
|
||||
store=True,
|
||||
compute="_compute_day_amount_service",
|
||||
)
|
||||
price_day_tax = fields.Float(
|
||||
string="Taxes Amount",
|
||||
help="",
|
||||
readonly=True,
|
||||
store=True,
|
||||
compute="_compute_day_amount_service",
|
||||
)
|
||||
currency_id = fields.Many2one(
|
||||
related="service_id.currency_id", store=True, string="Currency", readonly=True
|
||||
string="Currency",
|
||||
help="The currency used in relation to the service where it's included",
|
||||
readonly=True,
|
||||
store=True,
|
||||
related="service_id.currency_id",
|
||||
)
|
||||
room_id = fields.Many2one(
|
||||
string="Room", related="service_id.reservation_id", readonly=True, store=True
|
||||
string="Room",
|
||||
help="Room to which the services will be applied",
|
||||
readonly=True,
|
||||
store=True,
|
||||
related="service_id.reservation_id",
|
||||
)
|
||||
discount = fields.Float(
|
||||
string="Discount (%)",
|
||||
digits=("Discount"),
|
||||
default=0.0,
|
||||
compute="_compute_discount",
|
||||
help="Discount in the price of the service.",
|
||||
readonly=False,
|
||||
store=True,
|
||||
default=0.0,
|
||||
digits=("Discount"),
|
||||
compute="_compute_discount",
|
||||
)
|
||||
cancel_discount = fields.Float(
|
||||
"Cancelation Discount", compute="_compute_cancel_discount"
|
||||
string="Cancelation Discount", help="", compute="_compute_cancel_discount"
|
||||
)
|
||||
|
||||
@api.depends("day_qty", "discount", "price_unit", "tax_ids")
|
||||
|
||||
@@ -10,43 +10,60 @@ class PmsSharedRoom(models.Model):
|
||||
_name = "pms.shared.room"
|
||||
_description = "Shared Room"
|
||||
_order = "room_type_id, name"
|
||||
|
||||
# Fields declaration
|
||||
name = fields.Char("Room Name", required=True)
|
||||
name = fields.Char(
|
||||
string="Room Name", help="Name of the shared room", required=True
|
||||
)
|
||||
active = fields.Boolean(
|
||||
string="Active", help="Determines if shared room is active", default=True
|
||||
)
|
||||
sequence = fields.Integer(
|
||||
string="Sequence",
|
||||
help="Field used to change the position of the shared rooms in tree view."
|
||||
"Changing the position changes the sequence",
|
||||
required=True,
|
||||
)
|
||||
room_type_id = fields.Many2one(
|
||||
"pms.room.type",
|
||||
"Room Type",
|
||||
string="Room Type",
|
||||
help="Room type which the shared room belongs",
|
||||
comodel_name="pms.room.type",
|
||||
required=True,
|
||||
ondelete="restrict",
|
||||
domain=[("shared_room", "=", True)],
|
||||
)
|
||||
# TODO: properties relation
|
||||
pms_property_ids = fields.Many2many(
|
||||
"pms.property",
|
||||
string="Properties",
|
||||
help="Properties with access to the element;"
|
||||
" if not set, all properties can access",
|
||||
comodel_name="pms.property",
|
||||
relation="pms_shared_room_pms_property_rel",
|
||||
column1="shared_room_id",
|
||||
column2="pms_property_id",
|
||||
)
|
||||
floor_id = fields.Many2one(
|
||||
"pms.floor",
|
||||
"Ubication",
|
||||
ubication_id = fields.Many2one(
|
||||
string="Ubication",
|
||||
help="At which ubication the room is located.",
|
||||
comodel_name="pms.ubication",
|
||||
ondelete="restrict",
|
||||
help="At which floor the room is located.",
|
||||
)
|
||||
bed_ids = fields.One2many(
|
||||
"pms.room",
|
||||
"shared_room_id",
|
||||
string="Beds",
|
||||
help="Beds in one room",
|
||||
comodel_name="pms.room",
|
||||
inverse_name="shared_room_id",
|
||||
readonly=True,
|
||||
)
|
||||
active = fields.Boolean("Active", default=True)
|
||||
sequence = fields.Integer("Sequence", required=True)
|
||||
beds = fields.Integer("Beds")
|
||||
beds = fields.Integer(
|
||||
string="Number Of Beds", help="Number of beds in a shared room"
|
||||
)
|
||||
description_sale = fields.Text(
|
||||
"Sale Description",
|
||||
translate=True,
|
||||
string="Sale Description",
|
||||
help="A description of the Product that you want to communicate to "
|
||||
" your customers. This description will be copied to every Sales "
|
||||
" Order, Delivery Order and Customer Invoice/Credit Note",
|
||||
translate=True,
|
||||
)
|
||||
|
||||
# Constraints and onchanges
|
||||
@api.constrains("beds")
|
||||
def _constrain_beds(self):
|
||||
self.ensure_one()
|
||||
@@ -75,7 +92,7 @@ class PmsSharedRoom(models.Model):
|
||||
"capacity": 1,
|
||||
"room_type_id": self.room_type_id.id,
|
||||
"sequence": self.sequence,
|
||||
"floor_id": self.floor_id.id if self.floor_id else False,
|
||||
"ubication_id": self.ubication_id.id if self.ubication_id else False,
|
||||
"shared_room_id": self.id,
|
||||
}
|
||||
beds.append((0, False, bed_vals))
|
||||
@@ -98,11 +115,11 @@ class PmsSharedRoom(models.Model):
|
||||
}
|
||||
)
|
||||
|
||||
@api.constrains("floor_id")
|
||||
def _constrain_floor_id(self):
|
||||
@api.constrains("ubication_id")
|
||||
def _constrain_ubication_id(self):
|
||||
self.bed_ids.write(
|
||||
{
|
||||
"floor_id": self.floor_id.id,
|
||||
"ubication_id": self.ubication_id.id,
|
||||
}
|
||||
)
|
||||
|
||||
|
||||
46
pms/models/pms_ubication.py
Normal file
46
pms/models/pms_ubication.py
Normal file
@@ -0,0 +1,46 @@
|
||||
# Copyright 2017 Dario Lodeiros
|
||||
# License AGPL-3.0 or later (http://www.gnu.org/licenses/agpl).
|
||||
from odoo import _, api, fields, models
|
||||
from odoo.exceptions import ValidationError
|
||||
|
||||
|
||||
class PmsUbication(models.Model):
|
||||
_name = "pms.ubication"
|
||||
_description = "Ubication"
|
||||
|
||||
name = fields.Char(
|
||||
string="Ubication Name",
|
||||
help="Ubication Name",
|
||||
required=True,
|
||||
translate=True,
|
||||
)
|
||||
sequence = fields.Integer(
|
||||
string="Sequence",
|
||||
help="Field used to change the position of the ubications in tree view."
|
||||
"Changing the position changes the sequence",
|
||||
)
|
||||
pms_property_ids = fields.Many2many(
|
||||
string="Properties",
|
||||
help="Properties with access to the element;"
|
||||
" if not set, all properties can access",
|
||||
comodel_name="pms.property",
|
||||
relation="pms_ubication_pms_property_rel",
|
||||
column1="ubication_type_id",
|
||||
column2="pms_property_id",
|
||||
)
|
||||
pms_room_ids = fields.One2many(
|
||||
string="Rooms",
|
||||
help="Rooms found in this location",
|
||||
comodel_name="pms.room",
|
||||
inverse_name="ubication_id",
|
||||
)
|
||||
|
||||
@api.constrains(
|
||||
"pms_property_ids",
|
||||
"pms_room_ids",
|
||||
)
|
||||
def _check_property_integrity(self):
|
||||
for rec in self:
|
||||
if rec.pms_property_ids and rec.pms_room_ids:
|
||||
if rec.pms_room_ids.pms_property_id not in rec.pms_property_ids:
|
||||
raise ValidationError(_("Property not allowed"))
|
||||
@@ -37,7 +37,7 @@ class ProductPricelist(models.Model):
|
||||
)
|
||||
|
||||
availability_plan_id = fields.Many2one(
|
||||
comodel_name="pms.room.type.availability.plan",
|
||||
comodel_name="pms.availability.plan",
|
||||
string="Availability Plan",
|
||||
ondelete="restrict",
|
||||
domain=[
|
||||
@@ -83,7 +83,7 @@ class ProductPricelist(models.Model):
|
||||
if (
|
||||
"property" in self._context
|
||||
and self._context["property"]
|
||||
and self._context.get("date_overnight")
|
||||
and self._context.get("consumption_date")
|
||||
):
|
||||
# board_service_id = self._context.get("board_service")
|
||||
# on_board_service_bool = True if board_service_id else False
|
||||
@@ -140,8 +140,8 @@ class ProductPricelist(models.Model):
|
||||
self.id,
|
||||
date,
|
||||
date,
|
||||
self._context["date_overnight"],
|
||||
self._context["date_overnight"],
|
||||
self._context["consumption_date"],
|
||||
self._context["consumption_date"],
|
||||
),
|
||||
)
|
||||
|
||||
|
||||
@@ -11,15 +11,7 @@ class ProductProduct(models.Model):
|
||||
help="Get price price on board service",
|
||||
)
|
||||
|
||||
@api.depends_context(
|
||||
"pricelist",
|
||||
"partner",
|
||||
"quantity",
|
||||
"uom",
|
||||
"date",
|
||||
"date_overnight",
|
||||
"no_variant_attributes_price_extra",
|
||||
)
|
||||
@api.depends_context("consumption_date")
|
||||
def _compute_product_price(self):
|
||||
super(ProductProduct, self)._compute_product_price()
|
||||
|
||||
|
||||
@@ -9,27 +9,36 @@ class ProductTemplate(models.Model):
|
||||
_inherit = "product.template"
|
||||
|
||||
pms_property_ids = fields.Many2many(
|
||||
comodel_name="pms.property",
|
||||
relation="product_template_property_rel",
|
||||
column1="product_tmpl_id",
|
||||
column2="property_id",
|
||||
string="Properties",
|
||||
help="Properties with access to the element;"
|
||||
" if not set, all properties can access",
|
||||
required=False,
|
||||
ondelete="restrict",
|
||||
comodel_name="pms.property",
|
||||
relation="product_template_pms_property_rel",
|
||||
column1="product_tmpl_id",
|
||||
column2="pms_property_id",
|
||||
)
|
||||
per_day = fields.Boolean(
|
||||
string="Unit increment per day",
|
||||
help="Indicates that the product is sold by days",
|
||||
)
|
||||
per_person = fields.Boolean(
|
||||
string="Unit increment per person",
|
||||
help="Indicates that the product is sold per person",
|
||||
)
|
||||
per_day = fields.Boolean("Unit increment per day")
|
||||
per_person = fields.Boolean("Unit increment per person")
|
||||
consumed_on = fields.Selection(
|
||||
[("before", "Before night"), ("after", "After night")],
|
||||
"Consumed",
|
||||
string="Consumed",
|
||||
help="Indicates when the product is consumed",
|
||||
selection=[("before", "Before night"), ("after", "After night")],
|
||||
default="before",
|
||||
)
|
||||
daily_limit = fields.Integer("Daily limit")
|
||||
is_extra_bed = fields.Boolean("Is extra bed", default=False)
|
||||
show_in_calendar = fields.Boolean(
|
||||
"Show in Calendar",
|
||||
daily_limit = fields.Integer(
|
||||
string="Daily limit", help="Indicates how much products can consumed in one day"
|
||||
)
|
||||
is_extra_bed = fields.Boolean(
|
||||
string="Is extra bed",
|
||||
help="Indicates if that product is a extra bed, add +1 capacity in the room",
|
||||
default=False,
|
||||
help="Specifies if the product is shown in the calendar information.",
|
||||
)
|
||||
|
||||
@api.constrains("pms_property_ids", "company_id")
|
||||
|
||||
@@ -7,20 +7,9 @@ from odoo import fields, models
|
||||
class ResCompany(models.Model):
|
||||
_inherit = "res.company"
|
||||
|
||||
# Fields declaration
|
||||
pms_property_ids = fields.One2many("pms.property", "company_id", "Properties")
|
||||
# TODO: need extra explanation or remove otherwise
|
||||
# additional_hours = fields.Integer('Additional Hours',
|
||||
# help="Provide the min hours value for \
|
||||
# check in, checkout days, whatever \
|
||||
# the hours will be provided here based \
|
||||
# on that extra days will be \
|
||||
# calculated.")
|
||||
# TODO: move the text to the default template for confirmed reservations
|
||||
# cardex_warning = fields.Text(
|
||||
# 'Warning in Cardex',
|
||||
# default="Time to access rooms: 14: 00h. Departure time: \
|
||||
# 12: 00h. If the accommodation is not left at that time, \
|
||||
# the establishment will charge a day's stay according to \
|
||||
# current rate that day",
|
||||
# help="Notice under the signature on the traveler's ticket.")
|
||||
pms_property_ids = fields.One2many(
|
||||
string="Properties",
|
||||
help="Properties with access to the element",
|
||||
comodel_name="pms.property",
|
||||
inverse_name="company_id",
|
||||
)
|
||||
|
||||
@@ -11,35 +11,45 @@ _logger = logging.getLogger(__name__)
|
||||
class ResPartner(models.Model):
|
||||
_inherit = "res.partner"
|
||||
|
||||
# Fields declaration
|
||||
main_partner_id = fields.Many2one(
|
||||
"res.partner", string="Destination Partner fusion"
|
||||
)
|
||||
reservations_count = fields.Integer(
|
||||
"Reservations", compute="_compute_reservations_count"
|
||||
string="Reservations",
|
||||
help="Number of reservations of the partner",
|
||||
compute="_compute_reservations_count",
|
||||
)
|
||||
folios_count = fields.Integer(
|
||||
string="Folios",
|
||||
help="Number of folios of the partner",
|
||||
compute="_compute_folios_count",
|
||||
)
|
||||
is_agency = fields.Boolean(
|
||||
string="Is Agency", help="Indicates if the partner is an agency"
|
||||
)
|
||||
folios_count = fields.Integer("Folios", compute="_compute_folios_count")
|
||||
unconfirmed = fields.Boolean("Unconfirmed", default=True)
|
||||
is_agency = fields.Boolean("Is Agency")
|
||||
sale_channel_id = fields.Many2one(
|
||||
"pms.sale.channel",
|
||||
string="Sale Channel",
|
||||
ondelete="restrict",
|
||||
help="The sale channel of the partner",
|
||||
comodel_name="pms.sale.channel",
|
||||
domain=[("channel_type", "=", "indirect")],
|
||||
ondelete="restrict",
|
||||
)
|
||||
default_commission = fields.Integer(string="Commission", help="Default commission")
|
||||
apply_pricelist = fields.Boolean(
|
||||
string="Apply Pricelist",
|
||||
help="Indicates if agency pricelist is applied to his reservations",
|
||||
)
|
||||
invoice_to_agency = fields.Boolean(
|
||||
string="Invoice Agency",
|
||||
help="Indicates if agency invoices partner",
|
||||
)
|
||||
default_commission = fields.Integer("Commission")
|
||||
apply_pricelist = fields.Boolean("Apply Pricelist")
|
||||
invoice_agency = fields.Boolean("Invoice Agency")
|
||||
|
||||
# Compute and Search methods
|
||||
def _compute_reservations_count(self):
|
||||
# TODO: recuperar las reservas de los folios del partner
|
||||
pms_reservation_obj = self.env["pms.reservation"]
|
||||
for record in self:
|
||||
record.reservations_count = pms_reservation_obj.search_count(
|
||||
[
|
||||
(
|
||||
"partner_id.id",
|
||||
"=",
|
||||
"child_of",
|
||||
record.id if isinstance(record.id, int) else False,
|
||||
)
|
||||
]
|
||||
@@ -58,7 +68,6 @@ class ResPartner(models.Model):
|
||||
]
|
||||
)
|
||||
|
||||
# ORM Overrides
|
||||
@api.model
|
||||
def name_search(self, name, args=None, operator="ilike", limit=100):
|
||||
if not args:
|
||||
|
||||
@@ -8,23 +8,22 @@ from odoo.http import request
|
||||
class ResUsers(models.Model):
|
||||
_inherit = "res.users"
|
||||
|
||||
# Fields declaration
|
||||
pms_property_id = fields.Many2one(
|
||||
"pms.property",
|
||||
string="Property",
|
||||
help="The property this user is currently working for.",
|
||||
context={"user_preference": True},
|
||||
string="Default Property",
|
||||
help="The property that is selected within " "those allowed for the user",
|
||||
comodel_name="pms.property",
|
||||
domain="[('id','in',pms_property_ids)]",
|
||||
context={"user_preference": True},
|
||||
)
|
||||
pms_property_ids = fields.Many2many(
|
||||
"pms.property",
|
||||
"pms_property_users_rel",
|
||||
"user_id",
|
||||
"pms_property_id",
|
||||
string="Properties",
|
||||
help="The properties allowed for this user",
|
||||
comodel_name="pms.property",
|
||||
relation="pms_property_users_rel",
|
||||
column1="user_id",
|
||||
column2="pms_property_id",
|
||||
domain="[('company_id','in',company_ids)]",
|
||||
)
|
||||
# company_id = fields.Many2one(domain="[('id','in',company_ids)]")
|
||||
|
||||
@api.model
|
||||
def get_active_property_ids(self):
|
||||
|
||||
@@ -1,5 +1,5 @@
|
||||
id,name,model_id:id,group_id:id,perm_read,perm_write,perm_create,perm_unlink
|
||||
user_access_pms_floor,user_access_pms_floor,model_pms_floor,pms.group_pms_user,1,0,0,0
|
||||
user_access_pms_ubication,user_access_pms_ubication,model_pms_ubication,pms.group_pms_user,1,0,0,0
|
||||
user_access_pms_amenity,user_access_pms_amenity,model_pms_amenity,pms.group_pms_user,1,0,0,0
|
||||
user_access_pms_amenity_type,user_access_pms_amenity_type,model_pms_amenity_type,pms.group_pms_user,1,0,0,0
|
||||
user_access_pms_service,user_access_pms_service,model_pms_service,pms.group_pms_user,1,1,1,1
|
||||
@@ -11,8 +11,8 @@ user_access_pms_checkin_partner,user_access_pms_checkin_partner,model_pms_checki
|
||||
user_access_pms_room_type_class,user_access_pms_room_type_class,model_pms_room_type_class,pms.group_pms_user,1,0,0,0
|
||||
user_access_pms_room,user_access_pms_room,model_pms_room,pms.group_pms_user,1,0,0,0
|
||||
user_access_shared_pms_room,user_access_pms_shared_room,model_pms_shared_room,pms.group_pms_user,1,0,0,0
|
||||
user_access_pms_room_type_availability_rule,user_access_pms_room_type_availability_rule,model_pms_room_type_availability_rule,pms.group_pms_user,1,0,0,0
|
||||
user_access_pms_room_type_availability,user_access_pms_room_type_availability,model_pms_room_type_availability,pms.group_pms_user,1,1,1,0
|
||||
user_access_pms_availability_plan_rule,user_access_pms_availability_plan_rule,model_pms_availability_plan_rule,pms.group_pms_user,1,0,0,0
|
||||
user_access_pms_availability,user_access_pms_availability,model_pms_availability,pms.group_pms_user,1,1,1,0
|
||||
user_access_pms_reservation,user_access_pms_reservation,model_pms_reservation,pms.group_pms_user,1,1,1,1
|
||||
user_access_pms_folio,user_access_pms_folio,model_pms_folio,pms.group_pms_user,1,1,1,1
|
||||
user_access_pms_room_type,user_access_pms_room_type,model_pms_room_type,pms.group_pms_user,1,0,0,0
|
||||
@@ -23,9 +23,9 @@ user_access_account_partial_reconcile,user_access_account_partial_reconcile,acco
|
||||
user_access_pms_cancelation_rule,user_access_pms_cancelation_rule,model_pms_cancelation_rule,pms.group_pms_user,1,0,0,0
|
||||
user_access_account_full_reconcile,user_access_account_full_reconcile,account.model_account_full_reconcile,pms.group_pms_user,1,1,1,1
|
||||
user_access_property,user_access_property,model_pms_property,pms.group_pms_user,1,0,0,0
|
||||
user_access_availability,user_access_availability,model_pms_room_type_availability_plan,pms.group_pms_user,1,0,0,0
|
||||
user_access_availability,user_access_availability,model_pms_availability_plan,pms.group_pms_user,1,0,0,0
|
||||
user_access_pms_sale_channel,user_access_pms_sale_channel,model_pms_sale_channel,pms.group_pms_user,1,0,0,0
|
||||
manager_access_pms_floor,manager_access_pms_floor,model_pms_floor,pms.group_pms_manager,1,1,1,1
|
||||
manager_access_pms_ubication,manager_access_pms_ubication,model_pms_ubication,pms.group_pms_manager,1,1,1,1
|
||||
manager_access_pms_amenity,manager_access_pms_amenity,model_pms_amenity,pms.group_pms_manager,1,1,1,1
|
||||
manager_access_pms_amenity_type,manager_access_pms_amenity_type,model_pms_amenity_type,pms.group_pms_manager,1,1,1,1
|
||||
manager_access_pms_service,manager_access_pms_service,model_pms_service,pms.group_pms_manager,1,1,1,1
|
||||
@@ -37,9 +37,9 @@ manager_access_pms_checkin_partner,manager_access_pms_checkin_partner,model_pms_
|
||||
manager_access_pms_room_type_class,manager_access_pms_room_type_class,model_pms_room_type_class,pms.group_pms_manager,1,1,1,1
|
||||
manager_access_pms_room,manager_access_pms_room,model_pms_room,pms.group_pms_manager,1,1,1,1
|
||||
manager_access_pms_shared_room,manager_access_pms_shared_room,model_pms_shared_room,pms.group_pms_manager,1,1,1,1
|
||||
manager_access_pms_room_type_availability_rule,manager_access_pms_room_type_availability_rule,model_pms_room_type_availability_rule,pms.group_pms_manager,1,1,1,1
|
||||
manager_access_pms_availability_plan_rule,manager_access_pms_availability_plan_rule,model_pms_availability_plan_rule,pms.group_pms_manager,1,1,1,1
|
||||
manager_access_pms_reservation,manager_access_pms_reservation,model_pms_reservation,pms.group_pms_manager,1,1,1,1
|
||||
manager_access_pms_room_type_availability,manager_access_pms_room_type_availability,model_pms_room_type_availability,pms.group_pms_manager,1,1,1,0
|
||||
manager_access_pms_availability,manager_access_pms_availability,model_pms_availability,pms.group_pms_manager,1,1,1,0
|
||||
manager_access_pms_folio,manager_access_pms_folio,model_pms_folio,pms.group_pms_manager,1,1,1,1
|
||||
manager_access_pms_room_type,manager_access_pms_room_type,model_pms_room_type,pms.group_pms_manager,1,1,1,1
|
||||
manager_access_pms_board_service_room_type,manager_access_pms_board_service_room_type,model_pms_board_service_room_type,pms.group_pms_manager,1,1,1,1
|
||||
@@ -47,7 +47,7 @@ manager_access_pms_board_service_room_type_line,manager_access_pms_board_service
|
||||
manager_access_pms_board_service_line,manager_access_pms_board_service_line,model_pms_board_service_line,pms.group_pms_manager,1,1,1,1
|
||||
manager_access_property,manager_access_property,model_pms_property,pms.group_pms_manager,1,1,1,1
|
||||
manager_access_pms_cancelation_rule,manager_access_pms_cancelation_rule,model_pms_cancelation_rule,pms.group_pms_manager,1,1,1,1
|
||||
manager_access_availability,manager_access_availability,model_pms_room_type_availability_plan,pms.group_pms_manager,1,1,1,1
|
||||
manager_access_availability,manager_access_availability,model_pms_availability_plan,pms.group_pms_manager,1,1,1,1
|
||||
manager_access_pms_sale_channel,manager_access_pms_sale_channel,model_pms_sale_channel,pms.group_pms_manager,1,1,1,1
|
||||
user_access_pms_reservation_wizard,user_access_pms_reservation_wizard,model_pms_reservation_wizard,pms.group_pms_user,1,1,1,1
|
||||
user_access_pms_massive_changes_wizard,user_access_pms_massive_changes_wizard,model_pms_massive_changes_wizard,pms.group_pms_user,1,1,1,1
|
||||
|
||||
|
@@ -106,9 +106,9 @@
|
||||
user.get_active_property_ids())]
|
||||
</field>
|
||||
</record>
|
||||
<record id="pms_floor_property_rule" model="ir.rule">
|
||||
<field name="name">PMS Floor Property Rule</field>
|
||||
<field name="model_id" ref="model_pms_floor" />
|
||||
<record id="pms_ubication_property_rule" model="ir.rule">
|
||||
<field name="name">PMS Ubication Property Rule</field>
|
||||
<field name="model_id" ref="model_pms_ubication" />
|
||||
<field name="global" eval="True" />
|
||||
<field name="domain_force">
|
||||
['|',('pms_property_ids','=',False),('pms_property_ids', 'in',
|
||||
@@ -142,18 +142,18 @@
|
||||
user.get_active_property_ids())]
|
||||
</field>
|
||||
</record>
|
||||
<record id="pms_room_type_availability_plan_property_rule" model="ir.rule">
|
||||
<record id="pms_availability_plan_property_rule" model="ir.rule">
|
||||
<field name="name">PMS Room Type Availability Plan Property Rule</field>
|
||||
<field name="model_id" ref="model_pms_room_type_availability_plan" />
|
||||
<field name="model_id" ref="model_pms_availability_plan" />
|
||||
<field name="global" eval="True" />
|
||||
<field name="domain_force">
|
||||
['|',('pms_property_ids','=',False),('pms_property_ids', 'in',
|
||||
user.get_active_property_ids())]
|
||||
</field>
|
||||
</record>
|
||||
<record id="pms_room_type_availability_rule_property_rule" model="ir.rule">
|
||||
<record id="pms_availability_plan_rule_property_rule" model="ir.rule">
|
||||
<field name="name">PMS Room Type Availability Rule Property Rule</field>
|
||||
<field name="model_id" ref="model_pms_room_type_availability_rule" />
|
||||
<field name="model_id" ref="model_pms_availability_plan_rule" />
|
||||
<field name="global" eval="True" />
|
||||
<field name="domain_force">
|
||||
['|',('pms_property_id','=',False),('pms_property_id', 'in',
|
||||
@@ -189,7 +189,7 @@
|
||||
</record>
|
||||
<record id="pms_product_pricelist_item_property_rule" model="ir.rule">
|
||||
<field name="name">PMS Room Type Class Property Rule</field>
|
||||
<field name="model_id" ref="model_pms_room_type_availability_plan" />
|
||||
<field name="model_id" ref="model_pms_availability_plan" />
|
||||
<field name="global" eval="True" />
|
||||
<field name="domain_force">
|
||||
['|',('pms_property_ids','=',False),('pms_property_ids', 'in',
|
||||
|
||||
@@ -25,7 +25,7 @@ from . import test_pms_pricelist_priority
|
||||
from . import test_pms_checkin_partner
|
||||
from . import test_pms_sale_channel
|
||||
from . import test_pms_folio
|
||||
from . import test_pms_room_type_availability_rules
|
||||
from . import test_pms_availability_plan_rules
|
||||
from . import test_pms_room_type
|
||||
from . import test_pms_room_type_class
|
||||
from . import test_pms_wizard_massive_changes
|
||||
|
||||
@@ -1,63 +1,29 @@
|
||||
##############################################################################
|
||||
#
|
||||
# OpenERP, Open Source Management Solution
|
||||
# Copyright (C) 2017 Solucións Aloxa S.L. <info@aloxa.eu>
|
||||
# Alexandre Díaz <dev@redneboa.es>
|
||||
#
|
||||
#
|
||||
# This program is free software: you can redistribute it and/or modify
|
||||
# it under the terms of the GNU General Public License as published by
|
||||
# the Free Software Foundation, either version 3 of the License, or
|
||||
# (at your option) any later version.
|
||||
#
|
||||
# This program is distributed in the hope that it will be useful,
|
||||
# but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
# GNU General Public License for more details.
|
||||
#
|
||||
# You should have received a copy of the GNU General Public License
|
||||
# along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
#
|
||||
##############################################################################
|
||||
import logging
|
||||
|
||||
from odoo.tests import common
|
||||
|
||||
_logger = logging.getLogger(__name__)
|
||||
|
||||
|
||||
class TestHotel(common.SavepointCase):
|
||||
@classmethod
|
||||
def _init_mock_hotel(cls):
|
||||
return True
|
||||
|
||||
@classmethod
|
||||
def setUpClass(cls):
|
||||
super(TestHotel, cls).setUpClass()
|
||||
|
||||
cls._init_mock_hotel()
|
||||
|
||||
# Create Tests Records
|
||||
cls.main_hotel_property = cls.env.ref("pms.main_pms_property")
|
||||
cls.demo_hotel_property = cls.env.ref("pms.demo_pms_property")
|
||||
|
||||
cls.room_type_0 = cls.env.ref("pms.pms_room_type_0")
|
||||
cls.room_type_1 = cls.env.ref("pms.pms_room_type_1")
|
||||
cls.room_type_2 = cls.env.ref("pms.pms_room_type_2")
|
||||
cls.room_type_3 = cls.env.ref("pms.pms_room_type_3")
|
||||
|
||||
cls.demo_room_type_0 = cls.env.ref("pms.demo_pms_room_type_0")
|
||||
cls.demo_room_type_1 = cls.env.ref("pms.demo_pms_room_type_1")
|
||||
|
||||
cls.room_0 = cls.env.ref("pms.pms_room_0")
|
||||
cls.room_1 = cls.env.ref("pms.pms_room_1")
|
||||
cls.room_2 = cls.env.ref("pms.pms_room_2")
|
||||
cls.room_3 = cls.env.ref("pms.pms_room_3")
|
||||
cls.room_4 = cls.env.ref("pms.pms_room_4")
|
||||
cls.room_5 = cls.env.ref("pms.pms_room_5")
|
||||
cls.room_6 = cls.env.ref("pms.pms_room_6")
|
||||
|
||||
cls.list0 = cls.env.ref("product.list0")
|
||||
cls.list1 = cls.env["product.pricelist"].create(
|
||||
{"name": "Test Pricelist", "pricelist_type": ""}
|
||||
class TestPms(common.SavepointCase):
|
||||
def setUp(self):
|
||||
super().setUp()
|
||||
self.pricelist1 = self.env["product.pricelist"].create(
|
||||
{
|
||||
"name": "Pricelist 1",
|
||||
}
|
||||
)
|
||||
self.company1 = self.env["res.company"].create(
|
||||
{
|
||||
"name": "Company 1",
|
||||
}
|
||||
)
|
||||
self.pms_property1 = self.env["pms.property"].create(
|
||||
{
|
||||
"name": "Property 1",
|
||||
"company_id": self.company1.id,
|
||||
"default_pricelist_id": self.pricelist1.id,
|
||||
}
|
||||
)
|
||||
self.room_type_class1 = self.env["pms.room.type.class"].create(
|
||||
{
|
||||
"name": "Room Type Class 1",
|
||||
"code_class": "RTC1",
|
||||
}
|
||||
)
|
||||
|
||||
@@ -1,98 +1,183 @@
|
||||
from odoo.exceptions import ValidationError
|
||||
|
||||
from .common import TestHotel
|
||||
from .common import TestPms
|
||||
|
||||
|
||||
class TestPmsAmenity(TestHotel):
|
||||
def create_common_scenario(self):
|
||||
# create company and properties
|
||||
self.company1 = self.env["res.company"].create(
|
||||
{
|
||||
"name": "Pms_Company_Test",
|
||||
}
|
||||
)
|
||||
self.property1 = self.env["pms.property"].create(
|
||||
{
|
||||
"name": "Pms_property_test1",
|
||||
"company_id": self.company1.id,
|
||||
"default_pricelist_id": self.env.ref("product.list0").id,
|
||||
}
|
||||
)
|
||||
self.property2 = self.env["pms.property"].create(
|
||||
class TestPmsAmenity(TestPms):
|
||||
def setUp(self):
|
||||
super().setUp()
|
||||
# Create two properties
|
||||
# +-----------+-----------+
|
||||
# | Properties |
|
||||
# +-----------+-----------+
|
||||
# | Property2 - Property3 |
|
||||
# +-----------+-----------+
|
||||
|
||||
self.pms_property2 = self.env["pms.property"].create(
|
||||
{
|
||||
"name": "Pms_property_test2",
|
||||
"company_id": self.company1.id,
|
||||
"default_pricelist_id": self.env.ref("product.list0").id,
|
||||
"default_pricelist_id": self.pricelist1.id,
|
||||
}
|
||||
)
|
||||
|
||||
self.property3 = self.env["pms.property"].create(
|
||||
self.pms_property3 = self.env["pms.property"].create(
|
||||
{
|
||||
"name": "Pms_property_test3",
|
||||
"company_id": self.company1.id,
|
||||
"default_pricelist_id": self.env.ref("product.list0").id,
|
||||
"default_pricelist_id": self.pricelist1.id,
|
||||
}
|
||||
)
|
||||
|
||||
def test_property_not_allowed(self):
|
||||
# Creation of a Amenity with Properties incompatible with it Amenity Type
|
||||
|
||||
# +-----------------------------------+-----------------------------------+
|
||||
# | Amenity Type (TestAmenityType1) | Amenity (TestAmenity1) |
|
||||
# +-----------------------------------+-----------------------------------+
|
||||
# | Property1 - Property2 | Property1 - Property2 - Property3 |
|
||||
# +-----------------------------------+-----------------------------------+
|
||||
|
||||
# ARRANGE
|
||||
name = "amenityTest1"
|
||||
name2 = "amenity"
|
||||
self.create_common_scenario()
|
||||
AmenityType = self.env["pms.amenity.type"]
|
||||
Amenity = self.env["pms.amenity"]
|
||||
# ACT
|
||||
A1 = AmenityType.create(
|
||||
amenity_type1 = AmenityType.create(
|
||||
{
|
||||
"name": name,
|
||||
"name": "TestAmenityType1",
|
||||
"pms_property_ids": [
|
||||
(4, self.property1.id),
|
||||
(4, self.property2.id),
|
||||
(4, self.pms_property1.id),
|
||||
(4, self.pms_property2.id),
|
||||
],
|
||||
}
|
||||
)
|
||||
# ASSERT
|
||||
# ACT & ASSERT
|
||||
with self.assertRaises(ValidationError), self.cr.savepoint():
|
||||
Amenity.create(
|
||||
{
|
||||
"name": name2,
|
||||
"room_amenity_type_id": A1.id,
|
||||
"name": "TestAmenity1",
|
||||
"pms_amenity_type_id": amenity_type1.id,
|
||||
"pms_property_ids": [
|
||||
(4, self.property1.id),
|
||||
(4, self.property2.id),
|
||||
(4, self.property3.id),
|
||||
(
|
||||
6,
|
||||
0,
|
||||
[
|
||||
self.pms_property1.id,
|
||||
self.pms_property2.id,
|
||||
self.pms_property3.id,
|
||||
],
|
||||
)
|
||||
],
|
||||
}
|
||||
)
|
||||
|
||||
def test_check_allowed_property_ids(self):
|
||||
def test_property_allowed(self):
|
||||
# Creation of a Amenity with Properties compatible with it Amenity Type
|
||||
# Check Properties of Amenity are in Properties of Amenity Type
|
||||
# +----------------------------------------+-----------------------------------+
|
||||
# | Amenity Type (TestAmenityType1) | Amenity (TestAmenity1) |
|
||||
# +----------------------------------------+-----------------------------------+
|
||||
# | Property1 - Property2 - Property3 | Property1 - Property2 - Property3 |
|
||||
# +----------------------------------------+-----------------------------------+
|
||||
|
||||
# ARRANGE
|
||||
name = "amenityTest1"
|
||||
name2 = "amenity"
|
||||
self.create_common_scenario()
|
||||
AmenityType = self.env["pms.amenity.type"]
|
||||
Amenity = self.env["pms.amenity"]
|
||||
# ACT
|
||||
AT1 = AmenityType.create(
|
||||
amenity_type1 = AmenityType.create(
|
||||
{
|
||||
"name": name,
|
||||
"name": "TestAmenityType1",
|
||||
"pms_property_ids": [
|
||||
(4, self.property1.id),
|
||||
(4, self.property2.id),
|
||||
(
|
||||
6,
|
||||
0,
|
||||
[
|
||||
self.pms_property1.id,
|
||||
self.pms_property2.id,
|
||||
self.pms_property3.id,
|
||||
],
|
||||
)
|
||||
],
|
||||
}
|
||||
)
|
||||
A2 = Amenity.create(
|
||||
# ACT
|
||||
amenity1 = Amenity.create(
|
||||
{
|
||||
"name": name2,
|
||||
"room_amenity_type_id": AT1.id,
|
||||
"name": "TestAmenity1",
|
||||
"pms_amenity_type_id": amenity_type1.id,
|
||||
"pms_property_ids": [
|
||||
(4, self.property1.id),
|
||||
(4, self.property2.id),
|
||||
(
|
||||
6,
|
||||
0,
|
||||
[
|
||||
self.pms_property1.id,
|
||||
self.pms_property2.id,
|
||||
self.pms_property3.id,
|
||||
],
|
||||
)
|
||||
],
|
||||
}
|
||||
)
|
||||
|
||||
# ASSERT
|
||||
self.assertEqual(
|
||||
amenity1.pms_property_ids.ids,
|
||||
amenity_type1.pms_property_ids.ids,
|
||||
"Properties not allowed in amenity type",
|
||||
)
|
||||
|
||||
def test_change_amenity_property(self):
|
||||
# Creation of a Amenity with Properties compatible with it Amenity Type
|
||||
# Delete a Property in Amenity Type, check Validation Error when do that
|
||||
# 1st scenario:
|
||||
# +----------------------------------------+-----------------------------------+
|
||||
# | Amenity Type (TestAmenityType1) | Amenity (TestAmenity1) |
|
||||
# +----------------------------------------+-----------------------------------+
|
||||
# | Property1 - Property2 - Property3 | Property1 - Property2 - Property3 |
|
||||
# +----------------------------------------+-----------------------------------+
|
||||
# 2nd scenario(Error):
|
||||
# +----------------------------------------+-----------------------------------+
|
||||
# | Amenity Type (TestAmenityType1) | Amenity (TestAmenity1) |
|
||||
# +----------------------------------------+-----------------------------------+
|
||||
# | Property1 - Property2 | Property1 - Property2 - Property3 |
|
||||
# +----------------------------------------+-----------------------------------+
|
||||
|
||||
# ARRANGE
|
||||
AmenityType = self.env["pms.amenity.type"]
|
||||
Amenity = self.env["pms.amenity"]
|
||||
amenity_type1 = AmenityType.create(
|
||||
{
|
||||
"name": "TestAmenityType1",
|
||||
"pms_property_ids": [
|
||||
(4, self.pms_property1.id),
|
||||
(4, self.pms_property2.id),
|
||||
(4, self.pms_property3.id),
|
||||
],
|
||||
}
|
||||
)
|
||||
# ACT
|
||||
Amenity.create(
|
||||
{
|
||||
"name": "TestAmenity1",
|
||||
"pms_amenity_type_id": amenity_type1.id,
|
||||
"pms_property_ids": [
|
||||
(
|
||||
6,
|
||||
0,
|
||||
[
|
||||
self.pms_property1.id,
|
||||
self.pms_property2.id,
|
||||
self.pms_property3.id,
|
||||
],
|
||||
)
|
||||
],
|
||||
}
|
||||
)
|
||||
# ASSERT
|
||||
self.assertEqual(
|
||||
A2.allowed_property_ids, AT1.pms_property_ids, "Properties doesnt much"
|
||||
)
|
||||
with self.assertRaises(ValidationError):
|
||||
amenity_type1.pms_property_ids = [
|
||||
(
|
||||
6,
|
||||
0,
|
||||
[self.pms_property1.id, self.pms_property2.id],
|
||||
)
|
||||
]
|
||||
amenity_type1.flush()
|
||||
|
||||
@@ -4,12 +4,11 @@ from freezegun import freeze_time
|
||||
|
||||
from odoo import fields
|
||||
from odoo.exceptions import ValidationError
|
||||
|
||||
from .common import TestHotel
|
||||
from odoo.tests import common
|
||||
|
||||
|
||||
@freeze_time("1980-01-01")
|
||||
class TestPmsRoomTypeAvailabilityRules(TestHotel):
|
||||
class TestPmsRoomTypeAvailabilityRules(common.SavepointCase):
|
||||
def create_common_scenario(self):
|
||||
# product.pricelist
|
||||
self.test_pricelist1 = self.env["product.pricelist"].create(
|
||||
@@ -22,21 +21,47 @@ class TestPmsRoomTypeAvailabilityRules(TestHotel):
|
||||
"name": "test pricelist 2",
|
||||
}
|
||||
)
|
||||
# pms.room.type.availability.plan
|
||||
self.test_room_type_availability1 = self.env[
|
||||
"pms.room.type.availability.plan"
|
||||
].create(
|
||||
# pms.availability.plan
|
||||
self.test_room_type_availability1 = self.env["pms.availability.plan"].create(
|
||||
{
|
||||
"name": "Availability plan for TEST",
|
||||
"pms_pricelist_ids": [(6, 0, [self.test_pricelist1.id])],
|
||||
}
|
||||
)
|
||||
# SEQUENCES
|
||||
self.folio_sequence = self.env["ir.sequence"].create(
|
||||
{
|
||||
"name": "PMS Folio",
|
||||
"code": "pms.folio",
|
||||
"padding": 4,
|
||||
"company_id": self.env.ref("base.main_company").id,
|
||||
}
|
||||
)
|
||||
self.reservation_sequence = self.env["ir.sequence"].create(
|
||||
{
|
||||
"name": "PMS Reservation",
|
||||
"code": "pms.reservation",
|
||||
"padding": 4,
|
||||
"company_id": self.env.ref("base.main_company").id,
|
||||
}
|
||||
)
|
||||
self.checkin_sequence = self.env["ir.sequence"].create(
|
||||
{
|
||||
"name": "PMS Checkin",
|
||||
"code": "pms.checkin.partner",
|
||||
"padding": 4,
|
||||
"company_id": self.env.ref("base.main_company").id,
|
||||
}
|
||||
)
|
||||
# pms.property
|
||||
self.test_property = self.env["pms.property"].create(
|
||||
{
|
||||
"name": "MY PMS TEST",
|
||||
"company_id": self.env.ref("base.main_company").id,
|
||||
"default_pricelist_id": self.test_pricelist1.id,
|
||||
"folio_sequence_id": self.folio_sequence.id,
|
||||
"reservation_sequence_id": self.reservation_sequence.id,
|
||||
"checkin_sequence_id": self.checkin_sequence.id,
|
||||
}
|
||||
)
|
||||
# pms.room.type.class
|
||||
@@ -49,7 +74,7 @@ class TestPmsRoomTypeAvailabilityRules(TestHotel):
|
||||
{
|
||||
"pms_property_ids": [self.test_property.id],
|
||||
"name": "Single Test",
|
||||
"code_type": "SNG_Test",
|
||||
"default_code": "SNG_Test",
|
||||
"class_id": self.test_room_type_class.id,
|
||||
}
|
||||
)
|
||||
@@ -60,7 +85,7 @@ class TestPmsRoomTypeAvailabilityRules(TestHotel):
|
||||
(4, self.test_property.id),
|
||||
],
|
||||
"name": "Double Test",
|
||||
"code_type": "DBL_Test",
|
||||
"default_code": "DBL_Test",
|
||||
"class_id": self.test_room_type_class.id,
|
||||
}
|
||||
)
|
||||
@@ -129,6 +154,9 @@ class TestPmsRoomTypeAvailabilityRules(TestHotel):
|
||||
"name": "Property 1",
|
||||
"company_id": self.env.ref("base.main_company").id,
|
||||
"default_pricelist_id": self.test_pricelist2.id,
|
||||
"folio_sequence_id": self.folio_sequence.id,
|
||||
"reservation_sequence_id": self.reservation_sequence.id,
|
||||
"checkin_sequence_id": self.checkin_sequence.id,
|
||||
}
|
||||
)
|
||||
self.test_property2 = self.env["pms.property"].create(
|
||||
@@ -136,6 +164,9 @@ class TestPmsRoomTypeAvailabilityRules(TestHotel):
|
||||
"name": "Property 2",
|
||||
"company_id": self.env.ref("base.main_company").id,
|
||||
"default_pricelist_id": self.test_pricelist2.id,
|
||||
"folio_sequence_id": self.folio_sequence.id,
|
||||
"reservation_sequence_id": self.reservation_sequence.id,
|
||||
"checkin_sequence_id": self.checkin_sequence.id,
|
||||
}
|
||||
)
|
||||
self.test_property3 = self.env["pms.property"].create(
|
||||
@@ -143,11 +174,12 @@ class TestPmsRoomTypeAvailabilityRules(TestHotel):
|
||||
"name": "Property 3",
|
||||
"company_id": self.env.ref("base.main_company").id,
|
||||
"default_pricelist_id": self.test_pricelist2.id,
|
||||
"folio_sequence_id": self.folio_sequence.id,
|
||||
"reservation_sequence_id": self.reservation_sequence.id,
|
||||
"checkin_sequence_id": self.checkin_sequence.id,
|
||||
}
|
||||
)
|
||||
self.availability_multiproperty = self.env[
|
||||
"pms.room.type.availability.plan"
|
||||
].create(
|
||||
self.availability_multiproperty = self.env["pms.availability.plan"].create(
|
||||
{
|
||||
"name": "Availability plan for TEST",
|
||||
"pms_pricelist_ids": [(6, 0, [self.test_pricelist1.id])],
|
||||
@@ -172,7 +204,7 @@ class TestPmsRoomTypeAvailabilityRules(TestHotel):
|
||||
)
|
||||
|
||||
# ACT
|
||||
result = self.env["pms.room.type.availability.plan"].rooms_available(
|
||||
result = self.env["pms.availability.plan"].rooms_available(
|
||||
checkin=checkin,
|
||||
checkout=checkout,
|
||||
)
|
||||
@@ -206,7 +238,7 @@ class TestPmsRoomTypeAvailabilityRules(TestHotel):
|
||||
)
|
||||
|
||||
# ACT
|
||||
result = self.env["pms.room.type.availability.plan"].rooms_available(
|
||||
result = self.env["pms.availability.plan"].rooms_available(
|
||||
checkin=checkin,
|
||||
checkout=checkout,
|
||||
current_lines=test_reservation.reservation_line_ids.ids,
|
||||
@@ -234,7 +266,7 @@ class TestPmsRoomTypeAvailabilityRules(TestHotel):
|
||||
)
|
||||
|
||||
# ACT
|
||||
result = self.env["pms.room.type.availability.plan"].rooms_available(
|
||||
result = self.env["pms.availability.plan"].rooms_available(
|
||||
checkin=fields.date.today(),
|
||||
checkout=(fields.datetime.today() + datetime.timedelta(days=4)).date(),
|
||||
room_type_id=self.test_room_type_double.id,
|
||||
@@ -258,7 +290,7 @@ class TestPmsRoomTypeAvailabilityRules(TestHotel):
|
||||
# ARRANGE
|
||||
self.create_common_scenario()
|
||||
self.test_room_type_availability_rule1 = self.env[
|
||||
"pms.room.type.availability.rule"
|
||||
"pms.availability.plan.rule"
|
||||
].create(
|
||||
{
|
||||
"availability_plan_id": self.test_room_type_availability1.id,
|
||||
@@ -269,7 +301,7 @@ class TestPmsRoomTypeAvailabilityRules(TestHotel):
|
||||
}
|
||||
)
|
||||
# ACT
|
||||
result = self.env["pms.room.type.availability.plan"].rooms_available(
|
||||
result = self.env["pms.availability.plan"].rooms_available(
|
||||
checkin=fields.date.today(),
|
||||
checkout=(fields.datetime.today() + datetime.timedelta(days=4)).date(),
|
||||
# room_type_id=False, # <- (2/2)
|
||||
@@ -293,7 +325,7 @@ class TestPmsRoomTypeAvailabilityRules(TestHotel):
|
||||
self.create_common_scenario()
|
||||
|
||||
self.test_room_type_availability_rule1 = self.env[
|
||||
"pms.room.type.availability.rule"
|
||||
"pms.availability.plan.rule"
|
||||
].create(
|
||||
{
|
||||
"availability_plan_id": self.test_room_type_availability1.id,
|
||||
@@ -411,7 +443,7 @@ class TestPmsRoomTypeAvailabilityRules(TestHotel):
|
||||
# ACT
|
||||
self.test_room_type_availability_rule1.write(test_case)
|
||||
|
||||
result = self.env["pms.room.type.availability.plan"].rooms_available(
|
||||
result = self.env["pms.availability.plan"].rooms_available(
|
||||
checkin=checkin,
|
||||
checkout=checkout,
|
||||
room_type_id=self.test_room_type_double.id,
|
||||
@@ -435,7 +467,7 @@ class TestPmsRoomTypeAvailabilityRules(TestHotel):
|
||||
# ARRANGE
|
||||
self.create_common_scenario()
|
||||
self.test_room_type_availability_rule1 = self.env[
|
||||
"pms.room.type.availability.rule"
|
||||
"pms.availability.plan.rule"
|
||||
].create(
|
||||
{
|
||||
"availability_plan_id": self.test_room_type_availability1.id,
|
||||
@@ -475,7 +507,7 @@ class TestPmsRoomTypeAvailabilityRules(TestHotel):
|
||||
# ARRANGE
|
||||
self.create_common_scenario()
|
||||
self.test_room_type_availability_rule1 = self.env[
|
||||
"pms.room.type.availability.rule"
|
||||
"pms.availability.plan.rule"
|
||||
].create(
|
||||
{
|
||||
"availability_plan_id": self.test_room_type_availability1.id,
|
||||
@@ -541,7 +573,7 @@ class TestPmsRoomTypeAvailabilityRules(TestHotel):
|
||||
self.create_common_scenario()
|
||||
|
||||
self.test_room_type_availability_rule1 = self.env[
|
||||
"pms.room.type.availability.rule"
|
||||
"pms.availability.plan.rule"
|
||||
].create(
|
||||
{
|
||||
"availability_plan_id": self.test_room_type_availability1.id,
|
||||
@@ -595,7 +627,7 @@ class TestPmsRoomTypeAvailabilityRules(TestHotel):
|
||||
"name": "test pricelist 2",
|
||||
}
|
||||
)
|
||||
rule = self.env["pms.room.type.availability.rule"].create(
|
||||
rule = self.env["pms.availability.plan.rule"].create(
|
||||
{
|
||||
"availability_plan_id": self.test_room_type_availability1.id,
|
||||
"room_type_id": self.test_room_type_double.id,
|
||||
@@ -641,7 +673,7 @@ class TestPmsRoomTypeAvailabilityRules(TestHotel):
|
||||
(4, self.test_property2.id),
|
||||
],
|
||||
"name": "Special Room Test",
|
||||
"code_type": "SP_Test",
|
||||
"default_code": "SP_Test",
|
||||
"class_id": self.test_room_type_class.id,
|
||||
}
|
||||
)
|
||||
@@ -663,7 +695,7 @@ class TestPmsRoomTypeAvailabilityRules(TestHotel):
|
||||
}
|
||||
)
|
||||
self.test_room_type_availability_rule1 = self.env[
|
||||
"pms.room.type.availability.rule"
|
||||
"pms.availability.plan.rule"
|
||||
].create(
|
||||
{
|
||||
"availability_plan_id": self.availability_multiproperty.id,
|
||||
@@ -674,7 +706,7 @@ class TestPmsRoomTypeAvailabilityRules(TestHotel):
|
||||
}
|
||||
)
|
||||
self.test_room_type_availability_rule2 = self.env[
|
||||
"pms.room.type.availability.rule"
|
||||
"pms.availability.plan.rule"
|
||||
].create(
|
||||
{
|
||||
"availability_plan_id": self.availability_multiproperty.id,
|
||||
@@ -695,9 +727,7 @@ class TestPmsRoomTypeAvailabilityRules(TestHotel):
|
||||
for p in properties:
|
||||
with self.subTest(k=p):
|
||||
# ACT
|
||||
rooms_avail = self.env[
|
||||
"pms.room.type.availability.plan"
|
||||
].rooms_available(
|
||||
rooms_avail = self.env["pms.availability.plan"].rooms_available(
|
||||
checkin=fields.date.today(),
|
||||
checkout=(
|
||||
fields.datetime.today() + datetime.timedelta(days=2)
|
||||
@@ -725,12 +755,12 @@ class TestPmsRoomTypeAvailabilityRules(TestHotel):
|
||||
(4, self.test_property3.id),
|
||||
],
|
||||
"name": "Special Room Test",
|
||||
"code_type": "SP_Test",
|
||||
"default_code": "SP_Test",
|
||||
"class_id": self.test_room_type_class.id,
|
||||
}
|
||||
)
|
||||
# ACT
|
||||
self.availability_example = self.env["pms.room.type.availability.plan"].create(
|
||||
self.availability_example = self.env["pms.availability.plan"].create(
|
||||
{
|
||||
"name": "Availability plan for TEST",
|
||||
"pms_pricelist_ids": [(6, 0, [self.test_pricelist1.id])],
|
||||
@@ -740,7 +770,7 @@ class TestPmsRoomTypeAvailabilityRules(TestHotel):
|
||||
],
|
||||
}
|
||||
)
|
||||
self.availability_rule1 = self.env["pms.room.type.availability.rule"].create(
|
||||
self.availability_rule1 = self.env["pms.availability.plan.rule"].create(
|
||||
{
|
||||
"availability_plan_id": self.availability_example.id,
|
||||
"room_type_id": self.test_room_type_special.id,
|
||||
@@ -790,12 +820,12 @@ class TestPmsRoomTypeAvailabilityRules(TestHotel):
|
||||
(4, self.test_property3.id),
|
||||
],
|
||||
"name": "Special Room Test",
|
||||
"code_type": "SP_Test",
|
||||
"default_code": "SP_Test",
|
||||
"class_id": self.test_room_type_class.id,
|
||||
}
|
||||
)
|
||||
# ACT
|
||||
self.availability_example = self.env["pms.room.type.availability.plan"].create(
|
||||
self.availability_example = self.env["pms.availability.plan"].create(
|
||||
{
|
||||
"name": "Availability plan for TEST",
|
||||
"pms_pricelist_ids": [(6, 0, [self.test_pricelist1.id])],
|
||||
@@ -805,7 +835,7 @@ class TestPmsRoomTypeAvailabilityRules(TestHotel):
|
||||
],
|
||||
}
|
||||
)
|
||||
self.availability_rule1 = self.env["pms.room.type.availability.rule"].create(
|
||||
self.availability_rule1 = self.env["pms.availability.plan.rule"].create(
|
||||
{
|
||||
"availability_plan_id": self.availability_example.id,
|
||||
"room_type_id": self.test_room_type_special.id,
|
||||
@@ -1,20 +1,46 @@
|
||||
from odoo.exceptions import ValidationError
|
||||
|
||||
from .common import TestHotel
|
||||
from odoo.tests import common
|
||||
|
||||
|
||||
class TestPmsBoardService(TestHotel):
|
||||
class TestPmsBoardService(common.SavepointCase):
|
||||
def test_property_integrity(self):
|
||||
self.company1 = self.env["res.company"].create(
|
||||
{
|
||||
"name": "Pms_Company_Test",
|
||||
}
|
||||
)
|
||||
self.folio_sequence = self.env["ir.sequence"].create(
|
||||
{
|
||||
"name": "PMS Folio",
|
||||
"code": "pms.folio",
|
||||
"padding": 4,
|
||||
"company_id": self.company1.id,
|
||||
}
|
||||
)
|
||||
self.reservation_sequence = self.env["ir.sequence"].create(
|
||||
{
|
||||
"name": "PMS Reservation",
|
||||
"code": "pms.reservation",
|
||||
"padding": 4,
|
||||
"company_id": self.company1.id,
|
||||
}
|
||||
)
|
||||
self.checkin_sequence = self.env["ir.sequence"].create(
|
||||
{
|
||||
"name": "PMS Checkin",
|
||||
"code": "pms.checkin.partner",
|
||||
"padding": 4,
|
||||
"company_id": self.company1.id,
|
||||
}
|
||||
)
|
||||
self.property1 = self.env["pms.property"].create(
|
||||
{
|
||||
"name": "Pms_property_test1",
|
||||
"company_id": self.company1.id,
|
||||
"default_pricelist_id": self.env.ref("product.list0").id,
|
||||
"folio_sequence_id": self.folio_sequence.id,
|
||||
"reservation_sequence_id": self.reservation_sequence.id,
|
||||
"checkin_sequence_id": self.checkin_sequence.id,
|
||||
}
|
||||
)
|
||||
self.property2 = self.env["pms.property"].create(
|
||||
@@ -22,6 +48,9 @@ class TestPmsBoardService(TestHotel):
|
||||
"name": "Pms_property_test2",
|
||||
"company_id": self.company1.id,
|
||||
"default_pricelist_id": self.env.ref("product.list0").id,
|
||||
"folio_sequence_id": self.folio_sequence.id,
|
||||
"reservation_sequence_id": self.reservation_sequence.id,
|
||||
"checkin_sequence_id": self.checkin_sequence.id,
|
||||
}
|
||||
)
|
||||
self.product = self.env["product.product"].create(
|
||||
|
||||
@@ -1,18 +1,45 @@
|
||||
from .common import TestHotel
|
||||
from odoo.tests import common
|
||||
|
||||
|
||||
class TestPmsBoardServiceRoomType(TestHotel):
|
||||
class TestPmsBoardServiceRoomType(common.SavepointCase):
|
||||
def _create_common_scenario(self):
|
||||
self.company1 = self.env["res.company"].create(
|
||||
{
|
||||
"name": "Pms_Company_Test",
|
||||
}
|
||||
)
|
||||
self.folio_sequence = self.env["ir.sequence"].create(
|
||||
{
|
||||
"name": "PMS Folio",
|
||||
"code": "pms.folio",
|
||||
"padding": 4,
|
||||
"company_id": self.company1.id,
|
||||
}
|
||||
)
|
||||
self.reservation_sequence = self.env["ir.sequence"].create(
|
||||
{
|
||||
"name": "PMS Reservation",
|
||||
"code": "pms.reservation",
|
||||
"padding": 4,
|
||||
"company_id": self.company1.id,
|
||||
}
|
||||
)
|
||||
self.checkin_sequence = self.env["ir.sequence"].create(
|
||||
{
|
||||
"name": "PMS Checkin",
|
||||
"code": "pms.checkin.partner",
|
||||
"padding": 4,
|
||||
"company_id": self.company1.id,
|
||||
}
|
||||
)
|
||||
self.property1 = self.env["pms.property"].create(
|
||||
{
|
||||
"name": "Pms_property_test1",
|
||||
"company_id": self.company1.id,
|
||||
"default_pricelist_id": self.env.ref("product.list0").id,
|
||||
"folio_sequence_id": self.folio_sequence.id,
|
||||
"reservation_sequence_id": self.reservation_sequence.id,
|
||||
"checkin_sequence_id": self.checkin_sequence.id,
|
||||
}
|
||||
)
|
||||
self.property2 = self.env["pms.property"].create(
|
||||
@@ -20,6 +47,9 @@ class TestPmsBoardServiceRoomType(TestHotel):
|
||||
"name": "Pms_property_test2",
|
||||
"company_id": self.company1.id,
|
||||
"default_pricelist_id": self.env.ref("product.list0").id,
|
||||
"folio_sequence_id": self.folio_sequence.id,
|
||||
"reservation_sequence_id": self.reservation_sequence.id,
|
||||
"checkin_sequence_id": self.checkin_sequence.id,
|
||||
}
|
||||
)
|
||||
self.board_service = self.env["pms.board.service"].create(
|
||||
@@ -33,7 +63,7 @@ class TestPmsBoardServiceRoomType(TestHotel):
|
||||
self.room_type = self.env["pms.room.type"].create(
|
||||
{
|
||||
"name": "Room Type",
|
||||
"code_type": "Type1",
|
||||
"default_code": "Type1",
|
||||
"class_id": self.room_type_class.id,
|
||||
}
|
||||
)
|
||||
|
||||
@@ -1,20 +1,46 @@
|
||||
from odoo.exceptions import ValidationError
|
||||
|
||||
from .common import TestHotel
|
||||
from odoo.tests import common
|
||||
|
||||
|
||||
class TestPmsBoardServiceRoomTypeLine(TestHotel):
|
||||
class TestPmsBoardServiceRoomTypeLine(common.SavepointCase):
|
||||
def test_check_product_property_integrity(self):
|
||||
self.company1 = self.env["res.company"].create(
|
||||
{
|
||||
"name": "Pms_Company_Test",
|
||||
}
|
||||
)
|
||||
self.folio_sequence = self.env["ir.sequence"].create(
|
||||
{
|
||||
"name": "PMS Folio",
|
||||
"code": "pms.folio",
|
||||
"padding": 4,
|
||||
"company_id": self.company1.id,
|
||||
}
|
||||
)
|
||||
self.reservation_sequence = self.env["ir.sequence"].create(
|
||||
{
|
||||
"name": "PMS Reservation",
|
||||
"code": "pms.reservation",
|
||||
"padding": 4,
|
||||
"company_id": self.company1.id,
|
||||
}
|
||||
)
|
||||
self.checkin_sequence = self.env["ir.sequence"].create(
|
||||
{
|
||||
"name": "PMS Checkin",
|
||||
"code": "pms.checkin.partner",
|
||||
"padding": 4,
|
||||
"company_id": self.company1.id,
|
||||
}
|
||||
)
|
||||
self.property1 = self.env["pms.property"].create(
|
||||
{
|
||||
"name": "Pms_property_test1",
|
||||
"company_id": self.company1.id,
|
||||
"default_pricelist_id": self.env.ref("product.list0").id,
|
||||
"folio_sequence_id": self.folio_sequence.id,
|
||||
"reservation_sequence_id": self.reservation_sequence.id,
|
||||
"checkin_sequence_id": self.checkin_sequence.id,
|
||||
}
|
||||
)
|
||||
self.property2 = self.env["pms.property"].create(
|
||||
@@ -22,6 +48,9 @@ class TestPmsBoardServiceRoomTypeLine(TestHotel):
|
||||
"name": "Pms_property_test2",
|
||||
"company_id": self.company1.id,
|
||||
"default_pricelist_id": self.env.ref("product.list0").id,
|
||||
"folio_sequence_id": self.folio_sequence.id,
|
||||
"reservation_sequence_id": self.reservation_sequence.id,
|
||||
"checkin_sequence_id": self.checkin_sequence.id,
|
||||
}
|
||||
)
|
||||
self.board_service = self.env["pms.board.service"].create(
|
||||
@@ -39,7 +68,7 @@ class TestPmsBoardServiceRoomTypeLine(TestHotel):
|
||||
self.room_type = self.env["pms.room.type"].create(
|
||||
{
|
||||
"name": "Room Type",
|
||||
"code_type": "Type1",
|
||||
"default_code": "Type1",
|
||||
"class_id": self.room_type_class.id,
|
||||
}
|
||||
)
|
||||
|
||||
@@ -4,14 +4,13 @@ from freezegun import freeze_time
|
||||
|
||||
from odoo import fields
|
||||
from odoo.exceptions import ValidationError
|
||||
|
||||
from .common import TestHotel
|
||||
from odoo.tests import common
|
||||
|
||||
_logger = logging.getLogger(__name__)
|
||||
|
||||
|
||||
@freeze_time("2012-01-14")
|
||||
class TestPmsCheckinPartner(TestHotel):
|
||||
class TestPmsCheckinPartner(common.SavepointCase):
|
||||
@classmethod
|
||||
def arrange_single_checkin(cls):
|
||||
# Arrange for one checkin on one reservation
|
||||
@@ -336,7 +335,7 @@ class TestPmsCheckinPartner(TestHotel):
|
||||
"Fail the checkins data ratio on reservation",
|
||||
)
|
||||
|
||||
def test_auto_no_show(self):
|
||||
def test_auto_arrival_delayed(self):
|
||||
|
||||
# ARRANGE
|
||||
self.arrange_folio_reservations()
|
||||
@@ -345,21 +344,21 @@ class TestPmsCheckinPartner(TestHotel):
|
||||
# ACTION
|
||||
freezer = freeze_time("2012-01-15 10:00:00")
|
||||
freezer.start()
|
||||
PmsReservation.auto_no_show()
|
||||
PmsReservation.auto_arrival_delayed()
|
||||
|
||||
no_show_reservations = self.folio_1.reservation_ids.filtered(
|
||||
lambda r: r.state == "no_show"
|
||||
arrival_delayed_reservations = self.folio_1.reservation_ids.filtered(
|
||||
lambda r: r.state == "arrival_delayed"
|
||||
)
|
||||
|
||||
# ASSERT
|
||||
self.assertEqual(
|
||||
len(no_show_reservations),
|
||||
len(arrival_delayed_reservations),
|
||||
3,
|
||||
"Reservations not set like No Show",
|
||||
)
|
||||
freezer.stop()
|
||||
|
||||
def test_auto_no_checkout(self):
|
||||
def test_auto_departure_delayed(self):
|
||||
|
||||
# ARRANGE
|
||||
self.arrange_single_checkin()
|
||||
@@ -369,14 +368,14 @@ class TestPmsCheckinPartner(TestHotel):
|
||||
# ACTION
|
||||
freezer = freeze_time("2012-01-17 12:00:00")
|
||||
freezer.start()
|
||||
PmsReservation.auto_no_checkout()
|
||||
PmsReservation.auto_departure_delayed()
|
||||
|
||||
freezer.stop()
|
||||
# ASSERT
|
||||
self.assertEqual(
|
||||
self.reservation_1.state,
|
||||
"no_checkout",
|
||||
"Reservations not set like No checkout",
|
||||
"departure_delayed",
|
||||
"Reservations not set like Departure delayed",
|
||||
)
|
||||
|
||||
def test_not_valid_emails(self):
|
||||
|
||||
@@ -4,25 +4,51 @@ from freezegun import freeze_time
|
||||
|
||||
from odoo import fields
|
||||
from odoo.exceptions import ValidationError
|
||||
|
||||
from .common import TestHotel
|
||||
from odoo.tests import common
|
||||
|
||||
freeze_time("2000-02-02")
|
||||
|
||||
|
||||
class TestPmsFolio(TestHotel):
|
||||
class TestPmsFolio(common.SavepointCase):
|
||||
def create_common_scenario(self):
|
||||
# create a room type availability
|
||||
self.room_type_availability = self.env[
|
||||
"pms.room.type.availability.plan"
|
||||
].create({"name": "Availability plan for TEST"})
|
||||
|
||||
self.room_type_availability = self.env["pms.availability.plan"].create(
|
||||
{"name": "Availability plan for TEST"}
|
||||
)
|
||||
# sequences
|
||||
self.folio_sequence = self.env["ir.sequence"].create(
|
||||
{
|
||||
"name": "PMS Folio",
|
||||
"code": "pms.folio",
|
||||
"padding": 4,
|
||||
"company_id": self.env.ref("base.main_company").id,
|
||||
}
|
||||
)
|
||||
self.reservation_sequence = self.env["ir.sequence"].create(
|
||||
{
|
||||
"name": "PMS Reservation",
|
||||
"code": "pms.reservation",
|
||||
"padding": 4,
|
||||
"company_id": self.env.ref("base.main_company").id,
|
||||
}
|
||||
)
|
||||
self.checkin_sequence = self.env["ir.sequence"].create(
|
||||
{
|
||||
"name": "PMS Checkin",
|
||||
"code": "pms.checkin.partner",
|
||||
"padding": 4,
|
||||
"company_id": self.env.ref("base.main_company").id,
|
||||
}
|
||||
)
|
||||
# create a property
|
||||
self.property = self.env["pms.property"].create(
|
||||
{
|
||||
"name": "MY PMS TEST",
|
||||
"company_id": self.env.ref("base.main_company").id,
|
||||
"default_pricelist_id": self.env.ref("product.list0").id,
|
||||
"folio_sequence_id": self.folio_sequence.id,
|
||||
"reservation_sequence_id": self.reservation_sequence.id,
|
||||
"checkin_sequence_id": self.checkin_sequence.id,
|
||||
}
|
||||
)
|
||||
|
||||
@@ -36,7 +62,7 @@ class TestPmsFolio(TestHotel):
|
||||
{
|
||||
"pms_property_ids": [self.property.id],
|
||||
"name": "Double Test",
|
||||
"code_type": "DBL_Test",
|
||||
"default_code": "DBL_Test",
|
||||
"class_id": self.room_type_class.id,
|
||||
"price": 25,
|
||||
}
|
||||
@@ -62,11 +88,15 @@ class TestPmsFolio(TestHotel):
|
||||
)
|
||||
|
||||
def create_multiproperty_scenario(self):
|
||||
self.create_common_scenario()
|
||||
self.property1 = self.env["pms.property"].create(
|
||||
{
|
||||
"name": "Property_1",
|
||||
"company_id": self.env.ref("base.main_company").id,
|
||||
"default_pricelist_id": self.env.ref("product.list0").id,
|
||||
"folio_sequence_id": self.folio_sequence.id,
|
||||
"reservation_sequence_id": self.reservation_sequence.id,
|
||||
"checkin_sequence_id": self.checkin_sequence.id,
|
||||
}
|
||||
)
|
||||
|
||||
@@ -75,6 +105,9 @@ class TestPmsFolio(TestHotel):
|
||||
"name": "Property_2",
|
||||
"company_id": self.env.ref("base.main_company").id,
|
||||
"default_pricelist_id": self.env.ref("product.list0").id,
|
||||
"folio_sequence_id": self.folio_sequence.id,
|
||||
"reservation_sequence_id": self.reservation_sequence.id,
|
||||
"checkin_sequence_id": self.checkin_sequence.id,
|
||||
}
|
||||
)
|
||||
|
||||
@@ -83,6 +116,9 @@ class TestPmsFolio(TestHotel):
|
||||
"name": "Property_3",
|
||||
"company_id": self.env.ref("base.main_company").id,
|
||||
"default_pricelist_id": self.env.ref("product.list0").id,
|
||||
"folio_sequence_id": self.folio_sequence.id,
|
||||
"reservation_sequence_id": self.reservation_sequence.id,
|
||||
"checkin_sequence_id": self.checkin_sequence.id,
|
||||
}
|
||||
)
|
||||
|
||||
@@ -101,7 +137,7 @@ class TestPmsFolio(TestHotel):
|
||||
{
|
||||
"name": "partner1",
|
||||
"is_agency": True,
|
||||
"invoice_agency": True,
|
||||
"invoice_to_agency": True,
|
||||
"default_commission": 15,
|
||||
"sale_channel_id": saleChannel.id,
|
||||
}
|
||||
@@ -149,7 +185,7 @@ class TestPmsFolio(TestHotel):
|
||||
"pms_property_id": self.property.id,
|
||||
}
|
||||
)
|
||||
r1.left_for_checkin = False
|
||||
r1.allowed_checkin = False
|
||||
|
||||
self.env["pms.reservation"].create(
|
||||
{
|
||||
@@ -250,3 +286,35 @@ class TestPmsFolio(TestHotel):
|
||||
"closure_reason_id": cl_reason.id,
|
||||
}
|
||||
)
|
||||
|
||||
def _test_compute_currency(self):
|
||||
self.create_common_scenario()
|
||||
self.currency1 = self.env["res.currency"].create(
|
||||
{
|
||||
"name": "currency1",
|
||||
"symbol": "C",
|
||||
}
|
||||
)
|
||||
self.pricelist = self.env["product.pricelist"].create(
|
||||
{
|
||||
"name": "pricelist 1",
|
||||
"pms_property_ids": [
|
||||
(4, self.property.id),
|
||||
],
|
||||
"currency_id": self.currency1.id,
|
||||
}
|
||||
)
|
||||
self.reservation1 = self.env["pms.reservation"].create(
|
||||
{
|
||||
"pms_property_id": self.property.id,
|
||||
"checkin": datetime.datetime.now(),
|
||||
"checkout": datetime.datetime.now() + datetime.timedelta(days=1),
|
||||
"partner_id": self.env.ref("base.res_partner_12").id,
|
||||
"pricelist_id": self.pricelist.id,
|
||||
}
|
||||
)
|
||||
self.assertEqual(
|
||||
self.currency1.id,
|
||||
self.reservation1.folio_id.currency_id.id,
|
||||
"Currency must match",
|
||||
)
|
||||
|
||||
@@ -1,23 +1,51 @@
|
||||
import datetime
|
||||
|
||||
from .common import TestHotel
|
||||
from odoo.tests import common
|
||||
|
||||
|
||||
class TestPmsFolioInvoice(TestHotel):
|
||||
class TestPmsFolioInvoice(common.SavepointCase):
|
||||
def setUp(self):
|
||||
super(TestPmsFolioInvoice, self).setUp()
|
||||
|
||||
def create_common_scenario(self):
|
||||
# create a room type availability
|
||||
self.room_type_availability = self.env[
|
||||
"pms.room.type.availability.plan"
|
||||
].create({"name": "Availability plan for TEST"})
|
||||
# sequences
|
||||
self.folio_sequence = self.env["ir.sequence"].create(
|
||||
{
|
||||
"name": "PMS Folio",
|
||||
"code": "pms.folio",
|
||||
"padding": 4,
|
||||
"company_id": self.env.ref("base.main_company").id,
|
||||
}
|
||||
)
|
||||
self.reservation_sequence = self.env["ir.sequence"].create(
|
||||
{
|
||||
"name": "PMS Reservation",
|
||||
"code": "pms.reservation",
|
||||
"padding": 4,
|
||||
"company_id": self.env.ref("base.main_company").id,
|
||||
}
|
||||
)
|
||||
self.checkin_sequence = self.env["ir.sequence"].create(
|
||||
{
|
||||
"name": "PMS Checkin",
|
||||
"code": "pms.checkin.partner",
|
||||
"padding": 4,
|
||||
"company_id": self.env.ref("base.main_company").id,
|
||||
}
|
||||
)
|
||||
self.room_type_availability = self.env["pms.availability.plan"].create(
|
||||
{"name": "Availability plan for TEST"}
|
||||
)
|
||||
# create a property
|
||||
self.property = self.env["pms.property"].create(
|
||||
{
|
||||
"name": "MY PMS TEST",
|
||||
"company_id": self.env.ref("base.main_company").id,
|
||||
"default_pricelist_id": self.env.ref("product.list0").id,
|
||||
"folio_sequence_id": self.folio_sequence.id,
|
||||
"reservation_sequence_id": self.reservation_sequence.id,
|
||||
"checkin_sequence_id": self.checkin_sequence.id,
|
||||
}
|
||||
)
|
||||
# create room type class
|
||||
@@ -30,7 +58,7 @@ class TestPmsFolioInvoice(TestHotel):
|
||||
{
|
||||
"pms_property_ids": [self.property.id],
|
||||
"name": "Double Test",
|
||||
"code_type": "DBL_Test",
|
||||
"default_code": "DBL_Test",
|
||||
"class_id": self.room_type_class.id,
|
||||
"price": 25,
|
||||
}
|
||||
|
||||
@@ -5,13 +5,42 @@ from odoo.tests import common, tagged
|
||||
|
||||
|
||||
@tagged("standard", "nice")
|
||||
class TestPmsPricelist(common.TransactionCase):
|
||||
class TestPmsPricelist(common.SavepointCase):
|
||||
def create_common_scenario(self):
|
||||
# sequences
|
||||
self.folio_sequence = self.env["ir.sequence"].create(
|
||||
{
|
||||
"name": "PMS Folio",
|
||||
"code": "pms.folio",
|
||||
"padding": 4,
|
||||
"company_id": self.env.ref("base.main_company").id,
|
||||
}
|
||||
)
|
||||
self.reservation_sequence = self.env["ir.sequence"].create(
|
||||
{
|
||||
"name": "PMS Reservation",
|
||||
"code": "pms.reservation",
|
||||
"padding": 4,
|
||||
"company_id": self.env.ref("base.main_company").id,
|
||||
}
|
||||
)
|
||||
self.checkin_sequence = self.env["ir.sequence"].create(
|
||||
{
|
||||
"name": "PMS Checkin",
|
||||
"code": "pms.checkin.partner",
|
||||
"padding": 4,
|
||||
"company_id": self.env.ref("base.main_company").id,
|
||||
}
|
||||
)
|
||||
# create property
|
||||
self.property1 = self.env["pms.property"].create(
|
||||
{
|
||||
"name": "Property_1",
|
||||
"company_id": self.env.ref("base.main_company").id,
|
||||
"default_pricelist_id": self.env.ref("product.list0").id,
|
||||
"folio_sequence_id": self.folio_sequence.id,
|
||||
"reservation_sequence_id": self.reservation_sequence.id,
|
||||
"checkin_sequence_id": self.checkin_sequence.id,
|
||||
}
|
||||
)
|
||||
|
||||
@@ -20,6 +49,9 @@ class TestPmsPricelist(common.TransactionCase):
|
||||
"name": "Property_2",
|
||||
"company_id": self.env.ref("base.main_company").id,
|
||||
"default_pricelist_id": self.env.ref("product.list0").id,
|
||||
"folio_sequence_id": self.folio_sequence.id,
|
||||
"reservation_sequence_id": self.reservation_sequence.id,
|
||||
"checkin_sequence_id": self.checkin_sequence.id,
|
||||
}
|
||||
)
|
||||
|
||||
@@ -28,6 +60,9 @@ class TestPmsPricelist(common.TransactionCase):
|
||||
"name": "Property_3",
|
||||
"company_id": self.env.ref("base.main_company").id,
|
||||
"default_pricelist_id": self.env.ref("product.list0").id,
|
||||
"folio_sequence_id": self.folio_sequence.id,
|
||||
"reservation_sequence_id": self.reservation_sequence.id,
|
||||
"checkin_sequence_id": self.checkin_sequence.id,
|
||||
}
|
||||
)
|
||||
self.room_type_class = self.env["pms.room.type.class"].create(
|
||||
@@ -38,7 +73,7 @@ class TestPmsPricelist(common.TransactionCase):
|
||||
{
|
||||
"pms_property_ids": [self.property1.id, self.property2.id],
|
||||
"name": "Single",
|
||||
"code_type": "SIN",
|
||||
"default_code": "SIN",
|
||||
"class_id": self.room_type_class.id,
|
||||
"list_price": 30,
|
||||
}
|
||||
@@ -151,7 +186,7 @@ class TestPmsPricelist(common.TransactionCase):
|
||||
|
||||
def test_availability_plan_property_integrity(self):
|
||||
self.create_common_scenario()
|
||||
self.availability_plan = self.env["pms.room.type.availability.plan"].create(
|
||||
self.availability_plan = self.env["pms.availability.plan"].create(
|
||||
{"name": "Availability Plan", "pms_property_ids": [self.property1.id]}
|
||||
)
|
||||
with self.assertRaises(ValidationError):
|
||||
|
||||
@@ -5,7 +5,7 @@ from freezegun import freeze_time
|
||||
from odoo.tests import common
|
||||
|
||||
|
||||
class TestPmsPricelistRules(common.TransactionCase):
|
||||
class TestPmsPricelistRules(common.SavepointCase):
|
||||
def create_common_scenario(self):
|
||||
self.product_template = self.env["product.template"].create(
|
||||
{"name": "Template1"}
|
||||
@@ -14,18 +14,46 @@ class TestPmsPricelistRules(common.TransactionCase):
|
||||
{"name": "Category1"}
|
||||
)
|
||||
|
||||
self.availability_plan1 = self.env["pms.room.type.availability.plan"].create(
|
||||
self.availability_plan1 = self.env["pms.availability.plan"].create(
|
||||
{"name": "Availability 1"}
|
||||
)
|
||||
|
||||
self.availability_plan2 = self.env["pms.room.type.availability.plan"].create(
|
||||
self.availability_plan2 = self.env["pms.availability.plan"].create(
|
||||
{"name": "Availability"}
|
||||
)
|
||||
# sequences
|
||||
self.folio_sequence = self.env["ir.sequence"].create(
|
||||
{
|
||||
"name": "PMS Folio",
|
||||
"code": "pms.folio",
|
||||
"padding": 4,
|
||||
"company_id": self.env.ref("base.main_company").id,
|
||||
}
|
||||
)
|
||||
self.reservation_sequence = self.env["ir.sequence"].create(
|
||||
{
|
||||
"name": "PMS Reservation",
|
||||
"code": "pms.reservation",
|
||||
"padding": 4,
|
||||
"company_id": self.env.ref("base.main_company").id,
|
||||
}
|
||||
)
|
||||
self.checkin_sequence = self.env["ir.sequence"].create(
|
||||
{
|
||||
"name": "PMS Checkin",
|
||||
"code": "pms.checkin.partner",
|
||||
"padding": 4,
|
||||
"company_id": self.env.ref("base.main_company").id,
|
||||
}
|
||||
)
|
||||
self.property1 = self.env["pms.property"].create(
|
||||
{
|
||||
"name": "Property_1",
|
||||
"company_id": self.env.ref("base.main_company").id,
|
||||
"default_pricelist_id": self.env.ref("product.list0").id,
|
||||
"folio_sequence_id": self.folio_sequence.id,
|
||||
"reservation_sequence_id": self.reservation_sequence.id,
|
||||
"checkin_sequence_id": self.checkin_sequence.id,
|
||||
}
|
||||
)
|
||||
|
||||
@@ -34,6 +62,9 @@ class TestPmsPricelistRules(common.TransactionCase):
|
||||
"name": "Property_2",
|
||||
"company_id": self.env.ref("base.main_company").id,
|
||||
"default_pricelist_id": self.env.ref("product.list0").id,
|
||||
"folio_sequence_id": self.folio_sequence.id,
|
||||
"reservation_sequence_id": self.reservation_sequence.id,
|
||||
"checkin_sequence_id": self.checkin_sequence.id,
|
||||
}
|
||||
)
|
||||
|
||||
@@ -45,7 +76,7 @@ class TestPmsPricelistRules(common.TransactionCase):
|
||||
{
|
||||
"pms_property_ids": [self.property1.id, self.property2.id],
|
||||
"name": "Single",
|
||||
"code_type": "SIN",
|
||||
"default_code": "SIN",
|
||||
"class_id": self.room_type_class.id,
|
||||
"list_price": 30,
|
||||
}
|
||||
|
||||
@@ -2,12 +2,12 @@ from odoo.exceptions import ValidationError
|
||||
from odoo.tests import common
|
||||
|
||||
|
||||
class TestPmsResUser(common.TransactionCase):
|
||||
class TestPmsResUser(common.SavepointCase):
|
||||
def create_common_scenario(self):
|
||||
# create a room type availability
|
||||
self.room_type_availability = self.env[
|
||||
"pms.room.type.availability.plan"
|
||||
].create({"name": "Availability plan 1"})
|
||||
self.room_type_availability = self.env["pms.availability.plan"].create(
|
||||
{"name": "Availability plan 1"}
|
||||
)
|
||||
|
||||
# create a company and properties
|
||||
self.company_A = self.env["res.company"].create(
|
||||
@@ -20,11 +20,62 @@ class TestPmsResUser(common.TransactionCase):
|
||||
"name": "Pms_Company2",
|
||||
}
|
||||
)
|
||||
self.folio_sequenceA = self.env["ir.sequence"].create(
|
||||
{
|
||||
"name": "PMS Folio",
|
||||
"code": "pms.folio",
|
||||
"padding": 4,
|
||||
"company_id": self.company_A.id,
|
||||
}
|
||||
)
|
||||
self.reservation_sequenceA = self.env["ir.sequence"].create(
|
||||
{
|
||||
"name": "PMS Reservation",
|
||||
"code": "pms.reservation",
|
||||
"padding": 4,
|
||||
"company_id": self.company_A.id,
|
||||
}
|
||||
)
|
||||
self.checkin_sequenceA = self.env["ir.sequence"].create(
|
||||
{
|
||||
"name": "PMS Checkin",
|
||||
"code": "pms.checkin.partner",
|
||||
"padding": 4,
|
||||
"company_id": self.company_A.id,
|
||||
}
|
||||
)
|
||||
self.folio_sequenceB = self.env["ir.sequence"].create(
|
||||
{
|
||||
"name": "PMS Folio",
|
||||
"code": "pms.folio",
|
||||
"padding": 4,
|
||||
"company_id": self.company_B.id,
|
||||
}
|
||||
)
|
||||
self.reservation_sequenceB = self.env["ir.sequence"].create(
|
||||
{
|
||||
"name": "PMS Reservation",
|
||||
"code": "pms.reservation",
|
||||
"padding": 4,
|
||||
"company_id": self.company_B.id,
|
||||
}
|
||||
)
|
||||
self.checkin_sequenceB = self.env["ir.sequence"].create(
|
||||
{
|
||||
"name": "PMS Checkin",
|
||||
"code": "pms.checkin.partner",
|
||||
"padding": 4,
|
||||
"company_id": self.company_B.id,
|
||||
}
|
||||
)
|
||||
self.property_A1 = self.env["pms.property"].create(
|
||||
{
|
||||
"name": "Pms_property",
|
||||
"company_id": self.company_A.id,
|
||||
"default_pricelist_id": self.env.ref("product.list0").id,
|
||||
"folio_sequence_id": self.folio_sequenceA.id,
|
||||
"reservation_sequence_id": self.reservation_sequenceA.id,
|
||||
"checkin_sequence_id": self.checkin_sequenceA.id,
|
||||
}
|
||||
)
|
||||
self.property_A2 = self.env["pms.property"].create(
|
||||
@@ -32,6 +83,9 @@ class TestPmsResUser(common.TransactionCase):
|
||||
"name": "Pms_property2",
|
||||
"company_id": self.company_A.id,
|
||||
"default_pricelist_id": self.env.ref("product.list0").id,
|
||||
"folio_sequence_id": self.folio_sequenceA.id,
|
||||
"reservation_sequence_id": self.reservation_sequenceA.id,
|
||||
"checkin_sequence_id": self.checkin_sequenceA.id,
|
||||
}
|
||||
)
|
||||
self.property_B1 = self.env["pms.property"].create(
|
||||
@@ -39,6 +93,9 @@ class TestPmsResUser(common.TransactionCase):
|
||||
"name": "Pms_propertyB1",
|
||||
"company_id": self.company_B.id,
|
||||
"default_pricelist_id": self.env.ref("product.list0").id,
|
||||
"folio_sequence_id": self.folio_sequenceB.id,
|
||||
"reservation_sequence_id": self.reservation_sequenceB.id,
|
||||
"checkin_sequence_id": self.checkin_sequenceB.id,
|
||||
}
|
||||
)
|
||||
|
||||
|
||||
@@ -3,25 +3,61 @@ import datetime
|
||||
from freezegun import freeze_time
|
||||
|
||||
from odoo import fields
|
||||
from odoo.exceptions import ValidationError
|
||||
|
||||
from .common import TestHotel
|
||||
from odoo.exceptions import UserError, ValidationError
|
||||
from odoo.tests import common
|
||||
|
||||
|
||||
@freeze_time("2012-01-14")
|
||||
class TestPmsReservations(TestHotel):
|
||||
class TestPmsReservations(common.SavepointCase):
|
||||
def create_common_scenario(self):
|
||||
# create a room type availability
|
||||
self.room_type_availability = self.env[
|
||||
"pms.room.type.availability.plan"
|
||||
].create({"name": "Availability plan for TEST"})
|
||||
|
||||
self.test_pricelist1 = self.env["product.pricelist"].create(
|
||||
{
|
||||
"name": "test pricelist 1",
|
||||
}
|
||||
)
|
||||
# create a room type availability
|
||||
self.room_type_availability = self.env["pms.availability.plan"].create(
|
||||
{
|
||||
"name": "Availability plan for TEST",
|
||||
"pms_pricelist_ids": [(6, 0, [self.test_pricelist1.id])],
|
||||
}
|
||||
)
|
||||
|
||||
# create a sequences
|
||||
self.folio_sequence = self.env["ir.sequence"].create(
|
||||
{
|
||||
"name": "PMS Folio",
|
||||
"code": "pms.folio",
|
||||
"padding": 4,
|
||||
"company_id": self.env.ref("base.main_company").id,
|
||||
}
|
||||
)
|
||||
self.reservation_sequence = self.env["ir.sequence"].create(
|
||||
{
|
||||
"name": "PMS Reservation",
|
||||
"code": "pms.reservation",
|
||||
"padding": 4,
|
||||
"company_id": self.env.ref("base.main_company").id,
|
||||
}
|
||||
)
|
||||
self.checkin_sequence = self.env["ir.sequence"].create(
|
||||
{
|
||||
"name": "PMS Checkin",
|
||||
"code": "pms.checkin.partner",
|
||||
"padding": 4,
|
||||
"company_id": self.env.ref("base.main_company").id,
|
||||
}
|
||||
)
|
||||
# create a property
|
||||
self.property = self.env["pms.property"].create(
|
||||
{
|
||||
"name": "MY PMS TEST",
|
||||
"company_id": self.env.ref("base.main_company").id,
|
||||
"default_pricelist_id": self.env.ref("product.list0").id,
|
||||
"default_pricelist_id": self.test_pricelist1.id,
|
||||
"folio_sequence_id": self.folio_sequence.id,
|
||||
"reservation_sequence_id": self.reservation_sequence.id,
|
||||
"checkin_sequence_id": self.checkin_sequence.id,
|
||||
}
|
||||
)
|
||||
|
||||
@@ -35,7 +71,7 @@ class TestPmsReservations(TestHotel):
|
||||
{
|
||||
"pms_property_ids": [self.property.id],
|
||||
"name": "Double Test",
|
||||
"code_type": "DBL_Test",
|
||||
"default_code": "DBL_Test",
|
||||
"class_id": self.room_type_class.id,
|
||||
}
|
||||
)
|
||||
@@ -70,11 +106,15 @@ class TestPmsReservations(TestHotel):
|
||||
self.demo_user = self.env.ref("base.user_admin")
|
||||
|
||||
def create_multiproperty_scenario(self):
|
||||
self.create_common_scenario()
|
||||
self.property1 = self.env["pms.property"].create(
|
||||
{
|
||||
"name": "Property_1",
|
||||
"company_id": self.env.ref("base.main_company").id,
|
||||
"default_pricelist_id": self.env.ref("product.list0").id,
|
||||
"folio_sequence_id": self.folio_sequence.id,
|
||||
"reservation_sequence_id": self.reservation_sequence.id,
|
||||
"checkin_sequence_id": self.checkin_sequence.id,
|
||||
}
|
||||
)
|
||||
|
||||
@@ -83,6 +123,9 @@ class TestPmsReservations(TestHotel):
|
||||
"name": "Property_2",
|
||||
"company_id": self.env.ref("base.main_company").id,
|
||||
"default_pricelist_id": self.env.ref("product.list0").id,
|
||||
"folio_sequence_id": self.folio_sequence.id,
|
||||
"reservation_sequence_id": self.reservation_sequence.id,
|
||||
"checkin_sequence_id": self.checkin_sequence.id,
|
||||
}
|
||||
)
|
||||
|
||||
@@ -91,6 +134,9 @@ class TestPmsReservations(TestHotel):
|
||||
"name": "Property_3",
|
||||
"company_id": self.env.ref("base.main_company").id,
|
||||
"default_pricelist_id": self.env.ref("product.list0").id,
|
||||
"folio_sequence_id": self.folio_sequence.id,
|
||||
"reservation_sequence_id": self.reservation_sequence.id,
|
||||
"checkin_sequence_id": self.checkin_sequence.id,
|
||||
}
|
||||
)
|
||||
self.room_type_class = self.env["pms.room.type.class"].create(
|
||||
@@ -109,6 +155,7 @@ class TestPmsReservations(TestHotel):
|
||||
# reservation should start on checkin day
|
||||
|
||||
# ARRANGE
|
||||
self.create_common_scenario()
|
||||
today = fields.date.today()
|
||||
checkin = today + datetime.timedelta(days=8)
|
||||
checkout = checkin + datetime.timedelta(days=11)
|
||||
@@ -116,9 +163,9 @@ class TestPmsReservations(TestHotel):
|
||||
reservation_vals = {
|
||||
"checkin": checkin,
|
||||
"checkout": checkout,
|
||||
"room_type_id": self.room_type_3.id,
|
||||
"room_type_id": self.room_type_double.id,
|
||||
"partner_id": customer.id,
|
||||
"pms_property_id": self.main_hotel_property.id,
|
||||
"pms_property_id": self.property.id,
|
||||
}
|
||||
|
||||
# ACT
|
||||
@@ -134,7 +181,7 @@ class TestPmsReservations(TestHotel):
|
||||
def test_create_reservation_end_date(self):
|
||||
# TEST CASE
|
||||
# reservation should end on checkout day
|
||||
|
||||
self.create_common_scenario()
|
||||
# ARRANGE
|
||||
today = fields.date.today()
|
||||
checkin = today + datetime.timedelta(days=8)
|
||||
@@ -143,9 +190,9 @@ class TestPmsReservations(TestHotel):
|
||||
reservation_vals = {
|
||||
"checkin": checkin,
|
||||
"checkout": checkout,
|
||||
"room_type_id": self.room_type_3.id,
|
||||
"room_type_id": self.room_type_double.id,
|
||||
"partner_id": customer.id,
|
||||
"pms_property_id": self.main_hotel_property.id,
|
||||
"pms_property_id": self.property.id,
|
||||
}
|
||||
|
||||
# ACT
|
||||
@@ -637,7 +684,7 @@ class TestPmsReservations(TestHotel):
|
||||
self.assertEqual(r1, reservations[0])
|
||||
|
||||
@freeze_time("1981-11-01")
|
||||
def test_order_priority_left_for_checkin(self):
|
||||
def test_order_priority_allowed_checkin(self):
|
||||
# ARRANGE
|
||||
self.create_common_scenario()
|
||||
r1 = self.env["pms.reservation"].create(
|
||||
@@ -658,7 +705,7 @@ class TestPmsReservations(TestHotel):
|
||||
"pms_property_id": self.property.id,
|
||||
}
|
||||
)
|
||||
r1.left_for_checkin = False
|
||||
r1.allowed_checkin = False
|
||||
# ACT
|
||||
reservations = self.env["pms.reservation"].search(
|
||||
[("pms_property_id", "=", self.property.id)]
|
||||
@@ -667,7 +714,7 @@ class TestPmsReservations(TestHotel):
|
||||
self.assertEqual(r1, reservations[0])
|
||||
|
||||
@freeze_time("1981-11-01")
|
||||
def test_order_priority_left_for_checkout(self):
|
||||
def test_order_priority_allowed_checkout(self):
|
||||
# ARRANGE
|
||||
self.create_common_scenario()
|
||||
r1 = self.env["pms.reservation"].create(
|
||||
@@ -688,7 +735,7 @@ class TestPmsReservations(TestHotel):
|
||||
"pms_property_id": self.property.id,
|
||||
}
|
||||
)
|
||||
r1.left_for_checkout = True
|
||||
r1.allowed_checkout = True
|
||||
# ACT
|
||||
reservations = self.env["pms.reservation"].search(
|
||||
[("pms_property_id", "=", self.property.id)]
|
||||
@@ -816,7 +863,9 @@ class TestPmsReservations(TestHotel):
|
||||
checkin.flush()
|
||||
|
||||
# ACT
|
||||
r1.action_reservation_checkout()
|
||||
with freeze_time("1981-11-02"):
|
||||
r1._cache.clear()
|
||||
r1.action_reservation_checkout()
|
||||
|
||||
# ASSERT
|
||||
self.assertEqual(
|
||||
@@ -861,7 +910,7 @@ class TestPmsReservations(TestHotel):
|
||||
(4, self.property2.id),
|
||||
],
|
||||
"name": "Single",
|
||||
"code_type": "SIN",
|
||||
"default_code": "SIN",
|
||||
"class_id": self.room_type_class.id,
|
||||
"list_price": 30,
|
||||
}
|
||||
@@ -903,3 +952,622 @@ class TestPmsReservations(TestHotel):
|
||||
with self.subTest(k=test_case):
|
||||
with self.assertRaises(ValidationError):
|
||||
self.reservation_test.write(test_case)
|
||||
|
||||
@freeze_time("1950-11-01")
|
||||
def _test_check_date_order(self):
|
||||
self.create_common_scenario()
|
||||
customer = self.env.ref("base.res_partner_12")
|
||||
reservation = self.env["pms.reservation"].create(
|
||||
{
|
||||
"pms_property_id": self.property.id,
|
||||
"checkin": fields.date.today(),
|
||||
"checkout": fields.date.today() + datetime.timedelta(days=3),
|
||||
"partner_id": customer.id,
|
||||
}
|
||||
)
|
||||
|
||||
reservation.flush()
|
||||
self.assertEqual(
|
||||
str(reservation.date_order),
|
||||
str(fields.date.today()),
|
||||
"Date Order isn't correct",
|
||||
)
|
||||
|
||||
def _test_check_checkin_datetime(self):
|
||||
self.create_common_scenario()
|
||||
customer = self.env.ref("base.res_partner_12")
|
||||
reservation = self.env["pms.reservation"].create(
|
||||
{
|
||||
"pms_property_id": self.property.id,
|
||||
"checkin": fields.date.today() + datetime.timedelta(days=300),
|
||||
"checkout": fields.date.today() + datetime.timedelta(days=305),
|
||||
"partner_id": customer.id,
|
||||
}
|
||||
)
|
||||
r = reservation.checkin
|
||||
checkin_expected = datetime.datetime(r.year, r.month, r.day, 14, 00)
|
||||
# checkin_expected = checkin_expected.astimezone(self.property.tz.value)
|
||||
|
||||
self.assertEqual(
|
||||
str(reservation.checkin_datetime),
|
||||
str(checkin_expected),
|
||||
"Date Order isn't correct",
|
||||
)
|
||||
|
||||
def test_check_allowed_room_ids(self):
|
||||
self.create_common_scenario()
|
||||
customer = self.env.ref("base.res_partner_12")
|
||||
availability_rule = self.env["pms.availability.plan.rule"].create(
|
||||
{
|
||||
"pms_property_id": self.property.id,
|
||||
"room_type_id": self.room_type_double.id,
|
||||
"availability_plan_id": self.room_type_availability.id,
|
||||
"date": fields.date.today() + datetime.timedelta(days=153),
|
||||
}
|
||||
)
|
||||
reservation = self.env["pms.reservation"].create(
|
||||
{
|
||||
"pms_property_id": self.property.id,
|
||||
"checkin": fields.date.today() + datetime.timedelta(days=150),
|
||||
"checkout": fields.date.today() + datetime.timedelta(days=152),
|
||||
"partner_id": customer.id,
|
||||
"room_type_id": self.room_type_double.id,
|
||||
"pricelist_id": self.test_pricelist1.id,
|
||||
}
|
||||
)
|
||||
self.assertEqual(
|
||||
reservation.allowed_room_ids,
|
||||
availability_rule.room_type_id.room_ids,
|
||||
"Rooms allowed don't match",
|
||||
)
|
||||
|
||||
def _test_partner_is_agency(self):
|
||||
self.create_common_scenario()
|
||||
sale_channel1 = self.env["pms.sale.channel"].create(
|
||||
{"name": "Test Indirect", "channel_type": "indirect"}
|
||||
)
|
||||
agency = self.env["res.partner"].create(
|
||||
{
|
||||
"name": "partner1",
|
||||
"is_agency": True,
|
||||
"sale_channel_id": sale_channel1.id,
|
||||
}
|
||||
)
|
||||
|
||||
reservation = self.env["pms.reservation"].create(
|
||||
{
|
||||
"pms_property_id": self.property.id,
|
||||
"checkin": fields.date.today() + datetime.timedelta(days=150),
|
||||
"checkout": fields.date.today() + datetime.timedelta(days=152),
|
||||
# "partner_id": False,
|
||||
"agency_id": agency.id,
|
||||
# "folio_id":False,
|
||||
}
|
||||
)
|
||||
|
||||
reservation.flush()
|
||||
|
||||
self.assertEqual(
|
||||
reservation.partner_id.id,
|
||||
agency.id,
|
||||
"Partner_id doesn't match with agency_id",
|
||||
)
|
||||
|
||||
def test_agency_pricelist(self):
|
||||
self.create_common_scenario()
|
||||
sale_channel1 = self.env["pms.sale.channel"].create(
|
||||
{
|
||||
"name": "Test Indirect",
|
||||
"channel_type": "indirect",
|
||||
"product_pricelist_ids": [(6, 0, [self.test_pricelist1.id])],
|
||||
}
|
||||
)
|
||||
agency = self.env["res.partner"].create(
|
||||
{
|
||||
"name": "partner1",
|
||||
"is_agency": True,
|
||||
"sale_channel_id": sale_channel1.id,
|
||||
"apply_pricelist": True,
|
||||
}
|
||||
)
|
||||
|
||||
reservation = self.env["pms.reservation"].create(
|
||||
{
|
||||
"pms_property_id": self.property.id,
|
||||
"checkin": fields.date.today() + datetime.timedelta(days=150),
|
||||
"checkout": fields.date.today() + datetime.timedelta(days=152),
|
||||
"agency_id": agency.id,
|
||||
}
|
||||
)
|
||||
|
||||
self.assertEqual(
|
||||
reservation.pricelist_id.id,
|
||||
reservation.agency_id.property_product_pricelist.id,
|
||||
"Rervation pricelist doesn't match with Agency pricelist",
|
||||
)
|
||||
|
||||
def test_compute_access_url(self):
|
||||
self.create_common_scenario()
|
||||
customer = self.env.ref("base.res_partner_12")
|
||||
reservation = self.env["pms.reservation"].create(
|
||||
{
|
||||
"pms_property_id": self.property.id,
|
||||
"checkin": fields.date.today() + datetime.timedelta(days=150),
|
||||
"checkout": fields.date.today() + datetime.timedelta(days=152),
|
||||
"partner_id": customer.id,
|
||||
}
|
||||
)
|
||||
|
||||
url = "/my/reservations/%s" % reservation.id
|
||||
self.assertEqual(reservation.access_url, url, "Reservation url isn't correct")
|
||||
|
||||
def test_compute_ready_for_checkin(self):
|
||||
self.create_common_scenario()
|
||||
self.host1 = self.env["res.partner"].create(
|
||||
{
|
||||
"name": "Miguel",
|
||||
"phone": "654667733",
|
||||
"email": "miguel@example.com",
|
||||
}
|
||||
)
|
||||
self.host2 = self.env["res.partner"].create(
|
||||
{
|
||||
"name": "Brais",
|
||||
"phone": "654437733",
|
||||
"email": "brais@example.com",
|
||||
}
|
||||
)
|
||||
self.reservation = self.env["pms.reservation"].create(
|
||||
{
|
||||
"checkin": "2012-01-14",
|
||||
"checkout": "2012-01-17",
|
||||
"partner_id": self.host1.id,
|
||||
"allowed_checkin": True,
|
||||
"pms_property_id": self.property.id,
|
||||
"adults": 3,
|
||||
}
|
||||
)
|
||||
self.checkin1 = self.env["pms.checkin.partner"].create(
|
||||
{
|
||||
"partner_id": self.host1.id,
|
||||
"reservation_id": self.reservation.id,
|
||||
}
|
||||
)
|
||||
self.checkin2 = self.env["pms.checkin.partner"].create(
|
||||
{
|
||||
"partner_id": self.host2.id,
|
||||
"reservation_id": self.reservation.id,
|
||||
}
|
||||
)
|
||||
|
||||
self.reservation.checkin_partner_ids = [
|
||||
(6, 0, [self.checkin1.id, self.checkin2.id])
|
||||
]
|
||||
|
||||
self.assertTrue(
|
||||
self.reservation.ready_for_checkin,
|
||||
"Reservation should is ready for checkin",
|
||||
)
|
||||
|
||||
def test_check_checkin_less_checkout(self):
|
||||
self.create_common_scenario()
|
||||
self.host1 = self.env["res.partner"].create(
|
||||
{
|
||||
"name": "Host1",
|
||||
}
|
||||
)
|
||||
with self.assertRaises(ValidationError):
|
||||
self.env["pms.reservation"].create(
|
||||
{
|
||||
"checkin": fields.date.today() + datetime.timedelta(days=3),
|
||||
"checkout": fields.date.today(),
|
||||
"pms_property_id": self.property.id,
|
||||
"partner_id": self.host1.id,
|
||||
}
|
||||
)
|
||||
|
||||
def test_check_adults(self):
|
||||
self.create_common_scenario()
|
||||
self.host1 = self.env["res.partner"].create(
|
||||
{
|
||||
"name": "Host1",
|
||||
}
|
||||
)
|
||||
with self.assertRaises(ValidationError):
|
||||
self.env["pms.reservation"].create(
|
||||
{
|
||||
"checkin": fields.date.today() + datetime.timedelta(days=3),
|
||||
"checkout": fields.date.today(),
|
||||
"pms_property_id": self.property.id,
|
||||
"partner_id": self.host1.id,
|
||||
"room_type_id": self.room_type_double.id,
|
||||
"adults": 4,
|
||||
}
|
||||
)
|
||||
|
||||
def test_check_arrival_hour(self):
|
||||
self.create_common_scenario()
|
||||
self.host1 = self.env["res.partner"].create(
|
||||
{
|
||||
"name": "Host1",
|
||||
}
|
||||
)
|
||||
with self.assertRaises(ValidationError):
|
||||
self.env["pms.reservation"].create(
|
||||
{
|
||||
"checkin": fields.date.today(),
|
||||
"checkout": fields.date.today() + datetime.timedelta(days=3),
|
||||
"pms_property_id": self.property.id,
|
||||
"partner_id": self.host1.id,
|
||||
"arrival_hour": "14:00:00",
|
||||
}
|
||||
)
|
||||
|
||||
def test_check_departure_hour(self):
|
||||
self.create_common_scenario()
|
||||
self.host1 = self.env["res.partner"].create(
|
||||
{
|
||||
"name": "Host1",
|
||||
}
|
||||
)
|
||||
with self.assertRaises(ValidationError):
|
||||
self.env["pms.reservation"].create(
|
||||
{
|
||||
"checkin": fields.date.today(),
|
||||
"checkout": fields.date.today() + datetime.timedelta(days=3),
|
||||
"pms_property_id": self.property.id,
|
||||
"partner_id": self.host1.id,
|
||||
"departure_hour": "14:00:00",
|
||||
}
|
||||
)
|
||||
|
||||
def test_check_property_integrity_room(self):
|
||||
self.create_common_scenario()
|
||||
self.property2 = self.env["pms.property"].create(
|
||||
{
|
||||
"name": "MY PMS TEST",
|
||||
"company_id": self.env.ref("base.main_company").id,
|
||||
"default_pricelist_id": self.test_pricelist1.id,
|
||||
"folio_sequence_id": self.folio_sequence.id,
|
||||
"reservation_sequence_id": self.reservation_sequence.id,
|
||||
"checkin_sequence_id": self.checkin_sequence.id,
|
||||
}
|
||||
)
|
||||
self.host1 = self.env["res.partner"].create(
|
||||
{
|
||||
"name": "Host1",
|
||||
}
|
||||
)
|
||||
self.room_type_double.pms_property_ids = [
|
||||
(6, 0, [self.property.id, self.property2.id])
|
||||
]
|
||||
with self.assertRaises(ValidationError):
|
||||
self.env["pms.reservation"].create(
|
||||
{
|
||||
"checkin": fields.date.today(),
|
||||
"checkout": fields.date.today() + datetime.timedelta(days=3),
|
||||
"pms_property_id": self.property2.id,
|
||||
"partner_id": self.host1.id,
|
||||
"room_type_id": self.room_type_double.id,
|
||||
"preferred_room_id": self.room1.id,
|
||||
}
|
||||
)
|
||||
|
||||
def test_shared_folio_true(self):
|
||||
self.create_common_scenario()
|
||||
self.host1 = self.env["res.partner"].create(
|
||||
{
|
||||
"name": "Host1",
|
||||
}
|
||||
)
|
||||
self.reservation = self.env["pms.reservation"].create(
|
||||
{
|
||||
"checkin": fields.date.today() + datetime.timedelta(days=60),
|
||||
"checkout": fields.date.today() + datetime.timedelta(days=65),
|
||||
"pms_property_id": self.property.id,
|
||||
"partner_id": self.host1.id,
|
||||
}
|
||||
)
|
||||
self.reservation2 = self.env["pms.reservation"].create(
|
||||
{
|
||||
"checkin": fields.date.today() + datetime.timedelta(days=60),
|
||||
"checkout": fields.date.today() + datetime.timedelta(days=64),
|
||||
"pms_property_id": self.property.id,
|
||||
"partner_id": self.host1.id,
|
||||
"folio_id": self.reservation.folio_id.id,
|
||||
}
|
||||
)
|
||||
self.assertTrue(
|
||||
self.reservation.shared_folio,
|
||||
"Folio.reservations > 1, so reservation.shared_folio must be True",
|
||||
)
|
||||
|
||||
def test_shared_folio_false(self):
|
||||
self.create_common_scenario()
|
||||
self.host1 = self.env["res.partner"].create(
|
||||
{
|
||||
"name": "Host1",
|
||||
}
|
||||
)
|
||||
self.reservation = self.env["pms.reservation"].create(
|
||||
{
|
||||
"checkin": fields.date.today() + datetime.timedelta(days=60),
|
||||
"checkout": fields.date.today() + datetime.timedelta(days=65),
|
||||
"pms_property_id": self.property.id,
|
||||
"partner_id": self.host1.id,
|
||||
}
|
||||
)
|
||||
self.assertFalse(
|
||||
self.reservation.shared_folio,
|
||||
"Folio.reservations = 1, so reservation.shared_folio must be False",
|
||||
)
|
||||
|
||||
@freeze_time("1982-11-01")
|
||||
def test_reservation_action_cancel_fail(self):
|
||||
self.create_common_scenario()
|
||||
self.host1 = self.env["res.partner"].create(
|
||||
{
|
||||
"name": "Host1",
|
||||
}
|
||||
)
|
||||
reservation = self.env["pms.reservation"].create(
|
||||
{
|
||||
"checkin": fields.date.today(),
|
||||
"checkout": fields.date.today() + datetime.timedelta(days=1),
|
||||
"room_type_id": self.room_type_double.id,
|
||||
"partner_id": self.host1.id,
|
||||
"pms_property_id": self.property.id,
|
||||
}
|
||||
)
|
||||
|
||||
reservation.state = "cancelled"
|
||||
|
||||
with self.assertRaises(UserError):
|
||||
reservation.action_cancel()
|
||||
|
||||
@freeze_time("1983-11-01")
|
||||
def test_cancelation_reason_noshow(self):
|
||||
self.create_common_scenario()
|
||||
Pricelist = self.env["product.pricelist"]
|
||||
self.cancelation_rule = self.env["pms.cancelation.rule"].create(
|
||||
{
|
||||
"name": "Cancelation Rule Test",
|
||||
"pms_property_ids": [self.property.id],
|
||||
"penalty_noshow": 50,
|
||||
}
|
||||
)
|
||||
|
||||
self.pricelist = Pricelist.create(
|
||||
{
|
||||
"name": "Pricelist Test",
|
||||
"pms_property_ids": [self.property.id],
|
||||
"cancelation_rule_id": self.cancelation_rule.id,
|
||||
}
|
||||
)
|
||||
self.host1 = self.env["res.partner"].create(
|
||||
{
|
||||
"name": "Host1",
|
||||
}
|
||||
)
|
||||
|
||||
reservation = self.env["pms.reservation"].create(
|
||||
{
|
||||
"checkin": fields.date.today() + datetime.timedelta(days=-5),
|
||||
"checkout": fields.date.today() + datetime.timedelta(days=-3),
|
||||
"room_type_id": self.room_type_double.id,
|
||||
"partner_id": self.host1.id,
|
||||
"pms_property_id": self.property.id,
|
||||
"pricelist_id": self.pricelist.id,
|
||||
}
|
||||
)
|
||||
|
||||
reservation.action_cancel()
|
||||
reservation.flush()
|
||||
self.assertEqual(
|
||||
reservation.cancelled_reason,
|
||||
"noshow",
|
||||
"If reservation has already passed and no checkin,"
|
||||
"cancelled_reason must be 'noshow'",
|
||||
)
|
||||
|
||||
@freeze_time("1984-11-01")
|
||||
def test_cancelation_reason_intime(self):
|
||||
self.create_common_scenario()
|
||||
Pricelist = self.env["product.pricelist"]
|
||||
self.cancelation_rule = self.env["pms.cancelation.rule"].create(
|
||||
{
|
||||
"name": "Cancelation Rule Test",
|
||||
"pms_property_ids": [self.property.id],
|
||||
"days_intime": 3,
|
||||
}
|
||||
)
|
||||
|
||||
self.pricelist = Pricelist.create(
|
||||
{
|
||||
"name": "Pricelist Test",
|
||||
"pms_property_ids": [self.property.id],
|
||||
"cancelation_rule_id": self.cancelation_rule.id,
|
||||
}
|
||||
)
|
||||
self.host1 = self.env["res.partner"].create(
|
||||
{
|
||||
"name": "Host1",
|
||||
}
|
||||
)
|
||||
|
||||
reservation = self.env["pms.reservation"].create(
|
||||
{
|
||||
"checkin": fields.date.today() + datetime.timedelta(days=5),
|
||||
"checkout": fields.date.today() + datetime.timedelta(days=8),
|
||||
"room_type_id": self.room_type_double.id,
|
||||
"partner_id": self.host1.id,
|
||||
"pms_property_id": self.property.id,
|
||||
"pricelist_id": self.pricelist.id,
|
||||
}
|
||||
)
|
||||
|
||||
reservation.action_cancel()
|
||||
reservation.flush()
|
||||
|
||||
self.assertEqual(reservation.cancelled_reason, "intime", "-----------")
|
||||
|
||||
@freeze_time("1985-11-01")
|
||||
def _test_cancelation_reason_late(self):
|
||||
self.create_common_scenario()
|
||||
Pricelist = self.env["product.pricelist"]
|
||||
self.cancelation_rule = self.env["pms.cancelation.rule"].create(
|
||||
{
|
||||
"name": "Cancelation Rule Test",
|
||||
"pms_property_ids": [self.property.id],
|
||||
"days_late": 3,
|
||||
}
|
||||
)
|
||||
|
||||
self.pricelist = Pricelist.create(
|
||||
{
|
||||
"name": "Pricelist Test",
|
||||
"pms_property_ids": [self.property.id],
|
||||
"cancelation_rule_id": self.cancelation_rule.id,
|
||||
}
|
||||
)
|
||||
self.host1 = self.env["res.partner"].create(
|
||||
{
|
||||
"name": "Host1",
|
||||
}
|
||||
)
|
||||
|
||||
reservation = self.env["pms.reservation"].create(
|
||||
{
|
||||
"checkin": fields.date.today() + datetime.timedelta(days=1),
|
||||
"checkout": fields.date.today() + datetime.timedelta(days=4),
|
||||
"room_type_id": self.room_type_double.id,
|
||||
"partner_id": self.host1.id,
|
||||
"pms_property_id": self.property.id,
|
||||
"pricelist_id": self.pricelist.id,
|
||||
}
|
||||
)
|
||||
reservation.action_cancel()
|
||||
reservation.flush()
|
||||
self.assertEqual(reservation.cancelled_reason, "late", "-----------")
|
||||
|
||||
def test_compute_checkin_partner_count(self):
|
||||
self.create_common_scenario()
|
||||
self.host1 = self.env["res.partner"].create(
|
||||
{
|
||||
"name": "Miguel",
|
||||
"phone": "654667733",
|
||||
"email": "miguel@example.com",
|
||||
}
|
||||
)
|
||||
self.host2 = self.env["res.partner"].create(
|
||||
{
|
||||
"name": "Brais",
|
||||
"phone": "654437733",
|
||||
"email": "brais@example.com",
|
||||
}
|
||||
)
|
||||
self.reservation = self.env["pms.reservation"].create(
|
||||
{
|
||||
"checkin": "2013-01-14",
|
||||
"checkout": "2013-01-17",
|
||||
"partner_id": self.host1.id,
|
||||
"pms_property_id": self.property.id,
|
||||
"adults": 3,
|
||||
}
|
||||
)
|
||||
self.checkin1 = self.env["pms.checkin.partner"].create(
|
||||
{
|
||||
"partner_id": self.host1.id,
|
||||
"reservation_id": self.reservation.id,
|
||||
}
|
||||
)
|
||||
self.checkin2 = self.env["pms.checkin.partner"].create(
|
||||
{
|
||||
"partner_id": self.host2.id,
|
||||
"reservation_id": self.reservation.id,
|
||||
}
|
||||
)
|
||||
|
||||
self.reservation.checkin_partner_ids = [
|
||||
(6, 0, [self.checkin1.id, self.checkin2.id])
|
||||
]
|
||||
|
||||
self.assertEqual(
|
||||
self.reservation.checkin_partner_count,
|
||||
len(self.reservation.checkin_partner_ids),
|
||||
"Checkin_partner_count must be match with number of checkin_partner_ids",
|
||||
)
|
||||
|
||||
def test_compute_checkin_partner_pending_count(self):
|
||||
self.create_common_scenario()
|
||||
self.host1 = self.env["res.partner"].create(
|
||||
{
|
||||
"name": "Miguel",
|
||||
"phone": "654667733",
|
||||
"email": "miguel@example.com",
|
||||
}
|
||||
)
|
||||
self.host2 = self.env["res.partner"].create(
|
||||
{
|
||||
"name": "Brais",
|
||||
"phone": "654437733",
|
||||
"email": "brais@example.com",
|
||||
}
|
||||
)
|
||||
self.reservation = self.env["pms.reservation"].create(
|
||||
{
|
||||
"checkin": "2014-01-14",
|
||||
"checkout": "2014-01-17",
|
||||
"partner_id": self.host1.id,
|
||||
"pms_property_id": self.property.id,
|
||||
"adults": 3,
|
||||
}
|
||||
)
|
||||
self.checkin1 = self.env["pms.checkin.partner"].create(
|
||||
{
|
||||
"partner_id": self.host1.id,
|
||||
"reservation_id": self.reservation.id,
|
||||
}
|
||||
)
|
||||
self.checkin2 = self.env["pms.checkin.partner"].create(
|
||||
{
|
||||
"partner_id": self.host2.id,
|
||||
"reservation_id": self.reservation.id,
|
||||
}
|
||||
)
|
||||
|
||||
self.reservation.checkin_partner_ids = [
|
||||
(6, 0, [self.checkin1.id, self.checkin2.id])
|
||||
]
|
||||
|
||||
count_expected = self.reservation.adults - len(
|
||||
self.reservation.checkin_partner_ids
|
||||
)
|
||||
self.assertEqual(
|
||||
self.reservation.checkin_partner_pending_count,
|
||||
count_expected,
|
||||
"Checkin_partner_pending_count isn't correct",
|
||||
)
|
||||
|
||||
@freeze_time("1982-11-01")
|
||||
def test_reservation_action_checkout_fail(self):
|
||||
self.create_common_scenario()
|
||||
host = self.env["res.partner"].create(
|
||||
{
|
||||
"name": "Miguel",
|
||||
"phone": "654667733",
|
||||
"email": "miguel@example.com",
|
||||
}
|
||||
)
|
||||
reservation = self.env["pms.reservation"].create(
|
||||
{
|
||||
"checkin": fields.date.today(),
|
||||
"checkout": fields.date.today() + datetime.timedelta(days=1),
|
||||
"partner_id": host.id,
|
||||
"allowed_checkout": True,
|
||||
"pms_property_id": self.property.id,
|
||||
}
|
||||
)
|
||||
|
||||
with self.assertRaises(UserError):
|
||||
reservation.action_reservation_checkout()
|
||||
|
||||
@@ -1,54 +1,36 @@
|
||||
from odoo.exceptions import ValidationError
|
||||
from odoo.tests import common
|
||||
|
||||
from .common import TestPms
|
||||
|
||||
|
||||
class TestPmsRoom(common.TransactionCase):
|
||||
def create_common_scenario(self):
|
||||
self.property1 = self.env["pms.property"].create(
|
||||
{
|
||||
"name": "Property_1",
|
||||
"company_id": self.env.ref("base.main_company").id,
|
||||
"default_pricelist_id": self.env.ref("product.list0").id,
|
||||
}
|
||||
)
|
||||
|
||||
self.property2 = self.env["pms.property"].create(
|
||||
class TestPmsRoom(TestPms):
|
||||
def setUp(self):
|
||||
super().setUp()
|
||||
self.pms_property2 = self.env["pms.property"].create(
|
||||
{
|
||||
"name": "Property_2",
|
||||
"company_id": self.env.ref("base.main_company").id,
|
||||
"default_pricelist_id": self.env.ref("product.list0").id,
|
||||
}
|
||||
)
|
||||
self.property3 = self.env["pms.property"].create(
|
||||
{
|
||||
"name": "Property_3",
|
||||
"company_id": self.env.ref("base.main_company").id,
|
||||
"default_pricelist_id": self.env.ref("product.list0").id,
|
||||
"company_id": self.company1.id,
|
||||
"default_pricelist_id": self.pricelist1.id,
|
||||
}
|
||||
)
|
||||
|
||||
self.room_type_class = self.env["pms.room.type.class"].create(
|
||||
{"name": "Room Class", "code_class": "ROOM"}
|
||||
)
|
||||
|
||||
self.room_type = self.env["pms.room.type"].create(
|
||||
self.room_type1 = self.env["pms.room.type"].create(
|
||||
{
|
||||
"pms_property_ids": [self.property1.id, self.property2.id],
|
||||
"pms_property_ids": [self.pms_property1.id, self.pms_property2.id],
|
||||
"name": "Single",
|
||||
"code_type": "SIN",
|
||||
"class_id": self.room_type_class.id,
|
||||
"default_code": "SIN",
|
||||
"class_id": self.room_type_class1.id,
|
||||
"list_price": 30,
|
||||
}
|
||||
)
|
||||
|
||||
def test_check_property_floor(self):
|
||||
def test_check_property_ubication(self):
|
||||
# ARRANGE
|
||||
self.create_common_scenario()
|
||||
floor = self.env["pms.floor"].create(
|
||||
ubication1 = self.env["pms.ubication"].create(
|
||||
{
|
||||
"name": "Floor",
|
||||
"name": "UbicationTest",
|
||||
"pms_property_ids": [
|
||||
(4, self.property1.id),
|
||||
(4, self.pms_property1.id),
|
||||
],
|
||||
}
|
||||
)
|
||||
@@ -59,15 +41,21 @@ class TestPmsRoom(common.TransactionCase):
|
||||
self.env["pms.room"].create(
|
||||
{
|
||||
"name": "Room 101",
|
||||
"pms_property_id": self.property2.id,
|
||||
"room_type_id": self.room_type.id,
|
||||
"floor_id": floor.id,
|
||||
"pms_property_id": self.pms_property2.id,
|
||||
"room_type_id": self.room_type1.id,
|
||||
"ubication_id": ubication1.id,
|
||||
}
|
||||
)
|
||||
|
||||
def test_check_property_room_type(self):
|
||||
# ARRANGE
|
||||
self.create_common_scenario()
|
||||
self.pms_property3 = self.env["pms.property"].create(
|
||||
{
|
||||
"name": "Property_3",
|
||||
"company_id": self.company1.id,
|
||||
"default_pricelist_id": self.pricelist1.id,
|
||||
}
|
||||
)
|
||||
# ACT & ARRANGE
|
||||
with self.assertRaises(
|
||||
ValidationError, msg="Room has been created and it should't"
|
||||
@@ -75,7 +63,7 @@ class TestPmsRoom(common.TransactionCase):
|
||||
self.env["pms.room"].create(
|
||||
{
|
||||
"name": "Room 101",
|
||||
"pms_property_id": self.property3.id,
|
||||
"room_type_id": self.room_type.id,
|
||||
"pms_property_id": self.pms_property3.id,
|
||||
"room_type_id": self.room_type1.id,
|
||||
}
|
||||
)
|
||||
|
||||
File diff suppressed because it is too large
Load Diff
@@ -2,57 +2,47 @@
|
||||
# License AGPL-3.0 or later (http://www.gnu.org/licenses/agpl).
|
||||
|
||||
from odoo.exceptions import ValidationError
|
||||
from odoo.tests.common import SavepointCase
|
||||
|
||||
from .common import TestPms
|
||||
|
||||
|
||||
class TestRoomTypeClass(SavepointCase):
|
||||
class TestRoomTypeClass(TestPms):
|
||||
def setUp(self):
|
||||
super().setUp()
|
||||
self.p1 = self.browse_ref("pms.main_pms_property")
|
||||
self.m1 = self.p1.company_id
|
||||
self.p2 = self.env["pms.property"].create(
|
||||
self.company2 = self.env["res.company"].create(
|
||||
{
|
||||
"name": "p2",
|
||||
"company_id": self.m1.id,
|
||||
"default_pricelist_id": self.ref("product.list0"),
|
||||
"name": "Company 2",
|
||||
}
|
||||
)
|
||||
self.m2 = self.env["res.company"].create(
|
||||
self.pms_property3 = self.env["pms.property"].create(
|
||||
{
|
||||
"name": "Company m2",
|
||||
}
|
||||
)
|
||||
self.p3 = self.env["pms.property"].create(
|
||||
{
|
||||
"name": "p3",
|
||||
"company_id": self.m2.id,
|
||||
"default_pricelist_id": self.ref("product.list0"),
|
||||
"name": "Property 3",
|
||||
"company_id": self.company2.id,
|
||||
"default_pricelist_id": self.pricelist1.id,
|
||||
}
|
||||
)
|
||||
|
||||
|
||||
class TestRoomTypeClassCodePropertyIntegrity(TestRoomTypeClass):
|
||||
# external integrity
|
||||
def test_external_case_01(self):
|
||||
"""
|
||||
PRE: - room type class cl1 exists
|
||||
- cl1 has code c1
|
||||
- cl1 has property p1
|
||||
- p1 has company m1
|
||||
ACT: - create a new cl2 class
|
||||
- cl2 has code c1
|
||||
- cl2 has property p1
|
||||
- p1 has company m1
|
||||
- room_type_class1 has code c1
|
||||
- room_type_class1 has pms_property1
|
||||
- pms_property1 has company company1
|
||||
ACT: - create a new room_type_class2 class
|
||||
- room_type_class2 has code c1
|
||||
- room_type_class2 has pms_property1
|
||||
- pms_property1 has company company1
|
||||
POST: - Integrity error: the room type already exists
|
||||
- cl2 not created
|
||||
- room_type_class2 not created
|
||||
"""
|
||||
# ARRANGE
|
||||
# cl1
|
||||
# room_type_class1
|
||||
self.env["pms.room.type.class"].create(
|
||||
{
|
||||
"name": "Room type class cl1",
|
||||
"code_class": "c1",
|
||||
"pms_property_ids": [(6, 0, [self.p1.id])],
|
||||
"pms_property_ids": [(6, 0, [self.pms_property1.id])],
|
||||
}
|
||||
)
|
||||
|
||||
@@ -60,36 +50,44 @@ class TestRoomTypeClassCodePropertyIntegrity(TestRoomTypeClass):
|
||||
with self.assertRaises(
|
||||
ValidationError, msg="The room type class has been created and it shouldn't"
|
||||
):
|
||||
# cl2
|
||||
# room_type_class2
|
||||
self.env["pms.room.type.class"].create(
|
||||
{
|
||||
"name": "Room type class cl2",
|
||||
"code_class": "c1",
|
||||
"pms_property_ids": [(6, 0, [self.p1.id])],
|
||||
"pms_property_ids": [(6, 0, [self.pms_property1.id])],
|
||||
}
|
||||
)
|
||||
|
||||
def test_external_case_02(self):
|
||||
"""
|
||||
PRE: - room type class cl1 exists
|
||||
- cl1 has code c1
|
||||
- cl1 has property p1
|
||||
- p1 has company m1
|
||||
ACT: - create a new cl2 class
|
||||
- cl2 has code c1
|
||||
- cl2 has property p1, p2, p3
|
||||
- p1, p2 has company m1
|
||||
- p3 has company m2
|
||||
- room_type_class1 has code c1
|
||||
- room_type_class1 has property pms_property1
|
||||
- pms_property1 has company company1
|
||||
ACT: - create a new room_type_class2 class
|
||||
- room_type_class2 has code c1
|
||||
- room_type_class2 has property pms_property1, pms_property2,
|
||||
pms_property3
|
||||
- pms_property1, pms_property2 has company company1
|
||||
- pms_property3 has company company2
|
||||
POST: - Integrity error: the room type class already exists
|
||||
- cl2 not created
|
||||
- room_type_class2 not created
|
||||
"""
|
||||
# ARRANGE
|
||||
# cl1
|
||||
self.pms_property2 = self.env["pms.property"].create(
|
||||
{
|
||||
"name": "Property 2",
|
||||
"company_id": self.company1.id,
|
||||
"default_pricelist_id": self.pricelist1.id,
|
||||
}
|
||||
)
|
||||
# room_type_class1
|
||||
self.env["pms.room.type.class"].create(
|
||||
{
|
||||
"name": "Room type class cl1",
|
||||
"name": "Room type class 1",
|
||||
"code_class": "c1",
|
||||
"pms_property_ids": [(6, 0, [self.p1.id])],
|
||||
"pms_property_ids": [(6, 0, [self.pms_property1.id])],
|
||||
}
|
||||
)
|
||||
|
||||
@@ -97,158 +95,184 @@ class TestRoomTypeClassCodePropertyIntegrity(TestRoomTypeClass):
|
||||
with self.assertRaises(
|
||||
ValidationError, msg="The room type class has been created and it shouldn't"
|
||||
):
|
||||
# cl2
|
||||
# room_type_class2
|
||||
self.env["pms.room.type.class"].create(
|
||||
{
|
||||
"name": "Room type class cl2",
|
||||
"code_class": "c1",
|
||||
"pms_property_ids": [(6, 0, [self.p1.id, self.p2.id, self.p3.id])],
|
||||
"pms_property_ids": [
|
||||
(
|
||||
6,
|
||||
0,
|
||||
[
|
||||
self.pms_property1.id,
|
||||
self.pms_property2.id,
|
||||
self.pms_property3.id,
|
||||
],
|
||||
)
|
||||
],
|
||||
}
|
||||
)
|
||||
|
||||
|
||||
class TestRoomTypeClassCodePropertyUniqueness(TestRoomTypeClass):
|
||||
# test with one room type class
|
||||
def test_single_case_01(self):
|
||||
"""
|
||||
PRE: - room type class cl1 exists
|
||||
- cl1 has code c1
|
||||
- cl1 has 2 properties p1 and p2
|
||||
- p1 and p2 have the same company m1
|
||||
ACT: - search room type class with code c1 and property p1
|
||||
- p1 has company m1
|
||||
POST: - only cl1 room type class found
|
||||
- room_type_class1 has code c1
|
||||
- room_type_class1 has 2 properties pms_property1 and pms_property2
|
||||
- pms_property_1 and pms_property2 have the same company company1
|
||||
ACT: - search room type class with code c1 and pms_property1
|
||||
- pms_property1 has company company1
|
||||
POST: - only room_type_class1 room type class found
|
||||
"""
|
||||
# ARRANGE
|
||||
cl1 = self.env["pms.room.type.class"].create(
|
||||
room_type_class1 = self.env["pms.room.type.class"].create(
|
||||
{
|
||||
"name": "Room type class cl1",
|
||||
"name": "Room type class 1",
|
||||
"code_class": "c1",
|
||||
"pms_property_ids": [(6, 0, [self.p1.id, self.p3.id])],
|
||||
"pms_property_ids": [
|
||||
(6, 0, [self.pms_property1.id, self.pms_property3.id])
|
||||
],
|
||||
}
|
||||
)
|
||||
|
||||
# ACT
|
||||
room_type_class = self.env["pms.room.type.class"].get_unique_by_property_code(
|
||||
self.p1.id, "c1"
|
||||
room_type_classes = self.env["pms.room.type.class"].get_unique_by_property_code(
|
||||
self.pms_property1.id, "c1"
|
||||
)
|
||||
|
||||
# ASSERT
|
||||
self.assertEqual(
|
||||
room_type_class.id, cl1.id, "Expected room type class not found"
|
||||
room_type_classes.id,
|
||||
room_type_class1.id,
|
||||
"Expected room type class not found",
|
||||
)
|
||||
|
||||
def test_single_case_02(self):
|
||||
"""
|
||||
PRE: - room type class cl1 exists
|
||||
- cl1 has code c1
|
||||
- cl1 has 2 properties p1 and p3
|
||||
- p1 and p2 have different companies
|
||||
- p1 have company m1 and p3 have company m2
|
||||
ACT: - search room type class with code c1 and property p1
|
||||
- p1 has company m1
|
||||
POST: - only cl1 room type found
|
||||
- room_type_class1 has code c1
|
||||
- room_type_class1 has 2 properties pms_property1 and pms_property3
|
||||
- pms_property1 and pms_property2 have different companies
|
||||
- pms_property1 have company company1 and pms_property3 have company2
|
||||
ACT: - search room type class with code c1 and property pms_property1
|
||||
- pms_property1 has company company1
|
||||
POST: - only room_type_class1 room type found
|
||||
"""
|
||||
# ARRANGE
|
||||
cl1 = self.env["pms.room.type.class"].create(
|
||||
{
|
||||
"name": "Room type class cl1",
|
||||
"name": "Room type class 1",
|
||||
"code_class": "c1",
|
||||
"pms_property_ids": [(6, 0, [self.p1.id, self.p3.id])],
|
||||
"pms_property_ids": [
|
||||
(6, 0, [self.pms_property1.id, self.pms_property3.id])
|
||||
],
|
||||
}
|
||||
)
|
||||
|
||||
# ACT
|
||||
room_type_class = self.env["pms.room.type.class"].get_unique_by_property_code(
|
||||
self.p1.id, "c1"
|
||||
room_type_classes = self.env["pms.room.type.class"].get_unique_by_property_code(
|
||||
self.pms_property1.id, "c1"
|
||||
)
|
||||
|
||||
# ASSERT
|
||||
self.assertEqual(
|
||||
room_type_class.id, cl1.id, "Expected room type class not found"
|
||||
room_type_classes.id, cl1.id, "Expected room type class not found"
|
||||
)
|
||||
|
||||
def test_single_case_03(self):
|
||||
"""
|
||||
PRE: - room type class cl1 exists
|
||||
- cl1 has code c1
|
||||
- cl1 with 2 properties p1 and p2
|
||||
- p1 and p2 have same company m1
|
||||
ACT: - search room type class with code c1 and property p3
|
||||
- p3 have company m2
|
||||
PRE: - room_type_class1 exists
|
||||
- room_type_class1 has code c1
|
||||
- room_type_class1 with 2 properties pms_property1 and pms_property2
|
||||
- pms_property1 and pms_property2 have same company company1
|
||||
ACT: - search room type class with code c1 and property pms_property3
|
||||
- pms_property3 have company company2
|
||||
POST: - no room type found
|
||||
"""
|
||||
# ARRANGE
|
||||
# cl1
|
||||
self.pms_property2 = self.env["pms.property"].create(
|
||||
{
|
||||
"name": "Property 2",
|
||||
"company_id": self.company1.id,
|
||||
"default_pricelist_id": self.pricelist1.id,
|
||||
}
|
||||
)
|
||||
# room_type_class1
|
||||
self.env["pms.room.type.class"].create(
|
||||
{
|
||||
"name": "Room type class cl1",
|
||||
"name": "Room type class 1",
|
||||
"code_class": "c1",
|
||||
"pms_property_ids": [(6, 0, [self.p1.id, self.p2.id])],
|
||||
"pms_property_ids": [
|
||||
(6, 0, [self.pms_property1.id, self.pms_property2.id])
|
||||
],
|
||||
}
|
||||
)
|
||||
|
||||
# ACT
|
||||
room_type_class = self.env["pms.room.type.class"].get_unique_by_property_code(
|
||||
self.p3.id, "c1"
|
||||
room_type_classes = self.env["pms.room.type.class"].get_unique_by_property_code(
|
||||
self.pms_property3.id, "c1"
|
||||
)
|
||||
|
||||
# ASSERT
|
||||
self.assertFalse(
|
||||
room_type_class, "Room type class found but it should not have found any"
|
||||
room_type_classes, "Room type class found but it should not have found any"
|
||||
)
|
||||
|
||||
def test_single_case_04(self):
|
||||
"""
|
||||
PRE: - room type class cl1 exists
|
||||
- cl1 has code c1
|
||||
- cl1 properties are null
|
||||
ACT: - search room type class with code c1 and property p1
|
||||
- p1 have company m1
|
||||
POST: - only cl1 room type class found
|
||||
PRE: - room_type_class1 exists
|
||||
- room_type_class1 has code c1
|
||||
- room_type_class1 properties are null
|
||||
ACT: - search room type class with code c1 and property pms_property1
|
||||
- pms_property1 have company company1
|
||||
POST: - only room_type_class1 room type class found
|
||||
"""
|
||||
# ARRANGE
|
||||
cl1 = self.env["pms.room.type.class"].create(
|
||||
room_type_class1 = self.env["pms.room.type.class"].create(
|
||||
{
|
||||
"name": "Room type class cl1",
|
||||
"name": "Room type class 1",
|
||||
"code_class": "c1",
|
||||
"pms_property_ids": False,
|
||||
}
|
||||
)
|
||||
|
||||
# ACT
|
||||
room_type_class = self.env["pms.room.type.class"].get_unique_by_property_code(
|
||||
self.p1.id, "c1"
|
||||
room_type_classes = self.env["pms.room.type.class"].get_unique_by_property_code(
|
||||
self.pms_property1.id, "c1"
|
||||
)
|
||||
|
||||
# ASSERT
|
||||
self.assertEqual(
|
||||
room_type_class.id, cl1.id, "Expected room type class not found"
|
||||
room_type_classes.id,
|
||||
room_type_class1.id,
|
||||
"Expected room type class not found",
|
||||
)
|
||||
|
||||
# tests with more than one room type class
|
||||
def test_multiple_case_01(self):
|
||||
"""
|
||||
PRE: - room type class cl1 exists
|
||||
- cl1 has code c1
|
||||
- cl1 has 2 properties p1 and p2
|
||||
- p1 and p2 have the same company m1
|
||||
- room type class cl2 exists
|
||||
- cl2 has code c1
|
||||
- cl2 has no properties
|
||||
ACT: - search room type class with code c1 and property p1
|
||||
- p1 have company m1
|
||||
POST: - only cl1 room type class found
|
||||
PRE: - room_type_class1 exists
|
||||
- room_type_class1 has code c1
|
||||
- room_type_class1 has 2 properties pms_property1 and pms_property2
|
||||
- pms_property1 and pms_property2 have the same company company1
|
||||
- room type class room_type_class2 exists
|
||||
- room_type_class2 has code c1
|
||||
- room_type_class2 has no properties
|
||||
ACT: - search room type class with code c1 and property pms_property1
|
||||
- pms_property1 have company company1
|
||||
POST: - only room_type_class1 room type class found
|
||||
"""
|
||||
# ARRANGE
|
||||
cl1 = self.env["pms.room.type.class"].create(
|
||||
room_type_class1 = self.env["pms.room.type.class"].create(
|
||||
{
|
||||
"name": "Room type class cl1",
|
||||
"name": "Room type class 1",
|
||||
"code_class": "c1",
|
||||
"pms_property_ids": [(6, 0, [self.p1.id, self.p3.id])],
|
||||
"pms_property_ids": [
|
||||
(6, 0, [self.pms_property1.id, self.pms_property3.id])
|
||||
],
|
||||
}
|
||||
)
|
||||
# cl2
|
||||
# room_type_class2
|
||||
self.env["pms.room.type.class"].create(
|
||||
{
|
||||
"name": "Room type class cl2",
|
||||
@@ -258,38 +282,47 @@ class TestRoomTypeClassCodePropertyUniqueness(TestRoomTypeClass):
|
||||
)
|
||||
|
||||
# ACT
|
||||
room_type_class = self.env["pms.room.type.class"].get_unique_by_property_code(
|
||||
self.p1.id, "c1"
|
||||
room_type_classes = self.env["pms.room.type.class"].get_unique_by_property_code(
|
||||
self.pms_property1.id, "c1"
|
||||
)
|
||||
|
||||
# ASSERT
|
||||
self.assertEqual(
|
||||
room_type_class.id, cl1.id, "Expected room type class not found"
|
||||
room_type_classes.id,
|
||||
room_type_class1.id,
|
||||
"Expected room type class not found",
|
||||
)
|
||||
|
||||
def test_multiple_case_02(self):
|
||||
"""
|
||||
PRE: - room type class cl1 exists
|
||||
- cl1 has code c1
|
||||
- cl1 has property p1
|
||||
- p1 have the company m1
|
||||
- room type class cl2 exists
|
||||
- cl2 has code c1
|
||||
- cl2 has no properties
|
||||
ACT: - search room type class with code c1 and property p2
|
||||
- p2 have company m1
|
||||
POST: - only cl1 room type class found
|
||||
PRE: - room_type_class1 exists
|
||||
- room_type_class1 has code c1
|
||||
- room_type_class1 has property pms_property1
|
||||
- pms_property1 have the company company1
|
||||
- room type class room_type_class2 exists
|
||||
- room_type_class2 has code c1
|
||||
- room_type_class2 has no properties
|
||||
ACT: - search room type class with code c1 and pms_property2
|
||||
- pms_property2 have company company1
|
||||
POST: - only room_type_class1 room type class found
|
||||
"""
|
||||
# ARRANGE
|
||||
# cl1
|
||||
self.env["pms.room.type.class"].create(
|
||||
self.pms_property2 = self.env["pms.property"].create(
|
||||
{
|
||||
"name": "Room type class cl1",
|
||||
"code_class": "c1",
|
||||
"pms_property_ids": [(6, 0, [self.p1.id])],
|
||||
"name": "Property 2",
|
||||
"company_id": self.company1.id,
|
||||
"default_pricelist_id": self.pricelist1.id,
|
||||
}
|
||||
)
|
||||
cl2 = self.env["pms.room.type.class"].create(
|
||||
# room_type_class1
|
||||
self.env["pms.room.type.class"].create(
|
||||
{
|
||||
"name": "Room type class 1",
|
||||
"code_class": "c1",
|
||||
"pms_property_ids": [(6, 0, [self.pms_property1.id])],
|
||||
}
|
||||
)
|
||||
room_type_class2 = self.env["pms.room.type.class"].create(
|
||||
{
|
||||
"name": "Room type class cl2",
|
||||
"code_class": "c1",
|
||||
@@ -298,38 +331,40 @@ class TestRoomTypeClassCodePropertyUniqueness(TestRoomTypeClass):
|
||||
)
|
||||
|
||||
# ACT
|
||||
room_type_class = self.env["pms.room.type.class"].get_unique_by_property_code(
|
||||
self.p2.id, "c1"
|
||||
room_type_classes = self.env["pms.room.type.class"].get_unique_by_property_code(
|
||||
self.pms_property2.id, "c1"
|
||||
)
|
||||
|
||||
# ASSERT
|
||||
self.assertEqual(
|
||||
room_type_class.id, cl2.id, "Expected room type class not found"
|
||||
room_type_classes.id,
|
||||
room_type_class2.id,
|
||||
"Expected room type class not found",
|
||||
)
|
||||
|
||||
def test_multiple_case_03(self):
|
||||
"""
|
||||
PRE: - room type class cl1 exists
|
||||
- cl1 has code c1
|
||||
- cl1 has property p1
|
||||
- p1 have the company m1
|
||||
- room type class cl2 exists
|
||||
- cl2 has code c1
|
||||
- cl2 has no properties
|
||||
ACT: - search room type class with code c1 and property p3
|
||||
- p3 have company m2
|
||||
POST: - only cl2 room type class found
|
||||
PRE: - room_type_class1 exists
|
||||
- room_type_class1 has code c1
|
||||
- room_type_class1 has property pms_property1
|
||||
- pms_property1 have the company company1
|
||||
- room type class room_type_class2 exists
|
||||
- room_type_class2 has code c1
|
||||
- room_type_class2 has no properties
|
||||
ACT: - search room type class with code c1 and property pms_property3
|
||||
- pms_property3 have company company2
|
||||
POST: - only room_type_class2 room type class found
|
||||
"""
|
||||
# ARRANGE
|
||||
# cl1
|
||||
# room_type_class1
|
||||
self.env["pms.room.type.class"].create(
|
||||
{
|
||||
"name": "Room type class cl1",
|
||||
"code_class": "c1",
|
||||
"pms_property_ids": [(6, 0, [self.p1.id])],
|
||||
"pms_property_ids": [(6, 0, [self.pms_property1.id])],
|
||||
}
|
||||
)
|
||||
cl2 = self.env["pms.room.type.class"].create(
|
||||
room_type_class2 = self.env["pms.room.type.class"].create(
|
||||
{
|
||||
"name": "Room type class cl2",
|
||||
"code_class": "c1",
|
||||
@@ -338,38 +373,40 @@ class TestRoomTypeClassCodePropertyUniqueness(TestRoomTypeClass):
|
||||
)
|
||||
|
||||
# ACT
|
||||
room_type_class = self.env["pms.room.type.class"].get_unique_by_property_code(
|
||||
self.p3.id, "c1"
|
||||
room_type_classes = self.env["pms.room.type.class"].get_unique_by_property_code(
|
||||
self.pms_property3.id, "c1"
|
||||
)
|
||||
|
||||
# ASSERT
|
||||
self.assertEqual(
|
||||
room_type_class.id, cl2.id, "Expected room type class not found"
|
||||
room_type_classes.id,
|
||||
room_type_class2.id,
|
||||
"Expected room type class not found",
|
||||
)
|
||||
|
||||
def test_multiple_case_04(self):
|
||||
"""
|
||||
PRE: - room type class cl1 exists
|
||||
- cl1 has code c1
|
||||
- cl1 has property p1
|
||||
- p1 have the company m1
|
||||
- room type cl2 exists
|
||||
- cl2 has code c1
|
||||
- cl2 has no properties
|
||||
ACT: - search room type class with code c1 and property p3
|
||||
- p3 have company m2
|
||||
PRE: - room_type_class1 exists
|
||||
- room_type_class1 has code c1
|
||||
- room_type_class1 has property pms_property1
|
||||
- pms_property1 have the company company1
|
||||
- room type room_type_class2 exists
|
||||
- room_type_class2 has code c1
|
||||
- room_type_class2 has no properties
|
||||
ACT: - search room type class with code c1 and property pms_property3
|
||||
- pms_property3 have company company2
|
||||
POST: - r2 room type class found
|
||||
"""
|
||||
# ARRANGE
|
||||
# cl1
|
||||
# room_type_class1
|
||||
self.env["pms.room.type.class"].create(
|
||||
{
|
||||
"name": "Room type class cl1",
|
||||
"name": "Room type class 1",
|
||||
"code_class": "c1",
|
||||
"pms_property_ids": [(6, 0, [self.p1.id])],
|
||||
"pms_property_ids": [(6, 0, [self.pms_property1.id])],
|
||||
}
|
||||
)
|
||||
cl2 = self.env["pms.room.type.class"].create(
|
||||
room_type_class2 = self.env["pms.room.type.class"].create(
|
||||
{
|
||||
"name": "Room type class cl2",
|
||||
"code_class": "c1",
|
||||
@@ -378,9 +415,11 @@ class TestRoomTypeClassCodePropertyUniqueness(TestRoomTypeClass):
|
||||
)
|
||||
|
||||
# ACT
|
||||
room_type_class = self.env["pms.room.type.class"].get_unique_by_property_code(
|
||||
self.p3.id, "c1"
|
||||
room_type_classes = self.env["pms.room.type.class"].get_unique_by_property_code(
|
||||
self.pms_property3.id, "c1"
|
||||
)
|
||||
|
||||
# ASSERT
|
||||
self.assertEqual(room_type_class.id, cl2.id, "Expected room type not found")
|
||||
self.assertEqual(
|
||||
room_type_classes.id, room_type_class2.id, "Expected room type not found"
|
||||
)
|
||||
|
||||
@@ -4,24 +4,13 @@ from freezegun import freeze_time
|
||||
|
||||
from odoo.exceptions import ValidationError
|
||||
|
||||
from .common import TestHotel
|
||||
from .common import TestPms
|
||||
|
||||
|
||||
@freeze_time("2010-01-01")
|
||||
class TestPmsSaleChannel(TestHotel):
|
||||
def create_common_scenario(self):
|
||||
# create a property
|
||||
self.property = self.env["pms.property"].create(
|
||||
{
|
||||
"name": "MY PROPERTY TEST",
|
||||
"company_id": self.env.ref("base.main_company").id,
|
||||
"default_pricelist_id": self.env.ref("product.list0").id,
|
||||
}
|
||||
)
|
||||
|
||||
class TestPmsSaleChannel(TestPms):
|
||||
def test_not_agency_as_agency(self):
|
||||
# ARRANGE
|
||||
self.create_common_scenario()
|
||||
PmsReservation = self.env["pms.reservation"]
|
||||
not_agency = self.env["res.partner"].create(
|
||||
{"name": "partner1", "is_agency": False}
|
||||
@@ -34,61 +23,59 @@ class TestPmsSaleChannel(TestHotel):
|
||||
"checkin": datetime.datetime.now(),
|
||||
"checkout": datetime.datetime.now() + datetime.timedelta(days=3),
|
||||
"agency_id": not_agency.id,
|
||||
"pms_property_id": self.property.id,
|
||||
"pms_property_id": self.pms_property1.id,
|
||||
}
|
||||
)
|
||||
|
||||
def test_channel_type_id_only_directs(self):
|
||||
# ARRANGE
|
||||
self.create_common_scenario()
|
||||
PmsReservation = self.env["pms.reservation"]
|
||||
PmsSaleChannel = self.env["pms.sale.channel"]
|
||||
# ACT
|
||||
salechannel = PmsSaleChannel.create({"channel_type": "direct"})
|
||||
sale_channel1 = PmsSaleChannel.create({"channel_type": "direct"})
|
||||
partner1 = self.env["res.partner"].create({"name": "partner1"})
|
||||
reservation = PmsReservation.create(
|
||||
reservation1 = PmsReservation.create(
|
||||
{
|
||||
"checkin": datetime.datetime.now(),
|
||||
"checkout": datetime.datetime.now() + datetime.timedelta(days=3),
|
||||
"channel_type_id": salechannel.id,
|
||||
"channel_type_id": sale_channel1.id,
|
||||
"partner_id": partner1.id,
|
||||
"pms_property_id": self.property.id,
|
||||
"pms_property_id": self.pms_property1.id,
|
||||
}
|
||||
)
|
||||
# ASSERT
|
||||
self.assertEqual(
|
||||
reservation.channel_type_id.channel_type,
|
||||
reservation1.channel_type_id.channel_type,
|
||||
"direct",
|
||||
"Sale channel is not direct",
|
||||
)
|
||||
|
||||
def test_agency_id_is_agency(self):
|
||||
# ARRANGE
|
||||
self.create_common_scenario()
|
||||
PmsReservation = self.env["pms.reservation"]
|
||||
PmsSaleChannel = self.env["pms.sale.channel"]
|
||||
salechannel = PmsSaleChannel.create(
|
||||
sale_channel1 = PmsSaleChannel.create(
|
||||
{"name": "Test Indirect", "channel_type": "indirect"}
|
||||
)
|
||||
# ACT
|
||||
agency = self.env["res.partner"].create(
|
||||
agency1 = self.env["res.partner"].create(
|
||||
{
|
||||
"name": "partner1",
|
||||
"is_agency": True,
|
||||
"sale_channel_id": salechannel.id,
|
||||
"sale_channel_id": sale_channel1.id,
|
||||
}
|
||||
)
|
||||
reservation = PmsReservation.create(
|
||||
reservation1 = PmsReservation.create(
|
||||
{
|
||||
"checkin": datetime.datetime.now(),
|
||||
"checkout": datetime.datetime.now() + datetime.timedelta(days=3),
|
||||
"agency_id": agency.id,
|
||||
"pms_property_id": self.property.id,
|
||||
"agency_id": agency1.id,
|
||||
"pms_property_id": self.pms_property1.id,
|
||||
}
|
||||
)
|
||||
# ASSERT
|
||||
self.assertEqual(
|
||||
reservation.agency_id.is_agency,
|
||||
reservation1.agency_id.is_agency,
|
||||
True,
|
||||
"Agency_id doesn't correspond to an agency",
|
||||
)
|
||||
@@ -97,13 +84,13 @@ class TestPmsSaleChannel(TestHotel):
|
||||
# ARRANGE
|
||||
PmsSaleChannel = self.env["pms.sale.channel"]
|
||||
# ACT
|
||||
saleChannel = PmsSaleChannel.create({"channel_type": "indirect"})
|
||||
agency = self.env["res.partner"].create(
|
||||
{"name": "example", "is_agency": True, "sale_channel_id": saleChannel.id}
|
||||
saleChannel1 = PmsSaleChannel.create({"channel_type": "indirect"})
|
||||
agency1 = self.env["res.partner"].create(
|
||||
{"name": "example", "is_agency": True, "sale_channel_id": saleChannel1.id}
|
||||
)
|
||||
# ASSERT
|
||||
self.assertEqual(
|
||||
agency.sale_channel_id.channel_type,
|
||||
agency1.sale_channel_id.channel_type,
|
||||
"indirect",
|
||||
"An agency should be a indirect channel",
|
||||
)
|
||||
|
||||
@@ -3,12 +3,11 @@ import datetime
|
||||
from freezegun import freeze_time
|
||||
|
||||
from odoo import fields
|
||||
|
||||
from .common import TestHotel
|
||||
from odoo.tests import common
|
||||
|
||||
|
||||
@freeze_time("1980-12-01")
|
||||
class TestPmsWizardMassiveChanges(TestHotel):
|
||||
class TestPmsWizardMassiveChanges(common.SavepointCase):
|
||||
def create_common_scenario(self):
|
||||
# PRICELIST CREATION
|
||||
self.test_pricelist = self.env["product.pricelist"].create(
|
||||
@@ -19,9 +18,7 @@ class TestPmsWizardMassiveChanges(TestHotel):
|
||||
self.test_pricelist.flush()
|
||||
|
||||
# AVAILABILITY PLAN CREATION
|
||||
self.test_availability_plan = self.env[
|
||||
"pms.room.type.availability.plan"
|
||||
].create(
|
||||
self.test_availability_plan = self.env["pms.availability.plan"].create(
|
||||
{
|
||||
"name": "Availability plan for TEST",
|
||||
"pms_pricelist_ids": [(6, 0, [self.test_pricelist.id])],
|
||||
@@ -29,12 +26,40 @@ class TestPmsWizardMassiveChanges(TestHotel):
|
||||
)
|
||||
self.test_availability_plan.flush()
|
||||
|
||||
# SEQUENCES
|
||||
self.folio_sequence = self.env["ir.sequence"].create(
|
||||
{
|
||||
"name": "PMS Folio",
|
||||
"code": "pms.folio",
|
||||
"padding": 4,
|
||||
"company_id": self.env.ref("base.main_company").id,
|
||||
}
|
||||
)
|
||||
self.reservation_sequence = self.env["ir.sequence"].create(
|
||||
{
|
||||
"name": "PMS Reservation",
|
||||
"code": "pms.reservation",
|
||||
"padding": 4,
|
||||
"company_id": self.env.ref("base.main_company").id,
|
||||
}
|
||||
)
|
||||
self.checkin_sequence = self.env["ir.sequence"].create(
|
||||
{
|
||||
"name": "PMS Checkin",
|
||||
"code": "pms.checkin.partner",
|
||||
"padding": 4,
|
||||
"company_id": self.env.ref("base.main_company").id,
|
||||
}
|
||||
)
|
||||
# PROPERTY CREATION (WITH DEFAULT PRICELIST AND AVAILABILITY PLAN
|
||||
self.test_property = self.env["pms.property"].create(
|
||||
{
|
||||
"name": "MY PMS TEST",
|
||||
"company_id": self.env.ref("base.main_company").id,
|
||||
"default_pricelist_id": self.test_pricelist.id,
|
||||
"folio_sequence_id": self.folio_sequence.id,
|
||||
"reservation_sequence_id": self.reservation_sequence.id,
|
||||
"checkin_sequence_id": self.checkin_sequence.id,
|
||||
}
|
||||
)
|
||||
self.test_property.flush()
|
||||
@@ -50,7 +75,7 @@ class TestPmsWizardMassiveChanges(TestHotel):
|
||||
{
|
||||
"pms_property_ids": [self.test_property.id],
|
||||
"name": "Single Test",
|
||||
"code_type": "SNG_Test",
|
||||
"default_code": "SNG_Test",
|
||||
"class_id": self.test_room_type_class.id,
|
||||
"list_price": 25.0,
|
||||
}
|
||||
@@ -62,7 +87,7 @@ class TestPmsWizardMassiveChanges(TestHotel):
|
||||
{
|
||||
"pms_property_ids": [self.test_property.id],
|
||||
"name": "Double Test",
|
||||
"code_type": "DBL_Test",
|
||||
"default_code": "DBL_Test",
|
||||
"class_id": self.test_room_type_class.id,
|
||||
"list_price": 40.0,
|
||||
}
|
||||
@@ -676,7 +701,7 @@ class TestPmsWizardMassiveChanges(TestHotel):
|
||||
checkin = fields.date.today()
|
||||
checkout = fields.date.today() + datetime.timedelta(days=1)
|
||||
|
||||
self.env["pms.room.type.availability.rule"].create(
|
||||
self.env["pms.availability.plan.rule"].create(
|
||||
{
|
||||
"quota": 1,
|
||||
"room_type_id": self.test_room_type_double.id,
|
||||
@@ -718,7 +743,7 @@ class TestPmsWizardMassiveChanges(TestHotel):
|
||||
checkin = fields.date.today()
|
||||
checkout = fields.date.today() + datetime.timedelta(days=1)
|
||||
|
||||
self.env["pms.room.type.availability.rule"].create(
|
||||
self.env["pms.availability.plan.rule"].create(
|
||||
{
|
||||
"min_stay": 3,
|
||||
"room_type_id": self.test_room_type_double.id,
|
||||
|
||||
@@ -3,11 +3,10 @@ import datetime
|
||||
from freezegun import freeze_time
|
||||
|
||||
from odoo import fields
|
||||
|
||||
from .common import TestHotel
|
||||
from odoo.tests import common
|
||||
|
||||
|
||||
class TestPmsWizardMassiveChanges(TestHotel):
|
||||
class TestPmsWizardMassiveChanges(common.SavepointCase):
|
||||
def create_common_scenario(self):
|
||||
# product.pricelist
|
||||
self.test_pricelist = self.env["product.pricelist"].create(
|
||||
@@ -15,21 +14,47 @@ class TestPmsWizardMassiveChanges(TestHotel):
|
||||
"name": "test pricelist 1",
|
||||
}
|
||||
)
|
||||
# pms.room.type.availability.plan
|
||||
self.test_availability_plan = self.env[
|
||||
"pms.room.type.availability.plan"
|
||||
].create(
|
||||
# pms.availability.plan
|
||||
self.test_availability_plan = self.env["pms.availability.plan"].create(
|
||||
{
|
||||
"name": "Availability plan for TEST",
|
||||
"pms_pricelist_ids": [(6, 0, [self.test_pricelist.id])],
|
||||
}
|
||||
)
|
||||
# sequences
|
||||
self.folio_sequence = self.env["ir.sequence"].create(
|
||||
{
|
||||
"name": "PMS Folio",
|
||||
"code": "pms.folio",
|
||||
"padding": 4,
|
||||
"company_id": self.env.ref("base.main_company").id,
|
||||
}
|
||||
)
|
||||
self.reservation_sequence = self.env["ir.sequence"].create(
|
||||
{
|
||||
"name": "PMS Reservation",
|
||||
"code": "pms.reservation",
|
||||
"padding": 4,
|
||||
"company_id": self.env.ref("base.main_company").id,
|
||||
}
|
||||
)
|
||||
self.checkin_sequence = self.env["ir.sequence"].create(
|
||||
{
|
||||
"name": "PMS Checkin",
|
||||
"code": "pms.checkin.partner",
|
||||
"padding": 4,
|
||||
"company_id": self.env.ref("base.main_company").id,
|
||||
}
|
||||
)
|
||||
# pms.property
|
||||
self.test_property = self.env["pms.property"].create(
|
||||
{
|
||||
"name": "MY PMS TEST",
|
||||
"company_id": self.env.ref("base.main_company").id,
|
||||
"default_pricelist_id": self.test_pricelist.id,
|
||||
"folio_sequence_id": self.folio_sequence.id,
|
||||
"reservation_sequence_id": self.reservation_sequence.id,
|
||||
"checkin_sequence_id": self.checkin_sequence.id,
|
||||
}
|
||||
)
|
||||
# pms.room.type.class
|
||||
@@ -42,7 +67,7 @@ class TestPmsWizardMassiveChanges(TestHotel):
|
||||
{
|
||||
"pms_property_ids": [self.test_property.id],
|
||||
"name": "Single Test",
|
||||
"code_type": "SNG_Test",
|
||||
"default_code": "SNG_Test",
|
||||
"class_id": self.test_room_type_class.id,
|
||||
}
|
||||
)
|
||||
@@ -51,7 +76,7 @@ class TestPmsWizardMassiveChanges(TestHotel):
|
||||
{
|
||||
"pms_property_ids": [self.test_property.id],
|
||||
"name": "Double Test",
|
||||
"code_type": "DBL_Test",
|
||||
"default_code": "DBL_Test",
|
||||
"class_id": self.test_room_type_class.id,
|
||||
}
|
||||
)
|
||||
@@ -240,7 +265,7 @@ class TestPmsWizardMassiveChanges(TestHotel):
|
||||
self.create_common_scenario()
|
||||
date = fields.date.today()
|
||||
initial_quota = 20
|
||||
self.env["pms.room.type.availability.rule"].create(
|
||||
self.env["pms.availability.plan.rule"].create(
|
||||
{
|
||||
"availability_plan_id": self.test_availability_plan.id,
|
||||
"room_type_id": self.test_room_type_double.id,
|
||||
|
||||
@@ -1,21 +0,0 @@
|
||||
<?xml version="1.0" encoding="utf-8" ?>
|
||||
<odoo>
|
||||
<record id="ir_sequence_view_form" model="ir.ui.view">
|
||||
<field name="model">ir.sequence</field>
|
||||
<field name="inherit_id" ref="base.sequence_view" />
|
||||
<field name="arch" type="xml">
|
||||
<xpath expr="//field[@name='company_id']" position="after">
|
||||
<field string="Property" name="pms_property_id" />
|
||||
</xpath>
|
||||
</field>
|
||||
</record>
|
||||
<record id="ir_sequence_view_tree" model="ir.ui.view">
|
||||
<field name="model">ir.sequence</field>
|
||||
<field name="inherit_id" ref="base.sequence_view_tree" />
|
||||
<field name="arch" type="xml">
|
||||
<xpath expr="//field[@name='company_id']" position="after">
|
||||
<field string="Property" name="pms_property_id" />
|
||||
</xpath>
|
||||
</field>
|
||||
</record>
|
||||
</odoo>
|
||||
@@ -22,9 +22,10 @@
|
||||
options="{'no_create': True,'no_open': True}"
|
||||
/>
|
||||
<field
|
||||
name="room_amenity_type_id"
|
||||
name="pms_amenity_type_id"
|
||||
select="2"
|
||||
string="Amenity Type"
|
||||
domain="['|', ('pms_property_ids', '=', False), ('pms_property_ids', 'in', pms_property_ids)]"
|
||||
/>
|
||||
<!-- <field name="categ_id" select="1"
|
||||
domain="[('isamenitytype','=',True)]" /> -->
|
||||
@@ -73,7 +74,7 @@
|
||||
<field name="arch" type="xml">
|
||||
<search string="Room Amenities">
|
||||
<field name="name" />
|
||||
<field name="room_amenity_type_id" select="1" />
|
||||
<field name="pms_amenity_type_id" select="1" />
|
||||
<!-- <field name="list_price" string="ty rate" /> -->
|
||||
<newline />
|
||||
<group expand="0" string="Group By...">
|
||||
@@ -90,7 +91,7 @@
|
||||
<field name="arch" type="xml">
|
||||
<tree string="Room Amenities">
|
||||
<field name="name" />
|
||||
<field name="room_amenity_type_id" select="1" />
|
||||
<field name="pms_amenity_type_id" select="1" />
|
||||
<!-- <field name="list_price" string="Ty rate" invisible="1" /> -->
|
||||
</tree>
|
||||
</field>
|
||||
|
||||
@@ -1,8 +1,8 @@
|
||||
<?xml version="1.0" ?>
|
||||
<odoo>
|
||||
<record id="room_type_availability_rule_view_form" model="ir.ui.view">
|
||||
<field name="name">pms.room.type.availability.rule.form</field>
|
||||
<field name="model">pms.room.type.availability.rule</field>
|
||||
<record id="availability_plan_rule_view_form" model="ir.ui.view">
|
||||
<field name="name">pms.availability.plan.rule.form</field>
|
||||
<field name="model">pms.availability.plan.rule</field>
|
||||
<field name="arch" type="xml">
|
||||
<form string="Availability Plans">
|
||||
<group>
|
||||
@@ -37,9 +37,9 @@
|
||||
</form>
|
||||
</field>
|
||||
</record>
|
||||
<record id="room_type_availability_rule_view_tree" model="ir.ui.view">
|
||||
<field name="name">pms.room.type.availability.rule.tree</field>
|
||||
<field name="model">pms.room.type.availability.rule</field>
|
||||
<record id="availability_plan_rule_view_tree" model="ir.ui.view">
|
||||
<field name="name">pms.availability.plan.rule.tree</field>
|
||||
<field name="model">pms.availability.plan.rule</field>
|
||||
<field name="arch" type="xml">
|
||||
<tree string="Availability rules">
|
||||
<field name="date" />
|
||||
@@ -1,8 +1,8 @@
|
||||
<?xml version="1.0" ?>
|
||||
<odoo>
|
||||
<record id="room_type_availability_view_form" model="ir.ui.view">
|
||||
<field name="name">pms.room.type.availability.plan.form</field>
|
||||
<field name="model">pms.room.type.availability.plan</field>
|
||||
<record id="availability_view_form" model="ir.ui.view">
|
||||
<field name="name">pms.availability.plan.form</field>
|
||||
<field name="model">pms.availability.plan</field>
|
||||
<field name="arch" type="xml">
|
||||
<form string="Rules">
|
||||
<sheet>
|
||||
@@ -58,9 +58,9 @@
|
||||
</form>
|
||||
</field>
|
||||
</record>
|
||||
<record id="room_type_availability_view_tree" model="ir.ui.view">
|
||||
<field name="name">pms.room.type.availability.plan.tree</field>
|
||||
<field name="model">pms.room.type.availability.plan</field>
|
||||
<record id="availability_view_tree" model="ir.ui.view">
|
||||
<field name="name">pms.availability.plan.tree</field>
|
||||
<field name="model">pms.availability.plan</field>
|
||||
|
||||
<field name="arch" type="xml">
|
||||
<tree string="Availability Plans">
|
||||
@@ -76,16 +76,16 @@
|
||||
</field>
|
||||
</record>
|
||||
<!-- Action of reservation availability plan-->
|
||||
<record model="ir.actions.act_window" id="room_type_availability_action">
|
||||
<record model="ir.actions.act_window" id="availability_action">
|
||||
<field name="name">Reservation Availability Plans</field>
|
||||
<field name="res_model">pms.room.type.availability.plan</field>
|
||||
<field name="res_model">pms.availability.plan</field>
|
||||
<field name="view_mode">tree,form</field>
|
||||
</record>
|
||||
<!-- MENUS -->
|
||||
<menuitem
|
||||
name="Availability Plans"
|
||||
id="reservation_availability_rules_menu"
|
||||
action="room_type_availability_action"
|
||||
id="reservation_availability_plan_rules_menu"
|
||||
action="availability_action"
|
||||
sequence="5"
|
||||
parent="pms.revenue_management_menu"
|
||||
/>
|
||||
@@ -508,7 +508,7 @@
|
||||
<field
|
||||
name="payment_state"
|
||||
decoration-success="payment_state == 'paid'"
|
||||
decoration-danger="payment_state == 'not_paid' and state in ['cancelled','onboard','done','no_show','no_checkout']"
|
||||
decoration-danger="payment_state == 'not_paid' and state in ['cancelled','onboard','done','arrival_delayed','departure_delayed']"
|
||||
decoration-info="payment_state == 'not_paid' and state in ['draft','confirm',]"
|
||||
decoration-warning="payment_state == 'partial'"
|
||||
widget="badge"
|
||||
|
||||
@@ -30,15 +30,13 @@
|
||||
</group>
|
||||
<group string="Sequences">
|
||||
<field name="folio_sequence_id" />
|
||||
<field name="reservation_sequence_id" />
|
||||
<field name="checkin_sequence_id" />
|
||||
</group>
|
||||
<group colspan="4" col="4" string="Check-in hours">
|
||||
<field name="default_arrival_hour" />
|
||||
<field name="default_departure_hour" />
|
||||
</group>
|
||||
<group colspan="4" col="4" string="Cancellation policies">
|
||||
<field name="default_cancel_policy_days" />
|
||||
<field name="default_cancel_policy_percent" />
|
||||
</group>
|
||||
</page>
|
||||
<page string="Rooms" name="property_rooms">
|
||||
<group>
|
||||
|
||||
@@ -14,7 +14,6 @@
|
||||
<header>
|
||||
<field name="splitted" invisible="True" />
|
||||
<field name="tax_ids" invisible="1" />
|
||||
<field name="checkin_today" invisible="1" />
|
||||
<field name="checkin_partner_count" invisible="1" />
|
||||
<button
|
||||
name="confirm"
|
||||
@@ -32,14 +31,7 @@
|
||||
<button
|
||||
name="action_reservation_checkout"
|
||||
string="Check Out"
|
||||
states="onboard,no_checkout"
|
||||
type="object"
|
||||
/>
|
||||
<button
|
||||
name="draft"
|
||||
string="Set to Draft"
|
||||
states="cancelled"
|
||||
class="oe_highlight"
|
||||
states="onboard,departure_delayed"
|
||||
type="object"
|
||||
/>
|
||||
<field name="state" widget="statusbar" />
|
||||
@@ -98,9 +90,8 @@
|
||||
</div>
|
||||
<sheet>
|
||||
<field name="shared_folio" invisible="1" />
|
||||
<field name="left_for_checkin" invisible="1" />
|
||||
<field name="allowed_checkin" invisible="1" />
|
||||
<field name="ready_for_checkin" invisible="1" />
|
||||
<field name="departure_today" invisible="1" />
|
||||
<div
|
||||
class="oe_button_box"
|
||||
name="button_box"
|
||||
@@ -157,7 +148,7 @@
|
||||
<button
|
||||
type="object"
|
||||
class="oe_stat_button"
|
||||
name="action_onboard"
|
||||
name="action_checkin_partner_onboard_view"
|
||||
attrs="{'invisible': [
|
||||
('ready_for_checkin', '!=', True),
|
||||
]}"
|
||||
@@ -171,9 +162,9 @@
|
||||
<button
|
||||
type="object"
|
||||
class="oe_stat_button"
|
||||
name="action_checks"
|
||||
name="action_checkin_partner_view"
|
||||
attrs="{'invisible': [
|
||||
('left_for_checkin', '!=', True),
|
||||
('allowed_checkin', '!=', True),
|
||||
]}"
|
||||
>
|
||||
<field
|
||||
@@ -275,7 +266,7 @@
|
||||
name="contact_details"
|
||||
>
|
||||
<field
|
||||
name="email"
|
||||
name="partner_email"
|
||||
colspan="2"
|
||||
nolabel="1"
|
||||
placeholder="email"
|
||||
@@ -283,10 +274,10 @@
|
||||
force_save="1"
|
||||
attrs="{'invisible': [('reservation_type','in',('out'))],
|
||||
'readonly': [('partner_id', '!=', False),
|
||||
('email','!=', False)]}"
|
||||
('partner_email','!=', False)]}"
|
||||
/>
|
||||
<field
|
||||
name="mobile"
|
||||
name="partner_mobile"
|
||||
colspan="2"
|
||||
nolabel="1"
|
||||
placeholder="mobile"
|
||||
@@ -294,7 +285,7 @@
|
||||
force_save="1"
|
||||
attrs="{'invisible': [('reservation_type','in',('out'))],
|
||||
'readonly': [('partner_id', '!=', False),
|
||||
('mobile','!=', False)]}"
|
||||
('partner_mobile','!=', False)]}"
|
||||
/>
|
||||
<field
|
||||
placeholder="Partner Notes"
|
||||
@@ -568,12 +559,6 @@
|
||||
string="Invoicing"
|
||||
attrs="{'invisible': [('reservation_type','in',('out'))]}"
|
||||
>
|
||||
<group>
|
||||
<field
|
||||
name="partner_invoice_id"
|
||||
string="Contact Invoiced"
|
||||
/>
|
||||
</group>
|
||||
</page>
|
||||
<page name="others" string="Others">
|
||||
<div class="row">
|
||||
@@ -581,7 +566,6 @@
|
||||
<group>
|
||||
<field name="user_id" />
|
||||
<field name="pms_property_id" />
|
||||
<field name="localizator" />
|
||||
<field name="overbooking" />
|
||||
</group>
|
||||
<group>
|
||||
@@ -594,7 +578,7 @@
|
||||
</div>
|
||||
<div class="col-6">
|
||||
<group>
|
||||
<field name="requests" />
|
||||
<field name="partner_requests" />
|
||||
</group>
|
||||
</div>
|
||||
</div>
|
||||
@@ -668,7 +652,6 @@
|
||||
<field name="overbooking" invisible="1" />
|
||||
<field name="activity_ids" widget="list_activity" optional="show" />
|
||||
<field name="user_id" optional="show" widget="many2one_avatar_user" />
|
||||
<!-- <field name="origin" /> -->
|
||||
<field name="checkin_partner_ids" invisible="1" />
|
||||
<field name="to_assign" invisible="1" />
|
||||
<field name="checkin_partner_pending_count" invisible="1" />
|
||||
@@ -680,17 +663,17 @@
|
||||
name="state"
|
||||
decoration-success="state == 'onboard'"
|
||||
decoration-info="state == 'confirm'"
|
||||
decoration-primary="state == 'no_checkout'"
|
||||
decoration-primary="state == 'departure_delayed'"
|
||||
decoration-danger="state == 'cancelled'"
|
||||
decoration-bf="state == 'draft'"
|
||||
decoration-warning="state == 'no_show'"
|
||||
decoration-warning="state == 'arrival_delayed'"
|
||||
widget="badge"
|
||||
optional="show"
|
||||
/>
|
||||
<field
|
||||
name="folio_payment_state"
|
||||
decoration-success="folio_payment_state == 'paid'"
|
||||
decoration-danger="folio_payment_state == 'not_paid' and state in ['cancelled','onboard','done','no_show','no_checkout']"
|
||||
decoration-danger="folio_payment_state == 'not_paid' and state in ['cancelled','onboard','done','arrival_delayed','departure_delayed']"
|
||||
decoration-info="folio_payment_state == 'not_paid' and state in ['draft','confirm',]"
|
||||
decoration-warning="folio_payment_state == 'partial'"
|
||||
widget="badge"
|
||||
@@ -786,7 +769,7 @@
|
||||
<filter
|
||||
string="To enter"
|
||||
name="to_enter"
|
||||
domain="[('left_for_checkin', '=', True)]"
|
||||
domain="[('allowed_checkin', '=', True)]"
|
||||
/>
|
||||
<filter
|
||||
string="Overbookings"
|
||||
|
||||
@@ -27,7 +27,7 @@
|
||||
<group colspan="4">
|
||||
<group>
|
||||
<field name="name" />
|
||||
<field name="code_type" />
|
||||
<field name="default_code" />
|
||||
<field name="class_id" />
|
||||
</group>
|
||||
<group>
|
||||
@@ -37,7 +37,7 @@
|
||||
</group>
|
||||
<group colspan="2">
|
||||
<group name="room_ids_group">
|
||||
<field name="shared_room" />
|
||||
<field name="is_shared_room" />
|
||||
<field name="room_ids" widget="many2many_tags" />
|
||||
<field name="total_rooms_count" />
|
||||
</group>
|
||||
@@ -92,7 +92,7 @@
|
||||
<field name="sequence" widget="handle" />
|
||||
<field name="pms_property_ids" widget="many2many_tags" />
|
||||
<field name="name" />
|
||||
<field name="code_type" />
|
||||
<field name="default_code" />
|
||||
<field name="list_price" />
|
||||
<field name="room_ids" />
|
||||
<field name="total_rooms_count" />
|
||||
|
||||
@@ -34,10 +34,6 @@
|
||||
invisible='True'
|
||||
/>
|
||||
</h1>
|
||||
<!-- <label for="to_be_cleaned" string="To be Cleaned" />
|
||||
<h2>
|
||||
<field name="to_be_cleaned"/>
|
||||
</h2> -->
|
||||
</div>
|
||||
<notebook>
|
||||
<page name="information_pms_room" string="Information">
|
||||
@@ -48,7 +44,7 @@
|
||||
force_save="1"
|
||||
/>
|
||||
<field
|
||||
name="floor_id"
|
||||
name="ubication_id"
|
||||
string="Ubication"
|
||||
attrs="{'readonly':[('shared_room_id','!=', False)]}"
|
||||
/>
|
||||
|
||||
@@ -9,7 +9,7 @@
|
||||
<group>
|
||||
<field name="name" colspan="1" />
|
||||
<field name="channel_type" />
|
||||
<field name="on_line" />
|
||||
<field name="is_on_line" />
|
||||
<field name="product_pricelist_ids" widget="many2many_tags" />
|
||||
</group>
|
||||
</sheet>
|
||||
@@ -23,7 +23,7 @@
|
||||
<tree string=" Sale Channel">
|
||||
<field name="name" />
|
||||
<field name="channel_type" />
|
||||
<field name="on_line" />
|
||||
<field name="is_on_line" />
|
||||
<field name="product_pricelist_ids" widget="many2many_tags" />
|
||||
</tree>
|
||||
</field>
|
||||
|
||||
@@ -32,7 +32,7 @@
|
||||
string="Information"
|
||||
>
|
||||
<group colspan="4" col="4">
|
||||
<field name="floor_id" string="Ubication" />
|
||||
<field name="ubication_id" string="Ubication" />
|
||||
<field name="room_type_id" string="Room Type" />
|
||||
<field name="beds" />
|
||||
<field name="sequence" />
|
||||
|
||||
@@ -1,8 +1,8 @@
|
||||
<?xml version="1.0" encoding="utf-8" ?>
|
||||
<odoo>
|
||||
<record model="ir.ui.view" id="pms_floor_view_form">
|
||||
<field name="name">pms.floor.form</field>
|
||||
<field name="model">pms.floor</field>
|
||||
<record model="ir.ui.view" id="pms_ubication_view_form">
|
||||
<field name="name">pms.ubication.form</field>
|
||||
<field name="model">pms.ubication</field>
|
||||
<field name="arch" type="xml">
|
||||
<form string="Property Ubication">
|
||||
<sheet>
|
||||
@@ -14,14 +14,15 @@
|
||||
widget="many2many_tags"
|
||||
options="{'no_create': True,'no_open': True}"
|
||||
/>
|
||||
<field name="pms_room_ids" />
|
||||
</group>
|
||||
</sheet>
|
||||
</form>
|
||||
</field>
|
||||
</record>
|
||||
<record model="ir.ui.view" id="pms_floor_view_tree">
|
||||
<field name="name">pms.floor.tree</field>
|
||||
<field name="model">pms.floor</field>
|
||||
<record model="ir.ui.view" id="pms_ubication_view_tree">
|
||||
<field name="name">pms.ubication.tree</field>
|
||||
<field name="model">pms.ubication</field>
|
||||
<field name="arch" type="xml">
|
||||
<tree string=" Property Ubications">
|
||||
<field name="name" colspan="1" />
|
||||
@@ -29,15 +30,15 @@
|
||||
</tree>
|
||||
</field>
|
||||
</record>
|
||||
<record model="ir.actions.act_window" id="open_pms_floor_form_tree">
|
||||
<field name="name">Floor Structure</field>
|
||||
<field name="res_model">pms.floor</field>
|
||||
<record model="ir.actions.act_window" id="open_pms_ubication_form_tree">
|
||||
<field name="name">Ubication Structure</field>
|
||||
<field name="res_model">pms.ubication</field>
|
||||
<field name="view_mode">tree,form</field>
|
||||
</record>
|
||||
<menuitem
|
||||
name="Ubications"
|
||||
id="menu_open_pms_floor_form_tree"
|
||||
action="open_pms_floor_form_tree"
|
||||
id="menu_open_pms_ubication_form_tree"
|
||||
action="open_pms_ubication_form_tree"
|
||||
sequence="65"
|
||||
parent="pms.pms_rooms_menu"
|
||||
/>
|
||||
@@ -16,7 +16,6 @@
|
||||
/>
|
||||
<field name="is_extra_bed" />
|
||||
<field name="daily_limit" />
|
||||
<field name="show_in_calendar" />
|
||||
</group>
|
||||
<group>
|
||||
<field name="per_day" />
|
||||
|
||||
@@ -3,7 +3,9 @@
|
||||
<record id="pms_partner_reservations" model="ir.actions.act_window">
|
||||
<field name="name">Reservations</field>
|
||||
<field name="res_model">pms.reservation</field>
|
||||
<field name="domain">[('partner_id', '=',active_id)]</field>
|
||||
<field
|
||||
name="domain"
|
||||
>[('folio_id.partner_id', 'in', "TODO: O2m de partner a folios")]</field>
|
||||
</record>
|
||||
<record id="pms_partner_folios" model="ir.actions.act_window">
|
||||
<field name="name">Folios</field>
|
||||
@@ -80,7 +82,7 @@
|
||||
<span>%%</span>
|
||||
</div>-->
|
||||
<field name="apply_pricelist" />
|
||||
<field name="invoice_agency" />
|
||||
<field name="invoice_to_agency" />
|
||||
</group>
|
||||
</page>
|
||||
</xpath>
|
||||
|
||||
@@ -255,7 +255,7 @@
|
||||
<div class="col pl-md-0">
|
||||
<div
|
||||
t-field="reservation.partner_id"
|
||||
t-options='{"widget": "contact", "fields": ["name", "email", "phone"]}'
|
||||
t-options='{"widget": "contact", "fields": ["name", "partner_email", "partner_phone"]}'
|
||||
/>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
@@ -103,7 +103,7 @@ class FolioWizard(models.TransientModel):
|
||||
]
|
||||
):
|
||||
num_rooms_available = self.env[
|
||||
"pms.room.type.availability.plan"
|
||||
"pms.availability.plan"
|
||||
].get_count_rooms_available(
|
||||
checkin=record.start_date,
|
||||
checkout=record.end_date,
|
||||
|
||||
@@ -81,7 +81,7 @@ class AvailabilityWizard(models.TransientModel):
|
||||
partner=partner.id,
|
||||
quantity=1,
|
||||
date=fields.Date.today(),
|
||||
date_overnight=date_iterator,
|
||||
consumption_date=date_iterator,
|
||||
pricelist=record.folio_wizard_id.pricelist_id.id,
|
||||
uom=product.uom_id.id,
|
||||
property=record.folio_wizard_id.pms_property_id.id,
|
||||
@@ -113,7 +113,7 @@ class AvailabilityWizard(models.TransientModel):
|
||||
def _compute_num_rooms_available(self):
|
||||
for record in self:
|
||||
record.num_rooms_available = self.env[
|
||||
"pms.room.type.availability.plan"
|
||||
"pms.availability.plan"
|
||||
].get_count_rooms_available(
|
||||
record.checkin,
|
||||
record.checkout,
|
||||
|
||||
@@ -30,7 +30,7 @@ class AvailabilityWizard(models.TransientModel):
|
||||
required=True,
|
||||
)
|
||||
availability_plan_id = fields.Many2one(
|
||||
comodel_name="pms.room.type.availability.plan",
|
||||
comodel_name="pms.availability.plan",
|
||||
string="Availability Plan to apply massive changes",
|
||||
# can be setted by context from availability plan detail
|
||||
)
|
||||
@@ -169,7 +169,7 @@ class AvailabilityWizard(models.TransientModel):
|
||||
)
|
||||
|
||||
rules_to_overwrite = fields.One2many(
|
||||
comodel_name="pms.room.type.availability.rule",
|
||||
comodel_name="pms.availability.plan.rule",
|
||||
compute="_compute_rules_to_overwrite",
|
||||
store=False,
|
||||
readonly=True,
|
||||
@@ -275,7 +275,7 @@ class AvailabilityWizard(models.TransientModel):
|
||||
record.apply_on_sunday,
|
||||
)
|
||||
if record.start_date and record.end_date:
|
||||
rules = self.env["pms.room.type.availability.rule"].search(domain)
|
||||
rules = self.env["pms.availability.plan.rule"].search(domain)
|
||||
if (
|
||||
not record.apply_on_all_week
|
||||
and record.start_date
|
||||
@@ -525,7 +525,7 @@ class AvailabilityWizard(models.TransientModel):
|
||||
)
|
||||
overwrite.write(vals)
|
||||
else:
|
||||
self.env["pms.room.type.availability.rule"].create(
|
||||
self.env["pms.availability.plan.rule"].create(
|
||||
{
|
||||
"availability_plan_id": avail_plan_id,
|
||||
"date": date,
|
||||
@@ -556,9 +556,9 @@ class AvailabilityWizard(models.TransientModel):
|
||||
record.massive_changes_on == "availability_plan"
|
||||
and not record.avail_readonly
|
||||
):
|
||||
action = self.env.ref("pms.room_type_availability_action").read()[0]
|
||||
action = self.env.ref("pms.availability_action").read()[0]
|
||||
action["views"] = [
|
||||
(self.env.ref("pms.room_type_availability_view_form").id, "form")
|
||||
(self.env.ref("pms.availability_view_form").id, "form")
|
||||
]
|
||||
action["res_id"] = record.availability_plan_id.id
|
||||
return action
|
||||
|
||||
@@ -93,7 +93,7 @@
|
||||
<field name="arch" type="xml">
|
||||
<search string="Housekeeping filters">
|
||||
<field name="clean_employee_id" />
|
||||
<field name="floor_id" />
|
||||
<field name="ubication_id" />
|
||||
<field name="room_type_id" />
|
||||
<!-- <filter name="filter_occupied" string="Occupied" domain="[('clean_status','=','occupied')]"/> -->
|
||||
|
||||
@@ -113,8 +113,8 @@
|
||||
icon="fa-user"
|
||||
/>
|
||||
<field
|
||||
name="floor_id"
|
||||
string="Floor"
|
||||
name="ubication_id"
|
||||
string="Ubication"
|
||||
enable_counters="1"
|
||||
select="multi"
|
||||
icon="fa-hospital-o"
|
||||
@@ -134,8 +134,8 @@
|
||||
<field name="active" eval="True" />
|
||||
<field name="arch" type="xml">
|
||||
<kanban
|
||||
default_group_by="floor_id"
|
||||
default_order="floor_id"
|
||||
default_group_by="ubication_id"
|
||||
default_order="ubication_id"
|
||||
class="o_res_partner_kanban"
|
||||
sample="1"
|
||||
group_create="false"
|
||||
|
||||
@@ -10,11 +10,38 @@ from odoo.tests import common
|
||||
@freeze_time("2011-03-16")
|
||||
class TestResPartner(common.SavepointCase):
|
||||
def create_common_scenario(self):
|
||||
self.folio_sequence = self.env["ir.sequence"].create(
|
||||
{
|
||||
"name": "PMS Folio",
|
||||
"code": "pms.folio",
|
||||
"padding": 4,
|
||||
"company_id": self.env.ref("base.main_company").id,
|
||||
}
|
||||
)
|
||||
self.reservation_sequence = self.env["ir.sequence"].create(
|
||||
{
|
||||
"name": "PMS Reservation",
|
||||
"code": "pms.reservation",
|
||||
"padding": 4,
|
||||
"company_id": self.env.ref("base.main_company").id,
|
||||
}
|
||||
)
|
||||
self.checkin_sequence = self.env["ir.sequence"].create(
|
||||
{
|
||||
"name": "PMS Checkin",
|
||||
"code": "pms.checkin.partner",
|
||||
"padding": 4,
|
||||
"company_id": self.env.ref("base.main_company").id,
|
||||
}
|
||||
)
|
||||
self.property_test = self.property = self.env["pms.property"].create(
|
||||
{
|
||||
"name": "My property test",
|
||||
"company_id": self.env.ref("base.main_company").id,
|
||||
"default_pricelist_id": self.env.ref("product.list0").id,
|
||||
"folio_sequence_id": self.folio_sequence.id,
|
||||
"reservation_sequence_id": self.reservation_sequence.id,
|
||||
"checkin_sequence_id": self.checkin_sequence.id,
|
||||
}
|
||||
)
|
||||
|
||||
|
||||
Reference in New Issue
Block a user