我有一个客户机提供了一个API,它要求发送给他们的数据必须用
. 我试图在Delphi10.3Rio中使用密码箱3,但没有得到与
online test tool
他们指出要核实。很近,但不太近。
这里有很多关于
Unicode
,
PKCS5Padding
,和
related questions
有几件事我想确认一下:
-
密码和密钥的区别
-
PKCS5添加
LB3 Help site
也就是说,填充是根据密码、链接模式等的选择而智能地完成的,那么这是否意味着没有办法强制它使用特定的填充方法?我已经将数据转换为字节数组,并由自己的PKCS5Padding实现,但我认为LB3可能仍在填充。(我试过查看代码,但没有发现任何证据,这就是它所做的。)
我应该在Delphi中使用不同的加密库来完成这个任务吗?
我已经退房了
DelphiEncryptionCompendium
和
DcPCryptV2
为了说明我所做的尝试,我将代码从项目中提取到一个控制台应用程序中。也许我上面的假设是正确的,我的代码或LB3参数中有一个明显的错误,我不明白有人会指出:
program LB3ConsoleTest;
{$APPTYPE CONSOLE}
{$R *.res}
uses
System.SysUtils, System.Classes, System.NetEncoding,
uTPLb_Codec, uTPLb_CryptographicLibrary,
uTPLb_StreamUtils, uTPLb_Constants;
var
Codec: TCodec;
CryptographicLibrary: TCryptographicLibrary;
function PKCS5PadStringToBytes(RawData: string; const PadSize: Integer): TBytes;
{ implement our own block padding }
var
DataLen: Integer;
PKCS5PaddingCount: ShortInt;
begin
Result := TEncoding.UTF8.GetBytes(RawData);
DataLen := Length(RawData);
PKCS5PaddingCount := PadSize - DataLen mod PadSize;
if PKCS5PaddingCount = 0 then
PKCS5PaddingCount := PadSize;
Inc(DataLen, PKCS5PaddingCount);
SetLength(Result, DataLen);
FillChar(Result[DataLen - PKCS5PaddingCount], PKCS5PaddingCount, PKCS5PaddingCount);
end;
procedure InitializeAESKey(const AESKey: string);
{ convert the string to a byte array,
use that to initialize a ByteStream,
and call LB3's InitFromStream }
var
AESKeyBytes: TBytes;
AESKeyStream: TBytesStream;
begin
AESKeyBytes := TEncoding.UTF8.GetBytes(AESKey);
AESKeyStream := TBytesStream.Create(AESKeyBytes);
Codec.InitFromStream(AESKeyStream);
end;
const
RawData = '{"invoice_id":"456456000018047","clerk_id":"0023000130234234","trans_amount":1150034534,"cust_code":"19455605000987890641","trans_type":"TYPE1"}';
AESKeyStr = 'CEAA31AD1EE4BDC8';
var
DataBytes: TBytes;
DataStream: TBytesStream;
ResultStream: TBytesStream;
ResultBytes: TBytes;
Base64Encoder: TBase64Encoding;
begin
// create the LockBox3 objects
Codec := TCodec.Create(nil);
CryptographicLibrary := TCryptographicLibrary.Create(nil);
try
// setup LB3 for AES, 128-bit key, ECB
Codec.CryptoLibrary := CryptographicLibrary;
Codec.StreamCipherId := uTPLb_Constants.BlockCipher_ProgId;
Codec.BlockCipherId := Format(uTPLb_Constants.AES_ProgId, [128]);
Codec.ChainModeId := uTPLb_Constants.ECB_ProgId;
// prep the data, the key, and the resulting stream
DataBytes := PKCS5PadStringToBytes(RawData, 8);
DataStream := TBytesStream.Create(DataBytes);
InitializeAESKey(AESKeyStr);
ResultStream := TBytesStream.Create;
// ENCRYPT!
Codec.EncryptStream(DataStream, ResultStream);
// take the result stream, convert it to a byte array
ResultStream.Seek(0, soFromBeginning);
ResultBytes := Stream_to_Bytes(ResultStream);
// convert the byte array to a Base64-encoded string and display
Base64Encoder := TBase64Encoding.Create(0);
Writeln(Base64Encoder.EncodeBytesToString(ResultBytes));
Readln;
finally
Codec.Free;
CryptographicLibrary.Free;
end;
end.
online tool
生产。
为什么?