Desktop Operations in ElectronJS

ElectronJS is an Open Source Framework used for building Cross-Platform native desktop applications using web technologies such as HTML, CSS, and JavaScript which are capable of running on Windows, macOS, and Linux operating systems. It combines the Chromium engine and NodeJS into a Single Runtime.

The electron can interact with the native OS environment such as File System, System Tray, etc. Electron provides us with the built-in Shell Module which helps in managing files and URLs in the native OS environment using their default application. This module provides functions related to Desktop Integrations such as Opening External Links, Creating Shortcuts, Reading Shortcuts, etc. The Shell Module can be used directly in the Main Process and the Renderer Process of the application. This tutorial will demonstrate Desktop Integrations using the Shell Module in Electron.

We assume that you are familiar with the prerequisites as covered in the above-mentioned link. For Electron to work, node and npm need to be pre-installed in the system.

  • Project Structure:
    Project Structure
  • sample.txt:
    This is a Sample Text file
  • delete.txt:
    Sample Text FIle to delete
Example: We will start by building the basic Electron Application by following the given steps.

  • Step 1: Navigate to an Empty Directory to setup the project, and run the following command,
    npm init

    To generate the package.json file. Install Electron using npm if it is not installed.



    npm install electron --save-dev

    This command will also create the package-lock.json file and install the required node_modules dependencies. Once Electron has been successfully installed, Open the package.json file and perform the necessary changes under the "scripts" key.

    package.json:

    {
      "name": "electron-DesktopOperation",
      "version": "1.0.0",
      "description": "Desktop Operations in Electron",
      "main": "main.js",
      "scripts": {
        "start": "electron"
      },
      "keywords": [
        "electron"
      ],
      "author": "Radhesh Khanna",
      "license": "ISC",
      "dependencies": {
        "electron": "^8.2.5"
      }
    }
    
  • Step 2: Create a main.js file according to the project structure. This file is the Main Process and acts as an entry point into the application. Copy the Boilerplate code for the main.js file as given in the following link. We will modify the code to suit our project needs.

    main.js:

    filter_none

    edit
    close

    play_arrow

    link
    brightness_4
    code

    const { app, BrowserWindow } = require('electron')
      
    function createWindow() {
      // Create the browser window.
      const win = new BrowserWindow({
        width: 800,
        height: 600,
        webPreferences: {
          nodeIntegration: true
        }
      })
      
      // Load the index.html of the app.
      win.loadFile('src/index.html')
      
      // Open the DevTools.
      win.webContents.openDevTools()
    }
      
    // This method will be called when Electron has finished
    // initialization and is ready to create browser windows.
    // Some APIs can only be used after this event occurs.
    app.whenReady().then(createWindow)
      
    // Quit when all windows are closed.
    app.on('window-all-closed', () => {
      // On macOS it is common for applications and their menu bar
      // To stay active until the user quits explicitly with Cmd + Q
      if (process.platform !== 'darwin') {
        app.quit()
      }
    })
      
    app.on('activate', () => {
      // On macOS it's common to re-create a window in the app when the
      // dock icon is clicked and there are no other windows open.
      if (BrowserWindow.getAllWindows().length === 0) {
        createWindow()
      }
    })
      
    // In this file, you can include the rest of your app's specific
    // main process code. You can also put them in separate files and
    // require them here.

    chevron_right

    
    

  • Step 3: Create the index.html file within the src directory. We will also copy the boilerplate code for the index.html file from the above-mentioned link. We will modify the code to suit our project needs.

    index.html:

    filter_none

    edit
    close

    play_arrow

    link
    brightness_4
    code

    <!DOCTYPE html>
    <html>
      
    <head>
        <meta charset="UTF-8">
        <title>Hello World!</title>
        
        <meta http-equiv="Content-Security-Policy"
              content="script-src 'self' 'unsafe-inline';" />
    </head>
      
    <body>
        <h1>Hello World!</h1> We are using node
        <script>
            document.write(process.versions.node)
        </script>, Chrome
        <script>
            document.write(process.versions.chrome)
        </script>, and Electron
        <script>
            document.write(process.versions.electron)
        </script>.
      
        <!-- Adding Individual Renderer Process JS File -->
        <script src="index.js"></script>
    </body>
      
    </html>

    chevron_right

    
    

  • Output: At this point, our basic Electron Application is set up. To launch the Electron Application, run the Command:
    npm start

