Address review comments
This commit is contained in:
parent
7cd6f1d1cf
commit
2a6326ec0e
2 changed files with 29 additions and 29 deletions
|
@ -7,42 +7,42 @@ package com.zeapo.pwdstore
|
|||
import kotlin.test.assertFalse
|
||||
import kotlin.test.assertNull
|
||||
import kotlin.test.assertTrue
|
||||
import org.junit.Test as test
|
||||
import org.junit.Test
|
||||
|
||||
private infix fun String.matchedForDomain(domain: String) =
|
||||
SearchableRepositoryViewModel.generateStrictDomainRegex(domain)?.containsMatchIn(this) == true
|
||||
|
||||
class StrictDomainRegexTest {
|
||||
@test fun acceptsLiteralDomain() {
|
||||
@Test fun acceptsLiteralDomain() {
|
||||
assertTrue("work/example.org/john.doe@example.org.gpg" matchedForDomain "example.org")
|
||||
assertTrue("example.org/john.doe@example.org.gpg" matchedForDomain "example.org")
|
||||
assertTrue("example.org.gpg" matchedForDomain "example.org")
|
||||
}
|
||||
|
||||
@test fun acceptsSubdomains() {
|
||||
@Test fun acceptsSubdomains() {
|
||||
assertTrue("work/www.example.org/john.doe@example.org.gpg" matchedForDomain "example.org")
|
||||
assertTrue("www2.example.org/john.doe@example.org.gpg" matchedForDomain "example.org")
|
||||
assertTrue("www.login.example.org.gpg" matchedForDomain "example.org")
|
||||
}
|
||||
|
||||
@test fun rejectsPhishingAttempts() {
|
||||
@Test fun rejectsPhishingAttempts() {
|
||||
assertFalse("example.org.gpg" matchedForDomain "xample.org")
|
||||
assertFalse("login.example.org.gpg" matchedForDomain "xample.org")
|
||||
assertFalse("example.org/john.doe@exmple.org.gpg" matchedForDomain "xample.org")
|
||||
assertFalse("example.org.gpg" matchedForDomain "e/xample.org")
|
||||
}
|
||||
|
||||
@test fun rejectNonGpgComponentMatches() {
|
||||
@Test fun rejectNonGpgComponentMatches() {
|
||||
assertFalse("work/example.org" matchedForDomain "example.org")
|
||||
}
|
||||
|
||||
@test fun rejectsEmailAddresses() {
|
||||
@Test fun rejectsEmailAddresses() {
|
||||
assertFalse("work/notexample.org/john.doe@example.org.gpg" matchedForDomain "example.org")
|
||||
assertFalse("work/notexample.org/john.doe@www.example.org.gpg" matchedForDomain "example.org")
|
||||
assertFalse("work/john.doe@www.example.org/foo.org" matchedForDomain "example.org")
|
||||
}
|
||||
|
||||
@test fun rejectsPathSeparators() {
|
||||
@Test fun rejectsPathSeparators() {
|
||||
assertNull(SearchableRepositoryViewModel.generateStrictDomainRegex("ex/ample.org"))
|
||||
}
|
||||
}
|
||||
|
|
|
@ -126,28 +126,6 @@ enum class ListMode {
|
|||
@FlowPreview
|
||||
class SearchableRepositoryViewModel(application: Application) : AndroidViewModel(application) {
|
||||
|
||||
companion object {
|
||||
|
||||
fun generateStrictDomainRegex(domain: String): Regex? {
|
||||
// Valid domains do not contain path separators.
|
||||
if (domain.contains('/'))
|
||||
return null
|
||||
// Matches the start of a path component, which is either the start of the
|
||||
// string or a path separator.
|
||||
val prefix = """(?:^|/)"""
|
||||
val escapedFilter = Regex.escape(domain.replace("/", ""))
|
||||
// Matches either the filter literally or a strict subdomain of the filter term.
|
||||
// We allow a lot of freedom in what a subdomain is, as long as it is not an
|
||||
// email address.
|
||||
val subdomain = """(?:(?:[^/@]+\.)?$escapedFilter)"""
|
||||
// Matches the end of a path component, which is either the literal ".gpg" or a
|
||||
// path separator.
|
||||
val suffix = """(?:\.gpg|/)"""
|
||||
// Match any relative path with a component that is a subdomain of the filter.
|
||||
return Regex(prefix + subdomain + suffix)
|
||||
}
|
||||
}
|
||||
|
||||
private var _updateCounter = 0
|
||||
private val updateCounter: Int
|
||||
get() = _updateCounter
|
||||
|
@ -371,6 +349,28 @@ class SearchableRepositoryViewModel(application: Application) : AndroidViewModel
|
|||
forceUpdateOnNextSearchAction()
|
||||
searchAction.postValue(updateSearchAction(searchAction.value!!))
|
||||
}
|
||||
|
||||
companion object {
|
||||
|
||||
fun generateStrictDomainRegex(domain: String): Regex? {
|
||||
// Valid domains do not contain path separators.
|
||||
if (domain.contains('/'))
|
||||
return null
|
||||
// Matches the start of a path component, which is either the start of the
|
||||
// string or a path separator.
|
||||
val prefix = """(?:^|/)"""
|
||||
val escapedFilter = Regex.escape(domain.replace("/", ""))
|
||||
// Matches either the filter literally or a strict subdomain of the filter term.
|
||||
// We allow a lot of freedom in what a subdomain is, as long as it is not an
|
||||
// email address.
|
||||
val subdomain = """(?:(?:[^/@]+\.)?$escapedFilter)"""
|
||||
// Matches the end of a path component, which is either the literal ".gpg" or a
|
||||
// path separator.
|
||||
val suffix = """(?:\.gpg|/)"""
|
||||
// Match any relative path with a component that is a subdomain of the filter.
|
||||
return Regex(prefix + subdomain + suffix)
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
private object PasswordItemDiffCallback : DiffUtil.ItemCallback<PasswordItem>() {
|
||||
|
|
Loading…
Reference in a new issue