'How can I call a Powershell / Command Line Script using a BrowserAction in a FireFox WebExtension?

When the button is pressed, I want to get the URL from the current tab and pass it as an argument to the script.

I know that I have to use browser.browserAction.onClicked.addListener() but I have not found an API for the call to the command line.

Can anybody tell me if this is possible and if not if there is a workaround?

Edit: Thanks to @wOxxOm who pointed me to Native messaging in the comment I was able to proceed as follows:

I used the example here to create my extension and app manifest.

Extension manifest:

manifest.json

{
"manifest_version": 2,
"name": "test",
"version": "1.0",

"description": "Description",
"icons": {
  "48": "icons/test_logo-48.png"
},

"browser_action": {
  "default_icon": "icons/test_logo-48.png",
  "default_title": "test"
},

"browser_specific_settings": {
  "gecko": {
    "id": "[email protected]",
    "strict_min_version": "50.0"
  }
},

"background": {
  "scripts": ["background.js"]
},

"permissions": ["nativeMessaging"]
}

  

App manifest:

native_manifest.json:

{
    "name": "test",
    "description": "Example host for native messaging",
    "path": "C:\\Users\\test\\Documents\\PowerShell\\Scripts\\extension.bat",
    "type": "stdio",
    "allowed_extensions": [ "[email protected]" ]
  }

Note that the path in the native_manifest.json is the path to a Windows .bat file which runs the Powershell script

I created two registry entries:

New-Item -Path HKCU:\SOFTWARE\Mozilla\NativeMessagingHosts\test -Value "C:\\Users\\test\\Documents\\PowerShell\\firefox_extension\\test\\native_manifest.json"

New-Item -Path HKLM:\SOFTWARE\Mozilla\NativeMessagingHosts\test -Value "C:\\Users\\test\\Documents\\PowerShell\\firefox_extension\\test\\native_manifest.json"

These entries point to the location of the App manifest. This is the root folder of the extension where the manifest.json and the background.js is also saved.

The background.js extension script:

/*
On startup, connect to the nhative app.
*/
let port = browser.runtime.connectNative("test");

On a click on the browser action, send the app a message.
*/
browser.browserAction.onClicked.addListener(() => {
  console.log("Sending:  ping");
  port.postMessage("example.txt");
});

The .bat file launching the script:

extension.bat


@echo off
PowerShell -NoProfile -ExecutionPolicy Bypass -Command "& '.\fire.ps1'"

Powershell test script:

param ($test="C:\Users\test\Documents\PowerShell\firefox_extension\test\default.txt")
get-date | out-file $test

The script works, the test file is created, but with the default parameter path. So far so good, but I cannot figure out how to read the passed message in Powershell from Stdin.

I found an answer here explaining to use the -command - parameter, however I'm already using it to call my script. Another possibility seems to be to use [Console]::In but I'm not sure how.

Can anybody help and provide an example how I can read the passed message from the extension in the powershell script? According to documentation it is passed to stdin.



Sources

This article follows the attribution requirements of Stack Overflow and is licensed under CC BY-SA 3.0.

Source: Stack Overflow

Solution Source