// Copyright 2019 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 "third_party/blink/renderer/modules/file_system_access/global_file_system_access.h"

#include <utility>

#include "base/notreached.h"
#include "mojo/public/cpp/bindings/pending_remote.h"
#include "mojo/public/cpp/bindings/remote.h"
#include "services/network/public/mojom/web_sandbox_flags.mojom-blink.h"
#include "third_party/blink/public/common/browser_interface_broker_proxy.h"
#include "third_party/blink/public/mojom/file_system_access/file_system_access_manager.mojom-blink-forward.h"
#include "third_party/blink/public/mojom/file_system_access/file_system_access_manager.mojom-blink.h"
#include "third_party/blink/public/mojom/file_system_access/file_system_access_manager.mojom-shared.h"
#include "third_party/blink/renderer/bindings/core/v8/script_promise.h"
#include "third_party/blink/renderer/bindings/core/v8/script_promise_resolver.h"
#include "third_party/blink/renderer/bindings/modules/v8/v8_directory_picker_options.h"
#include "third_party/blink/renderer/bindings/modules/v8/v8_file_picker_accept_type.h"
#include "third_party/blink/renderer/bindings/modules/v8/v8_open_file_picker_options.h"
#include "third_party/blink/renderer/bindings/modules/v8/v8_save_file_picker_options.h"
#include "third_party/blink/renderer/bindings/modules/v8/well_known_directory_or_file_system_handle.h"
#include "third_party/blink/renderer/core/dom/dom_exception.h"
#include "third_party/blink/renderer/core/execution_context/security_context.h"
#include "third_party/blink/renderer/core/fileapi/file_error.h"
#include "third_party/blink/renderer/core/frame/local_dom_window.h"
#include "third_party/blink/renderer/core/frame/local_frame.h"
#include "third_party/blink/renderer/core/workers/worker_global_scope.h"
#include "third_party/blink/renderer/modules/file_system_access/file_system_access_error.h"
#include "third_party/blink/renderer/modules/file_system_access/file_system_directory_handle.h"
#include "third_party/blink/renderer/modules/file_system_access/file_system_file_handle.h"
#include "third_party/blink/renderer/platform/bindings/enumeration_base.h"
#include "third_party/blink/renderer/platform/bindings/exception_state.h"
#include "third_party/blink/renderer/platform/heap/heap.h"
#include "third_party/blink/renderer/platform/network/http_parsers.h"
#include "third_party/blink/renderer/platform/weborigin/security_origin.h"
#include "third_party/blink/renderer/platform/wtf/functional.h"
#include "third_party/blink/renderer/platform/wtf/text/ascii_ctype.h"

