// Copyright 2020 The Chromium Authors
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.

#import "ios/web/public/js_messaging/java_script_feature.h"

#import <Foundation/Foundation.h>

#import "base/functional/bind.h"
#import "base/strings/sys_string_conversions.h"
#import "base/time/time.h"
#import "build/blink_buildflags.h"
#import "ios/web/javascript_flags.h"
#import "ios/web/js_messaging/java_script_content_world.h"
#import "ios/web/js_messaging/java_script_feature_manager.h"
#import "ios/web/js_messaging/page_script_util.h"
#import "ios/web/js_messaging/web_frame_internal.h"
#import "ios/web/public/js_messaging/content_world.h"
#import "ios/web/public/js_messaging/web_frame.h"
#import "ios/web/public/js_messaging/web_frames_manager.h"
#import "ios/web/public/web_state.h"

#if BUILDFLAG(ENABLE_IOS_JAVASCRIPT_FLAGS)
#import "base/command_line.h"
#import "base/strings/string_split.h"
#import "ios/web/switches.h"
#endif

namespace {

// Returns a JavaScript safe string based on `script_filename`. This is used as
// a unique identifier for a given script and passed to
// `MakeScriptInjectableOnce` which ensures JS isn't executed multiple times due
// to duplicate injection.
NSString* InjectionTokenForScript(NSString* script_filename) {
  NSMutableCharacterSet* valid_characters =
      [NSMutableCharacterSet alphanumericCharacterSet];
  [valid_characters addCharactersInString:@"$_"];
  NSCharacterSet* invalid_characters = valid_characters.invertedSet;
  NSString* token =
      [[script_filename componentsSeparatedByCharactersInSet:invalid_characters]
          componentsJoinedByString:@""];
  DCHECK_GT(token.length, 0ul);
  return token;
}

bool IsScriptEnabled(NSString* script_token) {
#if BUILDFLAG(ENABLE_IOS_JAVASCRIPT_FLAGS)
  bool disable_all_scripts = base::CommandLine::ForCurrentProcess()->HasSwitch(
      web::switches::kDisableAllInjectedScripts);
  if (disable_all_scripts) {
    return false;
  }

  bool disable_feature_scripts =
      base::CommandLine::ForCurrentProcess()->HasSwitch(
          web::switches::kDisableInjectedFeatureScripts);
  if (disable_feature_scripts) {
    return [[NSSet setWithArray:@[ @"gcrweb", @"common", @"message" ]]
        containsObject:script_token];
  }

  if (base::CommandLine::ForCurrentProcess()->HasSwitch(
          web::switches::kDisableListedScripts)) {
    std::string token = base::SysNSStringToUTF8(script_token);
    auto disable_scripts_flag =
        base::CommandLine::ForCurrentProcess()->GetSwitchValueASCII(
            web::switches::kDisableListedScripts);
    auto disable_scripts =
        base::SplitStringPiece(disable_scripts_flag, ",", base::TRIM_WHITESPACE,
                               base::SPLIT_WANT_NONEMPTY);
    if (std::find(disable_scripts.begin(), disable_scripts.end(),
                  token.c_str()) != disable_scripts.end()) {
      // `token` found in passed switch value.
      return false;
    }
    return true;
  }

  if (base::CommandLine::ForCurrentProcess()->HasSwitch(
          web::switches::kEnableListedScripts)) {
    std::string token = base::SysNSStringToUTF8(script_token);
    auto enable_scripts_flag =
        base::CommandLine::ForCurrentProcess()->GetSwitchValueASCII(
            web::switches::kEnableListedScripts);
    auto enable_scripts =
        base::SplitStringPiece(enable_scripts_flag, ",", base::TRIM_WHITESPACE,
                               base::SPLIT_WANT_NONEMPTY);
    if (std::find(enable_scripts.begin(), enable_scripts.end(),
                  token.c_str()) != enable_scripts.end()) {
      // `token` found in passed switch value.
      return true;
    }
    return false;
  }
#endif

  return true;
}

}  // namespace

