1f2477e01787aa58f445919b809d89e252beef54fTorne (Richard Coles)// Copyright 2013 The Chromium Authors. All rights reserved.
25821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// Use of this source code is governed by a BSD-style license that can be
35821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// found in the LICENSE file.
45821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
5f2477e01787aa58f445919b809d89e252beef54fTorne (Richard Coles)#include "extensions/common/feature_switch.h"
65821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
75821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include "base/command_line.h"
85821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include "base/lazy_instance.h"
95821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include "base/metrics/field_trial.h"
10868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles)#include "base/strings/string_util.h"
11424c4d7b64af9d0d8fd9624f381f469654d5e3d2Torne (Richard Coles)#include "extensions/common/switches.h"
125821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
135821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)namespace extensions {
145821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
155821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)namespace {
165821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
175821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)class CommonSwitches {
185821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) public:
195821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  CommonSwitches()
20ca12bfac764ba476d6cd062bf1dde12cc64c3f40Ben Murdoch      : easy_off_store_install(
21c5cede9ae108bb15f6b7a8aea21c7e1fefa2834cBen Murdoch            NULL,
225821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)            FeatureSwitch::DEFAULT_DISABLED),
235d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)        force_dev_mode_highlighting(
245d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)            switches::kForceDevModeHighlighting,
255d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)            FeatureSwitch::DEFAULT_DISABLED),
265821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        prompt_for_external_extensions(
27a1401311d1ab56c4ed0a474bd38c108f75cb0cd9Torne (Richard Coles)            NULL,
282a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)#if defined(OS_WIN)
29424c4d7b64af9d0d8fd9624f381f469654d5e3d2Torne (Richard Coles)            FeatureSwitch::DEFAULT_ENABLED),
302a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)#else
31424c4d7b64af9d0d8fd9624f381f469654d5e3d2Torne (Richard Coles)            FeatureSwitch::DEFAULT_DISABLED),
322a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)#endif
33424c4d7b64af9d0d8fd9624f381f469654d5e3d2Torne (Richard Coles)        error_console(
34424c4d7b64af9d0d8fd9624f381f469654d5e3d2Torne (Richard Coles)            switches::kErrorConsole,
355d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)            FeatureSwitch::DEFAULT_DISABLED),
365d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)        enable_override_bookmarks_ui(
375d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)            switches::kEnableOverrideBookmarksUI,
38cedac228d2dd51db4b79ea1e72c7f249408ee061Torne (Richard Coles)            FeatureSwitch::DEFAULT_DISABLED),
39116680a4aac90f2aa7413d9095a592090648e557Ben Murdoch        extension_action_redesign(
40116680a4aac90f2aa7413d9095a592090648e557Ben Murdoch            switches::kExtensionActionRedesign,
41116680a4aac90f2aa7413d9095a592090648e557Ben Murdoch            FeatureSwitch::DEFAULT_DISABLED),
42cedac228d2dd51db4b79ea1e72c7f249408ee061Torne (Richard Coles)        scripts_require_action(switches::kScriptsRequireAction,
43116680a4aac90f2aa7413d9095a592090648e557Ben Murdoch                               FeatureSwitch::DEFAULT_DISABLED),
44116680a4aac90f2aa7413d9095a592090648e557Ben Murdoch        embedded_extension_options(
45116680a4aac90f2aa7413d9095a592090648e557Ben Murdoch            switches::kEmbeddedExtensionOptions,
461320f92c476a1ad9d19dba2a48c72b75566198e9Primiano Tucci            FeatureSwitch::DEFAULT_DISABLED),
471320f92c476a1ad9d19dba2a48c72b75566198e9Primiano Tucci        app_view(switches::kAppView,
481320f92c476a1ad9d19dba2a48c72b75566198e9Primiano Tucci                 FeatureSwitch::DEFAULT_DISABLED),
491320f92c476a1ad9d19dba2a48c72b75566198e9Primiano Tucci        mime_handler_view(switches::kMimeHandlerView,
501320f92c476a1ad9d19dba2a48c72b75566198e9Primiano Tucci                          FeatureSwitch::DEFAULT_DISABLED) {}
515821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
52c5cede9ae108bb15f6b7a8aea21c7e1fefa2834cBen Murdoch  // Enables extensions to be easily installed from sites other than the web
53c5cede9ae108bb15f6b7a8aea21c7e1fefa2834cBen Murdoch  // store.
545821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  FeatureSwitch easy_off_store_install;
55c5cede9ae108bb15f6b7a8aea21c7e1fefa2834cBen Murdoch
565d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)  FeatureSwitch force_dev_mode_highlighting;
57c5cede9ae108bb15f6b7a8aea21c7e1fefa2834cBen Murdoch
58c5cede9ae108bb15f6b7a8aea21c7e1fefa2834cBen Murdoch  // Should we prompt the user before allowing external extensions to install?
59c5cede9ae108bb15f6b7a8aea21c7e1fefa2834cBen Murdoch  // Default is yes.
605821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  FeatureSwitch prompt_for_external_extensions;
61c5cede9ae108bb15f6b7a8aea21c7e1fefa2834cBen Murdoch
62424c4d7b64af9d0d8fd9624f381f469654d5e3d2Torne (Richard Coles)  FeatureSwitch error_console;
635d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)  FeatureSwitch enable_override_bookmarks_ui;
64116680a4aac90f2aa7413d9095a592090648e557Ben Murdoch  FeatureSwitch extension_action_redesign;
65cedac228d2dd51db4b79ea1e72c7f249408ee061Torne (Richard Coles)  FeatureSwitch scripts_require_action;
66116680a4aac90f2aa7413d9095a592090648e557Ben Murdoch  FeatureSwitch embedded_extension_options;
671320f92c476a1ad9d19dba2a48c72b75566198e9Primiano Tucci  FeatureSwitch app_view;
681320f92c476a1ad9d19dba2a48c72b75566198e9Primiano Tucci  FeatureSwitch mime_handler_view;
695821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)};
705821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
715821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)base::LazyInstance<CommonSwitches> g_common_switches =
725821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    LAZY_INSTANCE_INITIALIZER;
735821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
745821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}  // namespace
755821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
765d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)FeatureSwitch* FeatureSwitch::force_dev_mode_highlighting() {
775d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)  return &g_common_switches.Get().force_dev_mode_highlighting;
785d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)}
795821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)FeatureSwitch* FeatureSwitch::easy_off_store_install() {
805821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  return &g_common_switches.Get().easy_off_store_install;
815821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
825821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)FeatureSwitch* FeatureSwitch::prompt_for_external_extensions() {
835821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  return &g_common_switches.Get().prompt_for_external_extensions;
845821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
85424c4d7b64af9d0d8fd9624f381f469654d5e3d2Torne (Richard Coles)FeatureSwitch* FeatureSwitch::error_console() {
86424c4d7b64af9d0d8fd9624f381f469654d5e3d2Torne (Richard Coles)  return &g_common_switches.Get().error_console;
87424c4d7b64af9d0d8fd9624f381f469654d5e3d2Torne (Richard Coles)}
885d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)FeatureSwitch* FeatureSwitch::enable_override_bookmarks_ui() {
895d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)  return &g_common_switches.Get().enable_override_bookmarks_ui;
905d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)}
91116680a4aac90f2aa7413d9095a592090648e557Ben MurdochFeatureSwitch* FeatureSwitch::extension_action_redesign() {
92116680a4aac90f2aa7413d9095a592090648e557Ben Murdoch  return &g_common_switches.Get().extension_action_redesign;
93116680a4aac90f2aa7413d9095a592090648e557Ben Murdoch}
94cedac228d2dd51db4b79ea1e72c7f249408ee061Torne (Richard Coles)FeatureSwitch* FeatureSwitch::scripts_require_action() {
95cedac228d2dd51db4b79ea1e72c7f249408ee061Torne (Richard Coles)  return &g_common_switches.Get().scripts_require_action;
96cedac228d2dd51db4b79ea1e72c7f249408ee061Torne (Richard Coles)}
97116680a4aac90f2aa7413d9095a592090648e557Ben MurdochFeatureSwitch* FeatureSwitch::embedded_extension_options() {
98116680a4aac90f2aa7413d9095a592090648e557Ben Murdoch  return &g_common_switches.Get().embedded_extension_options;
99116680a4aac90f2aa7413d9095a592090648e557Ben Murdoch}
1001320f92c476a1ad9d19dba2a48c72b75566198e9Primiano TucciFeatureSwitch* FeatureSwitch::app_view() {
1011320f92c476a1ad9d19dba2a48c72b75566198e9Primiano Tucci  return &g_common_switches.Get().app_view;
1021320f92c476a1ad9d19dba2a48c72b75566198e9Primiano Tucci}
1031320f92c476a1ad9d19dba2a48c72b75566198e9Primiano TucciFeatureSwitch* FeatureSwitch::mime_handler_view() {
1041320f92c476a1ad9d19dba2a48c72b75566198e9Primiano Tucci  return &g_common_switches.Get().mime_handler_view;
1051320f92c476a1ad9d19dba2a48c72b75566198e9Primiano Tucci}
106cedac228d2dd51db4b79ea1e72c7f249408ee061Torne (Richard Coles)
1075821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)FeatureSwitch::ScopedOverride::ScopedOverride(FeatureSwitch* feature,
1085821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                                              bool override_value)
1095821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    : feature_(feature),
1105821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      previous_value_(feature->GetOverrideValue()) {
1115821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  feature_->SetOverrideValue(
1125821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      override_value ? OVERRIDE_ENABLED : OVERRIDE_DISABLED);
1135821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
1145821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
1155821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)FeatureSwitch::ScopedOverride::~ScopedOverride() {
1165821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  feature_->SetOverrideValue(previous_value_);
1175821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
1185821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
1195821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)FeatureSwitch::FeatureSwitch(const char* switch_name,
1205821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                             DefaultValue default_value) {
1215821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  Init(CommandLine::ForCurrentProcess(), switch_name, default_value);
1225821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
1235821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
1245821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)FeatureSwitch::FeatureSwitch(const CommandLine* command_line,
1255821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                             const char* switch_name,
1265821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                             DefaultValue default_value) {
1275821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  Init(command_line, switch_name, default_value);
1285821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
1295821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
1305821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)void FeatureSwitch::Init(const CommandLine* command_line,
1315821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                         const char* switch_name,
1325821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                         DefaultValue default_value) {
1335821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  command_line_ = command_line;
1345821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  switch_name_ = switch_name;
1355821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  default_value_ = default_value == DEFAULT_ENABLED;
1365821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  override_value_ = OVERRIDE_NONE;
1375821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
1385821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
1395821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)bool FeatureSwitch::IsEnabled() const {
1405821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (override_value_ != OVERRIDE_NONE)
1415821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return override_value_ == OVERRIDE_ENABLED;
1425821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
143a1401311d1ab56c4ed0a474bd38c108f75cb0cd9Torne (Richard Coles)  if (!switch_name_)
144a1401311d1ab56c4ed0a474bd38c108f75cb0cd9Torne (Richard Coles)    return default_value_;
145a1401311d1ab56c4ed0a474bd38c108f75cb0cd9Torne (Richard Coles)
1465821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  std::string temp = command_line_->GetSwitchValueASCII(switch_name_);
1475821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  std::string switch_value;
148a1401311d1ab56c4ed0a474bd38c108f75cb0cd9Torne (Richard Coles)  base::TrimWhitespaceASCII(temp, base::TRIM_ALL, &switch_value);
1495821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
1505821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (switch_value == "1")
1515821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return true;
1525821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
1535821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (switch_value == "0")
1545821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return false;
1555821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
1565821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (!default_value_ && command_line_->HasSwitch(GetLegacyEnableFlag()))
1575821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return true;
1585821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
1595821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (default_value_ && command_line_->HasSwitch(GetLegacyDisableFlag()))
1605821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return false;
1615821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
1625821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  return default_value_;
1635821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
1645821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
1655821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)std::string FeatureSwitch::GetLegacyEnableFlag() const {
166a1401311d1ab56c4ed0a474bd38c108f75cb0cd9Torne (Richard Coles)  DCHECK(switch_name_);
1675821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  return std::string("enable-") + switch_name_;
1685821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
1695821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
1705821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)std::string FeatureSwitch::GetLegacyDisableFlag() const {
171a1401311d1ab56c4ed0a474bd38c108f75cb0cd9Torne (Richard Coles)  DCHECK(switch_name_);
1725821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  return std::string("disable-") + switch_name_;
1735821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
1745821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
1755821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)void FeatureSwitch::SetOverrideValue(OverrideValue override_value) {
1765821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  override_value_ = override_value;
1775821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
1785821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
1795821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)FeatureSwitch::OverrideValue FeatureSwitch::GetOverrideValue() const {
1805821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  return override_value_;
1815821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
1825821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
1835821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}  // namespace extensions
184