Skip to content

Commit

Permalink
Merge remote-tracking branch 'upstream/10.0' into 11.0-merge-379d32b
Browse files Browse the repository at this point in the history
  • Loading branch information
Ildar Nasyrov committed Feb 28, 2018
2 parents 6474779 + 379d32b commit bd489b3
Show file tree
Hide file tree
Showing 165 changed files with 8,100 additions and 948 deletions.
4 changes: 2 additions & 2 deletions .travis.yml
Original file line number Diff line number Diff line change
Expand Up @@ -23,9 +23,9 @@ env:

matrix:
- LINT_CHECK="1"
- TRANSIFEX="1"
- TESTS="1" ODOO_REPO="odoo/odoo"
- TESTS="1" ODOO_REPO="OCA/OCB""
- TRANSIFEX="1"


install:
Expand All @@ -38,7 +38,7 @@ script:
- travis_run_tests

after_success:
coveralls
- travis_after_tests_success

notifications:
email: false
1 change: 1 addition & 0 deletions hw_printer_network/README.rst
Original file line number Diff line number Diff line change
Expand Up @@ -13,6 +13,7 @@ Credits
Contributors
------------
* Dinar Gabbasov <gabbasov@it-projects.info>
* Tom Blauwendraat <tom@sunflowerweb.nl>

Sponsors
--------
Expand Down
2 changes: 1 addition & 1 deletion hw_printer_network/__openerp__.py
Original file line number Diff line number Diff line change
Expand Up @@ -4,7 +4,7 @@
"summary": """Hardware Driver for Network Printers""",
"category": "Point of Sale",
"images": [],
"version": "1.0.0",
"version": "2.0.0",
"application": False,

"author": "IT-Projects LLC, Dinar Gabbasov",
Expand Down
233 changes: 123 additions & 110 deletions hw_printer_network/controllers/hw_printer_network_controller.py
Original file line number Diff line number Diff line change
Expand Up @@ -2,8 +2,10 @@
from openerp import http
import logging
import time
import socket
import subprocess
import threading
import traceback
from ast import literal_eval


_logger = logging.getLogger(__name__)
Expand All @@ -13,157 +15,168 @@
from openerp.addons.hw_escpos.escpos import escpos
from openerp.addons.hw_escpos.controllers.main import EscposProxy
from openerp.addons.hw_escpos.controllers.main import EscposDriver
from openerp.addons.hw_escpos.escpos.exceptions import NoDeviceError, HandleDeviceError, TicketNotPrinted, NoStatusError
from openerp.addons.hw_escpos.escpos.printer import Network
import openerp.addons.hw_escpos.controllers.main as hw_escpos_main
import openerp.addons.hw_proxy.controllers.main as hw_proxy
except ImportError:
EscposProxy = object
EscposDriver = object


class UpdatedEscposDriver(EscposDriver):
class PingProcess(threading.Thread):
def __init__(self, ip):
self.stdout = None
self.stderr = None
threading.Thread.__init__(self)
self.status = 'offline'
self.ip = ip
self.stop = False

def run(self):
while not self.stop:
child = subprocess.Popen(
["ping", "-c1", "-w5", self.ip],
shell=False,
stdout=subprocess.PIPE,
stderr=subprocess.PIPE
)
child.communicate()
self.status = 'offline' if child.returncode else 'online'
time.sleep(1)

def get_status(self):
return self.status

def __del__(self):
self.stop = True


class EscposNetworkDriver(EscposDriver):

def __init__(self):
self.network_printers = False
self.usb_printer_active = False
self.run_network_connection()
super(UpdatedEscposDriver, self).__init__()

def run_network_connection(self):
while self.network_printers and len(self.network_printers) > 0:
driver.network_printers = self.connected_network_printers(self.network_printers)
time.sleep(5)

def connected_network_printers(self, printers):
printer = False
if printers and len(printers) > 0:
network_printers = []
for p in printers:
if type(p) is str:
p = literal_eval(p)
try:
printer = UpdatedNetwork(p['ip'])
printer.close()
p['status'] = 'online'
except:
p['status'] = 'offline'
if printer:
printer.close()
network_printers.append({
'ip': str(p['ip']),
'status': str(p['status']),
'name': str(p['name'])
})
return network_printers
return printers
self.network_printers = []
self.ping_processes = {}
self.printer_objects = {}
super(EscposNetworkDriver, self).__init__()

