webExtensions add-on mimic

I want to add new request to localhost to get files and run a javascript file when buffer loaded
Could you help me add a source to buffer sources? And run (or place it in main html) when documment loaded? I'm begginer in Nyxt.

2023-11-15_13-06

Take a look at buffer-loaded-hook. It should lead you in the right direction.

Thanks @aadcg, I will try that. Currently, I make a interactive command edit the html. That seems work, I could run shadow-cljs repl on local page and eval code from emacs.

But now I 'm stuck when run on normal web site, when inject js script from localhost to web page. I have add meta tag:

    <meta http-equiv="Content-Security-Policy" content="default-src 'self' data: gap: https://ssl.gstatic.com ws://localhost:9630/ http://localhost:8080/ 'unsafe-eval' 'unsafe-inline'; style-src 'self' 'unsafe-inline' 'unsafe-eval' ; media-src *; img-src 'self' data: content:;">

to the head tag.
But console warning that:

The page at https://www.lingohut.com/ was not allowed to run insecure content from http://localhost:8080/js/compiled/app.js

Could you tell me what do I do now?

I think I will try edit the body of the request before It was rendered, in buffer-loaded-hook.

If I understand correctly, the function that is triggered on buffer-loaded-hook needs to be conditionally inject js depending on the buffer's URL. Notice that each buffer object has a url slot, so you can check it via (url buffer).

Hi, thank you for the hint @aadcg , I cannot inject js to normal website because of security in header and html meta tag.
I inject code (shadow-cljs app with repl) like:

(ffi-buffer-evaluate-javascript (current-buffer) " 
var app = document.createElement('div'); app.setAttribute('id', 'cljs-app'); 
document.body.appendChild(app);
var script = document.createElement('script'); 
script.src = 'http://localhost:8080/js/compiled/app.js';
document.body.appendChild(script);
 ")

But console print:

[Warning] [blocked] The page at https://www.lingohut.com was not allowed to run insecure content from http://localhost:8080/js/compiled/app.js.

Maybe it's because the cljs app script have unsafe eval features. I tried to edit the response header before It was loaded:

(defun request-log (request-data)
  (let* ((header (request-headers request-data)))
    (print "log: ______________________________________________________________________")
    (if header
        (let ((new-header (cons '("abc" . "def") header)))
          (dolist (pair header)
            (when (string-equal (car pair) "Sec-Fetch-Mode")
              (setf (cdr pair) "cors")))
          (nconc header (list '("Access-Control-Allow-Origin" . "*")))
          (nconc header (list '("Access-Control-Allow-Credentials" . "true")))
          (print header)
          ;; this seem not work
          ;; (setf (request-headers request-data) new-header)
          )
        (print "no header")))
  ;; (princ-to-string request-data)
  request-data)

(define-configuration (web-buffer)
  ((request-resource-hook
    (hooks:add-hook %slot-value% #'request-log))))

I try to add Access-Control-Allow-Origin : * and Access-Control-Allow-Credentials: true to the header, to able to run script from localhost. But nothing changes, the script excursion is still blocked.

I just want to run js from other host. But I think I'm doing it wrong. Could you please help me with that?

My understanding is that you're trying to do something that violates security. You can't inject JS in https that comes from your localhost. How would you do it in a regular browser?

See this node of the documentation Nyxt browser: Documentation and WebKit2.SecurityManager.

You 're right. I have injected script shadow-cljs like that successfully (without error and isn't blocked) when open websites with google-chrome-stable --allow-running-insecure-content.
I read the two link you give but have little understanding. Do you mean I have to do something with WebKit2.SecurityManager?

I think I will create internal scheme my-localhost-scheme and return js file from localhost, as in document said:

Internal schemes can return any type of content 
(both strings and arrays of bytes are recognized), 
and they are capable of being CORS-enabled, protected, 
and are in general capable of whatever the renderer-provided schemes do.

then I could run this:

(ffi-buffer-evaluate-javascript (current-buffer) " 
var app = document.createElement('div'); app.setAttribute('id', 'cljs-app'); 
document.body.appendChild(app);
var script = document.createElement('script'); 
script.src = 'my-localhost-scheme:8080/js/compiled/app.js';
document.body.appendChild(script);
 ")

You have understood my suggestion correctly. I think that you need to create a custom scheme (hence the link to Nyxt's documentation) and the security settings need to be properly set.

You can find examples in Nyxt's codebase by grepping define-internal-scheme.