VBScriptの正規表現でパスワードに半角英数字と半角記号が使用されているか検証する

 パスワード設定の際に半角数字,半角英字,半角記号をそれぞれ最低でも 1 文字使用するよう求められるケースは多いと思います.今回は VBScript の正規表現を用いてパスワードをチェックする方法を紹介します.

 制約条件を半角英数字,半角記号を最低でも 1 文字用いることとし,文字列長を 8 文字以上とします.下図のようにユーザーフォーム上にラベルとテキストボックスとコマンドボタンを配置します.それぞれ Label1, TextBox1, CommandButton1 とします.

EnterPassword

 下記コードの 23 行目で制約条件を表現します.コメントアウトした 22 行目は半角英数字のみを 8 文字以上用いる場合の正規表現です.文字クラス内でエスケープが必要なメタ文字は \ と ] の 2 種類です.

Option Explicit

Private Sub CommandButton1_Click()
    With TextBox1
        If Not CheckPassword(.Text) Then
            .SetFocus
            .SelStart = 0
            .SelLength = Len(.Text)
            Exit Sub
        Else
            
        End If
    End With
    Unload Me
End Sub

Function CheckPassword(InputString As String) As Boolean
    Dim myReg   As Object
    CheckPassword = False
    Set myReg = CreateObject("VBScript.RegExp")
    With myReg
       '.Pattern = "(?!^[0-9]*$)(?!^[a-zA-Z]*$)^([a-zA-Z0-9]{8,})$"
        .Pattern = "(?!^[0-9]*$)(?!^[a-zA-Z]*$)(?!^[!-/:-@[-`{-~]*$)(?!^[a-zA-Z0-9]*$)(?!^[!-@[-`{-~]*$)(?!^[!-/:-~]*$)^([!-~]{8,})$"
        .IgnoreCase = False
        .Global = True
    End With
    If myReg.Test(InputString) Then
        CheckPassword = True
    End If
    Set myReg = Nothing
End Function

Private Sub UserForm_Initialize()
    With TextBox1
        .IMEMode = fmIMEModeDisable
        .PasswordChar = "*"
    End With
End Sub

 ここで解説が必要かと思います.(?!pattern) は否定先読みを示し,SQL で言うところの EXCEPT 演算子と同じ働きをします.半角英数字と半角記号を最低でも 1 文字以上使用するとは,下表の文字の組み合わせを許可しないということです.下図の 3 つの円の重なる領域を求めるには,その周辺の領域を引き算して求めます.許可しないパターンを否定先読みで予めフィルタリングしておき,最後に全種類の文字クラスの文字列長をチェックしています.集合論とも考え方の重なる領域です.ちなみに,n 種類の文字種を検証するのに必要な否定先読みのパターン数は 2n – 2 です.

Not Needed Negative Lookahead Pattern
Number (?!^[0-9]*$)
Character (?!^[a-zA-Z]*$)
Symbol (?!^[!-/:-@[-`{-~]*$)
Character and number (?!^[a-zA-Z0-9]*$)
Number and symbol (?!^[!-@[-`{-~]*$)
Character and symbol (?!^[!-/:-~]*$)

PasswordValidation

参照:
ASP.NET への入力を制約するために正規表現を使用する方法
正規表現の構文
ASCII文字コード(0-127)一覧表
インターフェースとしてのEXCEL VBAによるユーザーフォーム