предисловие
На собеседованиях нас часто спрашивают, как спроектировать безопасный внешний интерфейс?На самом деле мы можем ответить на это, подписав и проверив, что сделает ваш интерфейс более безопасным. Далее эта статья поможет вам узнать о подписании и проверке. От теории к реальному бою, давай~
- Понятия, связанные с криптографией
- Концепция проверки подписи
- Зачем нужно подписывать и подтверждать
- Введение в алгоритмы шифрования
- API для проверки подписи
- Реализация кода проверки подписи
- Общественный номер: маленький мальчик собирает улиток
Эта статья попала в личный гитхаб, если статья окажется полезной, вы можете поставить ей звезду:
Понятия, связанные с криптографией
открытый текст, зашифрованный текст, ключ, шифрование, дешифрование
- Открытый текст: Относится к информации/данным, которые не зашифрованы.
- Зашифрованный текст: после того, как открытый текст будет зашифрован алгоритмом шифрования, он станет зашифрованным текстом для обеспечения безопасности данных.
- Ключ: параметр, который вводится в алгоритм, преобразующий открытый текст в зашифрованный текст или преобразующий зашифрованный текст в открытый текст. Ключи делятся на симметричные и асимметричные.
- Шифрование: процесс преобразования открытого текста в зашифрованный.
- Расшифровка: процесс восстановления зашифрованного текста в открытый текст.
Симметричное шифрование, асимметричное шифрование
-
Симметричное шифрование: алгоритм шифрования, использующий один и тот же ключ для шифрования и дешифрования.
-
Асимметричное шифрование. Для алгоритмов асимметричного шифрования требуются два ключа (открытый ключ и закрытый ключ). Открытый ключ и закрытый ключ существуют парами, и если данные зашифрованы открытым ключом, только соответствующий закрытый ключ может их расшифровать.
Что такое открытый ключ и закрытый ключ?
- Открытый ключ и закрытый ключ — это ключи, которые существуют парами.Если данные зашифрованы с помощью открытого ключа, их можно расшифровать только с помощью соответствующего закрытого ключа.
- На самом деле открытый ключ — это открытый ключ, а закрытый ключ — это секретный ключ, который вы хотите сохранить в тайне.
- Алгоритм асимметричного шифрования требует пары открытого и закрытого ключей~
❝Предположим, у вас есть файл, который вы шифруете с помощью буквы а, а расшифровывать может только буква b; или вы шифруете с помощью b, а расшифровывать может только буква а, тогда а и b являются парой открытого и закрытого ключей. Если ключ a является открытым, а ключ b хранится в частном порядке, то ключ a является открытым ключом, а ключ b — закрытым ключом. Наоборот, если b делается общедоступным, необходимо сохранить a. В это время секретный ключ b является открытым ключом, а секретный ключ a — закрытым ключом.
❞
Концепция проверки подписи
-
"добавить подпись": Используйте хеш-функцию, чтобы создать дайджест сообщения из исходного сообщения, а затем зашифровать дайджест с помощью закрытого ключа, чтобы получить цифровую подпись, соответствующую сообщению."Обратите внимание, что процесс подписания должен включать в себя некоторые специальные личные вещи, такие как личные закрытые ключи."Как правило, запрашивающий"Цифровая подпись и исходное сообщение"вместе с получателем.
-
"проверка подписи": После того, как получатель получит исходное сообщение и цифровую подпись, используйте"та самая хэш-функция"Сгенерируйте дайджест A из сообщения. Кроме того, расшифруйте цифровую подпись с помощью открытого ключа, предоставленного другой стороной, и получите реферат B. Сравнив, совпадают ли A и B, вы можете узнать, было ли сообщение подделано.
Эту картинку в интернете легче понять:
Зачем нужна проверка подписи
В предыдущем разделе мы уже познакомились с концепцией подписи и проверки подписи, так зачем же нам нужна подпись подпись и проверка подписи? Некоторым друзьям может показаться, что мы не используем"Шифрование с открытым ключом, дешифрование с закрытым ключом"Хорошо?
Далее возьмем демо.
❝Предположим, что сейчас есть компания А, и она хочет получить доступ к системе переводов компании С. Сначала компания C отправляла свой открытый ключ компании A, а закрытый ключ хранила у себя. Когда продавец на стороне компании A инициирует перевод, компания A сначала использует открытый ключ компании C для шифрования сообщения запроса. Когда зашифрованное сообщение достигает системы перевода компании C, компания C использует свой собственный закрытый ключ для расшифровки сообщения. Предположим, что зашифрованное сообщение получено посредником Актером в процессе передачи, и он также подавлен, потому что у него нет закрытого ключа и он не может есть лебединое мясо. Я изначально хотел изменить сообщение и перевести 100 миллионов на свой счет, ха-ха. Эта реализация кажется бесшовной и стабильной.
❞
Однако, если компания C отправила открытый ключ компании A в начале, он был получен посредником Актером, тогда у Jiangzi возникли бы проблемы.
❝Актер, посредник, перехватил открытый ключ C и отправил свой открытый ключ компании A. A ошибочно подумал, что это открытый ключ компании C. Когда А инициирует передачу, он использует открытый ключ Актера для шифрования сообщения-запроса, а актор перехватывает зашифрованное сообщение во время передачи, в это время он расшифровывает его своим закрытым ключом, а затем модифицирует сообщение (сам себе Передача 100 миллионов), зашифровать его с помощью открытого ключа C и отправить компании C. После того, как компания C получит сообщение, она продолжит его расшифровку с помощью собственного закрытого ключа. В итоге трансферный счет компании А потерял 100 миллионов?
❞
Как компания C различает, исходит ли сообщение от A или оно было изменено посредником? Чтобы продемонстрировать подлинность личности и сообщения, требуется"проверка подписи"Ла!
❝Компания A также отправляет свой открытый ключ компании C, а закрытый ключ хранится у нее. При инициировании передачи сначала подпишите сообщение запроса своим закрытым ключом, а затем получите собственную цифровую подпись. Затем отправьте цифровую подпись вместе с сообщением запроса в компанию C. После того, как компания C получает сообщение, она использует открытый ключ A для проверки подписи. Если содержимое исходного сообщения и дайджест цифровой подписи несовместимы, это означает, что сообщение было подделано~
❞
У некоторых друзей могут возникнуть сомнения: предположим, что когда А отправляет свой открытый ключ компании С, он также перехватывается посредником Актером. Что ж, давайте смоделируем волну Актера и перехватим публичный ключ, чтобы посмотреть, что Актер может сделать~ Ха-ха
❝Предположим, что после того, как Актер перехватил открытый ключ А, он также перехватывает пакеты, отправленные А к С. После того, как он перехватил сообщение, первое, что он хотел сделать, это изменить содержание сообщения. Но если просто модифицировать исходное сообщение, это невозможно, потому что компания С точно не сможет проверить подпись. Однако похоже, что цифровая подпись не может быть разблокирована, потому что алгоритм дайджеста сообщения (алгоритм хеширования) не может быть обратно разблокирован, и он играет только роль проверки....
❞
Итак, открытый ключ и закрытый ключ используются для шифрования и шифрования,"Подпись и проверка используются для подтверждения личности", чтобы не заморачиваться.
Введение в общие алгоритмы, связанные с шифрованием
- алгоритм дайджеста сообщения
- Алгоритм симметричного шифрования
- Алгоритм асимметричного шифрования
- Национальный секретный алгоритм
Алгоритм дайджеста сообщения:
- Одни и те же данные открытого текста получат одно и то же значение результата зашифрованного текста с помощью одного и того же алгоритма дайджеста сообщения.
- Данные обрабатываются алгоритмом дайджеста сообщения, и полученное значение результата дайджеста не может быть восстановлено до данных до обработки.
- Алгоритмы дайджеста данных также известны как алгоритмы хеширования или алгоритмы хеширования.
- Алгоритм дайджеста сообщения обычно используется для проверки подписи.
Алгоритмы дайджеста сообщения в основном делятся на три категории: MD (дайджест сообщения, алгоритм дайджеста сообщения), SHA (алгоритм безопасного хеширования, алгоритм безопасного хеширования) и MAC (код аутентификации сообщения, алгоритм кода аутентификации сообщения).
Семейство алгоритмов MD
Семейство MD (Message Digest, алгоритм дайджеста сообщения), включая MD2, MD4, MD5.
- Результатом вычисления MD2, MD4 и MD5 является 128-битное (т.е. 16-байтовое) хеш-значение, которое используется для обеспечения полной и согласованной передачи информации.
- Алгоритм MD2 медленнее, но относительно безопасен, MD4 быстр, но менее безопасен, а MD5 более безопасен и быстрее, чем MD4.
- MD5 широко используется для проверки целостности данных, дайджеста данных (сообщений), шифрования данных и т. д.
- MD5 может быть взломан.Для данных, требующих высокой безопасности, эксперты обычно рекомендуют использовать другие алгоритмы, такие как SHA-2.В 2004 году было подтверждено, что алгоритм MD5 не может предотвратить атаки столкновений, поэтому он не подходит для сертификации безопасности, например как общедоступное шифрование SSL, аутентификация по ключу или цифровая подпись.
В качестве примера посмотрите, как получить значение MD5 строки:
public class MD5Test {
public static void main(String[] args) throws UnsupportedEncodingException {
String s = "123";
byte[] result = getMD5Bytes(s.getBytes());
StringBuilder stringBuilder = new StringBuilder();
for (byte temp : result) {
if (temp >= 0 && temp < 16) {
stringBuilder.append("0");
}
stringBuilder.append(Integer.toHexString(temp & 0xff));
}
System.out.println(s + ",MD5加密后:" + stringBuilder.toString());
}
private static byte[] getMD5Bytes(byte[] content) {
try {
MessageDigest md5 = MessageDigest.getInstance("MD5");
return md5.digest(content);
} catch (NoSuchAlgorithmException e) {
throw new RuntimeException(e);
}
}
}
результат операции:
123,MD5加密后:202cb962ac59075b964b07152d234b70
Семейство алгоритмов ShA
SHA (Secure Hash Algorithm, Безопасный алгоритм хэширования), включая SHA-0, SHA-1, SHA-2 (SHA-256, SHA-512, SHA-224, SHA-384 и т. д.), SHA-3. Он реализован на основе алгоритма МД, а отличие от алгоритма МД в том, что"Абстрактная длина", дайджест алгоритма SHA"Большая длина для большей безопасности".
❝❞
- SHA-0, предшественник SHA-1, был отозван АНБ вскоре после его выпуска, поскольку он содержал ошибки, снижающие криптографическую безопасность.
- SHA-1 широко используется во многих протоколах безопасности, включая TLS, GnuPG, SSH, S/MIME и IPsec, и является преемником MD5.
- SHA-2 включает SHA-224, SHA-256, SHA-384, SHA-512, SHA-512/224, SHA-512/256. Его алгоритм в основном похож на SHA-1, и явных слабых мест пока нет.
- SHA-3 был официально выпущен в 2015 году из-за"Появляется успешное нарушение MD5", а также метод теоретического взлома SHA-0 и SHA-1, появился SHA-3. Он отличается от предыдущего алгоритма тем, что является альтернативным алгоритмом криптографического хеширования.
Чаще используются такие алгоритмы, как SHA-1, SHA-2 (SHA-256, SHA-512, SHA-224, SHA-384), давайте взглянем на сравнение с MD5.
Тип алгоритма | длина дайджеста (биты) | Максимальная длина входного сообщения (биты) | атака столкновением (биты) | Пример производительности (МиБ/с) |
---|---|---|---|---|
MD5 | 128 | неограниченный | ≤18 (обнаружено столкновение) | 335 |
SHA-1 | 160 | 2 ^ 64 - 1 | 192 | |
SHA-224 | 224 | 2 ^ 64 - 1 | 112 | 139 |
SHA-256 | 256 | 2 ^ 64 - 1 | 128 | 139 |
SHA-384 | 384 | 2 ^ 128 - 1 | 192 | 154 |
SHA-512 | 512 | 2 ^ 128 - 1 | 256 | 154 |
Семейство алгоритмов MAC
Алгоритм MAC MAC (Message Authentication Code, алгоритм кода аутентификации сообщения) представляет собой хеш-функцию с ключом. Введите ключ и сообщение, выведите дайджест сообщения. Он объединяет две серии алгоритмов дайджеста сообщений, MD и SHA.
- Алгоритмы серии MD: HmacMD2, HmacMD4 и HmacMD5;
- Семейство алгоритмов SHA: HmacSHA1, HmacSHA224, HmacSHA256, HmacSHA384 и HmacSHA512.
Алгоритм симметричного шифрования
Использование шифрования и дешифрования"тот же ключ"Алгоритм шифрования является симметричным алгоритмом шифрования. Общие алгоритмы симметричного шифрования включают AES, 3DES, DES, RC5, RC6 и т. д.
DES
Стандарт шифрования данных (англ. Data Encryption Standard, сокращенно DES) — алгоритм блочного шифрования с симметричным ключом. Алгоритм DES имеет три входных параметра: ключ, данные и режим.
- Ключ: 7 байтов с общим количеством бит 56, который является рабочим ключом алгоритма DES;
- Данные: 8 байт 64 бита, это данные, которые нужно зашифровать или расшифровать;
- Режим: зашифровать или расшифровать.
3DES
Алгоритм тройного шифрования данных (англ. Triple Data Encryption Algorithm, также известный как 3DES (Triple DES) — это блочный шифр шифрования с симметричным ключом, который эквивалентен трем применениям алгоритма стандарта шифрования данных (DES) к каждому блоку данных.
AES
AES, расширенный стандарт шифрования (англ. Advanced Encryption Standard), также известный как шифрование Rijndael в криптографии, представляет собой стандарт блочного шифрования, принятый федеральным правительством США.
- Принята симметричная блочная система шифрования, длина ключа составляет 128 бит, 192 бит, 256 бит, а длина блока составляет 128 бит.
- По сравнению с DES, AES обладает большей безопасностью, эффективностью и гибкостью.
Алгоритм асимметричного шифрования
Алгоритмы асимметричного шифрования требуют два ключа: открытый ключ и закрытый ключ. Открытый ключ и закрытый ключ существуют парами. Если данные зашифрованы открытым ключом, их можно расшифровать только с помощью соответствующего закрытого ключа. Основные алгоритмы асимметричного шифрования: RSA, Elgamal, DSA, D-H, ECC.
Алгоритм RSA
- Алгоритм шифрования RSA — это асимметричный алгоритм шифрования, широко используемый в шифровании и цифровой подписи.
- Принцип алгоритма RSA: произведение двух больших простых чисел чрезвычайно сложно разложить на множители, поэтому произведение можно сделать общедоступным в качестве ключа шифрования.
- RSA является наиболее широко изученным алгоритмом с открытым ключом. Он был протестирован различными атаками с момента его предложения до настоящего времени. В настоящее время он считается одной из лучших схем с открытым ключом.
DSA
- DSA (Digital Signature Algorithm, алгоритм цифровой подписи) также является алгоритмом асимметричного шифрования.
- Разница между DSA и RSA заключается в том, что DSA используется только для цифровых подписей и не может использоваться для шифрования и дешифрования данных. Его безопасность сравнима с RSA, но его производительность выше, чем у RSA.
ECC-алгоритм
- ECC (криптография на эллиптических кривых), основанная на шифровании на эллиптических кривых.
- Основное преимущество Ecc заключается в том, что в некоторых случаях он использует ключи меньшего размера, чем другие методы, такие как алгоритм шифрования RSA, обеспечивая сравнимый или более высокий уровень безопасности.
- Одним из его недостатков является то, что операции шифрования и дешифрования требуют больше времени для реализации, чем другие механизмы (алгоритм интенсивно использует ЦП по сравнению с алгоритмом RSA).
Национальный секретный алгоритм
Государственной тайной является отечественный алгоритм шифрования, признанный Государственным управлением криптографии. Чтобы обеспечить безопасность коммерческой криптографии, Национальное управление по управлению коммерческой криптографией сформулировало ряд криптографических стандартов, а именно SM1, SM2, SM3, SM4 и другие национальные криптографические алгоритмы.
SM1
- SM1 — это алгоритм симметричного шифрования со степенью шифрования 128 бит, реализованный на аппаратном уровне.
- Сила шифрования и производительность SM1 сравнимы с AES.
SM2
- SM2 в основном включает три части: алгоритм подписи, алгоритм обмена ключами, алгоритм шифрования.
- SM2 используется для замены алгоритма шифрования RSA, который основан на ECC и менее эффективен.
SM3
- SM3 — это внутренний алгоритм дайджеста сообщений.
- Он подходит для цифровой подписи и проверки в коммерческих криптографических приложениях, генерации и проверки кодов аутентификации сообщений и генерации случайных чисел.
SM4
- SM4 — это алгоритм группировки, используемый в продуктах для беспроводных локальных сетей.
- Длина блока этого алгоритма составляет 128 бит, а длина ключа — 128 бит.
- И алгоритм шифрования, и алгоритм расширения ключа используют нелинейную итеративную структуру с 32 раундами.
- Структура алгоритма дешифрования такая же, как у алгоритма шифрования, за исключением того, что ключи раунда используются в обратном порядке, а ключ раунда дешифрования — это порядок, обратный ключу раунда шифрования.
- Его функция аналогична DES международного алгоритма.
Java API, связанный с проверкой подписи
В этом разделе давайте сначала представим API, необходимые для проверки подписи~
API, связанный с подписью
- java.security.Signature.getInstance(String algorithm); //根据对应算法,初始化签名对象
- KeyFactory.getInstance(String algorithm);// 根据对应算法,生成KeyFactory对象
- KeyFactory.generatePrivate(KeySpec keySpec); //生成私钥
- java.security.Signature.initSign(PrivateKey privateKey) //由私钥,初始化加签对象
- java.security.Signature.update(byte[] data) //把原始报文更新到加签对象
- java.security.Signature.sign();//加签
"Signature.getInstance(String algorithm);"
- Инициализировать объект подписи по соответствующему алгоритму
- Параметр алгоритма может принимать такие параметры, как SHA256WithRSA или MD5WithRSA.SHA256WithRSA означает, что алгоритм SHA256 используется для создания дайджеста, а алгоритм RSA используется для добавления подписи.
"KeyFactory.getInstance(String algorithm);"
- Сгенерируйте объект KeyFactory по соответствующему алгоритму, например, если ваши открытый и закрытый ключи используют алгоритм RSA, то передайте в RSA
"KeyFactory.generatePrivate(KeySpec keySpec)"
- Чтобы сгенерировать закрытый ключ, подпись является закрытым ключом, поэтому сначала необходимо создать объект закрытого ключа с помощью KeyFactory.
"Signature.initSign(PrivateKey privateKey)"
- В подписи используется закрытый ключ, поэтому передайте закрытый ключ для инициализации объекта подписи.
"Signature.update(byte[] data)"
- Обновите исходное сообщение до объекта подписи
"java.security.Signature.sign();"
- выполнить операцию подписи
API, связанные с проверкой подписи
- java.security.Signature.getInstance(String algorithm); //根据对应算法,初始化签名对象
- KeyFactory.getInstance(String algorithm);// 根据对应算法,生成KeyFactory对象
- KeyFactory.generatePublic(KeySpec keySpec); //生成公钥
- java.security.Signature.initVerify(publicKey); //由公钥,初始化验签对象
- java.security.Signature.update(byte[] data) //把原始报文更新到验签对象
- java.security.Signature.verify(byte[] signature);//验签
"Signature.getInstance(String algorithm)"
- Инициализируйте объект подписи согласно соответствующему алгоритму.Обратите внимание, что для проверки подписи и добавления подписи необходимо использовать одни и те же параметры алгоритма~
"KeyFactory.getInstance(String algorithm);"
- Сгенерировать объект KeyFactory по соответствующему алгоритму
"KeyFactory.generatePublic(KeySpec keySpec);"
- Создайте открытый ключ, используйте открытый ключ для проверки подписи, сначала создайте объект открытого ключа с помощью KeyFactory.
**Signature.initVerify(publicKey); **
- Открытый ключ используется для проверки подписи, поэтому параметр объекта открытого ключа передается для инициализации объекта проверки подписи.
"Signature.update(byte[] data)"
- Обновите исходное сообщение до объекта подписи
"Signature.verify(byte[] signature);"
- Выполнить проверку подписи
Реализация кода проверки подписи
После обсуждения концепций в предыдущих разделах пришло время применить код на практике.Я использую SHA-256 в качестве алгоритма дайджеста и RSA в качестве алгоритма проверки подписи следующим образом:
package pattern;
import sun.misc.BASE64Decoder;
import sun.misc.BASE64Encoder;
import java.io.IOException;
import java.io.UnsupportedEncodingException;
import java.security.*;
import java.security.spec.InvalidKeySpecException;
import java.security.spec.PKCS8EncodedKeySpec;
/**
* 加签验签demo
* @Author 捡田螺的小男孩
*/
public class SignatureTest {
//公钥字符串
private static final String PUBLIC_KEY_STR = "MIGfMA0GCSqGSIb3DQEBAQUAA4GNADCBiQKBgQDaJzVjC5K6kbS2YE2fiDs6H8pB\n" +
"JFDGEYqqJJC9I3E0Ebr5FsofdImV5eWdBSeADwcR9ppNbpORdZmcX6SipogKx9PX\n" +
"5aAO4GPesroVeOs91xrLEGt/arteW8iSD+ZaGDUVV3+wcEdci/eCvFlc5PUuZJou\n" +
"M2XZaDK4Fg2IRTfDXQIDAQAB";
//私钥字符串
private static final String PRIVATE_KEY_STR = "MIICdQIBADANBgkqhkiG9w0BAQEFAASCAl8wggJbAgEAAoGBANonNWMLkrqRtLZg\n" +
"TZ+IOzofykEkUMYRiqokkL0jcTQRuvkWyh90iZXl5Z0FJ4APBxH2mk1uk5F1mZxf\n" +
"pKKmiArH09floA7gY96yuhV46z3XGssQa39qu15byJIP5loYNRVXf7BwR1yL94K8\n" +
"WVzk9S5kmi4zZdloMrgWDYhFN8NdAgMBAAECgYA9bz1Bn0i68b2KfqRdgOfs/nbe\n" +
"0XNN1DLQp2t7WDfRCg01iI1zPkZgyFVZWtI85f5/uIrLs5ArLosL1oNuqqc0nNne\n" +
"CvJK+ZxvA98Hx3ZqYTzDnleR054YhofL5awbhSciYVic204DOG1rhSsYWMqtX7J7\n" +
"3geoWL7TYdMfYXcCAQJBAPMMKsz6ZJh98EeQ1tDG5gpAGWFQkYNrxZDelP/LjeO0\n" +
"TP3XkQnIpcaZoCs7V/rRGRGMWwQ2BUdc/01in89ZZ5ECQQDlx2oBc1CtOAm2UAhN\n" +
"1xWrPkZWENQ53wTrwXO4qbTGDfBKon0AehLlGCSqxQ71aufLkNO7ZlX0IHTAlnk1\n" +
"TvENAkAGSEQ69CXxgx/Y2beTwfBkR2/gghKg0QJUUkyLqBlMz3ZGAXJwTE1sqr/n\n" +
"HiuSAiGhwH0ByNuuEotO1sPGukrhAkAMK26a2w+nzPL+u+hkrwKPykGRZ1zGH+Cz\n" +
"19AYNKzFXJGgclCqiMydY5T1knBDYUEbj/UW1Mmyn1FvrciHoUG1AkAEMEIuDauz\n" +
"JabEAU08YmZw6OoDGsukRWaPfjOEiVhH88p00veM1R37nwhoDMGyEGXVeVzNPvk7\n" +
"cELg28MSRzCK";
public static void main(String[] args) throws SignatureException, NoSuchAlgorithmException, InvalidKeyException, IOException, InvalidKeySpecException {
//原始报文
String plain = "欢迎大家关注我的公众号,捡田螺的小男孩";
//加签
byte[] signatureByte = sign(plain);
System.out.println("原始报文是:" + plain);
System.out.println("加签结果:");
System.out.println(new BASE64Encoder().encode(signatureByte));
//验签
boolean verifyResult = verify(plain, signatureByte);
System.out.println("验签结果:" + verifyResult);
}
/**
* 加签方法
* @param plain
* @return
* @throws NoSuchAlgorithmException
* @throws InvalidKeyException
* @throws UnsupportedEncodingException
* @throws SignatureException
*/
private static byte[] sign(String plain) throws NoSuchAlgorithmException, InvalidKeyException, UnsupportedEncodingException, SignatureException {
//根据对应算法,获取签名对象实例
Signature signature = Signature.getInstance("SHA256WithRSA");
//获取私钥,加签用的是私钥,私钥一般是在配置文件里面读的,这里为了演示方便,根据私钥字符串生成私钥对象
PrivateKey privateKey = getPriveteKey(PRIVATE_KEY_STR);
//初始化签名对象
signature.initSign(privateKey);
//把原始报文更新到对象
signature.update(plain.getBytes("UTF-8"));
//加签
return signature.sign();
}
/**
* 验签方法
* @param plain
* @param signatureByte
* @return
* @throws NoSuchAlgorithmException
* @throws InvalidKeyException
* @throws IOException
* @throws SignatureException
* @throws InvalidKeySpecException
*/
private static boolean verify(String plain, byte[] signatureByte) throws NoSuchAlgorithmException, InvalidKeyException, IOException, SignatureException, InvalidKeySpecException {
//获取公钥
PublicKey publicKey = getPublicKey(PUBLIC_KEY_STR);
//根据对应算法,获取签名对象实例
Signature signature = Signature.getInstance("SHA256WithRSA");
//初始化签名对象
signature.initVerify(publicKey);
//把原始报文更新到签名对象
signature.update(plain.getBytes("UTF-8"));
//进行验签
return signature.verify(signatureByte);
}
private static PublicKey getPublicKey(String publicKeyStr) throws InvalidKeySpecException, IOException {
PublicKey publicKey = null;
try {
java.security.spec.X509EncodedKeySpec bobPubKeySpec = new java.security.spec.X509EncodedKeySpec(
new BASE64Decoder().decodeBuffer(publicKeyStr));
// RSA对称加密算法
java.security.KeyFactory keyFactory;
keyFactory = java.security.KeyFactory.getInstance("RSA");
// 生成公钥对象
publicKey = keyFactory.generatePublic(bobPubKeySpec);
} catch (NoSuchAlgorithmException e) {
e.printStackTrace();
}
return publicKey;
}
private static PrivateKey getPriveteKey(String privateKeyStr) {
PrivateKey privateKey = null;
PKCS8EncodedKeySpec priPKCS8;
try {
priPKCS8 = new PKCS8EncodedKeySpec(new BASE64Decoder().decodeBuffer(privateKeyStr));
KeyFactory keyf = KeyFactory.getInstance("RSA");
privateKey = keyf.generatePrivate(priPKCS8);
} catch (IOException | NoSuchAlgorithmException | InvalidKeySpecException e) {
e.printStackTrace();
}
return privateKey;
}
}
"результат операции:"
原始报文是:欢迎大家关注我的公众号,捡田螺的小男孩
加签结果:
Oz15/aybGe42eGHbc+iMoSYHSCc8tfRskTVjjGSTPD4HjadL0CC5JUWNUW0WxHjUb4MvxWo2oeWE
Qw0+m61d+JgBMto/TWcVDcgwL/AbObsbWdQ6E/fVRqG13clkE8MyKsjt9Z7tcbwpycYTv0rUR4co
rndAVfBdtv5KeV+OXqM=
验签结果:true
Ссылка и спасибо
- Википедия
- Энциклопедия Байду
- Введение в общие алгоритмы дайджеста сообщений
- Говоря о семи распространенных алгоритмах шифрования и их реализации
- [Концепция подверженности ошибкам] Национальный секретный алгоритм SM1 (SCB2), SM2, SM3, SM4, SM7, SM9, ZUC