1 // Copyright 2013 The Chromium Authors. All rights reserved.
2 // Use of this source code is governed by a BSD-style license that can be
3 // found in the LICENSE file.
5 #include "base/files/file_util.h"
6 #include "base/files/scoped_temp_dir.h"
7 #include "base/message_loop/message_loop.h"
8 #include "base/run_loop.h"
9 #include "chrome/browser/extensions/api/image_writer_private/error_messages.h"
10 #include "chrome/browser/extensions/api/image_writer_private/operation.h"
11 #include "chrome/browser/extensions/api/image_writer_private/operation_manager.h"
12 #include "chrome/browser/extensions/api/image_writer_private/test_utils.h"
13 #include "chrome/test/base/testing_profile.h"
14 #include "content/public/browser/browser_thread.h"
15 #include "content/public/test/test_browser_thread_bundle.h"
16 #include "testing/gmock/include/gmock/gmock.h"
17 #include "testing/gtest/include/gtest/gtest.h"
18 #include "third_party/zlib/google/zip.h"
20 namespace extensions {
21 namespace image_writer {
26 using testing::AnyNumber;
27 using testing::AtLeast;
31 // This class gives us a generic Operation with the ability to set or inspect
32 // the current path to the image file.
33 class OperationForTest : public Operation {
35 OperationForTest(base::WeakPtr<OperationManager> manager_,
36 const ExtensionId& extension_id,
37 const std::string& device_path)
38 : Operation(manager_, extension_id, device_path) {}
40 virtual void StartImpl() OVERRIDE {}
42 // Expose internal stages for testing.
43 void Unzip(const base::Closure& continuation) {
44 Operation::Unzip(continuation);
47 void Write(const base::Closure& continuation) {
48 Operation::Write(continuation);
51 void VerifyWrite(const base::Closure& continuation) {
52 Operation::VerifyWrite(continuation);
55 // Helpers to set-up state for intermediate stages.
56 void SetImagePath(const base::FilePath image_path) {
57 image_path_ = image_path;
60 base::FilePath GetImagePath() { return image_path_; }
63 virtual ~OperationForTest() {};
66 class ImageWriterOperationTest : public ImageWriterUnitTestBase {
68 ImageWriterOperationTest()
69 : profile_(new TestingProfile), manager_(profile_.get()) {}
70 virtual void SetUp() OVERRIDE {
71 ImageWriterUnitTestBase::SetUp();
73 // Create the zip file.
74 base::FilePath image_dir = test_utils_.GetTempDir().AppendASCII("zip");
75 ASSERT_TRUE(base::CreateDirectory(image_dir));
76 ASSERT_TRUE(base::CreateTemporaryFileInDir(image_dir, &image_path_));
78 test_utils_.FillFile(image_path_, kImagePattern, kTestFileSize);
80 zip_file_ = test_utils_.GetTempDir().AppendASCII("test_image.zip");
81 ASSERT_TRUE(zip::Zip(image_dir, zip_file_, true));
85 new OperationForTest(manager_.AsWeakPtr(),
87 test_utils_.GetDevicePath().AsUTF8Unsafe());
88 operation_->SetImagePath(test_utils_.GetImagePath());
91 virtual void TearDown() OVERRIDE {
92 // Ensure all callbacks have been destroyed and cleanup occurs.
95 ImageWriterUnitTestBase::TearDown();
98 base::FilePath image_path_;
99 base::FilePath zip_file_;
101 scoped_ptr<TestingProfile> profile_;
103 MockOperationManager manager_;
104 scoped_refptr<OperationForTest> operation_;
109 // Unizpping a non-zip should do nothing.
110 TEST_F(ImageWriterOperationTest, UnzipNonZipFile) {
111 EXPECT_CALL(manager_, OnProgress(kDummyExtensionId, _, _)).Times(0);
113 EXPECT_CALL(manager_, OnError(kDummyExtensionId, _, _, _)).Times(0);
114 EXPECT_CALL(manager_, OnProgress(kDummyExtensionId, _, _)).Times(0);
115 EXPECT_CALL(manager_, OnComplete(kDummyExtensionId)).Times(0);
118 content::BrowserThread::PostTask(
119 content::BrowserThread::FILE,
122 &OperationForTest::Unzip, operation_, base::Bind(&base::DoNothing)));
124 base::RunLoop().RunUntilIdle();
127 TEST_F(ImageWriterOperationTest, UnzipZipFile) {
128 EXPECT_CALL(manager_, OnError(kDummyExtensionId, _, _, _)).Times(0);
129 EXPECT_CALL(manager_,
130 OnProgress(kDummyExtensionId, image_writer_api::STAGE_UNZIP, _))
132 EXPECT_CALL(manager_,
133 OnProgress(kDummyExtensionId, image_writer_api::STAGE_UNZIP, 0))
135 EXPECT_CALL(manager_,
136 OnProgress(kDummyExtensionId, image_writer_api::STAGE_UNZIP, 100))
139 operation_->SetImagePath(zip_file_);
142 content::BrowserThread::PostTask(
143 content::BrowserThread::FILE,
146 &OperationForTest::Unzip, operation_, base::Bind(&base::DoNothing)));
148 base::RunLoop().RunUntilIdle();
150 EXPECT_TRUE(base::ContentsEqual(image_path_, operation_->GetImagePath()));
153 #if defined(OS_LINUX)
154 TEST_F(ImageWriterOperationTest, WriteImageToDevice) {
155 EXPECT_CALL(manager_, OnError(kDummyExtensionId, _, _, _)).Times(0);
156 EXPECT_CALL(manager_,
157 OnProgress(kDummyExtensionId, image_writer_api::STAGE_WRITE, _))
159 EXPECT_CALL(manager_,
160 OnProgress(kDummyExtensionId, image_writer_api::STAGE_WRITE, 0))
162 EXPECT_CALL(manager_,
163 OnProgress(kDummyExtensionId, image_writer_api::STAGE_WRITE, 100))
167 content::BrowserThread::PostTask(
168 content::BrowserThread::FILE,
171 &OperationForTest::Write, operation_, base::Bind(&base::DoNothing)));
173 base::RunLoop().RunUntilIdle();
175 #if !defined(OS_CHROMEOS)
176 test_utils_.GetUtilityClient()->Progress(0);
177 test_utils_.GetUtilityClient()->Progress(kTestFileSize / 2);
178 test_utils_.GetUtilityClient()->Progress(kTestFileSize);
179 test_utils_.GetUtilityClient()->Success();
181 base::RunLoop().RunUntilIdle();
186 #if !defined(OS_CHROMEOS)
187 // Chrome OS doesn't support verification in the ImageBurner, so these two tests
190 TEST_F(ImageWriterOperationTest, VerifyFileSuccess) {
191 EXPECT_CALL(manager_, OnError(kDummyExtensionId, _, _, _)).Times(0);
194 OnProgress(kDummyExtensionId, image_writer_api::STAGE_VERIFYWRITE, _))
198 OnProgress(kDummyExtensionId, image_writer_api::STAGE_VERIFYWRITE, 0))
202 OnProgress(kDummyExtensionId, image_writer_api::STAGE_VERIFYWRITE, 100))
205 test_utils_.FillFile(
206 test_utils_.GetDevicePath(), kImagePattern, kTestFileSize);
209 content::BrowserThread::PostTask(content::BrowserThread::FILE,
211 base::Bind(&OperationForTest::VerifyWrite,
213 base::Bind(&base::DoNothing)));
215 base::RunLoop().RunUntilIdle();
217 #if !defined(OS_CHROMEOS)
218 test_utils_.GetUtilityClient()->Progress(0);
219 test_utils_.GetUtilityClient()->Progress(kTestFileSize / 2);
220 test_utils_.GetUtilityClient()->Progress(kTestFileSize);
221 test_utils_.GetUtilityClient()->Success();
224 base::RunLoop().RunUntilIdle();
227 TEST_F(ImageWriterOperationTest, VerifyFileFailure) {
230 OnProgress(kDummyExtensionId, image_writer_api::STAGE_VERIFYWRITE, _))
234 OnProgress(kDummyExtensionId, image_writer_api::STAGE_VERIFYWRITE, 100))
236 EXPECT_CALL(manager_, OnComplete(kDummyExtensionId)).Times(0);
239 OnError(kDummyExtensionId, image_writer_api::STAGE_VERIFYWRITE, _, _))
242 test_utils_.FillFile(
243 test_utils_.GetDevicePath(), kDevicePattern, kTestFileSize);
246 content::BrowserThread::PostTask(content::BrowserThread::FILE,
248 base::Bind(&OperationForTest::VerifyWrite,
250 base::Bind(&base::DoNothing)));
252 base::RunLoop().RunUntilIdle();
254 test_utils_.GetUtilityClient()->Progress(0);
255 test_utils_.GetUtilityClient()->Progress(kTestFileSize / 2);
256 test_utils_.GetUtilityClient()->Error(error::kVerificationFailed);
258 base::RunLoop().RunUntilIdle();
262 // Tests that on creation the operation_ has the expected state.
263 TEST_F(ImageWriterOperationTest, Creation) {
264 EXPECT_EQ(0, operation_->GetProgress());
265 EXPECT_EQ(image_writer_api::STAGE_UNKNOWN, operation_->GetStage());
268 } // namespace image_writer
269 } // namespace extensions