def get_network_printer(self, ip, name=None):
found_printer = False
for printer in self.network_printers:
if printer['ip'] == ip:
found_printer = True
if name:
printer['name'] = name
if printer['status'] == 'online':
printer_object = self.printer_objects.get(ip, None)
if not printer_object:
try:
printer_object = Network(ip)
self.printer_objects[ip] = printer_object
except socket.error:
pass
return printer
if not found_printer:
self.add_network_printer(ip, name)
return None

def add_network_printer(self, ip, name=None):
printer = dict(
ip=ip,
status='offline',
name=name or 'Unnamed printer'
)
self.network_printers.append(printer) # dont return because offline
self.start_pinging(ip)

def start_pinging(self, ip):
pinger = PingProcess(ip)
self.ping_processes[ip] = pinger
pinger.start()

def update_driver_status(self):
count = len([p for p in self.network_printers if p.get('status', None) == 'online'])
if count:
self.set_status('connected', '{} printer(s) Connected'.format(count))
else:
self.set_status('disconnected', 'Disconnected')

def run(self):
printer = None
if not escpos:
_logger.error('ESC/POS cannot initialize, please verify system dependencies.')
return
while True:
try:
error = True
timestamp, task, data = self.queue.get(True)
printer = None
if len(task) == 2:
if task[0] == 'network_xml_receipt':
if timestamp >= time.time() - 1 * 60 * 60:
network_printer_proxy = task[1]
# print in network printer
printer = UpdatedNetwork(network_printer_proxy)
printer.receipt(data)
else:
if self.usb_printer_active:
printer = self.get_escpos_printer()
elif self.network_printers:
self.set_status('connected', 'Connected')
if printer is None:
if self.usb_printer_active is False:
if self.network_printers:
self.set_status('connected', 'Connected')
else:
if task != 'status':
self.queue.put((timestamp, task, data))
elif self.usb_printer_active is True:
if task != 'status':
self.queue.put((timestamp, task, data))
if task == 'xml_receipt':
error = False
time.sleep(5)
continue
elif task == 'receipt':
if timestamp >= time.time() - 1 * 60 * 60:
self.print_receipt_body(printer, data)
printer.cut()
elif task == 'xml_receipt':
if timestamp >= time.time() - 1 * 60 * 60:
printer.receipt(data)
elif task == 'cashbox':
if timestamp >= time.time() - 12:
self.open_cashbox(printer)
if timestamp >= (time.time() - 1 * 60 * 60):
receipt, network_printer_ip = data
printer_info = self.get_network_printer(network_printer_ip)
printer = self.printer_objects.get(network_printer_ip, None)
if printer_info and printer_info['status'] == 'online' and printer:
_logger.info('Printing XML receipt on printer %s...', network_printer_ip)
try:
printer.receipt(receipt)
except socket.error:
printer.open()
printer.receipt(receipt)
_logger.info('Done printing XML receipt on printer %s', network_printer_ip)
else:
_logger.error('xml_receipt: printer offline!')
# TODO: do something with the missed order?
elif task == 'printstatus':
self.print_status(printer)
elif task == 'status':
pass
elif task == 'status':
error = False
for printer in self.network_printers:
ip = printer['ip']
pinger = self.ping_processes.get(ip, None)
if pinger and pinger.isAlive():
status = pinger.get_status()
if status != printer['status']:
# todo: use a lock?
printer['status'] = status
self.update_driver_status()
else:
self.start_pinging(ip)
error = False

except NoDeviceError as e:
_logger.error("No device found %s" % str(e))
except HandleDeviceError as e:
_logger.error("Impossible to handle the device due to previous error %s" % str(e))
except TicketNotPrinted as e:
_logger.error("The ticket does not seems to have been fully printed %s" % str(e))
except NoStatusError as e:
_logger.error("Impossible to get the status of the printer %s" % str(e))
except Exception as e:
self.set_status('error', str(e))
errmsg = str(e) + '\n' + '-'*60+'\n' + traceback.format_exc() + '-'*60 + '\n'
_logger.error(errmsg)
finally:
if error:
self.queue.put((timestamp, task, data))
if printer:
printer.close()


driver = UpdatedEscposDriver()
hw_escpos_main.driver = driver
driver.push_task('printstatus')
# Separate instance, mainloop and queue for network printers
# original driver runs in parallel and deals with USB printers
network_driver = EscposNetworkDriver()

hw_proxy.drivers['escpos_network'] = network_driver

# this will also start the message handling loop
network_driver.push_task('printstatus')


