Donate to e Foundation | Murena handsets with /e/OS | Own a part of Murena! Learn more

Commit 76278fcc authored by Arpan Kaphle's avatar Arpan Kaphle Committed by Automerger Merge Worker
Browse files

Merge changes Ib3db0b27,I82c2f747,If4b77e08,I17ac83de into udc-dev am: d10dc902

parents 2f9bc4a9 d10dc902
Loading
Loading
Loading
Loading
+134 −42
Original line number Diff line number Diff line
@@ -24,6 +24,7 @@ import android.util.Slog;
import com.android.internal.util.FrameworkStatsLog;
import com.android.server.credentials.metrics.ApiName;
import com.android.server.credentials.metrics.ApiStatus;
import com.android.server.credentials.metrics.BrowsedAuthenticationMetric;
import com.android.server.credentials.metrics.CandidateAggregateMetric;
import com.android.server.credentials.metrics.CandidateBrowsingPhaseMetric;
import com.android.server.credentials.metrics.CandidatePhaseMetric;
@@ -45,6 +46,7 @@ public class MetricUtilities {

    private static final String TAG = "MetricUtilities";
    public static final String USER_CANCELED_SUBSTRING = "TYPE_USER_CANCELED";
    public static final int MIN_EMIT_WAIT_TIME_MS = 10;

    public static final int DEFAULT_INT_32 = -1;
    public static final String DEFAULT_STRING = "";
@@ -117,7 +119,8 @@ public class MetricUtilities {
    }

    /**
     * A logging utility used primarily for the final phase of the current metric setup.
     * A logging utility used primarily for the final phase of the current metric setup, focused on
     * track 2, where the provider uid is known.
     *
     * @param finalPhaseMetric     the coalesced data of the chosen provider
     * @param browsingPhaseMetrics the coalesced data of the browsing phase
@@ -188,6 +191,86 @@ public class MetricUtilities {
        }
    }

    /**
     * This emits the authentication entry metrics for track 2, where the provider uid is known.
     *
     * @param authenticationMetric the authentication metric collection to emit with
     * @param emitSequenceId       an emitted sequence id for the current session
     */
    public static void logApiCalledAuthenticationMetric(
            BrowsedAuthenticationMetric authenticationMetric,
            int emitSequenceId) {
        try {
            if (!LOG_FLAG) {
                return;
            }
            FrameworkStatsLog.write(FrameworkStatsLog.CREDENTIAL_MANAGER_AUTH_CLICK_REPORTED,
                    /* session_id */ authenticationMetric.getSessionIdProvider(),
                    /* sequence_num */ emitSequenceId,
                    /* chosen_provider_uid */ authenticationMetric.getProviderUid(),
                    /* unique_response_classtypes */
                    authenticationMetric.getAuthEntryCollective().getUniqueResponseStrings(),
                    /* per_classtype_counts */
                    authenticationMetric.getAuthEntryCollective().getUniqueResponseCounts(),
                    /* unique_entries */
                    authenticationMetric.getAuthEntryCollective().getUniqueEntries(),
                    /* auth_per_entry_counts */
                    authenticationMetric.getAuthEntryCollective().getUniqueEntryCounts(),
                    /* framework_exception_unique_classtype */
                    authenticationMetric.getFrameworkException(),
                    /* exception_specified */ authenticationMetric.isHasException(),
                    /* auth_provider_status */
                    authenticationMetric.getProviderStatus(),
                    /* query_returned */
                    authenticationMetric.isQueryReturned()
            );
        } catch (Exception e) {
            Slog.w(TAG, "Unexpected error during candidate get metric logging: " + e);
        }
    }

    /**
     * A logging utility used primarily for the candidate phase's get responses in the current
     * metric setup. This helps avoid nested proto-files. This is primarily focused on track 2,
     * where the provider uid is known. It ensures to run in a separate thread while emitting
     * the multiple atoms to work with expected emit limits.
     *
     * @param providers      a map with known providers and their held metric objects
     * @param emitSequenceId an emitted sequence id for the current session, that matches the
     *                       candidate emit value, as these metrics belong with the candidates
     */
    public static void logApiCalledCandidateGetMetric(Map<String, ProviderSession> providers,
            int emitSequenceId) {
        try {
            // TODO(b/274954697) : To queue format in future optimizations (metrics POC support)
            if (!LOG_FLAG) {
                return;
            }
            var sessions = providers.values();
            for (var session : sessions) {
                try {
                    var metric = session.getProviderSessionMetric()
                            .getCandidatePhasePerProviderMetric();
                    FrameworkStatsLog.write(
                            FrameworkStatsLog.CREDENTIAL_MANAGER_GET_REPORTED,
                            /* session_id */ metric.getSessionIdProvider(),
                            /* sequence_num */ emitSequenceId,
                            /* candidate_provider_uid */ metric.getCandidateUid(),
                            /* response_unique_classtypes */
                            metric.getResponseCollective().getUniqueResponseStrings(),
                            /* per_classtype_counts */
                            metric.getResponseCollective().getUniqueResponseCounts()
                    );
                } catch (Exception e) {
                    Slog.w(TAG, "Unexpected exception during get metric logging" + e);
                }
            }
        } catch (Exception e) {
            Slog.w(TAG, "Unexpected error during candidate get metric logging: " + e);
        }
    }


    /**
     * A logging utility used primarily for the candidate phase of the current metric setup. This
     * will primarily focus on track 2, where the session id is associated with known providers,
@@ -359,23 +442,29 @@ public class MetricUtilities {
            int sequenceNum) {
        try {
            if (!LOG_FLAG) {
                return;
            }
            FrameworkStatsLog.write(FrameworkStatsLog.CREDENTIAL_MANAGER_TOTAL_REPORTED,
                    /*session_id*/ candidateAggregateMetric.getSessionIdProvider(),
                    /*sequence_num*/ sequenceNum,
                    /*query_returned*/ candidateAggregateMetric.isQueryReturned(),
                        /*num_providers*/ candidateAggregateMetric.getNumProviders(),
                    /*num_query_providers*/ candidateAggregateMetric.getNumProviders(),
                    /*min_query_start_timestamp_microseconds*/
                    DEFAULT_INT_32,
                    /*max_query_end_timestamp_microseconds*/
                    DEFAULT_INT_32,
                    /*query_response_unique_classtypes*/
                        DEFAULT_REPEATED_STR,
                    candidateAggregateMetric.getAggregateCollectiveQuery()
                            .getUniqueResponseStrings(),
                    /*query_per_classtype_counts*/
                        DEFAULT_REPEATED_INT_32,
                    candidateAggregateMetric.getAggregateCollectiveQuery()
                            .getUniqueResponseCounts(),
                    /*query_unique_entries*/
                        DEFAULT_REPEATED_INT_32,
                    candidateAggregateMetric.getAggregateCollectiveQuery()
                            .getUniqueEntries(),
                    /*query_per_entry_counts*/
                        DEFAULT_REPEATED_INT_32,
                    candidateAggregateMetric.getAggregateCollectiveQuery()
                            .getUniqueEntryCounts(),
                    /*query_total_candidate_failure*/
                    DEFAULT_INT_32,
                    /*query_framework_exception_unique_classtypes*/
@@ -383,13 +472,17 @@ public class MetricUtilities {
                    /*query_per_exception_classtype_counts*/
                    DEFAULT_REPEATED_INT_32,
                    /*auth_response_unique_classtypes*/
                        DEFAULT_REPEATED_STR,
                    candidateAggregateMetric.getAggregateCollectiveAuth()
                            .getUniqueResponseStrings(),
                    /*auth_per_classtype_counts*/
                        DEFAULT_REPEATED_INT_32,
                    candidateAggregateMetric.getAggregateCollectiveAuth()
                            .getUniqueResponseCounts(),
                    /*auth_unique_entries*/
                        DEFAULT_REPEATED_INT_32,
                    candidateAggregateMetric.getAggregateCollectiveAuth()
                            .getUniqueEntries(),
                    /*auth_per_entry_counts*/
                        DEFAULT_REPEATED_INT_32,
                    candidateAggregateMetric.getAggregateCollectiveAuth()
                            .getUniqueEntryCounts(),
                    /*auth_total_candidate_failure*/
                    DEFAULT_INT_32,
                    /*auth_framework_exception_unique_classtypes*/
@@ -397,10 +490,9 @@ public class MetricUtilities {
                    /*auth_per_exception_classtype_counts*/
                    DEFAULT_REPEATED_INT_32,
                    /*num_auth_clicks*/
                        DEFAULT_INT_32,
                    candidateAggregateMetric.getNumAuthEntriesTapped(),
                    /*auth_returned*/ false
            );
            }
        } catch (Exception e) {
            Slog.w(TAG, "Unexpected error during metric logging: " + e);
        }
