OLD | NEW |
---|---|
1 // Copyright 2013 The Chromium Authors. All rights reserved. | 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 | 2 // Use of this source code is governed by a BSD-style license that can be |
3 // found in the LICENSE file. | 3 // found in the LICENSE file. |
4 | 4 |
5 #include "content/browser/frame_host/navigator_impl.h" | 5 #include "content/browser/frame_host/navigator_impl.h" |
6 | 6 |
7 #include "base/command_line.h" | 7 #include "base/command_line.h" |
8 #include "base/metrics/histogram.h" | 8 #include "base/metrics/histogram.h" |
9 #include "base/time/time.h" | 9 #include "base/time/time.h" |
10 #include "content/browser/frame_host/frame_tree.h" | 10 #include "content/browser/frame_host/frame_tree.h" |
(...skipping 161 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
172 } else { | 172 } else { |
173 params->redirects.clear(); | 173 params->redirects.clear(); |
174 } | 174 } |
175 | 175 |
176 params->can_load_local_resources = entry.GetCanLoadLocalResources(); | 176 params->can_load_local_resources = entry.GetCanLoadLocalResources(); |
177 params->frame_to_navigate = entry.GetFrameToNavigate(); | 177 params->frame_to_navigate = entry.GetFrameToNavigate(); |
178 } | 178 } |
179 | 179 |
180 } // namespace | 180 } // namespace |
181 | 181 |
182 class NavigatorImpl::NavigationMetricsData { | |
clamy
2014/10/09 19:02:32
I think this should be a struct. If you keep it a
carlosk
2014/10/10 10:00:04
Done.
| |
183 public: | |
184 NavigationMetricsData() {} | |
185 ~NavigationMetricsData() {} | |
182 | 186 |
183 NavigatorImpl::NavigatorImpl( | 187 void Reset(); |
184 NavigationControllerImpl* navigation_controller, | 188 void Set(base::TimeTicks start_time, GURL url); |
clamy
2014/10/09 19:02:32
I would remove those methods and use the scoped_pt
carlosk
2014/10/10 10:00:04
Done! Much better indeed!
| |
185 NavigatorDelegate* delegate) | 189 bool IsTracking(); |
190 | |
191 base::TimeTicks start_time_; | |
192 GURL url_; | |
193 base::TimeTicks url_job_start_time_; | |
194 base::TimeDelta before_unload_delay_; | |
195 }; | |
196 | |
197 void NavigatorImpl::NavigationMetricsData::Reset() { | |
198 start_time_ = base::TimeTicks(); | |
199 url_ = GURL(); | |
200 url_job_start_time_ = base::TimeTicks(); | |
201 before_unload_delay_ = base::TimeDelta(); | |
202 } | |
203 | |
204 void NavigatorImpl::NavigationMetricsData::Set(base::TimeTicks start_time, | |
205 GURL url) { | |
206 start_time_ = start_time; | |
207 url_ = url; | |
208 url_job_start_time_ = base::TimeTicks(); | |
209 before_unload_delay_ = base::TimeDelta(); | |
210 } | |
211 | |
212 bool NavigatorImpl::NavigationMetricsData::IsTracking() { | |
213 return !start_time_.is_null(); | |
214 } | |
215 | |
216 NavigatorImpl::NavigatorImpl(NavigationControllerImpl* navigation_controller, | |
217 NavigatorDelegate* delegate) | |
186 : controller_(navigation_controller), | 218 : controller_(navigation_controller), |
187 delegate_(delegate) { | 219 delegate_(delegate), |
220 navigation_data_(new NavigationMetricsData()) { | |
188 } | 221 } |
189 | 222 |
190 NavigatorImpl::~NavigatorImpl() {} | 223 NavigatorImpl::~NavigatorImpl() {} |
191 | 224 |
192 NavigationController* NavigatorImpl::GetController() { | 225 NavigationController* NavigatorImpl::GetController() { |
193 return controller_; | 226 return controller_; |
194 } | 227 } |
195 | 228 |
196 void NavigatorImpl::DidStartProvisionalLoad( | 229 void NavigatorImpl::DidStartProvisionalLoad( |
197 RenderFrameHostImpl* render_frame_host, | 230 RenderFrameHostImpl* render_frame_host, |
(...skipping 156 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
354 // "Open link in new tab"). We need to keep it above RFHM::Navigate() call to | 387 // "Open link in new tab"). We need to keep it above RFHM::Navigate() call to |
355 // capture the time needed for the RenderFrameHost initialization. | 388 // capture the time needed for the RenderFrameHost initialization. |
356 base::TimeTicks navigation_start = base::TimeTicks::Now(); | 389 base::TimeTicks navigation_start = base::TimeTicks::Now(); |
357 | 390 |
358 RenderFrameHostManager* manager = | 391 RenderFrameHostManager* manager = |
359 render_frame_host->frame_tree_node()->render_manager(); | 392 render_frame_host->frame_tree_node()->render_manager(); |
360 | 393 |
361 // PlzNavigate: the RenderFrameHosts are no longer asked to navigate. | 394 // PlzNavigate: the RenderFrameHosts are no longer asked to navigate. |
362 if (CommandLine::ForCurrentProcess()->HasSwitch( | 395 if (CommandLine::ForCurrentProcess()->HasSwitch( |
363 switches::kEnableBrowserSideNavigation)) { | 396 switches::kEnableBrowserSideNavigation)) { |
364 navigation_start_time_and_url = MakeTuple(navigation_start, entry.GetURL()); | 397 navigation_data_->Set(navigation_start, entry.GetURL()); |
clamy
2014/10/09 19:02:32
I would rather use an explicit reset on the scoped
carlosk
2014/10/10 10:00:04
Done.
| |
365 return RequestNavigation(render_frame_host->frame_tree_node(), | 398 return RequestNavigation(render_frame_host->frame_tree_node(), |
366 entry, | 399 entry, |
367 reload_type, | 400 reload_type, |
368 navigation_start); | 401 navigation_start); |
369 } | 402 } |
370 | 403 |
371 RenderFrameHostImpl* dest_render_frame_host = manager->Navigate(entry); | 404 RenderFrameHostImpl* dest_render_frame_host = manager->Navigate(entry); |
372 if (!dest_render_frame_host) | 405 if (!dest_render_frame_host) |
373 return false; // Unable to create the desired RenderFrameHost. | 406 return false; // Unable to create the desired RenderFrameHost. |
374 | 407 |
(...skipping 18 matching lines...) Expand all Loading... | |
393 | 426 |
394 // Navigate in the desired RenderFrameHost. | 427 // Navigate in the desired RenderFrameHost. |
395 // We can skip this step in the rare case that this is a transfer navigation | 428 // We can skip this step in the rare case that this is a transfer navigation |
396 // which began in the chosen RenderFrameHost, since the request has already | 429 // which began in the chosen RenderFrameHost, since the request has already |
397 // been issued. In that case, simply resume the response. | 430 // been issued. In that case, simply resume the response. |
398 bool is_transfer_to_same = | 431 bool is_transfer_to_same = |
399 navigate_params.transferred_request_child_id != -1 && | 432 navigate_params.transferred_request_child_id != -1 && |
400 navigate_params.transferred_request_child_id == | 433 navigate_params.transferred_request_child_id == |
401 dest_render_frame_host->GetProcess()->GetID(); | 434 dest_render_frame_host->GetProcess()->GetID(); |
402 if (!is_transfer_to_same) { | 435 if (!is_transfer_to_same) { |
403 navigation_start_time_and_url = MakeTuple(navigation_start, entry.GetURL()); | 436 navigation_data_->Set(navigation_start, entry.GetURL()); |
404 dest_render_frame_host->Navigate(navigate_params); | 437 dest_render_frame_host->Navigate(navigate_params); |
405 } else { | 438 } else { |
406 // No need to navigate again. Just resume the deferred request. | 439 // No need to navigate again. Just resume the deferred request. |
407 dest_render_frame_host->GetProcess()->ResumeDeferredNavigation( | 440 dest_render_frame_host->GetProcess()->ResumeDeferredNavigation( |
408 GlobalRequestID(navigate_params.transferred_request_child_id, | 441 GlobalRequestID(navigate_params.transferred_request_child_id, |
409 navigate_params.transferred_request_request_id)); | 442 navigate_params.transferred_request_request_id)); |
410 } | 443 } |
411 | 444 |
412 // Make sure no code called via RFH::Navigate clears the pending entry. | 445 // Make sure no code called via RFH::Navigate clears the pending entry. |
413 CHECK_EQ(controller_->GetPendingEntry(), &entry); | 446 CHECK_EQ(controller_->GetPendingEntry(), &entry); |
(...skipping 152 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
566 if (!did_navigate) | 599 if (!did_navigate) |
567 return; // No navigation happened. | 600 return; // No navigation happened. |
568 | 601 |
569 // DO NOT ADD MORE STUFF TO THIS FUNCTION! Your component should either listen | 602 // DO NOT ADD MORE STUFF TO THIS FUNCTION! Your component should either listen |
570 // for the appropriate notification (best) or you can add it to | 603 // for the appropriate notification (best) or you can add it to |
571 // DidNavigateMainFramePostCommit / DidNavigateAnyFramePostCommit (only if | 604 // DidNavigateMainFramePostCommit / DidNavigateAnyFramePostCommit (only if |
572 // necessary, please). | 605 // necessary, please). |
573 | 606 |
574 // TODO(carlosk): Move this out when PlzNavigate implementation properly calls | 607 // TODO(carlosk): Move this out when PlzNavigate implementation properly calls |
575 // the observer methods. | 608 // the observer methods. |
576 if (details.is_main_frame && | 609 RecordNavigationMetrics(details, params, site_instance); |
577 navigation_start_time_and_url.a.ToInternalValue() != 0 | |
578 && navigation_start_time_and_url.b == params.original_request_url) { | |
579 base::TimeDelta time_to_commit = | |
580 base::TimeTicks::Now() - navigation_start_time_and_url.a; | |
581 UMA_HISTOGRAM_TIMES("Navigation.TimeToCommit", time_to_commit); | |
582 navigation_start_time_and_url = MakeTuple(base::TimeTicks(), GURL()); | |
583 } | |
584 | 610 |
585 // Run post-commit tasks. | 611 // Run post-commit tasks. |
586 if (delegate_) { | 612 if (delegate_) { |
587 if (details.is_main_frame) | 613 if (details.is_main_frame) |
588 delegate_->DidNavigateMainFramePostCommit(details, params); | 614 delegate_->DidNavigateMainFramePostCommit(details, params); |
589 | 615 |
590 delegate_->DidNavigateAnyFramePostCommit( | 616 delegate_->DidNavigateAnyFramePostCommit( |
591 render_frame_host, details, params); | 617 render_frame_host, details, params); |
592 } | 618 } |
593 } | 619 } |
(...skipping 172 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
766 | 792 |
767 // PlzNavigate | 793 // PlzNavigate |
768 void NavigatorImpl::CancelNavigation(FrameTreeNode* frame_tree_node) { | 794 void NavigatorImpl::CancelNavigation(FrameTreeNode* frame_tree_node) { |
769 CHECK(CommandLine::ForCurrentProcess()->HasSwitch( | 795 CHECK(CommandLine::ForCurrentProcess()->HasSwitch( |
770 switches::kEnableBrowserSideNavigation)); | 796 switches::kEnableBrowserSideNavigation)); |
771 navigation_request_map_.erase(frame_tree_node->frame_tree_node_id()); | 797 navigation_request_map_.erase(frame_tree_node->frame_tree_node_id()); |
772 } | 798 } |
773 | 799 |
774 void NavigatorImpl::LogResourceRequestTime( | 800 void NavigatorImpl::LogResourceRequestTime( |
775 base::TimeTicks timestamp, const GURL& url) { | 801 base::TimeTicks timestamp, const GURL& url) { |
776 if (navigation_start_time_and_url.a.ToInternalValue() != 0 | 802 if (navigation_data_->IsTracking() && navigation_data_->url_ == url) { |
777 && navigation_start_time_and_url.b == url) { | 803 navigation_data_->url_job_start_time_ = timestamp; |
778 base::TimeDelta time_to_network = | 804 UMA_HISTOGRAM_TIMES( |
779 timestamp - navigation_start_time_and_url.a; | 805 "Navigation.TimeToURLJobStart", |
780 UMA_HISTOGRAM_TIMES("Navigation.TimeToURLJobStart", time_to_network); | 806 navigation_data_->url_job_start_time_ - navigation_data_->start_time_); |
781 } | 807 } |
782 } | 808 } |
783 | 809 |
810 void NavigatorImpl::LogBeforeUnloadTime( | |
811 const base::TimeTicks& renderer_before_unload_start_time, | |
812 const base::TimeTicks& renderer_before_unload_end_time) { | |
813 // Only stores the beforeunload delay if we're tracking the navigation and it | |
814 // happened later than the navigation request | |
815 if (navigation_data_->IsTracking() && | |
816 renderer_before_unload_start_time > navigation_data_->start_time_) { | |
817 navigation_data_->before_unload_delay_ = | |
818 renderer_before_unload_end_time - renderer_before_unload_start_time; | |
819 } | |
820 } | |
821 | |
784 void NavigatorImpl::CheckWebUIRendererDoesNotDisplayNormalURL( | 822 void NavigatorImpl::CheckWebUIRendererDoesNotDisplayNormalURL( |
785 RenderFrameHostImpl* render_frame_host, | 823 RenderFrameHostImpl* render_frame_host, |
786 const GURL& url) { | 824 const GURL& url) { |
787 int enabled_bindings = | 825 int enabled_bindings = |
788 render_frame_host->render_view_host()->GetEnabledBindings(); | 826 render_frame_host->render_view_host()->GetEnabledBindings(); |
789 bool is_allowed_in_web_ui_renderer = | 827 bool is_allowed_in_web_ui_renderer = |
790 WebUIControllerFactoryRegistry::GetInstance()->IsURLAcceptableForWebUI( | 828 WebUIControllerFactoryRegistry::GetInstance()->IsURLAcceptableForWebUI( |
791 controller_->GetBrowserContext(), url); | 829 controller_->GetBrowserContext(), url); |
792 if ((enabled_bindings & BINDINGS_POLICY_WEB_UI) && | 830 if ((enabled_bindings & BINDINGS_POLICY_WEB_UI) && |
793 !is_allowed_in_web_ui_renderer) { | 831 !is_allowed_in_web_ui_renderer) { |
(...skipping 41 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
835 } | 873 } |
836 | 874 |
837 // The navigation request is sent directly to the IO thread. | 875 // The navigation request is sent directly to the IO thread. |
838 OnBeginNavigation( | 876 OnBeginNavigation( |
839 frame_tree_node, | 877 frame_tree_node, |
840 MakeDefaultBeginNavigation(request_params, navigation_type), | 878 MakeDefaultBeginNavigation(request_params, navigation_type), |
841 navigation_request_map_.get(frame_tree_node_id)->common_params()); | 879 navigation_request_map_.get(frame_tree_node_id)->common_params()); |
842 return true; | 880 return true; |
843 } | 881 } |
844 | 882 |
883 void NavigatorImpl::RecordNavigationMetrics( | |
884 const LoadCommittedDetails& details, | |
885 const FrameHostMsg_DidCommitProvisionalLoad_Params& params, | |
886 SiteInstance* site_instance) { | |
887 DCHECK(site_instance->HasProcess()); | |
888 if (details.is_main_frame && navigation_data_->IsTracking() && | |
889 navigation_data_->url_ == params.original_request_url) { | |
890 base::TimeDelta time_to_commit = | |
891 base::TimeTicks::Now() - navigation_data_->start_time_; | |
892 UMA_HISTOGRAM_TIMES("Navigation.TimeToCommit", time_to_commit); | |
893 | |
894 time_to_commit -= navigation_data_->before_unload_delay_; | |
895 base::TimeDelta time_to_network = navigation_data_->url_job_start_time_ - | |
896 navigation_data_->start_time_ - | |
897 navigation_data_->before_unload_delay_; | |
898 RenderProcessHostImpl* process_host = | |
899 static_cast<RenderProcessHostImpl*>(site_instance->GetProcess()); | |
900 bool spawned_new_process = | |
901 process_host->GetInitTime() > navigation_data_->start_time_; | |
902 if (spawned_new_process) { | |
903 UMA_HISTOGRAM_TIMES( | |
904 "Navigation.TimeToCommit_NewRenderer_BeforeUnloadDiscounted", | |
905 time_to_commit); | |
906 UMA_HISTOGRAM_TIMES( | |
907 "Navigation.TimeToURLJobStart_NewRenderer_BeforeUnloadDiscounted", | |
908 time_to_network); | |
909 } else { | |
910 UMA_HISTOGRAM_TIMES( | |
911 "Navigation.TimeToCommit_OldRenderer_BeforeUnloadDiscounted", | |
912 time_to_commit); | |
913 UMA_HISTOGRAM_TIMES( | |
914 "Navigation.TimeToURLJobStart_OldRenderer_BeforeUnloadDiscounted", | |
915 time_to_network); | |
916 } | |
917 | |
918 navigation_data_->Reset(); | |
clamy
2014/10/09 19:02:32
I would reset the scoped ptr explicitly (navigatio
carlosk
2014/10/10 10:00:04
Done.
| |
919 } | |
920 } | |
921 | |
845 } // namespace content | 922 } // namespace content |
OLD | NEW |