sql >> データベース >  >> RDS >> Mysql

ユーザー名とパスワードをデータベースに保存しても安全ですか?

    基本的なセキュリティ対策を講じてパスワードを保存するプロセスは非常に簡単です。

    • パスワードをソルトでハッシュする
    • ユーザー/パスワードごとに異なるソルトを使用する
    • ハッシュされたパスワードを使用してソルトをDBに保存します
    • ログインしようとしたときに、同じ方法で試行したPWを実行します。結果を比較します。

    正しいパスワードを入力すると、ハッシュされたPWが一致します。ハッシュは、ユーザーを攻撃から保護するだけでなく、管理人がmembersと一緒に画面を歩いていることからも保護します。 展示されているテーブル。

    ソルトの作成とPWのハッシュ

    ' salt size is 32 (0-31
    Private Const SaltSize As Integer = 31
    ...
    
    Dim dbPW As String = TextBox1.Text
    Dim dbSalt = CreateNewSalt(SaltSize)
    ' eg: "dsEGWpJpwfAOvdRZyUo9rA=="
    
    Dim SaltedPWHash As String = GetSaltedHash(dbPW, dbSalt)
    ' examples:
    ' using SHA256: bbKN8wYYgoZmNaG3IsQ2DPS2ZPIOnenl6i5NwUmrGmo=
    ' using SHA512: 
    ' 0vqZWBIbOlyzL25l9iWk51CxxJTiEM6QUZEH1ph+/aNp+lk4Yf8NYv8RLhYtbqCNpOqO3y8BmM+0YWtbAhE+RA=="
    

    PWハッシュとソルトをユーザーのレコードの一部として保存します。ソルトは秘密ではありませんが、ユーザーがパスワードを変更したとき/変更した場合に変更してください。

    ログイン試行の比較

    ' check if PW entered equals DB
    Dim pwTry = TextBox2.Text
    ' hash the login attempt using the salt stored in the DB
    Dim pwLogin = GetSaltedHash(pwTry, dbSalt)
    
    ' compare the hash of what they entered to whats in the DB:
    If String.Compare(SaltedPWHash, pwLogin, False) = 0 Then
        ' okay!
        Console.Beep()
    End If
    

    ユーザーが同じPWを入力すると、同じハッシュになるはずです。それはそれと同じくらい簡単です。ハッシュコードはそれほど複雑ではありません:

    ハッシュメソッド

    Private Function GetSaltedHash(pw As String, salt As String) As String
        Dim tmp As String = pw & salt
    
        ' or SHA512Managed
        Using hash As HashAlgorithm = New SHA256Managed()
            ' convert pw+salt to bytes:
            Dim saltyPW = Encoding.UTF8.GetBytes(tmp)
            ' hash the pw+salt bytes:
            Dim hBytes = hash.ComputeHash(saltyPW)
            ' return a B64 string so it can be saved as text 
            Return Convert.ToBase64String(hBytes)
        End Using
    
    End Function
    
    Private Function CreateNewSalt(size As Integer) As String
        ' use the crypto random number generator to create
        ' a new random salt 
        Using rng As New RNGCryptoServiceProvider
            ' dont allow very small salt
            Dim data(If(size < 7, 7, size)) As Byte
            ' fill the array
            rng.GetBytes(data)
            ' convert to B64 for saving as text
            Return Convert.ToBase64String(data)
        End Using
    End Function
    
    • GUID(System.Guid.NewGuid.ToString)のようなものを使用したくなります )塩としてですが、暗号化乱数ジェネレーターを使用するのはそれほど難しいことではありません。
    • ハッシュされたパスワードと同様に、エンコードのために返される文字列は長くなります。
    • ユーザーがパスワードを変更するたびに、新しいソルトを作成します。グローバルソルトを使用しないでください。目的が損なわれます。
    • PWを複数回ハッシュすることもできます。重要なのは、攻撃された場合にさまざまな組み合わせをすべて試すのに長い時間をかけることです。
    • 関数はSharedの理想的な候補です /static クラスのメンバー。

    また、ケネス によってリンクされている記事にも注意してください 読む価値は十分にあります。

    記事 に注意してください 言及The salt should be stored in the user account table alongside the hash これは、Saltが必要だという意味ではありません DBの列。リンク先の記事で次のことが行われていることがわかります。

    Dim dbPW As String = TextBox1.Text
    Dim dbSalt = CreateNewSalt(SaltSize)
    
    ' get the salted PW hash
    Dim SaltedPWHash As String = GetSaltedHash(dbPW, dbSalt)
    ' store salt with the hash:
    SaltedPWHash = String.Format("{0}:{1}", dbSalt, dbPW)
    ' salt + ":" + hashed PW now ready to store in the db
    

    ハッシュされたパスワードからソルトを分割するには:

    Dim SaltAndPWHash = rdr.Item("PWHash").ToString()
    
    Dim split = SaltAndPWHash.Split(":"c)    ' split on ":"
    Dim Salt = split(0)                      ' element(0) == salt
    Dim StoredPWHash = split(1)              ' element(1) == hashed PW
    

    両方の部分が必要です。PWで試行されたログをハッシュした後、それをsplit(1)と比較します。 。



    1. ゼロ/0の結果をCOUNT集計に含める方法は?

    2. 例外の取得ORA-00942:表またはビューが存在しません-既存の表に挿入する場合

    3. MSAccessプロジェクトのすべてのコントロールのコントロールソースを検査します

    4. プレーンADOを使用してSQLServerからビュー定義を取得する方法はありますか?