From 51d87f766a09b0d5100db176f9f2bdc6728eaa0e Mon Sep 17 00:00:00 2001 From: "Kai Mindermann M.Sc" Date: Fri, 27 Apr 2018 14:19:06 +0200 Subject: [PATCH 01/33] Update README.md --- README.md | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/README.md b/README.md index d2b213f..f3804da 100644 --- a/README.md +++ b/README.md @@ -1,6 +1,6 @@ -# java-crypto-examples for [cryptoexamples.com](http://cryptoexamples.com) +# java-crypto-examples for [CryptoExamples](http://www.cryptoexamples.com) -Example code for cryptographic use cases. Used in [crypto-examples](https://github.com/kmindi/crypto-examples) +Example code for cryptographic use cases. Used in [CryptoExamples](https://github.com/cryptoexamples/CryptoExamples) ![Coverage](https://sonarqube.com/api/badges/measure?key=java-crypto-examples&metric=coverage) ![Technical Debt Ratio](https://sonarqube.com/api/badges/measure?key=java-crypto-examples&metric=sqale_debt_ratio) From baeaa32454f560ec285d75fadee1e51e27b6f407 Mon Sep 17 00:00:00 2001 From: "Kai Mindermann M.Sc" Date: Fri, 27 Apr 2018 14:37:00 +0200 Subject: [PATCH 02/33] fixes typos --- java_string_hash.md | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/java_string_hash.md b/java_string_hash.md index dbc9a80..53d6bac 100644 --- a/java_string_hash.md +++ b/java_string_hash.md @@ -9,9 +9,9 @@ tags: [Java, hash, SHA, SHA-512] ## Use cases -- verifying if a string has been changed +- Verifying if a string has been changed -## Sample Code for Java based hasing of a String using SHA-512, BASE64 and UTF-8 encoding +## Sample Code for Java based hashing of a String using SHA-512, BASE64 and UTF-8 encoding ```java {% include_relative src/main/java/com/cryptoexamples/java/ExampleHashInOneMethod.java %} From 7ad745a686f596026c3f385257aba361a6431670 Mon Sep 17 00:00:00 2001 From: "Kai Mindermann M.Sc" Date: Sat, 28 Apr 2018 11:42:09 +0200 Subject: [PATCH 03/33] Create CHANGELOG.md --- CHANGELOG.md | 42 ++++++++++++++++++++++++++++++++++++++++++ 1 file changed, 42 insertions(+) create mode 100644 CHANGELOG.md diff --git a/CHANGELOG.md b/CHANGELOG.md new file mode 100644 index 0000000..e18f16d --- /dev/null +++ b/CHANGELOG.md @@ -0,0 +1,42 @@ +# Changelog +All notable changes to this project will be documented in this file. + +The format is based on [Keep a Changelog](http://keepachangelog.com/en/1.0.0/) +and this project adheres to [Semantic Versioning](http://semver.org/spec/v2.0.0.html). + +## [Unreleased] + +## [X.Y.Z] - XXXX-XX-XX (TEMPLATE for new versions) + +### Added + +- added something +- added something else + +### Changed + +- changed something +- changed something else + +### Deprecated + +- deprecated something +- deprecated something else + +### Removed + +- removed something +- removed something else + +### Fixed + +- fixed something +- fixed something else + +### Security + +- made some security relevant changes +- made other security relevant changes + +[Unreleased]: https://github.com/cryptoexamples/CryptoExamples-Guidelines/compare/v0.0.1...HEAD +[0.0.1]: https://github.com/cryptoexamples/CryptoExamples-Guidelines/releases/tag/0.0.1 From 97356f5537c3a3ea481a7f98132742494e6ca4f0 Mon Sep 17 00:00:00 2001 From: "Kai Mindermann M.Sc" Date: Sat, 28 Apr 2018 11:43:02 +0200 Subject: [PATCH 04/33] Update CHANGELOG.md --- CHANGELOG.md | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/CHANGELOG.md b/CHANGELOG.md index e18f16d..4b897a7 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -38,5 +38,5 @@ and this project adheres to [Semantic Versioning](http://semver.org/spec/v2.0.0. - made some security relevant changes - made other security relevant changes -[Unreleased]: https://github.com/cryptoexamples/CryptoExamples-Guidelines/compare/v0.0.1...HEAD -[0.0.1]: https://github.com/cryptoexamples/CryptoExamples-Guidelines/releases/tag/0.0.1 +[Unreleased]: https://github.com/cryptoexamples/java-crypto-examples/compare/v0.0.1...HEAD +[0.0.1]: https://github.com/cryptoexamples/java-crypto-examples/releases/tag/0.0.1 From 4917d3ac7d5c14a2012ef8b6b6ee1adc9c362abc Mon Sep 17 00:00:00 2001 From: "Kai Mindermann M.Sc" Date: Sat, 28 Apr 2018 19:29:08 +0200 Subject: [PATCH 05/33] adds asymmetric string encryption example (#5) --- java_landing_page.md | 2 +- java_string_encryption_asymmetric.md | 41 ++++++++++++++ ...AsymmetricStringEncryptionInOneMethod.java | 56 +++++++++++++++++++ .../java/EncryptionInOneMethodTests.java | 6 ++ 4 files changed, 104 insertions(+), 1 deletion(-) create mode 100644 java_string_encryption_asymmetric.md create mode 100644 src/main/java/com/cryptoexamples/java/ExampleAsymmetricStringEncryptionInOneMethod.java diff --git a/java_landing_page.md b/java_landing_page.md index df75b30..4feb5da 100644 --- a/java_landing_page.md +++ b/java_landing_page.md @@ -12,7 +12,7 @@ is_landingpage: 1 | | All in One | Easy Object oriented | |-------------------------------------------------|----------------------------------------|--------------------------------------| | Symmetric Encryption | [String Encryption (password based) ✔](java_string_encryption_password_based_symmetric.html)
[String Encryption (key based) ✔](java_string_encryption_key_based_symmetric.html)
[File Encryption ✔](java_file_encryption_symmetric_password_based.html) | [String Encryption with separate class ✔](java_easy_AES_string_encryption.html)
[File Encryption with separate class ✔](java_easy_AES_file_encryption.html) | -| Asymmetric Encryption / Public Key Cryptography | | | +| Asymmetric Encryption / Public Key Cryptography | [String Encryption ✔](java_asymmetric_string_encryption.html) | | | Key Storage | | | | Hashing | [String Hash ✔](java_string_hash.html) | N/A | | Crypto Provider Setup | | | diff --git a/java_string_encryption_asymmetric.md b/java_string_encryption_asymmetric.md new file mode 100644 index 0000000..e677ad9 --- /dev/null +++ b/java_string_encryption_asymmetric.md @@ -0,0 +1,41 @@ +--- +title: Asymmetric String Encryption using Java JDK +keywords: sample +summary: "Asymmetric String Encryption in Java" +permalink: java_asymmetric_string_encryption.html +folder: Java JDK +references: [ + # Place a list of references used to create and/or understand this example. + { + url: "https://docs.oracle.com/javase/10/docs/api/javax/crypto/Cipher.html", + description: "Java JDK Ciper" + } +] +authors: [ + { + name: "Kai Mindermann", + url: "https://github.com/kmindi" + } +] +# List all reviewers that reviewed this version of the example. When the example is updated all old reviews +# must be removed from the list below and the code has to be reviewed again. The complete review process +# is documented in the main repository of CryptoExamples +current_reviews: [ + +] +# Indicates when this example was last updated/created. Reviews don't change this. +last_updated: "2018-04-28" +tags: [Java, RSA, Asymmetric, String, Encryption] +--- + +## Use cases + +- + +## Sample Code for Java based asymmetric encryption + +```java +{% include_relative src/main/java/com/cryptoexamples/java/ExampleAsymmetricStringEncryptionInOneMethod.java %} +``` + +{% include links.html %} diff --git a/src/main/java/com/cryptoexamples/java/ExampleAsymmetricStringEncryptionInOneMethod.java b/src/main/java/com/cryptoexamples/java/ExampleAsymmetricStringEncryptionInOneMethod.java new file mode 100644 index 0000000..3f8b85a --- /dev/null +++ b/src/main/java/com/cryptoexamples/java/ExampleAsymmetricStringEncryptionInOneMethod.java @@ -0,0 +1,56 @@ +package com.cryptoexamples.java; + +import javax.crypto.BadPaddingException; +import javax.crypto.Cipher; +import javax.crypto.IllegalBlockSizeException; +import javax.crypto.NoSuchPaddingException; +import java.security.InvalidKeyException; +import java.security.InvalidParameterException; +import java.security.KeyPair; +import java.security.KeyPairGenerator; +import java.security.NoSuchAlgorithmException; +import java.util.Base64; +import java.util.logging.Level; +import java.util.logging.Logger; + +/** + * All in one example for asymmetric encryption and decryption of a string in one method. + * - Generation of public and private RSA 4096 bit keypair + * - AES-256 authenticated encryption using GCM + * - BASE64-encoding as representation for the byte-arrays + * - UTF-8 encoding of String + * - Exception handling + */ +public class ExampleAsymmetricStringEncryptionInOneMethod { + private static final Logger LOGGER = Logger.getLogger(ExampleAsymmetricStringEncryptionInOneMethod.class.getName()); + + public static void main(String[] args) { + String plainText = "Text that is going to be sent over an insecure channel and must be encrypted at all costs!"; + try { + + // GENERATE NEW KEYPAIR + KeyPairGenerator keyPairGenerator = KeyPairGenerator.getInstance("RSA"); + /* @see https://www.keylength.com/ */ + keyPairGenerator.initialize(4096); + KeyPair keyPair = keyPairGenerator.generateKeyPair(); + + // ENCRYPTION + Cipher cipher = Cipher.getInstance("RSA/ECB/OAEPWithSHA-256AndMGF1Padding"); + cipher.init(Cipher.ENCRYPT_MODE, keyPair.getPublic()); + + byte[] byteCipher = cipher.doFinal(plainText.getBytes()); + + // CONVERSION of raw bytes to BASE64 representation + String cipherText = new String(Base64.getEncoder().encode(byteCipher)); + + // DECRYPTION + cipher.init(Cipher.DECRYPT_MODE, keyPair.getPrivate()); + byte[] decryptedCipher = cipher.doFinal(Base64.getDecoder().decode(cipherText)); + String decryptedCipherText = new String(decryptedCipher); + + LOGGER.log(Level.INFO, () -> String.format("Decrypted and original plain text are the same: %b", decryptedCipherText.compareTo(plainText) == 0)); + } catch (NoSuchAlgorithmException | NoSuchPaddingException | InvalidKeyException | IllegalBlockSizeException | BadPaddingException | InvalidParameterException e) { + LOGGER.log(Level.SEVERE, e.getMessage(), e); + } + } +} diff --git a/src/test/java/com/cryptoexamples/java/EncryptionInOneMethodTests.java b/src/test/java/com/cryptoexamples/java/EncryptionInOneMethodTests.java index ffc715e..14ffd92 100644 --- a/src/test/java/com/cryptoexamples/java/EncryptionInOneMethodTests.java +++ b/src/test/java/com/cryptoexamples/java/EncryptionInOneMethodTests.java @@ -46,6 +46,12 @@ public void testStringEncryptionKeyBasedMain() { assertThat(errContent.toString(), containsString("Decrypted and original plain text are the same: true")); } + @Test + public void testAsymmetricStringEncryptionMain() { + ExampleAsymmetricStringEncryptionInOneMethod.main(new String[1]); + assertThat(errContent.toString(), containsString("Decrypted and original plain text are the same: true")); + } + @Test public void testFileEncryptionMain() { ExampleFileEncryptionInOneMethod.main(new String[1]); From 4e58563132215abd70a9355779367806eb27336d Mon Sep 17 00:00:00 2001 From: Kai Mindermann Date: Sat, 28 Apr 2018 19:32:02 +0200 Subject: [PATCH 06/33] updates CHANGELOG.md for release 0.1.0 --- CHANGELOG.md | 8 ++++++++ 1 file changed, 8 insertions(+) diff --git a/CHANGELOG.md b/CHANGELOG.md index 4b897a7..fa19fc4 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -1,4 +1,5 @@ # Changelog + All notable changes to this project will be documented in this file. The format is based on [Keep a Changelog](http://keepachangelog.com/en/1.0.0/) @@ -6,6 +7,13 @@ and this project adheres to [Semantic Versioning](http://semver.org/spec/v2.0.0. ## [Unreleased] +## [0.1.0] - 2018-04-28 + +### Added + +- added Changelog +- added Asymmetric RSA String Encryption + ## [X.Y.Z] - XXXX-XX-XX (TEMPLATE for new versions) ### Added From 9eeffdf42c64cca20e0a636d42b869eb02e82a7c Mon Sep 17 00:00:00 2001 From: Kai Mindermann Date: Sat, 28 Apr 2018 19:34:36 +0200 Subject: [PATCH 07/33] fixes CHANGELOG.md --- CHANGELOG.md | 11 +++++++++-- 1 file changed, 9 insertions(+), 2 deletions(-) diff --git a/CHANGELOG.md b/CHANGELOG.md index fa19fc4..9af60f1 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -7,6 +7,12 @@ and this project adheres to [Semantic Versioning](http://semver.org/spec/v2.0.0. ## [Unreleased] +## [0.1.1] - 2018-04-28 + +### Changed + +- fixed Changelog + ## [0.1.0] - 2018-04-28 ### Added @@ -46,5 +52,6 @@ and this project adheres to [Semantic Versioning](http://semver.org/spec/v2.0.0. - made some security relevant changes - made other security relevant changes -[Unreleased]: https://github.com/cryptoexamples/java-crypto-examples/compare/v0.0.1...HEAD -[0.0.1]: https://github.com/cryptoexamples/java-crypto-examples/releases/tag/0.0.1 +[Unreleased]: https://github.com/cryptoexamples/java-crypto-examples/compare/v0.1.1...HEAD +[0.1.1]: https://github.com/cryptoexamples/java-crypto-examples/compare/v0.1.0...v0.1.1 +[0.1.0]: https://github.com/cryptoexamples/java-crypto-examples/releases/tag/0.1.0 \ No newline at end of file From 6bed65bdf72736ae23e9ee86b1b820ab3fa1c5fe Mon Sep 17 00:00:00 2001 From: Kai Mindermann Date: Sat, 28 Apr 2018 19:43:16 +0200 Subject: [PATCH 08/33] fixes version link in CHANGELOG.md --- CHANGELOG.md | 6 +++++- 1 file changed, 5 insertions(+), 1 deletion(-) diff --git a/CHANGELOG.md b/CHANGELOG.md index 9af60f1..c5fe59b 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -7,6 +7,10 @@ and this project adheres to [Semantic Versioning](http://semver.org/spec/v2.0.0. ## [Unreleased] +### Changed + +- fixed version link in Changelog + ## [0.1.1] - 2018-04-28 ### Changed @@ -54,4 +58,4 @@ and this project adheres to [Semantic Versioning](http://semver.org/spec/v2.0.0. [Unreleased]: https://github.com/cryptoexamples/java-crypto-examples/compare/v0.1.1...HEAD [0.1.1]: https://github.com/cryptoexamples/java-crypto-examples/compare/v0.1.0...v0.1.1 -[0.1.0]: https://github.com/cryptoexamples/java-crypto-examples/releases/tag/0.1.0 \ No newline at end of file +[0.1.0]: https://github.com/cryptoexamples/java-crypto-examples/releases/tag/v0.1.0 \ No newline at end of file From ecd404e9b0d13336feb633ce057ce416168bdc97 Mon Sep 17 00:00:00 2001 From: "Kai Mindermann M.Sc" Date: Thu, 3 May 2018 12:58:33 +0200 Subject: [PATCH 09/33] Update README.md --- README.md | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/README.md b/README.md index f3804da..d2d0e03 100644 --- a/README.md +++ b/README.md @@ -1,4 +1,4 @@ -# java-crypto-examples for [CryptoExamples](http://www.cryptoexamples.com) +# java-crypto-examples for [CryptoExamples](https://www.cryptoexamples.com) Example code for cryptographic use cases. Used in [CryptoExamples](https://github.com/cryptoexamples/CryptoExamples) From b67cdd54dddd8ec4972b025649a958ceeabdbe4d Mon Sep 17 00:00:00 2001 From: "Kai Mindermann M.Sc" Date: Mon, 7 May 2018 13:03:01 +0200 Subject: [PATCH 10/33] adds jdk 9 to travis ci (#6) * adds jdk 9 to travis ci * updates gradle-wrapper.properties * updates sonarqube plugin to 2.6.2 and sourceCompatibility to 11 * corrects sonarcloud addon --- .travis.yml | 3 ++- build.gradle | 2 +- gradle/wrapper/gradle-wrapper.properties | 2 +- 3 files changed, 4 insertions(+), 3 deletions(-) diff --git a/.travis.yml b/.travis.yml index bab5140..661c840 100644 --- a/.travis.yml +++ b/.travis.yml @@ -1,8 +1,9 @@ language: java jdk: - oraclejdk8 + - oraclejdk9 addons: - sonarqube: + sonarcloud: organization: "kmindi-github" # the key of the org you chose at step #3 cache: directories: diff --git a/build.gradle b/build.gradle index 8046bbc..6acdd54 100644 --- a/build.gradle +++ b/build.gradle @@ -1,5 +1,5 @@ plugins { - id "org.sonarqube" version "2.3" + id "org.sonarqube" version "2.6.2" } group 'com.cryptoexamples.java' diff --git a/gradle/wrapper/gradle-wrapper.properties b/gradle/wrapper/gradle-wrapper.properties index aa674ec..88a3bc5 100644 --- a/gradle/wrapper/gradle-wrapper.properties +++ b/gradle/wrapper/gradle-wrapper.properties @@ -3,4 +3,4 @@ distributionBase=GRADLE_USER_HOME distributionPath=wrapper/dists zipStoreBase=GRADLE_USER_HOME zipStorePath=wrapper/dists -distributionUrl=https\://services.gradle.org/distributions/gradle-3.3-all.zip +distributionUrl=https\://services.gradle.org/distributions/gradle-4.7-all.zip From e62f762d73a6da3f5e12252e1275092c594270b8 Mon Sep 17 00:00:00 2001 From: "Kai Mindermann M.Sc" Date: Mon, 7 May 2018 15:09:24 +0200 Subject: [PATCH 11/33] updates badges --- README.md | 18 ++++++++++++++---- 1 file changed, 14 insertions(+), 4 deletions(-) diff --git a/README.md b/README.md index d2d0e03..246ed93 100644 --- a/README.md +++ b/README.md @@ -2,10 +2,20 @@ Example code for cryptographic use cases. Used in [CryptoExamples](https://github.com/cryptoexamples/CryptoExamples) -![Coverage](https://sonarqube.com/api/badges/measure?key=java-crypto-examples&metric=coverage) -![Technical Debt Ratio](https://sonarqube.com/api/badges/measure?key=java-crypto-examples&metric=sqale_debt_ratio) -![Test Success Density](https://sonarqube.com/api/badges/measure?key=java-crypto-examples&metric=test_success_density) -![Lines Of Code](https://sonarqube.com/api/badges/measure?key=java-crypto-examples&metric=ncloc) +[![Build status](https://travis-ci.org/SonarSource/sq-com_example_java-gradle-travis.svg?branch=master)](https://travis-ci.org/SonarSource/sq-com_example_java-gradle-travis) +[![Quality Gate](https://sonarcloud.io/api/project_badges/measure?project=java-crypto-examples&metric=alert_status)](https://sonarcloud.io/dashboard?id=java-crypto-examples) +[![Maintainability Rating](https://sonarcloud.io/api/project_badges/measure?project=java-crypto-examples&metric=sqale_rating)](https://sonarcloud.io/component_measures?id=java-crypto-examples&metric=sqale_rating) +[![Security Rating](https://sonarcloud.io/api/project_badges/measure?project=java-crypto-examples&metric=security_rating)](https://sonarcloud.io/component_measures?id=java-crypto-examples&metric=security_rating) +[![Reliability Rating](https://sonarcloud.io/api/project_badges/measure?project=java-crypto-examples&metric=reliability_rating)](https://sonarcloud.io/component_measures?id=java-crypto-examples&metric=reliability_rating) + +[![Code smells](https://sonarcloud.io/api/project_badges/measure?project=java-crypto-examples&metric=code_smells)](https://sonarcloud.io/component_measures?id=java-crypto-examples&metric=code_smells) +[![Bugs](https://sonarcloud.io/api/project_badges/measure?project=java-crypto-examples&metric=bugs)](https://sonarcloud.io/component_measures?id=java-crypto-examples&metric=bugs) +[![Technical debt](https://sonarcloud.io/api/project_badges/measure?project=java-crypto-examples&metric=sqale_index)](https://sonarcloud.io/component_measures?id=java-crypto-examples&metric=sqale_index) +[![Coverage](https://sonarcloud.io/api/project_badges/measure?project=java-crypto-examples&metric=coverage)](https://sonarcloud.io/component_measures?id=java-crypto-examples&metric=coverage) +[![Vulnerabilities](https://sonarcloud.io/api/project_badges/measure?project=java-crypto-examples&metric=vulnerabilities)](https://sonarcloud.io/component_measures?id=java-crypto-examples&metric=vulnerabilities) +[![Duplicated Lines Density](https://sonarcloud.io/api/project_badges/measure?project=java-crypto-examples&metric=duplicated_lines_density)](https://sonarcloud.io/component_measures?id=java-crypto-examples&metric=duplicated_lines_density) + +![Lines Of Code](https://sonarcloud.io/api/project_badges/measure?project=java-crypto-examples&metric=ncloc) ## License From 7cf119c6d5b0e637984eefd52a9efb00aebcf647 Mon Sep 17 00:00:00 2001 From: "Kai Mindermann M.Sc" Date: Mon, 7 May 2018 15:13:56 +0200 Subject: [PATCH 12/33] fixes build status link --- README.md | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/README.md b/README.md index 246ed93..2414c89 100644 --- a/README.md +++ b/README.md @@ -2,7 +2,7 @@ Example code for cryptographic use cases. Used in [CryptoExamples](https://github.com/cryptoexamples/CryptoExamples) -[![Build status](https://travis-ci.org/SonarSource/sq-com_example_java-gradle-travis.svg?branch=master)](https://travis-ci.org/SonarSource/sq-com_example_java-gradle-travis) +[![Build status](https://travis-ci.org/cryptoexamples/java-crypto-examples.svg?branch=master)](https://travis-ci.org/SonarSource/cryptoexamples/java-crypto-examples) [![Quality Gate](https://sonarcloud.io/api/project_badges/measure?project=java-crypto-examples&metric=alert_status)](https://sonarcloud.io/dashboard?id=java-crypto-examples) [![Maintainability Rating](https://sonarcloud.io/api/project_badges/measure?project=java-crypto-examples&metric=sqale_rating)](https://sonarcloud.io/component_measures?id=java-crypto-examples&metric=sqale_rating) [![Security Rating](https://sonarcloud.io/api/project_badges/measure?project=java-crypto-examples&metric=security_rating)](https://sonarcloud.io/component_measures?id=java-crypto-examples&metric=security_rating) From bde196a757b8489a416eeccc592b02336a95c78a Mon Sep 17 00:00:00 2001 From: Kai Mindermann Date: Sun, 13 May 2018 09:25:24 +0200 Subject: [PATCH 13/33] removes "separate class" examples --- java_easy_AES_file_encryption.md | 22 -- java_easy_AES_string_encryption.md | 22 -- .../cryptoexamples/java/EncryptedFile.java | 194 ------------------ .../cryptoexamples/java/EncryptedString.java | 188 ----------------- .../java/ExampleEncryptedFile.java | 43 ---- .../java/ExampleEncryptedString.java | 41 ---- .../java/EncryptedFileTest.java | 55 ----- .../java/EncryptedStringTest.java | 50 ----- 8 files changed, 615 deletions(-) delete mode 100644 java_easy_AES_file_encryption.md delete mode 100644 java_easy_AES_string_encryption.md delete mode 100644 src/main/java/com/cryptoexamples/java/EncryptedFile.java delete mode 100644 src/main/java/com/cryptoexamples/java/EncryptedString.java delete mode 100644 src/main/java/com/cryptoexamples/java/ExampleEncryptedFile.java delete mode 100644 src/main/java/com/cryptoexamples/java/ExampleEncryptedString.java delete mode 100644 src/test/java/com/cryptoexamples/java/EncryptedFileTest.java delete mode 100644 src/test/java/com/cryptoexamples/java/EncryptedStringTest.java diff --git a/java_easy_AES_file_encryption.md b/java_easy_AES_file_encryption.md deleted file mode 100644 index 54bdc4b..0000000 --- a/java_easy_AES_file_encryption.md +++ /dev/null @@ -1,22 +0,0 @@ ---- -title: Java File Encryption using JDK -keywords: sample -summary: "Java based string encryption" -permalink: java_easy_AES_file_encryption.html -folder: Java JDK -tags: [Java, AES, GCM, PBKDF2, Salt, AEAD] ---- - -## Sample Code for Java based symmetric file encryption - -```java -{% include_relative src/main/java/com/cryptoexamples/java/ExampleEncryptedFile.java %} -``` - -### EncryptedFile encapsulating class using AES-GCM and PBKDF2 -```java -{% include_relative src/main/java/com/cryptoexamples/java/EncryptedFile.java %} -``` - - -{% include links.html %} diff --git a/java_easy_AES_string_encryption.md b/java_easy_AES_string_encryption.md deleted file mode 100644 index a5e8262..0000000 --- a/java_easy_AES_string_encryption.md +++ /dev/null @@ -1,22 +0,0 @@ ---- -title: Java String Encryption using JDK -keywords: sample -summary: "Java based string encryption" -permalink: java_easy_AES_string_encryption.html -folder: Java JDK -tags: [Java, AES, GCM, PBKDF2, Salt, AEAD] ---- - -## Sample Code for Java based symmetric encryption - -```java -{% include_relative src/main/java/com/cryptoexamples/java/ExampleEncryptedString.java %} -``` - -### EncryptedString Encapsulating class using AES-GCM and PBKDF2 -```java -{% include_relative src/main/java/com/cryptoexamples/java/EncryptedString.java %} -``` - - -{% include links.html %} diff --git a/src/main/java/com/cryptoexamples/java/EncryptedFile.java b/src/main/java/com/cryptoexamples/java/EncryptedFile.java deleted file mode 100644 index e2b894d..0000000 --- a/src/main/java/com/cryptoexamples/java/EncryptedFile.java +++ /dev/null @@ -1,194 +0,0 @@ -package com.cryptoexamples.java; - -import javax.crypto.*; -import javax.crypto.spec.GCMParameterSpec; -import javax.crypto.spec.PBEKeySpec; -import javax.crypto.spec.SecretKeySpec; -import java.io.*; -import java.nio.charset.StandardCharsets; -import java.security.GeneralSecurityException; -import java.security.NoSuchAlgorithmException; -import java.security.SecureRandom; -import java.security.spec.KeySpec; -import java.util.Base64; -import java.util.logging.Level; -import java.util.logging.Logger; - -/** - * Encapsulating class for saving a String encrypted in a file and to decrypt/retrieve it. - * - * Including - * - Random password generation using strong secure random number generator - * - Random salt generation - * - Key derivation using PBKDF2 HMAC SHA-256, - * - AES-256 authenticated encryption using GCM - * - UTF-8 encoding - * // TODO store all encryption parameters (as authenticated data) prepended to the file content - * // TODO use Cryptographic Message Snytax (https://tools.ietf.org/html/rfc5652) - */ -public class EncryptedFile implements Serializable { - private static final Logger LOGGER = Logger.getLogger(EncryptedFile.class.getName()); - - /* 128, 120, 112, 104, or 96 @see NIST Special Publication 800-38D*/ - private static final int DEFAULT_GCM_AUTHENTICATION_TAG_SIZE_BITS = 128; - - private static final int DEFAULT_GCM_IV_NONCE_SIZE_BYTES = 12; - private static final int DEFAULT_PBKDF2_ITERATIONS = 65536; - private static final int DEFAULT_PBKDF2_SALT_SIZE_BYTES = 32; - - /* @see https://www.keylength.com/ */ - private static final int DEFAULT_AES_KEY_LENGTH_BITS = 256; - private static final String DEFAULT_CIPHER = "AES"; - private static final String DEFAULT_CIPHERSCHEME = "AES/GCM/NoPadding"; - private static final String DEFAULT_PBKDF2_SCHEME = "PBKDF2WithHmacSHA256"; - - private int gcmAuthenticationTagSizeBits = DEFAULT_GCM_AUTHENTICATION_TAG_SIZE_BITS; - private int gcmIvNonceSizeBytes = DEFAULT_GCM_IV_NONCE_SIZE_BYTES; - private int pbkdf2Iterations = DEFAULT_PBKDF2_ITERATIONS; - private int pbkdf2SaltSizeBytes = DEFAULT_PBKDF2_SALT_SIZE_BYTES; - private int aesKeyLengthBits = DEFAULT_AES_KEY_LENGTH_BITS; - private String cipher = DEFAULT_CIPHER; - private String cipherscheme = DEFAULT_CIPHERSCHEME; - private String pbkdf2Scheme = DEFAULT_PBKDF2_SCHEME; - - /** - * Creates a new empty EncryptedFile object - */ - public EncryptedFile() { - // uses default parameters, see initialization at the beginning. - } - - /** - * Generates a randomly filled byte array - * - * @param sizeInBytes length of the array in bytes - * @return byte array containing random values - * @throws NoSuchAlgorithmException - */ - private static byte[] generateRandomArry(int sizeInBytes) throws NoSuchAlgorithmException { - /* generate random salt */ - final byte[] salt = new byte[sizeInBytes]; - SecureRandom random = SecureRandom.getInstanceStrong(); - random.nextBytes(salt); - return salt; - } - - /** - * Generates a random password. - * - * @param sizeInBytes length of the password in byte - * @return Base64 encoded string with a random password - * @throws NoSuchAlgorithmException - */ - public static String generatePassword(int sizeInBytes) throws NoSuchAlgorithmException { - return Base64.getEncoder().encodeToString(generateRandomArry(sizeInBytes)); - } - - /** - * Encrypts the provided plainText using the provided password and stores it in a file - * - * @param plainText plaintext that should be encrypted - * @param password password which is used to generate the key - * @param path path to a writeable file (may already exist) - * @throws GeneralSecurityException - */ - public void encrypt(String plainText, String password, String path) throws GeneralSecurityException { - /* Derive the key*/ - SecretKeyFactory factory = SecretKeyFactory.getInstance(pbkdf2Scheme); - byte[] newSalt = generateRandomArry(pbkdf2SaltSizeBytes); - KeySpec keyspec = new PBEKeySpec(password.toCharArray(), newSalt, pbkdf2Iterations, aesKeyLengthBits); - SecretKey tmp = factory.generateSecret(keyspec); - SecretKey key = new SecretKeySpec(tmp.getEncoded(), cipher); - - Cipher myCipher = Cipher.getInstance(cipherscheme); - byte[] newNonce = generateRandomArry(gcmIvNonceSizeBytes); - GCMParameterSpec spec = new GCMParameterSpec(gcmAuthenticationTagSizeBits, newNonce); - myCipher.init(Cipher.ENCRYPT_MODE, key, spec); - - // SET UP OUTPUT STREAM and write content of String - try ( - FileOutputStream fileOutputStream = new FileOutputStream(path); - CipherOutputStream encryptedOutputStream = new CipherOutputStream(fileOutputStream, myCipher); - InputStream stringInputStream = new ByteArrayInputStream(plainText.getBytes(StandardCharsets.UTF_8)); - ) { - // write IV/nonce - fileOutputStream.write(newNonce); - - // write salt - fileOutputStream.write(newSalt); - - byte[] buffer = new byte[8192]; - while (stringInputStream.read(buffer) > 0) { - encryptedOutputStream.write(buffer); - } - } catch (IOException e) { - LOGGER.log(Level.SEVERE, e.getMessage(), e); - throw new SecurityException(e.getMessage(), e); - } - } - - /** - * Decrypts the cipherText using the provided password. - * - * @param password password which is used to generate the key - * @param path path to a previously encrypted file to be decrypted - * @return plaintext - * @throws GeneralSecurityException - */ - public String decrypt(String password, String path ) throws GeneralSecurityException { - - // Read configuration from file - - byte[] myNonce = new byte[gcmIvNonceSizeBytes]; - byte[] mySalt = new byte[pbkdf2SaltSizeBytes]; - - try ( - FileInputStream fileInputStream = new FileInputStream(path); - ) { - int countReadBytesNonce = fileInputStream.read(myNonce); - int countReadBytesSalt = fileInputStream.read(mySalt); - } catch (IOException e) { - LOGGER.log(Level.SEVERE, e.getMessage(), e); - throw new SecurityException(e.getMessage(), e); - } - - /* Derive the key*/ - SecretKeyFactory factory = SecretKeyFactory.getInstance(pbkdf2Scheme); - // Needs unlimited strength policy files http://www.oracle.com/technetwork/java/javase/downloads - KeySpec keyspec = new PBEKeySpec(password.toCharArray(), mySalt, pbkdf2Iterations, aesKeyLengthBits); - SecretKey tmp = factory.generateSecret(keyspec); - SecretKey key = new SecretKeySpec(tmp.getEncoded(), cipher); - - Cipher myCipher = Cipher.getInstance(cipherscheme); - GCMParameterSpec spec = new GCMParameterSpec(gcmAuthenticationTagSizeBits, myNonce); - - myCipher.init(Cipher.DECRYPT_MODE, key, spec); - - // READ ENCRYPTED FILE - StringBuilder stringBuilder = new StringBuilder(); - - //cipher.updateAAD(aad); - try ( - FileInputStream fileInputStream = new FileInputStream(path); - CipherInputStream cipherInputStream = new CipherInputStream(fileInputStream, myCipher); - ) { - // offset the stream by the bytes already read previosly - - // TODO check if file has this bytes at least. - byte[] skipped = new byte[gcmIvNonceSizeBytes+pbkdf2SaltSizeBytes]; - int read = fileInputStream.read(skipped); - - byte[] buffer = new byte[8192]; - while (cipherInputStream.read(buffer) > 0) { - stringBuilder.append(new String(buffer, StandardCharsets.UTF_8)); - } - } catch (IOException e) { - LOGGER.log(Level.SEVERE, e.getMessage(), e); - throw new SecurityException(e.getMessage(), e); - } - - // TODO trim() should not be needed! - return stringBuilder.toString().trim(); - } -} - diff --git a/src/main/java/com/cryptoexamples/java/EncryptedString.java b/src/main/java/com/cryptoexamples/java/EncryptedString.java deleted file mode 100644 index fd1b7b9..0000000 --- a/src/main/java/com/cryptoexamples/java/EncryptedString.java +++ /dev/null @@ -1,188 +0,0 @@ -package com.cryptoexamples.java; - -import javax.crypto.Cipher; -import javax.crypto.SecretKey; -import javax.crypto.SecretKeyFactory; -import javax.crypto.spec.GCMParameterSpec; -import javax.crypto.spec.PBEKeySpec; -import javax.crypto.spec.SecretKeySpec; -import java.io.Serializable; -import java.security.GeneralSecurityException; -import java.security.NoSuchAlgorithmException; -import java.security.SecureRandom; -import java.security.spec.KeySpec; -import java.util.Base64; - -/** - * Encapsulating class for encrypting and decrypting strings - * Including - * - Random password generation using strong secure random number generator - * - Random salt generation - * - Key derivation using PBKDF2 HMAC SHA-256, - * - AES-256 authenticated encryption using GCM - * - BASE64-encoding as representation for the byte-arrays - */ -public class EncryptedString implements Serializable { - - /* 128, 120, 112, 104, or 96 @see NIST Special Publication 800-38D*/ - private static final int DEFAULT_GCM_AUTHENTICATION_TAG_SIZE_BITS = 128; - - private static final int DEFAULT_GCM_IV_NONCE_SIZE_BYTES = 12; - private static final int DEFAULT_PBKDF2_ITERATIONS = 65536; - private static final int DEFAULT_PBKDF2_SALT_SIZE_BYTES = 32; - - /* @see https://www.keylength.com/ */ - private static final int DEFAULT_AES_KEY_LENGTH_BITS = 256; - private static final String DEFAULT_CIPHER = "AES"; - private static final String DEFAULT_CIPHERSCHEME = "AES/GCM/NoPadding"; - private static final String DEFAULT_PBKDF2_SCHEME = "PBKDF2WithHmacSHA256"; - - private int gcmAuthenticationTagSizeBits = DEFAULT_GCM_AUTHENTICATION_TAG_SIZE_BITS; - private int gcmIvNonceSizeBytes = DEFAULT_GCM_IV_NONCE_SIZE_BYTES; - private int pbkdf2Iterations = DEFAULT_PBKDF2_ITERATIONS; - private int pbkdf2SaltSizeBytes = DEFAULT_PBKDF2_SALT_SIZE_BYTES; - private int aesKeyLengthBits = DEFAULT_AES_KEY_LENGTH_BITS; - private String cipher = DEFAULT_CIPHER; - private String cipherscheme = DEFAULT_CIPHERSCHEME; - private String pbkdf2Scheme = DEFAULT_PBKDF2_SCHEME; - - private byte[] nonce; - private byte[] salt; - private String cipherText; - - /** - * Creates a new com.cryptoexamples.java.EncryptedString object based on cipherText, nonce and salt. - * - * @param cipherText encrypted plaintext (generated from encrypt) - * @param nonce byte array, number used once (random) see gcmIvNonceSizeBytes - * @param salt random byte array to prevent rainbow table attacks on password lists - */ - public EncryptedString(String cipherText, byte[] nonce, byte[] salt) { - this.cipherText = cipherText; - this.nonce = nonce; - this.salt = salt; - } - - /** - * Initializes this com.cryptoexamples.java.EncryptedString object with the provided parameters - * - * @param cipher - * @param cipherscheme - * @param gcmAuthenticationTagSizeBits - * @param gcmIvNonceSizeBytes - * @param pbkdf2Iterations - * @param pbkdf2SaltSizeBytes - * @param aesKeyLengthBits - * @param pbkdf2Scheme - */ - private EncryptedString(String cipherText, byte[] nonce, byte[] salt, String cipher, String cipherscheme, int gcmAuthenticationTagSizeBits, int gcmIvNonceSizeBytes, int pbkdf2Iterations, int pbkdf2SaltSizeBytes, int aesKeyLengthBits, String pbkdf2Scheme) { - this.cipherText = cipherText; - this.nonce = nonce; - this.salt = salt; - - this.cipher = cipher; - this.cipherscheme = cipherscheme; - this.gcmAuthenticationTagSizeBits = gcmAuthenticationTagSizeBits; - this.gcmIvNonceSizeBytes = gcmIvNonceSizeBytes; - this.pbkdf2Iterations = pbkdf2Iterations; - this.pbkdf2SaltSizeBytes = pbkdf2SaltSizeBytes; - this.aesKeyLengthBits = aesKeyLengthBits; - this.pbkdf2Scheme = pbkdf2Scheme; - } - - /** - * Creates a new empty com.cryptoexamples.java.EncryptedString object - */ - public EncryptedString() { - // uses default parameters, see initialization at the beginning. - } - - /** - * Generates a randomly filled byte array - * - * @param sizeInBytes length of the array in bytes - * @return byte array containing random values - * @throws NoSuchAlgorithmException - */ - private static byte[] generateRandomArry(int sizeInBytes) throws NoSuchAlgorithmException { - /* generate random salt */ - final byte[] salt = new byte[sizeInBytes]; - SecureRandom random = SecureRandom.getInstanceStrong(); - random.nextBytes(salt); - return salt; - } - - /** - * Generates a random password. - * - * @param sizeInBytes length of the password in byte - * @return Base64 encoded string with a random password - * @throws NoSuchAlgorithmException - */ - public static String generatePassword(int sizeInBytes) throws NoSuchAlgorithmException { - return Base64.getEncoder().encodeToString(generateRandomArry(sizeInBytes)); - } - - private byte[] getNonce() { - return this.nonce; - } - - private byte[] getSalt() { - return this.salt; - } - - private String getCipherText() { - return this.cipherText; - } - - /** - * Encrypts the provided plainText using the provided password. - * - * @param plainText plaintext that should be encrypted - * @param password password which is used to generate the key - * @return new com.cryptoexamples.java.EncryptedString object - * @throws GeneralSecurityException - */ - public EncryptedString encrypt(String plainText, String password) throws GeneralSecurityException { - /* Derive the key*/ - SecretKeyFactory factory = SecretKeyFactory.getInstance(pbkdf2Scheme); - byte[] newSalt = generateRandomArry(pbkdf2SaltSizeBytes); - KeySpec keyspec = new PBEKeySpec(password.toCharArray(), newSalt, pbkdf2Iterations, aesKeyLengthBits); - SecretKey tmp = factory.generateSecret(keyspec); - SecretKey key = new SecretKeySpec(tmp.getEncoded(), cipher); - - Cipher myCipher = Cipher.getInstance(cipherscheme); - byte[] newNonce = generateRandomArry(gcmIvNonceSizeBytes); - GCMParameterSpec spec = new GCMParameterSpec(gcmAuthenticationTagSizeBits, newNonce); - myCipher.init(Cipher.ENCRYPT_MODE, key, spec); - - byte[] byteCipher = myCipher.doFinal(plainText.getBytes()); - - return new EncryptedString(new String(Base64.getEncoder().encode(byteCipher)), newNonce, newSalt, this.cipher, cipherscheme, gcmAuthenticationTagSizeBits, gcmIvNonceSizeBytes, pbkdf2Iterations, pbkdf2SaltSizeBytes, aesKeyLengthBits, pbkdf2Scheme); - } - - /** - * Decrypts the cipherText using the provided password. - * - * @param password password which is used to generate the key - * @return plaintext - * @throws GeneralSecurityException - */ - public String decrypt(String password) throws GeneralSecurityException { - /* Derive the key*/ - SecretKeyFactory factory = SecretKeyFactory.getInstance(pbkdf2Scheme); - // Needs unlimited strength policy files http://www.oracle.com/technetwork/java/javase/downloads - KeySpec keyspec = new PBEKeySpec(password.toCharArray(), getSalt(), pbkdf2Iterations, aesKeyLengthBits); - SecretKey tmp = factory.generateSecret(keyspec); - SecretKey key = new SecretKeySpec(tmp.getEncoded(), cipher); - - Cipher myCipher = Cipher.getInstance(cipherscheme); - GCMParameterSpec spec = new GCMParameterSpec(gcmAuthenticationTagSizeBits, getNonce()); - - myCipher.init(Cipher.DECRYPT_MODE, key, spec); - - byte[] decryptedCipher = myCipher.doFinal(Base64.getDecoder().decode(getCipherText())); - return new String(decryptedCipher); - } -} - diff --git a/src/main/java/com/cryptoexamples/java/ExampleEncryptedFile.java b/src/main/java/com/cryptoexamples/java/ExampleEncryptedFile.java deleted file mode 100644 index b45eeb6..0000000 --- a/src/main/java/com/cryptoexamples/java/ExampleEncryptedFile.java +++ /dev/null @@ -1,43 +0,0 @@ -package com.cryptoexamples.java; - -import java.security.GeneralSecurityException; -import java.util.logging.Level; -import java.util.logging.Logger; - -// TODO check if KeyStore should be used - -/** - * Object oriented example for encryption and decryption of a string; - * Including - * - Random password generation using strong secure random number generator - * - Random salt generation - * - Key derivation using PBKDF2 HMAC SHA-256, - * - AES-256 authenticated encryption using GCM - * - BASE64-encoding as representation for the byte-arrays - * - Exception handling - */ -public class ExampleEncryptedFile { - private static final Logger LOGGER = Logger.getLogger(ExampleEncryptedFile.class.getName()); - - public static void main(String[] args) { - String plainText = "Text that is going to be sent over an insecure channel and must be encrypted at all costs!"; - - try { - // GENERATE a password (if a password exists, use that). - String password = EncryptedFile.generatePassword(32); - String path = "encryptedFile.enc"; - - - // ENCRYPTION - new EncryptedFile().encrypt(plainText, password, path); - - // DECRYPTION - String decryptedCipherText = new EncryptedFile().decrypt(password, path); - - LOGGER.log(Level.INFO, () -> String.format("Decrypted and original plain text are the same: %b", decryptedCipherText.compareTo(plainText) == 0)); - } catch (GeneralSecurityException e) { - LOGGER.log(Level.SEVERE, e.getMessage(), e); - } - } - -} diff --git a/src/main/java/com/cryptoexamples/java/ExampleEncryptedString.java b/src/main/java/com/cryptoexamples/java/ExampleEncryptedString.java deleted file mode 100644 index 2d30af1..0000000 --- a/src/main/java/com/cryptoexamples/java/ExampleEncryptedString.java +++ /dev/null @@ -1,41 +0,0 @@ -package com.cryptoexamples.java; - -import java.security.GeneralSecurityException; -import java.util.logging.Level; -import java.util.logging.Logger; - -// TODO check if KeyStore should be used - -/** - * Object oriented example for encryption and decryption of a string; - * Including - * - Random password generation using strong secure random number generator - * - random salt generation - * - Key derivation using PBKDF2 HMAC SHA-256, - * - AES-256 authenticated encryption using GCM - * - BASE64-encoding as representation for the byte-arrays - * - Exception handling - */ -public class ExampleEncryptedString { - private static final Logger LOGGER = Logger.getLogger(ExampleEncryptedString.class.getName()); - - public static void main(String[] args) { - String plainText = "Text that is going to be sent over an insecure channel and must be encrypted at all costs!"; - - try { - // GENERATE a password (if a password exists, use that). - String password = EncryptedString.generatePassword(32); - - // ENCRYPTION - EncryptedString encryptedString = new EncryptedString().encrypt(plainText, password); - - // DECRYPTION - String decryptedCipherText = encryptedString.decrypt(password); - - LOGGER.log(Level.INFO, () -> String.format("Decrypted and original plain text are the same: %b", decryptedCipherText.compareTo(plainText) == 0)); - } catch (GeneralSecurityException e) { - LOGGER.log(Level.SEVERE, e.getMessage(), e); - } - } - -} diff --git a/src/test/java/com/cryptoexamples/java/EncryptedFileTest.java b/src/test/java/com/cryptoexamples/java/EncryptedFileTest.java deleted file mode 100644 index 0173762..0000000 --- a/src/test/java/com/cryptoexamples/java/EncryptedFileTest.java +++ /dev/null @@ -1,55 +0,0 @@ -package com.cryptoexamples.java; - -import org.junit.Test; - -import java.security.GeneralSecurityException; - -import static org.junit.Assert.assertEquals; -import static org.junit.Assert.assertTrue; - - -/** - * Created by Kai on 12.04.2017. - */ -public class EncryptedFileTest { - - - public void setUp() { - - } - - - public void tearDown() { - - } - - @Test - public void testEncryptAndDecryptWithUmlaut() { - try { - String password = EncryptedString.generatePassword(32); - String testString = "Die heiße Zypernsonne quälte Max und Victoria ja böse auf dem Weg bis zur Küste"; - String path = "encryptedFile.enc"; - EncryptedFile encryptedFile = new EncryptedFile(); - encryptedFile.encrypt(testString,password,path); - - assertEquals(testString, new EncryptedFile().decrypt(password, path)); - } catch (GeneralSecurityException e) { - assertTrue(false); - } - } - - @Test - public void testEncryptAndDecryptWithASCII() { - try { - String password = EncryptedString.generatePassword(32); - String testString = "A quick movement of the enemy will jeopardize six gunboats."; - String path = "encryptedFile.enc"; - EncryptedFile encryptedFile = new EncryptedFile(); - encryptedFile.encrypt(testString,password,path); - - assertEquals(testString, new EncryptedFile().decrypt(password, path)); - } catch (GeneralSecurityException e) { - assertTrue(false); - } - } -} diff --git a/src/test/java/com/cryptoexamples/java/EncryptedStringTest.java b/src/test/java/com/cryptoexamples/java/EncryptedStringTest.java deleted file mode 100644 index 96aed10..0000000 --- a/src/test/java/com/cryptoexamples/java/EncryptedStringTest.java +++ /dev/null @@ -1,50 +0,0 @@ -package com.cryptoexamples.java; - -import com.cryptoexamples.java.EncryptedString; -import org.junit.Test; - -import java.security.GeneralSecurityException; - -import static org.junit.Assert.assertEquals; -import static org.junit.Assert.assertTrue; - - -/** - * Created by Kai on 12.04.2017. - */ -public class EncryptedStringTest { - - - public void setUp() { - - } - - - public void tearDown() { - - } - - @Test - public void testEncryptAndDecryptWithUmlaut() { - try { - String password = EncryptedString.generatePassword(32); - String testString = "Die heiße Zypernsonne quälte Max und Victoria ja böse auf dem Weg bis zur Küste"; - EncryptedString encryptedString = new EncryptedString().encrypt(testString, password); - assertEquals(testString, encryptedString.decrypt(password)); - } catch (GeneralSecurityException e) { - assertTrue(false); - } - } - - @Test - public void testEncryptAndDecryptWithASCII() { - try { - String password = EncryptedString.generatePassword(32); - String testString = "A quick movement of the enemy will jeopardize six gunboats."; - EncryptedString encryptedString = new EncryptedString().encrypt(testString, password); - assertEquals(testString, encryptedString.decrypt(password)); - } catch (GeneralSecurityException e) { - assertTrue(false); - } - } -} From 0aa41a87b55b280fe0f0585f3f4d7a73277bbb92 Mon Sep 17 00:00:00 2001 From: Kai Mindermann Date: Sun, 13 May 2018 09:29:56 +0200 Subject: [PATCH 14/33] refactors example code (variable names) and base64 usage --- java_landing_page.md | 16 +++++++------- java_string_encryption_asymmetric.md | 2 +- java_string_encryption_key_based_symmetric.md | 21 ++++++++++++++++++ ...ing_encryption_password_based_symmetric.md | 21 ++++++++++++++++++ java_string_hash.md | 21 ++++++++++++++++++ java_string_sign.md | 21 ++++++++++++++++++ ...AsymmetricStringEncryptionInOneMethod.java | 13 +++++------ .../ExampleFileEncryptionInOneMethod.java | 8 +++---- .../java/ExampleHashInOneMethod.java | 11 +++++----- .../java/ExampleSignatureInOneMethod.java | 10 ++++----- ...leStringEncryptionKeyBasedInOneMethod.java | 16 ++++++-------- ...ingEncryptionPasswordBasedInOneMethod.java | 22 +++++++------------ 12 files changed, 127 insertions(+), 55 deletions(-) diff --git a/java_landing_page.md b/java_landing_page.md index 4feb5da..ccdbb84 100644 --- a/java_landing_page.md +++ b/java_landing_page.md @@ -9,11 +9,11 @@ is_landingpage: 1 # Available Crypto Scenarios and Use Cases -| | All in One | Easy Object oriented | -|-------------------------------------------------|----------------------------------------|--------------------------------------| -| Symmetric Encryption | [String Encryption (password based) ✔](java_string_encryption_password_based_symmetric.html)
[String Encryption (key based) ✔](java_string_encryption_key_based_symmetric.html)
[File Encryption ✔](java_file_encryption_symmetric_password_based.html) | [String Encryption with separate class ✔](java_easy_AES_string_encryption.html)
[File Encryption with separate class ✔](java_easy_AES_file_encryption.html) | -| Asymmetric Encryption / Public Key Cryptography | [String Encryption ✔](java_asymmetric_string_encryption.html) | | -| Key Storage | | | -| Hashing | [String Hash ✔](java_string_hash.html) | N/A | -| Crypto Provider Setup | | | -| Digital Signatures | [String Signing ✔](java_string_sign.html) | | +| | All in One | +|-------------------------------------------------|----------------------------------------| +| Symmetric Encryption | [Symmetric String Encryption (password based) ✔](java_string_encryption_password_based_symmetric.html)
[Symmetric String Encryption (key based) ✔](java_string_encryption_key_based_symmetric.html)
[Symmetric File Encryption ✔](java_file_encryption_symmetric_password_based.html) | +| Asymmetric Encryption / Public Key Cryptography | [Asymmetric String Encryption ✔](java_asymmetric_string_encryption.html) | | +| Key Storage | | +| Hashing | [String Hash ✔](java_string_hash.html) | +| Crypto Provider Setup | | +| Digital Signatures | [String Signing ✔](java_string_sign.html) | diff --git a/java_string_encryption_asymmetric.md b/java_string_encryption_asymmetric.md index e677ad9..5b29676 100644 --- a/java_string_encryption_asymmetric.md +++ b/java_string_encryption_asymmetric.md @@ -24,7 +24,7 @@ current_reviews: [ ] # Indicates when this example was last updated/created. Reviews don't change this. -last_updated: "2018-04-28" +last_updated: "2018-05-13" tags: [Java, RSA, Asymmetric, String, Encryption] --- diff --git a/java_string_encryption_key_based_symmetric.md b/java_string_encryption_key_based_symmetric.md index 9a36731..c866aff 100644 --- a/java_string_encryption_key_based_symmetric.md +++ b/java_string_encryption_key_based_symmetric.md @@ -4,6 +4,27 @@ keywords: sample summary: "String encryption in Java with key generation" permalink: java_string_encryption_key_based_symmetric.html folder: Java JDK +references: [ + # Place a list of references used to create and/or understand this example. + { + url: "https://docs.oracle.com/javase/10/docs/api/javax/crypto/Cipher.html", + description: "Oracle JDK Cipher Documentation" + } +] +authors: [ + { + name: "Kai Mindermann", + url: "https://github.com/kmindi" + } +] +# List all reviewers that reviewed this version of the example. When the example is updated all old reviews +# must be removed from the list below and the code has to be reviewed again. The complete review process +# is documented in the main repository of CryptoExamples +current_reviews: [ + +] +# Indicates when this example was last updated/created. Reviews don't change this. +last_updated: "2018-05-13" tags: [Java, AES, GCM, Salt, AEAD] --- diff --git a/java_string_encryption_password_based_symmetric.md b/java_string_encryption_password_based_symmetric.md index b5de4ae..debfdc3 100644 --- a/java_string_encryption_password_based_symmetric.md +++ b/java_string_encryption_password_based_symmetric.md @@ -4,6 +4,27 @@ keywords: sample summary: "Password based string encryption in Java" permalink: java_string_encryption_password_based_symmetric.html folder: Java JDK +references: [ + # Place a list of references used to create and/or understand this example. + { + url: "https://docs.oracle.com/javase/10/docs/api/javax/crypto/Cipher.html", + description: "Oracle JDK Cipher Documentation" + } +] +authors: [ + { + name: "Kai Mindermann", + url: "https://github.com/kmindi" + } +] +# List all reviewers that reviewed this version of the example. When the example is updated all old reviews +# must be removed from the list below and the code has to be reviewed again. The complete review process +# is documented in the main repository of CryptoExamples +current_reviews: [ + +] +# Indicates when this example was last updated/created. Reviews don't change this. +last_updated: "2018-05-13" tags: [Java, AES, GCM, PBKDF2, Salt, AEAD] --- diff --git a/java_string_hash.md b/java_string_hash.md index 53d6bac..e97bc40 100644 --- a/java_string_hash.md +++ b/java_string_hash.md @@ -4,6 +4,27 @@ keywords: sample summary: "Java based string hashing" permalink: java_string_hash.html folder: Java JDK +references: [ + # Place a list of references used to create and/or understand this example. + { + url: "https://docs.oracle.com/javase/10/docs/api/java/security/MessageDigest.html", + description: "Oracle JDK MessageDigest Documentation" + } +] +authors: [ + { + name: "Kai Mindermann", + url: "https://github.com/kmindi" + } +] +# List all reviewers that reviewed this version of the example. When the example is updated all old reviews +# must be removed from the list below and the code has to be reviewed again. The complete review process +# is documented in the main repository of CryptoExamples +current_reviews: [ + +] +# Indicates when this example was last updated/created. Reviews don't change this. +last_updated: "2018-05-13" tags: [Java, hash, SHA, SHA-512] --- diff --git a/java_string_sign.md b/java_string_sign.md index 446ed84..5f34073 100644 --- a/java_string_sign.md +++ b/java_string_sign.md @@ -4,6 +4,27 @@ keywords: sample summary: "Java based string signing" permalink: java_string_sign.html folder: Java JDK +references: [ + # Place a list of references used to create and/or understand this example. + { + url: "https://docs.oracle.com/javase/10/docs/api/java/security/Signature.html", + description: "Oracle JDK Signature Documentation" + } +] +authors: [ + { + name: "Kai Mindermann", + url: "https://github.com/kmindi" + } +] +# List all reviewers that reviewed this version of the example. When the example is updated all old reviews +# must be removed from the list below and the code has to be reviewed again. The complete review process +# is documented in the main repository of CryptoExamples +current_reviews: [ + +] +# Indicates when this example was last updated/created. Reviews don't change this. +last_updated: "2018-05-13" tags: [Java, hash, SHA, SHA-512] --- diff --git a/src/main/java/com/cryptoexamples/java/ExampleAsymmetricStringEncryptionInOneMethod.java b/src/main/java/com/cryptoexamples/java/ExampleAsymmetricStringEncryptionInOneMethod.java index 3f8b85a..84e25c2 100644 --- a/src/main/java/com/cryptoexamples/java/ExampleAsymmetricStringEncryptionInOneMethod.java +++ b/src/main/java/com/cryptoexamples/java/ExampleAsymmetricStringEncryptionInOneMethod.java @@ -17,8 +17,8 @@ * All in one example for asymmetric encryption and decryption of a string in one method. * - Generation of public and private RSA 4096 bit keypair * - AES-256 authenticated encryption using GCM - * - BASE64-encoding as representation for the byte-arrays - * - UTF-8 encoding of String + * - BASE64 encoding as representation for the byte-arrays + * - UTF-8 encoding of Strings * - Exception handling */ public class ExampleAsymmetricStringEncryptionInOneMethod { @@ -27,7 +27,6 @@ public class ExampleAsymmetricStringEncryptionInOneMethod { public static void main(String[] args) { String plainText = "Text that is going to be sent over an insecure channel and must be encrypted at all costs!"; try { - // GENERATE NEW KEYPAIR KeyPairGenerator keyPairGenerator = KeyPairGenerator.getInstance("RSA"); /* @see https://www.keylength.com/ */ @@ -38,15 +37,15 @@ public static void main(String[] args) { Cipher cipher = Cipher.getInstance("RSA/ECB/OAEPWithSHA-256AndMGF1Padding"); cipher.init(Cipher.ENCRYPT_MODE, keyPair.getPublic()); - byte[] byteCipher = cipher.doFinal(plainText.getBytes()); + byte[] cipherTextBytes = cipher.doFinal(plainText.getBytes()); // CONVERSION of raw bytes to BASE64 representation - String cipherText = new String(Base64.getEncoder().encode(byteCipher)); + String cipherText = Base64.getEncoder().encodeToString(cipherTextBytes); // DECRYPTION cipher.init(Cipher.DECRYPT_MODE, keyPair.getPrivate()); - byte[] decryptedCipher = cipher.doFinal(Base64.getDecoder().decode(cipherText)); - String decryptedCipherText = new String(decryptedCipher); + byte[] decryptedCipherTextBytes = cipher.doFinal(Base64.getDecoder().decode(cipherText)); + String decryptedCipherText = new String(decryptedCipherTextBytes); LOGGER.log(Level.INFO, () -> String.format("Decrypted and original plain text are the same: %b", decryptedCipherText.compareTo(plainText) == 0)); } catch (NoSuchAlgorithmException | NoSuchPaddingException | InvalidKeyException | IllegalBlockSizeException | BadPaddingException | InvalidParameterException e) { diff --git a/src/main/java/com/cryptoexamples/java/ExampleFileEncryptionInOneMethod.java b/src/main/java/com/cryptoexamples/java/ExampleFileEncryptionInOneMethod.java index ef89604..b4a0d00 100644 --- a/src/main/java/com/cryptoexamples/java/ExampleFileEncryptionInOneMethod.java +++ b/src/main/java/com/cryptoexamples/java/ExampleFileEncryptionInOneMethod.java @@ -63,9 +63,9 @@ public static void main(String[] args) { // SET UP OUTPUT STREAM and write content of String try ( - FileOutputStream fileOutputStream = new FileOutputStream("encryptedFile.enc"); - CipherOutputStream encryptedOutputStream = new CipherOutputStream(fileOutputStream, cipher); - InputStream stringInputStream = new ByteArrayInputStream(plainText.getBytes(StandardCharsets.UTF_8)); + FileOutputStream fileOutputStream = new FileOutputStream("encryptedFile.enc"); + CipherOutputStream encryptedOutputStream = new CipherOutputStream(fileOutputStream, cipher); + InputStream stringInputStream = new ByteArrayInputStream(plainText.getBytes(StandardCharsets.UTF_8)) ) { byte[] buffer = new byte[8192]; while (stringInputStream.read(buffer) > 0) { @@ -79,7 +79,7 @@ public static void main(String[] args) { //cipher.updateAAD(aad); try ( FileInputStream fileInputStream = new FileInputStream("encryptedFile.enc"); - CipherInputStream cipherInputStream = new CipherInputStream(fileInputStream, cipher); + CipherInputStream cipherInputStream = new CipherInputStream(fileInputStream, cipher) ) { byte[] buffer = new byte[8192]; while (cipherInputStream.read(buffer) > 0) { diff --git a/src/main/java/com/cryptoexamples/java/ExampleHashInOneMethod.java b/src/main/java/com/cryptoexamples/java/ExampleHashInOneMethod.java index c3b15d7..736a2c2 100644 --- a/src/main/java/com/cryptoexamples/java/ExampleHashInOneMethod.java +++ b/src/main/java/com/cryptoexamples/java/ExampleHashInOneMethod.java @@ -9,10 +9,9 @@ import java.util.logging.Logger; /** - * All in one example for hashing of a string in one method; - * Including + * All in one example for hashing of a string in one method. * - SHA-512 - * - BASE64-encoding as representation for the byte-arrays + * - BASE64 encoding as representation for the byte-arrays * - UTF-8 encoding of String * - Exception handling */ @@ -22,14 +21,14 @@ public class ExampleHashInOneMethod { public static void main(String[] args) { String plainText = "Text that should be authenticated by comparing the hash of it!"; try { - // https://docs.oracle.com/javase/8/docs/technotes/guides/security/StandardNames.html#MessageDigest + // Get MessageDigest Instance MessageDigest messageDigest = MessageDigest.getInstance("SHA-512"); // CREATE HASH - byte[] hash = messageDigest.digest(plainText.getBytes(StandardCharsets.UTF_8)); + byte[] hashBytes = messageDigest.digest(plainText.getBytes(StandardCharsets.UTF_8)); // CONVERT/ENCODE IN BASE64 - String hashString = new String(Base64.getEncoder().encode(hash),StandardCharsets.UTF_8); + String hashString = Base64.getEncoder().encodeToString(hashBytes); LOGGER.log(Level.INFO, hashString); } catch (NoSuchAlgorithmException e) { diff --git a/src/main/java/com/cryptoexamples/java/ExampleSignatureInOneMethod.java b/src/main/java/com/cryptoexamples/java/ExampleSignatureInOneMethod.java index ddb3306..e97fd47 100644 --- a/src/main/java/com/cryptoexamples/java/ExampleSignatureInOneMethod.java +++ b/src/main/java/com/cryptoexamples/java/ExampleSignatureInOneMethod.java @@ -12,11 +12,10 @@ import java.util.logging.Logger; /** - * All in one example for cryptographic signing of a string in one method; - * Including + * All in one example for cryptographic signing of a string in one method. * - Generation of public and private RSA 4096 bit keypair * - SHA-512 with RSA - * - BASE64-encoding as representation for the byte-arrays + * - BASE64 encoding as representation for the byte-arrays * - UTF-8 encoding of String * - Exception handling */ @@ -38,15 +37,14 @@ public static void main(String[] args) { signature.update(plainText.getBytes(StandardCharsets.UTF_8)); // SIGN DATA/STRING - byte[] signatureForPlainText = signature.sign(); - String signatureForPlainTextString = new String(Base64.getEncoder().encode(signatureForPlainText),StandardCharsets.UTF_8); + String signatureForPlainTextString = Base64.getEncoder().encodeToString(signature.sign()); LOGGER.log(Level.INFO, () -> String.format("Signature: %s", signatureForPlainTextString)); // VERIFY JUST CREATED SIGNATURE USING PUBLIC KEY signature.initVerify(keyPair.getPublic()); signature.update(plainText.getBytes(StandardCharsets.UTF_8)); - boolean isSignatureCorrect = signature.verify(signatureForPlainText); + boolean isSignatureCorrect = signature.verify(Base64.getDecoder().decode(signatureForPlainTextString)); LOGGER.log(Level.INFO, () -> String.format("Signature is correct: %b", isSignatureCorrect)); } catch (NoSuchAlgorithmException | InvalidKeyException | SignatureException e) { LOGGER.log(Level.SEVERE, e.getLocalizedMessage(), e); diff --git a/src/main/java/com/cryptoexamples/java/ExampleStringEncryptionKeyBasedInOneMethod.java b/src/main/java/com/cryptoexamples/java/ExampleStringEncryptionKeyBasedInOneMethod.java index 5c8cfc9..1dbd06d 100644 --- a/src/main/java/com/cryptoexamples/java/ExampleStringEncryptionKeyBasedInOneMethod.java +++ b/src/main/java/com/cryptoexamples/java/ExampleStringEncryptionKeyBasedInOneMethod.java @@ -7,6 +7,7 @@ import javax.crypto.NoSuchPaddingException; import javax.crypto.SecretKey; import javax.crypto.spec.GCMParameterSpec; +import java.nio.charset.StandardCharsets; import java.security.InvalidAlgorithmParameterException; import java.security.InvalidKeyException; import java.security.InvalidParameterException; @@ -17,11 +18,11 @@ import java.util.logging.Logger; /** - * All in one example for encryption and decryption of a string in one method; - * Including + * All in one example for encryption and decryption of a string in one method. * - Random key generation using strong secure random number generator * - AES-256 authenticated encryption using GCM - * - BASE64-encoding as representation for the byte-arrays + * - BASE64 encoding as representation for the byte-arrays + * - UTF-8 encoding of Strings * - Exception handling */ public class ExampleStringEncryptionKeyBasedInOneMethod { @@ -47,18 +48,15 @@ public static void main(String[] args) { GCMParameterSpec spec = new GCMParameterSpec(16 * 8, nonce); cipher.init(Cipher.ENCRYPT_MODE, key, spec); - //byte[] aad = "Additional authenticated not encrypted data".getBytes(); - //cipher.updateAAD(aad); - - byte[] byteCipher = cipher.doFinal(plainText.getBytes()); + byte[] byteCipher = cipher.doFinal(plainText.getBytes(StandardCharsets.UTF_8)); // CONVERSION of raw bytes to BASE64 representation - String cipherText = new String(Base64.getEncoder().encode(byteCipher)); + String cipherText = Base64.getEncoder().encodeToString(byteCipher); // DECRYPTION cipher.init(Cipher.DECRYPT_MODE, key, spec); //cipher.updateAAD(aad); byte[] decryptedCipher = cipher.doFinal(Base64.getDecoder().decode(cipherText)); - String decryptedCipherText = new String(decryptedCipher); + String decryptedCipherText = new String(decryptedCipher, StandardCharsets.UTF_8); LOGGER.log(Level.INFO, () -> String.format("Decrypted and original plain text are the same: %b", decryptedCipherText.compareTo(plainText) == 0)); } catch (NoSuchAlgorithmException | NoSuchPaddingException | InvalidKeyException | IllegalBlockSizeException | BadPaddingException | InvalidParameterException | InvalidAlgorithmParameterException e) { diff --git a/src/main/java/com/cryptoexamples/java/ExampleStringEncryptionPasswordBasedInOneMethod.java b/src/main/java/com/cryptoexamples/java/ExampleStringEncryptionPasswordBasedInOneMethod.java index 7455b6b..1bb70a3 100644 --- a/src/main/java/com/cryptoexamples/java/ExampleStringEncryptionPasswordBasedInOneMethod.java +++ b/src/main/java/com/cryptoexamples/java/ExampleStringEncryptionPasswordBasedInOneMethod.java @@ -10,6 +10,7 @@ import javax.crypto.spec.GCMParameterSpec; import javax.crypto.spec.PBEKeySpec; import javax.crypto.spec.SecretKeySpec; +import java.nio.charset.StandardCharsets; import java.security.InvalidAlgorithmParameterException; import java.security.InvalidKeyException; import java.security.InvalidParameterException; @@ -22,13 +23,13 @@ import java.util.logging.Logger; /** - * All in one example for encryption and decryption of a string in one method; - * Including + * All in one example for encryption and decryption of a string in one method. * - Random password generation using strong secure random number generator * - Random salt generation * - Key derivation using PBKDF2 HMAC SHA-256, * - AES-256 authenticated encryption using GCM - * - BASE64-encoding as representation for the byte-arrays + * - BASE64 encoding as representation for the byte-arrays + * - UTF-8 encoding of Strings * - Exception handling */ public class ExampleStringEncryptionPasswordBasedInOneMethod { @@ -39,7 +40,6 @@ public static void main(String[] args) { try { // GENERATE password (not needed if you have a password already) KeyGenerator keyGen = KeyGenerator.getInstance("AES"); - // Needs unlimited strength policy files http://www.oracle.com/technetwork/java/javase/downloads keyGen.init(256); String password = Base64.getEncoder().encodeToString(keyGen.generateKey().getEncoded()); @@ -50,12 +50,10 @@ public static void main(String[] args) { // DERIVE key (from password and salt) SecretKeyFactory factory = SecretKeyFactory.getInstance("PBKDF2WithHmacSHA256"); - // Needs unlimited strength policy files http://www.oracle.com/technetwork/java/javase/downloads KeySpec keyspec = new PBEKeySpec(password.toCharArray(), salt, 65536, 256); SecretKey tmp = factory.generateSecret(keyspec); SecretKey key = new SecretKeySpec(tmp.getEncoded(), "AES"); - // GENERATE random nonce (number used once) final byte[] nonce = new byte[32]; random.nextBytes(nonce); @@ -65,18 +63,14 @@ public static void main(String[] args) { GCMParameterSpec spec = new GCMParameterSpec(16 * 8, nonce); cipher.init(Cipher.ENCRYPT_MODE, key, spec); - //byte[] aad = "Additional authenticated not encrypted data".getBytes(); - //cipher.updateAAD(aad); - - byte[] byteCipher = cipher.doFinal(plainText.getBytes()); + byte[] cipherTextBytes = cipher.doFinal(plainText.getBytes(StandardCharsets.UTF_8)); // CONVERSION of raw bytes to BASE64 representation - String cipherText = new String(Base64.getEncoder().encode(byteCipher)); + String cipherText = Base64.getEncoder().encodeToString(cipherTextBytes); // DECRYPTION cipher.init(Cipher.DECRYPT_MODE, key, spec); - //cipher.updateAAD(aad); - byte[] decryptedCipher = cipher.doFinal(Base64.getDecoder().decode(cipherText)); - String decryptedCipherText = new String(decryptedCipher); + byte[] decryptedCipherTextBytes = cipher.doFinal(Base64.getDecoder().decode(cipherText)); + String decryptedCipherText = new String(decryptedCipherTextBytes, StandardCharsets.UTF_8); LOGGER.log(Level.INFO, () -> String.format("Decrypted and original plain text are the same: %b", decryptedCipherText.compareTo(plainText) == 0)); } catch (NoSuchAlgorithmException | NoSuchPaddingException | InvalidKeyException | IllegalBlockSizeException | BadPaddingException | InvalidParameterException | InvalidAlgorithmParameterException | InvalidKeySpecException e) { From 075a1d0f8925cd94fe559335051e32a4fce209f7 Mon Sep 17 00:00:00 2001 From: Kai Mindermann Date: Sun, 13 May 2018 09:34:35 +0200 Subject: [PATCH 15/33] removes commented out code --- .../java/ExampleFileEncryptionInOneMethod.java | 5 +---- 1 file changed, 1 insertion(+), 4 deletions(-) diff --git a/src/main/java/com/cryptoexamples/java/ExampleFileEncryptionInOneMethod.java b/src/main/java/com/cryptoexamples/java/ExampleFileEncryptionInOneMethod.java index b4a0d00..8c569cc 100644 --- a/src/main/java/com/cryptoexamples/java/ExampleFileEncryptionInOneMethod.java +++ b/src/main/java/com/cryptoexamples/java/ExampleFileEncryptionInOneMethod.java @@ -56,9 +56,6 @@ public static void main(String[] args) { GCMParameterSpec spec = new GCMParameterSpec(16 * 8, nonce); cipher.init(Cipher.ENCRYPT_MODE, key, spec); - //byte[] aad = "Additional authenticated not encrypted data".getBytes(); - //cipher.updateAAD(aad); - // TODO store encryption parameters as authenticated data prepended to the file content // SET UP OUTPUT STREAM and write content of String @@ -76,7 +73,7 @@ public static void main(String[] args) { // READ ENCRYPTED FILE StringBuilder stringBuilder = new StringBuilder(); cipher.init(Cipher.DECRYPT_MODE, key, spec); - //cipher.updateAAD(aad); + try ( FileInputStream fileInputStream = new FileInputStream("encryptedFile.enc"); CipherInputStream cipherInputStream = new CipherInputStream(fileInputStream, cipher) From ad11e9b0eadec683523a2538a4d9bcf3dbb881b4 Mon Sep 17 00:00:00 2001 From: Kai Mindermann Date: Sun, 13 May 2018 09:36:55 +0200 Subject: [PATCH 16/33] removes commented out code --- .../java/ExampleStringEncryptionKeyBasedInOneMethod.java | 1 - 1 file changed, 1 deletion(-) diff --git a/src/main/java/com/cryptoexamples/java/ExampleStringEncryptionKeyBasedInOneMethod.java b/src/main/java/com/cryptoexamples/java/ExampleStringEncryptionKeyBasedInOneMethod.java index 1dbd06d..0f9ddf9 100644 --- a/src/main/java/com/cryptoexamples/java/ExampleStringEncryptionKeyBasedInOneMethod.java +++ b/src/main/java/com/cryptoexamples/java/ExampleStringEncryptionKeyBasedInOneMethod.java @@ -54,7 +54,6 @@ public static void main(String[] args) { // DECRYPTION cipher.init(Cipher.DECRYPT_MODE, key, spec); - //cipher.updateAAD(aad); byte[] decryptedCipher = cipher.doFinal(Base64.getDecoder().decode(cipherText)); String decryptedCipherText = new String(decryptedCipher, StandardCharsets.UTF_8); From e22cd1340f4e24b2e6f1a82fa2e726105a807d1b Mon Sep 17 00:00:00 2001 From: Kai Mindermann Date: Sun, 13 May 2018 09:52:48 +0200 Subject: [PATCH 17/33] updates CHANGELOG.md for release 0.2.0 --- CHANGELOG.md | 15 +++++++++++++-- 1 file changed, 13 insertions(+), 2 deletions(-) diff --git a/CHANGELOG.md b/CHANGELOG.md index c5fe59b..658002c 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -7,9 +7,19 @@ and this project adheres to [Semantic Versioning](http://semver.org/spec/v2.0.0. ## [Unreleased] +## [0.2.0] - 2018-05-13 + ### Changed -- fixed version link in Changelog +- Fixed version link in Changelog +- Refactored examples +- Updated class comments + +### Removed + +- Removed easy object oriented examples that used a separate class +- Removed mentions of the need for unlimited policy files (unlimited is default since JDK / Java SE 9) +- Removed commented out code ## [0.1.1] - 2018-04-28 @@ -56,6 +66,7 @@ and this project adheres to [Semantic Versioning](http://semver.org/spec/v2.0.0. - made some security relevant changes - made other security relevant changes -[Unreleased]: https://github.com/cryptoexamples/java-crypto-examples/compare/v0.1.1...HEAD +[Unreleased]: https://github.com/cryptoexamples/java-crypto-examples/compare/v0.2.0...HEAD +[0.2.0]: https://github.com/cryptoexamples/java-crypto-examples/compare/v0.1.1...v0.2.0 [0.1.1]: https://github.com/cryptoexamples/java-crypto-examples/compare/v0.1.0...v0.1.1 [0.1.0]: https://github.com/cryptoexamples/java-crypto-examples/releases/tag/v0.1.0 \ No newline at end of file From 4208df0922c6bc5fc972ff45d66f2a9494ec28f5 Mon Sep 17 00:00:00 2001 From: Kai Mindermann Date: Wed, 11 Jul 2018 14:43:01 +0200 Subject: [PATCH 18/33] increases salt size to 32 bytes to be equal in size for the used SHA-256 (for PBKDF2 ) --- .../java/ExampleStringEncryptionPasswordBasedInOneMethod.java | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/main/java/com/cryptoexamples/java/ExampleStringEncryptionPasswordBasedInOneMethod.java b/src/main/java/com/cryptoexamples/java/ExampleStringEncryptionPasswordBasedInOneMethod.java index 1bb70a3..f833162 100644 --- a/src/main/java/com/cryptoexamples/java/ExampleStringEncryptionPasswordBasedInOneMethod.java +++ b/src/main/java/com/cryptoexamples/java/ExampleStringEncryptionPasswordBasedInOneMethod.java @@ -44,7 +44,7 @@ public static void main(String[] args) { String password = Base64.getEncoder().encodeToString(keyGen.generateKey().getEncoded()); // GENERATE random salt (needed for PBKDF2) - final byte[] salt = new byte[12]; + final byte[] salt = new byte[32]; SecureRandom random = SecureRandom.getInstanceStrong(); random.nextBytes(salt); From 732178dd109d3d10ca72fcefd8166e57fb303d16 Mon Sep 17 00:00:00 2001 From: Kai Mindermann Date: Wed, 11 Jul 2018 15:08:01 +0200 Subject: [PATCH 19/33] updates code (pbkdf2 iterations to 10000, salt size to 32 bytes, exception only log name) --- CHANGELOG.md | 7 +++++++ .../java/ExampleAsymmetricStringEncryptionInOneMethod.java | 2 +- .../java/ExampleFileEncryptionInOneMethod.java | 6 +++--- .../com/cryptoexamples/java/ExampleHashInOneMethod.java | 2 +- .../cryptoexamples/java/ExampleSignatureInOneMethod.java | 2 +- .../java/ExampleStringEncryptionKeyBasedInOneMethod.java | 2 +- .../ExampleStringEncryptionPasswordBasedInOneMethod.java | 4 ++-- 7 files changed, 16 insertions(+), 9 deletions(-) diff --git a/CHANGELOG.md b/CHANGELOG.md index 658002c..1196159 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -7,6 +7,13 @@ and this project adheres to [Semantic Versioning](http://semver.org/spec/v2.0.0. ## [Unreleased] +### Changed +- Increased PBKDF2 salt size to 32 bytes (equal to SHA-256 size) +- Increased PBKDF2 iterations to 10000 + +### Fixed +- Exceptions were logged including the stack trace, now only the localized message is logged + ## [0.2.0] - 2018-05-13 ### Changed diff --git a/src/main/java/com/cryptoexamples/java/ExampleAsymmetricStringEncryptionInOneMethod.java b/src/main/java/com/cryptoexamples/java/ExampleAsymmetricStringEncryptionInOneMethod.java index 84e25c2..a5ec84e 100644 --- a/src/main/java/com/cryptoexamples/java/ExampleAsymmetricStringEncryptionInOneMethod.java +++ b/src/main/java/com/cryptoexamples/java/ExampleAsymmetricStringEncryptionInOneMethod.java @@ -49,7 +49,7 @@ public static void main(String[] args) { LOGGER.log(Level.INFO, () -> String.format("Decrypted and original plain text are the same: %b", decryptedCipherText.compareTo(plainText) == 0)); } catch (NoSuchAlgorithmException | NoSuchPaddingException | InvalidKeyException | IllegalBlockSizeException | BadPaddingException | InvalidParameterException e) { - LOGGER.log(Level.SEVERE, e.getMessage(), e); + LOGGER.log(Level.SEVERE, e.getLocalizedMessage()); } } } diff --git a/src/main/java/com/cryptoexamples/java/ExampleFileEncryptionInOneMethod.java b/src/main/java/com/cryptoexamples/java/ExampleFileEncryptionInOneMethod.java index 8c569cc..36ac08b 100644 --- a/src/main/java/com/cryptoexamples/java/ExampleFileEncryptionInOneMethod.java +++ b/src/main/java/com/cryptoexamples/java/ExampleFileEncryptionInOneMethod.java @@ -36,14 +36,14 @@ public static void main(String[] args) { String password = Base64.getEncoder().encodeToString(keyGen.generateKey().getEncoded()); // GENERATE random salt - final byte[] salt = new byte[12]; + final byte[] salt = new byte[32]; SecureRandom random = SecureRandom.getInstanceStrong(); random.nextBytes(salt); // DERIVE key (from password and salt) SecretKeyFactory factory = SecretKeyFactory.getInstance("PBKDF2WithHmacSHA256"); // Needs unlimited strength policy files http://www.oracle.com/technetwork/java/javase/downloads - KeySpec keyspec = new PBEKeySpec(password.toCharArray(), salt, 65536, 256); + KeySpec keyspec = new PBEKeySpec(password.toCharArray(), salt, 10000, 256); SecretKey tmp = factory.generateSecret(keyspec); SecretKey key = new SecretKeySpec(tmp.getEncoded(), "AES"); @@ -98,7 +98,7 @@ public static void main(String[] args) { InvalidAlgorithmParameterException | InvalidKeySpecException | IOException e) { - LOGGER.log(Level.SEVERE, e.getMessage(), e); + LOGGER.log(Level.SEVERE, e.getLocalizedMessage()); } } diff --git a/src/main/java/com/cryptoexamples/java/ExampleHashInOneMethod.java b/src/main/java/com/cryptoexamples/java/ExampleHashInOneMethod.java index 736a2c2..7bc9406 100644 --- a/src/main/java/com/cryptoexamples/java/ExampleHashInOneMethod.java +++ b/src/main/java/com/cryptoexamples/java/ExampleHashInOneMethod.java @@ -32,7 +32,7 @@ public static void main(String[] args) { LOGGER.log(Level.INFO, hashString); } catch (NoSuchAlgorithmException e) { - LOGGER.log(Level.SEVERE, e.getLocalizedMessage(), e); + LOGGER.log(Level.SEVERE, e.getLocalizedMessage()); } } } diff --git a/src/main/java/com/cryptoexamples/java/ExampleSignatureInOneMethod.java b/src/main/java/com/cryptoexamples/java/ExampleSignatureInOneMethod.java index e97fd47..12a5f51 100644 --- a/src/main/java/com/cryptoexamples/java/ExampleSignatureInOneMethod.java +++ b/src/main/java/com/cryptoexamples/java/ExampleSignatureInOneMethod.java @@ -47,7 +47,7 @@ public static void main(String[] args) { boolean isSignatureCorrect = signature.verify(Base64.getDecoder().decode(signatureForPlainTextString)); LOGGER.log(Level.INFO, () -> String.format("Signature is correct: %b", isSignatureCorrect)); } catch (NoSuchAlgorithmException | InvalidKeyException | SignatureException e) { - LOGGER.log(Level.SEVERE, e.getLocalizedMessage(), e); + LOGGER.log(Level.SEVERE, e.getLocalizedMessage()); } } } diff --git a/src/main/java/com/cryptoexamples/java/ExampleStringEncryptionKeyBasedInOneMethod.java b/src/main/java/com/cryptoexamples/java/ExampleStringEncryptionKeyBasedInOneMethod.java index 0f9ddf9..5128494 100644 --- a/src/main/java/com/cryptoexamples/java/ExampleStringEncryptionKeyBasedInOneMethod.java +++ b/src/main/java/com/cryptoexamples/java/ExampleStringEncryptionKeyBasedInOneMethod.java @@ -59,7 +59,7 @@ public static void main(String[] args) { LOGGER.log(Level.INFO, () -> String.format("Decrypted and original plain text are the same: %b", decryptedCipherText.compareTo(plainText) == 0)); } catch (NoSuchAlgorithmException | NoSuchPaddingException | InvalidKeyException | IllegalBlockSizeException | BadPaddingException | InvalidParameterException | InvalidAlgorithmParameterException e) { - LOGGER.log(Level.SEVERE, e.getMessage(), e); + LOGGER.log(Level.SEVERE, e.getLocalizedMessage()); } } } diff --git a/src/main/java/com/cryptoexamples/java/ExampleStringEncryptionPasswordBasedInOneMethod.java b/src/main/java/com/cryptoexamples/java/ExampleStringEncryptionPasswordBasedInOneMethod.java index f833162..439fafb 100644 --- a/src/main/java/com/cryptoexamples/java/ExampleStringEncryptionPasswordBasedInOneMethod.java +++ b/src/main/java/com/cryptoexamples/java/ExampleStringEncryptionPasswordBasedInOneMethod.java @@ -50,7 +50,7 @@ public static void main(String[] args) { // DERIVE key (from password and salt) SecretKeyFactory factory = SecretKeyFactory.getInstance("PBKDF2WithHmacSHA256"); - KeySpec keyspec = new PBEKeySpec(password.toCharArray(), salt, 65536, 256); + KeySpec keyspec = new PBEKeySpec(password.toCharArray(), salt, 10000, 256); SecretKey tmp = factory.generateSecret(keyspec); SecretKey key = new SecretKeySpec(tmp.getEncoded(), "AES"); @@ -74,7 +74,7 @@ public static void main(String[] args) { LOGGER.log(Level.INFO, () -> String.format("Decrypted and original plain text are the same: %b", decryptedCipherText.compareTo(plainText) == 0)); } catch (NoSuchAlgorithmException | NoSuchPaddingException | InvalidKeyException | IllegalBlockSizeException | BadPaddingException | InvalidParameterException | InvalidAlgorithmParameterException | InvalidKeySpecException e) { - LOGGER.log(Level.SEVERE, e.getMessage(), e); + LOGGER.log(Level.SEVERE, e.getLocalizedMessage()); } } From 8f6c193b9ee05c4d5a90b6cb8070196289317bbf Mon Sep 17 00:00:00 2001 From: Kai Mindermann Date: Wed, 11 Jul 2018 15:14:42 +0200 Subject: [PATCH 20/33] changes pbkdf2 hash function to SHA-512 --- CHANGELOG.md | 3 ++- .../cryptoexamples/java/ExampleFileEncryptionInOneMethod.java | 4 ++-- .../java/ExampleStringEncryptionPasswordBasedInOneMethod.java | 4 ++-- 3 files changed, 6 insertions(+), 5 deletions(-) diff --git a/CHANGELOG.md b/CHANGELOG.md index 1196159..08db93e 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -8,7 +8,8 @@ and this project adheres to [Semantic Versioning](http://semver.org/spec/v2.0.0. ## [Unreleased] ### Changed -- Increased PBKDF2 salt size to 32 bytes (equal to SHA-256 size) +- Changed PBKDF2 hash function to SHA-512 +- Increased PBKDF2 salt size to 64 bytes (equal to SHA-512 size) - Increased PBKDF2 iterations to 10000 ### Fixed diff --git a/src/main/java/com/cryptoexamples/java/ExampleFileEncryptionInOneMethod.java b/src/main/java/com/cryptoexamples/java/ExampleFileEncryptionInOneMethod.java index 36ac08b..8d78072 100644 --- a/src/main/java/com/cryptoexamples/java/ExampleFileEncryptionInOneMethod.java +++ b/src/main/java/com/cryptoexamples/java/ExampleFileEncryptionInOneMethod.java @@ -36,12 +36,12 @@ public static void main(String[] args) { String password = Base64.getEncoder().encodeToString(keyGen.generateKey().getEncoded()); // GENERATE random salt - final byte[] salt = new byte[32]; + final byte[] salt = new byte[64]; SecureRandom random = SecureRandom.getInstanceStrong(); random.nextBytes(salt); // DERIVE key (from password and salt) - SecretKeyFactory factory = SecretKeyFactory.getInstance("PBKDF2WithHmacSHA256"); + SecretKeyFactory factory = SecretKeyFactory.getInstance("PBKDF2WithHmacSHA512"); // Needs unlimited strength policy files http://www.oracle.com/technetwork/java/javase/downloads KeySpec keyspec = new PBEKeySpec(password.toCharArray(), salt, 10000, 256); SecretKey tmp = factory.generateSecret(keyspec); diff --git a/src/main/java/com/cryptoexamples/java/ExampleStringEncryptionPasswordBasedInOneMethod.java b/src/main/java/com/cryptoexamples/java/ExampleStringEncryptionPasswordBasedInOneMethod.java index 439fafb..895b4be 100644 --- a/src/main/java/com/cryptoexamples/java/ExampleStringEncryptionPasswordBasedInOneMethod.java +++ b/src/main/java/com/cryptoexamples/java/ExampleStringEncryptionPasswordBasedInOneMethod.java @@ -44,12 +44,12 @@ public static void main(String[] args) { String password = Base64.getEncoder().encodeToString(keyGen.generateKey().getEncoded()); // GENERATE random salt (needed for PBKDF2) - final byte[] salt = new byte[32]; + final byte[] salt = new byte[64]; SecureRandom random = SecureRandom.getInstanceStrong(); random.nextBytes(salt); // DERIVE key (from password and salt) - SecretKeyFactory factory = SecretKeyFactory.getInstance("PBKDF2WithHmacSHA256"); + SecretKeyFactory factory = SecretKeyFactory.getInstance("PBKDF2WithHmacSHA512"); KeySpec keyspec = new PBEKeySpec(password.toCharArray(), salt, 10000, 256); SecretKey tmp = factory.generateSecret(keyspec); SecretKey key = new SecretKeySpec(tmp.getEncoded(), "AES"); From 2c2e9d741599e48841f906058deeedac652ded91 Mon Sep 17 00:00:00 2001 From: Kai Mindermann Date: Wed, 11 Jul 2018 16:02:03 +0200 Subject: [PATCH 21/33] refactors variable names and fixes comments and makes password generation conditional --- CHANGELOG.md | 1 + .../ExampleFileEncryptionInOneMethod.java | 23 ++++++++++--------- ...ingEncryptionPasswordBasedInOneMethod.java | 19 ++++++++------- 3 files changed, 24 insertions(+), 19 deletions(-) diff --git a/CHANGELOG.md b/CHANGELOG.md index 08db93e..0c7b329 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -11,6 +11,7 @@ and this project adheres to [Semantic Versioning](http://semver.org/spec/v2.0.0. - Changed PBKDF2 hash function to SHA-512 - Increased PBKDF2 salt size to 64 bytes (equal to SHA-512 size) - Increased PBKDF2 iterations to 10000 +- Refactored variable names ### Fixed - Exceptions were logged including the stack trace, now only the localized message is logged diff --git a/src/main/java/com/cryptoexamples/java/ExampleFileEncryptionInOneMethod.java b/src/main/java/com/cryptoexamples/java/ExampleFileEncryptionInOneMethod.java index 8d78072..1273721 100644 --- a/src/main/java/com/cryptoexamples/java/ExampleFileEncryptionInOneMethod.java +++ b/src/main/java/com/cryptoexamples/java/ExampleFileEncryptionInOneMethod.java @@ -18,7 +18,7 @@ * Including * - Random password generation using strong secure random number generator * - Random salt generation - * - Key derivation using PBKDF2 HMAC SHA-256, + * - Key derivation using PBKDF2 HMAC SHA-512, * - AES-256 authenticated encryption using GCM * - BASE64-encoding as representation for the byte-arrays * - Exception handling @@ -29,11 +29,13 @@ public class ExampleFileEncryptionInOneMethod { public static void main(String[] args) { String plainText = "Multiline text:"; try { - // GENERATE password - KeyGenerator keyGen = KeyGenerator.getInstance("AES"); - // Needs unlimited strength policy files http://www.oracle.com/technetwork/java/javase/downloads - keyGen.init(256); - String password = Base64.getEncoder().encodeToString(keyGen.generateKey().getEncoded()); + String password = null; + // GENERATE password (not needed if you have a password already) + if(password == null || password.isEmpty()) { + KeyGenerator keyGen = KeyGenerator.getInstance("AES"); + keyGen.init(256); + password = Base64.getEncoder().encodeToString(keyGen.generateKey().getEncoded()); + } // GENERATE random salt final byte[] salt = new byte[64]; @@ -41,11 +43,10 @@ public static void main(String[] args) { random.nextBytes(salt); // DERIVE key (from password and salt) - SecretKeyFactory factory = SecretKeyFactory.getInstance("PBKDF2WithHmacSHA512"); - // Needs unlimited strength policy files http://www.oracle.com/technetwork/java/javase/downloads - KeySpec keyspec = new PBEKeySpec(password.toCharArray(), salt, 10000, 256); - SecretKey tmp = factory.generateSecret(keyspec); - SecretKey key = new SecretKeySpec(tmp.getEncoded(), "AES"); + SecretKeyFactory secretKeyFactory = SecretKeyFactory.getInstance("PBKDF2WithHmacSHA512"); + KeySpec passwordBasedEncryptionKeySpec = new PBEKeySpec(password.toCharArray(), salt, 10000, 256); + SecretKey secretKeyFromPBKDF2 = secretKeyFactory.generateSecret(passwordBasedEncryptionKeySpec); + SecretKey key = new SecretKeySpec(secretKeyFromPBKDF2.getEncoded(), "AES"); // GENERATE random nonce (number used once) final byte[] nonce = new byte[32]; diff --git a/src/main/java/com/cryptoexamples/java/ExampleStringEncryptionPasswordBasedInOneMethod.java b/src/main/java/com/cryptoexamples/java/ExampleStringEncryptionPasswordBasedInOneMethod.java index 895b4be..3b203db 100644 --- a/src/main/java/com/cryptoexamples/java/ExampleStringEncryptionPasswordBasedInOneMethod.java +++ b/src/main/java/com/cryptoexamples/java/ExampleStringEncryptionPasswordBasedInOneMethod.java @@ -26,7 +26,7 @@ * All in one example for encryption and decryption of a string in one method. * - Random password generation using strong secure random number generator * - Random salt generation - * - Key derivation using PBKDF2 HMAC SHA-256, + * - Key derivation using PBKDF2 HMAC SHA-512, * - AES-256 authenticated encryption using GCM * - BASE64 encoding as representation for the byte-arrays * - UTF-8 encoding of Strings @@ -38,10 +38,13 @@ public class ExampleStringEncryptionPasswordBasedInOneMethod { public static void main(String[] args) { String plainText = "Text that is going to be sent over an insecure channel and must be encrypted at all costs!"; try { + String password = null; // GENERATE password (not needed if you have a password already) - KeyGenerator keyGen = KeyGenerator.getInstance("AES"); - keyGen.init(256); - String password = Base64.getEncoder().encodeToString(keyGen.generateKey().getEncoded()); + if(password == null || password.isEmpty()) { + KeyGenerator keyGen = KeyGenerator.getInstance("AES"); + keyGen.init(256); + password = Base64.getEncoder().encodeToString(keyGen.generateKey().getEncoded()); + } // GENERATE random salt (needed for PBKDF2) final byte[] salt = new byte[64]; @@ -49,10 +52,10 @@ public static void main(String[] args) { random.nextBytes(salt); // DERIVE key (from password and salt) - SecretKeyFactory factory = SecretKeyFactory.getInstance("PBKDF2WithHmacSHA512"); - KeySpec keyspec = new PBEKeySpec(password.toCharArray(), salt, 10000, 256); - SecretKey tmp = factory.generateSecret(keyspec); - SecretKey key = new SecretKeySpec(tmp.getEncoded(), "AES"); + SecretKeyFactory secretKeyFactory = SecretKeyFactory.getInstance("PBKDF2WithHmacSHA512"); + KeySpec passwordBasedEncryptionKeySpec = new PBEKeySpec(password.toCharArray(), salt, 10000, 256); + SecretKey secretKeyFromPBKDF2 = secretKeyFactory.generateSecret(passwordBasedEncryptionKeySpec); + SecretKey key = new SecretKeySpec(secretKeyFromPBKDF2.getEncoded(), "AES"); // GENERATE random nonce (number used once) final byte[] nonce = new byte[32]; From 37ceacc602b775e695932f1f8a77c74708007701 Mon Sep 17 00:00:00 2001 From: Kai Mindermann Date: Wed, 11 Jul 2018 16:10:59 +0200 Subject: [PATCH 22/33] Refactors main method to call a demonstrate...-method --- ...StringEncryptionPasswordBasedInOneMethod.java | 16 +++++++++++++--- .../java/EncryptionInOneMethodTests.java | 7 ++++++- 2 files changed, 19 insertions(+), 4 deletions(-) diff --git a/src/main/java/com/cryptoexamples/java/ExampleStringEncryptionPasswordBasedInOneMethod.java b/src/main/java/com/cryptoexamples/java/ExampleStringEncryptionPasswordBasedInOneMethod.java index 3b203db..65e13b5 100644 --- a/src/main/java/com/cryptoexamples/java/ExampleStringEncryptionPasswordBasedInOneMethod.java +++ b/src/main/java/com/cryptoexamples/java/ExampleStringEncryptionPasswordBasedInOneMethod.java @@ -35,10 +35,14 @@ public class ExampleStringEncryptionPasswordBasedInOneMethod { private static final Logger LOGGER = Logger.getLogger(ExampleStringEncryptionPasswordBasedInOneMethod.class.getName()); - public static void main(String[] args) { - String plainText = "Text that is going to be sent over an insecure channel and must be encrypted at all costs!"; + /** + * Demonstrational method that encrypts the plainText using a password (that is used to derive the required key). + * @param plainText + * @param password + * @return true if encryption and decryption is working, false otherwise + */ + public static boolean demonstratePasswordBasedSymmetricEncryption(String plainText, String password) { try { - String password = null; // GENERATE password (not needed if you have a password already) if(password == null || password.isEmpty()) { KeyGenerator keyGen = KeyGenerator.getInstance("AES"); @@ -76,9 +80,15 @@ public static void main(String[] args) { String decryptedCipherText = new String(decryptedCipherTextBytes, StandardCharsets.UTF_8); LOGGER.log(Level.INFO, () -> String.format("Decrypted and original plain text are the same: %b", decryptedCipherText.compareTo(plainText) == 0)); + return decryptedCipherText.compareTo(plainText) == 0; } catch (NoSuchAlgorithmException | NoSuchPaddingException | InvalidKeyException | IllegalBlockSizeException | BadPaddingException | InvalidParameterException | InvalidAlgorithmParameterException | InvalidKeySpecException e) { LOGGER.log(Level.SEVERE, e.getLocalizedMessage()); + return false; } } + public static void main(String[] args) { + demonstratePasswordBasedSymmetricEncryption("Text that is going to be sent over an insecure channel and must be encrypted at all costs!",null); + } + } diff --git a/src/test/java/com/cryptoexamples/java/EncryptionInOneMethodTests.java b/src/test/java/com/cryptoexamples/java/EncryptionInOneMethodTests.java index 14ffd92..6f72e33 100644 --- a/src/test/java/com/cryptoexamples/java/EncryptionInOneMethodTests.java +++ b/src/test/java/com/cryptoexamples/java/EncryptionInOneMethodTests.java @@ -3,10 +3,12 @@ import org.junit.*; import java.io.ByteArrayOutputStream; +import java.io.IOException; import java.io.PrintStream; import static org.hamcrest.CoreMatchers.containsString; import static org.junit.Assert.assertThat; +import static org.junit.Assert.assertTrue; /** @@ -35,9 +37,12 @@ public void resetOut() { } @Test - public void testStringEncryptionPasswordBasedMain() { + public void testStringEncryptionPasswordBasedMain() throws IOException { ExampleStringEncryptionPasswordBasedInOneMethod.main(new String[1]); assertThat(errContent.toString(), containsString("Decrypted and original plain text are the same: true")); + errContent.flush(); + assertTrue(ExampleStringEncryptionPasswordBasedInOneMethod.demonstratePasswordBasedSymmetricEncryption("plaintext",null)); + assertThat(errContent.toString(), containsString("Decrypted and original plain text are the same: true")); } @Test From df0b39146eb48ddacc007818056712e0f5dfd693 Mon Sep 17 00:00:00 2001 From: Kai Mindermann Date: Wed, 18 Jul 2018 16:50:58 +0200 Subject: [PATCH 23/33] releases 0.3.0 --- CHANGELOG.md | 8 +++++++- 1 file changed, 7 insertions(+), 1 deletion(-) diff --git a/CHANGELOG.md b/CHANGELOG.md index 0c7b329..2218517 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -7,13 +7,18 @@ and this project adheres to [Semantic Versioning](http://semver.org/spec/v2.0.0. ## [Unreleased] +## [0.3.0] - 2018-07-18 + ### Changed + - Changed PBKDF2 hash function to SHA-512 - Increased PBKDF2 salt size to 64 bytes (equal to SHA-512 size) - Increased PBKDF2 iterations to 10000 - Refactored variable names +- Refactored main methods to call a demonstrate...-method ### Fixed + - Exceptions were logged including the stack trace, now only the localized message is logged ## [0.2.0] - 2018-05-13 @@ -75,7 +80,8 @@ and this project adheres to [Semantic Versioning](http://semver.org/spec/v2.0.0. - made some security relevant changes - made other security relevant changes -[Unreleased]: https://github.com/cryptoexamples/java-crypto-examples/compare/v0.2.0...HEAD +[Unreleased]: https://github.com/cryptoexamples/java-crypto-examples/compare/v0.3.0...HEAD +[0.3.0]: https://github.com/cryptoexamples/java-crypto-examples/compare/v0.2.0...v0.3.0 [0.2.0]: https://github.com/cryptoexamples/java-crypto-examples/compare/v0.1.1...v0.2.0 [0.1.1]: https://github.com/cryptoexamples/java-crypto-examples/compare/v0.1.0...v0.1.1 [0.1.0]: https://github.com/cryptoexamples/java-crypto-examples/releases/tag/v0.1.0 \ No newline at end of file From 9c57b64470ef140f704efa7a4d876ebd3c104cc5 Mon Sep 17 00:00:00 2001 From: Kai Mindermann Date: Thu, 2 Aug 2018 12:27:27 +0200 Subject: [PATCH 24/33] updates examples according to guidlines (refs #7) --- CHANGELOG.md | 13 ++++ ...ile_encryption_symmetric_password_based.md | 32 ++++++++-- java_string_encryption_asymmetric.md | 12 ++-- java_string_encryption_key_based_symmetric.md | 8 ++- ...ing_encryption_password_based_symmetric.md | 9 ++- java_string_hash.md | 8 ++- java_string_sign.md | 8 ++- ...=> ExampleAsymmetricStringEncryption.java} | 12 ++-- ...Method.java => ExampleFileEncryption.java} | 59 +++++++++++++------ ...eHashInOneMethod.java => ExampleHash.java} | 20 +++++-- ...InOneMethod.java => ExampleSignature.java} | 21 +++++-- ...a => ExampleStringEncryptionKeyBased.java} | 23 +++++--- ...ExampleStringEncryptionPasswordBased.java} | 8 +-- .../java/EncryptionInOneMethodTests.java | 38 ++++++++---- 14 files changed, 195 insertions(+), 76 deletions(-) rename src/main/java/com/cryptoexamples/java/{ExampleAsymmetricStringEncryptionInOneMethod.java => ExampleAsymmetricStringEncryption.java} (88%) rename src/main/java/com/cryptoexamples/java/{ExampleFileEncryptionInOneMethod.java => ExampleFileEncryption.java} (66%) rename src/main/java/com/cryptoexamples/java/{ExampleHashInOneMethod.java => ExampleHash.java} (69%) rename src/main/java/com/cryptoexamples/java/{ExampleSignatureInOneMethod.java => ExampleSignature.java} (78%) rename src/main/java/com/cryptoexamples/java/{ExampleStringEncryptionKeyBasedInOneMethod.java => ExampleStringEncryptionKeyBased.java} (76%) rename src/main/java/com/cryptoexamples/java/{ExampleStringEncryptionPasswordBasedInOneMethod.java => ExampleStringEncryptionPasswordBased.java} (93%) diff --git a/CHANGELOG.md b/CHANGELOG.md index 2218517..e31ec22 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -7,6 +7,19 @@ and this project adheres to [Semantic Versioning](http://semver.org/spec/v2.0.0. ## [Unreleased] +### Changed + +- Changed class names to conform with guidelines +- Added demonstrate-methods for all examples +- Corrected meta format for file encryption example + +### Fixed + +- Added missing UTF-8 encoding in assymetric encryption example +- Fixed file encryption not needing trim anymore +- Fixed Headings according to guidlines +- Fixed import statements not expclicit in file encryption example + ## [0.3.0] - 2018-07-18 ### Changed diff --git a/java_file_encryption_symmetric_password_based.md b/java_file_encryption_symmetric_password_based.md index 583d949..c6f3140 100644 --- a/java_file_encryption_symmetric_password_based.md +++ b/java_file_encryption_symmetric_password_based.md @@ -1,18 +1,42 @@ --- -title: Password based symmetric file encryption in Java using JDK +title: Java Password based symmetric file encryption using JDK keywords: sample summary: "Password based symmetric file encryption in Java" permalink: java_file_encryption_symmetric_password_based.html folder: Java JDK +references: [ + # Place a list of references used to create and/or understand this example. + { + url: "https://docs.oracle.com/javase/10/docs/api/javax/crypto/Cipher.html", + description: "Java JDK Ciper" + } +] +authors: [ + { + name: "Kai Mindermann", + url: "https://github.com/kmindi" + } +] +# List all reviewers that reviewed this version of the example. When the example is updated all old reviews +# must be removed from the list below and the code has to be reviewed again. The complete review process +# is documented in the main repository of CryptoExamples +current_reviews: [ + +] +# Indicates when this example was last updated/created. Reviews don't change this. +last_updated: "2018-08-02" tags: [Java, AES, GCM, PBKDF2, Salt, AEAD] --- ## Use cases -- password based encryption of a file -- previously shared common secret (password) +- Password based symmetric encryption of a file + +## Java version + +- JDK 11 -## Sample Code for Java based symmetric file encryption using AES-GCM and PBKDF2 +## Example Code for Java Password based symmetric file encryption using AES-GCM and PBKDF2 ```java {% include_relative src/main/java/com/cryptoexamples/java/ExampleFileEncryptionInOneMethod.java %} diff --git a/java_string_encryption_asymmetric.md b/java_string_encryption_asymmetric.md index 5b29676..eba52d4 100644 --- a/java_string_encryption_asymmetric.md +++ b/java_string_encryption_asymmetric.md @@ -1,5 +1,5 @@ --- -title: Asymmetric String Encryption using Java JDK +title: Java Asymmetric String Encryption using JDK keywords: sample summary: "Asymmetric String Encryption in Java" permalink: java_asymmetric_string_encryption.html @@ -24,15 +24,19 @@ current_reviews: [ ] # Indicates when this example was last updated/created. Reviews don't change this. -last_updated: "2018-05-13" +last_updated: "2018-08-02" tags: [Java, RSA, Asymmetric, String, Encryption] --- ## Use cases -- +- Asymmetric encryption -## Sample Code for Java based asymmetric encryption +## Java version + +- JDK 11 + +## Example Code for Java Asymmetric String Encryption using RSA 4096 ```java {% include_relative src/main/java/com/cryptoexamples/java/ExampleAsymmetricStringEncryptionInOneMethod.java %} diff --git a/java_string_encryption_key_based_symmetric.md b/java_string_encryption_key_based_symmetric.md index c866aff..cb0e308 100644 --- a/java_string_encryption_key_based_symmetric.md +++ b/java_string_encryption_key_based_symmetric.md @@ -24,7 +24,7 @@ current_reviews: [ ] # Indicates when this example was last updated/created. Reviews don't change this. -last_updated: "2018-05-13" +last_updated: "2018-08-02" tags: [Java, AES, GCM, Salt, AEAD] --- @@ -33,7 +33,11 @@ tags: [Java, AES, GCM, Salt, AEAD] - Random key generation - String encryption -## Sample Code for Java based symmetric encryption using AES-GCM and generation of keys +## Java version + +- JDK 11 + +## Example Code for Java String Encryption with key generation using AES-GCM ```java {% include_relative src/main/java/com/cryptoexamples/java/ExampleStringEncryptionKeyBasedInOneMethod.java %} diff --git a/java_string_encryption_password_based_symmetric.md b/java_string_encryption_password_based_symmetric.md index debfdc3..1de745c 100644 --- a/java_string_encryption_password_based_symmetric.md +++ b/java_string_encryption_password_based_symmetric.md @@ -24,7 +24,7 @@ current_reviews: [ ] # Indicates when this example was last updated/created. Reviews don't change this. -last_updated: "2018-05-13" +last_updated: "2018-08-02" tags: [Java, AES, GCM, PBKDF2, Salt, AEAD] --- @@ -32,9 +32,12 @@ tags: [Java, AES, GCM, PBKDF2, Salt, AEAD] - Password based encryption - Previously shared common secret (password) -- -## Sample Code for Java based symmetric encryption using AES-GCM and PBKDF2 +## Java version + +- JDK 11 + +## Example Code for Java Password Based String Encryption using AES-GCM and PBKDF2 ```java {% include_relative src/main/java/com/cryptoexamples/java/ExampleStringEncryptionPasswordBasedInOneMethod.java %} diff --git a/java_string_hash.md b/java_string_hash.md index e97bc40..943e016 100644 --- a/java_string_hash.md +++ b/java_string_hash.md @@ -24,7 +24,7 @@ current_reviews: [ ] # Indicates when this example was last updated/created. Reviews don't change this. -last_updated: "2018-05-13" +last_updated: "2018-08-02" tags: [Java, hash, SHA, SHA-512] --- @@ -32,7 +32,11 @@ tags: [Java, hash, SHA, SHA-512] - Verifying if a string has been changed -## Sample Code for Java based hashing of a String using SHA-512, BASE64 and UTF-8 encoding +## Java version + +- JDK 11 + +## Example Code for Java String Hashing using SHA-512, BASE64 and UTF-8 encoding ```java {% include_relative src/main/java/com/cryptoexamples/java/ExampleHashInOneMethod.java %} diff --git a/java_string_sign.md b/java_string_sign.md index 5f34073..7dc87b6 100644 --- a/java_string_sign.md +++ b/java_string_sign.md @@ -24,7 +24,7 @@ current_reviews: [ ] # Indicates when this example was last updated/created. Reviews don't change this. -last_updated: "2018-05-13" +last_updated: "2018-08-02" tags: [Java, hash, SHA, SHA-512] --- @@ -32,7 +32,11 @@ tags: [Java, hash, SHA, SHA-512] - verifying if a string has been changed -## Sample Code for Java based signing of a String using SHA-512, RSA 4096, BASE64 and UTF-8 encoding +## Java version + +- JDK 11 + +## Example Code for Java String Signing using SHA-512, RSA 4096, BASE64 and UTF-8 encoding ```java {% include_relative src/main/java/com/cryptoexamples/java/ExampleSignatureInOneMethod.java %} diff --git a/src/main/java/com/cryptoexamples/java/ExampleAsymmetricStringEncryptionInOneMethod.java b/src/main/java/com/cryptoexamples/java/ExampleAsymmetricStringEncryption.java similarity index 88% rename from src/main/java/com/cryptoexamples/java/ExampleAsymmetricStringEncryptionInOneMethod.java rename to src/main/java/com/cryptoexamples/java/ExampleAsymmetricStringEncryption.java index a5ec84e..b5c84c3 100644 --- a/src/main/java/com/cryptoexamples/java/ExampleAsymmetricStringEncryptionInOneMethod.java +++ b/src/main/java/com/cryptoexamples/java/ExampleAsymmetricStringEncryption.java @@ -4,6 +4,7 @@ import javax.crypto.Cipher; import javax.crypto.IllegalBlockSizeException; import javax.crypto.NoSuchPaddingException; +import java.nio.charset.StandardCharsets; import java.security.InvalidKeyException; import java.security.InvalidParameterException; import java.security.KeyPair; @@ -14,15 +15,14 @@ import java.util.logging.Logger; /** - * All in one example for asymmetric encryption and decryption of a string in one method. + * Example for asymmetric encryption and decryption of a string in one method. * - Generation of public and private RSA 4096 bit keypair - * - AES-256 authenticated encryption using GCM * - BASE64 encoding as representation for the byte-arrays * - UTF-8 encoding of Strings * - Exception handling */ -public class ExampleAsymmetricStringEncryptionInOneMethod { - private static final Logger LOGGER = Logger.getLogger(ExampleAsymmetricStringEncryptionInOneMethod.class.getName()); +public class ExampleAsymmetricStringEncryption { + private static final Logger LOGGER = Logger.getLogger(ExampleAsymmetricStringEncryption.class.getName()); public static void main(String[] args) { String plainText = "Text that is going to be sent over an insecure channel and must be encrypted at all costs!"; @@ -37,7 +37,7 @@ public static void main(String[] args) { Cipher cipher = Cipher.getInstance("RSA/ECB/OAEPWithSHA-256AndMGF1Padding"); cipher.init(Cipher.ENCRYPT_MODE, keyPair.getPublic()); - byte[] cipherTextBytes = cipher.doFinal(plainText.getBytes()); + byte[] cipherTextBytes = cipher.doFinal(plainText.getBytes(StandardCharsets.UTF_8)); // CONVERSION of raw bytes to BASE64 representation String cipherText = Base64.getEncoder().encodeToString(cipherTextBytes); @@ -45,7 +45,7 @@ public static void main(String[] args) { // DECRYPTION cipher.init(Cipher.DECRYPT_MODE, keyPair.getPrivate()); byte[] decryptedCipherTextBytes = cipher.doFinal(Base64.getDecoder().decode(cipherText)); - String decryptedCipherText = new String(decryptedCipherTextBytes); + String decryptedCipherText = new String(decryptedCipherTextBytes,StandardCharsets.UTF_8); LOGGER.log(Level.INFO, () -> String.format("Decrypted and original plain text are the same: %b", decryptedCipherText.compareTo(plainText) == 0)); } catch (NoSuchAlgorithmException | NoSuchPaddingException | InvalidKeyException | IllegalBlockSizeException | BadPaddingException | InvalidParameterException e) { diff --git a/src/main/java/com/cryptoexamples/java/ExampleFileEncryptionInOneMethod.java b/src/main/java/com/cryptoexamples/java/ExampleFileEncryption.java similarity index 66% rename from src/main/java/com/cryptoexamples/java/ExampleFileEncryptionInOneMethod.java rename to src/main/java/com/cryptoexamples/java/ExampleFileEncryption.java index 1273721..d1404db 100644 --- a/src/main/java/com/cryptoexamples/java/ExampleFileEncryptionInOneMethod.java +++ b/src/main/java/com/cryptoexamples/java/ExampleFileEncryption.java @@ -1,6 +1,12 @@ package com.cryptoexamples.java; -import javax.crypto.*; +import javax.crypto.Cipher; +import javax.crypto.CipherInputStream; +import javax.crypto.CipherOutputStream; +import javax.crypto.KeyGenerator; +import javax.crypto.NoSuchPaddingException; +import javax.crypto.SecretKey; +import javax.crypto.SecretKeyFactory; import javax.crypto.spec.GCMParameterSpec; import javax.crypto.spec.PBEKeySpec; import javax.crypto.spec.SecretKeySpec; @@ -14,8 +20,7 @@ import java.util.logging.Logger; /** - * All in one example for encryption and decryption of a file in one method; - * Including + * Example for encryption and decryption of a file in one method. * - Random password generation using strong secure random number generator * - Random salt generation * - Key derivation using PBKDF2 HMAC SHA-512, @@ -23,13 +28,18 @@ * - BASE64-encoding as representation for the byte-arrays * - Exception handling */ -public class ExampleFileEncryptionInOneMethod { - private static final Logger LOGGER = Logger.getLogger(ExampleFileEncryptionInOneMethod.class.getName()); +public class ExampleFileEncryption { + private static final Logger LOGGER = Logger.getLogger(ExampleFileEncryption.class.getName()); - public static void main(String[] args) { - String plainText = "Multiline text:"; + /** + * Demonstrational method that encrypts a file using a password (that is used to derive the required key). + * @param fileName + * @param plainText + * @param password + * @return true if encryption and decryption were successful, false otherwise + */ + public static boolean demonstrateFileEncryption(String fileName, String plainText, String password) { try { - String password = null; // GENERATE password (not needed if you have a password already) if(password == null || password.isEmpty()) { KeyGenerator keyGen = KeyGenerator.getInstance("AES"); @@ -61,37 +71,42 @@ public static void main(String[] args) { // SET UP OUTPUT STREAM and write content of String try ( - FileOutputStream fileOutputStream = new FileOutputStream("encryptedFile.enc"); + FileOutputStream fileOutputStream = new FileOutputStream(fileName); CipherOutputStream encryptedOutputStream = new CipherOutputStream(fileOutputStream, cipher); InputStream stringInputStream = new ByteArrayInputStream(plainText.getBytes(StandardCharsets.UTF_8)) ) { byte[] buffer = new byte[8192]; - while (stringInputStream.read(buffer) > 0) { - encryptedOutputStream.write(buffer); + int nread; + while ((nread = stringInputStream.read(buffer)) > 0) { + encryptedOutputStream.write(buffer, 0, nread); } + encryptedOutputStream.flush(); } // READ ENCRYPTED FILE StringBuilder stringBuilder = new StringBuilder(); cipher.init(Cipher.DECRYPT_MODE, key, spec); - + String decryptedCipherText; try ( - FileInputStream fileInputStream = new FileInputStream("encryptedFile.enc"); - CipherInputStream cipherInputStream = new CipherInputStream(fileInputStream, cipher) + FileInputStream fileInputStream = new FileInputStream(fileName); + CipherInputStream cipherInputStream = new CipherInputStream(fileInputStream, cipher); + ByteArrayOutputStream byteArrayOutputStream = new ByteArrayOutputStream(); ) { byte[] buffer = new byte[8192]; - while (cipherInputStream.read(buffer) > 0) { - stringBuilder.append(new String(buffer, StandardCharsets.UTF_8)); + int nread; + while ((nread = cipherInputStream.read(buffer)) > 0) { + byteArrayOutputStream.write(buffer, 0, nread); } + byteArrayOutputStream.flush(); + decryptedCipherText = new String(byteArrayOutputStream.toByteArray(), StandardCharsets.UTF_8); } - // TODO trim() should not be needed! - String decryptedCipherText = stringBuilder.toString().trim(); - LOGGER.log(Level.INFO, decryptedCipherText); + LOGGER.log(Level.INFO, decryptedCipherText); LOGGER.log(Level.INFO, () -> String.format("Decrypted file content and original plain text are the same: %b", decryptedCipherText.compareTo(plainText) == 0) ); + return decryptedCipherText.compareTo(plainText) == 0; } catch (NoSuchAlgorithmException | NoSuchPaddingException | InvalidKeyException | @@ -100,7 +115,13 @@ public static void main(String[] args) { InvalidKeySpecException | IOException e) { LOGGER.log(Level.SEVERE, e.getLocalizedMessage()); + return false; } } + + public static void main(String[] args) { + demonstrateFileEncryption("encryptedFile.enc","Multiline text:\nMultiline text:\n",null ); + } + } diff --git a/src/main/java/com/cryptoexamples/java/ExampleHashInOneMethod.java b/src/main/java/com/cryptoexamples/java/ExampleHash.java similarity index 69% rename from src/main/java/com/cryptoexamples/java/ExampleHashInOneMethod.java rename to src/main/java/com/cryptoexamples/java/ExampleHash.java index 7bc9406..5a20e0a 100644 --- a/src/main/java/com/cryptoexamples/java/ExampleHashInOneMethod.java +++ b/src/main/java/com/cryptoexamples/java/ExampleHash.java @@ -9,17 +9,21 @@ import java.util.logging.Logger; /** - * All in one example for hashing of a string in one method. + * Example for hashing of a string in one method. * - SHA-512 * - BASE64 encoding as representation for the byte-arrays * - UTF-8 encoding of String * - Exception handling */ -public class ExampleHashInOneMethod { - private static final Logger LOGGER = Logger.getLogger(ExampleHashInOneMethod.class.getName()); +public class ExampleHash { + private static final Logger LOGGER = Logger.getLogger(ExampleHash.class.getName()); - public static void main(String[] args) { - String plainText = "Text that should be authenticated by comparing the hash of it!"; + /** + * Demonstrational method that hashes the plainText. + * @param plainText + * @return true if hashing was successful, false otherwise + */ + public static boolean demonstrateHash(String plainText) { try { // Get MessageDigest Instance MessageDigest messageDigest = MessageDigest.getInstance("SHA-512"); @@ -31,8 +35,14 @@ public static void main(String[] args) { String hashString = Base64.getEncoder().encodeToString(hashBytes); LOGGER.log(Level.INFO, hashString); + return true; } catch (NoSuchAlgorithmException e) { LOGGER.log(Level.SEVERE, e.getLocalizedMessage()); + return false; } } + + public static void main(String[] args) { + demonstrateHash("Text that should be authenticated by comparing the hash of it!"); + } } diff --git a/src/main/java/com/cryptoexamples/java/ExampleSignatureInOneMethod.java b/src/main/java/com/cryptoexamples/java/ExampleSignature.java similarity index 78% rename from src/main/java/com/cryptoexamples/java/ExampleSignatureInOneMethod.java rename to src/main/java/com/cryptoexamples/java/ExampleSignature.java index 12a5f51..1ad54f0 100644 --- a/src/main/java/com/cryptoexamples/java/ExampleSignatureInOneMethod.java +++ b/src/main/java/com/cryptoexamples/java/ExampleSignature.java @@ -12,18 +12,22 @@ import java.util.logging.Logger; /** - * All in one example for cryptographic signing of a string in one method. + * Example for cryptographic signing of a string in one method. * - Generation of public and private RSA 4096 bit keypair * - SHA-512 with RSA * - BASE64 encoding as representation for the byte-arrays * - UTF-8 encoding of String * - Exception handling */ -public class ExampleSignatureInOneMethod { - private static final Logger LOGGER = Logger.getLogger(ExampleSignatureInOneMethod.class.getName()); +public class ExampleSignature { + private static final Logger LOGGER = Logger.getLogger(ExampleSignature.class.getName()); - public static void main(String[] args) { - String plainText = "Text that should be signed to prevent unknown tampering with its content."; + /** + * Demonstrational method that signs the plainText using a newly generated keypair. + * @param plainText + * @return true if signing and verification were successful, false otherwise + */ + public static boolean demonstrateSignature(String plainText) { try { // GENERATE NEW KEYPAIR KeyPairGenerator keyPairGenerator = KeyPairGenerator.getInstance("RSA"); @@ -46,8 +50,15 @@ public static void main(String[] args) { boolean isSignatureCorrect = signature.verify(Base64.getDecoder().decode(signatureForPlainTextString)); LOGGER.log(Level.INFO, () -> String.format("Signature is correct: %b", isSignatureCorrect)); + return isSignatureCorrect; } catch (NoSuchAlgorithmException | InvalidKeyException | SignatureException e) { LOGGER.log(Level.SEVERE, e.getLocalizedMessage()); + return false; } } + + public static void main(String[] args) { + demonstrateSignature("Text that should be signed to prevent unknown tampering with its content."); + + } } diff --git a/src/main/java/com/cryptoexamples/java/ExampleStringEncryptionKeyBasedInOneMethod.java b/src/main/java/com/cryptoexamples/java/ExampleStringEncryptionKeyBased.java similarity index 76% rename from src/main/java/com/cryptoexamples/java/ExampleStringEncryptionKeyBasedInOneMethod.java rename to src/main/java/com/cryptoexamples/java/ExampleStringEncryptionKeyBased.java index 5128494..749c9a8 100644 --- a/src/main/java/com/cryptoexamples/java/ExampleStringEncryptionKeyBasedInOneMethod.java +++ b/src/main/java/com/cryptoexamples/java/ExampleStringEncryptionKeyBased.java @@ -18,23 +18,26 @@ import java.util.logging.Logger; /** - * All in one example for encryption and decryption of a string in one method. + * Example for encryption and decryption of a string in one method. * - Random key generation using strong secure random number generator * - AES-256 authenticated encryption using GCM * - BASE64 encoding as representation for the byte-arrays * - UTF-8 encoding of Strings * - Exception handling */ -public class ExampleStringEncryptionKeyBasedInOneMethod { - private static final Logger LOGGER = Logger.getLogger(ExampleStringEncryptionKeyBasedInOneMethod.class.getName()); +public class ExampleStringEncryptionKeyBased { + private static final Logger LOGGER = Logger.getLogger(ExampleStringEncryptionKeyBased.class.getName()); - public static void main(String[] args) { - String plainText = "Text that is going to be sent over an insecure channel and must be encrypted at all costs!"; + /** + * Demonstrational method that encrypts the plainText using a newly generated key. + * @param plainText + * @return true if encryption and decryption were successful, false otherwise + */ + public static boolean demonstrateKeyBasedSymmetricEncryption(String plainText) { try { // GENERATE key - // TODO key should only be generated once and then stored in a secure location. + // TODO key should only be generated once and then managed with a key manager/key store. KeyGenerator keyGen = KeyGenerator.getInstance("AES"); - // 256 bit requires unlimited strength policy files http://www.oracle.com/technetwork/java/javase/downloads keyGen.init(256); SecretKey key = keyGen.generateKey(); @@ -58,8 +61,14 @@ public static void main(String[] args) { String decryptedCipherText = new String(decryptedCipher, StandardCharsets.UTF_8); LOGGER.log(Level.INFO, () -> String.format("Decrypted and original plain text are the same: %b", decryptedCipherText.compareTo(plainText) == 0)); + return decryptedCipherText.compareTo(plainText) == 0; } catch (NoSuchAlgorithmException | NoSuchPaddingException | InvalidKeyException | IllegalBlockSizeException | BadPaddingException | InvalidParameterException | InvalidAlgorithmParameterException e) { LOGGER.log(Level.SEVERE, e.getLocalizedMessage()); + return false; } } + + public static void main(String[] args) { + demonstrateKeyBasedSymmetricEncryption("Text that is going to be sent over an insecure channel and must be encrypted at all costs!"); + } } diff --git a/src/main/java/com/cryptoexamples/java/ExampleStringEncryptionPasswordBasedInOneMethod.java b/src/main/java/com/cryptoexamples/java/ExampleStringEncryptionPasswordBased.java similarity index 93% rename from src/main/java/com/cryptoexamples/java/ExampleStringEncryptionPasswordBasedInOneMethod.java rename to src/main/java/com/cryptoexamples/java/ExampleStringEncryptionPasswordBased.java index 65e13b5..666aff9 100644 --- a/src/main/java/com/cryptoexamples/java/ExampleStringEncryptionPasswordBasedInOneMethod.java +++ b/src/main/java/com/cryptoexamples/java/ExampleStringEncryptionPasswordBased.java @@ -23,7 +23,7 @@ import java.util.logging.Logger; /** - * All in one example for encryption and decryption of a string in one method. + * Example for encryption and decryption of a string in one method. * - Random password generation using strong secure random number generator * - Random salt generation * - Key derivation using PBKDF2 HMAC SHA-512, @@ -32,14 +32,14 @@ * - UTF-8 encoding of Strings * - Exception handling */ -public class ExampleStringEncryptionPasswordBasedInOneMethod { - private static final Logger LOGGER = Logger.getLogger(ExampleStringEncryptionPasswordBasedInOneMethod.class.getName()); +public class ExampleStringEncryptionPasswordBased { + private static final Logger LOGGER = Logger.getLogger(ExampleStringEncryptionPasswordBased.class.getName()); /** * Demonstrational method that encrypts the plainText using a password (that is used to derive the required key). * @param plainText * @param password - * @return true if encryption and decryption is working, false otherwise + * @return true if encryption and decryption were successful, false otherwise */ public static boolean demonstratePasswordBasedSymmetricEncryption(String plainText, String password) { try { diff --git a/src/test/java/com/cryptoexamples/java/EncryptionInOneMethodTests.java b/src/test/java/com/cryptoexamples/java/EncryptionInOneMethodTests.java index 6f72e33..a023870 100644 --- a/src/test/java/com/cryptoexamples/java/EncryptionInOneMethodTests.java +++ b/src/test/java/com/cryptoexamples/java/EncryptionInOneMethodTests.java @@ -37,42 +37,54 @@ public void resetOut() { } @Test - public void testStringEncryptionPasswordBasedMain() throws IOException { - ExampleStringEncryptionPasswordBasedInOneMethod.main(new String[1]); + public void testStringEncryptionPasswordBased() throws IOException { + ExampleStringEncryptionPasswordBased.main(new String[1]); assertThat(errContent.toString(), containsString("Decrypted and original plain text are the same: true")); errContent.flush(); - assertTrue(ExampleStringEncryptionPasswordBasedInOneMethod.demonstratePasswordBasedSymmetricEncryption("plaintext",null)); + assertTrue(ExampleStringEncryptionPasswordBased.demonstratePasswordBasedSymmetricEncryption("plaintext",null)); assertThat(errContent.toString(), containsString("Decrypted and original plain text are the same: true")); } @Test - public void testStringEncryptionKeyBasedMain() { - ExampleStringEncryptionKeyBasedInOneMethod.main(new String[1]); + public void testStringEncryptionKeyBased() throws IOException { + ExampleStringEncryptionKeyBased.main(new String[1]); + assertThat(errContent.toString(), containsString("Decrypted and original plain text are the same: true")); + errContent.flush(); + assertTrue(ExampleStringEncryptionKeyBased.demonstrateKeyBasedSymmetricEncryption("plaintext")); assertThat(errContent.toString(), containsString("Decrypted and original plain text are the same: true")); } @Test - public void testAsymmetricStringEncryptionMain() { - ExampleAsymmetricStringEncryptionInOneMethod.main(new String[1]); + public void testAsymmetricStringEncryption() { + ExampleAsymmetricStringEncryption.main(new String[1]); assertThat(errContent.toString(), containsString("Decrypted and original plain text are the same: true")); } @Test - public void testFileEncryptionMain() { - ExampleFileEncryptionInOneMethod.main(new String[1]); + public void testFileEncryption() throws IOException { + ExampleFileEncryption.main(new String[1]); + assertThat(errContent.toString(), containsString("Decrypted file content and original plain text are the same: true")); + errContent.flush(); + assertTrue(ExampleFileEncryption.demonstrateFileEncryption("file.enc", "plaintext", null)); assertThat(errContent.toString(), containsString("Decrypted file content and original plain text are the same: true")); } @Test - public void testHashMain() { - ExampleHashInOneMethod.main(new String[1]); + public void testHash() throws IOException { + ExampleHash.main(new String[1]); // uses string: "Text that should be authenticated by comparing the hash of it!" assertThat(errContent.toString(), containsString("jg0X629+SmdP0/LTHZV/3zXBrizM3/hptRZVIuTXSCtyaqAe0NB8KMld2qebBIXFS1yowCUpCPu93l/fPmKEXg==")); + errContent.flush(); + assertTrue(ExampleHash.demonstrateHash("plaintext")); + assertThat(errContent.toString(), containsString("jg0X629+SmdP0/LTHZV/3zXBrizM3/hptRZVIuTXSCtyaqAe0NB8KMld2qebBIXFS1yowCUpCPu93l/fPmKEXg==")); } @Test - public void testSignatureMain() { - ExampleSignatureInOneMethod.main(new String[1]); + public void testSignature() throws IOException { + ExampleSignature.main(new String[1]); + assertThat(errContent.toString(), containsString("Signature is correct: true")); + errContent.flush(); + assertTrue(ExampleSignature.demonstrateSignature("plainText")); assertThat(errContent.toString(), containsString("Signature is correct: true")); } From 3c59528ac01b8683a71c34ea0e6475fe835584e2 Mon Sep 17 00:00:00 2001 From: Kai Mindermann Date: Thu, 2 Aug 2018 12:41:37 +0200 Subject: [PATCH 25/33] releases 0.4.0 --- CHANGELOG.md | 5 ++++- 1 file changed, 4 insertions(+), 1 deletion(-) diff --git a/CHANGELOG.md b/CHANGELOG.md index e31ec22..e7db086 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -7,6 +7,8 @@ and this project adheres to [Semantic Versioning](http://semver.org/spec/v2.0.0. ## [Unreleased] +## [0.4.0] - 2018-08-02 + ### Changed - Changed class names to conform with guidelines @@ -93,7 +95,8 @@ and this project adheres to [Semantic Versioning](http://semver.org/spec/v2.0.0. - made some security relevant changes - made other security relevant changes -[Unreleased]: https://github.com/cryptoexamples/java-crypto-examples/compare/v0.3.0...HEAD +[Unreleased]: https://github.com/cryptoexamples/java-crypto-examples/compare/v0.4.0...HEAD +[0.4.0]: https://github.com/cryptoexamples/java-crypto-examples/compare/v0.3.0...v0.4.0 [0.3.0]: https://github.com/cryptoexamples/java-crypto-examples/compare/v0.2.0...v0.3.0 [0.2.0]: https://github.com/cryptoexamples/java-crypto-examples/compare/v0.1.1...v0.2.0 [0.1.1]: https://github.com/cryptoexamples/java-crypto-examples/compare/v0.1.0...v0.1.1 From 7a88da5716079bd20a33e8274fec87e0a316ccce Mon Sep 17 00:00:00 2001 From: Kai Mindermann Date: Thu, 2 Aug 2018 12:53:24 +0200 Subject: [PATCH 26/33] fixes inclusion paths, releases 0.4.1 --- CHANGELOG.md | 9 ++++++++- java_file_encryption_symmetric_password_based.md | 2 +- java_string_encryption_asymmetric.md | 2 +- java_string_encryption_key_based_symmetric.md | 2 +- java_string_encryption_password_based_symmetric.md | 2 +- java_string_hash.md | 2 +- java_string_sign.md | 2 +- 7 files changed, 14 insertions(+), 7 deletions(-) diff --git a/CHANGELOG.md b/CHANGELOG.md index e7db086..dc1b45e 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -7,6 +7,12 @@ and this project adheres to [Semantic Versioning](http://semver.org/spec/v2.0.0. ## [Unreleased] +## [0.4.1] - 2018-08-02 + +### Fixed + +- Fixed inclusion of source code links to old files + ## [0.4.0] - 2018-08-02 ### Changed @@ -95,7 +101,8 @@ and this project adheres to [Semantic Versioning](http://semver.org/spec/v2.0.0. - made some security relevant changes - made other security relevant changes -[Unreleased]: https://github.com/cryptoexamples/java-crypto-examples/compare/v0.4.0...HEAD +[Unreleased]: https://github.com/cryptoexamples/java-crypto-examples/compare/v0.4.1...HEAD +[0.4.1]: https://github.com/cryptoexamples/java-crypto-examples/compare/v0.4.0...v0.4.1 [0.4.0]: https://github.com/cryptoexamples/java-crypto-examples/compare/v0.3.0...v0.4.0 [0.3.0]: https://github.com/cryptoexamples/java-crypto-examples/compare/v0.2.0...v0.3.0 [0.2.0]: https://github.com/cryptoexamples/java-crypto-examples/compare/v0.1.1...v0.2.0 diff --git a/java_file_encryption_symmetric_password_based.md b/java_file_encryption_symmetric_password_based.md index c6f3140..b2797ae 100644 --- a/java_file_encryption_symmetric_password_based.md +++ b/java_file_encryption_symmetric_password_based.md @@ -39,7 +39,7 @@ tags: [Java, AES, GCM, PBKDF2, Salt, AEAD] ## Example Code for Java Password based symmetric file encryption using AES-GCM and PBKDF2 ```java -{% include_relative src/main/java/com/cryptoexamples/java/ExampleFileEncryptionInOneMethod.java %} +{% include_relative src/main/java/com/cryptoexamples/java/ExampleFileEncryption.java %} ``` diff --git a/java_string_encryption_asymmetric.md b/java_string_encryption_asymmetric.md index eba52d4..9c2d7dc 100644 --- a/java_string_encryption_asymmetric.md +++ b/java_string_encryption_asymmetric.md @@ -39,7 +39,7 @@ tags: [Java, RSA, Asymmetric, String, Encryption] ## Example Code for Java Asymmetric String Encryption using RSA 4096 ```java -{% include_relative src/main/java/com/cryptoexamples/java/ExampleAsymmetricStringEncryptionInOneMethod.java %} +{% include_relative src/main/java/com/cryptoexamples/java/ExampleAsymmetricStringEncryption.java %} ``` {% include links.html %} diff --git a/java_string_encryption_key_based_symmetric.md b/java_string_encryption_key_based_symmetric.md index cb0e308..c0a9434 100644 --- a/java_string_encryption_key_based_symmetric.md +++ b/java_string_encryption_key_based_symmetric.md @@ -40,7 +40,7 @@ tags: [Java, AES, GCM, Salt, AEAD] ## Example Code for Java String Encryption with key generation using AES-GCM ```java -{% include_relative src/main/java/com/cryptoexamples/java/ExampleStringEncryptionKeyBasedInOneMethod.java %} +{% include_relative src/main/java/com/cryptoexamples/java/ExampleStringEncryptionKeyBased.java %} ``` diff --git a/java_string_encryption_password_based_symmetric.md b/java_string_encryption_password_based_symmetric.md index 1de745c..19adae2 100644 --- a/java_string_encryption_password_based_symmetric.md +++ b/java_string_encryption_password_based_symmetric.md @@ -40,7 +40,7 @@ tags: [Java, AES, GCM, PBKDF2, Salt, AEAD] ## Example Code for Java Password Based String Encryption using AES-GCM and PBKDF2 ```java -{% include_relative src/main/java/com/cryptoexamples/java/ExampleStringEncryptionPasswordBasedInOneMethod.java %} +{% include_relative src/main/java/com/cryptoexamples/java/ExampleStringEncryptionPasswordBased.java %} ``` diff --git a/java_string_hash.md b/java_string_hash.md index 943e016..16b56fe 100644 --- a/java_string_hash.md +++ b/java_string_hash.md @@ -39,7 +39,7 @@ tags: [Java, hash, SHA, SHA-512] ## Example Code for Java String Hashing using SHA-512, BASE64 and UTF-8 encoding ```java -{% include_relative src/main/java/com/cryptoexamples/java/ExampleHashInOneMethod.java %} +{% include_relative src/main/java/com/cryptoexamples/java/ExampleHash.java %} ``` diff --git a/java_string_sign.md b/java_string_sign.md index 7dc87b6..67a851d 100644 --- a/java_string_sign.md +++ b/java_string_sign.md @@ -39,7 +39,7 @@ tags: [Java, hash, SHA, SHA-512] ## Example Code for Java String Signing using SHA-512, RSA 4096, BASE64 and UTF-8 encoding ```java -{% include_relative src/main/java/com/cryptoexamples/java/ExampleSignatureInOneMethod.java %} +{% include_relative src/main/java/com/cryptoexamples/java/ExampleSignature.java %} ``` From 22696f249f12ad93d3a1d2b93f53fff309781a91 Mon Sep 17 00:00:00 2001 From: "Kai Mindermann M.Sc" Date: Sun, 11 Aug 2019 16:53:59 +0200 Subject: [PATCH 27/33] Update ExampleAsymmetricStringEncryption.java --- .../cryptoexamples/java/ExampleAsymmetricStringEncryption.java | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/main/java/com/cryptoexamples/java/ExampleAsymmetricStringEncryption.java b/src/main/java/com/cryptoexamples/java/ExampleAsymmetricStringEncryption.java index b5c84c3..114bdd8 100644 --- a/src/main/java/com/cryptoexamples/java/ExampleAsymmetricStringEncryption.java +++ b/src/main/java/com/cryptoexamples/java/ExampleAsymmetricStringEncryption.java @@ -34,7 +34,7 @@ public static void main(String[] args) { KeyPair keyPair = keyPairGenerator.generateKeyPair(); // ENCRYPTION - Cipher cipher = Cipher.getInstance("RSA/ECB/OAEPWithSHA-256AndMGF1Padding"); + Cipher cipher = Cipher.getInstance("RSA/None/OAEPWithSHA-256AndMGF1Padding"); cipher.init(Cipher.ENCRYPT_MODE, keyPair.getPublic()); byte[] cipherTextBytes = cipher.doFinal(plainText.getBytes(StandardCharsets.UTF_8)); From 19ef25c167f56eb0bb61ae6813591993a1cfcd1e Mon Sep 17 00:00:00 2001 From: "Kai Mindermann M.Sc" Date: Sun, 11 Aug 2019 16:57:49 +0200 Subject: [PATCH 28/33] Update ExampleAsymmetricStringEncryption.java --- .../cryptoexamples/java/ExampleAsymmetricStringEncryption.java | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/main/java/com/cryptoexamples/java/ExampleAsymmetricStringEncryption.java b/src/main/java/com/cryptoexamples/java/ExampleAsymmetricStringEncryption.java index 114bdd8..b5c84c3 100644 --- a/src/main/java/com/cryptoexamples/java/ExampleAsymmetricStringEncryption.java +++ b/src/main/java/com/cryptoexamples/java/ExampleAsymmetricStringEncryption.java @@ -34,7 +34,7 @@ public static void main(String[] args) { KeyPair keyPair = keyPairGenerator.generateKeyPair(); // ENCRYPTION - Cipher cipher = Cipher.getInstance("RSA/None/OAEPWithSHA-256AndMGF1Padding"); + Cipher cipher = Cipher.getInstance("RSA/ECB/OAEPWithSHA-256AndMGF1Padding"); cipher.init(Cipher.ENCRYPT_MODE, keyPair.getPublic()); byte[] cipherTextBytes = cipher.doFinal(plainText.getBytes(StandardCharsets.UTF_8)); From de485fcf6281e37bb0ee7e4a78e6653aca406b90 Mon Sep 17 00:00:00 2001 From: Kai Mindermann Date: Sun, 16 Feb 2020 14:43:54 +0100 Subject: [PATCH 29/33] updates gradle (removes jacoco definitions) --- build.gradle | 13 +------------ gradle/wrapper/gradle-wrapper.properties | 2 +- 2 files changed, 2 insertions(+), 13 deletions(-) diff --git a/build.gradle b/build.gradle index 6acdd54..83f2747 100644 --- a/build.gradle +++ b/build.gradle @@ -18,16 +18,5 @@ dependencies { testCompile group: 'junit', name: 'junit', version: '4.12' } -tasks.withType(Test) { task -> - jacoco { - append = false - } -} -jacocoTestReport { - reports { - xml.enabled true - csv.enabled false - html.destination "${buildDir}/jacocoHtml" - } -} \ No newline at end of file + diff --git a/gradle/wrapper/gradle-wrapper.properties b/gradle/wrapper/gradle-wrapper.properties index 88a3bc5..c60eeea 100644 --- a/gradle/wrapper/gradle-wrapper.properties +++ b/gradle/wrapper/gradle-wrapper.properties @@ -3,4 +3,4 @@ distributionBase=GRADLE_USER_HOME distributionPath=wrapper/dists zipStoreBase=GRADLE_USER_HOME zipStorePath=wrapper/dists -distributionUrl=https\://services.gradle.org/distributions/gradle-4.7-all.zip +distributionUrl=https\://services.gradle.org/distributions/gradle-6.0-all.zip From 7233446ecf6bd335dc7aa91cc8416ec9699ae196 Mon Sep 17 00:00:00 2001 From: Kai Mindermann Date: Sun, 16 Feb 2020 14:47:45 +0100 Subject: [PATCH 30/33] removes oraclejdk8 and adds oraclejdk 10 to 15 --- .travis.yml | 7 ++++++- 1 file changed, 6 insertions(+), 1 deletion(-) diff --git a/.travis.yml b/.travis.yml index 661c840..232ea47 100644 --- a/.travis.yml +++ b/.travis.yml @@ -1,7 +1,12 @@ language: java jdk: - - oraclejdk8 - oraclejdk9 + - oraclejdk10 + - oraclejdk11 + - oraclejdk12 + - oraclejdk13 + - oraclejdk14 + - oraclejdk15 addons: sonarcloud: organization: "kmindi-github" # the key of the org you chose at step #3 From 4d264ae995cfeec5ddaba729e3a64a629dbe1539 Mon Sep 17 00:00:00 2001 From: Kai Mindermann Date: Sun, 16 Feb 2020 14:57:27 +0100 Subject: [PATCH 31/33] updates gradle to 6.1.1 and changes used jdks in travis --- .travis.yml | 8 ++++---- gradle/wrapper/gradle-wrapper.properties | 2 +- 2 files changed, 5 insertions(+), 5 deletions(-) diff --git a/.travis.yml b/.travis.yml index 232ea47..20b3a1c 100644 --- a/.travis.yml +++ b/.travis.yml @@ -1,12 +1,12 @@ language: java jdk: + - openjdk8 - oraclejdk9 - - oraclejdk10 + - openjdk9 - oraclejdk11 - - oraclejdk12 + - openjdk11 - oraclejdk13 - - oraclejdk14 - - oraclejdk15 + - openjdk13 addons: sonarcloud: organization: "kmindi-github" # the key of the org you chose at step #3 diff --git a/gradle/wrapper/gradle-wrapper.properties b/gradle/wrapper/gradle-wrapper.properties index c60eeea..a362cda 100644 --- a/gradle/wrapper/gradle-wrapper.properties +++ b/gradle/wrapper/gradle-wrapper.properties @@ -3,4 +3,4 @@ distributionBase=GRADLE_USER_HOME distributionPath=wrapper/dists zipStoreBase=GRADLE_USER_HOME zipStorePath=wrapper/dists -distributionUrl=https\://services.gradle.org/distributions/gradle-6.0-all.zip +distributionUrl=https\://services.gradle.org/distributions/gradle-6.1.1-all.zip From 69959d5e536a7875fd27aef97b9f97ad26637549 Mon Sep 17 00:00:00 2001 From: Kai Mindermann Date: Sun, 16 Feb 2020 15:09:35 +0100 Subject: [PATCH 32/33] updates markdown files --- .travis.yml | 4 ++++ java_file_encryption_symmetric_password_based.md | 10 ++++++++-- java_string_encryption_asymmetric.md | 10 ++++++++-- java_string_encryption_key_based_symmetric.md | 10 ++++++++-- java_string_encryption_password_based_symmetric.md | 10 ++++++++-- java_string_hash.md | 10 ++++++++-- java_string_sign.md | 10 ++++++++-- 7 files changed, 52 insertions(+), 12 deletions(-) diff --git a/.travis.yml b/.travis.yml index 20b3a1c..5c77f1d 100644 --- a/.travis.yml +++ b/.travis.yml @@ -7,6 +7,10 @@ jdk: - openjdk11 - oraclejdk13 - openjdk13 + #- oraclejdk14 + #- openjdk14 + #- oraclejdk15 + #- openjdk15 addons: sonarcloud: organization: "kmindi-github" # the key of the org you chose at step #3 diff --git a/java_file_encryption_symmetric_password_based.md b/java_file_encryption_symmetric_password_based.md index b2797ae..5c7a3a5 100644 --- a/java_file_encryption_symmetric_password_based.md +++ b/java_file_encryption_symmetric_password_based.md @@ -24,7 +24,7 @@ current_reviews: [ ] # Indicates when this example was last updated/created. Reviews don't change this. -last_updated: "2018-08-02" +last_updated: "2020-02-16" tags: [Java, AES, GCM, PBKDF2, Salt, AEAD] --- @@ -34,7 +34,13 @@ tags: [Java, AES, GCM, PBKDF2, Salt, AEAD] ## Java version -- JDK 11 +- openjdk8 +- oraclejdk9 +- openjdk9 +- oraclejdk11 +- openjdk11 +- oraclejdk13 +- openjdk13 ## Example Code for Java Password based symmetric file encryption using AES-GCM and PBKDF2 diff --git a/java_string_encryption_asymmetric.md b/java_string_encryption_asymmetric.md index 9c2d7dc..2c0d40c 100644 --- a/java_string_encryption_asymmetric.md +++ b/java_string_encryption_asymmetric.md @@ -24,7 +24,7 @@ current_reviews: [ ] # Indicates when this example was last updated/created. Reviews don't change this. -last_updated: "2018-08-02" +last_updated: "2020-02-16" tags: [Java, RSA, Asymmetric, String, Encryption] --- @@ -34,7 +34,13 @@ tags: [Java, RSA, Asymmetric, String, Encryption] ## Java version -- JDK 11 +- openjdk8 +- oraclejdk9 +- openjdk9 +- oraclejdk11 +- openjdk11 +- oraclejdk13 +- openjdk13 ## Example Code for Java Asymmetric String Encryption using RSA 4096 diff --git a/java_string_encryption_key_based_symmetric.md b/java_string_encryption_key_based_symmetric.md index c0a9434..b2fc025 100644 --- a/java_string_encryption_key_based_symmetric.md +++ b/java_string_encryption_key_based_symmetric.md @@ -24,7 +24,7 @@ current_reviews: [ ] # Indicates when this example was last updated/created. Reviews don't change this. -last_updated: "2018-08-02" +last_updated: "2020-02-16" tags: [Java, AES, GCM, Salt, AEAD] --- @@ -35,7 +35,13 @@ tags: [Java, AES, GCM, Salt, AEAD] ## Java version -- JDK 11 +- openjdk8 +- oraclejdk9 +- openjdk9 +- oraclejdk11 +- openjdk11 +- oraclejdk13 +- openjdk13 ## Example Code for Java String Encryption with key generation using AES-GCM diff --git a/java_string_encryption_password_based_symmetric.md b/java_string_encryption_password_based_symmetric.md index 19adae2..0e5ba9c 100644 --- a/java_string_encryption_password_based_symmetric.md +++ b/java_string_encryption_password_based_symmetric.md @@ -24,7 +24,7 @@ current_reviews: [ ] # Indicates when this example was last updated/created. Reviews don't change this. -last_updated: "2018-08-02" +last_updated: "2020-02-16" tags: [Java, AES, GCM, PBKDF2, Salt, AEAD] --- @@ -35,7 +35,13 @@ tags: [Java, AES, GCM, PBKDF2, Salt, AEAD] ## Java version -- JDK 11 +- openjdk8 +- oraclejdk9 +- openjdk9 +- oraclejdk11 +- openjdk11 +- oraclejdk13 +- openjdk13 ## Example Code for Java Password Based String Encryption using AES-GCM and PBKDF2 diff --git a/java_string_hash.md b/java_string_hash.md index 16b56fe..08dbd49 100644 --- a/java_string_hash.md +++ b/java_string_hash.md @@ -24,7 +24,7 @@ current_reviews: [ ] # Indicates when this example was last updated/created. Reviews don't change this. -last_updated: "2018-08-02" +last_updated: "2020-02-16" tags: [Java, hash, SHA, SHA-512] --- @@ -34,7 +34,13 @@ tags: [Java, hash, SHA, SHA-512] ## Java version -- JDK 11 +- openjdk8 +- oraclejdk9 +- openjdk9 +- oraclejdk11 +- openjdk11 +- oraclejdk13 +- openjdk13 ## Example Code for Java String Hashing using SHA-512, BASE64 and UTF-8 encoding diff --git a/java_string_sign.md b/java_string_sign.md index 67a851d..d4b2d74 100644 --- a/java_string_sign.md +++ b/java_string_sign.md @@ -24,7 +24,7 @@ current_reviews: [ ] # Indicates when this example was last updated/created. Reviews don't change this. -last_updated: "2018-08-02" +last_updated: "2020-02-16" tags: [Java, hash, SHA, SHA-512] --- @@ -34,7 +34,13 @@ tags: [Java, hash, SHA, SHA-512] ## Java version -- JDK 11 +- openjdk8 +- oraclejdk9 +- openjdk9 +- oraclejdk11 +- openjdk11 +- oraclejdk13 +- openjdk13 ## Example Code for Java String Signing using SHA-512, RSA 4096, BASE64 and UTF-8 encoding From 4f15659801a2fe23c7ff8b061e64831f3ef341a2 Mon Sep 17 00:00:00 2001 From: Kai Mindermann Date: Sun, 16 Feb 2020 15:35:46 +0100 Subject: [PATCH 33/33] releases 0.4.2 --- CHANGELOG.md | 10 +++++++++- 1 file changed, 9 insertions(+), 1 deletion(-) diff --git a/CHANGELOG.md b/CHANGELOG.md index dc1b45e..1e64ef8 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -7,6 +7,13 @@ and this project adheres to [Semantic Versioning](http://semver.org/spec/v2.0.0. ## [Unreleased] +## [0.4.2] - 2020-02-16 + +### Changed + +- Changed gradle version to 6.1.1 +- Changed used jdks in travis + ## [0.4.1] - 2018-08-02 ### Fixed @@ -101,7 +108,8 @@ and this project adheres to [Semantic Versioning](http://semver.org/spec/v2.0.0. - made some security relevant changes - made other security relevant changes -[Unreleased]: https://github.com/cryptoexamples/java-crypto-examples/compare/v0.4.1...HEAD +[Unreleased]: https://github.com/cryptoexamples/java-crypto-examples/compare/v0.4.2...HEAD +[0.4.2]: https://github.com/cryptoexamples/java-crypto-examples/compare/v0.4.1...v0.4.2 [0.4.1]: https://github.com/cryptoexamples/java-crypto-examples/compare/v0.4.0...v0.4.1 [0.4.0]: https://github.com/cryptoexamples/java-crypto-examples/compare/v0.3.0...v0.4.0 [0.3.0]: https://github.com/cryptoexamples/java-crypto-examples/compare/v0.2.0...v0.3.0