javascript cut/copy/paste to clipboard: how did Google solve it?

Jos de Jong picture Jos de Jong · Mar 11, 2012 · Viewed 41.7k times · Source

Yes, this question has been asked again and again: how to copy and paste from and to the system clipboard with javascript? I have found only partial solutions and hacks so far. The reason that it has been asked so often in the past is that there still is no working solution. However, I saw that Google Docs actually has a working solution now for both keyboard events as well as buttons. So, it is possible, but how do they do it? Software Salad article, Accessing the System Clipboard with JavaScript – A Holy Grail?, gives a nice overview of the problem (but it's a few years old).

In short:

  • you can use keyboard events ctrl+x, ctrl+c, ctrl+v to either copy text from a hidden textarea with prepared data, or catch pasted text in a hidden field and then do something with it

  • you can use some hack via Flash or maybe a Java Applet to copy something to the system clipboard without need for user approval.

  • you can use a "real" solution with clipboardData.setData for IE and execCommand for other browsers, which depends on approval of the user.

Any idea how Google has tackled the clipboard problem?

Answer

Mateusz W picture Mateusz W · Apr 3, 2014

I know that question was posted long ago, but I needed to check how google does that, so maybe someone will find that useful.

Actually google uses also system clipboard but it's a bit tricky. In case when you use keyboard shortcut you can catch copy/paste/cut event on e.g. window:

window.addEventListener('copy', function (ev) {
    console.log('copy event');
    // you can set clipboard data here, e.g.
    ev.clipboardData.setData('text/plain', 'some text pushed to clipboard');
    // you need to prevent default behaviour here, otherwise browser will overwrite your content with currently selected 
    ev.preventDefault();
});

live example for keyboard shortcut: http://jsfiddle.net/tyk9U/

Unfortunately this is only solution for keyboard shortcut and there is a problem with context menu, because you can't access clipboard data without native (trusted) copy/cut/paste event. But google does interesting trick. There is API document.execCommand() that allows you to run commands for contenteditable element and there is the command 'copy' which you can trigger it via document.execCommand('copy'). But when you try this in console in Chrome it will return false. I spent a bit of time investigating that and it turned out that they have Chrome extension installed, called "Google Drive" (go to chrome://apps/ and you can see it there) that enables clipboard access for domains drive.google.com and docs.google.com. Open some document or spreadsheet and type in console document.execCommand('copy') - it will return true. When you uninstall the extension you won't be able to use clipboard operations from context menu.

You can create such application for yourself with very simple manifest file (details here https://developer.chrome.com/apps/first_app):

{
    "manifest_version": 2,
    "name": "App name",
    "description": "App description",
    "version": "1.0",
    "app": {
        "urls": [
            "http://your.app.url.here/"
        ],
        "launch": {
            "web_url": "http://your.app.url.here/"
        }
    },
    "icons": {
        "128": "x-128.png"
    },
    "permissions": [
        "clipboardRead",
        "clipboardWrite"
    ]
}

"permissions" field here enables clipboard operations.

Now when you have this enabled you can do document.execCommand('copy') and it will work (will return true). But this is not everything - document.execCommand('copy') in chrome triggers copy event and you can catch it with the same code that is used for catching keyboard clipboard shortcuts. This is now Google does it.

Of course this description is valid only for Chrome.