namespace web {

#pragma mark - JavaScriptFeature::FeatureScript

JavaScriptFeature::FeatureScript
JavaScriptFeature::FeatureScript::CreateWithFilename(
    const std::string& filename,
    InjectionTime injection_time,
    TargetFrames target_frames,
    ReinjectionBehavior reinjection_behavior,
    const PlaceholderReplacementsCallback& replacements_callback) {
  NSString* injection_token =
      InjectionTokenForScript(base::SysUTF8ToNSString(filename));
  return JavaScriptFeature::FeatureScript(
      filename, /*script=*/std::nullopt, injection_token, injection_time,
      target_frames, reinjection_behavior, replacements_callback);
}

JavaScriptFeature::FeatureScript
JavaScriptFeature::FeatureScript::CreateWithString(
    const std::string& script,
    InjectionTime injection_time,
    TargetFrames target_frames,
    ReinjectionBehavior reinjection_behavior,
    const PlaceholderReplacementsCallback& replacements_callback) {
  NSString* unique_id = [[NSProcessInfo processInfo] globallyUniqueString];
  NSString* injection_token = InjectionTokenForScript(unique_id);
  return JavaScriptFeature::FeatureScript(
      /*filename=*/std::nullopt, script, injection_token, injection_time,
      target_frames, reinjection_behavior, replacements_callback);
}

JavaScriptFeature::FeatureScript::FeatureScript(
    std::optional<std::string> filename,
    std::optional<std::string> script,
    NSString* injection_token,
    InjectionTime injection_time,
    TargetFrames target_frames,
    ReinjectionBehavior reinjection_behavior,
    const PlaceholderReplacementsCallback& replacements_callback)
    : script_filename_(filename),
      script_(script),
      injection_token_(injection_token),
      injection_time_(injection_time),
      target_frames_(target_frames),
      reinjection_behavior_(reinjection_behavior),
      replacements_callback_(replacements_callback) {}

JavaScriptFeature::FeatureScript::FeatureScript(const FeatureScript&) = default;

JavaScriptFeature::FeatureScript& JavaScriptFeature::FeatureScript::operator=(
    const FeatureScript&) = default;

JavaScriptFeature::FeatureScript::FeatureScript(FeatureScript&&) = default;

JavaScriptFeature::FeatureScript& JavaScriptFeature::FeatureScript::operator=(
    FeatureScript&&) = default;

JavaScriptFeature::FeatureScript::~FeatureScript() = default;

NSString* JavaScriptFeature::FeatureScript::GetScriptString() const {
  if (!IsScriptEnabled(injection_token_)) {
    return @"";
  }

  NSString* script = nil;
  if (script_) {
    script = base::SysUTF8ToNSString(script_.value());
  } else {
    CHECK(script_filename_);
    script = GetPageScript(base::SysUTF8ToNSString(*script_filename_));
  }

  if (reinjection_behavior_ ==
      ReinjectionBehavior::kReinjectOnDocumentRecreation) {
    return ReplacePlaceholders(script);
  }
  // WKUserScript instances will automatically be re-injected by WebKit when the
  // document is re-created, even though the JavaScript context will not be
  // re-created. So the script needs to be wrapped in `MakeScriptInjectableOnce`
  // so that is is not re-injected.
  return MakeScriptInjectableOnce(injection_token_,
                                  ReplacePlaceholders(script));
}

NSString* JavaScriptFeature::FeatureScript::ReplacePlaceholders(
    NSString* script) const {
  if (replacements_callback_.is_null()) {
    return script;
  }

  PlaceholderReplacements replacements = replacements_callback_.Run();
  if (!replacements) {
    return script;
  }

  for (NSString* key in replacements) {
    script = [script stringByReplacingOccurrencesOfString:key
                                               withString:replacements[key]];
  }

  return script;
}

#pragma mark - JavaScriptFeature

JavaScriptFeature::JavaScriptFeature(ContentWorld supported_world)
    : supported_world_(supported_world), weak_factory_(this) {}

JavaScriptFeature::JavaScriptFeature(ContentWorld supported_world,
                                     std::vector<FeatureScript> feature_scripts)
    : supported_world_(supported_world),
      scripts_(feature_scripts),
      weak_factory_(this) {}

JavaScriptFeature::JavaScriptFeature(
    ContentWorld supported_world,
    std::vector<FeatureScript> feature_scripts,
    std::vector<const JavaScriptFeature*> dependent_features)
    : supported_world_(supported_world),
      scripts_(feature_scripts),
      dependent_features_(dependent_features),
      weak_factory_(this) {}

JavaScriptFeature::~JavaScriptFeature() = default;

ContentWorld JavaScriptFeature::GetSupportedContentWorld() const {
  return supported_world_;
}

WebFramesManager* JavaScriptFeature::GetWebFramesManager(WebState* web_state) {
  return web_state->GetWebFramesManager(GetSupportedContentWorld());
}

std::vector<JavaScriptFeature::FeatureScript> JavaScriptFeature::GetScripts()
    const {
  return scripts_;
}

std::vector<const JavaScriptFeature*> JavaScriptFeature::GetDependentFeatures()
    const {
  return dependent_features_;
}

std::optional<std::string> JavaScriptFeature::GetScriptMessageHandlerName()
    const {
  return std::nullopt;
}

std::optional<JavaScriptFeature::ScriptMessageHandler>
JavaScriptFeature::GetScriptMessageHandler() const {
  if (!GetScriptMessageHandlerName()) {
    return std::nullopt;
  }

  return base::BindRepeating(&JavaScriptFeature::ScriptMessageReceived,
                             weak_factory_.GetMutableWeakPtr());
}

void JavaScriptFeature::ScriptMessageReceived(WebState* web_state,
                                              const ScriptMessage& message) {}

bool JavaScriptFeature::CallJavaScriptFunction(
    WebFrame* web_frame,
    const std::string& function_name,
    const base::Value::List& parameters) {
  DCHECK(web_frame);

#if BUILDFLAG(USE_BLINK)
  // TODO(crbug.com/40254930): Call the ContentJavascriptFeatureManager instead.
  return false;
#else
  JavaScriptFeatureManager* feature_manager =
      JavaScriptFeatureManager::FromBrowserState(web_frame->GetBrowserState());
  DCHECK(feature_manager);

  JavaScriptContentWorld* content_world =
      feature_manager->GetContentWorldForFeature(this);
#if BUILDFLAG(ENABLE_IOS_JAVASCRIPT_FLAGS)
  // If this JavaScript feature was not registered due to a JavaScript debug
  // flag, do not attempt to call `function_name`.
  if (!content_world) {
    return false;
  }
#endif
  DCHECK(content_world);

  return web_frame->GetWebFrameInternal()->CallJavaScriptFunctionInContentWorld(
      function_name, parameters, content_world);
#endif
}

bool JavaScriptFeature::CallJavaScriptFunction(
    WebFrame* web_frame,
    const std::string& function_name,
    const base::Value::List& parameters,
    base::OnceCallback<void(const base::Value*)> callback,
    base::TimeDelta timeout) {
  DCHECK(web_frame);

#if BUILDFLAG(USE_BLINK)
  // TODO(crbug.com/40254930): Call the ContentJavascriptFeatureManager instead.
  return false;
#else
  JavaScriptFeatureManager* feature_manager =
      JavaScriptFeatureManager::FromBrowserState(web_frame->GetBrowserState());
  DCHECK(feature_manager);

  JavaScriptContentWorld* content_world =
      feature_manager->GetContentWorldForFeature(this);
#if BUILDFLAG(ENABLE_IOS_JAVASCRIPT_FLAGS)
  // If this JavaScript feature was not registered due to a JavaScript debug
  // flag, do not attempt to call `function_name`.
  if (!content_world) {
    return false;
  }
#endif
  DCHECK(content_world);

  return web_frame->GetWebFrameInternal()->CallJavaScriptFunctionInContentWorld(
      function_name, parameters, content_world, std::move(callback), timeout);
#endif
}

bool JavaScriptFeature::ExecuteJavaScript(
    WebFrame* web_frame,
    const std::u16string& script,
    ExecuteJavaScriptCallbackWithError callback) {
  DCHECK(web_frame);

#if BUILDFLAG(USE_BLINK)
  // TODO(crbug.com/40254930): Call the ContentJavascriptFeatureManager instead.
  return false;
#else
  JavaScriptFeatureManager* feature_manager =
      JavaScriptFeatureManager::FromBrowserState(web_frame->GetBrowserState());
  DCHECK(feature_manager);

  JavaScriptContentWorld* content_world =
      feature_manager->GetContentWorldForFeature(this);
#if BUILDFLAG(ENABLE_IOS_JAVASCRIPT_FLAGS)
  // If this JavaScript feature was not registered due to a JavaScript debug
  // flag, do not attempt to call `function_name`.
  if (!content_world) {
    return false;
  }
#endif
  DCHECK(content_world);

  return web_frame->GetWebFrameInternal()->ExecuteJavaScriptInContentWorld(
      script, content_world, std::move(callback));
#endif
}

}  // namespace web
