Clarify package id parsing and AutofillView creation (#6138)

This commit is contained in:
David Perez
2025-11-07 12:07:20 -06:00
committed by GitHub
parent 50e50eb08c
commit 1024f77ddf
2 changed files with 28 additions and 37 deletions

View File

@@ -254,7 +254,9 @@ private fun AssistStructure.ViewNode.traverse(
// Set up mutable lists for collecting valid AutofillViews and ignorable view ids.
val mutableAutofillViewList: MutableList<AutofillView> = mutableListOf()
val mutableIgnoreAutofillIdList: MutableList<AutofillId> = mutableListOf()
var idPackage: String? = this.idPackage
// OS sometimes defaults node.idPackage to "android", which is not a valid
// package name so it is ignored to prevent auto-filling unknown applications.
var storedIdPackage: String? = this.idPackage?.takeUnless { it.isBlank() || it == "android" }
// Try converting this `ViewNode` into an `AutofillView`. If a valid instance is returned, add
// it to the list. Otherwise, ignore the `AutofillId` associated with this `ViewNode`.
@@ -272,12 +274,8 @@ private fun AssistStructure.ViewNode.traverse(
viewNodeTraversalData.ignoreAutofillIds.forEach(mutableIgnoreAutofillIdList::add)
// Get the first non-null idPackage.
if (idPackage.isNullOrBlank() &&
// OS sometimes defaults node.idPackage to "android", which is not a valid
// package name so it is ignored to prevent auto-filling unknown applications.
viewNodeTraversalData.idPackage?.equals("android") == false
) {
idPackage = viewNodeTraversalData.idPackage
if (storedIdPackage == null) {
storedIdPackage = viewNodeTraversalData.idPackage
}
}
}
@@ -286,7 +284,7 @@ private fun AssistStructure.ViewNode.traverse(
// descendant's.
return ViewNodeTraversalData(
autofillViews = mutableAutofillViewList,
idPackage = idPackage,
idPackage = storedIdPackage,
ignoreAutofillIds = mutableIgnoreAutofillIdList,
)
}

View File

@@ -51,35 +51,28 @@ private val AssistStructure.ViewNode.isInputField: Boolean
*/
fun AssistStructure.ViewNode.toAutofillView(
parentWebsite: String?,
): AutofillView? =
this
.autofillId
// We only care about nodes with a valid `AutofillId`.
?.let { nonNullAutofillId ->
if (supportedAutofillHint != null || this.isInputField) {
val autofillOptions = this
.autofillOptions
.orEmpty()
.map { it.toString() }
val autofillViewData = AutofillView.Data(
autofillId = nonNullAutofillId,
autofillOptions = autofillOptions,
autofillType = this.autofillType,
isFocused = this.isFocused,
textValue = this.autofillValue?.extractTextValue(),
hasPasswordTerms = this.hasPasswordTerms(),
website = this.website ?: parentWebsite,
)
buildAutofillView(
autofillOptions = autofillOptions,
autofillViewData = autofillViewData,
autofillHint = supportedAutofillHint,
)
} else {
null
}
}
): AutofillView? {
val nonNullAutofillId = this.autofillId ?: return null
if (this.supportedAutofillHint == null && !this.isInputField) return null
val autofillOptions = this
.autofillOptions
.orEmpty()
.map { it.toString() }
val autofillViewData = AutofillView.Data(
autofillId = nonNullAutofillId,
autofillOptions = autofillOptions,
autofillType = this.autofillType,
isFocused = this.isFocused,
textValue = this.autofillValue?.extractTextValue(),
hasPasswordTerms = this.hasPasswordTerms(),
website = this.website ?: parentWebsite,
)
return buildAutofillView(
autofillOptions = autofillOptions,
autofillViewData = autofillViewData,
autofillHint = this.supportedAutofillHint,
)
}
/**
* The first supported autofill hint for this view node, or null if none are found.