Chromium Code Reviews
chromiumcodereview-hr@appspot.gserviceaccount.com (chromiumcodereview-hr) | Please choose your nickname with Settings | Help | Chromium Project | Gerrit Changes | Sign out
(336)

Unified Diff: net/url_request/url_request_file_job_unittest.cc

Issue 227943003: Add experiment to measure time to hash extension content as we read it (Closed) Base URL: svn://svn.chromium.org/chrome/trunk/src
Patch Set: responded to review comments Created 6 years, 8 months ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View side-by-side diff with in-line comments
Download patch
« no previous file with comments | « net/url_request/url_request_file_job.cc ('k') | no next file » | no next file with comments »
Expand Comments ('e') | Collapse Comments ('c') | Show Comments Hide Comments ('s')
Index: net/url_request/url_request_file_job_unittest.cc
diff --git a/net/url_request/url_request_file_job_unittest.cc b/net/url_request/url_request_file_job_unittest.cc
new file mode 100644
index 0000000000000000000000000000000000000000..4b329ca0297a7406639a4ac570527e4e9a11161e
--- /dev/null
+++ b/net/url_request/url_request_file_job_unittest.cc
@@ -0,0 +1,256 @@
+// Copyright 2014 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 "net/url_request/url_request_file_job.h"
+
+#include "base/file_util.h"
+#include "base/files/scoped_temp_dir.h"
+#include "base/run_loop.h"
+#include "base/strings/stringprintf.h"
+#include "base/threading/sequenced_worker_pool.h"
+#include "net/base/net_util.h"
+#include "net/url_request/url_request_test_util.h"
+#include "testing/gtest/include/gtest/gtest.h"
+
+namespace {
+
+// A URLRequestFileJob for testing OnSeekComplete / OnReadComplete callbacks.
+class URLRequestFileJobWithCallbacks : public net::URLRequestFileJob {
+ public:
+ URLRequestFileJobWithCallbacks(
+ net::URLRequest* request,
+ net::NetworkDelegate* network_delegate,
+ const base::FilePath& file_path,
+ const scoped_refptr<base::TaskRunner>& file_task_runner)
+ : URLRequestFileJob(request,
+ network_delegate,
+ file_path,
+ file_task_runner),
+ seek_position_(0) {
+ }
+
+ int64 seek_position() { return seek_position_; }
+ const std::vector<std::string>& data_chunks() { return data_chunks_; }
+
+ protected:
+ virtual ~URLRequestFileJobWithCallbacks() {}
+
+ virtual void OnSeekComplete(int64 result) OVERRIDE {
+ ASSERT_EQ(seek_position_, 0);
+ seek_position_ = result;
+ }
+
+ virtual void OnReadComplete(net::IOBuffer* buf, int result) OVERRIDE {
+ data_chunks_.push_back(std::string(buf->data(), result));
+ }
+
+ int64 seek_position_;
+ std::vector<std::string> data_chunks_;
+};
+
+// A URLRequestJobFactory that will return URLRequestFileJobWithCallbacks
+// instances for file:// scheme URLs.
+class CallbacksJobFactory : public net::URLRequestJobFactory {
+ public:
+ class JobObserver {
+ public:
+ virtual void OnJobCreated(URLRequestFileJobWithCallbacks* job) = 0;
+ };
+
+ CallbacksJobFactory(const base::FilePath& path, JobObserver* observer)
+ : path_(path), observer_(observer) {
+ }
+
+ virtual ~CallbacksJobFactory() {}
+
+ virtual net::URLRequestJob* MaybeCreateJobWithProtocolHandler(
+ const std::string& scheme,
+ net::URLRequest* request,
+ net::NetworkDelegate* network_delegate) const OVERRIDE {
+ URLRequestFileJobWithCallbacks* job = new URLRequestFileJobWithCallbacks(
+ request,
+ network_delegate,
+ path_,
+ base::MessageLoop::current()->message_loop_proxy());
+ observer_->OnJobCreated(job);
+ return job;
+ }
+
+ virtual bool IsHandledProtocol(const std::string& scheme) const OVERRIDE {
+ return scheme == "file";
+ }
+
+ virtual bool IsHandledURL(const GURL& url) const OVERRIDE {
+ return IsHandledProtocol(url.scheme());
+ }
+
+ virtual bool IsSafeRedirectTarget(const GURL& location) const OVERRIDE {
+ return false;
+ }
+
+ private:
+ base::FilePath path_;
+ JobObserver* observer_;
+};
+
+// Helper function to create a file in |directory| named |filename| filled with
+// |content|. Returns true on succes and fills in |path| with the full path to
+// the file. If |directory| does not exist yet, it will be created.
+bool CreateTempFileWithContent(const std::string& filename,
+ const std::string& content,
+ base::ScopedTempDir* directory,
+ base::FilePath* path) {
+ if (directory == NULL || path == NULL || !IsStringASCII(filename))
+ return false;
+ if (!directory->IsValid() && !directory->CreateUniqueTempDir())
+ return false;
+ *path = directory->path().AppendASCII(filename);
+
+ if (!base::CreateTemporaryFileInDir(directory->path(), path))
rvargas (doing something else) 2014/04/09 23:48:50 doing this makes some of the code above redundant
asargent_no_longer_on_chrome 2014/04/10 00:17:27 Yep, good catch. I've further simplified it - made
+ return false;
+
+ return base::WriteFile(*path, content.c_str(), content.length());
+}
+
+class JobObserverImpl : public CallbacksJobFactory::JobObserver {
+ public:
+ virtual void OnJobCreated(URLRequestFileJobWithCallbacks* job) OVERRIDE {
+ jobs_.push_back(job);
+ }
+
+ typedef std::vector<scoped_refptr<URLRequestFileJobWithCallbacks> > JobList;
+
+ const JobList& jobs() { return jobs_; }
+
+ protected:
+ JobList jobs_;
+};
+
+// A simple holder for start/end used in http range requests.
+struct Range {
+ int start;
+ int end;
+
+ Range() {
+ start = 0;
+ end = 0;
+ }
+
+ Range(int start, int end) {
+ this->start = start;
+ this->end = end;
+ }
+};
+
+// A superclass for tests of the OnSeekComplete / OnReadComplete functions of
+// URLRequestFileJob.
+class URLRequestFileJobEventsTest : public testing::Test {
+ public:
+ URLRequestFileJobEventsTest();
+
+ protected:
+ // This creates a file with |content| as the contents, and then creates and
+ // runs a URLRequestFileJobWithCallbacks job to get the contents out of it,
+ // and makes sure that the callbacks observed the correct bytes. If a Range
+ // is provided, this function will add the appropriate Range http header to
+ // the request and verify that only the bytes in that range (inclusive) were
+ // observed.
+ void RunRequest(const std::string& content, const Range* range);
+
+ JobObserverImpl observer_;
+ net::TestURLRequestContext context_;
+ net::TestDelegate delegate_;
+};
+
+URLRequestFileJobEventsTest::URLRequestFileJobEventsTest() {}
+
+void URLRequestFileJobEventsTest::RunRequest(const std::string& content,
+ const Range* range) {
+ base::ScopedTempDir directory;
+ base::FilePath path;
+ ASSERT_TRUE(
+ CreateTempFileWithContent("file.dat", content, &directory, &path));
+ CallbacksJobFactory factory(path, &observer_);
+ context_.set_job_factory(&factory);
+
+ net::TestURLRequest request(net::FilePathToFileURL(path),
+ net::DEFAULT_PRIORITY,
+ &delegate_,
+ &context_);
+ if (range) {
+ ASSERT_GE(range->start, 0);
+ ASSERT_GE(range->end, 0);
+ ASSERT_LE(range->start, range->end);
+ ASSERT_LT(static_cast<unsigned int>(range->end), content.length());
+ std::string range_value =
+ base::StringPrintf("bytes=%d-%d", range->start, range->end);
+ request.SetExtraRequestHeaderByName(
+ net::HttpRequestHeaders::kRange, range_value, true /*overwrite*/);
+ }
+ request.Start();
+
+ base::RunLoop loop;
+ loop.Run();
+
+ EXPECT_FALSE(delegate_.request_failed());
+ int expected_length =
+ range ? (range->end - range->start + 1) : content.length();
+ EXPECT_EQ(delegate_.bytes_received(), expected_length);
+
+ std::string expected_content;
+ if (range) {
+ expected_content.insert(0, content, range->start, expected_length);
+ } else {
+ expected_content = content;
+ }
+ EXPECT_TRUE(delegate_.data_received() == expected_content);
+
+ ASSERT_EQ(observer_.jobs().size(), 1u);
+ ASSERT_EQ(observer_.jobs().at(0)->seek_position(), range ? range->start : 0);
+
+ std::string observed_content;
+ const std::vector<std::string>& chunks =
+ observer_.jobs().at(0)->data_chunks();
+ for (std::vector<std::string>::const_iterator i = chunks.begin();
+ i != chunks.end();
+ ++i) {
+ observed_content.append(*i);
+ }
+ EXPECT_EQ(expected_content, observed_content);
+ EXPECT_TRUE(expected_content == observed_content);
+}
+
+// Helper function to make a character array filled with |size| bytes of
+// test content.
+std::string MakeContentOfSize(int size) {
+ EXPECT_GE(size, 0);
+ std::string result;
+ result.reserve(size);
+ for (int i = 0; i < size; i++) {
+ result.append(1, static_cast<char>(i % 256));
+ }
+ return result;
+}
+
+} // namespace
+
+TEST_F(URLRequestFileJobEventsTest, TinyFile) {
+ RunRequest(std::string("hello world"), NULL);
+}
+
+TEST_F(URLRequestFileJobEventsTest, SmallFile) {
+ RunRequest(MakeContentOfSize(17 * 1024), NULL);
+}
+
+TEST_F(URLRequestFileJobEventsTest, BigFile) {
+ RunRequest(MakeContentOfSize(3 * 1024 * 1024), NULL);
+}
+
+TEST_F(URLRequestFileJobEventsTest, Range) {
+ // Use a 15KB content file and read a range chosen somewhat arbitrarily but
+ // not aligned on any likely page boundaries.
+ int size = 15 * 1024;
+ Range range(1701, (6 * 1024) + 3);
+ RunRequest(MakeContentOfSize(size), &range);
+}
« no previous file with comments | « net/url_request/url_request_file_job.cc ('k') | no next file » | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698