gmail.js icon indicating copy to clipboard operation
gmail.js copied to clipboard

Error in the function: gmail.tools.add_compose_button

Open guzman-rc opened this issue 2 years ago • 8 comments

I get this console error when I call gmail.tools.add_compose_button

Uncaught TypeError: Illegal invocation
    at T.fn.init.<anonymous> (jquery.module.min.js:2:44823)
    at Y (jquery.module.min.js:2:6326)
    at T.fn.init.html (jquery.module.min.js:2:44634)
    at Gmail.api.tools.add_compose_button (gmail.js:3712:16)
    at extension.js:31:15
    at handler (gmail.js:2573:21)
    at Gmail.api.observe.trigger_dom (gmail.js:2451:13)
    at Gmail.api.tools.insertion_observer (gmail.js:2797:37)
    at MutationObserver.<anonymous> (gmail.js:2710:39)

This is my extension.js file

"use strict";

(() => {
  // src/extension.js
  var loaderId = setInterval(() => {
    if (!window._gmailjs) {
      return;
    }
    clearInterval(loaderId);
    startExtension(window._gmailjs);
  }, 100);
  
  function startExtension(gmail) {
    console.log("Extension loading...");
    window.gmail = gmail;
	
    gmail.observe.on("load", () => {
      const userEmail = gmail.get.user_email();
      console.log("Hello, " + userEmail + ". This is your extension talking!");
	  
      gmail.observe.on("view_email", (domEmail) => {
        console.log("Looking at email:", domEmail);
        const emailData = gmail.new.get.email_data(domEmail);
        console.log("Email data:", emailData);
      });
	  
      gmail.observe.on("compose", (compose) => {
        console.log("New compose window is opened!", compose);
	
	var compose_ref = gmail.dom.composes()[0];		
	gmail.tools.add_compose_button(compose_ref, 'content_html', function() {
		// Code here			
	}, 'Custom Style Classes');

      });
    });
  }
})();

guzman-rc avatar Mar 15 '24 20:03 guzman-rc

What you are passing in to "add_compose_button" is not trusted html. This is why it fails.

Convert your string to trusted html first and it should work.

josteink avatar Mar 15 '24 23:03 josteink

Sorry, I'm very lost... For this example, how could I convert my string to a trusted string?

guzman-rc avatar Mar 16 '24 00:03 guzman-rc

For now automagically handling this is not part of Gmail.js.

You're probably best off reading the full docs on Trusted Types to understand how all the pieces fits together.

https://developer.mozilla.org/en-US/docs/Web/API/Trusted_Types_API

josteink avatar Mar 16 '24 08:03 josteink

Shouldn't the htmlPrefilter function take care of this? I think this is the same issue I have in #784

kaeevans avatar Mar 17 '24 16:03 kaeevans

I fixed the error, just delete this line: e11 = T.htmlPrefilter(e11);

from the html function in the gmailJsLoader.js file:

html: function(e10) {
      return Y(this, function(e11) {
        var t10 = this[0] || {}, n2 = 0, r2 = this.length;
        if (void 0 === e11 && 1 === t10.nodeType)
          return t10.innerHTML;
        if ("string" == typeof e11 && !tE.test(e11) && !tc[(tl.exec(e11) || ["", ""])[1].toLowerCase()]) {
          //e11 = T.htmlPrefilter(e11); 
          try {
            for (; n2 < r2; n2++)
              t10 = this[n2] || {}, 1 === t10.nodeType && (T.cleanData(tf(t10, false)), t10.innerHTML = e11);
            t10 = 0;
          } catch (e12) {
          }
        }
        t10 && this.empty().append(e11);
      }, null, e10, arguments.length);
    }

guzman-rc avatar Mar 17 '24 17:03 guzman-rc

Shouldn't the htmlPrefilter function take care of this? I think this is the same issue I have in #784

Thats only for the parts using jquery.

We're trying to rely on that as little as possible.

We haven't updated -any- of gmailjs to automatically do Trusted HTML. You need to do yourself that before inserting html into Gmail.js APIs.

A future version might make this smoother, but not the version we have right now.

josteink avatar Mar 17 '24 18:03 josteink

e11 = T.htmlPrefilter(e11);

@guzman-rc : thx for this tip.. do you make this change post npm build manually? or is this already part of the build process?

I am doing this manually, but wondering if there's a better way until long term fix comes out.

anuragphadke avatar Mar 18 '24 20:03 anuragphadke

Try document.createTextNode('XYZ') to pass in? This worked for me:

            gmail.tools.add_toolbar_button(document.createTextNode('XYZ'), (domEmail) => {
                ...
            }, 'asa');

dblock avatar Feb 23 '25 20:02 dblock