Permissions: query() method

Baseline 2022

Newly available

Since September 2022, this feature works across the latest devices and browser versions. This feature might not work in older devices or browsers.

Note: This feature is available in Web Workers.

The query() method of the Permissions interface returns the state of a user permission on the global scope.





An object that sets options for the query operation consisting of a comma-separated list of name-value pairs. The available options are:


The name of the API whose permissions you want to query. Each browser supports a different set of values. You'll find Firefox values there, Chromium values there, and WebKit values there.


(Push only, not supported in Firefox — see the Browser Support section below) Indicates whether you want to show a notification for every message or be able to send silent push notifications. The default is false.

sysex (MIDI only)

Indicates whether you need and/or receive system exclusive messages. The default is false.

Note: As of Firefox 44, the permissions for Notifications and Push have been merged. If permission is granted (e.g. by the user, in the relevant permissions dialog), navigator.permissions.query() will return true for both notifications and push.

Note: The persistent-storage permission allows an origin to use a persistent box (i.e., persistent storage) for its storage, as per the Storage API.

Return value

A Promise that resolves to a PermissionStatus object.


InvalidStateError DOMException

Thrown if query() method is invoked in the browsing context and its associated document is not fully active.


Thrown if retrieving the PermissionDescriptor information failed in some way, or the permission doesn't exist or is unsupported by the user agent.


Display news based on geolocation permission

This example shows how you might display news related to the current location if the geolocation permission is granted, and otherwise prompt the user to enable granting access to the location.

navigator.permissions.query({ name: "geolocation" }).then((result) => {
  if (result.state === "granted") {
  } else if (result.state === "prompt") {
  // Don't do anything if the permission was denied.

Test support for various permissions

This example shows the result of querying each of the permissions.

The code uses navigator.permissions.query() to query each permission, logging either the permission status or the fact that the permission is not supported on the browser. Note that the query() is called inside a try...catch block because the associated Promise will reject if the permission is not supported.

// Array of permissions
const permissions = [


// Iterate through the permissions and log the result
async function processPermissions() {
  for (const permission of permissions) {
    const result = await getPermission(permission);

// Query a single permission in a try...catch block and return result
async function getPermission(permission) {
  try {
    const result = await navigator.permissions.query({ name: permission });
    return `${permission}: ${result.state}`;
  } catch (error) {
    return `${permission} (not supported)`;

The log from running the code is shown below:


# dom-permissions-query

Browser compatibility

BCD tables only load in the browser