Chromedriver only supports characters in the BMP error while sending Emoji with ChromeDriver Chrome using Selenium Python to Tkinter's label() textbox

This error message...

selenium.common.exceptions.WebDriverException: Message: unknown error: ChromeDriver only supports characters in the BMP

...implies that the ChromeDriver was unable to send the emoji signal through send_keys() method.

ChromeDriver only supports characters in the BMP is a known issue with Chromium team as ChromeDriver still doesn't support characters with a Unicode after FFFF. Hence it is impossible to send any character beyond FFFF via ChromeDriver. As a result any attempt to send SMP characters (e.g. CJK, Emojis, Symbols, etc) raises the error.


Alternative

A potential alternative would be to use GeckoDriver / Firefox.

  • Code Block:

      from selenium import webdriver
      from selenium.webdriver.support.ui import WebDriverWait
      from selenium.webdriver.common.by import By
      from selenium.webdriver.support import expected_conditions as EC
    
      driver = webdriver.Firefox(executable_path=r'C:\Utility\BrowserDrivers\geckodriver.exe')
      driver.get('https://www.google.com/')
      # Chineese Character
      WebDriverWait(driver, 20).until(EC.element_to_be_clickable((By.NAME, "q"))).send_keys("")
      # Emoji Character
      WebDriverWait(driver, 20).until(EC.element_to_be_clickable((By.NAME, "q"))).send_keys("")
    
  • Browser Snapshot:

Emoji

You can find a relevant discussion in OpenQA.Selenium.WebDriverException: 'unknown error: ChromeDriver only supports characters in the BMP while sending an emoji through C# Selenium


Outro

A few links:

  • Full Emoji List
  • Unicode character inspector

It works for me:

from selenium import webdriver

JS_ADD_TEXT_TO_INPUT = """
  var elm = arguments[0], txt = arguments[1];
  elm.value += txt;
  elm.dispatchEvent(new Event('change'));
  """

browser = webdriver.Chrome('C:\\Python37\\chromedriver.exe')
browser.get("https://google.com/")
elem = browser.find_element_by_name('q')

text = "  " + u'\u2764'

browser.execute_script(JS_ADD_TEXT_TO_INPUT, elem, text)

enter image description here


For those who wants to send emojis on Chrome

Solution

    async sendKeysWithEmojis(element, text) {
        const script = `var elm = arguments[0],
        txt = arguments[1];elm.value += txt;
        elm.dispatchEvent(new Event('keydown', {bubbles: true}));
        elm.dispatchEvent(new Event('keypress', {bubbles: true}));
        elm.dispatchEvent(new Event('input', {bubbles: true}));
        elm.dispatchEvent(new Event('keyup', {bubbles: true}));`;
        await this.driver.executeScript(script, element, text);
    }

Call it like so

const element = await this.driver.findElement(selector);
await sendKeysWithEmojis(element, ' This one shall pass ');

What is happening here? We are emulating native key presses using events

Notice that the {bubbles: true} is optional (Was needed in my case due to a complex wrapped input)