from cups import Connection as cups_connection
from re import sub
from threading import Lock

from odoo.addons.hw_drivers.controllers.driver 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'

    def get_devices(self):
        printer_devices = {}
        with cups_lock:
            printers = conn.getPrinters()
            for printer in printers:
                printers[printer]['supported'] = True # these printers are automatically supported
                printers[printer]['device-make-and-model'] = printers[printer]['printer-make-and-model']
                if 'usb' in printers[printer]['device-uri']:
                    printers[printer]['device-class'] = 'direct'
                else:
                    printers[printer]['device-class'] = 'network'
            devices = conn.getDevices()
            if printers:
                devices.update(printers)
        for path in devices:
            if 'uuid=' in path:
                identifier = sub('[^a-zA-Z0-9_]', '', path.split('uuid=')[1])
            elif 'serial=' in path:
                identifier = sub('[^a-zA-Z0-9_]', '', path.split('serial=')[1])
            else:
                identifier = sub('[^a-zA-Z0-9_]', '', path)
            devices[path]['identifier'] = identifier
            devices[path]['url'] = path
            printer_devices[identifier] = devices[path]
        return printer_devices

from cups import Connection as cups_connection
from re import sub
from threading import Lock

from odoo.addons.hw_drivers.controllers.driver 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'

    def get_devices(self):
        printer_devices = {}
        with cups_lock:
            printers = conn.getPrinters()
            devices = conn.getDevices()
            for printer in printers:
                path = printers.get(printer).get('device-uri', False)
                if path and path in devices:
                    devices.get(path).update({'supported': True}) # these printers are automatically supported
        for path in devices:
            if 'uuid=' in path:
                identifier = sub('[^a-zA-Z0-9_]', '', path.split('uuid=')[1])
            elif 'serial=' in path:
                identifier = sub('[^a-zA-Z0-9_]', '', path.split('serial=')[1])
            else:
                identifier = sub('[^a-zA-Z0-9_]', '', path)
            devices[path]['identifier'] = identifier
            devices[path]['url'] = path
            printer_devices[identifier] = devices[path]
        return printer_devices

Fix issue with printer device-id
[FIX] hw_drivers: Fix issue with printer device-id

When we print a ticket status with a thermal printer we need printer's device-id
But if we add manually a printer this device-id doesn't exist
So now we update de devices list with a supported = True if
printer are manually added

closes odoo/odoo#53043

Signed-off-by: Quentin Lejeune (qle) <5d1c09880ce30fdcf63039932dac0c183ef0bdc7@odoo.com>

  from cups import Connection as cups_connection
  from re import sub
  from threading import Lock
  
  from odoo.addons.hw_drivers.controllers.driver 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'
  
      def get_devices(self):
          printer_devices = {}
          with cups_lock:
              printers = conn.getPrinters()
+             devices = conn.getDevices()
              for printer in printers:
+                 path = printers.get(printer).get('device-uri', False)
+                 if path and path in devices:
-                 printers[printer]['supported'] = True # these printers are automatically supported
+                     devices.get(path).update({'supported': True}) # these printers are automatically supported
-                 printers[printer]['device-make-and-model'] = printers[printer]['printer-make-and-model']
-                 if 'usb' in printers[printer]['device-uri']:
-                     printers[printer]['device-class'] = 'direct'
-                 else:
-                     printers[printer]['device-class'] = 'network'
-             devices = conn.getDevices()
-             if printers:
-                 devices.update(printers)
          for path in devices:
              if 'uuid=' in path:
                  identifier = sub('[^a-zA-Z0-9_]', '', path.split('uuid=')[1])
              elif 'serial=' in path:
                  identifier = sub('[^a-zA-Z0-9_]', '', path.split('serial=')[1])
              else:
                  identifier = sub('[^a-zA-Z0-9_]', '', path)
              devices[path]['identifier'] = identifier
              devices[path]['url'] = path
              printer_devices[identifier] = devices[path]
          return printer_devices
  
Fix issue with printer device-id
## Code Before:
from cups import Connection as cups_connection
from re import sub
from threading import Lock

from odoo.addons.hw_drivers.controllers.driver 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'

    def get_devices(self):
        printer_devices = {}
        with cups_lock:
            printers = conn.getPrinters()
            for printer in printers:
                printers[printer]['supported'] = True # these printers are automatically supported
                printers[printer]['device-make-and-model'] = printers[printer]['printer-make-and-model']
                if 'usb' in printers[printer]['device-uri']:
                    printers[printer]['device-class'] = 'direct'
                else:
                    printers[printer]['device-class'] = 'network'
            devices = conn.getDevices()
            if printers:
                devices.update(printers)
        for path in devices:
            if 'uuid=' in path:
                identifier = sub('[^a-zA-Z0-9_]', '', path.split('uuid=')[1])
            elif 'serial=' in path:
                identifier = sub('[^a-zA-Z0-9_]', '', path.split('serial=')[1])
            else:
                identifier = sub('[^a-zA-Z0-9_]', '', path)
            devices[path]['identifier'] = identifier
            devices[path]['url'] = path
            printer_devices[identifier] = devices[path]
        return printer_devices

## Instruction:
Fix issue with printer device-id
## Code After:
from cups import Connection as cups_connection
from re import sub
from threading import Lock

from odoo.addons.hw_drivers.controllers.driver 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'

    def get_devices(self):
        printer_devices = {}
        with cups_lock:
            printers = conn.getPrinters()
            devices = conn.getDevices()
            for printer in printers:
                path = printers.get(printer).get('device-uri', False)
                if path and path in devices:
                    devices.get(path).update({'supported': True}) # these printers are automatically supported
        for path in devices:
            if 'uuid=' in path:
                identifier = sub('[^a-zA-Z0-9_]', '', path.split('uuid=')[1])
            elif 'serial=' in path:
                identifier = sub('[^a-zA-Z0-9_]', '', path.split('serial=')[1])
            else:
                identifier = sub('[^a-zA-Z0-9_]', '', path)
            devices[path]['identifier'] = identifier
            devices[path]['url'] = path
            printer_devices[identifier] = devices[path]
        return printer_devices
