{"id":4563,"library":"hidapi","title":"hidapi Python Wrapper","description":"hidapi is a Python library providing a Cython interface to the native HIDAPI library, enabling cross-platform communication with USB Human Interface Devices (HID). It works on Linux, Windows, and macOS. The current version is 0.15.0, with regular updates typically following the underlying HIDAPI C library.","status":"active","version":"0.15.0","language":"en","source_language":"en","source_url":"https://github.com/trezor/cython-hidapi","tags":["HID","USB","hardware","interface","cython","device communication"],"install":[{"cmd":"pip install hidapi","lang":"bash","label":"Basic installation"},{"cmd":"sudo apt-get install python3-dev libusb-1.0-0-dev libudev-dev && pip install hidapi","lang":"bash","label":"Linux (Debian/Ubuntu) with system dependencies"},{"cmd":"brew install hidapi && pip install hidapi","lang":"bash","label":"macOS with Homebrew and system dependencies"}],"dependencies":[{"reason":"Required for building the Cython extensions if installing from source or if pre-built wheels are not available.","package":"Cython","optional":true},{"reason":"Native HIDAPI library backend (often provided by system packages like libusb-1.0-0-dev on Linux, or Homebrew hidapi on macOS). Essential for device communication.","package":"libusb","optional":false},{"reason":"System dependency on Linux for device discovery and access (e.g., libudev-dev on Debian/Ubuntu).","package":"libudev","optional":false},{"reason":"Alternative Linux backend to libusb. The cython-hidapi library defaults to hidraw where available.","package":"hidraw (Linux kernel module)","optional":false}],"imports":[{"note":"The PyPI package is 'hidapi', but the import module name is 'hid'.","wrong":"import hidapi","symbol":"hid","correct":"import hid"},{"note":"Instantiate the device object directly from the 'hid' module.","symbol":"device","correct":"h = hid.device()"}],"quickstart":{"code":"import hid\nimport os\nimport time\n\n# --- Enumerate devices (useful for finding VID/PID) ---\nprint('Enumerating HID devices:')\nfor device_dict in hid.enumerate():\n    print('---')\n    for key, value in device_dict.items():\n        print(f'{key}: {value}')\nprint('---\\n')\n\n# --- Connect, read, and write (example with placeholder VID/PID) ---\n# Replace with your device's Vendor ID and Product ID.\n# On Linux, you may need appropriate udev rules or root privileges.\n# On Windows, you might need hidapi.dll in your PATH.\nVENDOR_ID = int(os.environ.get('HIDAPI_VENDOR_ID', '0x0000'), 16) # Example: 0x534C for Trezor\nPRODUCT_ID = int(os.environ.get('HIDAPI_PRODUCT_ID', '0x0000'), 16) # Example: 0x0001 for Trezor One\n\nif VENDOR_ID == 0x0000 or PRODUCT_ID == 0x0000:\n    print('Warning: Please set HIDAPI_VENDOR_ID and HIDAPI_PRODUCT_ID environment variables for a real test.')\n    print('Falling back to placeholder values; device opening may fail.')\n\ntry:\n    print(f'Attempting to open device VID: {hex(VENDOR_ID)}, PID: {hex(PRODUCT_ID)}')\n    h = hid.device()\n    h.open(VENDOR_ID, PRODUCT_ID)\n\n    print(f'Manufacturer: {h.get_manufacturer_string()}')\n    print(f'Product: {h.get_product_string()}')\n    print(f'Serial No: {h.get_serial_number_string()}')\n\n    h.set_nonblocking(1) # Enable non-blocking mode\n\n    # Example: Write some data (replace with actual device commands)\n    print('Writing example data...')\n    # Ensure data length matches device report size, padded with zeros if needed.\n    # The first byte might be a Report ID, or 0 if not used by the device.\n    data_to_write = [0, 63, 35, 35] + [0] * 60 # Example 64-byte report\n    h.write(data_to_write)\n    time.sleep(0.05)\n\n    # Example: Read data\n    print('Reading data...')\n    read_data = []\n    while True:\n        d = h.read(64) # Read up to 64 bytes\n        if d:\n            read_data.extend(d)\n        else:\n            break\n    \n    if read_data:\n        print(f'Read data: {read_data}')\n    else:\n        print('No data read.')\n\n    print('Closing the device.')\n    h.close()\n\nexcept IOError as ex:\n    print(f'Error opening or communicating with device: {ex}')\n    print('Ensure the device is connected and permissions are correct.')\nexcept Exception as e:\n    print(f'An unexpected error occurred: {e}')","lang":"python","description":"This quickstart enumerates all connected HID devices, then attempts to connect to a specified device (using environment variables for Vendor ID and Product ID, or placeholders if not set). It demonstrates enabling non-blocking mode, writing data, and reading data from the device. Users should replace `VENDOR_ID` and `PRODUCT_ID` with their specific device's identifiers and adjust `data_to_write` and read sizes according to their device's HID report descriptor."},"warnings":[{"fix":"On Linux (Debian/Ubuntu), install `libusb-1.0-0-dev` and `libudev-dev` (or `libhidapi-hidraw0`/`libhidapi-libusb0`). On macOS, install `hidapi` via Homebrew (`brew install hidapi`). On Windows, ensure `hidapi.dll` is in a directory listed in your system's PATH, or beside your executable. The specific `hidapi.dll` might need to match your Python's architecture (32-bit vs 64-bit).","message":"The `hidapi` Python package requires the underlying native `hidapi` library to be installed on your system. `pip install hidapi` only installs the Python bindings, not the C library itself. Users often encounter `IOError` or `OSError` if the native library is missing or improperly configured.","severity":"gotcha","affected_versions":"All versions"},{"fix":"Run your Python script with `sudo` (not recommended for production). A better solution is to create a udev rule file (`.rules` in `/etc/udev/rules.d/`) to grant appropriate access to your user or a specific group for the target device's Vendor/Product ID. Remember to reload udev rules (`sudo udevadm control --reload-rules && sudo udevadm trigger`) and potentially replug the device.","message":"On Linux, accessing HID devices typically requires special permissions. Without them, `hid.open()` calls will fail with `IOError`.","severity":"gotcha","affected_versions":"All versions on Linux"},{"fix":"Consult your device's HID Report Descriptor to understand whether it uses numbered reports and what the expected report structure is. Adjust your `read()` and `write()` calls to account for the Report ID byte if present.","message":"When reading or writing HID reports, the first byte often represents the 'Report ID'. If your device uses numbered reports, this byte will be the Report ID. If not, it's typically `0x00`. Misinterpreting this can lead to incorrect data parsing or writing issues.","severity":"gotcha","affected_versions":"All versions"}],"env_vars":null,"last_verified":"2026-04-12T00:00:00.000Z","next_check":"2026-07-11T00:00:00.000Z"}