Detta problem löses enkelt i 12c med funktionen STANDARD_HASH .
Lösningen i tidigare versioner är bara något mer komplicerad. Bygg ett enkelt omslag runt DBMS_CRYPTO som fungerar precis som STANDARD_HASH:
--Imitation of the 12c function with the same name.
--Remember to drop this function when you upgrade!
create or replace function standard_hash(
p_string varchar2,
p_method varchar2 default 'SHA1'
) return varchar2 is
v_method number;
v_invalid_identifier exception;
pragma exception_init(v_invalid_identifier, -904);
begin
--Intentionally case-sensitive, just like the 12c version.
if p_method = 'SHA1' then
v_method := dbms_crypto.hash_sh1;
--These algorithms are only available in 12c and above.
$IF NOT DBMS_DB_VERSION.VER_LE_11 $THEN
elsif p_method = 'SHA256' then
v_method := dbms_crypto.hash_sh256;
elsif p_method = 'SHA384' then
v_method := dbms_crypto.hash_sh384;
elsif p_method = 'SHA512' then
v_method := dbms_crypto.hash_sh512;
$END
elsif p_method = 'MD5' then
v_method := dbms_crypto.hash_md5;
else
raise v_invalid_identifier;
end if;
return rawToHex(dbms_crypto.hash(utl_raw.cast_to_raw(p_string), v_method));
end;
/
Du kan behöva logga in med SYS och ge din användare åtkomst till DBMS_CRYPTO för att funktionen ska fungera:
grant execute on sys.dbms_crypto to <your_schema>;
Skapa en offentlig synonym, ge den till alla, och det fungerar på exakt samma sätt.
create public synonym standard_hash for <schema with function>.standard_hash;
grant execute on standard_hash to public;
select standard_hash('Some text', 'MD5') from dual;
9DB5682A4D778CA2CB79580BDB67083F
select standard_hash('Some text', 'md5') from dual;
ORA-00904: : invalid identifier
Här är ett enkelt exempel på hur du använder funktionen:
update some_table
set column1 = standard_hash(column1),
column2 = standard_hash(column2);
Men det kan gå långsamt att uppdatera stora mängder data. Det kan vara snabbare att skapa en ny tabell, släppa den gamla, byta namn på den nya etc. Och hashvärdet kan vara större än kolumnstorleken, det kan vara nödvändigt att alter table some_table modify column1 varchar2(40 byte);
Det förvånar mig hur många produkter och verktyg det finns för att göra en så enkel sak.