diff options
Diffstat (limited to 'chrome')
6 files changed, 140 insertions, 34 deletions
diff --git a/chrome/common/extensions/docs/examples/extensions/gdocs/chrome_ex_oauth.js b/chrome/common/extensions/docs/examples/extensions/gdocs/chrome_ex_oauth.js index 384616c..1b62882 100644 --- a/chrome/common/extensions/docs/examples/extensions/gdocs/chrome_ex_oauth.js +++ b/chrome/common/extensions/docs/examples/extensions/gdocs/chrome_ex_oauth.js @@ -32,6 +32,14 @@ function ChromeExOAuth(url_request_token, url_auth_token, url_access_token, this.key_token_secret = "oauth_token_secret"; this.callback_page = opt_args && opt_args['callback_page'] || "chrome_ex_oauth.html"; + this.auth_params = {}; + if (opt_args && opt_args['auth_params']) { + for (key in opt_args['auth_params']) { + if (opt_args['auth_params'].hasOwnProperty(key)) { + this.auth_params[key] = opt_args['auth_params'][key]; + } + } + } }; /******************************************************************************* @@ -51,20 +59,26 @@ function ChromeExOAuth(url_request_token, url_auth_token, url_access_token, * "consumer_secret" {String} OAuth consumer secret. * "scope" {String} OAuth access scope. * "app_name" {String} Application name. + * "auth_params" {Object} Additional parameters to pass to the + * Authorization token URL. For an example, 'hd', 'hl', 'btmpl': + * http://code.google.com/apis/accounts/docs/OAuth_ref.html#GetAuth * @return {ChromeExOAuth} An initialized ChromeExOAuth object. */ ChromeExOAuth.initBackgroundPage = function(oauth_config) { window.chromeExOAuthConfig = oauth_config; window.chromeExOAuth = ChromeExOAuth.fromConfig(oauth_config); window.chromeExOAuthRedirectStarted = false; + window.chromeExOAuthRequestingAccess = false; var url_match = chrome.extension.getURL(window.chromeExOAuth.callback_page); + var tabs = {}; chrome.tabs.onUpdated.addListener(function(tabId, changeInfo, tab) { if (changeInfo.url && changeInfo.url.substr(0, url_match.length) === url_match && - !window.chromeExOAuthRedirectStarted) { - window.chromeExOAuthRedirectStarted = true; - chrome.tabs.create({ 'url' : changeInfo.url }, function() { + changeInfo.url != tabs[tabId] && + window.chromeExOAuthRequestingAccess == false) { + chrome.tabs.create({ 'url' : changeInfo.url }, function(tab) { + tabs[tab.id] = tab.url; chrome.tabs.remove(tabId); }); } @@ -131,8 +145,8 @@ ChromeExOAuth.prototype.hasToken = function() { ChromeExOAuth.prototype.sendSignedRequest = function(url, callback, opt_params) { var method = opt_params && opt_params['method'] || 'GET'; - var params = opt_params && opt_params['parameters'] || {}; var body = opt_params && opt_params['body'] || null; + var params = opt_params && opt_params['parameters'] || {}; var headers = opt_params && opt_params['headers'] || {}; var signedUrl = this.signURL(url, method, params); @@ -148,7 +162,7 @@ ChromeExOAuth.prototype.sendSignedRequest = function(url, callback, * Adds the required OAuth parameters to the given url and returns the * result. Useful if you need a signed url but don't want to make an XHR * request. - * @param {String} method The HTTP method to use. + * @param {String} method The http method to use. * @param {String} url The base url of the resource you are querying. * @param {Object} opt_params Query parameters to include in the request. * @return {String} The base url plus any query params plus any OAuth params. @@ -163,7 +177,7 @@ ChromeExOAuth.prototype.signURL = function(url, method, opt_params) { var params = opt_params || {}; var result = OAuthSimple().sign({ - action: method, + action : method, path : url, parameters : params, signatures: { @@ -222,6 +236,9 @@ ChromeExOAuth.prototype.getAuthorizationHeader = function(url, method, * "consumer_secret" {String} OAuth consumer secret. * "scope" {String} OAuth access scope. * "app_name" {String} Application name. + * "auth_params" {Object} Additional parameters to pass to the + * Authorization token URL. For an example, 'hd', 'hl', 'btmpl': + * http://code.google.com/apis/accounts/docs/OAuth_ref.html#GetAuth * @return {ChromeExOAuth} An initialized ChromeExOAuth object. */ ChromeExOAuth.fromConfig = function(oauth_config) { @@ -233,7 +250,8 @@ ChromeExOAuth.fromConfig = function(oauth_config) { oauth_config['consumer_secret'], oauth_config['scope'], { - 'app_name' : oauth_config['app_name'] + 'app_name' : oauth_config['app_name'], + 'auth_params' : oauth_config['auth_params'] } ); }; @@ -244,13 +262,16 @@ ChromeExOAuth.fromConfig = function(oauth_config) { * chrome_ex_oauth.html. */ ChromeExOAuth.initCallbackPage = function() { - var oauth_config = chrome.extension.getBackgroundPage().chromeExOAuthConfig; + var background_page = chrome.extension.getBackgroundPage(); + var oauth_config = background_page.chromeExOAuthConfig; var oauth = ChromeExOAuth.fromConfig(oauth_config); + background_page.chromeExOAuthRedirectStarted = true; oauth.initOAuthFlow(function (token, secret) { - var background_page = chrome.extension.getBackgroundPage(); background_page.chromeExOAuthOnAuthorize(token, secret); background_page.chromeExOAuthRedirectStarted = false; - window.close(); + chrome.tabs.getSelected(null, function (tab) { + chrome.tabs.remove(tab.id); + }); }); }; @@ -292,7 +313,9 @@ ChromeExOAuth.formDecode = function(encoded) { for (var i = 0, param; param = params[i]; i++) { var keyval = param.split("="); if (keyval.length == 2) { - decoded[decodeURIComponent(keyval[0])] = decodeURIComponent(keyval[1]); + var key = ChromeExOAuth.fromRfc3986(keyval[0]); + var val = ChromeExOAuth.fromRfc3986(keyval[1]); + decoded[key] = val; } } return decoded; @@ -329,6 +352,33 @@ ChromeExOAuth.bind = function(func, obj) { }; /** + * Encodes a value according to the RFC3986 specification. + * @param {String} val The string to encode. + */ +ChromeExOAuth.toRfc3986 = function(val){ + return encodeURIComponent(val) + .replace(/\!/g, "%21") + .replace(/\*/g, "%2A") + .replace(/'/g, "%27") + .replace(/\(/g, "%28") + .replace(/\)/g, "%29"); +}; + +/** + * Decodes a string that has been encoded according to RFC3986. + * @param {String} val The string to decode. + */ +ChromeExOAuth.fromRfc3986 = function(val){ + var tmp = val + .replace(/%21/g, "!") + .replace(/%2A/g, "*") + .replace(/%27/g, "'") + .replace(/%28/g, "(") + .replace(/%29/g, ")"); + return decodeURIComponent(tmp); +}; + +/** * Adds a key/value parameter to the supplied URL. * @param {String} url An URL which may or may not contain querystring values. * @param {String} key A key @@ -338,7 +388,8 @@ ChromeExOAuth.bind = function(func, obj) { */ ChromeExOAuth.addURLParam = function(url, key, value) { var sep = (url.indexOf('?') >= 0) ? "&" : "?"; - return url + sep + encodeURIComponent(key) + "=" + encodeURIComponent(value); + return url + sep + + ChromeExOAuth.toRfc3986(key) + "=" + ChromeExOAuth.toRfc3986(value); }; /** @@ -465,6 +516,11 @@ ChromeExOAuth.prototype.onRequestToken = function(callback, xhr) { this.setTokenSecret(params['oauth_token_secret']); var url = ChromeExOAuth.addURLParam(this.url_auth_token, "oauth_token", token); + for (var key in this.auth_params) { + if (this.auth_params.hasOwnProperty(key)) { + url = ChromeExOAuth.addURLParam(url, key, this.auth_params[key]); + } + } callback(url); } else { throw new Error("Fetching request token failed. Status " + xhr.status); @@ -486,21 +542,26 @@ ChromeExOAuth.prototype.getAccessToken = function(oauth_token, oauth_verifier, if (typeof callback !== "function") { throw new Error("Specified callback must be a function."); } - var result = OAuthSimple().sign({ - path : this.url_access_token, - parameters: { - "oauth_token" : oauth_token, - "oauth_verifier" : oauth_verifier - }, - signatures: { - consumer_key : this.consumer_key, - shared_secret : this.consumer_secret, - oauth_secret : this.getTokenSecret(this.oauth_scope) - } - }); + var bg = chrome.extension.getBackgroundPage(); + if (bg.chromeExOAuthRequestingAccess == false) { + bg.chromeExOAuthRequestingAccess = true; + + var result = OAuthSimple().sign({ + path : this.url_access_token, + parameters: { + "oauth_token" : oauth_token, + "oauth_verifier" : oauth_verifier + }, + signatures: { + consumer_key : this.consumer_key, + shared_secret : this.consumer_secret, + oauth_secret : this.getTokenSecret(this.oauth_scope) + } + }); - var onToken = ChromeExOAuth.bind(this.onAccessToken, this, callback) - ChromeExOAuth.sendRequest("GET", result.signed_url, null, null, onToken); + var onToken = ChromeExOAuth.bind(this.onAccessToken, this, callback); + ChromeExOAuth.sendRequest("GET", result.signed_url, null, null, onToken); + } }; /** @@ -515,14 +576,17 @@ ChromeExOAuth.prototype.getAccessToken = function(oauth_token, oauth_verifier, */ ChromeExOAuth.prototype.onAccessToken = function(callback, xhr) { if (xhr.readyState == 4) { + var bg = chrome.extension.getBackgroundPage(); if (xhr.status == 200) { var params = ChromeExOAuth.formDecode(xhr.responseText); var token = params["oauth_token"]; var secret = params["oauth_token_secret"]; this.setToken(token); this.setTokenSecret(secret); + bg.chromeExOAuthRequestingAccess = false; callback(token, secret); } else { + bg.chromeExOAuthRequestingAccess = false; throw new Error("Fetching access token failed with status " + xhr.status); } } diff --git a/chrome/common/extensions/docs/examples/extensions/gdocs/manifest.json b/chrome/common/extensions/docs/examples/extensions/gdocs/manifest.json index 5e715f6..1d26f72 100644 --- a/chrome/common/extensions/docs/examples/extensions/gdocs/manifest.json +++ b/chrome/common/extensions/docs/examples/extensions/gdocs/manifest.json @@ -1,6 +1,6 @@ { "name": "Google Document List Viewer", - "version": "1.0.1", + "version": "1.0.2", "icons": { "48": "img/docs_spreadsheets-48.gif", "128": "img/docs_spreadsheets-128.gif" diff --git a/chrome/common/extensions/docs/examples/extensions/oauth_contacts/chrome_ex_oauth.js b/chrome/common/extensions/docs/examples/extensions/oauth_contacts/chrome_ex_oauth.js index 2aef56c..7e13710 100644 --- a/chrome/common/extensions/docs/examples/extensions/oauth_contacts/chrome_ex_oauth.js +++ b/chrome/common/extensions/docs/examples/extensions/oauth_contacts/chrome_ex_oauth.js @@ -32,6 +32,14 @@ function ChromeExOAuth(url_request_token, url_auth_token, url_access_token, this.key_token_secret = "oauth_token_secret"; this.callback_page = opt_args && opt_args['callback_page'] || "chrome_ex_oauth.html"; + this.auth_params = {}; + if (opt_args && opt_args['auth_params']) { + for (key in opt_args['auth_params']) { + if (opt_args['auth_params'].hasOwnProperty(key)) { + this.auth_params[key] = opt_args['auth_params'][key]; + } + } + } }; /******************************************************************************* @@ -51,6 +59,9 @@ function ChromeExOAuth(url_request_token, url_auth_token, url_access_token, * "consumer_secret" {String} OAuth consumer secret. * "scope" {String} OAuth access scope. * "app_name" {String} Application name. + * "auth_params" {Object} Additional parameters to pass to the + * Authorization token URL. For an example, 'hd', 'hl', 'btmpl': + * http://code.google.com/apis/accounts/docs/OAuth_ref.html#GetAuth * @return {ChromeExOAuth} An initialized ChromeExOAuth object. */ ChromeExOAuth.initBackgroundPage = function(oauth_config) { @@ -225,6 +236,9 @@ ChromeExOAuth.prototype.getAuthorizationHeader = function(url, method, * "consumer_secret" {String} OAuth consumer secret. * "scope" {String} OAuth access scope. * "app_name" {String} Application name. + * "auth_params" {Object} Additional parameters to pass to the + * Authorization token URL. For an example, 'hd', 'hl', 'btmpl': + * http://code.google.com/apis/accounts/docs/OAuth_ref.html#GetAuth * @return {ChromeExOAuth} An initialized ChromeExOAuth object. */ ChromeExOAuth.fromConfig = function(oauth_config) { @@ -236,7 +250,8 @@ ChromeExOAuth.fromConfig = function(oauth_config) { oauth_config['consumer_secret'], oauth_config['scope'], { - 'app_name' : oauth_config['app_name'] + 'app_name' : oauth_config['app_name'], + 'auth_params' : oauth_config['auth_params'] } ); }; @@ -501,6 +516,11 @@ ChromeExOAuth.prototype.onRequestToken = function(callback, xhr) { this.setTokenSecret(params['oauth_token_secret']); var url = ChromeExOAuth.addURLParam(this.url_auth_token, "oauth_token", token); + for (var key in this.auth_params) { + if (this.auth_params.hasOwnProperty(key)) { + url = ChromeExOAuth.addURLParam(url, key, this.auth_params[key]); + } + } callback(url); } else { throw new Error("Fetching request token failed. Status " + xhr.status); @@ -570,5 +590,4 @@ ChromeExOAuth.prototype.onAccessToken = function(callback, xhr) { throw new Error("Fetching access token failed with status " + xhr.status); } } -}; - +};
\ No newline at end of file diff --git a/chrome/common/extensions/docs/examples/extensions/oauth_contacts/manifest.json b/chrome/common/extensions/docs/examples/extensions/oauth_contacts/manifest.json index bfd2994..5f9a4a5 100644 --- a/chrome/common/extensions/docs/examples/extensions/oauth_contacts/manifest.json +++ b/chrome/common/extensions/docs/examples/extensions/oauth_contacts/manifest.json @@ -1,6 +1,6 @@ { "name": "Sample - OAuth Contacts", - "version": "1.0.5", + "version": "1.0.6", "icons": { "48": "img/icon-48.png", "128": "img/icon-128.png" }, "description": "Uses OAuth to connect to Google's contacts service and display a list of your contacts.", diff --git a/chrome/common/extensions/docs/examples/extensions/wave/chrome_ex_oauth.js b/chrome/common/extensions/docs/examples/extensions/wave/chrome_ex_oauth.js index f28111a..1b62882 100644 --- a/chrome/common/extensions/docs/examples/extensions/wave/chrome_ex_oauth.js +++ b/chrome/common/extensions/docs/examples/extensions/wave/chrome_ex_oauth.js @@ -32,6 +32,14 @@ function ChromeExOAuth(url_request_token, url_auth_token, url_access_token, this.key_token_secret = "oauth_token_secret"; this.callback_page = opt_args && opt_args['callback_page'] || "chrome_ex_oauth.html"; + this.auth_params = {}; + if (opt_args && opt_args['auth_params']) { + for (key in opt_args['auth_params']) { + if (opt_args['auth_params'].hasOwnProperty(key)) { + this.auth_params[key] = opt_args['auth_params'][key]; + } + } + } }; /******************************************************************************* @@ -51,6 +59,9 @@ function ChromeExOAuth(url_request_token, url_auth_token, url_access_token, * "consumer_secret" {String} OAuth consumer secret. * "scope" {String} OAuth access scope. * "app_name" {String} Application name. + * "auth_params" {Object} Additional parameters to pass to the + * Authorization token URL. For an example, 'hd', 'hl', 'btmpl': + * http://code.google.com/apis/accounts/docs/OAuth_ref.html#GetAuth * @return {ChromeExOAuth} An initialized ChromeExOAuth object. */ ChromeExOAuth.initBackgroundPage = function(oauth_config) { @@ -60,11 +71,14 @@ ChromeExOAuth.initBackgroundPage = function(oauth_config) { window.chromeExOAuthRequestingAccess = false; var url_match = chrome.extension.getURL(window.chromeExOAuth.callback_page); + var tabs = {}; chrome.tabs.onUpdated.addListener(function(tabId, changeInfo, tab) { if (changeInfo.url && changeInfo.url.substr(0, url_match.length) === url_match && + changeInfo.url != tabs[tabId] && window.chromeExOAuthRequestingAccess == false) { - chrome.tabs.create({ 'url' : changeInfo.url }, function() { + chrome.tabs.create({ 'url' : changeInfo.url }, function(tab) { + tabs[tab.id] = tab.url; chrome.tabs.remove(tabId); }); } @@ -222,6 +236,9 @@ ChromeExOAuth.prototype.getAuthorizationHeader = function(url, method, * "consumer_secret" {String} OAuth consumer secret. * "scope" {String} OAuth access scope. * "app_name" {String} Application name. + * "auth_params" {Object} Additional parameters to pass to the + * Authorization token URL. For an example, 'hd', 'hl', 'btmpl': + * http://code.google.com/apis/accounts/docs/OAuth_ref.html#GetAuth * @return {ChromeExOAuth} An initialized ChromeExOAuth object. */ ChromeExOAuth.fromConfig = function(oauth_config) { @@ -233,7 +250,8 @@ ChromeExOAuth.fromConfig = function(oauth_config) { oauth_config['consumer_secret'], oauth_config['scope'], { - 'app_name' : oauth_config['app_name'] + 'app_name' : oauth_config['app_name'], + 'auth_params' : oauth_config['auth_params'] } ); }; @@ -498,6 +516,11 @@ ChromeExOAuth.prototype.onRequestToken = function(callback, xhr) { this.setTokenSecret(params['oauth_token_secret']); var url = ChromeExOAuth.addURLParam(this.url_auth_token, "oauth_token", token); + for (var key in this.auth_params) { + if (this.auth_params.hasOwnProperty(key)) { + url = ChromeExOAuth.addURLParam(url, key, this.auth_params[key]); + } + } callback(url); } else { throw new Error("Fetching request token failed. Status " + xhr.status); diff --git a/chrome/common/extensions/docs/examples/extensions/wave/manifest.json b/chrome/common/extensions/docs/examples/extensions/wave/manifest.json index 34a22f7..d9af513 100644 --- a/chrome/common/extensions/docs/examples/extensions/wave/manifest.json +++ b/chrome/common/extensions/docs/examples/extensions/wave/manifest.json @@ -1,6 +1,6 @@ { "name": "Google Wave Notifier", - "version": "1.0.0", + "version": "1.0.1", "description": "Find out when you have new waves and preview them fast.", "icons": {"16": "16.png", "48": "48.png", "128": "128.png"}, "permissions": [ |