Home | History | Annotate | Download | only in docs
      1 <!DOCTYPE html><!-- This page is a placeholder for generated extensions api doc. Note:
      2     1) The <head> information in this page is significant, should be uniform
      3        across api docs and should be edited only with knowledge of the
      4        templating mechanism.
      5     3) All <body>.innerHTML is genereated as an rendering step. If viewed in a
      6        browser, it will be re-generated from the template, json schema and
      7        authored overview content.
      8     4) The <body>.innerHTML is also generated by an offline step so that this
      9        page may easily be indexed by search engines.
     10 --><html xmlns="http://www.w3.org/1999/xhtml"><head>
     11     <meta http-equiv="Content-Type" content="text/html; charset=UTF-8">
     12     <link href="css/ApiRefStyles.css" rel="stylesheet" type="text/css">
     13     <link href="css/print.css" rel="stylesheet" type="text/css" media="print">
     14     <script type="text/javascript" src="../../../third_party/jstemplate/jstemplate_compiled.js">
     15     </script>
     16     <script type="text/javascript" src="js/api_page_generator.js"></script>
     17     <script type="text/javascript" src="js/bootstrap.js"></script>
     18     <script type="text/javascript" src="js/sidebar.js"></script>
     19   <title>Message Passing - Google Chrome Extensions - Google Code</title></head>
     20   <body>  <div id="gc-container" class="labs">
     21       <div id="devModeWarning">
     22         You are viewing extension docs in chrome via the 'file:' scheme: are you expecting to see local changes when you refresh? You'll need run chrome with --allow-file-access-from-files.
     23       </div>
     24       <!-- SUBTEMPLATES: DO NOT MOVE FROM THIS LOCATION -->
     25       <!-- In particular, sub-templates that recurse, must be used by allowing
     26            jstemplate to make a copy of the template in this section which
     27            are not operated on by way of the jsskip="true" -->
     28       <div style="display:none">
     29 
     30         <!-- VALUE -->
     31         <div id="valueTemplate">
     32           <dt>
     33             <var>paramName</var>
     34               <em>
     35 
     36                 <!-- TYPE -->
     37                 <div style="display:inline">
     38                   (
     39                     <span class="optional">optional</span>
     40                     <span class="enum">enumerated</span>
     41                     <span id="typeTemplate">
     42                       <span>
     43                         <a> Type</a>
     44                       </span>
     45                       <span>
     46                         <span>
     47                           array of <span><span></span></span>
     48                         </span>
     49                         <span>paramType</span>
     50                         <span></span>
     51                       </span>
     52                     </span>
     53                   )
     54                 </div>
     55 
     56               </em>
     57           </dt>
     58           <dd class="todo">
     59             Undocumented.
     60           </dd>
     61           <dd>
     62             Description of this parameter from the json schema.
     63           </dd>
     64           <dd>
     65             This parameter was added in version
     66             <b><span></span></b>.
     67             You must omit this parameter in earlier versions,
     68             and you may omit it in any version.  If you require this
     69             parameter, the manifest key
     70             <a href="manifest.html#minimum_chrome_version">minimum_chrome_version</a>
     71             can ensure that your extension won't be run in an earlier browser version.
     72           </dd>
     73 
     74           <!-- OBJECT PROPERTIES -->
     75           <dd>
     76             <dl>
     77               <div>
     78                 <div>
     79                 </div>
     80               </div>
     81             </dl>
     82           </dd>
     83 
     84           <!-- OBJECT METHODS -->
     85           <dd>
     86             <div></div>
     87           </dd>
     88 
     89           <!-- OBJECT EVENT FIELDS -->
     90           <dd>
     91             <div></div>
     92           </dd>
     93 
     94           <!-- FUNCTION PARAMETERS -->
     95           <dd>
     96             <div></div>
     97           </dd>
     98 
     99         </div> <!-- /VALUE -->
    100 
    101         <div id="functionParametersTemplate">
    102           <h5>Parameters</h5>
    103           <dl>
    104             <div>
    105               <div>
    106               </div>
    107             </div>
    108           </dl>
    109         </div>
    110       </div> <!-- /SUBTEMPLATES -->
    111 
    112   <a id="top"></a>
    113     <div id="skipto">
    114       <a href="#gc-pagecontent">Skip to page content</a>
    115       <a href="#gc-toc">Skip to main navigation</a>
    116     </div>
    117     <!-- API HEADER -->
    118     <table id="header" width="100%" cellspacing="0" border="0">
    119       <tbody><tr>
    120         <td valign="middle"><a href="http://code.google.com/"><img src="images/code_labs_logo.gif" height="43" width="161" alt="Google Code Labs" style="border:0; margin:0;"></a></td>
    121         <td valign="middle" width="100%" style="padding-left:0.6em;">
    122           <form action="http://www.google.com/cse" id="cse" style="margin-top:0.5em">
    123             <div id="gsc-search-box">
    124               <input type="hidden" name="cx" value="002967670403910741006:61_cvzfqtno">
    125               <input type="hidden" name="ie" value="UTF-8">
    126               <input type="text" name="q" value="" size="55">
    127               <input class="gsc-search-button" type="submit" name="sa" value="Search">
    128               <br>
    129               <span class="greytext">e.g. "page action" or "tabs"</span>
    130             </div>
    131           </form>
    132 
    133           <script type="text/javascript" src="http://www.google.com/jsapi"></script>
    134           <script type="text/javascript">google.load("elements", "1", {packages: "transliteration"});</script>
    135           <script type="text/javascript" src="http://www.google.com/coop/cse/t13n?form=cse&t13n_langs=en"></script>
    136           <script type="text/javascript" src="http://www.google.com/coop/cse/brand?form=cse&lang=en"></script>
    137         </td>
    138       </tr>
    139     </tbody></table>
    140 
    141     <div id="codesiteContent" class="">
    142 
    143       <a id="gc-topnav-anchor"></a>
    144       <div id="gc-topnav">
    145         <h1>Google Chrome Extensions (<a href="http://code.google.com/labs/">Labs</a>)</h1>
    146         <ul id="home" class="gc-topnav-tabs">
    147           <li id="home_link">
    148             <a href="index.html" title="Google Chrome Extensions home page">Home</a>
    149           </li>
    150           <li id="docs_link">
    151             <a href="docs.html" title="Official Google Chrome Extensions documentation">Docs</a>
    152           </li>
    153           <li id="faq_link">
    154             <a href="faq.html" title="Answers to frequently asked questions about Google Chrome Extensions">FAQ</a>
    155           </li>
    156           <li id="samples_link">
    157             <a href="samples.html" title="Sample extensions (with source code)">Samples</a>
    158           </li>
    159           <li id="group_link">
    160             <a href="http://groups.google.com/a/chromium.org/group/chromium-extensions" title="Google Chrome Extensions developer forum">Group</a>
    161           </li>
    162         </ul>
    163       </div> <!-- end gc-topnav -->
    164 
    165     <div class="g-section g-tpl-170">
    166       <!-- SIDENAV -->
    167       <div class="g-unit g-first" id="gc-toc">
    168         <ul>
    169           <li><a href="getstarted.html">Getting Started</a></li>
    170           <li><a href="overview.html">Overview</a></li>
    171           <li><a href="whats_new.html">What's New?</a></li>
    172           <li><h2><a href="devguide.html">Developer's Guide</a></h2>
    173             <ul>
    174               <li>Browser UI
    175                 <ul>
    176                   <li><a href="browserAction.html">Browser Actions</a></li>
    177                   <li><a href="contextMenus.html">Context Menus</a></li>
    178                   <li><a href="notifications.html">Desktop Notifications</a></li>
    179                   <li><a href="omnibox.html">Omnibox</a></li>
    180                   <li><a href="options.html">Options Pages</a></li>
    181                   <li><a href="override.html">Override Pages</a></li>
    182                   <li><a href="pageAction.html">Page Actions</a></li>
    183                 </ul>
    184               </li>
    185               <li>Browser Interaction
    186                 <ul>
    187                   <li><a href="bookmarks.html">Bookmarks</a></li>
    188                   <li><a href="cookies.html">Cookies</a></li>
    189                   <li><a href="events.html">Events</a></li>
    190                   <li><a href="history.html">History</a></li>
    191                   <li><a href="management.html">Management</a></li>
    192                   <li><a href="tabs.html">Tabs</a></li>
    193                   <li><a href="windows.html">Windows</a></li>
    194                 </ul>
    195               </li>
    196               <li>Implementation
    197                 <ul>
    198                   <li><a href="a11y.html">Accessibility</a></li>
    199                   <li><a href="background_pages.html">Background Pages</a></li>
    200                   <li><a href="content_scripts.html">Content Scripts</a></li>
    201                   <li><a href="xhr.html">Cross-Origin XHR</a></li>
    202                   <li><a href="idle.html">Idle</a></li>
    203                   <li><a href="i18n.html">Internationalization</a></li>
    204                   <li class="leftNavSelected">Message Passing</li>
    205                   <li><a href="npapi.html">NPAPI Plugins</a></li>
    206                 </ul>
    207               </li>
    208               <li>Finishing
    209                 <ul>
    210                   <li><a href="hosting.html">Hosting</a></li>
    211                   <li><a href="external_extensions.html">Other Deployment Options</a></li>
    212                 </ul>
    213               </li>
    214             </ul>
    215           </li>
    216           <li><h2><a href="apps.html">Packaged Apps</a></h2></li>
    217           <li><h2><a href="tutorials.html">Tutorials</a></h2>
    218             <ul>
    219               <li><a href="tut_debugging.html">Debugging</a></li>
    220               <li><a href="tut_analytics.html">Google Analytics</a></li>
    221               <li><a href="tut_oauth.html">OAuth</a></li>
    222             </ul>
    223           </li>
    224           <li><h2>Reference</h2>
    225             <ul>
    226               <li>Formats
    227                 <ul>
    228                   <li><a href="manifest.html">Manifest Files</a></li>
    229                   <li><a href="match_patterns.html">Match Patterns</a></li>
    230                 </ul>
    231               </li>
    232               <li><a href="permission_warnings.html">Permission Warnings</a></li>
    233               <li><a href="api_index.html">chrome.* APIs</a></li>
    234               <li><a href="api_other.html">Other APIs</a></li>
    235             </ul>
    236           </li>
    237           <li><h2><a href="samples.html">Samples</a></h2></li>
    238           <div class="line"> </div>
    239           <li><h2>More</h2>
    240             <ul>
    241               <li><a href="http://code.google.com/chrome/webstore/docs/index.html">Chrome Web Store</a></li>
    242               <li><a href="http://code.google.com/chrome/apps/docs/developers_guide.html">Hosted Apps</a></li>
    243               <li><a href="themes.html">Themes</a></li>
    244             </ul>
    245           </li>
    246         </ul>
    247       </div>
    248       <script>
    249         initToggles();
    250       </script>
    251 
    252     <div class="g-unit" id="gc-pagecontent">
    253       <div id="pageTitle">
    254         <h1 class="page_title">Message Passing</h1>
    255       </div>
    256         <!-- TABLE OF CONTENTS -->
    257         <div id="toc">
    258           <h2>Contents</h2>
    259           <ol>
    260             <li>
    261               <a href="#simple">Simple one-time requests</a>
    262               <ol>
    263                 <li style="display: none; ">
    264                   <a>h3Name</a>
    265                 </li>
    266               </ol>
    267             </li><li>
    268               <a href="#connect">Long-lived connections</a>
    269               <ol>
    270                 <li style="display: none; ">
    271                   <a>h3Name</a>
    272                 </li>
    273               </ol>
    274             </li><li>
    275               <a href="#external">Cross-extension messaging</a>
    276               <ol>
    277                 <li style="display: none; ">
    278                   <a>h3Name</a>
    279                 </li>
    280               </ol>
    281             </li><li>
    282               <a href="#security-considerations">Security considerations</a>
    283               <ol>
    284                 <li style="display: none; ">
    285                   <a>h3Name</a>
    286                 </li>
    287               </ol>
    288             </li><li>
    289               <a href="#examples">Examples</a>
    290               <ol>
    291                 <li style="display: none; ">
    292                   <a>h3Name</a>
    293                 </li>
    294               </ol>
    295             </li>
    296               <li style="display: none; ">
    297                 <a href="#apiReference">API reference</a>
    298                 <ol>
    299                   <li>
    300                     <a href="#properties">Properties</a>
    301                     <ol>
    302                       <li>
    303                         <a href="#property-anchor">propertyName</a>
    304                       </li>
    305                     </ol>
    306                   </li>
    307                   <li>
    308                     <a>Methods</a>
    309                     <ol>
    310                       <li>
    311                         <a href="#method-anchor">methodName</a>
    312                       </li>
    313                     </ol>
    314                   </li>
    315                   <li>
    316                     <a>Events</a>
    317                     <ol>
    318                       <li>
    319                         <a href="#event-anchor">eventName</a>
    320                       </li>
    321                     </ol>
    322                   </li>
    323                   <li>
    324                     <a href="#types">Types</a>
    325                     <ol>
    326                       <li>
    327                         <a href="#id-anchor">id</a>
    328                       </li>
    329                     </ol>
    330                   </li>
    331                 </ol>
    332               </li>
    333           </ol>
    334         </div>
    335         <!-- /TABLE OF CONTENTS -->
    336 
    337         <!-- Standard content lead-in for experimental API pages -->
    338         <p id="classSummary" style="display: none; ">
    339           For information on how to use experimental APIs, see the <a href="experimental.html">chrome.experimental.* APIs</a> page.
    340         </p>
    341 
    342         <!-- STATIC CONTENT PLACEHOLDER -->
    343         <div id="static"><div id="pageData-name" class="pageData">Message Passing</div>
    344 <div id="pageData-showTOC" class="pageData">true</div>
    345 
    346 <p>
    347 Since content scripts run in the context of a web page and not the extension,
    348 they often need some way of communicating with the rest of the extension. For
    349 example, an RSS reader extension might use content scripts to detect the
    350 presence of an RSS feed on a page, then notify the background page in order to
    351 display a page action icon for that page.
    352 
    353 </p><p>
    354 Communication between extensions and their content scripts works by using
    355 message passing. Either side can listen for messages sent from the other end,
    356 and respond on the same channel. A message can contain any valid JSON object
    357 (null, boolean, number, string, array, or object). There is a simple API for
    358 <a href="#simple">one-time requests</a>
    359 and a more complex API that allows you to have
    360 <a href="#connect">long-lived connections</a>
    361 for exchanging multiple messages with a shared context. It is also possible to
    362 send a message to another extension if you know its ID, which is covered in
    363 the
    364 <a href="#external">cross-extension messages</a>
    365 section.
    366 
    367 
    368 </p><h2 id="simple">Simple one-time requests</h2>
    369 <p>
    370 If you only need to send a single message to another part of your extension
    371 (and optionally get a response back), you should use the simplified
    372 <a href="extension.html#method-sendRequest">chrome.extension.sendRequest()</a>
    373 or
    374 <a href="tabs.html#method-sendRequest">chrome.tabs.sendRequest()</a>
    375 methods. This lets you send a one-time JSON-serializable message from a
    376 content script to extension, or vice versa, respectively. An optional
    377 callback parameter allows you handle the response from the other side, if
    378 there is one.
    379 
    380 </p><p>
    381 Sending a request from a content script looks like this:
    382 </p><pre>contentscript.js
    383 ================
    384 chrome.extension.sendRequest({greeting: "hello"}, function(response) {
    385   console.log(response.farewell);
    386 });
    387 </pre>
    388 
    389 <p>
    390 Sending a request from the extension to a content script looks very similar,
    391 except that you need to specify which tab to send it to. This example
    392 demonstrates sending a message to the content script in the selected tab.
    393 </p><pre>background.html
    394 ===============
    395 chrome.tabs.getSelected(null, function(tab) {
    396   chrome.tabs.sendRequest(tab.id, {greeting: "hello"}, function(response) {
    397     console.log(response.farewell);
    398   });
    399 });
    400 </pre>
    401 
    402 <p>
    403 On the receiving end, you need to set up an
    404 <a href="extension.html#event-onRequest">chrome.extension.onRequest</a>
    405 event listener to handle the message. This looks the same from a content
    406 script or extension page. The request will remain open until you call
    407 sendResponse, so it is good practice to call sendResponse with an empty
    408 object to allow the request to be cleaned up.
    409 </p><pre>chrome.extension.onRequest.addListener(
    410   function(request, sender, sendResponse) {
    411     console.log(sender.tab ?
    412                 "from a content script:" + sender.tab.url :
    413                 "from the extension");
    414     if (request.greeting == "hello")
    415       sendResponse({farewell: "goodbye"});
    416     else
    417       sendResponse({}); // snub them.
    418   });
    419 </pre>
    420 
    421 <p class="note">
    422 <b>Note:</b> If multiple pages are listening for onRequest events, only the
    423 first to call sendResponse() for a particular event will succeed in sending the
    424 response. All other responses to that event will be ignored.
    425 </p>
    426 
    427 
    428 <h2 id="connect">Long-lived connections</h2>
    429 <p>
    430 Sometimes it's useful to have a conversation that lasts longer than a single
    431 request and response. In this case, you can open a long-lived channel from
    432 your content script to an extension page, or vice versa, using
    433 <a href="extension.html#method-connect">chrome.extension.connect()</a>
    434 or
    435 <a href="tabs.html#method-connect">chrome.tabs.connect()</a> respectively. The
    436 channel can optionally have a name, allowing you to distinguish between
    437 different types of connections.
    438 
    439 </p><p>
    440 One use case might be an automatic form fill extension. The content script
    441 could open a channel to the extension page for a particular login, and send a
    442 message to the extension for each input element on the page to request the
    443 form data to fill in. The shared connection allows the extension to keep
    444 shared state linking the several messages coming from the content script.
    445 
    446 </p><p>
    447 When establishing a connection, each end is given a
    448 <a href="extension.html#type-Port">Port</a>
    449 object which is used for sending and receiving messages through that
    450 connection.
    451 
    452 </p><p>
    453 Here is how you open a channel from a content script, and send and listen for
    454 messages:
    455 </p><pre>contentscript.js
    456 ================
    457 var port = chrome.extension.connect({name: "knockknock"});
    458 port.postMessage({joke: "Knock knock"});
    459 port.onMessage.addListener(function(msg) {
    460   if (msg.question == "Who's there?")
    461     port.postMessage({answer: "Madame"});
    462   else if (msg.question == "Madame who?")
    463     port.postMessage({answer: "Madame... Bovary"});
    464 });
    465 </pre>
    466 
    467 <p>
    468 Sending a request from the extension to a content script looks very similar,
    469 except that you need to specify which tab to connect to. Simply replace the
    470 call to connect in the above example with
    471 <a href="tabs.html#method-connect">chrome.tabs.connect(tabId, {name:
    472 "knockknock"})</a>.
    473 
    474 </p><p>
    475 In order to handle incoming connections, you need to set up a
    476 <a href="extension.html#event-onConnect">chrome.extension.onConnect</a>
    477 event listener. This looks the same from a content script or an extension
    478 page. When another part of your extension calls "connect()", this event is
    479 fired, along with the
    480 <a href="extension.html#type-Port">Port</a>
    481 object you can use to send and receive messages through the connection. Here's
    482 what it looks like to respond to incoming connections:
    483 </p><pre>chrome.extension.onConnect.addListener(function(port) {
    484   console.assert(port.name == "knockknock");
    485   port.onMessage.addListener(function(msg) {
    486     if (msg.joke == "Knock knock")
    487       port.postMessage({question: "Who's there?"});
    488     else if (msg.answer == "Madame")
    489       port.postMessage({question: "Madame who?"});
    490     else if (msg.answer == "Madame... Bovary")
    491       port.postMessage({question: "I don't get it."});
    492   });
    493 });
    494 </pre>
    495 
    496 <p>
    497 You may want to find out when a connection is closed, for example if you are
    498 maintaining separate state for each open port. For this you can listen to the
    499 <a href="extension.html#type-Port">Port.onDisconnect</a>
    500 event. This event is fired either when the other side of the channel manually
    501 calls
    502 <a href="extension.html#type-Port">Port.disconnect()</a>, or when the page
    503 containing the port is unloaded (for example if the tab is navigated).
    504 onDisconnect is guaranteed to be fired only once for any given port.
    505 
    506 
    507 </p><h2 id="external">Cross-extension messaging</h2>
    508 <p>
    509 In addition to sending messages between different components in your
    510 extension, you can use the messaging API to communicate with other extensions.
    511 This lets you expose a public API that other extensions can take advantage of.
    512 
    513 </p><p>
    514 Listening for incoming requests and connections is similar to the internal
    515 case, except you use the
    516 <a href="extension.html#event-onRequestExternal">chrome.extension.onRequestExternal</a>
    517 or
    518 <a href="extension.html#event-onConnectExternal">chrome.extension.onConnectExternal</a>
    519 methods. Here's an example of each:
    520 </p><pre>// For simple requests:
    521 chrome.extension.onRequestExternal.addListener(
    522   function(request, sender, sendResponse) {
    523     if (sender.id == blacklistedExtension)
    524       sendResponse({});  // don't allow this extension access
    525     else if (request.getTargetData)
    526       sendResponse({targetData: targetData});
    527     else if (request.activateLasers) {
    528       var success = activateLasers();
    529       sendResponse({activateLasers: success});
    530     }
    531   });
    532 
    533 // For long-lived connections:
    534 chrome.extension.onConnectExternal.addListener(function(port) {
    535   port.onMessage.addListener(function(msg) {
    536     // See other examples for sample onMessage handlers.
    537   });
    538 });
    539 </pre>
    540 
    541 <p>
    542 Likewise, sending a message to another extension is similar to sending one
    543 within your extension. The only difference is that you must pass the ID of the
    544 extension you want to communicate with. For example:
    545 </p><pre>// The ID of the extension we want to talk to.
    546 var laserExtensionId = "abcdefghijklmnoabcdefhijklmnoabc";
    547 
    548 // Make a simple request:
    549 chrome.extension.sendRequest(laserExtensionId, {getTargetData: true},
    550   function(response) {
    551     if (targetInRange(response.targetData))
    552       chrome.extension.sendRequest(laserExtensionId, {activateLasers: true});
    553   });
    554 
    555 // Start a long-running conversation:
    556 var port = chrome.extension.connect(laserExtensionId);
    557 port.postMessage(...);
    558 </pre>
    559 
    560 <h2 id="security-considerations">Security considerations</h2>
    561 
    562 <p>
    563 When receiving a message from a content script or another extension, your
    564 background page should be careful not to fall victim to <a href="http://en.wikipedia.org/wiki/Cross-site_scripting">cross-site
    565 scripting</a>.  Specifically, avoid using dangerous APIs such as the
    566 below:
    567 </p>
    568 <pre>background.html
    569 ===============
    570 chrome.tabs.sendRequest(tab.id, {greeting: "hello"}, function(response) {
    571   // WARNING! Might be evaluating an evil script!
    572   var resp = eval("(" + response.farewell + ")");
    573 });
    574 
    575 background.html
    576 ===============
    577 chrome.tabs.sendRequest(tab.id, {greeting: "hello"}, function(response) {
    578   // WARNING! Might be injecting a malicious script!
    579   document.getElementById("resp").innerHTML = response.farewell;
    580 });
    581 </pre>
    582 <p>
    583 Instead, prefer safer APIs that do not run scripts:
    584 </p>
    585 <pre>background.html
    586 ===============
    587 chrome.tabs.sendRequest(tab.id, {greeting: "hello"}, function(response) {
    588   // JSON.parse does not evaluate the attacker's scripts.
    589   var resp = JSON.parse(response.farewell);
    590 });
    591 
    592 background.html
    593 ===============
    594 chrome.tabs.sendRequest(tab.id, {greeting: "hello"}, function(response) {
    595   // innerText does not let the attacker inject HTML elements.
    596   document.getElementById("resp").innerText = response.farewell;
    597 });
    598 </pre>
    599 
    600 <h2 id="examples">Examples</h2>
    601 
    602 <p>
    603 You can find simple examples of communication via messages in the
    604 <a href="http://src.chromium.org/viewvc/chrome/trunk/src/chrome/common/extensions/docs/examples/api/messaging/">examples/api/messaging</a>
    605 directory.
    606 Also see the
    607 <a href="http://src.chromium.org/viewvc/chrome/trunk/src/chrome/common/extensions/docs/examples/howto/contentscript_xhr">contentscript_xhr</a> example,
    608 in which a content script and its parent extension exchange messages,
    609 so that the parent extension can perform
    610 cross-site requests on behalf of the content script.
    611 For more examples and for help in viewing the source code, see
    612 <a href="samples.html">Samples</a>.
    613 </p>
    614 </div>
    615 
    616         <!-- API PAGE -->
    617         <div class="apiPage" style="display: none; ">
    618         <a name="apiReference"></a>
    619         <h2>API reference: chrome.apiname </h2>
    620 
    621           <!-- PROPERTIES -->
    622           <div class="apiGroup">
    623             <a name="properties"></a>
    624             <h3 id="properties">Properties</h3>
    625 
    626             <div>
    627               <a></a>
    628               <h4>getLastError</h4>
    629               <div class="summary">
    630                 <!-- Note: intentionally longer 80 columns -->
    631                 <span>chrome.extension</span><span>lastError</span>
    632               </div>
    633               <div>
    634               </div>
    635             </div>
    636 
    637           </div> <!-- /apiGroup -->
    638 
    639           <!-- METHODS -->
    640           <div id="methodsTemplate" class="apiGroup">
    641             <a></a>
    642             <h3>Methods</h3>
    643 
    644             <!-- iterates over all functions -->
    645             <div class="apiItem">
    646               <a></a> <!-- method-anchor -->
    647               <h4>method name</h4>
    648 
    649               <div class="summary"><span>void</span>
    650                   <!-- Note: intentionally longer 80 columns -->
    651                   <span>chrome.module.methodName</span>(<span><span>, </span><span></span>
    652                       <var><span></span></var></span>)</div>
    653 
    654               <div class="description">
    655                 <p class="todo">Undocumented.</p>
    656                 <p>
    657                   A description from the json schema def of the function goes here.
    658                 </p>
    659 
    660                 <!-- PARAMETERS -->
    661                 <h4>Parameters</h4>
    662                 <dl>
    663                   <div>
    664                     <div>
    665                     </div>
    666                   </div>
    667                 </dl>
    668 
    669                 <!-- RETURNS -->
    670                 <h4>Returns</h4>
    671                 <dl>
    672                   <div>
    673                     <div>
    674                     </div>
    675                   </div>
    676                 </dl>
    677 
    678                 <!-- CALLBACK -->
    679                 <div>
    680                   <div>
    681                   <h4>Callback function</h4>
    682                   <p>
    683                     The callback <em>parameter</em> should specify a function
    684                     that looks like this:
    685                   </p>
    686                   <p>
    687                     If you specify the <em>callback</em> parameter, it should
    688                     specify a function that looks like this:
    689                   </p>
    690 
    691                   <!-- Note: intentionally longer 80 columns -->
    692                   <pre>function(<span>Type param1, Type param2</span>) <span class="subdued">{...}</span>;</pre>
    693                   <dl>
    694                     <div>
    695                       <div>
    696                       </div>
    697                     </div>
    698                   </dl>
    699                   </div>
    700                 </div>
    701 
    702                 <!-- MIN_VERSION -->
    703                 <p>
    704                   This function was added in version <b><span></span></b>.
    705                   If you require this function, the manifest key
    706                   <a href="manifest.html#minimum_chrome_version">minimum_chrome_version</a>
    707                   can ensure that your extension won't be run in an earlier browser version.
    708                 </p>
    709               </div> <!-- /description -->
    710 
    711             </div>  <!-- /apiItem -->
    712 
    713           </div>  <!-- /apiGroup -->
    714 
    715           <!-- EVENTS -->
    716           <div id="eventsTemplate" class="apiGroup">
    717             <a></a>
    718             <h3>Events</h3>
    719             <!-- iterates over all events -->
    720             <div class="apiItem">
    721               <a></a>
    722               <h4>event name</h4>
    723 
    724               <div class="summary">
    725                 <!-- Note: intentionally longer 80 columns -->
    726                 <span class="subdued">chrome.bookmarks</span><span>onEvent</span><span class="subdued">.addListener</span>(function(<span>Type param1, Type param2</span>) <span class="subdued">{...}</span>);
    727               </div>
    728 
    729               <div class="description">
    730                 <p class="todo">Undocumented.</p>
    731                 <p>
    732                   A description from the json schema def of the event goes here.
    733                 </p>
    734 
    735                 <!-- PARAMETERS -->
    736                 <div>
    737                   <h4>Parameters</h4>
    738                   <dl>
    739                     <div>
    740                       <div>
    741                       </div>
    742                     </div>
    743                   </dl>
    744                 </div>
    745               </div> <!-- /decription -->
    746 
    747             </div> <!-- /apiItem -->
    748 
    749           </div> <!-- /apiGroup -->
    750 
    751           <!-- TYPES -->
    752           <div class="apiGroup">
    753             <a name="types"></a>
    754             <h3 id="types">Types</h3>
    755 
    756             <!-- iterates over all types -->
    757             <div class="apiItem">
    758               <a></a>
    759               <h4>type name</h4>
    760 
    761               <div>
    762               </div>
    763 
    764             </div> <!-- /apiItem -->
    765 
    766           </div> <!-- /apiGroup -->
    767 
    768         </div> <!-- /apiPage -->
    769       </div> <!-- /gc-pagecontent -->
    770     </div> <!-- /g-section -->
    771   </div> <!-- /codesiteContent -->
    772     <div id="gc-footer" --="">
    773       <div class="text">
    774   <p>
    775   Except as otherwise <a href="http://code.google.com/policies.html#restrictions">noted</a>,
    776   the content of this page is licensed under the <a rel="license" href="http://creativecommons.org/licenses/by/3.0/">Creative Commons
    777   Attribution 3.0 License</a>, and code samples are licensed under the
    778   <a rel="license" href="http://code.google.com/google_bsd_license.html">BSD License</a>.
    779   </p>
    780   <p>
    781   2011 Google
    782   </p>
    783 
    784 <!-- begin analytics -->
    785 <script src="http://www.google-analytics.com/urchin.js" type="text/javascript"></script>
    786 <script src="http://www.google-analytics.com/ga.js" type="text/javascript"></script>
    787 
    788 <script type="text/javascript">
    789   // chrome doc tracking
    790   try {
    791     var engdocs = _gat._getTracker("YT-10763712-2");
    792     engdocs._trackPageview();
    793   } catch(err) {}
    794 
    795   // code.google.com site-wide tracking
    796   try {
    797     _uacct="UA-18071-1";
    798     _uanchor=1;
    799     _uff=0;
    800     urchinTracker();
    801   }
    802   catch(e) {/* urchinTracker not available. */}
    803 </script>
    804 <!-- end analytics -->
    805       </div>
    806     </div> <!-- /gc-footer -->
    807   </div> <!-- /gc-container -->
    808 </body></html>
    809