此包适合Oracle 10g 之前的版本,10g及之后出现了DBMS_CRYPTO 包(推荐使用)
在执行使用下面的函数的时候要注意权限,在sys账号下或者把这个包授权给其他用户也行。
下面加解密传入两个参数,(需要加密的数据,秘钥),这里的秘钥自己随意,但是要解密的话秘钥要和加密的一样。
grant execute on sys.dbms_crypto to siebel;-- siebel 是用户名
加密
CREATE OR REPLACE function
ds_func_encrypt_des(p_text varchar2, p_key varchar2) return varchar2 is
v_text varchar2(4000);
v_enc varchar2(4000);
raw_input RAW(20000) ;
key_input RAW(1000) ;
decrypted_raw RAW(20000);
v_ErrorText varchar2(500);
begin
if(p_text is null or p_text = '' )
then return '';
end if;
dbms_output.put_line(p_text);
v_text := rpad( p_text, (trunc(lengthb(p_text)/8)+1)*8, chr(0));
dbms_output.put_line(v_text);
raw_input := UTL_I18N.STRING_TO_RAW(v_text,'ZHS16GBK');
key_input := UTL_I18N.STRING_TO_RAW(p_key,'ZHS16GBK');
dbms_obfuscation_toolkit.DESEncrypt(input => raw_input,key => key_input,encrypted_data =>decrypted_raw);
v_enc := rawtohex(decrypted_raw);
dbms_output.put_line(v_enc);
return v_enc;
exception
when others then
v_ErrorText := 'dserror:'||SUBSTR(SQLERRM, 1, 200);
return v_ErrorText;
end;
解密
CREATE OR REPLACE function ds_func_decrypt_des(p_text varchar2, p_key varchar2) return varchar2 is
p_text_raw RAW(20000);
p_key_raw RAW(20000);
v_text_raw RAW(20000);
v_text varchar2(4000);
v_ErrorText varchar2(500);
begin
if(p_text is null or p_text = '' )
then return '';
end if;
p_text_raw := HEXTORAW(p_text);
p_key_raw := UTL_I18N.STRING_TO_RAW(p_key, 'ZHS16GBK');
dbms_obfuscation_toolkit.DESDECRYPT(input => p_text_raw, key =>p_key_raw, decrypted_data=> v_text_raw);
v_text := UTL_I18N.RAW_TO_CHAR(v_text_raw, 'ZHS16GBK');
dbms_output.put_line(v_text);
return rtrim(v_text,chr(0));
exception
when others then
v_ErrorText := 'dserror:'||SUBSTR(SQLERRM, 1, 200);
return v_ErrorText;
end;
如果是在sys账号下创建的函数,其他用户要使用的话,需要授权。授权后调用要加前缀sys.
比如:sys.ds_func_encrypt_des ()
-- 在sys账号下执行
-- 授权
grant execute on ds_func_encrypt_des to siebel;
grant execute on ds_func_decrypt_des to siebel;
-- 取消授权 使用的话siebel账号不能调用了,
revoke execute on ds_func_encrypt_des from siebel;
revoke execute on ds_func_decrypt_des from siebel;
之后直接使用就可以了,我举个例子:
在Oracle的Functionsl里面会找到你创建的函数
加密
解密
授权和上面的一样(sys账号下不需要)
加解密函数—秘钥写死,传的时候只需要一个加解密的数据即可
-- 加密
create or replace function ENCRYPTBYKEY(string_in in varchar2) return raw is
string_in_raw RAW(1024) := UTL_RAW.CAST_TO_RAW(string_in);
key_string varchar2(32) := 'molaerpfadfaerewrewrewrewrf87980';
key_raw RAW(128) := UTL_RAW.CAST_TO_RAW(key_string);
encrypted_raw RAW(1024);
begin
encrypted_raw := dbms_crypto.Encrypt(src => string_in_raw,
typ => DBMS_CRYPTO.DES3_CBC_PKCS5,
key => key_raw);
return encrypted_raw;
end;
-- 解密
create or replace function DECRYPTBYKEY(raw_in in raw) return varchar2 is
string_out varchar2(1024);
key_string varchar2(32) := 'molaerpfadfaerewrewrewrewrf87980';
key_raw RAW(128) := UTL_RAW.CAST_TO_RAW(key_string);
decrypted_raw RAW(1024);
begin
decrypted_raw := dbms_crypto.Decrypt(src => raw_in,
typ => DBMS_CRYPTO.DES3_CBC_PKCS5,
key => key_raw);
string_out := UTL_RAW.cast_to_varchar2(decrypted_raw);
return string_out;
end;
加解密函数—传秘钥的函数
-- 加密 传秘钥
create or replace function YENCRYPTBYKEY(string_in in varchar2,key_in in varchar2) return raw is
string_in_raw RAW(1024) := UTL_RAW.CAST_TO_RAW(string_in);
key_string varchar2(32) := key_in;
key_raw RAW(128) := UTL_RAW.CAST_TO_RAW(key_string);
encrypted_raw RAW(1024);
begin
encrypted_raw := dbms_crypto.Encrypt(src => string_in_raw,
typ => DBMS_CRYPTO.DES3_CBC_PKCS5,
key => key_raw);
return encrypted_raw;
end;
-- 解密 传秘钥
create or replace function YDECRYPTBYKEY(raw_in in raw,key_in in varchar2) return varchar2 is
string_out varchar2(1024);
key_string varchar2(32) := key_in;
key_raw RAW(128) := UTL_RAW.CAST_TO_RAW(key_string);
decrypted_raw RAW(1024);
begin
decrypted_raw := dbms_crypto.Decrypt(src => raw_in,
typ => DBMS_CRYPTO.DES3_CBC_PKCS5,
key => key_raw);
string_out := UTL_RAW.cast_to_varchar2(decrypted_raw);
return string_out;
end;
以上两个都可以,看使用哪一个
如果是在sys账号下创建的函数,其他用户要使用的话,需要授权。授权后调用要加前缀sys.
比如:sys.YENCRYPTBYKEY()
-- 在sys账号下执行
-- 授权
grant execute on YDECRYPTBYKEY to siebel;
grant execute on YENCRYPTBYKEY to siebel;
-- 取消授权 使用的话siebel账号不能调用了,
revoke execute on YDECRYPTBYKEY from siebel;
revoke execute on YENCRYPTBYKEY from siebel;
有无秘钥的两个方法都写出来了如下。
注意:
在where条件里是不能调用函数的,想要调用的话写法如下:其中dual是自带的表,Oracle都会有的,就是个空表。
where phone = (select YENCRYPTBYKEY('123456789') from dual)
-- 加密 AES256
create or replace function ENCRYPTBYKEY(string_in in varchar2) return raw is
string_in_raw RAW(1024) := utl_i18n.string_to_raw(string_in,'AL32UTF8');
key_string varchar2(32) := '72f606d870054588851dbed8e57c45fa';
key_raw RAW(128) := utl_i18n.string_to_raw(key_string,'AL32UTF8');
encrypted_raw RAW(1024);
begin
encrypted_raw := dbms_crypto.Encrypt(src => string_in_raw,
typ => dbms_crypto.encrypt_aes256 + dbms_crypto.chain_cbc + dbms_crypto.pad_pkcs5,
key => key_raw);
return encrypted_raw;
end;
-- 解密
create or replace function DECRYPTBYKEY(raw_in in raw) return varchar2 is
string_out varchar2(1024);
key_string varchar2(32) := '72f606d870054588851dbed8e57c45fa';
key_raw RAW(128) := utl_i18n.string_to_raw(key_string,'AL32UTF8');
decrypted_raw RAW(1024);
begin
decrypted_raw := dbms_crypto.Decrypt(src => raw_in,
typ => dbms_crypto.encrypt_aes256 + dbms_crypto.chain_cbc + dbms_crypto.pad_pkcs5,
--typ => DBMS_CRYPTO.DES3_CBC_PKCS5,
key => key_raw);
string_out := UTL_RAW.cast_to_varchar2(decrypted_raw);
return string_out;
end;
在Idea创建一个普通的Java程序即可,写完打成jar包。如果是Java程序需要调用Http接口,需要导入下面四个jar包。
打完的jar包放在数据库所在的服务器,进入jar包所在的目录下
// 加载jar包编译出来导入Oracle数据库里面 loadjava -u 用户名/密码@连接名 -r -v -f -genmissing -s -grant public jar包
loadjava -u SYS/123456@orcl -r -v -f -genmissing -s -grant public Test.jar
// 删除jar包编译出来导入Oracle数据库里的程序 dropjava -u 用户名/密码@连接名 -r -v -f -genmissing -s -grant public jar包
dropjava -u SYS/123456@orcl -r -v -f -genmissing -s -grant public Test.jar
打开数据库执行sql语句
-- YgetName是自己定义的函数名,DsddPwd是Java类,getName是类下的一个方法
CREATE OR REPLACE FUNCTION YgetName(da VARCHAR2) RETURN VARCHAR2 AS
LANGUAGE JAVA NAME 'DsddPwd.getName(java.lang.String) return java.lang.String';