JavaScript Permissions API: Check Browser Authorization
The JavaScript Permissions API provides a standardized way for web
applications to query the current authorization status of browser
features, such as geolocation, camera access, and notifications, without
actively prompting the user. By utilizing the
navigator.permissions.query() method, developers can
determine whether a capability is already granted, denied, or awaiting
user interaction, allowing applications to adapt their user interface
seamlessly based on real-time permissions.
Understanding Permission States
When you query a feature using the Permissions API, the browser
returns a PermissionStatus object containing a
state property. This property will always be one of three
values:
granted: The user has explicitly authorized access to the feature. The application can invoke the API immediately without displaying a prompt.denied: The user has blocked access to the feature, or access is prohibited by system/browser policy. Attempting to use the API will fail automatically.prompt: The user has not yet decided. Invoking the feature’s API will trigger a browser dialog asking the user for permission.
Querying Permission Status with JavaScript
To inspect the status of a specific API, call
navigator.permissions.query() and pass a descriptor object
containing the permission name. Because this method returns
a Promise, it is typically handled using async/await
syntax.
async function checkGeolocationPermission() {
try {
const status = await navigator.permissions.query({ name: 'geolocation' });
switch (status.state) {
case 'granted':
console.log('Location access is already allowed.');
break;
case 'prompt':
console.log('User will be prompted when location is requested.');
break;
case 'denied':
console.log('Location access has been blocked by the user.');
break;
}
} catch (error) {
console.error('Permission query failed or is unsupported:', error);
}
}
checkGeolocationPermission();Listening for Permission State Changes
A user can revoke or grant permissions at any time via the browser’s
site settings. The PermissionStatus object inherits from
EventTarget, enabling you to listen for dynamic state
transitions via the change event.
async function monitorCameraPermission() {
try {
const status = await navigator.permissions.query({ name: 'camera' });
status.onchange = () => {
console.log(`Camera permission changed to: ${status.state}`);
// Update UI elements dynamically
};
} catch (error) {
console.error('Unable to monitor camera permission:', error);
}
}Common Permission Descriptors
Different browser capabilities use distinct permission names within the query object:
{ name: 'geolocation' }- Access to device location.{ name: 'notifications' }- Access to display desktop notifications.{ name: 'camera' }- Access to video input devices.{ name: 'microphone' }- Access to audio input devices.{ name: 'clipboard-read' }or{ name: 'clipboard-write' }- Access to system clipboard contents.
Best Practices
- Feature Detection: Always verify that
navigator.permissionsis supported before calling it. - Context-Aware Requests: Check for the
promptstate to present explanatory UI to users before triggering the browser’s native prompt. - Graceful Degradation: When a state is
denied, disable related UI elements and provide clear fallback instructions so users understand why the feature is unavailable.