mirror of
https://github.com/bringout/oca-ocb-hw.git
synced 2026-04-22 07:02:01 +02:00
Initial commit: Hw packages
This commit is contained in:
commit
a9d00500da
161 changed files with 10506 additions and 0 deletions
|
|
@ -0,0 +1,96 @@
|
|||
# -*- coding: utf-8 -*-
|
||||
# Part of Odoo. See LICENSE file for full copyright and licensing details.
|
||||
|
||||
from re import sub, finditer
|
||||
import subprocess
|
||||
import RPi.GPIO as GPIO
|
||||
import logging
|
||||
|
||||
from odoo.addons.hw_drivers.interface import Interface
|
||||
|
||||
|
||||
_logger = logging.getLogger(__name__)
|
||||
|
||||
try:
|
||||
from vcgencmd import Vcgencmd
|
||||
except ImportError:
|
||||
Vcgencmd = None
|
||||
_logger.warning('Could not import library vcgencmd')
|
||||
|
||||
|
||||
class DisplayInterface(Interface):
|
||||
_loop_delay = 0
|
||||
connection_type = 'display'
|
||||
|
||||
def get_devices(self):
|
||||
|
||||
# If no display connected, create "fake" device to be accessed from another computer
|
||||
display_devices = {
|
||||
'distant_display' : {
|
||||
'name': "Distant Display",
|
||||
},
|
||||
}
|
||||
|
||||
if Vcgencmd:
|
||||
return self.get_devices_vcgencmd() or display_devices
|
||||
else:
|
||||
return self.get_devices_tvservice() or display_devices
|
||||
|
||||
|
||||
def get_devices_tvservice(self):
|
||||
display_devices = {}
|
||||
displays = subprocess.check_output(['tvservice', '-l']).decode()
|
||||
x_screen = 0
|
||||
for match in finditer(r'Display Number (\d), type HDMI (\d)', displays):
|
||||
display_id, hdmi_id = match.groups()
|
||||
tvservice_output = subprocess.check_output(['tvservice', '-nv', display_id]).decode().strip()
|
||||
if tvservice_output:
|
||||
display_name = tvservice_output.split('=')[1]
|
||||
display_identifier = sub('[^a-zA-Z0-9 ]+', '', display_name).replace(' ', '_') + "_" + str(hdmi_id)
|
||||
iot_device = {
|
||||
'identifier': display_identifier,
|
||||
'name': display_name,
|
||||
'x_screen': str(x_screen),
|
||||
}
|
||||
display_devices[display_identifier] = iot_device
|
||||
x_screen += 1
|
||||
|
||||
return display_devices
|
||||
|
||||
def get_devices_vcgencmd(self):
|
||||
"""
|
||||
With the new IoT build 23_11 which uses Raspi OS Bookworm,
|
||||
tvservice is no longer usable.
|
||||
vcgencmd returns the display power state as on or off of the display whose ID is passed as the parameter.
|
||||
The display ID for the preceding three methods are determined by the following table.
|
||||
|
||||
Display ID
|
||||
Main LCD 0
|
||||
Secondary LCD 1
|
||||
HDMI 0 2
|
||||
Composite 3
|
||||
HDMI 1 7
|
||||
"""
|
||||
display_devices = {}
|
||||
x_screen = 0
|
||||
hdmi_port = {'hdmi_0' : 2} # HDMI 0
|
||||
rpi_type = GPIO.RPI_INFO.get('TYPE')
|
||||
# Check if it is a RPI 3B+ beacause he response on for booth hdmi port
|
||||
if 'Pi 4' in rpi_type:
|
||||
hdmi_port.update({'hdmi_1': 7}) # HDMI 1
|
||||
|
||||
try:
|
||||
for hdmi in hdmi_port:
|
||||
power_state_hdmi = Vcgencmd().display_power_state(hdmi_port.get(hdmi))
|
||||
if power_state_hdmi == 'on':
|
||||
iot_device = {
|
||||
'identifier': hdmi,
|
||||
'name': 'Display hdmi ' + str(x_screen),
|
||||
'x_screen': str(x_screen),
|
||||
}
|
||||
display_devices[hdmi] = iot_device
|
||||
x_screen += 1
|
||||
except subprocess.CalledProcessError:
|
||||
_logger.warning('Vcgencmd "display_power_state" method call failed')
|
||||
|
||||
return display_devices
|
||||
|
|
@ -0,0 +1,69 @@
|
|||
# -*- coding: utf-8 -*-
|
||||
# Part of Odoo. See LICENSE file for full copyright and licensing details.
|
||||
|
||||
from cups import Connection as cups_connection
|
||||
from re import sub
|
||||
from threading import Lock
|
||||
|
||||
from odoo.addons.hw_drivers.interface import Interface
|
||||
|
||||
conn = cups_connection()
|
||||
PPDs = conn.getPPDs()
|
||||
cups_lock = Lock() # We can only make one call to Cups at a time
|
||||
|
||||
class PrinterInterface(Interface):
|
||||
_loop_delay = 120
|
||||
connection_type = 'printer'
|
||||
printer_devices = {}
|
||||
|
||||
def get_devices(self):
|
||||
discovered_devices = {}
|
||||
with cups_lock:
|
||||
printers = conn.getPrinters()
|
||||
devices = conn.getDevices()
|
||||
for printer_name, printer in printers.items():
|
||||
path = printer.get('device-uri', False)
|
||||
if printer_name != self.get_identifier(path):
|
||||
printer.update({'supported': True}) # these printers are automatically supported
|
||||
device_class = 'network'
|
||||
if 'usb' in printer.get('device-uri'):
|
||||
device_class = 'direct'
|
||||
printer.update({'device-class': device_class})
|
||||
printer.update({'device-make-and-model': printer_name}) # give name setted in Cups
|
||||
printer.update({'device-id': ''})
|
||||
devices.update({printer_name: printer})
|
||||
for path, device in devices.items():
|
||||
identifier = self.get_identifier(path)
|
||||
device.update({'identifier': identifier})
|
||||
device.update({'url': path})
|
||||
device.update({'disconnect_counter': 0})
|
||||
discovered_devices.update({identifier: device})
|
||||
self.printer_devices.update(discovered_devices)
|
||||
# Deal with devices which are on the list but were not found during this call of "get_devices"
|
||||
# If they aren't detected 3 times consecutively, remove them from the list of available devices
|
||||
for device in list(self.printer_devices):
|
||||
if not discovered_devices.get(device):
|
||||
disconnect_counter = self.printer_devices.get(device).get('disconnect_counter')
|
||||
if disconnect_counter >= 2:
|
||||
self.printer_devices.pop(device, None)
|
||||
else:
|
||||
self.printer_devices[device].update({'disconnect_counter': disconnect_counter + 1})
|
||||
return dict(self.printer_devices)
|
||||
|
||||
def get_identifier(self, path):
|
||||
"""
|
||||
Necessary because the path is not always a valid Cups identifier,
|
||||
as it may contain characters typically found in URLs or paths.
|
||||
|
||||
- Removes characters: ':', '/', '.', '\', and space.
|
||||
- Removes the exact strings: "uuid=" and "serial=".
|
||||
|
||||
Example 1:
|
||||
Input: "ipp://printers/printer1:1234/abcd"
|
||||
Output: "ippprintersprinter11234abcd"
|
||||
|
||||
Example 2:
|
||||
Input: "uuid=1234-5678-90ab-cdef"
|
||||
Output: "1234-5678-90ab-cdef
|
||||
"""
|
||||
return sub(r'[:\/\.\\ ]|(uuid=)|(serial=)', '', path)
|
||||
|
|
@ -0,0 +1,24 @@
|
|||
# -*- coding: utf-8 -*-
|
||||
# Part of Odoo. See LICENSE file for full copyright and licensing details.
|
||||
|
||||
import win32print
|
||||
|
||||
from odoo.addons.hw_drivers.interface import Interface
|
||||
|
||||
class PrinterInterface(Interface):
|
||||
_loop_delay = 30
|
||||
connection_type = 'printer'
|
||||
|
||||
def get_devices(self):
|
||||
printer_devices = {}
|
||||
printers = win32print.EnumPrinters(win32print.PRINTER_ENUM_LOCAL)
|
||||
|
||||
for printer in printers:
|
||||
identifier = printer[2]
|
||||
handle_printer = win32print.OpenPrinter(identifier)
|
||||
win32print.GetPrinter(handle_printer, 2)
|
||||
printer_devices[identifier] = {
|
||||
'identifier': identifier,
|
||||
'printer_handle': handle_printer,
|
||||
}
|
||||
return printer_devices
|
||||
|
|
@ -0,0 +1,18 @@
|
|||
# -*- coding: utf-8 -*-
|
||||
# Part of Odoo. See LICENSE file for full copyright and licensing details.
|
||||
|
||||
import serial.tools.list_ports
|
||||
|
||||
from odoo.addons.hw_drivers.interface import Interface
|
||||
|
||||
|
||||
class SerialInterface(Interface):
|
||||
connection_type = 'serial'
|
||||
|
||||
def get_devices(self):
|
||||
serial_devices = {}
|
||||
for port in serial.tools.list_ports.comports():
|
||||
serial_devices[port.device] = {
|
||||
'identifier': port.device
|
||||
}
|
||||
return serial_devices
|
||||
|
|
@ -0,0 +1,29 @@
|
|||
# -*- coding: utf-8 -*-
|
||||
# Part of Odoo. See LICENSE file for full copyright and licensing details.
|
||||
|
||||
from usb import core
|
||||
|
||||
from odoo.addons.hw_drivers.interface import Interface
|
||||
|
||||
|
||||
class USBInterface(Interface):
|
||||
connection_type = 'usb'
|
||||
|
||||
def get_devices(self):
|
||||
"""
|
||||
USB devices are identified by a combination of their `idVendor` and
|
||||
`idProduct`. We can't be sure this combination in unique per equipment.
|
||||
To still allow connecting multiple similar equipments, we complete the
|
||||
identifier by a counter. The drawbacks are we can't be sure the equipments
|
||||
will get the same identifiers after a reboot or a disconnect/reconnect.
|
||||
"""
|
||||
usb_devices = {}
|
||||
devs = core.find(find_all=True)
|
||||
cpt = 2
|
||||
for dev in devs:
|
||||
identifier = "usb_%04x:%04x" % (dev.idVendor, dev.idProduct)
|
||||
if identifier in usb_devices:
|
||||
identifier += '_%s' % cpt
|
||||
cpt += 1
|
||||
usb_devices[identifier] = dev
|
||||
return usb_devices
|
||||
Loading…
Add table
Add a link
Reference in a new issue