namespace blink {

namespace {

constexpr char kDefaultStartingDirectoryId[] = "";

constexpr bool IsHTTPWhitespace(UChar chr) {
  return chr == ' ' || chr == '\n' || chr == '\t' || chr == '\r';
}

bool IsValidSuffixCodePoint(UChar chr) {
  return IsASCIIAlphanumeric(chr) || chr == '+' || chr == '.';
}

bool IsValidIdCodePoint(UChar chr) {
  return IsASCIIAlphanumeric(chr) || chr == '_' || chr == '-';
}

bool VerifyIsValidExtension(const String& extension,
                            ExceptionState& exception_state) {
  if (!extension.StartsWith(".")) {
    exception_state.ThrowTypeError("Extension '" + extension +
                                   "' must start with '.'.");
    return false;
  }
  if (!extension.IsAllSpecialCharacters<IsValidSuffixCodePoint>()) {
    exception_state.ThrowTypeError("Extension '" + extension +
                                   "' contains invalid characters.");
    return false;
  }
  if (extension.EndsWith(".")) {
    exception_state.ThrowTypeError("Extension '" + extension +
                                   "' must not end with '.'.");
    return false;
  }
  if (extension.length() > 16) {
    exception_state.ThrowTypeError("Extension '" + extension +
                                   "' cannot be longer than 16 characters.");
    return false;
  }

  return true;
}

String VerifyIsValidId(const String& id, ExceptionState& exception_state) {
  if (!id.IsAllSpecialCharacters<IsValidIdCodePoint>()) {
    exception_state.ThrowTypeError("ID '" + id +
                                   "' contains invalid characters.");
    return String();
  }
  if (id.length() > 32) {
    exception_state.ThrowTypeError("ID '" + id +
                                   "' cannot be longer than 32 characters.");
    return String();
  }

  return std::move(id);
}

bool AddExtension(const String& extension,
                  Vector<String>& extensions,
                  ExceptionState& exception_state) {
  if (!VerifyIsValidExtension(extension, exception_state))
    return false;

  extensions.push_back(extension.Substring(1));
  return true;
}

Vector<mojom::blink::ChooseFileSystemEntryAcceptsOptionPtr> ConvertAccepts(
    const HeapVector<Member<FilePickerAcceptType>>& types,
    ExceptionState& exception_state) {
  Vector<mojom::blink::ChooseFileSystemEntryAcceptsOptionPtr> result;
  result.ReserveInitialCapacity(types.size());
  for (const auto& t : types) {
    Vector<String> mimeTypes;
    mimeTypes.ReserveInitialCapacity(t->accept().size());
    Vector<String> extensions;
    for (const auto& a : t->accept()) {
      String type = a.first.StripWhiteSpace(IsHTTPWhitespace);
      if (type.IsEmpty()) {
        exception_state.ThrowTypeError("Invalid type: " + a.first);
        return {};
      }
      Vector<String> parsed_type;
      type.Split('/', true, parsed_type);
      if (parsed_type.size() != 2) {
        exception_state.ThrowTypeError("Invalid type: " + a.first);
        return {};
      }
      if (!IsValidHTTPToken(parsed_type[0])) {
        exception_state.ThrowTypeError("Invalid type: " + a.first);
        return {};
      }
      if (!IsValidHTTPToken(parsed_type[1])) {
        exception_state.ThrowTypeError("Invalid type: " + a.first);
        return {};
      }

      mimeTypes.push_back(type);
      if (a.second.IsUSVString()) {
        if (!AddExtension(a.second.GetAsUSVString(), extensions,
                          exception_state))
          return {};
      } else {
        for (const auto& extension : a.second.GetAsUSVStringSequence()) {
          if (!AddExtension(extension, extensions, exception_state))
            return {};
        }
      }
    }
    result.emplace_back(
        blink::mojom::blink::ChooseFileSystemEntryAcceptsOption::New(
            t->hasDescription() ? t->description() : g_empty_string,
            std::move(mimeTypes), std::move(extensions)));
  }
  return result;
}

void VerifyIsAllowedToShowFilePicker(const LocalDOMWindow& window,
                                     ExceptionState& exception_state) {
  if (!window.IsCurrentlyDisplayedInFrame()) {
    exception_state.ThrowDOMException(DOMExceptionCode::kAbortError, "");
    return;
  }

  if (!window.GetSecurityOrigin()->CanAccessFileSystem()) {
    if (window.IsSandboxed(network::mojom::blink::WebSandboxFlags::kOrigin)) {
      exception_state.ThrowSecurityError(
          "Sandboxed documents aren't allowed to show a file picker.");
      return;
    } else {
      exception_state.ThrowSecurityError(
          "This document isn't allowed to show a file picker.");
      return;
    }
  }

  LocalFrame* local_frame = window.GetFrame();
  if (!local_frame || local_frame->IsCrossOriginToMainFrame()) {
    exception_state.ThrowSecurityError(
        "Cross origin sub frames aren't allowed to show a file picker.");
    return;
  }

  if (!LocalFrame::HasTransientUserActivation(local_frame)) {
    exception_state.ThrowSecurityError(
        "Must be handling a user gesture to show a file picker.");
    return;
  }
}

mojom::blink::WellKnownDirectory ConvertWellKnownDirectory(
    const String& directory,
    ExceptionState& exception_state) {
  if (directory == "")
    return mojom::blink::WellKnownDirectory::kDefault;
  else if (directory == "desktop")
    return mojom::blink::WellKnownDirectory::kDirDesktop;
  else if (directory == "documents")
    return mojom::blink::WellKnownDirectory::kDirDocuments;
  else if (directory == "downloads")
    return mojom::blink::WellKnownDirectory::kDirDownloads;
  else if (directory == "music")
    return mojom::blink::WellKnownDirectory::kDirMusic;
  else if (directory == "pictures")
    return mojom::blink::WellKnownDirectory::kDirPictures;
  else if (directory == "videos")
    return mojom::blink::WellKnownDirectory::kDirVideos;

  NOTREACHED();
  return mojom::blink::WellKnownDirectory::kDefault;
}

ScriptPromise ShowFilePickerImpl(
    ScriptState* script_state,
    LocalDOMWindow& window,
    mojom::blink::FilePickerOptionsPtr options,
    mojom::blink::CommonFilePickerOptionsPtr common_options,
    bool return_as_sequence) {
  auto* resolver = MakeGarbageCollected<ScriptPromiseResolver>(script_state);
  ScriptPromise resolver_result = resolver->Promise();

  // TODO(mek): Cache mojo::Remote<mojom::blink::FileSystemAccessManager>
  // associated with an ExecutionContext, so we don't have to request a new one
  // for each operation, and can avoid code duplication between here and other
  // uses.
  mojo::Remote<mojom::blink::FileSystemAccessManager> manager;
  window.GetBrowserInterfaceBroker().GetInterface(
      manager.BindNewPipeAndPassReceiver());

  auto* raw_manager = manager.get();
  raw_manager->ChooseEntries(
      std::move(options), std::move(common_options),
      WTF::Bind(
          [](ScriptPromiseResolver* resolver,
             mojo::Remote<mojom::blink::FileSystemAccessManager>,
             bool return_as_sequence, LocalFrame* local_frame,
             mojom::blink::FileSystemAccessErrorPtr file_operation_result,
             Vector<mojom::blink::FileSystemAccessEntryPtr> entries) {
            ExecutionContext* context = resolver->GetExecutionContext();
            if (!context)
              return;
            if (file_operation_result->status !=
                mojom::blink::FileSystemAccessStatus::kOk) {
              file_system_access_error::Reject(resolver,
                                               *file_operation_result);
              return;
            }

            // While it would be better to not trust the renderer process,
            // we're doing this here to avoid potential mojo message pipe
            // ordering problems, where the frame activation state
            // reconciliation messages would compete with concurrent File
            // System Access messages to the browser.
            // TODO(https://crbug.com/1017270): Remove this after spec change,
            // or when activation moves to browser.
            LocalFrame::NotifyUserActivation(
                local_frame, mojom::blink::UserActivationNotificationType::
                                 kFileSystemAccess);

            if (return_as_sequence) {
              HeapVector<Member<FileSystemHandle>> results;
              results.ReserveInitialCapacity(entries.size());
              for (auto& entry : entries) {
                results.push_back(FileSystemHandle::CreateFromMojoEntry(
                    std::move(entry), context));
              }
              resolver->Resolve(results);
            } else {
              DCHECK_EQ(1u, entries.size());
              resolver->Resolve(FileSystemHandle::CreateFromMojoEntry(
                  std::move(entries[0]), context));
            }
          },
          WrapPersistent(resolver), std::move(manager), return_as_sequence,
          WrapPersistent(window.GetFrame())));
  return resolver_result;
}

}  // namespace

// static
ScriptPromise GlobalFileSystemAccess::showOpenFilePicker(
    ScriptState* script_state,
    LocalDOMWindow& window,
    const OpenFilePickerOptions* options,
    ExceptionState& exception_state) {
  UseCounter::Count(window, WebFeature::kFileSystemPickerMethod);

  Vector<mojom::blink::ChooseFileSystemEntryAcceptsOptionPtr> accepts;
  if (options->hasTypes())
    accepts = ConvertAccepts(options->types(), exception_state);
  if (exception_state.HadException())
    return ScriptPromise();

  if (accepts.IsEmpty() && options->excludeAcceptAllOption()) {
    exception_state.ThrowTypeError("Need at least one accepted type");
    return ScriptPromise();
  }

  String starting_directory_id = kDefaultStartingDirectoryId;
  if (options->hasId()) {
    starting_directory_id = VerifyIsValidId(options->id(), exception_state);
    if (exception_state.HadException())
      return ScriptPromise();
  }

  auto well_known_starting_directory =
      mojom::blink::WellKnownDirectory::kDefault;
  mojo::PendingRemote<blink::mojom::blink::FileSystemAccessTransferToken> token;
  if (options->hasStartIn()) {
    auto& start_in = options->startIn();
    if (start_in.IsWellKnownDirectory()) {
      well_known_starting_directory = ConvertWellKnownDirectory(
          start_in.GetAsWellKnownDirectory(), exception_state);
      if (exception_state.HadException())
        return ScriptPromise();
    }
    if (start_in.IsFileSystemHandle()) {
      token = start_in.GetAsFileSystemHandle()->Transfer();
    }
  }

  VerifyIsAllowedToShowFilePicker(window, exception_state);
  if (exception_state.HadException())
    return ScriptPromise();

  auto open_file_picker_options = mojom::blink::OpenFilePickerOptions::New(
      mojom::blink::AcceptsTypesInfo::New(std::move(accepts),
                                          !options->excludeAcceptAllOption()),
      options->multiple());

  return ShowFilePickerImpl(
      script_state, window,
      mojom::blink::FilePickerOptions::NewOpenFilePickerOptions(
          std::move(open_file_picker_options)),
      mojom::blink::CommonFilePickerOptions::New(
          std::move(starting_directory_id),
          std::move(well_known_starting_directory), std::move(token)),
      /*return_as_sequence=*/true);
}

// static
ScriptPromise GlobalFileSystemAccess::showSaveFilePicker(
    ScriptState* script_state,
    LocalDOMWindow& window,
    const SaveFilePickerOptions* options,
    ExceptionState& exception_state) {
  UseCounter::Count(window, WebFeature::kFileSystemPickerMethod);

  Vector<mojom::blink::ChooseFileSystemEntryAcceptsOptionPtr> accepts;
  if (options->hasTypes())
    accepts = ConvertAccepts(options->types(), exception_state);
  if (exception_state.HadException())
    return ScriptPromise();

  if (accepts.IsEmpty() && options->excludeAcceptAllOption()) {
    exception_state.ThrowTypeError("Need at least one accepted type");
    return ScriptPromise();
  }

  String starting_directory_id = kDefaultStartingDirectoryId;
  if (options->hasId()) {
    starting_directory_id = VerifyIsValidId(options->id(), exception_state);
    if (exception_state.HadException())
      return ScriptPromise();
  }

  auto well_known_starting_directory =
      mojom::blink::WellKnownDirectory::kDefault;
  mojo::PendingRemote<blink::mojom::blink::FileSystemAccessTransferToken> token;
  if (options->hasStartIn()) {
    auto& start_in = options->startIn();
    if (start_in.IsWellKnownDirectory()) {
      well_known_starting_directory = ConvertWellKnownDirectory(
          start_in.GetAsWellKnownDirectory(), exception_state);
      if (exception_state.HadException())
        return ScriptPromise();
    }
    if (start_in.IsFileSystemHandle()) {
      token = start_in.GetAsFileSystemHandle()->Transfer();
    }
  }

  VerifyIsAllowedToShowFilePicker(window, exception_state);
  if (exception_state.HadException())
    return ScriptPromise();

  auto save_file_picker_options = mojom::blink::SaveFilePickerOptions::New(
      mojom::blink::AcceptsTypesInfo::New(std::move(accepts),
                                          !options->excludeAcceptAllOption()),
      (options->hasSuggestedName() && !options->suggestedName().IsNull())
          ? options->suggestedName()
          : g_empty_string);
  return ShowFilePickerImpl(
      script_state, window,
      mojom::blink::FilePickerOptions::NewSaveFilePickerOptions(
          std::move(save_file_picker_options)),
      mojom::blink::CommonFilePickerOptions::New(
          std::move(starting_directory_id),
          std::move(well_known_starting_directory), std::move(token)),
      /*return_as_sequence=*/false);
}

// static
ScriptPromise GlobalFileSystemAccess::showDirectoryPicker(
    ScriptState* script_state,
    LocalDOMWindow& window,
    const DirectoryPickerOptions* options,
    ExceptionState& exception_state) {
  UseCounter::Count(window, WebFeature::kFileSystemPickerMethod);

  String starting_directory_id = kDefaultStartingDirectoryId;
  if (options->hasId()) {
    starting_directory_id = VerifyIsValidId(options->id(), exception_state);
    if (exception_state.HadException())
      return ScriptPromise();
  }

  auto well_known_starting_directory =
      mojom::blink::WellKnownDirectory::kDefault;
  mojo::PendingRemote<blink::mojom::blink::FileSystemAccessTransferToken> token;
  if (options->hasStartIn()) {
    auto& start_in = options->startIn();
    if (start_in.IsWellKnownDirectory()) {
      well_known_starting_directory = ConvertWellKnownDirectory(
          start_in.GetAsWellKnownDirectory(), exception_state);
      if (exception_state.HadException())
        return ScriptPromise();
    }
    if (start_in.IsFileSystemHandle()) {
      token = start_in.GetAsFileSystemHandle()->Transfer();
    }
  }

  VerifyIsAllowedToShowFilePicker(window, exception_state);
  if (exception_state.HadException())
    return ScriptPromise();

  auto directory_picker_options = mojom::blink::DirectoryPickerOptions::New();
  return ShowFilePickerImpl(
      script_state, window,
      mojom::blink::FilePickerOptions::NewDirectoryPickerOptions(
          std::move(directory_picker_options)),
      mojom::blink::CommonFilePickerOptions::New(
          std::move(starting_directory_id),
          std::move(well_known_starting_directory), std::move(token)),
      /*return_as_sequence=*/false);
}

}  // namespace blink
