Skip to content

Commit

Permalink
updates on floors (#377)
Browse files Browse the repository at this point in the history
for ms

[IMP] Added "Multi-session Settings" form, 
[CI] Added unittests, 
[DEMO] Added unsynchronized POS in Demo,
[IMP] added search function for computed field current_session_state,

for msr

[DEMO] Added floor for unsynchronized POS in Demo
[IMP] IMP POSes in Multi-session have one common floor set. Unsynchronized POSes may have its own floor set.
  • Loading branch information
KolushovAlexandr authored and Ivan Yelizariev committed Sep 27, 2017
1 parent 7f2d8aa commit 338804a
Show file tree
Hide file tree
Showing 16 changed files with 167 additions and 11 deletions.
6 changes: 6 additions & 0 deletions pos_multi_session/README.rst
Original file line number Diff line number Diff line change
@@ -1,6 +1,12 @@
Sync POS orders across multiple sessions
========================================

The module synchronize orders data between POSes related to a common multi session. Longpolling provides instant updates between POSes in a multi session.

All work data is stored on server. Offline POS is only able to create new orders, after connecting a POS back, data will be synchronized.

POSes are able to work without synchronization, like without the module.

Tests: `<external_tests/README.rst>`__

Tested on Odoo 10.0 5a3c43b480b404ca660fe2b0860e0a1572c08017
3 changes: 2 additions & 1 deletion pos_multi_session/__manifest__.py
Original file line number Diff line number Diff line change
Expand Up @@ -4,7 +4,7 @@
"summary": """Use multiple POS for handling orders""",
"category": "Point Of Sale",
"images": ["images/pos-multi-session.png"],
"version": "3.0.4",
"version": "3.1.0",
"application": False,

"author": "IT-Projects LLC, Ivan Yelizariev",
Expand All @@ -22,6 +22,7 @@
"data": [
"security/ir.model.access.csv",
"views.xml",
"multi_session_view.xml"
],
"qweb": [
"static/src/xml/pos_multi_session.xml",
Expand Down
3 changes: 3 additions & 0 deletions pos_multi_session/demo/demo.xml
Original file line number Diff line number Diff line change
Expand Up @@ -12,6 +12,9 @@
<field name="name">POS2</field>
<field name="multi_session_id" ref="demo_multi_session"/>
</record>
<record id="demo_multi_pos_config_three" model="pos.config">
<field name="name">POS3</field>
</record>
<record id="point_of_sale.pos_config_main" model="pos.config">
<field name="multi_session_id" ref="demo_multi_session"/>
</record>
Expand Down
7 changes: 7 additions & 0 deletions pos_multi_session/doc/changelog.rst
Original file line number Diff line number Diff line change
Expand Up @@ -3,6 +3,13 @@
Updates
=======

`3.1.0`
-------

- NEW: Added "Multi-session Settings" form.
- NEW: Added unsynchronized POS in Demo.
- NEW: Added unittests.

`3.0.4`
-------

Expand Down
15 changes: 14 additions & 1 deletion pos_multi_session/models/pos_multi_session_models.py
Original file line number Diff line number Diff line change
Expand Up @@ -18,13 +18,26 @@ class PosConfig(models.Model):
multi_session_replace_empty_order = fields.Boolean('Replace empty order', default=True, help='Empty order is deleted whenever new order is come from another POS')
multi_session_deactivate_empty_order = fields.Boolean('Deactivate empty order', default=False, help='POS is switched to new foreign Order, if current order is empty')
multi_session_message_ID = fields.Integer(default=1, string="Last sent message number")
current_session_state = fields.Char(search='_search_current_session_state')

def _search_current_session_state(self, operator, value):
ids = map(lambda x: x.id, self.env["pos.config"].search([]))
value_ids = map(lambda x: x.config_id.id, self.env["pos.session"].search([('state', '=', value)]))
value_ids = list(set(value_ids))
if operator == '=':
return [('id', 'in', value_ids)]
elif operator == '!=':
ids = [item for item in ids if item not in value_ids]
return [('id', 'in', ids)]
else:
return [('id', 'in', [])]


class PosMultiSession(models.Model):
_name = 'pos.multi_session'

name = fields.Char('Name')
pos_ids = fields.One2many('pos.config', 'multi_session_id', 'POSes')
pos_ids = fields.One2many('pos.config', 'multi_session_id', string='POSes in Multi-session')
order_ids = fields.One2many('pos.multi_session.order', 'multi_session_id', 'Orders')
order_ID = fields.Integer(string="Order number", default=0, help="Current Order Number shared across all POS in Multi Session")

Expand Down
37 changes: 37 additions & 0 deletions pos_multi_session/multi_session_view.xml
Original file line number Diff line number Diff line change
@@ -0,0 +1,37 @@
<?xml version="1.0" encoding="utf-8"?>
<odoo>
<data>

<record id="multi_session_form" model="ir.ui.view">
<field name="name">pos.multi_session.form</field>
<field name="model">pos.multi_session</field>
<field name="type">form</field>
<field name="arch" type="xml">
<form>
<sheet string="Multi-session">
<label for="name" class="oe_edit_only"/>
<h1><field name="name"/></h1>
<group string="Settings">
<field name="pos_ids" widget="many2many_tags" domain="[('current_session_state', '!=', 'opened')]" options="{'not_delete': True}"/>
<field name="order_ID" readonly="1"/>
<field name="order_ids" readonly="1"/>
</group>
<group>
<p class="oe_edit_only"> To remove or add a POS to multi-session close its session first </p>
</group>
</sheet>
</form>
</field>
</record>

<record id="action_multi_session_form" model="ir.actions.act_window">
<field name="name">Multi-sessions</field>
<field name="res_model">pos.multi_session</field>
<field name="view_type">form</field>
<field name="view_mode">tree,form</field>
</record>

<menuitem id="menu_pos_ms_settings" name="Multi-session Settings" parent="point_of_sale.menu_point_config_product" sequence="25" action="action_multi_session_form" groups="base.group_system"/>

</data>
</odoo>
3 changes: 3 additions & 0 deletions pos_multi_session/static/src/js/pos_multi_session.js
Original file line number Diff line number Diff line change
Expand Up @@ -396,6 +396,9 @@ odoo.define('pos_multi_session', function(require){
}
})
};
if (!this.pos.config.multi_session_id){
return;
}
this.enquied = true;
this.pos.multi_session.enque(f);
}
Expand Down
2 changes: 2 additions & 0 deletions pos_multi_session/tests/__init__.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,2 @@
# -*- coding: utf-8 -*-
from . import test_test
35 changes: 35 additions & 0 deletions pos_multi_session/tests/test_test.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,35 @@
# -*- coding: utf-8 -*-

