PasswordPolicyTest.kt

2.9 KB · raw

1package com.peachpasswords.autofill23import org.junit.Assert.assertEquals4import org.junit.Assert.assertNull5import org.junit.Test67class PasswordPolicyTest {89    @Test fun reads_minlength_and_maxlength_attributes() {10        val p = PasswordPolicy.fromHtmlAttributes(mapOf("minlength" to "8", "maxlength" to "64"))11        assertEquals(8, p.minLength)12        assertEquals(64, p.maxLength)13    }1415    @Test fun ignores_non_positive_lengths() {16        val p = PasswordPolicy.fromHtmlAttributes(mapOf("minlength" to "0", "maxlength" to "-1"))17        assertNull(p.minLength)18        assertNull(p.maxLength)19    }2021    @Test fun pattern_range_fills_both_bounds() {22        val p = PasswordPolicy.fromHtmlAttributes(mapOf("pattern" to ".{8,20}"))23        assertEquals(8, p.minLength)24        assertEquals(20, p.maxLength)25    }2627    @Test fun pattern_min_only() {28        val p = PasswordPolicy.fromHtmlAttributes(mapOf("pattern" to ".{12,}"))29        assertEquals(12, p.minLength)30        assertNull(p.maxLength)31    }3233    @Test fun pattern_exact_sets_both() {34        val p = PasswordPolicy.fromHtmlAttributes(mapOf("pattern" to "[a-z]{10}"))35        assertEquals(10, p.minLength)36        assertEquals(10, p.maxLength)37    }3839    @Test fun attributes_win_over_pattern() {40        val p = PasswordPolicy.fromHtmlAttributes(41            mapOf("minlength" to "6", "maxlength" to "30", "pattern" to ".{8,20}"),42        )43        assertEquals(6, p.minLength)44        assertEquals(30, p.maxLength)45    }4647    @Test fun no_constraints_yields_empty_policy() {48        val p = PasswordPolicy.fromHtmlAttributes(mapOf("autocomplete" to "new-password"))49        assertNull(p.minLength)50        assertNull(p.maxLength)51    }5253    @Test fun generation_prefers_max_length() {54        // Strongest the site accepts.55        assertEquals(64, PasswordPolicy(minLength = 8, maxLength = 64).generationLength())56    }5758    @Test fun generation_caps_at_hard_max() {59        assertEquals(128, PasswordPolicy(maxLength = 500).generationLength())60    }6162    @Test fun generation_snaps_up_to_min() {63        // default 20 < min 25 -> snap up.64        assertEquals(25, PasswordPolicy(minLength = 25).generationLength())65    }6667    @Test fun generation_default_when_unconstrained() {68        assertEquals(PasswordPolicy.DEFAULT_LENGTH, PasswordPolicy().generationLength())69    }7071    @Test fun generation_never_below_one() {72        assertEquals(1, PasswordPolicy(maxLength = 0).generationLength())73    }7475    @Test fun constraint_note_max() {76        val p = PasswordPolicy(maxLength = 20)77        assertEquals("This site allows max 20 characters", p.constraintNote(20))78    }7980    @Test fun constraint_note_min() {81        val p = PasswordPolicy(minLength = 12)82        assertEquals("This site requires at least 12 characters", p.constraintNote(12))83    }8485    @Test fun constraint_note_empty_when_interior() {86        val p = PasswordPolicy(minLength = 8, maxLength = 64)87        assertEquals("", p.constraintNote(30))88    }89}