Обеспечение безопасности передачи данных через Интернет имеет решающее значение, особенно когда речь идет о конфиденциальной информации. Шифрование играет решающую роль в защите таких данных. В этой статье мы обсудим, как использовать шифрование AES в Java и JavaScript, обеспечивая при этом совместимость между ними.

Во-первых, давайте начнем с создания пары ключей RSA в Java, используя следующий код:

public class RSAKeyPairGenerator {

    private PrivateKey privateKey;
    private PublicKey publicKey;

    public RSAKeyPairGenerator() throws NoSuchAlgorithmException {
        KeyPairGenerator keyGen = KeyPairGenerator.getInstance("RSA");
        keyGen.initialize(2056);
        KeyPair pair = keyGen.generateKeyPair();
        this.privateKey = pair.getPrivate();
        this.publicKey = pair.getPublic();
    }

    public PrivateKey getPrivateKey() {
        return privateKey;
    }

    public PublicKey getPublicKey() {
        return publicKey;
    }
}

Этот код генерирует 2056-битную пару ключей RSA, состоящую из закрытого ключа и открытого ключа. Методы `getPrivateKey()` и `getPublicKey()` возвращают закрытый и открытый ключи соответственно.

Следующий код предоставляет методы для декодирования закрытого ключа в кодировке Base64 и открытого ключа в объект «PrivateKey» и объект «PublicKey», которые будут использоваться позже для шифрования обычного текста в зашифрованный текст и расшифровки зашифрованного текста в обычный текст.

public class RSAEncryptionUtils {
    public static PublicKey getPublicKey(String base64PublicKey) {
        PublicKey publicKey = null;
        try {
            X509EncodedKeySpec keySpec = new X509EncodedKeySpec(Base64.getDecoder().decode(base64PublicKey.getBytes()));
            KeyFactory keyFactory = KeyFactory.getInstance("RSA");
            publicKey = keyFactory.generatePublic(keySpec);
            return publicKey;
        } catch (NoSuchAlgorithmException | InvalidKeySpecException e) {
            e.printStackTrace();
        }
        return publicKey;
    }

    public static PrivateKey getPrivateKey(String base64PrivateKey) {
        PrivateKey privateKey = null;
        PKCS8EncodedKeySpec keySpec = new PKCS8EncodedKeySpec(Base64.getDecoder().decode(base64PrivateKey.getBytes()));
        KeyFactory keyFactory = null;
        try {
            keyFactory = KeyFactory.getInstance("RSA");
        } catch (NoSuchAlgorithmException e) {
            e.printStackTrace();
        }
        try {
            privateKey = keyFactory.generatePrivate(keySpec);
        } catch (InvalidKeySpecException e) {
            e.printStackTrace();
        }
        return privateKey;
    }
}

Теперь мы можем использовать пару ключей RSA для шифрования обычного текста и расшифровки зашифрованного текста.

Вот код Java для шифрования:

public static byte[] encrypt(String data, String publicKey) throws BadPaddingException, IllegalBlockSizeException,
 InvalidKeyException, NoSuchPaddingException, NoSuchAlgorithmException {
 Cipher cipher = Cipher.getInstance("RSA/ECB/OAEPWITHSHA-256ANDMGF1PADDING");
 cipher.init(Cipher.ENCRYPT_MODE, getPublicKey(publicKey));
 return cipher.doFinal(data.getBytes());
}

А вот код Java для расшифровки:

public static String decrypt(String data) throws IllegalBlockSizeException, InvalidKeyException,
   BadPaddingException, NoSuchAlgorithmException, NoSuchPaddingException {
  return decrypt(Base64.getDecoder().decode(data.getBytes()), getPrivateKey(privateKey));
 }
 
public static String decrypt(byte[] data, PrivateKey privateKey) throws NoSuchPaddingException,
 NoSuchAlgorithmException, InvalidKeyException, BadPaddingException, IllegalBlockSizeException {
 Cipher cipher = Cipher.getInstance("RSA/ECB/OAEPWITHSHA-256ANDMGF1PADDING");
 cipher.init(Cipher.DECRYPT_MODE, privateKey);
 return new String(cipher.doFinal(data));
}

Теперь давайте перейдем к части JavaScript. Мы будем использовать библиотеку Forge для шифрования в JavaScript. Вы можете скачать библиотеку Forge с официального сайта или подключить ее через CDN. В следующем коде показано, как зашифровать сообщение с помощью RSA-OAEP с SHA-256 и SHA-1 в качестве функций дайджеста сообщения и генерации маски соответственно.

Код для шифрования с помощью JS:

<html>
<head>
  <script src="https://cdnjs.cloudflare.com/ajax/libs/forge/0.10.0/forge.min.js"></script>
  <script src="https://code.jquery.com/jquery-3.6.0.min.js"></script>
  <script>
    $(document).ready(function() {
      // Base64-encoded public key
      const publicKeyBase64 = 'INSERT YOUR PUBLIC KEY HERE';

      // Convert base64-encoded public key to ASN.1 representation
      const publicKeyAsn1 = forge.asn1.fromDer(forge.util.decode64(publicKeyBase64));

      // Convert ASN.1 public key to Forge public key object
      const publicKey = forge.pki.publicKeyFromAsn1(publicKeyAsn1);

      // Encrypt a message with RSA-OAEP and the public key
      const message = 'Hello, World!';
      const encryptedMessage = publicKey.encrypt(message, 'RSA-OAEP', {
        md: forge.md.sha256.create(),
        mgf1: {
          md: forge.md.sha1.create()
        }
      });

      // Display the encrypted message
      console.log('Encrypted message:', forge.util.encode64(encryptedMessage));
    });
  </script>
</head>
<body>
</body>
</html>

Код для расшифровки с помощью JS:

<html>
<head>
  <script src="https://cdnjs.cloudflare.com/ajax/libs/forge/0.10.0/forge.min.js"></script>
  <script src="https://code.jquery.com/jquery-3.6.0.min.js"></script>
  <script>
    $(document).ready(function() {
      // Base64-encoded private key
      const privateKeyBase64 = 'INSERT YOUR PRIVATE KEY HERE';
      // Convert base64-encoded private key to ASN.1 representation
      const privateKeyAsn1 = forge.asn1.fromDer(forge.util.decode64(privateKeyBase64));

      // Convert ASN.1 private key to Forge private key object
      const privateKey = forge.pki.privateKeyFromAsn1(privateKeyAsn1);

      // Base64-encoded encrypted message
      const encryptedMessageBase64 = 'HERE GOES YOUR ENCRYPTED MESSAGE';

      // Decode base64-encoded encrypted message to a binary format
      const encryptedMessage = forge.util.decode64(encryptedMessageBase64);

      // Decrypt the encrypted message with RSA-OAEP and the private key
      const decryptedMessage = privateKey.decrypt(encryptedMessage, 'RSA-OAEP', {
        md: forge.md.sha256.create(),
        mgf1: {
          md: forge.md.sha1.create()
        }
      });

      // Display the decrypted message
      console.log('Decrypted message:', decryptedMessage);
    });
  </script>
</head>
<body>
</body>
</html>