Chrome Extension - Migration to Manifest v3 - chrome.permissions user gesture issue

745 views
Skip to first unread message

Tom Isherwood

unread,
Jan 5, 2022, 6:17:26 AM1/5/22
to Chromium Extensions

I have built a chrome extension in manifest version 2 and am now looking at migrating to version 3. As part of this migration I have come across an issue when trying to toggle an optional permission to use the chrome notifications api.

Since you can't request a new permission from a content script as the api is not accessible from a content script, you have to send a message to the background script to perform the request and return the response to the content script. This worked as expected with version 2, now I am receiving this error:

Unchecked runtime.lastError: This function must be called during a user gesture

This means that the extension wants the permission request to be initiated on the back of an event initiated by a user action, such as a click. This indicates that the extension wishes the permission request to be completed from the content script but as stated above this is impossible.

Could anyone illuminate me if I'm missing something?

Content Script:

chrome.runtime.sendMessage( {message: 'requestPermissions', permissions: ['notifications']}, (res) => console.log(res) );

Background Script:

export function requestPermissions(request, sender, sendResponse) {
const {permissions} = request;

new Promise((resolve) => {
chrome.permissions.request( { permissions },
(granted) => resolve(granted) );
}).then((res) => sendResponse(res));

return true;
}

Simeon Vincent

unread,
Jan 6, 2022, 3:48:14 AM1/6/22
to Tom Isherwood, Chromium Extensions
The background script code you provided does not have a chrome.runtime.onMessage listener registered. Instead, it looks like background.js is a service worker module script that exports a function that has the signature of an onMessage callback that is never called.

The content script also appears to attempt to send a "requestPermissions" message on initial injection rather than in response to a user action such as a click event.

Simeon - @dotproto
Chrome Extensions DevRel


--
You received this message because you are subscribed to the Google Groups "Chromium Extensions" group.
To unsubscribe from this group and stop receiving emails from it, send an email to chromium-extens...@chromium.org.
To view this discussion on the web visit https://groups.google.com/a/chromium.org/d/msgid/chromium-extensions/65438533-1cd3-41f5-8756-9721eff6801dn%40chromium.org.

Simeon Vincent

unread,
Jan 6, 2022, 4:13:42 AM1/6/22
to Tom Isherwood, Chromium Extensions
I couldn't shake the feeling that something was wrong, so I took a closer look and verified that user gestures are not being passed as expected. I just opened https://crbug.com/1284891 to track this issue.

Simeon - @dotproto
Chrome Extensions DevRel

Tom Isherwood

unread,
Jan 6, 2022, 5:40:24 AM1/6/22
to Chromium Extensions, Simeon Vincent, Chromium Extensions, Tom Isherwood
Thank you for posting the bug report!

wOxxOm

unread,
Jan 6, 2022, 9:27:28 AM1/6/22
to Chromium Extensions, tom.is...@reversemediagroup.com, Simeon Vincent, Chromium Extensions
It's a known issue that was reported more than a year ago in https://crbug.com/1152555.

Kamt Schatka

unread,
Sep 7, 2022, 5:18:53 AM9/7/22
to Chromium Extensions, wOxxOm, tom.is...@reversemediagroup.com, Simeon Vincent, Chromium Extensions
I just ran into the same issue, but my extension has a bit of a twist:
* Before requesting the permissions, we are requesting if we already have the permission using chrome.permissions.contains({ permissions: ['notifications'] })

This of course executes async and therefore the message "This function must be called during a user gesture" is appearing again.

From a technical standpoint I understand why it is happening, but I am wondering if that is what should be happening or not? It definitely worked fine with Manifest v2, but does not behave the same anymore in Manifest v3.
In case you need to run any async function (e.g. against the Chrome API) this will not work anymore.

wOxxOm

unread,
Sep 7, 2022, 5:44:18 AM9/7/22
to Chromium Extensions, ssch...@gmail.com, wOxxOm, tom.is...@reversemediagroup.com, Simeon Vincent, Chromium Extensions
You can check the permission synchronously: `if (chrome.notifications)`
Anyway, if you see the problem in Chrome 105 and newer, which didn't occur in MV2, open a new bug report with the demo extension.

Simeon Vincent

unread,
Sep 8, 2022, 10:55:06 AM9/8/22
to wOxxOm, Chromium Extensions, ssch...@gmail.com, tom.is...@reversemediagroup.com
As wOxxOm said, the notifications namespace won't be exposed on the chrome global if the user hasn't granted that permission. That works most of the time, but it doesn't work for host permissions since they're not exposed directly in the JS interface.

If you need to check host permissions, you may want to try to front load your call to chrome.permissions.contains. For example, make the call when the UI that would display the permission grant request is first initialized.

Simeon - @dotproto
Chrome Extensions DevRel

Reply all
Reply to author
Forward
0 new messages