Index: chrome/browser/extensions/api/push_messaging/push_messaging_api.cc |
diff --git a/chrome/browser/extensions/api/push_messaging/push_messaging_api.cc b/chrome/browser/extensions/api/push_messaging/push_messaging_api.cc |
deleted file mode 100644 |
index 35f4f7f3b2eb61f843f1876d8e69829e247016f7..0000000000000000000000000000000000000000 |
--- a/chrome/browser/extensions/api/push_messaging/push_messaging_api.cc |
+++ /dev/null |
@@ -1,395 +0,0 @@ |
-// Copyright (c) 2012 The Chromium Authors. All rights reserved. |
-// Use of this source code is governed by a BSD-style license that can be |
-// found in the LICENSE file. |
- |
-#include "chrome/browser/extensions/api/push_messaging/push_messaging_api.h" |
- |
-#include <set> |
- |
-#include "base/bind.h" |
-#include "base/lazy_instance.h" |
-#include "base/logging.h" |
-#include "base/strings/string_number_conversions.h" |
-#include "base/values.h" |
-#include "chrome/browser/extensions/api/push_messaging/push_messaging_invalidation_handler.h" |
-#include "chrome/browser/extensions/extension_service.h" |
-#include "chrome/browser/extensions/token_cache/token_cache_service.h" |
-#include "chrome/browser/extensions/token_cache/token_cache_service_factory.h" |
-#include "chrome/browser/invalidation/profile_invalidation_provider_factory.h" |
-#include "chrome/browser/profiles/profile.h" |
-#include "chrome/browser/signin/profile_oauth2_token_service_factory.h" |
-#include "chrome/browser/signin/signin_manager_factory.h" |
-#include "chrome/common/extensions/api/push_messaging.h" |
-#include "components/invalidation/invalidation_service.h" |
-#include "components/invalidation/profile_invalidation_provider.h" |
-#include "components/signin/core/browser/profile_oauth2_token_service.h" |
-#include "components/signin/core/browser/signin_manager.h" |
-#include "content/public/browser/browser_thread.h" |
-#include "extensions/browser/event_router.h" |
-#include "extensions/browser/extension_registry.h" |
-#include "extensions/browser/extension_registry_factory.h" |
-#include "extensions/browser/extension_system_provider.h" |
-#include "extensions/browser/extensions_browser_client.h" |
-#include "extensions/common/extension.h" |
-#include "extensions/common/permissions/api_permission.h" |
-#include "extensions/common/permissions/permissions_data.h" |
-#include "google_apis/gaia/gaia_constants.h" |
-#include "google_apis/gaia/identity_provider.h" |
- |
-using content::BrowserThread; |
- |
-namespace extensions { |
- |
-namespace { |
-const char kChannelIdSeparator[] = "/"; |
-const char kUserNotSignedIn[] = "The user is not signed in."; |
-const char kUserAccessTokenFailure[] = |
- "Cannot obtain access token for the user."; |
-const char kAPINotAvailableForUser[] = |
- "The API is not available for this user."; |
-const int kObfuscatedGaiaIdTimeoutInDays = 30; |
-const char kDeprecationMessage[] = |
- "The chrome.pushMessaging API is deprecated. Use chrome.gcm API instead."; |
-} // namespace |
- |
-namespace glue = api::push_messaging; |
- |
-PushMessagingEventRouter::PushMessagingEventRouter( |
- content::BrowserContext* context) |
- : browser_context_(context) { |
-} |
- |
-PushMessagingEventRouter::~PushMessagingEventRouter() {} |
- |
-void PushMessagingEventRouter::TriggerMessageForTest( |
- const std::string& extension_id, |
- int subchannel, |
- const std::string& payload) { |
- OnMessage(extension_id, subchannel, payload); |
-} |
- |
-void PushMessagingEventRouter::OnMessage(const std::string& extension_id, |
- int subchannel, |
- const std::string& payload) { |
- glue::Message message; |
- message.subchannel_id = subchannel; |
- message.payload = payload; |
- |
- DVLOG(2) << "PushMessagingEventRouter::OnMessage" |
- << " payload = '" << payload |
- << "' subchannel = '" << subchannel |
- << "' extension = '" << extension_id << "'"; |
- |
- scoped_ptr<base::ListValue> args(glue::OnMessage::Create(message)); |
- scoped_ptr<Event> event(new Event(glue::OnMessage::kEventName, args.Pass())); |
- event->restrict_to_browser_context = browser_context_; |
- EventRouter::Get(browser_context_) |
- ->DispatchEventToExtension(extension_id, event.Pass()); |
-} |
- |
-// GetChannelId class functions |
- |
-PushMessagingGetChannelIdFunction::PushMessagingGetChannelIdFunction() |
- : OAuth2TokenService::Consumer("push_messaging"), |
- interactive_(false) {} |
- |
-PushMessagingGetChannelIdFunction::~PushMessagingGetChannelIdFunction() {} |
- |
-bool PushMessagingGetChannelIdFunction::RunAsync() { |
- // Issue a deprecation message. |
- WriteToConsole(content::CONSOLE_MESSAGE_LEVEL_WARNING, kDeprecationMessage); |
- |
- // Fetch the function arguments. |
- scoped_ptr<glue::GetChannelId::Params> params( |
- glue::GetChannelId::Params::Create(*args_)); |
- EXTENSION_FUNCTION_VALIDATE(params.get()); |
- |
- if (params && params->interactive) { |
- interactive_ = *params->interactive; |
- } |
- |
- // Balanced in ReportResult() |
- AddRef(); |
- |
- invalidation::ProfileInvalidationProvider* invalidation_provider = |
- invalidation::ProfileInvalidationProviderFactory::GetForProfile( |
- GetProfile()); |
- if (!invalidation_provider) { |
- error_ = kAPINotAvailableForUser; |
- ReportResult(std::string(), error_); |
- return false; |
- } |
- |
- IdentityProvider* identity_provider = |
- invalidation_provider->GetInvalidationService()->GetIdentityProvider(); |
- if (!identity_provider->GetTokenService()->RefreshTokenIsAvailable( |
- identity_provider->GetActiveAccountId())) { |
- if (interactive_ && identity_provider->RequestLogin()) { |
- identity_provider->AddActiveAccountRefreshTokenObserver(this); |
- return true; |
- } else { |
- error_ = kUserNotSignedIn; |
- ReportResult(std::string(), error_); |
- return false; |
- } |
- } |
- |
- DVLOG(2) << "Logged in profile name: " << GetProfile()->GetProfileUserName(); |
- |
- StartAccessTokenFetch(); |
- return true; |
-} |
- |
-void PushMessagingGetChannelIdFunction::StartAccessTokenFetch() { |
- invalidation::ProfileInvalidationProvider* invalidation_provider = |
- invalidation::ProfileInvalidationProviderFactory::GetForProfile( |
- GetProfile()); |
- CHECK(invalidation_provider); |
- IdentityProvider* identity_provider = |
- invalidation_provider->GetInvalidationService()->GetIdentityProvider(); |
- |
- OAuth2TokenService::ScopeSet scopes = ObfuscatedGaiaIdFetcher::GetScopes(); |
- fetcher_access_token_request_ = |
- identity_provider->GetTokenService()->StartRequest( |
- identity_provider->GetActiveAccountId(), scopes, this); |
-} |
- |
-void PushMessagingGetChannelIdFunction::OnRefreshTokenAvailable( |
- const std::string& account_id) { |
- invalidation::ProfileInvalidationProvider* invalidation_provider = |
- invalidation::ProfileInvalidationProviderFactory::GetForProfile( |
- GetProfile()); |
- CHECK(invalidation_provider); |
- invalidation_provider->GetInvalidationService()->GetIdentityProvider()-> |
- RemoveActiveAccountRefreshTokenObserver(this); |
- DVLOG(2) << "Newly logged in: " << GetProfile()->GetProfileUserName(); |
- StartAccessTokenFetch(); |
-} |
- |
-void PushMessagingGetChannelIdFunction::OnGetTokenSuccess( |
- const OAuth2TokenService::Request* request, |
- const std::string& access_token, |
- const base::Time& expiration_time) { |
- DCHECK_EQ(fetcher_access_token_request_.get(), request); |
- fetcher_access_token_request_.reset(); |
- |
- StartGaiaIdFetch(access_token); |
-} |
- |
-void PushMessagingGetChannelIdFunction::OnGetTokenFailure( |
- const OAuth2TokenService::Request* request, |
- const GoogleServiceAuthError& error) { |
- DCHECK_EQ(fetcher_access_token_request_.get(), request); |
- fetcher_access_token_request_.reset(); |
- |
- // TODO(fgorski): We are currently ignoring the error passed in upon failure. |
- // It should be revisited when we are working on improving general error |
- // handling for the identity related code. |
- DVLOG(1) << "Cannot obtain access token for this user " |
- << error.error_message() << " " << error.state(); |
- error_ = kUserAccessTokenFailure; |
- ReportResult(std::string(), error_); |
-} |
- |
-void PushMessagingGetChannelIdFunction::StartGaiaIdFetch( |
- const std::string& access_token) { |
- // Start the async fetch of the Gaia Id. |
- DCHECK_CURRENTLY_ON(BrowserThread::UI); |
- fetcher_.reset(new ObfuscatedGaiaIdFetcher(this)); |
- |
- // Get the token cache and see if we have already cached a Gaia Id. |
- TokenCacheService* token_cache = |
- TokenCacheServiceFactory::GetForProfile(GetProfile()); |
- |
- // Check the cache, if we already have a Gaia ID, use it instead of |
- // fetching the ID over the network. |
- const std::string& gaia_id = |
- token_cache->RetrieveToken(GaiaConstants::kObfuscatedGaiaId); |
- if (!gaia_id.empty()) { |
- ReportResult(gaia_id, std::string()); |
- return; |
- } |
- |
- net::URLRequestContextGetter* context = GetProfile()->GetRequestContext(); |
- fetcher_->Start(context, access_token); |
-} |
- |
-void PushMessagingGetChannelIdFunction::ReportResult( |
- const std::string& gaia_id, const std::string& error_string) { |
- DCHECK_CURRENTLY_ON(BrowserThread::UI); |
- |
- BuildAndSendResult(gaia_id, error_string); |
- |
- // Cache the obfuscated ID locally. It never changes for this user, |
- // and if we call the web API too often, we get errors due to rate limiting. |
- if (!gaia_id.empty()) { |
- base::TimeDelta timeout = |
- base::TimeDelta::FromDays(kObfuscatedGaiaIdTimeoutInDays); |
- TokenCacheService* token_cache = |
- TokenCacheServiceFactory::GetForProfile(GetProfile()); |
- token_cache->StoreToken(GaiaConstants::kObfuscatedGaiaId, gaia_id, |
- timeout); |
- } |
- |
- // Balanced in RunAsync. |
- Release(); |
-} |
- |
-void PushMessagingGetChannelIdFunction::BuildAndSendResult( |
- const std::string& gaia_id, const std::string& error_message) { |
- std::string channel_id; |
- if (!gaia_id.empty()) { |
- channel_id = gaia_id; |
- channel_id += kChannelIdSeparator; |
- channel_id += extension_id(); |
- } |
- |
- // TODO(petewil): It may be a good idea to further |
- // obfuscate the channel ID to prevent the user's obfuscated Gaia Id |
- // from being readily obtained. Security review will tell us if we need to. |
- |
- // Create a ChannelId results object and set the fields. |
- glue::ChannelIdResult result; |
- result.channel_id = channel_id; |
- SetError(error_message); |
- results_ = glue::GetChannelId::Results::Create(result); |
- |
- bool success = error_message.empty() && !gaia_id.empty(); |
- SendResponse(success); |
-} |
- |
-void PushMessagingGetChannelIdFunction::OnObfuscatedGaiaIdFetchSuccess( |
- const std::string& gaia_id) { |
- ReportResult(gaia_id, std::string()); |
-} |
- |
-void PushMessagingGetChannelIdFunction::OnObfuscatedGaiaIdFetchFailure( |
- const GoogleServiceAuthError& error) { |
- std::string error_text = error.error_message(); |
- // If the error message is blank, see if we can set it from the state. |
- if (error_text.empty() && |
- (0 != error.state())) { |
- error_text = base::IntToString(error.state()); |
- } |
- |
- DVLOG(1) << "GetChannelId status: '" << error_text << "'"; |
- |
- // If we had bad credentials, try the logon again. |
- switch (error.state()) { |
- case GoogleServiceAuthError::INVALID_GAIA_CREDENTIALS: |
- case GoogleServiceAuthError::ACCOUNT_DELETED: |
- case GoogleServiceAuthError::ACCOUNT_DISABLED: { |
- invalidation::ProfileInvalidationProvider* invalidation_provider = |
- invalidation::ProfileInvalidationProviderFactory::GetForProfile( |
- GetProfile()); |
- CHECK(invalidation_provider); |
- if (!interactive_ || !invalidation_provider->GetInvalidationService()-> |
- GetIdentityProvider()->RequestLogin()) { |
- ReportResult(std::string(), error_text); |
- } |
- return; |
- } |
- default: |
- // Return error to caller. |
- ReportResult(std::string(), error_text); |
- return; |
- } |
-} |
- |
-PushMessagingAPI::PushMessagingAPI(content::BrowserContext* context) |
- : extension_registry_observer_(this), browser_context_(context) { |
- extension_registry_observer_.Add(ExtensionRegistry::Get(browser_context_)); |
-} |
- |
-PushMessagingAPI::~PushMessagingAPI() { |
-} |
- |
-// static |
-PushMessagingAPI* PushMessagingAPI::Get(content::BrowserContext* context) { |
- return BrowserContextKeyedAPIFactory<PushMessagingAPI>::Get(context); |
-} |
- |
-void PushMessagingAPI::Shutdown() { |
- event_router_.reset(); |
- handler_.reset(); |
-} |
- |
-static base::LazyInstance<BrowserContextKeyedAPIFactory<PushMessagingAPI> > |
- g_factory = LAZY_INSTANCE_INITIALIZER; |
- |
-// static |
-BrowserContextKeyedAPIFactory<PushMessagingAPI>* |
-PushMessagingAPI::GetFactoryInstance() { |
- return g_factory.Pointer(); |
-} |
- |
-bool PushMessagingAPI::InitEventRouterAndHandler() { |
- invalidation::ProfileInvalidationProvider* invalidation_provider = |
- invalidation::ProfileInvalidationProviderFactory::GetForProfile( |
- Profile::FromBrowserContext(browser_context_)); |
- if (!invalidation_provider) |
- return false; |
- |
- if (!event_router_) |
- event_router_.reset(new PushMessagingEventRouter(browser_context_)); |
- if (!handler_) { |
- handler_.reset(new PushMessagingInvalidationHandler( |
- invalidation_provider->GetInvalidationService(), |
- event_router_.get())); |
- } |
- |
- return true; |
-} |
- |
-void PushMessagingAPI::OnExtensionLoaded( |
- content::BrowserContext* browser_context, |
- const Extension* extension) { |
- if (!InitEventRouterAndHandler()) |
- return; |
- |
- if (extension->permissions_data()->HasAPIPermission( |
- APIPermission::kPushMessaging)) { |
- handler_->RegisterExtension(extension->id()); |
- } |
-} |
- |
-void PushMessagingAPI::OnExtensionUnloaded( |
- content::BrowserContext* browser_context, |
- const Extension* extension, |
- UnloadedExtensionInfo::Reason reason) { |
- if (!InitEventRouterAndHandler()) |
- return; |
- |
- if (extension->permissions_data()->HasAPIPermission( |
- APIPermission::kPushMessaging)) { |
- handler_->UnregisterExtension(extension->id()); |
- } |
-} |
- |
-void PushMessagingAPI::OnExtensionWillBeInstalled( |
- content::BrowserContext* browser_context, |
- const Extension* extension, |
- bool is_update, |
- bool from_ephemeral, |
- const std::string& old_name) { |
- if (InitEventRouterAndHandler() && |
- extension->permissions_data()->HasAPIPermission( |
- APIPermission::kPushMessaging)) { |
- handler_->SuppressInitialInvalidationsForExtension(extension->id()); |
- } |
-} |
- |
-void PushMessagingAPI::SetMapperForTest( |
- scoped_ptr<PushMessagingInvalidationMapper> mapper) { |
- handler_ = mapper.Pass(); |
-} |
- |
-template <> |
-void |
-BrowserContextKeyedAPIFactory<PushMessagingAPI>::DeclareFactoryDependencies() { |
- DependsOn(ExtensionRegistryFactory::GetInstance()); |
- DependsOn(ExtensionsBrowserClient::Get()->GetExtensionSystemFactory()); |
- DependsOn(invalidation::ProfileInvalidationProviderFactory::GetInstance()); |
-} |
- |
-} // namespace extensions |