scanner: Add coarse-grained CanShowUi metrics
These metrics will be useful for debugging feature access issues, and getting an overview of how many users have the Scanner UI shown. Bug: b:397105844 Change-Id: I6a6a2100b3665daa3b5c2d5d056589840ba56327 Reviewed-on: https://chromium-review.googlesource.com/c/chromium/src/+/6275365 Reviewed-by: Michelle Chen <michellegc@google.com> Reviewed-by: Tony Yeoman <tby@chromium.org> Commit-Queue: Michael Cui <mlcui@google.com> Cr-Commit-Position: refs/heads/main@{#1421682}
This commit is contained in:

committed by
Chromium LUCI CQ

parent
0c0498b7cc
commit
b86adced66
ash/scanner
tools/metrics/histograms/metadata/ash
@ -401,11 +401,15 @@ void ScannerController::RegisterProfilePrefs(PrefRegistrySimple* registry) {
|
||||
// static
|
||||
bool ScannerController::CanShowUiForShell() {
|
||||
if (!Shell::HasInstance()) {
|
||||
RecordScannerFeatureUserState(
|
||||
ScannerFeatureUserState::kCanShowUiReturnedFalse);
|
||||
return false;
|
||||
}
|
||||
|
||||
ScannerController* controller = Shell::Get()->scanner_controller();
|
||||
if (!controller) {
|
||||
RecordScannerFeatureUserState(
|
||||
ScannerFeatureUserState::kCanShowUiReturnedFalse);
|
||||
return false;
|
||||
}
|
||||
|
||||
@ -423,15 +427,22 @@ bool ScannerController::CanShowUi() {
|
||||
delegate_->GetProfileScopedDelegate();
|
||||
|
||||
if (profile_scoped_delegate == nullptr) {
|
||||
RecordScannerFeatureUserState(
|
||||
ScannerFeatureUserState::kCanShowUiReturnedFalse);
|
||||
return false;
|
||||
}
|
||||
|
||||
specialized_features::FeatureAccessFailureSet checks =
|
||||
profile_scoped_delegate->CheckFeatureAccess();
|
||||
|
||||
bool consent_not_accepted = checks.Has(
|
||||
specialized_features::FeatureAccessFailure::kConsentNotAccepted);
|
||||
|
||||
checks.Remove(
|
||||
specialized_features::FeatureAccessFailure::kConsentNotAccepted);
|
||||
if (!checks.empty()) {
|
||||
RecordScannerFeatureUserState(
|
||||
ScannerFeatureUserState::kCanShowUiReturnedFalse);
|
||||
return false;
|
||||
}
|
||||
|
||||
@ -444,9 +455,18 @@ bool ScannerController::CanShowUi() {
|
||||
if (prefs != nullptr &&
|
||||
prefs->GetInteger(prefs::kScannerEnterprisePolicyAllowed) ==
|
||||
static_cast<int>(ScannerEnterprisePolicy::kDisallowed)) {
|
||||
RecordScannerFeatureUserState(
|
||||
ScannerFeatureUserState::kCanShowUiReturnedFalse);
|
||||
return false;
|
||||
}
|
||||
|
||||
if (consent_not_accepted) {
|
||||
RecordScannerFeatureUserState(
|
||||
ScannerFeatureUserState::kCanShowUiReturnedTrueWithoutConsent);
|
||||
} else {
|
||||
RecordScannerFeatureUserState(
|
||||
ScannerFeatureUserState::kCanShowUiReturnedTrueWithConsent);
|
||||
}
|
||||
return true;
|
||||
}
|
||||
|
||||
|
@ -24,6 +24,7 @@
|
||||
#include "ash/scanner/fake_scanner_profile_scoped_delegate.h"
|
||||
#include "ash/scanner/scanner_action_view_model.h"
|
||||
#include "ash/scanner/scanner_enterprise_policy.h"
|
||||
#include "ash/scanner/scanner_metrics.h"
|
||||
#include "ash/scanner/scanner_session.h"
|
||||
#include "ash/session/session_controller_impl.h"
|
||||
#include "ash/shell.h"
|
||||
@ -38,6 +39,7 @@
|
||||
#include "base/strings/string_split.h"
|
||||
#include "base/test/gmock_callback_support.h"
|
||||
#include "base/test/gmock_expected_support.h"
|
||||
#include "base/test/metrics/histogram_tester.h"
|
||||
#include "base/test/mock_callback.h"
|
||||
#include "base/test/protobuf_matchers.h"
|
||||
#include "base/test/scoped_feature_list.h"
|
||||
@ -140,6 +142,20 @@ class MockToastManager : public ToastManager {
|
||||
MOCK_METHOD(void, Resume, (), (override));
|
||||
};
|
||||
|
||||
class MockScannerDelegate : public ScannerDelegate {
|
||||
public:
|
||||
MOCK_METHOD(ScannerProfileScopedDelegate*,
|
||||
GetProfileScopedDelegate,
|
||||
(),
|
||||
(override));
|
||||
MOCK_METHOD(void,
|
||||
OpenFeedbackDialog,
|
||||
(const AccountId& account_id,
|
||||
ScannerFeedbackInfo feedback_info,
|
||||
SendFeedbackCallback send_feedback_callback),
|
||||
(override));
|
||||
};
|
||||
|
||||
class ScannerControllerTest : public AshTestBase {
|
||||
public:
|
||||
ScannerControllerTest() = default;
|
||||
@ -356,6 +372,113 @@ TEST_F(ScannerControllerDisabledTest, CanShowUiForShellFalseWhenNoController) {
|
||||
EXPECT_FALSE(ScannerController::CanShowUiForShell());
|
||||
}
|
||||
|
||||
TEST(ScannerControllerNoFixtureTest, CanShowUiForShellFalseWhenNoShellMetrics) {
|
||||
base::HistogramTester histogram_tester;
|
||||
|
||||
ASSERT_FALSE(Shell::HasInstance());
|
||||
ASSERT_FALSE(ScannerController::CanShowUiForShell());
|
||||
|
||||
histogram_tester.ExpectBucketCount(
|
||||
"Ash.ScannerFeature.UserState",
|
||||
ScannerFeatureUserState::kCanShowUiReturnedFalse, 1);
|
||||
}
|
||||
|
||||
TEST_F(ScannerControllerDisabledTest,
|
||||
CanShowUiForShellFalseWhenNoControllerMetrics) {
|
||||
base::HistogramTester histogram_tester;
|
||||
|
||||
ASSERT_FALSE(Shell::Get()->scanner_controller());
|
||||
ASSERT_FALSE(ScannerController::CanShowUiForShell());
|
||||
|
||||
histogram_tester.ExpectBucketCount(
|
||||
"Ash.ScannerFeature.UserState",
|
||||
ScannerFeatureUserState::kCanShowUiReturnedFalse, 1);
|
||||
}
|
||||
|
||||
TEST(ScannerControllerNoFixtureTest,
|
||||
CanShowUiFalseWhenNoProfileScopedDelegateMetrics) {
|
||||
base::HistogramTester histogram_tester;
|
||||
SessionControllerImpl session_controller;
|
||||
auto mock_delegate = std::make_unique<MockScannerDelegate>();
|
||||
EXPECT_CALL(*mock_delegate, GetProfileScopedDelegate())
|
||||
.WillRepeatedly(Return(nullptr));
|
||||
ScannerController scanner_controller(std::move(mock_delegate),
|
||||
session_controller);
|
||||
|
||||
ASSERT_FALSE(scanner_controller.CanShowUi());
|
||||
|
||||
histogram_tester.ExpectBucketCount(
|
||||
"Ash.ScannerFeature.UserState",
|
||||
ScannerFeatureUserState::kCanShowUiReturnedFalse, 1);
|
||||
}
|
||||
|
||||
TEST_F(ScannerControllerTest,
|
||||
CanShowUiFalseWhenFeatureAccessCheckFailsMetrics) {
|
||||
base::HistogramTester histogram_tester;
|
||||
ScannerController* scanner_controller = Shell::Get()->scanner_controller();
|
||||
ASSERT_TRUE(scanner_controller);
|
||||
EXPECT_CALL(*GetFakeScannerProfileScopedDelegate(*scanner_controller),
|
||||
CheckFeatureAccess)
|
||||
.WillRepeatedly(Return(specialized_features::FeatureAccessFailureSet{
|
||||
specialized_features::FeatureAccessFailure::kDisabledInSettings}));
|
||||
|
||||
ASSERT_FALSE(scanner_controller->CanShowUi());
|
||||
|
||||
histogram_tester.ExpectBucketCount(
|
||||
"Ash.ScannerFeature.UserState",
|
||||
ScannerFeatureUserState::kCanShowUiReturnedFalse, 1);
|
||||
}
|
||||
|
||||
TEST_F(ScannerControllerTest,
|
||||
CanShowUiFalseWhenEnterprisePolicyDisallowedMetrics) {
|
||||
base::HistogramTester histogram_tester;
|
||||
ScannerController* scanner_controller = Shell::Get()->scanner_controller();
|
||||
ASSERT_TRUE(scanner_controller);
|
||||
EXPECT_CALL(*GetFakeScannerProfileScopedDelegate(*scanner_controller),
|
||||
CheckFeatureAccess)
|
||||
.WillRepeatedly(Return(specialized_features::FeatureAccessFailureSet{}));
|
||||
Shell::Get()->session_controller()->GetActivePrefService()->SetInteger(
|
||||
prefs::kScannerEnterprisePolicyAllowed,
|
||||
static_cast<int>(ScannerEnterprisePolicy::kDisallowed));
|
||||
|
||||
ASSERT_FALSE(scanner_controller->CanShowUi());
|
||||
|
||||
histogram_tester.ExpectBucketCount(
|
||||
"Ash.ScannerFeature.UserState",
|
||||
ScannerFeatureUserState::kCanShowUiReturnedFalse, 1);
|
||||
}
|
||||
|
||||
TEST_F(ScannerControllerTest, CanShowUiTrueWithoutConsentMetrics) {
|
||||
base::HistogramTester histogram_tester;
|
||||
ScannerController* scanner_controller = Shell::Get()->scanner_controller();
|
||||
ASSERT_TRUE(scanner_controller);
|
||||
EXPECT_CALL(*GetFakeScannerProfileScopedDelegate(*scanner_controller),
|
||||
CheckFeatureAccess)
|
||||
.WillRepeatedly(Return(specialized_features::FeatureAccessFailureSet{
|
||||
specialized_features::FeatureAccessFailure::kConsentNotAccepted}));
|
||||
|
||||
ASSERT_TRUE(scanner_controller->CanShowUi());
|
||||
|
||||
histogram_tester.ExpectBucketCount(
|
||||
"Ash.ScannerFeature.UserState",
|
||||
ScannerFeatureUserState::kCanShowUiReturnedTrueWithoutConsent, 1);
|
||||
}
|
||||
|
||||
TEST_F(ScannerControllerTest, CanShowUiTrueWithConsentMetrics) {
|
||||
base::HistogramTester histogram_tester;
|
||||
ScannerController* scanner_controller = Shell::Get()->scanner_controller();
|
||||
ASSERT_TRUE(scanner_controller);
|
||||
EXPECT_CALL(*GetFakeScannerProfileScopedDelegate(*scanner_controller),
|
||||
CheckFeatureAccess)
|
||||
.WillRepeatedly(Return(specialized_features::FeatureAccessFailureSet{}));
|
||||
|
||||
ASSERT_TRUE(scanner_controller->CanShowUi());
|
||||
|
||||
histogram_tester.ExpectBucketCount(
|
||||
"Ash.ScannerFeature.UserState",
|
||||
ScannerFeatureUserState::kCanShowUiReturnedTrueWithConsent, 1);
|
||||
}
|
||||
|
||||
TEST_F(ScannerControllerTest,
|
||||
CannotShowConsentScreenEntryPointsIfOtherCheckFail) {
|
||||
ScannerController* scanner_controller = Shell::Get()->scanner_controller();
|
||||
|
@ -84,7 +84,12 @@ enum class ScannerFeatureUserState {
|
||||
kNewGoogleSheetPopulatedActionExecutionFailed,
|
||||
kNewGoogleDocPopulatedActionExecutionFailed,
|
||||
kCopyToClipboardPopulatedActionExecutionFailed,
|
||||
kMaxValue = kCopyToClipboardPopulatedActionExecutionFailed,
|
||||
|
||||
kCanShowUiReturnedFalse = 27,
|
||||
kCanShowUiReturnedTrueWithoutConsent = 28,
|
||||
kCanShowUiReturnedTrueWithConsent = 29,
|
||||
|
||||
kMaxValue = kCanShowUiReturnedTrueWithConsent,
|
||||
};
|
||||
// LINT.ThenChange(//tools/metrics/histograms/metadata/ash/enums.xml:ScannerFeatureUserState)
|
||||
|
||||
|
@ -51,6 +51,9 @@ INSTANTIATE_TEST_SUITE_P(
|
||||
kNewGoogleSheetPopulatedActionExecutionFailed,
|
||||
kNewGoogleDocPopulatedActionExecutionFailed,
|
||||
kCopyToClipboardPopulatedActionExecutionFailed,
|
||||
kCanShowUiReturnedFalse,
|
||||
kCanShowUiReturnedTrueWithoutConsent,
|
||||
kCanShowUiReturnedTrueWithConsent,
|
||||
}));
|
||||
|
||||
TEST_P(ScannerMetricsTest, Record) {
|
||||
|
@ -2031,6 +2031,14 @@ chromeos/ash/components/peripheral_notification/peripheral_notification_manager.
|
||||
<int value="25" label="New Google Doc populated action failed on execution"/>
|
||||
<int value="26"
|
||||
label="Copy to clipboard populated action failed on execution"/>
|
||||
<int value="27"
|
||||
label="UI access checks resulted in "do not show UI""/>
|
||||
<int value="28"
|
||||
label="UI access checks resulted in "show UI, but user not
|
||||
consented""/>
|
||||
<int value="29"
|
||||
label="UI access checks resulted in "show UI and user
|
||||
consented""/>
|
||||
</enum>
|
||||
|
||||
<!-- LINT.ThenChange(//ash/scanner/scanner_metrics.h:ScannerFeatureUserState) -->
|
||||
|
Reference in New Issue
Block a user