以前は構造が不十分だったため、現在使用しているデータベースはユーザーのパスワードをテキストとして保存しています。
現在、これらのパスワードを使用する必要があるフロントエンド部分を構築していますが、パスワードを暗号化せずに送信したくはありません。
私の考えは、テキストパスワードを暗号化および復号化するOracle関数を作成し、暗号化されたデータを返すストアドプロシージャでこれらの関数を使用することです。
そうするためのOracleでの最良のアプローチは何でしょうか?
以前は構造が不十分だったため、現在使用しているデータベースはユーザーのパスワードをテキストとして保存しています。
現在、これらのパスワードを使用する必要があるフロントエンド部分を構築していますが、パスワードを暗号化せずに送信したくはありません。
私の考えは、テキストパスワードを暗号化および復号化するOracle関数を作成し、暗号化されたデータを返すストアドプロシージャでこれらの関数を使用することです。
そうするためのOracleでの最良のアプローチは何でしょうか?
データを暗号化および復号化するための独自の関数を作成する場合は、DBMS_CRYPTO encrypt
およびdecrypt
メソッドを適切なパラメータ (つまり、暗号化アルゴリズム、キーなどを選択) で呼び出すだけです。
もちろん、独自のルーチンを作成する場合、キーをデータベースまたはデータベースがアクセスできる場所に格納すると仮定すると、セキュリティのために多くのことを行うことにはなりません。暗号化されていないパスワードをネットワーク経由で送信するのはよくありませんが、暗号化されていないパスワードをデータベースに保存するのは一般的にははるかに悪いことです (またはdecrypt
、データを復号化するためのキーにアクセスできる方法がデータベースにある場合は、暗号化されたパスワード)。一般に、パスワードを見つけるためにネットワーク経由で送信されるデータを傍受するよりも、データベースからデータを盗む方がはるかに簡単です。
もちろん、正しい答えは、パスワードをまったく保存しないようにシステムを再設計することです。元に戻せないパスワード ハッシュ (DBMS_CRYPTO
パッケージを使用して生成することもできます) を保存する必要があります。
DBMS_CRYPTO を見てください。
組み込みのデータを暗号化および復号化する方法があります。独自に作成するよりも優れています。
http://docs.oracle.com/cd/B19306_01/appdev.102/b14258/d_crypto.htm
DBMS_CRYPTO
( )-を使用してパスワードを暗号化するためのパッケージ化された関数 (成功した実装) を次に示します。
CREATE OR REPLACE
PACKAGE BODY encrypt_paswd
AS
G_CHARACTER_SET VARCHAR2(10) := 'AL32UTF8';
G_STRING VARCHAR2(32) := '12345678901234567890123456789012';
G_KEY RAW(250) := utl_i18n.string_to_raw
( data => G_STRING,
dst_charset => G_CHARACTER_SET );
G_ENCRYPTION_TYPE PLS_INTEGER := dbms_crypto.encrypt_aes256
+ dbms_crypto.chain_cbc
+ dbms_crypto.pad_pkcs5;
------------------------------------------------------------------------
--Encrypt a password
--Salt the password
------------------------------------------------------------------------
FUNCTION encrypt_val( p_val IN VARCHAR2 ) RETURN RAW
IS
l_val RAW(32) := UTL_I18N.STRING_TO_RAW( p_val, G_CHARACTER_SET );
l_encrypted RAW(32);
BEGIN
l_val := utl_i18n.string_to_raw
( data => p_val,
dst_charset => G_CHARACTER_SET );
l_encrypted := dbms_crypto.encrypt
( src => l_val,
typ => G_ENCRYPTION_TYPE,
key => G_KEY );
RETURN l_encrypted;
END encrypt_val;
END encrypt_paswd;
これは、encrypt_aes256
「高度な暗号化標準。ブロック暗号。256 ビットの鍵サイズを使用」を使用します。, chain_cbc
- 「暗号ブロック連鎖。平文は、暗号化される前に前の暗号文ブロックと XOR されます。」およびpad_pkcs5
- 「PKCS #5: パスワードベースの暗号化標準に準拠するパディングを提供します」。
これに加えて、同様の関数を作成して復号化できます。お気に入り -
FUNCTION decrypt_val( p_val IN RAW ) RETURN VARCHAR2
IS
l_decrypted RAW(32);
l_decrypted_string VARCHAR2(32);
l_user VARCHAR2(32);
BEGIN
SELECT user
INTO l_user
FROM dual;
if l_user = 'ADMIN' -- you can restrict usage of decrypt to certain db users only.
then
l_decrypted := dbms_crypto.decrypt
( src => p_val,
typ => G_ENCRYPTION_TYPE,
key => G_KEY );
l_decrypted_string := utl_i18n.raw_to_char
( data => l_decrypted,
src_charset => G_CHARACTER_SET );
RETURN l_decrypted_string;
else
RAISE_APPLICATION_ERROR(-20101, 'You are not authorized to use this function - decrypt_val()');
end if;
RETURN 'Unknown';
END decrypt_val;
wrap iname=package_name.pkb
データベースでパッケージをコンパイルする前にパッケージをラップしてから、結果の をコンパイルすることも検討してplb
ください。
または、このようなパスワード ハッシュ アルゴリズム pbkdf2 を使用することもできますhttp://mikepargeter.wordpress.com/2012/11/26/pbkdf2-in-oracle/ rfc で結果を確認しましたhttps://www.ietf.org/ rfc/rfc6070.txtで、正常に動作します。
最小限の反復と key_size については、このリンクを確認してください: PBKDF2 推奨キー サイズ? 結果は 16 進数でエンコードされているため、長さが 2 倍になることに注意してください。
これらの列をデータベースに保存します
PASSWORD_HASH VARCHAR2(512 BYTE),
PASSWORD_SALT VARCHAR2(256 BYTE),
PASSWORD_ITERATIONS NUMBER(10),
PASSWORD_HASH_METHOD VARCHAR2(30 BYTE),
PASSWORD_CHANGED_DT DATE
hash、salt、および iterations は pbkdf2 アルゴリズムにフィードするためのものであり、hash_method は移行目的のためのものであり、changed_dt はパスワードを期限切れにするためのものです。