Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Gmail hides the button added by the tools.add_toolbar_button( api by gmailjs #796

Open
mohammedfarhan99 opened this issue Sep 26, 2024 · 3 comments

Comments

@mohammedfarhan99
Copy link

mohammedfarhan99 commented Sep 26, 2024

Context

In our chrome extension, we inject a button into gmail's toolbar,via gmailjs' add_toolbar_button button api, via this func (code modified for brevity):

function addButton(){
// we have a check to see if the button is already present, we don't re-add it
gmail.tools.add_toolbar_button(
  `
   <button>
   Click Me!
   </button>   
  `,
  () => alert('CLick me!')
)
}

Incident Report

After the newest chrome update to version 129.0.6668.70, this injected button appears into gmail's toolbar for a couple of seconds and disappears, so to alleviate that we tried adding a setTimeout to where we call this function, which is in the event handlers of hashChange and load
So previously in these event handlers if we called addButton() directly now it would change to
setTimeout(addButton, 5000),

Although this would make our injected button appear after 4s, it would still disappear once again. But at least now we would notice that our injected button appears on gmail's toolbar dom, but not on gmail's toolbar itself, the reason for this being that the parent element of our injected button has a css style of { display: none } which was causing our button to not appear in the toolbar

So we modify our above function to also see if the parent's css has display as none and if it does, then we modify the property of display to 'block'.

So the function is rewritten to accommodate the button's parent css

function addButton(){
//Fetch parent 
const toolbar = _gmailjs__jQuery('[gh="tm"]');
const buttonToolbar = toolbar.find('#my-button')
//Compute if button toolbar already has your button, via find or other jquery methods
const doesToolBarHaveMyButton;
if(doesToolBarHaveMyButton){
gmail.tools.add_toolbar_button(
  `
   <button>
   Click Me!
   </button>   
  `,
  () => alert('CLick me!')
)
}
} else {
  //Check if toolbar's parent has display property as none and update accordingly
  const buttonToolBarParent = buttonToolbar.parent()
  const parentEl = buttonToolBarParent.parent()
  const currentCssValue = parentEl.css('display')
 if(currentCss === 'none'){
   parentEl.css('display','block')
 }
}

Conclusion

This rewrite works, but it feels like this solution is a little hacky and seems like something that's best handled within gmail-js itself. If anyone could pick it up, that would be great. Otherwise, would love some guidance as to the best place to handle this, and a good practice to handle it, since I'm sure gmail-js would have had to handle similar issues in the past

@josteink
Copy link
Collaborator

Hey there and thanks for the very detailed issue report.

I agree this sounds like something which should be handled within Gmail.js itself.

My best suggestion would be to inspect the code for the gmail.tools.add_toolbar_button() function and see what sort of CSS selectors it uses. Maybe they can be adjusted so that we avoid the issue entirely? In that case, you might just submit a PR with those changes.

If you think something more complicated will be required, lets keep this issue open, so we can discuss possible solutions here, with a full context and code sample which is easy to refer to, and for others to join in on.

Let me know what you find 😄

@shrikrishnaholla
Copy link

Thanks for the prompt response @josteink !

I don't think the css selector is an issue here. Here's how the add toolbar picks the parent element:

api.tools.add_toolbar_button = function(content_html, onClickFunction, styleClass) {

    api.dom.toolbar = function() {
        var tb = $("[gh='mtb']");

        while($(tb).children().length === 1){
            tb = $(tb).children().first();
        }

        return tb;
    };

And all gmail.tools.add_toolbar_button() does is add a child to it:

api.tools.add_toolbar_button = function(content_html, onClickFunction, styleClass) {

But the issue is that the child's style is mutated, possibly by some useEffect-esque function in gmail's js

Screenshot_20240927_142652

Have you encountered similar issues in the past? What's the best way to solve this?

@shrikrishnaholla
Copy link

Here's a slightly different, but more reliable change:

    // Get the DOM element from the jQuery object
    const parentElHTML = parentEl.get(0);

    const observer = new MutationObserver(mutationsList => {
      for (let mutation of mutationsList) {
        if (
          mutation.type === 'attributes' &&
          mutation.attributeName === 'style'
        ) {
          if (mutation.target && mutation.target.style && mutation.target.style.display === 'none') {
            // Detected change, forcing display to block
            mutation.target.style.display = 'block'; // Force visibility
          }
        }
      }
    });
    // Observe for changes in the target element's style attribute
    observer.observe(parentElHTML, {
      attributes: true,
      attributeFilter: ['style'],
    });

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

No branches or pull requests

3 participants