class UpdatedEscposProxy(EscposProxy):
@http.route('/hw_proxy/print_xml_receipt', type='json', auth='none', cors='*')
def print_xml_receipt(self, receipt, proxy=None):
if proxy:
driver.push_task(['network_xml_receipt', proxy], receipt)
network_driver.push_task('xml_receipt', (receipt, proxy))
else:
super(UpdatedEscposProxy, self).print_xml_receipt(receipt)

@http.route('/hw_proxy/network_printers', type='json', auth='none', cors='*')
def networ_printers(self, network_printers=None):
network_printers = list(set([str(e) for e in network_printers]))
for i in range(len(network_printers)):
network_printers[i] = literal_eval(network_printers[i])
driver.network_printers = network_printers
driver.run_network_connection()
def network_printers(self, network_printers=None):
for printer in network_printers:
network_driver.get_network_printer(printer['ip'], name=printer['name'])

@http.route('/hw_proxy/status_network_printers', type='json', auth='none', cors='*')
def networ_printers_status(self):
return driver.network_printers
def network_printers_status(self):
return network_driver.network_printers

@http.route('/hw_proxy/without_usb', type='http', auth='none', cors='*')
def without_usb(self):
driver.usb_printer_active = False
""" Old pos_printer_network module expects this to work """
return "ping"

@http.route('/hw_proxy/hello', type='http', auth='none', cors='*')
def hello(self):
driver.usb_printer_active = True
return super(UpdatedEscposProxy, self).hello()


class UpdatedNetwork(Network):
def close(self):
""" Close TCP connection """
if self.device:
self.device.close()
5 changes: 5 additions & 0 deletions hw_printer_network/doc/changelog.rst
Original file line number Diff line number Diff line change
@@ -1,3 +1,8 @@
`2.0.0`
-------

- **IMP:** Asynchroneous checking of network status to speed it up when there are more than one network printer in the system. Also, there is no need to modify code of posbox anymore.

`1.0.0`
-------

Expand Down
9 changes: 0 additions & 9 deletions hw_printer_network/doc/index.rst
Original file line number Diff line number Diff line change
Expand Up @@ -8,15 +8,6 @@ Installation
In PosBox
---------

* Comment out line 354 in hw_escpos/controllers/main.py, i.e. replace

``driver.push_task('printstatus')``

with

``# driver.push_task('printstatus')``

Read here how to edit files at PosBox: https://odoo-development.readthedocs.io/en/latest/admin/posbox/administrate-posbox.html#how-to-edit-odoo-source.
* add ``hw_printer_network`` module to *server wide modules*. Detailed instruction is here: https://odoo-development.readthedocs.io/en/latest/admin/posbox/administrate-posbox.html#how-to-update-odoo-command-line-options

Usage
Expand Down
2 changes: 1 addition & 1 deletion pos_debt_notebook/__manifest__.py
Original file line number Diff line number Diff line change
Expand Up @@ -4,7 +4,7 @@
'category': 'Point Of Sale',
'live_test_url': 'http://apps.it-projects.info/shop/product/pos-debt-notebook?version=10.0',
"images": ['images/debt_notebook.png'],
'version': '4.4.1',
'version': '4.4.3',

'author': 'IT-Projects LLC, Ivan Yelizariev',
"support": "apps@it-projects.info",
Expand Down
10 changes: 10 additions & 0 deletions pos_debt_notebook/doc/changelog.rst
Original file line number Diff line number Diff line change
@@ -1,3 +1,13 @@
`4.4.3`
-------

**FIX:** Compatibility with Chinese localization

`4.4.2`
-------

**ADD:** Compatibility with Pos Mobile

`4.4.1`
-------

Expand Down
10 changes: 10 additions & 0 deletions pos_debt_notebook/doc/index.rst
Original file line number Diff line number Diff line change
Expand Up @@ -19,6 +19,16 @@ Debt Journal
* select Customer
* on payment screen use "Debt Journal" to pay

Pay Full Debt button
--------------------

The button appears when you select Customer which has unpaid debt (red amount). You can see this button in 2 places:

* At the top of the Customer's form
* On the payment page

When you click ``[Pay Full Debt]`` button, the debt amount will be added to the payment list with negative sign. That negative amount has to be covered by normal payment (e.g. by cash). After that the Customer will have zero debt value.

Credit Products
---------------

Expand Down
Loading

0 comments on commit bd489b3

Please sign in to comment.