JavascriptExecutor in Selenium is an interface that executes Javascript code snippets within the context of browser. It is implemented through the RemoteWebDriver class. It is used to perform some advanced operations that are not yet supported by Selenium WebDriver. 

The syntax of JavascriptExecutor is as follows:
Syntax:
         public interface JavascriptExecutor

Selenium supports JavascriptExecutor without any separate script, an extra plugin or add-on. We just need to import a package (org.openqa.selenium.JavascriptExecutor) in the script to use JavaScriptExecutor.

Why do we need JavaScriptExecutor in Selenium?


Selenium JavascriptExecutor allows users easily to inject and execute Javascript code directly within the context of browser window. This feature is useful in case when the standard WebDriver's methods do not work to find an element on the browser web page.

For example, in general, we use click() method of Selenium WebDriver to click on a web element. 
        driver.findElement(By.id("submit")).click();

But, sometimes, click() method might not work on all browser and we may face issues with the above lines of code. To overcome such kind of issue, we use the JavaScriptExecutor interface. It could help you to click on an element in any browser by executing appropriate Javascript codes. It helps to execute Javascript commands synchronously or asynchronously on the page.

We can also use JavascriptExecutor to perform the desired operation on a web element if locators like XPath, CSS, etc. do not work.

Basic Syntax for JavascriptExecutor

The basic syntax for JavascriptExecutor is as follows:
Syntax:

    JavascriptExecutor js = (JavascriptExecutor) driver; // Line 1. // Casting. js.executeScript( Script, Arguments ); // Line 2.
Where, 
1. In line 1 of the preceding code, we have cast WebDriver object into the JavascriptExecutor interface so that we can easily execute the javascript code in Selenium WebDriver. 
2. In line 2, an executeScript() method provided by JavascriptExecutor interface is called by using reference variable js. Without casting, the executeScript() method of JavascriptExecutor will not be available to use.
3.   Script – It is the JavaScript that needs to execute.
     Arguments – It is the arguments to the script. It's optional.

Let's move ahead towards methods of JavascriptExecutor in selenium.

JavascriptExecutor Methods in Selenium


The most common methods of JavascriptExecutor used in selenium is as follows:

1. executeScript

The executeScript() method is used to execute JavaScript code in the context of the currently selected frame or window. The script provided in this method will be executed as the body of an anonymous function (anonymous function means a function without a name).
Method:
    executeScript( String script, Object... args) : Object
It takes two input parameters such as script and args. The parameter script is a Javascript code that has to be executed. Within the script, we will use document object that refers to the current document. The document object represents a web page that is displayed in the full browser window, frame, or layer. An object is created with each document that is loaded by the browser. 

If the Javascript code returns a value (i.e. if the script contains a return statement), then we need to use the return keyword. The returned value is as follows:
1. WebElement for HTML element.
2. Double for decimal.
3. Long for non-decimal number.
4. Boolean for boolean.
5. String for all other cases.
6. Null if there is no return value.

Based on the type of return value, we will need to cast the executeScript() method. For decimal values, Double will be used. For text value, String will be used. If Javascript code returns an HTML element, WebElement can be used and so on.
For example:
    JavascriptExecutor js = (JavascriptExecutor)driver; // Casting. String title = (String) js.executeScript("return document.title"); // Casting. System.out.println(title);
The second parameter is the args. args is the argument to the script. It may be empty. Arguments such as a number, a boolean, a String, WebElement, or a List of any combination of the above can also be passed to the Javascript code being executed by using the executedScript() method. If the arguments do not meet these criteria then an exception will be thrown.

When a function is called, a special "magic" variable named arguments will be added to the Javascript code in which function will be run. This magic variable refers to an object that resembles an array. It has a property 0 for the first argument, 1 for the second, and so on.
For example:
    WebElement element = driver.findElement(By.xpath("//a[text() = 'Gmail']")); JavascriptExecutor js = (JavascriptExecutor) driver; js.executeScript("arguments[0].click()", element);
In the above example, arguments[0].click() has been used to click on element "Gmail".

Let's take different scenarios based on executeScript() method one by one.

How to get Title of Webpage using JavascriptExecutor in Selenium?


Scenario to Automate:
1. In this scenario, we will call Javascript code to return title of the Google home page. In this example, we will automate the following scenario. They are as follows:
a. Launch the Firefox browser.
b. Open the URL https://www.google.com of Google home page.
c. Get the title of the home page.
d. Close the browser. 