import odoo
from odoo import fields
from odoo.tools import float_compare, mute_logger
from odoo.tests.common import TransactionCase
# from odoo.addons.point_of_sale.tests.common import TestPointOfSaleCommon

@odoo.tests.common.at_install(False)
@odoo.tests.common.post_install(True)
class TestPoSSessionState(TransactionCase):

def test_current_session_state(self):

self.pos_config = self.env.ref('point_of_sale.pos_config_main')

# I click on create a new session button
self.pos_config.open_session_cb()
opened_session_pos = self.pos_config.id

# Check that this session state is opened
self.assertEqual(
self.pos_config.current_session_state, 'opened')

# _search_current_session_state function check
poses_with_opened_sessions = self.env['pos.config'].search([('current_session_state', '=', 'opened')])
poses_with_not_opened_sessions = self.env['pos.config'].search([('current_session_state', '!=', 'opened')])
third_case = self.env['pos.config'].search([('current_session_state', '>', 'opened')])
# Checking next cases: operator = '=', operator = '!=' and contradictory case
self.assertIn(
opened_session_pos, poses_with_opened_sessions.ids)
self.assertNotIn(
opened_session_pos, poses_with_not_opened_sessions.ids)
self.assertEqual(
len(third_case), 0)
2 changes: 2 additions & 0 deletions pos_multi_session_restaurant/README.rst
Original file line number Diff line number Diff line change
Expand Up @@ -8,6 +8,8 @@ Syncs additional restaurant data:
* Printer status (green "Order" button)
* Notes

Each multi-session and each unsynchronized POS may have its own floor set. POSes in multi-session have same floors.

FIXME: there is issue with floor real-time synchronization, to synchronize tables after modifying them it is mandatory to refresh all POSes pages, also deleting a table with open order on it leads to constant error messages. See https://github.com/it-projects-llc/pos-addons/issues/375.

Local run
Expand Down
2 changes: 1 addition & 1 deletion pos_multi_session_restaurant/__manifest__.py
Original file line number Diff line number Diff line change
Expand Up @@ -4,7 +4,7 @@
"summary": """Staff get order details immediately after waiter taps on tablet""",
"category": "Point of Sale",
"images": ['images/s2.png'],
"version": "2.0.0",
"version": "2.1.0",
"application": False,

"author": "IT-Projects LLC, Ivan Yelizariev",
Expand Down
4 changes: 4 additions & 0 deletions pos_multi_session_restaurant/demo/demo.xml
Original file line number Diff line number Diff line change
Expand Up @@ -5,6 +5,10 @@
<field name="floor_ids" eval="[(6,0,[ref('pos_restaurant.floor_main')])]"/>
</record>

