Skip loading installed extensions when --install-from-webstore is active.

Loading installed extensions was interfering in a bad way with the --install-from-webstore abbreviated workflow. In particular, if an extension subscribed to the onStartup event and showed some UI when it came:
1) The UI was disabled, while the modal install dialog was active.
2) DCHECK in ProfileDestroyer would fire when Install or Cancel was clicked in the dialog.
3) As a result, the new extension wouldn't get installed.

Since loading installed extensions makes little sense for the --install-from-webstore workflow, there is no harm in just not loading them.

BUG=164183


Review URL: https://chromiumcodereview.appspot.com/12858005

git-svn-id: svn://svn.chromium.org/chrome/trunk/src@191964 0039d316-1c4b-4281-b951-d872f2087c98
diff --git a/chrome/browser/extensions/extension_service.cc b/chrome/browser/extensions/extension_service.cc
index e6f28b7..63c35b27 100644
--- a/chrome/browser/extensions/extension_service.cc
+++ b/chrome/browser/extensions/extension_service.cc
@@ -576,41 +576,45 @@
   DCHECK(!ready_);  // Can't redo init.
   DCHECK_EQ(extensions_.size(), 0u);
 
-  CHECK(!ProfileManager::IsImportProcess(*CommandLine::ForCurrentProcess()));
+  const CommandLine* cmd_line = CommandLine::ForCurrentProcess();
 
-  // TODO(mek): It might be cleaner to do the FinishDelayedInstallInfo stuff
-  // here instead of in installedloader.
-  if (g_browser_process->profile_manager() &&
-      g_browser_process->profile_manager()->will_import()) {
-    // Do not load any component extensions, since they may conflict with the
-    // import process.
+  CHECK(!ProfileManager::IsImportProcess(*cmd_line));
 
-    extensions::InstalledLoader(this).LoadAllExtensions();
-    RegisterForImportFinished();
+  if (cmd_line->HasSwitch(switches::kInstallFromWebstore) ||
+      cmd_line->HasSwitch(switches::kLimitedInstallFromWebstore)) {
+    // The sole purpose of this launch is to install a new extension from CWS
+    // and immediately terminate: loading already installed extensions is
+    // unnecessary and may interfere with the inline install dialog (e.g. if an
+    // extension listens to onStartup and opens a window).
+    SetReadyAndNotifyListeners();
   } else {
-    component_loader_->LoadAll();
-    extensions::InstalledLoader(this).LoadAllExtensions();
+    // TODO(mek): It might be cleaner to do the FinishDelayedInstallInfo stuff
+    // here instead of in installedloader.
+    if (g_browser_process->profile_manager() &&
+        g_browser_process->profile_manager()->will_import()) {
+      // Do not load any component extensions, since they may conflict with the
+      // import process.
 
-    // TODO(erikkay) this should probably be deferred to a future point
-    // rather than running immediately at startup.
-    CheckForExternalUpdates();
+      extensions::InstalledLoader(this).LoadAllExtensions();
+      RegisterForImportFinished();
+    } else {
+      // In this case, LoadAllExtensions() calls OnLoadedInstalledExtensions(),
+      // which calls SetReadyAndNotifyListeners().
+      component_loader_->LoadAll();
+      extensions::InstalledLoader(this).LoadAllExtensions();
 
-    // TODO(erikkay) this should probably be deferred as well.
-    GarbageCollectExtensions();
-  }
+      // TODO(erikkay) this should probably be deferred to a future point
+      // rather than running immediately at startup.
+      CheckForExternalUpdates();
 
-  // The Sideload Wipeout effort takes place during load (see above), so once
-  // that is done the flag can be set so that we don't have to check again.
-  if (wipeout_is_active_) {
-    extension_prefs_->SetSideloadWipeoutDone();
-    wipeout_is_active_ = false;  // Wipeout is only on during load.
-    UMA_HISTOGRAM_BOOLEAN("DisabledExtension.SideloadWipeoutNeeded",
-                          wipeout_count_ > 0u);
-  }
+      // TODO(erikkay) this should probably be deferred as well.
+      GarbageCollectExtensions();
+    }
 
-  if (extension_prefs_->NeedsStorageGarbageCollection()) {
-    GarbageCollectIsolatedStorage();
-    extension_prefs_->SetNeedsStorageGarbageCollection(false);
+    if (extension_prefs_->NeedsStorageGarbageCollection()) {
+      GarbageCollectIsolatedStorage();
+      extension_prefs_->SetNeedsStorageGarbageCollection(false);
+    }
   }
 }
 
@@ -2011,17 +2015,30 @@
   }
 }
 
+void ExtensionService::SetReadyAndNotifyListeners() {
+  ready_ = true;
+  content::NotificationService::current()->Notify(
+      chrome::NOTIFICATION_EXTENSIONS_READY,
+      content::Source<Profile>(profile_),
+      content::NotificationService::NoDetails());
+}
+
 void ExtensionService::OnLoadedInstalledExtensions() {
   if (updater_.get())
     updater_->Start();
 
   OnBlacklistUpdated();
 
-  ready_ = true;
-  content::NotificationService::current()->Notify(
-      chrome::NOTIFICATION_EXTENSIONS_READY,
-      content::Source<Profile>(profile_),
-      content::NotificationService::NoDetails());
+  // The Sideload Wipeout effort takes place during load (see above), so once
+  // that is done the flag can be set so that we don't have to check again.
+  if (wipeout_is_active_) {
+    extension_prefs_->SetSideloadWipeoutDone();
+    wipeout_is_active_ = false;  // Wipeout is only on during load.
+    UMA_HISTOGRAM_BOOLEAN("DisabledExtension.SideloadWipeoutNeeded",
+                          wipeout_count_ > 0u);
+  }
+
+  SetReadyAndNotifyListeners();
 }
 
 void ExtensionService::AddExtension(const Extension* extension) {