The example code for the above scenario is as follows:
Program source code 1:
    package seleniumProject; import java.util.concurrent.TimeUnit; import org.openqa.selenium.JavascriptExecutor; import org.openqa.selenium.WebDriver; import org.openqa.selenium.firefox.FirefoxDriver; public class GetTitle { public static void main(String[] args) { WebDriver driver = new FirefoxDriver(); // Maximize the window. driver.manage().window().maximize(); // Store the URL of home page in a variable URL of type String. String URL = "https://www.google.com"; // Call get() method and pass URL as a parameter. driver.get(URL); driver.manage().timeouts().implicitlyWait(10, TimeUnit.SECONDS); // Create the JavascriptExecutor interface object by Type casting of WebDriver instance. JavascriptExecutor js = (JavascriptExecutor)driver; // Call executeScript() method to get the title of web page. Object title = js.executeScript("return document.title"); // Here, the return type of executeScript() method is object. // Since the return type of executeScript() method is object, we need to perform type casting to get title in String text. String getTitle = (String)title; System.out.println("Title of Home page: " +getTitle); // The last three lines of code can also be written in one line like this: // String getTitle = (String)js.executeScript("return document.title"); driver.close(); } }
    Output: Title of Home page: Google
By casting WebDriver object to JavascriptExecutor interface, we can easily execute Javascript code in Selenium WebDriver. The JavascriptExecuter interface provides an executeScript() method where we passed the Javascript code and executed Javascript code to return the title of page.

How to Send Text and Click on Element using JavascriptExecutor in Selenium?


2. Let's take another scenario where we will send a text in the search box and click on the submit button by using JavascriptExecutor. We will use the same URL. Here, we will not use the sendKeys() method.
Program source code 2:
    package seleniumProject; import java.util.concurrent.TimeUnit; import org.openqa.selenium.By; import org.openqa.selenium.JavascriptExecutor; import org.openqa.selenium.WebDriver; import org.openqa.selenium.WebElement; import org.openqa.selenium.firefox.FirefoxDriver; public class ClickExample { public static void main(String[] args) { WebDriver driver = new FirefoxDriver(); driver.manage().window().maximize(); String URL = "https://www.google.com"; // Call get() method and pass URL as a parameter. driver.get(URL); driver.manage().timeouts().implicitlyWait(10, TimeUnit.SECONDS); // Locate the WebElement Searchbox and submit button of Google home page by By.xpath. WebElement search = driver.findElement(By.xpath("//input[@name = 'q']")); WebElement submit = driver.findElement(By.xpath("//input[@name = 'btnK']")); // Create the JavascriptExecutor interface object by Type casting of WebDriver instance. JavascriptExecutor js = (JavascriptExecutor)driver; // Send a text value "Selenium" using JavascriptExecutor. js.executeScript("arguments[0].value = 'Selenium'", search); // Line 1 // Click on submit button using JavascriptExecutor. js.executeScript("arguments[0].click()", submit); // Line 2 // We can write Line 1 and Line 2 code in a single line like this: // js.executeScript("arguments[0].value = 'Selenium', arguments[1].click()", search, submit); System.out.println("Test successful"); driver.close(); } }
    Output: Test successful
In this way, there are many important scenarios for an interview that could be asked such as handle checkbox, generate Alert Pop window in selenium, to refresh browser window using Javascript, to perform Scroll on application, and many more. We will learn all scenarios in further tutorial one by one.

2. executeAsyncScript

The executeAsyncScript() method is used to execute an asynchronous block of JavaScript code in the context of the currently selected frame or window in selenium. With the Asynchronous script, the web page renders more instantly.
Method:

    executeAsyncScript(String script, Object... args ) : Object

It takes two input parameters such as script and args. The parameter script is a Javascript code that has to be executed whereas, args is the arguments to the script. The return type of this method is object. 

How to perform sleep in the browser using JavascriptExecutor?


To perform a sleep in the browser under test, we will use the "Demo Selenium08" site to illustrate executeAsyncScript. In this example, we will automate the following scenario:

Scenario to Automate:
1. Launch the Firefox browser.
2. Open site "https://selenium08.blogspot.com/".
3. Application waits for 5 sec to perform further action.

Important steps to perform sleep operation in the browser:
1. Capture the start time before waiting for 5 seconds ( 5000 milliseconds) by using the System.currentTimeMillis() method of System class. This method returns current time in format of millisecond. Millisecond will be returned as a unit of time.
2. Now, use executeAsyncScript() method to wait 5 seconds.
3. Then, get the current time.
4. Subtract (current time – start time) to get passed time.
5. Verify that output (passed time) must be displayed more than 5000 milliseconds.

Let's see the following source code to automate the following scenario.
Program source code 3:
    package seleniumProject; import java.util.concurrent.TimeUnit; import org.openqa.selenium.JavascriptExecutor; import org.openqa.selenium.WebDriver; import org.openqa.selenium.firefox.FirefoxDriver; public class SleepTest { public static void main(String[] args) { WebDriver driver = new FirefoxDriver(); driver.manage().window().maximize(); driver.get("https://selenium08.blogspot.com/"); driver.manage().timeouts().setScriptTimeout(20, TimeUnit.SECONDS); JavascriptExecutor js = (JavascriptExecutor)driver; // Declare and set the start time long start_time = System.currentTimeMillis(); System.out.println("Start_time: " +start_time); // Call executeAsyncScript() method of JavascriptExecutor to wait for 5 seconds. js.executeAsyncScript("window.setTimeout(arguments[arguments.length - 1], 5000);"); long current_time = System.currentTimeMillis(); System.out.println("Current_time: " +current_time); // Get the difference (current time - startTime) of times. System.out.println("Passed time: " + (current_time - start_time)); } }
    Output: Start_time: 1575095232107 Current_time: 1575095237137 Passed time: 5030
Final words
Hope that this tutorial has covered almost all important points related to JavascriptExecutor in Selenium WebDriver with example. I hope that you will have understood coding related to scenarios. If you like this tutorial, please, share it on social networking sites for your friends.
Thanks for reading!