<record id="pos_multi_session.demo_multi_pos_config_three" model="pos.config">
<field name="floor_ids" eval="[(6,0,[ref('pos_restaurant.floor_patio')])]"/>
</record>

<record id="point_of_sale.pos_config_main" model="pos.config">
<field name="multi_session_id" ref="pos_multi_session.demo_multi_session"/>
</record>
Expand Down
5 changes: 5 additions & 0 deletions pos_multi_session_restaurant/doc/changelog.rst
Original file line number Diff line number Diff line change
Expand Up @@ -3,6 +3,11 @@
Updates
=======

`2.1.0`
-------
- IMP: POSes in Multi-session have one common floor set. Unsynchronized POSes may have its own floor set.
- FIX: Deleting floors data whilst removing them from POS.

`2.0.0`
-------
- FIX: POS floors synchronization.
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -8,13 +8,15 @@ class RestaurantFloor(models.Model):
pos_multi_session_ids = fields.Many2many('pos.multi_session', 'pos_multi_session_floor_rel', 'floor_id', 'pos_multi_session_id')


class PosConfig(models.Model):
_inherit = 'pos.config'
class PosMultiSession(models.Model):
_inherit = 'pos.multi_session'

floor_ids = fields.Many2many(related='multi_session_id.floor_ids')
floor_ids = fields.Many2many('restaurant.floor', 'pos_multi_session_floor_rel', 'pos_multi_session_id', 'floor_id',
string='Restaurant Floors', help='The restaurant floors served by this point of sale',
ondelete="restrict")


class PosMultiSession(models.Model):
_inherit = 'pos.multi_session'
class PosConfig(models.Model):
_inherit = 'pos.config'

floor_ids = fields.Many2many('restaurant.floor', 'pos_multi_session_floor_rel', 'pos_multi_session_id', 'floor_id')
ms_floor_ids = fields.Many2many(related='multi_session_id.floor_ids')
Original file line number Diff line number Diff line change
Expand Up @@ -56,14 +56,36 @@ odoo.define('pos_multi_session_restaurant', function(require){
var PosModelSuper = models.PosModel;
models.PosModel = models.PosModel.extend({
initialize: function(){
var ms_model = {
model: 'pos.multi_session',
fields: ['name','floor_ids'],
domain: null,
loaded: function(self,floors){
self.multi_session_floors = floors;
}};
this.models.splice(
1 + this.models.indexOf(_.find(this.models, function(model){
return model.model === 'pos.config';
})), 0, ms_model);
var floor_model = _.find(this.models, function(model){ return model.model === 'restaurant.floor'; });
floor_model.domain = function(self){ return [['id','in',self.config.floor_ids]]; };
floor_model.domain = function(self, ms_model){
var temporary = [['id','in',self.config.floor_ids]];
if (self.config.multi_session_id){
var ms_floors = _.find(self.multi_session_floors, function(session){
return session.id === self.config.multi_session_id[0];
});
temporary = [['id','in', ms_floors.floor_ids]];
}
return temporary;
};
var self = this;
PosModelSuper.prototype.initialize.apply(this, arguments);
this.ready.then(function () {
if (!self.config.multi_session_id){
return;
}
self.multi_session.floor_ids = self.multi_session_floors.floor_ids;
self.config.floor_ids = self.multi_session.floor_ids;
var remove_order_super = Object.getPrototypeOf(self.multi_session).remove_order;
self.multi_session.remove_order = function(data) {
if (data.transfer) {
Expand Down
16 changes: 15 additions & 1 deletion pos_multi_session_restaurant/views/views.xml
Original file line number Diff line number Diff line change
Expand Up @@ -25,7 +25,21 @@
<field name="arch" type="xml">
<data>
<xpath expr="//field[@name='floor_ids']" position="replace">
<field name="floor_ids" required="1" widget="many2many_tags"/>
<field name="floor_ids" widget="many2many_tags" attrs="{'invisible':[('multi_session_id', 'not in', [None,False])]}"/>
<field name="ms_floor_ids" widget="many2many_tags" attrs="{'invisible':[('multi_session_id', 'in', [None,False])]}"/>
</xpath>
</data>
</field>
</record>

<record id="multi_session_restaurant_form" model="ir.ui.view">
<field name="name">pos.multi_session.form</field>
<field name="model">pos.multi_session</field>
<field name="inherit_id" ref="pos_multi_session.multi_session_form"/>
<field name="arch" type="xml">
<data>
<xpath expr="//field[@name='pos_ids']" position="after">
<field name="floor_ids" widget="many2many_tags"/>
</xpath>
</data>
</field>
Expand Down

0 comments on commit 338804a

Please sign in to comment.