0

我正在尝试学习加密,我想出了以下代码

import java.util.Base64
object JavaCryptoEncryption{

  val Algorithm = "AES/CBC/PKCS5Padding"
  val IvSpec = new IvParameterSpec(new Array[Byte](16))

  def encrypt(text: String, b64secret: String): String = {
    val cipher = Cipher.getInstance(Algorithm)
    val key = new SecretKeySpec(Base64.getDecoder.decode(b64secret), "AES")
    cipher.init(Cipher.ENCRYPT_MODE, key, IvSpec)

    new String(Base64.getEncoder.encode(cipher.doFinal(text.getBytes("utf-8"))), "utf-8")
  }

  def decrypt(text: String, b64secret: String): String = {
    val cipher = Cipher.getInstance(Algorithm)
    val key = new SecretKeySpec(Base64.getDecoder.decode(b64secret), "AES")
    cipher.init(Cipher.DECRYPT_MODE, key, IvSpec)

    new String(cipher.doFinal(Base64.getDecoder.decode(text.getBytes("utf-8"))), "utf-8")
  }
}

在我系统的其他地方,我定义并存储了密钥。然后我将JavaCryptoEncryption.encryptandJavaCryptoEncryption.decrypt应用于一个字符串值,它工作正常。但是,当我想将它们转换为 UDF 并应用于 DataFrame 的列时,我得到org.apache.spark.SparkException: Task not serializable. 类似的代码(没有 iv)适用于 AES/ECB/PKCS5Padding。某些模式不支持并行性吗?有办法吗?或者也许有不同的原因?

4

1 回答 1

0

我认为问题在于您正在IvParameterSpec驱动程序上创建实例,然后 Spark 尝试对其进行序列化并发送到执行程序(实际上执行所有 UDF)。也许,尝试将所有与对象创建相关的代码放入 UDF 本身,然后将您的密钥作为 UDF 参数提供?这样你只需String要向工作人员发送一个,所以不应该有序列化问题。

于 2020-02-25T16:14:54.373 回答