blob: 1dd3040cef73bab720134e043bb7decc5e1d5341 [file] [log] [blame]
// Copyright 2019 The Chromium Authors
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.
#include "content/browser/browsing_data/browsing_data_browsertest_utils.h"
#include <memory>
#include <string>
#include <utility>
#include <vector>
#include "base/command_line.h"
#include "base/containers/heap_array.h"
#include "base/containers/span.h"
#include "base/functional/bind.h"
#include "base/run_loop.h"
#include "base/strings/string_view_util.h"
#include "components/network_session_configurator/common/network_switches.h"
#include "content/browser/browsing_data/browsing_data_test_utils.h"
#include "content/public/browser/browser_thread.h"
#include "content/public/browser/network_service_instance.h"
#include "content/public/browser/network_service_util.h"
#include "content/public/browser/service_worker_context.h"
#include "content/public/browser/storage_partition.h"
#include "content/public/browser/storage_usage_info.h"
#include "content/public/common/content_switches.h"
#include "content/public/test/content_browser_test_utils.h"
#include "mojo/public/cpp/bindings/remote.h"
#include "net/base/url_util.h"
#include "net/test/embedded_test_server/http_response.h"
#include "services/network/public/mojom/network_service.mojom.h"
#include "services/network/public/mojom/network_service_test.mojom.h"
#include "testing/gtest/include/gtest/gtest.h"
#include "third_party/blink/public/common/storage_key/storage_key.h"
#include "third_party/blink/public/mojom/service_worker/service_worker_registration_options.mojom.h"
#include "url/origin.h"
namespace content {
namespace browsing_data_browsertest_utils {
namespace {
void AddServiceWorkerCallback(blink::ServiceWorkerStatusCode status) {
ASSERT_EQ(status, blink::ServiceWorkerStatusCode::kOk);
}
void GetServiceWorkersCallback(
base::OnceClosure callback,
std::vector<StorageUsageInfo>* out_service_workers,
const std::vector<StorageUsageInfo>& service_workers) {
*out_service_workers = service_workers;
std::move(callback).Run();
}
} // namespace
// static
void ServiceWorkerActivationObserver::SignalActivation(
ServiceWorkerContextWrapper* context,
base::OnceClosure callback) {
new ServiceWorkerActivationObserver(context, std::move(callback));
}
ServiceWorkerActivationObserver::ServiceWorkerActivationObserver(
ServiceWorkerContextWrapper* context,
base::OnceClosure callback)
: context_(context),
callback_(std::move(callback)) {
scoped_observation_.Observe(context);
}
ServiceWorkerActivationObserver::~ServiceWorkerActivationObserver() {}
void ServiceWorkerActivationObserver::OnVersionStateChanged(
int64_t version_id,
const GURL& scope,
const blink::StorageKey& key,
ServiceWorkerVersion::Status) {
if (context_->GetLiveVersion(version_id)->status() ==
ServiceWorkerVersion::ACTIVATED) {
std::move(callback_).Run();
delete this;
}
}
void SetIgnoreCertificateErrors(base::CommandLine* command_line) {
if (IsOutOfProcessNetworkService()) {
// |MockCertVerifier| only seems to work when Network Service was enabled.
command_line->AppendSwitch(switches::kUseMockCertVerifierForTesting);
} else {
// We're redirecting all hosts to localhost even on HTTPS, so we'll get
// certificate errors.
command_line->AppendSwitch(switches::kIgnoreCertificateErrors);
}
}
GURL AddServiceWorker(const std::string& origin,
StoragePartition* storage_partition,
net::EmbeddedTestServer* https_server) {
DCHECK_CURRENTLY_ON(BrowserThread::UI);
ServiceWorkerContextWrapper* service_worker_context =
static_cast<ServiceWorkerContextWrapper*>(
storage_partition->GetServiceWorkerContext());
GURL scope_url = https_server->GetURL(origin, "/");
GURL js_url = https_server->GetURL(origin, "/?file=worker.js");
// Register the worker.
blink::mojom::ServiceWorkerRegistrationOptions options(
scope_url, blink::mojom::ScriptType::kClassic,
blink::mojom::ServiceWorkerUpdateViaCache::kImports);
const blink::StorageKey key =
blink::StorageKey::CreateFirstParty(url::Origin::Create(options.scope));
service_worker_context->RegisterServiceWorker(
js_url, key, options, base::BindOnce(&AddServiceWorkerCallback));
// Wait for its activation.
base::RunLoop run_loop;
ServiceWorkerActivationObserver::SignalActivation(service_worker_context,
run_loop.QuitClosure());
run_loop.Run();
return scope_url;
}
std::vector<StorageUsageInfo> GetServiceWorkers(
StoragePartition* storage_partition) {
DCHECK_CURRENTLY_ON(BrowserThread::UI);
ServiceWorkerContextWrapper* service_worker_context =
static_cast<ServiceWorkerContextWrapper*>(
storage_partition->GetServiceWorkerContext());
std::vector<StorageUsageInfo> service_workers;
base::RunLoop run_loop;
service_worker_context->GetAllStorageKeysInfo(
base::BindOnce(&GetServiceWorkersCallback, run_loop.QuitClosure(),
base::Unretained(&service_workers)));
run_loop.Run();
return service_workers;
}
void SetResponseContent(const GURL& url,
std::string* value,
net::test_server::BasicHttpResponse* response) {
if (net::GetValueForKeyInQuery(url, "file", value)) {
base::FilePath path(GetTestFilePath("browsing_data", value->c_str()));
base::File file(path, base::File::FLAG_OPEN | base::File::FLAG_READ);
EXPECT_TRUE(file.IsValid());
int64_t length = file.GetLength();
EXPECT_GE(length, 0);
auto buffer = base::HeapArray<uint8_t>::WithSize(length);
file.Read(0, buffer);
if (path.Extension() == FILE_PATH_LITERAL(".js")) {
response->set_content_type("application/javascript");
} else if (path.Extension() == FILE_PATH_LITERAL(".html")) {
response->set_content_type("text/html");
} else {
NOTREACHED();
}
response->set_content(base::as_string_view(buffer));
}
}
void SetUpMockCertVerifier(int32_t default_result) {
mojo::Remote<network::mojom::NetworkServiceTest> network_service_test;
GetNetworkService()->BindTestInterfaceForTesting(
network_service_test.BindNewPipeAndPassReceiver());
base::RunLoop run_loop(base::RunLoop::Type::kNestableTasksAllowed);
network_service_test->MockCertVerifierSetDefaultResult(
default_result, run_loop.QuitClosure());
run_loop.Run();
}
} // namespace browsing_data_browsertest_utils
} // namespace content