navigator. clipboard
Asynchronous access to the system clipboard. The writeText() method copies text, and readText() reads it back from the clipboard.
- Returns
- A promise. For
writeText()andwrite()it fulfills withundefined, forreadText()with the clipboard’s string, and forread()with an array ofClipboardItemobjects.
Example
#const copyButton = document.querySelector('#copy')
const snippet = document.querySelector('#snippet')
copyButton.addEventListener('click', async () => {
try {
await navigator.clipboard.writeText(snippet.textContent)
copyButton.textContent = 'Copied!'
console.log('Copied:', snippet.textContent)
} catch (error) {
console.log('Could not copy:', error.name)
}
})Copied: console.log('Welcome to CodeWorlds!')The browser blocks the clipboard in the isolated frame the examples on this page run in, so the code doesn’t run in the preview. On a regular page with a #snippet code block, clicking the button copies its content, and the console shows the result above.
Definition and usage
#navigator.clipboard is an object for working with the system clipboard. Most often you’ll use the writeText(text) method, which copies a string to the clipboard, e.g. after clicking a “Copy code” button. The readText() method reads text from the clipboard, and write() and read() also handle other data, such as images, wrapped in ClipboardItem objects.
All the methods are asynchronous and return promises, so use them with await or then(). The promise is rejected when the browser doesn’t allow the operation, so always handle errors, e.g. with a try...catch block.
The clipboard only works on pages opened over HTTPS (or from localhost), and browsers guard it against abuse. Writing requires the page to be active, and in some browsers also that the code runs in response to a user action, such as a click. Reading is protected more strictly: the browser may ask for permission or show a “Paste” button. Inside iframe frames, the parent page must also grant access.
The writeText() method has worked in all major browsers for years. readText(), read(), write(), and ClipboardItem objects have only been available everywhere since 2024, so it’s worth checking that they exist before using them.
Syntax
#navigator.clipboard.writeText(text)
navigator.clipboard.readText()
navigator.clipboard.write(items)
navigator.clipboard.read()Parameters
#text
string
The text to copy, inwriteText().items
array of ClipboardItem
The data to save inwrite(), e.g. an image or text in several formats.
More examples
#document.querySelector('#paste').addEventListener('click', async () => {
try {
const text = await navigator.clipboard.readText()
document.querySelector('#project-link').value = text.trim()
console.log('Pasted:', text.trim())
} catch (error) {
console.log('No access to the clipboard:', error.name)
}
})Pasted: https://github.com/emma/calculator
When reading, the browser may ask for permission or show a “Paste” button. If the user refuses, the promise is rejected with a NotAllowedError, and the catch block runs.
async function copyText(text) {
if (!navigator.clipboard) return 'Clipboard unavailable, copy the text by hand'
try {
await navigator.clipboard.writeText(text)
return 'Copied to clipboard'
} catch (error) {
return `No permission to write: ${error.name}`
}
}
document.querySelector('#coupon').addEventListener('click', async () => {
console.log(await copyText('COURSE-20'))
})Copied to clipboard
The result appears after clicking the button on a page opened over HTTPS. On a page opened over plain HTTP, the navigator.clipboard object doesn’t exist, and the function returns the first message.
Browser support
#Newly available · since 2024
Works in the current versions of all major browsers. Older versions may not support it.
- Chrome
- Edge
- Firefox
- Safari
Good practices
#- Call
writeText()from inside a click handler. Some browsers block copying without a user action. - Always handle a rejected promise and let the user know whether copying succeeded, e.g. by changing the button’s text to “Copied!”.
navigator.clipboarddoesn’t exist on pages without HTTPS. Check for it before use, e.g. withnavigator.clipboard?.writeText.
Related entries
#- EventTarget.addEventListener()Registers a function that’s called every time a given event occurs on an element, for example a click.
- async functionDeclares an asynchronous function that always returns a promise and can use the await keyword inside it.
- awaitPauses an async function until a promise settles, then returns its value or throws its error.
- try...catchCatches errors thrown in the try block and handles them in catch. The optional finally always runs.
- PromiseAn object representing the result of an operation that will be available in the future: a value on success or an error.
Spotted a mistake or missing an example? Write to us.