Shell Module in Electron: All the Shell modules are explained with the example below:

  1. shell.openExternal(url, options): To open External URLs in the systems default manner. We can pass external links or mail ID's and it will be resolved based on the protocol provided.

    The shell.OpenExternal(url, options) returns a Promise. It takes in the following parameters,

    • url: String The external URL to be resolved. Maximum of 2081 Characters are allowed in Windows. URL will be resolved based on systems default behaviour.
    • options: Object (Optional) It is an Object consisting of the following parameters,
      • activate: Boolean It is supported by macOS only. It is used to bring the opened application to the foreground. Default is set as true.

    index.html: Add the following snippet in that file.

    filter_none

    edit
    close

    play_arrow

    link
    brightness_4
    code

    <br>
      <h3>
       Desktop Integrations in Electron using Shell Module
      </h3>
      <button id="external">
       Open GeeksForGeeks.org in Default Browser
      </button>
      
      <br><br>
      <button id="mail">
       Open GeeksForGeeks in Default Mail
      </button>

    chevron_right

    
    

    index.js: Add the following snippet in that file.



    filter_none

    edit
    close

    play_arrow

    link
    brightness_4
    code

    const electron = require('electron');
    const path = require('path');
      
    // Importing the Shell Module from the electron 
    // in the Renderer Process
    const shell = electron.shell;
      
    var external = document.getElementById('external');
    var externalOptions = {
      
        // Supported by macOS only
        activate: true,
    }
      
    external.addEventListener('click', (event) => {
          
        // Returns a Promise<void>, Hence we can use 
        // the .then( function() {} )
        shell.openExternal(
            'https://www.geeksforgeeks.org/', externalOptions)
            .then(() => {
                console.log('Link Opened Successfully');
            });
    });
      
    var mail = document.getElementById('mail');
      
    mail.addEventListener('click', (event) => {
      
        // Resolving the External URL to the Default Mail Agent
        // Because we have specified 'mailto'
        shell.openExternal(
            'mailto: https://www.geeksforgeeks.org/', externalOptions)
            .then(() => {
            console.log('Link Opened Successfully');
        });
    });

    chevron_right

    
    

    Output:

  2. shell.showItemInFolder(path): To resolve the given String file path and show the file in the Windows/File explorer. If possible, select the file as well. This method does not have any return type.

    index.html: Add the following snippet in that file.

    filter_none

    edit
    close

    play_arrow

    link
    brightness_4
    code

    <br><be>
      <button id="show">
        Show sample.txt in File Explorer
      </button>

    chevron_right

    
    

    index.js: Add the following snippet in that file.

    filter_none

    edit
    close

    play_arrow

    link
    brightness_4
    code

    var show = document.getElementById('show');
      
    show.addEventListener('click', (event) => {
        // Providing a dynamic file path to the 'sample.txt' 
        // file in the 'assets' Folder. Using the path Module. 
        // '__dirname' automatically detects current working directory
        shell.showItemInFolder(path.join(__dirname, '../assets/sample.txt'));
    });

    chevron_right

    
    

    Output:

  3. shell.openItem(path): To resolve the given String file path and open the file in the systems default manner. It returns a Boolean value stating whether the file was successfully opened or not.

    index.html: Add the following snippet in that file.

    filter_none

    edit
    close

    play_arrow

    link
    brightness_4
    code

    <br><br>
      <button id="open">Open sample.txt</button>

    chevron_right

    
    

    index.js: Add the following snippet in that file.

    filter_none

    edit
    close

    play_arrow

    link
    brightness_4
    code

    var open = document.getElementById('open');
      
    open.addEventListener('click', (event) => {
        var success = shell.openItem(path.join(__dirname, 
             '../assets/sample.txt'));
      
        console.log('File Opened Successfully - ', success);
    });

    chevron_right

    
    

    Output:

  4. shell.beep(): To play the Native OS Sound. This method does not have any return type. In this tutorial, it is used in combination with shell.moveItemToTrash() method.
  5. shell.moveItemToTrash(path, deleteFailure): To resolve the given String file path and move the specified file to the Trash/Bin. Returns a Boolean value stating whether the file was successfully moved to the trash or not.

    The shell.moveItemToTrash(path, delete) returns a Boolean value. It takes in the following parameters,

    • path: String The filepath to be resolved.
    • deleteFailure: Boolean (Optional) It is supported by macOS only. It signifies whether or not to remove the file entirely from the System in case the Trash is disbaled or unsupported in the system.

    index.html: Add the following snippet in that file.

    filter_none

    edit
    close

    play_arrow

    link
    brightness_4
    code

    <br><br>
      <button id="delete">Delete delete.txt</button>

    chevron_right

    
    

    index.js: Add the following snippet in that file.

    filter_none

    edit
    close

    play_arrow

    link
    brightness_4
    code

    var deleteItem = document.getElementById('delete');
      
    deleteItem.addEventListener('click', (event) => {
        // Play the Native OS Beep Sound
        shell.beep();
          
        // Returns a Boolean Value
        var success = shell.moveItemToTrash(path.join(__dirname, 
                 '../assets/delete.txt'), true);
      
        console.log('File Deleted Successfully - ', success);
    });

    chevron_right

    
    

    Output:

  6. shell.writeShortcutLink(path, operation, options): This operation is supported in Windows only. To resolve the given String path and create/update the Shortcut Link at that path. It returns a Boolean value stating whether specified operation was successfully performed or not.

    The shell.writeShortcutLink(path, operations, options) returns a Boolean value. It takes in the following parameters,

    • path: String Defining the path for the shortcut for the Operation to be carried out.
    • operations: String (Optional) Specifies the Operation to be carried out. Default Value of the Operation is create. It can have any of the following values,
      • create: Creates a new Shortcut. Performs Overwrite if necessary.
      • update: Updates the specified properties of an existing Shortcut.
      • replace: Overwrites an existing Shortcut. This operation fails if the Shortcut does not exist.
    • Options: It is a shortcutDetails Object consisting of the following parameters,
      • target: String The target File which is supposed to be launched from this shortcut.
      • cwd: String (Optional) Specifies the Current Working Directory. Default value is empty.
      • args: String (Optional) The arguments to be passed and applied to the target file when launched from the shortcut. Default value is empty.
      • description: String (Optional) The Description of the Shortcut. Default value is empty. Value is shown as Tooltip on hovering over the created shortcut.
      • icon: String (Optional) The path to the icon to be used. It can be a .dll or an .exe file. icon property and iconIndex property have to be specified together. Default value of the icon Property is empty which in-turn uses the default target icon or the icon which is supposed to be used as defined in the System. In this tutorial, we have created a shortcut for a .txt file. It has a pre-defined icon as per the System, but we have changed it to the icon of the notepad file by specifying the path of notepad.exe in the System.
      • iconIndex: Number (Optional) The resource ID of icon when the icon property is a .dll or an .exe file. Default value of the iconIndex property is 0. In this tutorial, we will keep the iconIndex property to 0 for the notepad.exe file icon to take effect.
      • appUserModelId: String (Optional) The Application User Model ID. Default value is empty.

    index.html: Add the following snippet in that file.

    filter_none

    edit
    close

    play_arrow

    link
    brightness_4
    code

    <br><br>
      <button id="create">
       Create sample.txt Shortcut
      </button>
    <br><br>

    chevron_right

    
    

    index.js: Add the following snippet in that file.

    filter_none

    edit
    close

    play_arrow

    link
    brightness_4
    code

    var create = document.getElementById('create');
      
    var shortcutDetails = {
        // Defining the target File as the 'sample.txt' File 
        target: path.join(__dirname, '../assets/sample.txt'),
      
        // Current Working Directory is 'assets' folder
        cwd: path.join(__dirname, '../assets/'),
        args: "Passing Arguments",
        // Shown as Tooltip 
        description: "Shortcut for sample.txt file",
          
        // Defining the icon for shortcut as the 
        // 'notepad.exe' file 
        // Instead of the System Default icon
      
        // Keeping the default value of iconIndex for the 
        // 'notepad.exe' file icon to take effect  
        iconIndex: 0,
        appUserModelId: "",
    }
    create.addEventListener('click', (event) => {
      
        // Desktop - C:\\Users\\radhesh.khanna\\Desktop\\sample-shortcut.lnk
        // Specifying the name of the Shortcut while creation
        var success = shell.writeShortcutLink(path.join(__dirname, 
         '../assets/sample-shortcut.lnk'), 'create', shortcutDetails);
      
        console.log('Shortcut Created Successfully - ', success);
    });

    chevron_right

    
    

    Output:

  7. shell.readShortcutLink(path): This operation is supported in Windows only. To resolve the given String path and read the shortcut specified at the path. This method returns the shortcutDetails Object. This object is explained above when creating a shortcut. An exception will be thrown if an error occurs. In this tutorial, we will read and display the shortcutDetails object for the same shortcut (sample-shortcut.lnk) that we have created above for the sample.txt file.

    index.html: Add the following snippet in that file.

    filter_none

    edit
    close

    play_arrow

    link
    brightness_4
    code

    <div>
     <textarea name="Shortcut Details"
               id="textarea" cols="30" 
               rows="10">
     </textarea>
    </div>
      
    <button id="read">
       Read sample.txt Shortcut Details
    </button>

    chevron_right

    
    

    index.js: Add the following snippet in that file.

    filter_none

    edit
    close

    play_arrow

    link
    brightness_4
    code

    var read = document.getElementById('read');
      
    // Defining a textarea to display the 'shortcutDetails' Object 
    var textArea = document.getElementById('textarea');
      
    read.addEventListener(('click'), (event) => {
        var object = shell.readShortcutLink(path.join(__dirname,
                 '../assets/sample-shortcut.lnk'));
      
        // Object Returned is in JSON format, using 'JSON.stringify()' 
        // method to convert to String
        console.log(object);
        textArea.innerHTML = JSON.stringify(object);
    });

    chevron_right

    
    

    Output:

full-stack-img




My Personal Notes arrow_drop_up

Check out this Author's contributed articles.

If you like GeeksforGeeks and would like to contribute, you can also write an article using contribute.geeksforgeeks.org or mail your article to contribute@geeksforgeeks.org. See your article appearing on the GeeksforGeeks main page and help other Geeks.

Please Improve this article if you find anything incorrect by clicking on the "Improve Article" button below.


Article Tags :

Be the First to upvote.


Please write to us at contribute@geeksforgeeks.org to report any issue with the above content.