| OLD | NEW |
| 1 // Copyright (c) 2011 The Chromium Authors. All rights reserved. | 1 // Copyright (c) 2011 The Chromium Authors. All rights reserved. |
| 2 // Use of this source code is governed by a BSD-style license that can be | 2 // Use of this source code is governed by a BSD-style license that can be |
| 3 // found in the LICENSE file. | 3 // found in the LICENSE file. |
| 4 | 4 |
| 5 // This script contains privileged chrome extension related javascript APIs. | 5 // This script contains privileged chrome extension related javascript APIs. |
| 6 // It is loaded by pages whose URL has the chrome-extension protocol. | 6 // It is loaded by pages whose URL has the chrome-extension protocol. |
| 7 | 7 |
| 8 var chrome = chrome || {}; | 8 var chrome = chrome || {}; |
| 9 (function() { | 9 (function() { |
| 10 native function GetExtensionAPIDefinition(); | 10 native function GetExtensionAPIDefinition(); |
| (...skipping 107 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 118 } | 118 } |
| 119 | 119 |
| 120 if (request.callbackSchema.parameters.length > 1) { | 120 if (request.callbackSchema.parameters.length > 1) { |
| 121 throw "Callbacks may only define one parameter"; | 121 throw "Callbacks may only define one parameter"; |
| 122 } | 122 } |
| 123 | 123 |
| 124 chromeHidden.validate(callbackArgs, | 124 chromeHidden.validate(callbackArgs, |
| 125 request.callbackSchema.parameters); | 125 request.callbackSchema.parameters); |
| 126 } catch (exception) { | 126 } catch (exception) { |
| 127 return "Callback validation error during " + name + " -- " + | 127 return "Callback validation error during " + name + " -- " + |
| 128 exception; | 128 exception.stack; |
| 129 } | 129 } |
| 130 } | 130 } |
| 131 | 131 |
| 132 if (response) { | 132 if (response) { |
| 133 request.callback(callbackArgs[0]); | 133 request.callback(callbackArgs[0]); |
| 134 } else { | 134 } else { |
| 135 request.callback(); | 135 request.callback(); |
| 136 } | 136 } |
| 137 } | 137 } |
| 138 } finally { | 138 } finally { |
| (...skipping 201 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 340 | 340 |
| 341 function extendSchema(schema) { | 341 function extendSchema(schema) { |
| 342 var extendedSchema = schema.slice(); | 342 var extendedSchema = schema.slice(); |
| 343 extendedSchema.unshift({'type': 'string'}); | 343 extendedSchema.unshift({'type': 'string'}); |
| 344 return extendedSchema; | 344 return extendedSchema; |
| 345 } | 345 } |
| 346 | 346 |
| 347 var customBindings = {}; | 347 var customBindings = {}; |
| 348 | 348 |
| 349 function setupChromeSetting() { | 349 function setupChromeSetting() { |
| 350 customBindings['ChromeSetting'] = function(prefKey, valueSchema) { | 350 function ChromeSetting(prefKey, valueSchema) { |
| 351 this.get = function(details, callback) { | 351 this.get = function(details, callback) { |
| 352 var getSchema = this.parameters.get; | 352 var getSchema = this.parameters.get; |
| 353 chromeHidden.validate([details, callback], getSchema); | 353 chromeHidden.validate([details, callback], getSchema); |
| 354 return sendRequest('types.ChromeSetting.get', | 354 return sendRequest('types.ChromeSetting.get', |
| 355 [prefKey, details, callback], | 355 [prefKey, details, callback], |
| 356 extendSchema(getSchema)); | 356 extendSchema(getSchema)); |
| 357 }; | 357 }; |
| 358 this.set = function(details, callback) { | 358 this.set = function(details, callback) { |
| 359 var setSchema = this.parameters.set.slice(); | 359 var setSchema = this.parameters.set.slice(); |
| 360 setSchema[0].properties.value = valueSchema; | 360 setSchema[0].properties.value = valueSchema; |
| 361 chromeHidden.validate([details, callback], setSchema); | 361 chromeHidden.validate([details, callback], setSchema); |
| 362 return sendRequest('types.ChromeSetting.set', | 362 return sendRequest('types.ChromeSetting.set', |
| 363 [prefKey, details, callback], | 363 [prefKey, details, callback], |
| 364 extendSchema(setSchema)); | 364 extendSchema(setSchema)); |
| 365 }; | 365 }; |
| 366 this.clear = function(details, callback) { | 366 this.clear = function(details, callback) { |
| 367 var clearSchema = this.parameters.clear; | 367 var clearSchema = this.parameters.clear; |
| 368 chromeHidden.validate([details, callback], clearSchema); | 368 chromeHidden.validate([details, callback], clearSchema); |
| 369 return sendRequest('types.ChromeSetting.clear', | 369 return sendRequest('types.ChromeSetting.clear', |
| 370 [prefKey, details, callback], | 370 [prefKey, details, callback], |
| 371 extendSchema(clearSchema)); | 371 extendSchema(clearSchema)); |
| 372 }; | 372 }; |
| 373 this.onChange = new chrome.Event('types.ChromeSetting.' + prefKey + | 373 this.onChange = new chrome.Event('types.ChromeSetting.' + prefKey + |
| 374 '.onChange'); | 374 '.onChange'); |
| 375 }; | 375 }; |
| 376 customBindings['ChromeSetting'].prototype = new CustomBindingsObject(); | 376 ChromeSetting.prototype = new CustomBindingsObject(); |
| 377 customBindings['ChromeSetting'] = ChromeSetting; |
| 378 } |
| 379 |
| 380 function setupContentSetting() { |
| 381 function ContentSetting(content_type, settingSchema) { |
| 382 this.get = function(details, callback) { |
| 383 var getSchema = this.parameters.get; |
| 384 chromeHidden.validate([details, callback], getSchema); |
| 385 return sendRequest('experimental.contentSettings.get', |
| 386 [content_type, details, callback], |
| 387 extendSchema(getSchema)); |
| 388 }; |
| 389 this.set = function(details, callback) { |
| 390 var setSchema = this.parameters.set.slice(); |
| 391 setSchema[0].properties.setting = settingSchema; |
| 392 chromeHidden.validate([details, callback], setSchema); |
| 393 return sendRequest('experimental.contentSettings.set', |
| 394 [content_type, details, callback], |
| 395 extendSchema(setSchema)); |
| 396 }; |
| 397 this.clear = function(details, callback) { |
| 398 var clearSchema = this.parameters.clear; |
| 399 chromeHidden.validate([details, callback], clearSchema); |
| 400 return sendRequest('experimental.contentSettings.clear', |
| 401 [content_type, details, callback], |
| 402 extendSchema(clearSchema)); |
| 403 }; |
| 404 } |
| 405 ContentSetting.prototype = new CustomBindingsObject(); |
| 406 customBindings['ContentSetting'] = ContentSetting; |
| 377 } | 407 } |
| 378 | 408 |
| 379 // Page action events send (pageActionId, {tabId, tabUrl}). | 409 // Page action events send (pageActionId, {tabId, tabUrl}). |
| 380 function setupPageActionEvents(extensionId) { | 410 function setupPageActionEvents(extensionId) { |
| 381 var pageActions = GetCurrentPageActions(extensionId); | 411 var pageActions = GetCurrentPageActions(extensionId); |
| 382 | 412 |
| 383 var oldStyleEventName = "pageActions"; | 413 var oldStyleEventName = "pageActions"; |
| 384 // TODO(EXTENSIONS_DEPRECATED): only one page action | 414 // TODO(EXTENSIONS_DEPRECATED): only one page action |
| 385 for (var i = 0; i < pageActions.length; ++i) { | 415 for (var i = 0; i < pageActions.length; ++i) { |
| 386 // Setup events for each extension_id/page_action_id string we find. | 416 // Setup events for each extension_id/page_action_id string we find. |
| (...skipping 115 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 502 chromeHidden.onLoad.addListener(function (extensionId) { | 532 chromeHidden.onLoad.addListener(function (extensionId) { |
| 503 if (!extensionId) { | 533 if (!extensionId) { |
| 504 return; | 534 return; |
| 505 } | 535 } |
| 506 chrome.initExtension(extensionId, false, IsIncognitoProcess()); | 536 chrome.initExtension(extensionId, false, IsIncognitoProcess()); |
| 507 | 537 |
| 508 // Setup the ChromeSetting class so we can use it to construct | 538 // Setup the ChromeSetting class so we can use it to construct |
| 509 // ChromeSetting objects from the API definition. | 539 // ChromeSetting objects from the API definition. |
| 510 setupChromeSetting(); | 540 setupChromeSetting(); |
| 511 | 541 |
| 542 // Setup the ContentSetting class so we can use it to construct |
| 543 // ContentSetting objects from the API definition. |
| 544 setupContentSetting(); |
| 545 |
| 512 // |apiFunctions| is a hash of name -> object that stores the | 546 // |apiFunctions| is a hash of name -> object that stores the |
| 513 // name & definition of the apiFunction. Custom handling of api functions | 547 // name & definition of the apiFunction. Custom handling of api functions |
| 514 // is implemented by adding a "handleRequest" function to the object. | 548 // is implemented by adding a "handleRequest" function to the object. |
| 515 var apiFunctions = {}; | 549 var apiFunctions = {}; |
| 516 | 550 |
| 517 // Read api definitions and setup api functions in the chrome namespace. | 551 // Read api definitions and setup api functions in the chrome namespace. |
| 518 // TODO(rafaelw): Consider defining a json schema for an api definition | 552 // TODO(rafaelw): Consider defining a json schema for an api definition |
| 519 // and validating either here, in a unit_test or both. | 553 // and validating either here, in a unit_test or both. |
| 520 // TODO(rafaelw): Handle synchronous functions. | 554 // TODO(rafaelw): Handle synchronous functions. |
| 521 // TOOD(rafaelw): Consider providing some convenient override points | 555 // TOOD(rafaelw): Consider providing some convenient override points |
| (...skipping 72 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 594 // WebRequest events have a special structure. | 628 // WebRequest events have a special structure. |
| 595 module[eventDef.name] = new chrome.WebRequestEvent(eventName, | 629 module[eventDef.name] = new chrome.WebRequestEvent(eventName, |
| 596 eventDef.parameters, eventDef.extraParameters); | 630 eventDef.parameters, eventDef.extraParameters); |
| 597 } else { | 631 } else { |
| 598 module[eventDef.name] = new chrome.Event(eventName, | 632 module[eventDef.name] = new chrome.Event(eventName, |
| 599 eventDef.parameters); | 633 eventDef.parameters); |
| 600 } | 634 } |
| 601 }); | 635 }); |
| 602 } | 636 } |
| 603 | 637 |
| 638 function addProperties(m, def) { |
| 639 // Parse any values defined for properties. |
| 640 if (def.properties) { |
| 641 forEach(def.properties, function(prop, property) { |
| 642 var value = property.value; |
| 643 if (value) { |
| 644 if (property.type === 'integer') { |
| 645 value = parseInt(value); |
| 646 } else if (property.type === 'boolean') { |
| 647 value = value === "true"; |
| 648 } else if (property["$ref"]) { |
| 649 var constructor = customBindings[property["$ref"]]; |
| 650 var args = value; |
| 651 // For an object property, |value| is an array of constructor |
| 652 // arguments, but we want to pass the arguments directly |
| 653 // (i.e. not as an array), so we have to fake calling |new| on |
| 654 // the constructor. |
| 655 value = { __proto__: constructor.prototype }; |
| 656 constructor.apply(value, args); |
| 657 } else if (property.type === 'object') { |
| 658 // Recursively add properties. |
| 659 addProperties(value, property); |
| 660 } else if (property.type !== 'string') { |
| 661 throw "NOT IMPLEMENTED (extension_api.json error): Cannot " + |
| 662 "parse values for type \"" + property.type + "\""; |
| 663 } |
| 664 } |
| 665 if (value) { |
| 666 m[prop] = value; |
| 667 } |
| 668 }); |
| 669 } |
| 670 } |
| 604 | 671 |
| 605 // Parse any values defined for properties. | 672 addProperties(module, apiDef); |
| 606 if (apiDef.properties) { | |
| 607 forEach(apiDef.properties, function(prop, property) { | |
| 608 if (property.value) { | |
| 609 var value = property.value; | |
| 610 if (property.type === 'integer') { | |
| 611 value = parseInt(value); | |
| 612 } else if (property.type === 'boolean') { | |
| 613 value = value === "true"; | |
| 614 } else if (property["$ref"]) { | |
| 615 var constructor = customBindings[property["$ref"]]; | |
| 616 var args = value; | |
| 617 // For an object property, |value| is an array of constructor | |
| 618 // arguments, but we want to pass the arguments directly | |
| 619 // (i.e. not as an array), so we have to fake calling |new| on the | |
| 620 // constructor. | |
| 621 value = { __proto__: constructor.prototype }; | |
| 622 constructor.apply(value, args); | |
| 623 } else if (property.type !== 'string') { | |
| 624 throw "NOT IMPLEMENTED (extension_api.json error): Cannot " + | |
| 625 "parse values for type \"" + property.type + "\""; | |
| 626 } | |
| 627 module[prop] = value; | |
| 628 } | |
| 629 }); | |
| 630 } | |
| 631 | 673 |
| 632 // getTabContentses is retained for backwards compatibility | 674 // getTabContentses is retained for backwards compatibility |
| 633 // See http://crbug.com/21433 | 675 // See http://crbug.com/21433 |
| 634 chrome.extension.getTabContentses = chrome.extension.getExtensionTabs; | 676 chrome.extension.getTabContentses = chrome.extension.getExtensionTabs; |
| 635 }); | 677 }); |
| 636 | 678 |
| 637 apiFunctions["tabs.connect"].handleRequest = function(tabId, connectInfo) { | 679 apiFunctions["tabs.connect"].handleRequest = function(tabId, connectInfo) { |
| 638 var name = ""; | 680 var name = ""; |
| 639 if (connectInfo) { | 681 if (connectInfo) { |
| 640 name = connectInfo.name || name; | 682 name = connectInfo.name || name; |
| (...skipping 266 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 907 | 949 |
| 908 if (!chrome.experimental) | 950 if (!chrome.experimental) |
| 909 chrome.experimental = {}; | 951 chrome.experimental = {}; |
| 910 | 952 |
| 911 if (!chrome.experimental.accessibility) | 953 if (!chrome.experimental.accessibility) |
| 912 chrome.experimental.accessibility = {}; | 954 chrome.experimental.accessibility = {}; |
| 913 | 955 |
| 914 if (!chrome.experimental.tts) | 956 if (!chrome.experimental.tts) |
| 915 chrome.experimental.tts = {}; | 957 chrome.experimental.tts = {}; |
| 916 })(); | 958 })(); |
| OLD | NEW |