blob: 28d6415ef1291ab6c6a08730e2c81432e1a9e561 [file] [log] [blame]
// Copyright 2020 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.
#import "ios/web/web_state/policy_decision_state_tracker.h"
#include "base/barrier_closure.h"
#if !defined(__has_feature) || !__has_feature(objc_arc)
#error "This file requires ARC support."
#endif
namespace web {
PolicyDecisionStateTracker::PolicyDecisionStateTracker(
base::OnceCallback<void(WebStatePolicyDecider::PolicyDecision)> callback)
: callback_(std::move(callback)) {}
PolicyDecisionStateTracker::~PolicyDecisionStateTracker() {
if (!callback_.is_null()) {
std::move(callback_).Run(WebStatePolicyDecider::PolicyDecision::Cancel());
}
}
void PolicyDecisionStateTracker::OnSinglePolicyDecisionReceived(
WebStatePolicyDecider::PolicyDecision decision) {
if (DeterminedFinalResult())
return;
if (decision.ShouldCancelNavigation() && !decision.ShouldDisplayError()) {
result_ = decision;
OnFinalResultDetermined();
return;
}
num_decisions_received_++;
if (decision.ShouldDisplayError() && result_.ShouldAllowNavigation()) {
result_ = decision;
}
decision_closure_.Run();
}
bool PolicyDecisionStateTracker::DeterminedFinalResult() {
return callback_.is_null();
}
void PolicyDecisionStateTracker::FinishedRequestingDecisions(
int num_decisions_requested) {
if (DeterminedFinalResult())
return;
decision_closure_ = base::BarrierClosure(
num_decisions_requested - num_decisions_received_,
base::BindOnce(&PolicyDecisionStateTracker::OnFinalResultDetermined,
AsWeakPtr()));
}
void PolicyDecisionStateTracker::OnFinalResultDetermined() {
std::move(callback_).Run(result_);
}
} // namespace web