当我在Oracle中解码Base64字符串(NVARCHAR2
)时,我试图获得与Java中相同的结果。
我确实有以下字符串:N'AAECAwQFBgdNu+qx2ZcqsA=='
,它基本上是一个加密的密码,打包成Base64编码。
在Java中,我正在这样做:
byte[] bytes = Base64.decodeBase64(testValue.getBytes());
for(byte b: bytes){
System.out.print(String.valueOf(b & 0xFF) + " "); //Decimal (unsigned)
}
for(byte b: bytes){
System.out.print(Integer.toHexString(b & 0xFF) + " "); //Hex
}
印在我下面:
Unsigned: 0 1 2 3 4 5 6 7 77 187 234 177 217 151 42 176
Hex: 0 1 2 3 4 5 6 7 4d bb ea b1 d9 97 2a b0
现在,我想复制Base64解码,就像它是用Java制造的。我正在尝试使用PL/SQL-函数:
base64DecodedInput:= UTL_ENCODE.base64_decode(UTL_I18N.STRING_TO_RAW(valueToDecrypt, charset));
DBMS_OUTPUT.PUT_LINE ( 'Base64 decoded is: ' || base64DecodedInput);
字符集是: AL16UTF16和valueToDecrypt是我前面提到的作为NVARCHAR2(200)
的测试字符串
DBMS_OUTPUT打印我:
Base64 decoded is: 0000004200300105A8308FDD02FE02B11B7901EA02C0
这是不对的!
我错过了什么。PL/SQL不使用url安全解码吗?
我被卡住了。
代码是PL/SQL-函数的一部分:
CREATE OR REPLACE FUNCTION decodeBase64
(valueToDecrypt IN NVARCHAR2)
RETURN NVARCHAR2
AS
--Declaration area
charset VARCHAR(100);
base64DecodedInput RAW(2000);
...
服务器/数据库设置如下:
NLS_RDBMS_VERSION 12.1.0.2.0
NLS_NCHAR_CONV_EXCP FALSE
NLS_LENGTH_SEMANTICS BYTE
NLS_COMP BINARY
NLS_DUAL_CURRENCY $
NLS_TIMESTAMP_TZ_FORMAT DD-MON-RR HH.MI.SSXFF AM TZR
NLS_TIME_TZ_FORMAT HH.MI.SSXFF AM TZR
NLS_TIMESTAMP_FORMAT DD-MON-RR HH.MI.SSXFF AM
NLS_TIME_FORMAT HH.MI.SSXFF AM
NLS_SORT BINARY
NLS_DATE_LANGUAGE AMERICAN
NLS_DATE_FORMAT DD-MON-RR
NLS_CALENDAR GREGORIAN
NLS_NUMERIC_CHARACTERS .,
NLS_NCHAR_CHARACTERSET AL16UTF16
NLS_CHARACTERSET WE8MSWIN1252
NLS_ISO_CURRENCY AMERICA
NLS_CURRENCY $
NLS_TERRITORY AMERICA
NLS_LANGUAGE AMERICAN
发布于 2017-07-04 06:41:20
请看一下未加工文档:
此函数将使用一定数量的数据字节表示的VARCHAR2值转换为具有该数据字节数的原始值。
你应该用这个:
base64DecodedInput:= UTL_ENCODE.base64_decode(UTL_RAW.CAST_TO_RAW(TO_CHAR(valueToDecrypt)));
DBMS_OUTPUT.PUT_LINE ( 'Base64 decoded is: ' || base64DecodedInput);
00010203040506074DBBEAB1D9972AB0
哪一个(格式化)应该等于期望的结果:
00 01 02 03 04 05 06 07 4D BB EA B1 D9 97 2A B0
将NVARCHAR2
用于BASE64字符串是非常无用的。BASE64编码的主要目的是仅用ASCII字符表示任意数据,因此NVARCHAR2没有任何意义。由于BASE64只包含ASCII,所以您不必担心CAST(... AS VARCHAR2(200))
上的任何字符编码。
当然,对于解码的字符串数据类型,NVARCHAR2
可能非常有用。
发布于 2017-07-04 07:49:04
一个更好的方法,@Wernfried回答,是使用转换,而不是铸造。
在本例中,由于Java正在打印UTF-8值,您必须在解码之前将NVARCHAR2转换为UTF-8。
base64DecodedInput:= UTL_ENCODE.base64_decode(UTL_I18N.STRING_TO_RAW(valueToDecrypt, conversionCharset));
https://stackoverflow.com/questions/44898285
复制相似问题