1 // Copyright 2015 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 #ifndef CHROME_BROWSER_BANNERS_APP_BANNER_DATA_FETCHER_H_
6 #define CHROME_BROWSER_BANNERS_APP_BANNER_DATA_FETCHER_H_
8 #include "base/memory/ref_counted.h"
9 #include "base/memory/scoped_ptr.h"
10 #include "base/memory/weak_ptr.h"
11 #include "base/observer_list.h"
12 #include "base/time/time.h"
13 #include "chrome/common/web_application_info.h"
14 #include "content/public/browser/web_contents.h"
15 #include "content/public/browser/web_contents_observer.h"
16 #include "content/public/common/manifest.h"
17 #include "third_party/WebKit/public/platform/modules/app_banner/WebAppBannerPromptReply.h"
25 } // namespace infobars
28 class AppBannerDataFetcher
;
30 // Fetches data required to show a web app banner for the URL currently shown by
32 class AppBannerDataFetcher
33 : public base::RefCounted
<AppBannerDataFetcher
>,
34 public content::WebContentsObserver
{
38 virtual void OnDecidedWhetherToShow(AppBannerDataFetcher
* fetcher
,
40 virtual void OnFetcherDestroyed(AppBannerDataFetcher
* fetcher
) = 0;
45 // Called to handle a non-web app. Returns |true| if the non-web app can be
46 // handled, and the fetcher needs to remain active and wait for a callback.
47 virtual bool HandleNonWebApp(const std::string
& platform
,
49 const std::string
& id
) = 0;
52 // Returns the current time.
53 static base::Time
GetCurrentTime();
55 // Fast-forwards the current time for testing.
56 static void SetTimeDeltaForTesting(int days
);
58 AppBannerDataFetcher(content::WebContents
* web_contents
,
59 base::WeakPtr
<Delegate
> weak_delegate
,
60 int ideal_icon_size_in_dp
);
62 // Begins creating a banner for the URL being displayed by the Delegate's
64 void Start(const GURL
& validated_url
, ui::PageTransition transition_type
);
66 // Stops the pipeline when any asynchronous calls return.
69 // Replaces the WebContents that is being observed.
70 void ReplaceWebContents(content::WebContents
* web_contents
);
72 // Adds an observer to the list.
73 void AddObserverForTesting(Observer
* observer
);
75 // Removes an observer from the list.
76 void RemoveObserverForTesting(Observer
* observer
);
78 // Returns whether or not the pipeline has been stopped.
79 bool is_active() { return is_active_
; }
81 // Returns whether the beforeinstallprompt Javascript event was canceled.
82 bool was_canceled_by_page() { return was_canceled_by_page_
; }
84 // Returns whether the page has validly requested that the banner be shown
85 // by calling prompt() on the beforeinstallprompt Javascript event.
86 bool page_requested_prompt() { return page_requested_prompt_
; }
88 // Returns the type of transition which triggered this fetch.
89 ui::PageTransition
transition_type() { return transition_type_
; }
91 // Returns the URL that kicked off the banner data retrieval.
92 const GURL
& validated_url() { return validated_url_
; }
94 // WebContentsObserver overrides.
95 void WebContentsDestroyed() override
;
96 void DidNavigateMainFrame(
97 const content::LoadCommittedDetails
& details
,
98 const content::FrameNavigateParams
& params
) override
;
99 bool OnMessageReceived(const IPC::Message
& message
,
100 content::RenderFrameHost
* render_frame_host
) override
;
103 ~AppBannerDataFetcher() override
;
105 // Return a string describing what type of banner is being created. Used when
106 // alerting websites that a banner is about to be created.
107 virtual std::string
GetBannerType();
109 // Called after the manager sends a message to the renderer regarding its
110 // intention to show a prompt. The renderer will send a message back with the
111 // opportunity to cancel.
112 void OnBannerPromptReply(content::RenderFrameHost
* render_frame_host
,
114 blink::WebAppBannerPromptReply reply
,
115 std::string referrer
);
117 // Called when the client has prevented a banner from being shown, and is
118 // now requesting that it be shown later.
119 void OnRequestShowAppBanner(content::RenderFrameHost
* render_frame_host
,
122 content::WebContents
* GetWebContents();
123 virtual std::string
GetAppIdentifier();
124 const content::Manifest
& web_app_data() { return web_app_data_
; }
125 void set_app_title(const base::string16
& title
) { app_title_
= title
; }
126 int event_request_id() { return event_request_id_
; }
128 // Fetches the icon at the given URL asynchronously, returning |false| if a
129 // load could not be started.
130 bool FetchAppIcon(content::WebContents
* web_contents
, const GURL
& url
);
132 // Records that a banner was shown. The |event_name| corresponds to the RAPPOR
133 // metric being recorded.
134 void RecordDidShowBanner(const std::string
& event_name
);
137 // Callbacks for data retrieval.
138 void OnDidGetManifest(const content::Manifest
& manifest
);
139 void OnDidCheckHasServiceWorker(bool has_service_worker
);
140 void OnAppIconFetched(const SkBitmap
& bitmap
);
142 // Called when it is determined that the webapp has fulfilled the initial
143 // criteria of having a manifest and a service worker.
144 void OnHasServiceWorker(content::WebContents
* web_contents
);
146 // Returns whether the given web app has already been installed.
147 // Implemented on desktop platforms only.
148 virtual bool IsWebAppInstalled(content::BrowserContext
* browser_context
,
149 const GURL
& start_url
);
151 // Record that the banner could be shown at this point, if the triggering
152 // heuristic allowed.
153 void RecordCouldShowBanner();
155 // Creates a banner for the app using the given |icon|.
156 virtual void ShowBanner(const SkBitmap
* icon
,
157 const base::string16
& title
,
158 const std::string
& referrer
) = 0;
160 // Returns whether the banner should be shown.
161 bool CheckIfShouldShowBanner();
163 // Returns whether the fetcher is active and web contents have not been
165 bool CheckFetcherIsStillAlive(content::WebContents
* web_contents
);
167 // Returns whether the given Manifest is following the requirements to show
169 static bool IsManifestValidForWebApp(const content::Manifest
& manifest
,
170 content::WebContents
* web_contents
);
172 const int ideal_icon_size_in_dp_
;
173 const base::WeakPtr
<Delegate
> weak_delegate_
;
174 base::ObserverList
<Observer
> observer_list_
;
176 bool was_canceled_by_page_
;
177 bool page_requested_prompt_
;
178 ui::PageTransition transition_type_
;
179 int event_request_id_
;
180 scoped_ptr
<SkBitmap
> app_icon_
;
181 std::string referrer_
;
184 base::string16 app_title_
;
185 content::Manifest web_app_data_
;
187 friend class AppBannerDataFetcherUnitTest
;
188 friend class base::RefCounted
<AppBannerDataFetcher
>;
189 DISALLOW_COPY_AND_ASSIGN(AppBannerDataFetcher
);
192 } // namespace banners
194 #endif // CHROME_BROWSER_BANNERS_APP_BANNER_DATA_FETCHER_H_