如何加密凭据对象 - Cipher.doFinal,SealedObject或CipherOutputStream?

时间:2017-09-25 10:13:35

标签: java encryption

我需要加密一组用户凭据并将其发送到SOAP Web服务。文档中提供了以下代码片段(我认为它是C#),我的Java代码基于它。

private string Encrypt256(string text, AesCryptoServiceProvider aes)
{
    // Convert string to byte array
    byte[] src = Encoding.Unicode.GetBytes(text);
    // encryption
    using (ICryptoTransform encrypt = aes.CreateEncryptor())
    {
        byte[] dest = encrypt.TransformFinalBlock(src, 0, src.Length);
        // Convert byte array to Base64 strings
        return Convert.ToBase64String(dest);
    }
}
...
Credentials credential = new Credentials();
credential.UserName = "username";
credential.Password = "password";
credential.ClientUtcTime = DateTime.UtcNow.ToString("yyyy-MM-ddTHH:mm:ssZ", System.Globalization.CultureInfo.InvariantCulture);

//--Serialize credential
XmlSerializer serializer = new XmlSerializer(credential.GetType());
string xmlCredential = string.Empty;
using (var stringwriter = new System.IO.StringWriter())
{
    serializer.Serialize(stringwriter, credential);
    xmlCredential = stringwriter.ToString();
}
//--Encrypt credential with AES256 symmetric
String encryptedCredential = Encrypt256(xmlCredential, aesServiceProvider);
...

以下是我的Java代码。

KeyGenerator kg = KeyGenerator.getInstance("AES");
kg.init(256);
SecretKey sk = kg.generateKey();
Cipher aesCipher = Cipher.getInstance("AES");
aesCipher.init(Cipher.ENCRYPT_MODE, sk);
Credentials cred = new UsernamePasswordCredentials("username", "password");//no need for time field?
String eCred = Base64.encodeBase64String(aesCipher.doFinal(objectToByteArray(cred)));

...

private byte[] objectToByteArray(Object obj) {
    byte[] bytes = null;
    try (
        ByteArrayOutputStream bos = new ByteArrayOutputStream();
        ObjectOutputStream oos = new ObjectOutputStream(bos);
    ) {
        oos.writeObject(obj);
        oos.flush();
        bytes = bos.toByteArray();
    }
    catch (IOException e) {
        e.printStackTrace();
    }

    return bytes;
}

然后我遇到了SealedObjectCipherOutputStream。我尝试为这些代码片段编写代码片段。

使用 SealedObject

// slight change here; cred must implement Serializable
UsernamePasswordCredentials cred = new UsernamePasswordCredentials("username", "password");

// same as above except for the following two lines
SealedObject so = new SealedObject(cred, aesCipher);
String eCred = Base64.encodeBase64String(objectToByteArray(so));

使用 CipherOutputStream

Credentials cred = new UsernamePasswordCredentials("username", "password");
ByteArrayOutputStream bos = new ByteArrayOutputStream();
CipherOutputStream cos = new CipherOutputStream(bos, aesCipher);
cos.write(objectToByteArray(cred));
cos.close();

String eCred = Base64.encodeBase64String(bos.toByteArray());

对于所有三个代码段,代码是否正确?考虑到这个代码会被频繁调用,哪种方法效率最高?

0 个答案:

没有答案