1// Copyright (c) 2012 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.
4
5#include "chrome/browser/ui/global_error/global_error_service.h"
6
7#include "base/memory/scoped_ptr.h"
8#include "chrome/browser/ui/browser.h"
9#include "chrome/browser/ui/global_error/global_error.h"
10#include "chrome/browser/ui/global_error/global_error_bubble_view_base.h"
11#include "chrome/browser/ui/global_error/global_error_service_factory.h"
12#include "chrome/test/base/in_process_browser_test.h"
13#include "chrome/test/base/ui_test_utils.h"
14
15namespace {
16
17// An error that has a bubble view.
18class BubbleViewError : public GlobalErrorWithStandardBubble {
19 public:
20  BubbleViewError() : bubble_view_close_count_(0) { }
21
22  int bubble_view_close_count() { return bubble_view_close_count_; }
23
24  virtual bool HasMenuItem() OVERRIDE { return false; }
25  virtual int MenuItemCommandID() OVERRIDE {
26    ADD_FAILURE();
27    return 0;
28  }
29  virtual base::string16 MenuItemLabel() OVERRIDE {
30    ADD_FAILURE();
31    return base::string16();
32  }
33  virtual void ExecuteMenuItem(Browser* browser) OVERRIDE { ADD_FAILURE(); }
34
35  virtual bool HasBubbleView() OVERRIDE { return true; }
36  virtual base::string16 GetBubbleViewTitle() OVERRIDE {
37    return base::string16();
38  }
39  virtual std::vector<base::string16> GetBubbleViewMessages() OVERRIDE {
40    return std::vector<base::string16>();
41  }
42  virtual base::string16 GetBubbleViewAcceptButtonLabel() OVERRIDE {
43    return base::string16();
44  }
45  virtual base::string16 GetBubbleViewCancelButtonLabel() OVERRIDE {
46    return base::string16();
47  }
48  virtual void OnBubbleViewDidClose(Browser* browser) OVERRIDE {
49    EXPECT_TRUE(browser);
50    ++bubble_view_close_count_;
51  }
52  virtual void BubbleViewAcceptButtonPressed(Browser* browser) OVERRIDE {}
53  virtual void BubbleViewCancelButtonPressed(Browser* browser) OVERRIDE {}
54
55 private:
56  int bubble_view_close_count_;
57
58  DISALLOW_COPY_AND_ASSIGN(BubbleViewError);
59};
60
61} // namespace
62
63class GlobalErrorServiceBrowserTest : public InProcessBrowserTest {
64};
65
66// Test that showing a error with a bubble view works.
67IN_PROC_BROWSER_TEST_F(GlobalErrorServiceBrowserTest, ShowBubbleView) {
68  // This will be deleted by the GlobalErrorService.
69  BubbleViewError* error = new BubbleViewError;
70
71  GlobalErrorService* service =
72      GlobalErrorServiceFactory::GetForProfile(browser()->profile());
73  service->AddGlobalError(error);
74
75  EXPECT_EQ(error, service->GetFirstGlobalErrorWithBubbleView());
76  EXPECT_FALSE(error->HasShownBubbleView());
77  EXPECT_EQ(0, error->bubble_view_close_count());
78
79  // Creating a second browser window should show the bubble view.
80  CreateBrowser(browser()->profile());
81  EXPECT_EQ(NULL, service->GetFirstGlobalErrorWithBubbleView());
82  EXPECT_TRUE(error->HasShownBubbleView());
83  EXPECT_EQ(0, error->bubble_view_close_count());
84}
85
86// Test that GlobalErrorBubbleViewBase::CloseBubbleView correctly closes the
87// bubble view.
88IN_PROC_BROWSER_TEST_F(GlobalErrorServiceBrowserTest, CloseBubbleView) {
89  // This will be deleted by the GlobalErrorService.
90  BubbleViewError* error = new BubbleViewError;
91
92  GlobalErrorService* service =
93      GlobalErrorServiceFactory::GetForProfile(browser()->profile());
94  service->AddGlobalError(error);
95
96  EXPECT_EQ(error, service->GetFirstGlobalErrorWithBubbleView());
97  EXPECT_FALSE(error->HasShownBubbleView());
98  EXPECT_EQ(0, error->bubble_view_close_count());
99
100  // Creating a second browser window should show the bubble view.
101  CreateBrowser(browser()->profile());
102  EXPECT_EQ(NULL, service->GetFirstGlobalErrorWithBubbleView());
103  EXPECT_TRUE(error->HasShownBubbleView());
104  EXPECT_EQ(0, error->bubble_view_close_count());
105
106  // Explicitly close the bubble view.
107  EXPECT_TRUE(error->GetBubbleView());
108  error->GetBubbleView()->CloseBubbleView();
109  content::RunAllPendingInMessageLoop();
110  EXPECT_EQ(1, error->bubble_view_close_count());
111}
112
113// Test that bubble is silently dismissed if it is showing when the GlobalError
114// instance is removed from the profile.
115#if defined(OS_WIN) || defined(OS_LINUX)
116// http://crbug.com/396473
117#define MAYBE_BubbleViewDismissedOnRemove DISABLED_BubbleViewDismissedOnRemove
118#else
119#define MAYBE_BubbleViewDismissedOnRemove BubbleViewDismissedOnRemove
120#endif
121IN_PROC_BROWSER_TEST_F(GlobalErrorServiceBrowserTest,
122                       MAYBE_BubbleViewDismissedOnRemove) {
123  scoped_ptr<BubbleViewError> error(new BubbleViewError);
124
125  GlobalErrorService* service =
126      GlobalErrorServiceFactory::GetForProfile(browser()->profile());
127  service->AddGlobalError(error.get());
128
129  EXPECT_EQ(error.get(), service->GetFirstGlobalErrorWithBubbleView());
130  error->ShowBubbleView(browser());
131  content::RunAllPendingInMessageLoop();
132  EXPECT_TRUE(error->HasShownBubbleView());
133  EXPECT_EQ(0, error->bubble_view_close_count());
134
135  // Removing |error| from profile should dismiss the bubble view without
136  // calling |error->BubbleViewDidClose|.
137  service->RemoveGlobalError(error.get());
138  content::RunAllPendingInMessageLoop();
139  EXPECT_EQ(1, error->bubble_view_close_count());
140  // |error| is no longer owned by service and will be deleted.
141}
142