+2 −0
Original line number Diff line number Diff line
@@ -269,6 +269,7 @@ public final class ProviderGetSession extends ProviderSession<BeginGetCredential
            case AUTHENTICATION_ACTION_ENTRY_KEY:
                Action authenticationEntry = mProviderResponseDataHandler
                        .getAuthenticationAction(entryKey);
                mProviderSessionMetric.createAuthenticationBrowsingMetric();
                if (authenticationEntry == null) {
                    Slog.i(TAG, "Unexpected authenticationEntry key");
                    invokeCallbackOnInternalInvalidState();
@@ -423,6 +424,7 @@ public final class ProviderGetSession extends ProviderSession<BeginGetCredential
                providerPendingIntentResponse);
        if (exception != null) {
            // TODO (b/271135048), for AuthenticationEntry callback selection, set error
            mProviderSessionMetric.collectAuthenticationExceptionStatus(/*hasException*/true);
            invokeCallbackWithError(exception.getType(),
                    exception.getMessage());
            // Additional content received is in the form of an exception which ends the flow.
+11 −0
Original line number Diff line number Diff line
@@ -38,6 +38,7 @@ import android.util.Slog;
import com.android.internal.R;
import com.android.server.credentials.metrics.ApiName;
import com.android.server.credentials.metrics.ApiStatus;
import com.android.server.credentials.metrics.ProviderSessionMetric;
import com.android.server.credentials.metrics.ProviderStatusForMetrics;
import com.android.server.credentials.metrics.RequestSessionMetric;

@@ -199,10 +200,20 @@ abstract class RequestSession<T, U, V> implements CredentialManagerUi.Credential
            Slog.w(TAG, "providerSession not found in onUiSelection. This is strange.");
            return;
        }
        ProviderSessionMetric providerSessionMetric = providerSession.mProviderSessionMetric;
        int initialAuthMetricsProvider = providerSessionMetric.getBrowsedAuthenticationMetric()
                .size();
        mRequestSessionMetric.collectMetricPerBrowsingSelect(selection,
                providerSession.mProviderSessionMetric.getCandidatePhasePerProviderMetric());
        providerSession.onUiEntrySelected(selection.getEntryKey(),
                selection.getEntrySubkey(), selection.getPendingIntentProviderResponse());
        int numAuthPerProvider = providerSessionMetric.getBrowsedAuthenticationMetric().size();
        boolean authMetricLogged = (numAuthPerProvider - initialAuthMetricsProvider) == 1;
        if (authMetricLogged) {
            mRequestSessionMetric.logAuthEntry(
                    providerSession.mProviderSessionMetric.getBrowsedAuthenticationMetric()
                            .get(numAuthPerProvider - 1));
        }
    }

    protected void finishSession(boolean propagateCancellation) {
+70 −0
Original line number Diff line number Diff line
@@ -16,13 +16,34 @@

package com.android.server.credentials.metrics;

import com.android.server.credentials.metrics.shared.ResponseCollective;

import java.util.Map;

/**
 * Encapsulates an authentication entry click atom, as a part of track 2.
 * Contains information about what was collected from the authentication entry output.
 */
public class BrowsedAuthenticationMetric {
    private static final String TAG = "BrowsedAuthenticationMetric";
    // The session id of this provider known flow related metric
    private final int mSessionIdProvider;

    // The provider associated with the press, defaults to -1
    private int mProviderUid = -1;

    // The response objects collected for this authentication entry click, default empty
    private ResponseCollective mAuthEntryCollective = new ResponseCollective(Map.of(), Map.of());

    // Indicates if an exception was thrown by this provider, false by default
    private boolean mHasException = false;
    // Indicates the framework only exception belonging to this provider, defaults to empty string
    private String mFrameworkException = "";
    // The status of this particular provider
    private int mProviderStatus = -1;
    // Indicates if this provider returned from the authentication entry query, default false
    private boolean mQueryReturned = false;

    // TODO(b/271135048) - Match the atom and provide a clean per provider session metric
    // encapsulation.

@@ -33,4 +54,53 @@ public class BrowsedAuthenticationMetric {
    public int getSessionIdProvider() {
        return mSessionIdProvider;
    }

    public void setProviderUid(int providerUid) {
        mProviderUid = providerUid;
    }

    public int getProviderUid() {
        return mProviderUid;
    }

    public void setAuthEntryCollective(
            ResponseCollective authEntryCollective) {
        this.mAuthEntryCollective = authEntryCollective;
    }

    public ResponseCollective getAuthEntryCollective() {
        return mAuthEntryCollective;
    }

    public void setHasException(boolean hasException) {
        mHasException = hasException;
    }

    public void setFrameworkException(String frameworkException) {
        mFrameworkException = frameworkException;
    }

    public void setProviderStatus(int providerStatus) {
        mProviderStatus = providerStatus;
    }

    public void setQueryReturned(boolean queryReturned) {
        mQueryReturned = queryReturned;
    }

    public boolean isQueryReturned() {
        return mQueryReturned;
    }

    public int getProviderStatus() {
        return mProviderStatus;
    }

    public String getFrameworkException() {
        return mFrameworkException;
    }

    public boolean isHasException() {
        return mHasException;
    }
}
+63 −5
Original line number Diff line number Diff line
@@ -17,7 +17,9 @@
package com.android.server.credentials.metrics;

import com.android.server.credentials.ProviderSession;
import com.android.server.credentials.metrics.shared.ResponseCollective;

import java.util.LinkedHashMap;
import java.util.Map;

/**
@@ -29,12 +31,22 @@ public class CandidateAggregateMetric {
    private static final String TAG = "CandidateProviderMetric";
    // The session id of this provider metric
    private final int mSessionIdProvider;
    // Indicates if this provider returned from the query phase, default false
    // Indicates if this provider returned from the candidate query phase,
    // true if at least one provider returns validly, even if empty, default false
    private boolean mQueryReturned = false;
    // Indicates the total number of providers this aggregate captures information for, default 0
    private int mNumProviders = 0;
    // Indicates if the authentication entry returned, true if at least one entry returns validly,
    // even if empty, default false
    private boolean mAuthReturned = false;
    // Indicates the total number of authentication entries that were tapped in aggregate, default 0
    private int mNumAuthEntriesTapped = 0;
    // The combined aggregate collective across the candidate get/create
    private ResponseCollective mAggregateCollectiveQuery =
            new ResponseCollective(Map.of(), Map.of());
    // The combined aggregate collective across the auth entry info
    private ResponseCollective mAggregateCollectiveAuth =
            new ResponseCollective(Map.of(), Map.of());

    public CandidateAggregateMetric(int sessionIdTrackOne) {
        mSessionIdProvider = sessionIdTrackOne;
@@ -51,15 +63,48 @@ public class CandidateAggregateMetric {
     * @param providers the providers associated with the candidate flow
     */
    public void collectAverages(Map<String, ProviderSession> providers) {
        // TODO(b/271135048) : Complete this method
        collectQueryAggregates(providers);
        collectAuthAggregates(providers);
    }

    private void collectQueryAggregates(Map<String, ProviderSession> providers) {
        mNumProviders = providers.size();
        Map<String, Integer> responseCountQuery = new LinkedHashMap<>();
        Map<EntryEnum, Integer> entryCountQuery = new LinkedHashMap<>();
        var providerSessions = providers.values();
        for (var session : providerSessions) {
            var sessionMetric = session.getProviderSessionMetric();
            var candidateMetric = sessionMetric.getCandidatePhasePerProviderMetric();
            mQueryReturned = mQueryReturned || candidateMetric.isQueryReturned();
            ResponseCollective candidateCollective = candidateMetric.getResponseCollective();
            ResponseCollective.combineTypeCountMaps(responseCountQuery,
                    candidateCollective.getResponseCountsMap());
            ResponseCollective.combineTypeCountMaps(entryCountQuery,
                    candidateCollective.getEntryCountsMap());
        }
        mAggregateCollectiveQuery = new ResponseCollective(responseCountQuery, entryCountQuery);
    }

    private void collectAuthAggregates(Map<String, ProviderSession> providers) {
        mNumProviders = providers.size();
        Map<String, Integer> responseCountAuth = new LinkedHashMap<>();
        Map<EntryEnum, Integer> entryCountAuth = new LinkedHashMap<>();
        var providerSessions = providers.values();
        for (var session : providerSessions) {
            var metric = session.getProviderSessionMetric();
            mQueryReturned = mQueryReturned || metric
                    .mCandidatePhasePerProviderMetric.isQueryReturned();
            var sessionMetric = session.getProviderSessionMetric();
            var authMetrics = sessionMetric.getBrowsedAuthenticationMetric();
            mNumAuthEntriesTapped += authMetrics.size();
            for (var authMetric : authMetrics) {
                mAuthReturned = mAuthReturned || authMetric.isQueryReturned();
                ResponseCollective authCollective = authMetric.getAuthEntryCollective();
                ResponseCollective.combineTypeCountMaps(responseCountAuth,
                        authCollective.getResponseCountsMap());
                ResponseCollective.combineTypeCountMaps(entryCountAuth,
                        authCollective.getEntryCountsMap());
            }
        }
        mAggregateCollectiveAuth = new ResponseCollective(responseCountAuth, entryCountAuth);
    }

    public int getNumProviders() {
        return mNumProviders;
@@ -69,7 +114,20 @@ public class CandidateAggregateMetric {
        return mQueryReturned;
    }


    public int getNumAuthEntriesTapped() {
        return mNumAuthEntriesTapped;
    }

    public ResponseCollective getAggregateCollectiveQuery() {
        return mAggregateCollectiveQuery;
    }

    public ResponseCollective getAggregateCollectiveAuth() {
        return mAggregateCollectiveAuth;
    }

    public boolean isAuthReturned() {
        return mAuthReturned;
    }
}
Loading