'RSA'에 해당되는 글 3건

반응형

RSA 키생성 후 생성된 키로 암복호화 테스트 해 보았다.

package com.rsatest.rsaTest;

import java.io.File;
import java.io.FileInputStream;
import java.io.IOException;
import java.io.UnsupportedEncodingException;
import java.nio.file.Files;
import java.security.InvalidKeyException;
import java.security.KeyFactory;
import java.security.NoSuchAlgorithmException;
import java.security.PrivateKey;
import java.security.PublicKey;
import java.security.spec.DSAPrivateKeySpec;
import java.security.spec.DSAPublicKeySpec;
import java.security.spec.EncodedKeySpec;
import java.security.spec.PKCS8EncodedKeySpec;
import java.security.spec.X509EncodedKeySpec;
import javax.crypto.BadPaddingException;
import javax.crypto.Cipher;
import javax.crypto.IllegalBlockSizeException;
import javax.crypto.NoSuchPaddingException;
import org.apache.commons.codec.binary.Base64;


//
// RSA 암복호화 및 테스트
//
// Created by netcanis on 2019/04/29.
// Copyright © 2019 netcanis. All rights reserved.
//

public class RSAEncryption
{
	private Cipher cipher;
	
	public RSAEncryption() throws NoSuchAlgorithmException, NoSuchPaddingException{
		this.cipher = Cipher.getInstance("RSA");
	}
	
	// 주어진 파일을 byte array로 읽기 
	public byte[] getFileInBytes(File f) throws IOException{
		FileInputStream fis = new FileInputStream(f);
		byte[] fbytes = new byte[(int) f.length()];
		fis.read(fbytes);
		fis.close();
		return fbytes;
	}
		
	// X509EncodedKey
	public PublicKey getPublic(String filename) throws Exception {
		byte[] keyBytes = Files.readAllBytes(new File(filename).toPath());
		X509EncodedKeySpec spec = new X509EncodedKeySpec(keyBytes);
		KeyFactory kf = KeyFactory.getInstance("RSA");
		return kf.generatePublic(spec);
	}

	// PKCS8EncodedKeySpec
	public PrivateKey getPrivate(String filename) throws Exception {
		byte[] keyBytes = Files.readAllBytes(new File(filename).toPath());
		
		//byte[] decoded = Base64.getDecoder().decode(keyBytes);
		//println(new String(decoded));    // Outputs "Hello"
		
		//Base64 codec = new Base64();
		//byte[] decoded = codec.decode(keyBytes);
		//System.out.println( new String(decoded) );    // Outputs "Hello"
		
		PKCS8EncodedKeySpec spec = new PKCS8EncodedKeySpec(keyBytes);
		KeyFactory kf = KeyFactory.getInstance("RSA");
		return kf.generatePrivate(spec);
	}
	
	
	
	// PKCS1
//	public PrivateKey getPrivate2(String filename) throws Exception {
//		PEMParser pemParser = new PEMParser(new FileReader(privateKeyFile));
//		JcaPEMKeyConverter converter = new JcaPEMKeyConverter().setProvider("BC");
//		Object object = pemParser.readObject();
//		KeyPair kp = converter.getKeyPair((PEMKeyPair) object);
//		PrivateKey privateKey = kp.getPrivate();
//	}
	
	// public key로 암호화 
	public String encrypt(String str, PublicKey key) throws NoSuchAlgorithmException, NoSuchPaddingException, UnsupportedEncodingException, IllegalBlockSizeException, BadPaddingException, InvalidKeyException{
		this.cipher.init(Cipher.ENCRYPT_MODE, key);
		return Base64.encodeBase64String(cipher.doFinal(str.getBytes("UTF-8")));
	}
	
	// private key로 복호화 
	public String decrypt(String str, PrivateKey key) throws InvalidKeyException, UnsupportedEncodingException, IllegalBlockSizeException, BadPaddingException{
		this.cipher.init(Cipher.DECRYPT_MODE, key);
		return new String(cipher.doFinal(Base64.decodeBase64(str)), "UTF-8");
	}

	/*
	  String hexString = "01020304FF11";
      byte[] ByteArray = hexStringToByteArray(hexString);
      String str = byteArrayToHexString(ByteArray);
      System.out.println(str);
	 */
	
	// hex to byte[]
	public byte[] hexStringToByteArray(String s) {
	    int len = s.length();
	    byte[] data = new byte[len / 2];
	    for (int i = 0; i < len; i += 2) {
	        data[i / 2] = (byte) ((Character.digit(s.charAt(i), 16) << 4)
	                             + Character.digit(s.charAt(i+1), 16));
	    }
	    return data;
	}
	
	// byte[] to hex
	public String byteArrayToHexString(byte[] bytes){ 
		StringBuilder sb = new StringBuilder(); 
		for(byte b : bytes){ 
			sb.append(String.format("%02X", b&0xff)); 
		} 
		return sb.toString(); 
	} 
    
	
	public static void main(String[] args) throws Exception {
		RSAEncryption ac = new RSAEncryption();
		
		// 공개키
		PublicKey publicKey = ac.getPublic("KeyPair/public.key");
		// 개인키 
		PrivateKey privateKey = ac.getPrivate("KeyPair/private.key");
		
		// 원문 
		String msg = "test message";
		
		
		System.out.println("----------------------------------------------------");
		System.out.println(":::: TEST 암호화 및 복호화 ::::");
		
		// 암호화 원문 BASE64
		String encryptedString = ac.encrypt(msg, publicKey);
		// 복호화
		String decryptedString = ac.decrypt(encryptedString, privateKey);
		
		System.out.println("----------------------------------------------------");
		System.out.println(
    			"원문 = " + msg + "\n" +
				"공개키 암호화 = " + encryptedString + "\n" +
				"개인키 복호화 = " + decryptedString
				);
		System.out.println("----------------------------------------------------");

	}
}

 

사용방법 :

Encode or decode byte arrays:

byte[] encoded = Base64.getEncoder().encode("Hello".getBytes());
println(new String(encoded));   // Outputs "SGVsbG8="

byte[] decoded = Base64.getDecoder().decode(encoded);
println(new String(decoded))    // Outputs "Hello"
Or if you just want the strings:

String encoded = Base64.getEncoder().encodeToString("Hello".getBytes());
println(encoded);   // Outputs "SGVsbG8="

String decoded = new String(Base64.getDecoder().decode(encoded.getBytes()));
println(decoded)    // Outputs "Hello"


Base64 codec = new Base64();
byte[] encoded = codec.encode("Hello".getBytes());
println(new String(encoded));   // Outputs "SGVsbG8="

byte[] decoded = codec.decode(encoded);
println(new String(decoded))    // Outputs "Hello"


	

openssl rsa -text -in public.key -inform DER -pubin
-----BEGIN PUBLIC KEY-----
MIGfMA0GCSqGSIb3DQEBAQUAA4GNADCBiQKBgQCCH+bC/6rGV8I9NgqCUTpcUcUX
q15NC8N86kHtSPFl03dwwGIO3hPQVZyMiVwJYq8gz0ZFacf27tkvgphqJOAf/ckY
PKb52+8bEXNowbPhKqiwPaclEmtvm8MJplxZKa/Y+IhYitRRI7aVow841PRxC/nA
Z8AEiw5xkfBMsy9jdwIDAQAB
-----END PUBLIC KEY-----


openssl rsa -text -in private.key -inform DER
-----BEGIN RSA PRIVATE KEY-----
MIICXQIBAAKBgQCCH+bC/6rGV8I9NgqCUTpcUcUXq15NC8N86kHtSPFl03dwwGIO
3hPQVZyMiVwJYq8gz0ZFacf27tkvgphqJOAf/ckYPKb52+8bEXNowbPhKqiwPacl
Emtvm8MJplxZKa/Y+IhYitRRI7aVow841PRxC/nAZ8AEiw5xkfBMsy9jdwIDAQAB
AoGAGfdvvz3xwD7G/hwIoNTAxqdyozSJTuqoCgddPJKvyVgXn6Jkbv8WCR7sbIcE
nMLam7uBFFz1kGs9X+O5soTFTJHvyN1QyhvWODd2Gqqheh2fHqNunjegBJKnMVDS
ZCF+0HQe1SBub2D/WkPRMNb1O24v0FaR9LalaZAPqgM9eYECQQDpl+lSEddOsB7f
jX6QS9Z56s8St2Lql/HVlEsyZ3RZIHA+oGMuHaK124fo/CEQxH/SHouVCrjdgiR1
2rLbZY1hAkEAjps5Yw2SHb3AOUqG7x+FmVhb+DaMR+KZZpVlJvRxy4fQpoB2GdC4
Okf7idpQGZJHXeOI8sQbtS4GTFT7nwgH1wJBAKS2natlMTEnN13jZA9TqpSlYgaM
kY9iPQChZLTSBlSibwN6DPWDqCwb9KXww1ATfx4ms74QpXJsRlFkOSJDZYECQD4I
T6JC2PiO/frt7FxAPgFCal9CeysZ6tiwy9tyIb4DSkPjRXxdSoYvob+Jc6Zr9xdk
TsIrhFH/v0WdAgdfmukCQQCRnRh0nMw5GhjkP9pJTLZo4j8H/kp7lY0LDBLzo1cW
+nvyJ4Xg+Jgig5/lsn3QaIckocfnxcq10fGk+bFr67gM
-----END RSA PRIVATE KEY-----


UBpay RSA 암호화 결과 (위의 public key로 암호화)
원문 = test message
원문 HEXA = 74657374206D657373616765
암호화 원문 BASE64 = JLvhRkfskdQNcJ5mjMIy9hcCrfM1QDL5Qy/4tsnW8pG7QXvPrwmo7OxiTiC4FVBMw/Ae/NeLJCxY2jr9uRvKXFxqSrdrjBoO3QL+oFpKbldcvTRUzXCRsWzKzeM8v3FOclWgkZYZMzGq8PQQu3PgFKHCVMnX7//UE7aguHvLiJo=

반응형

'개발 > Note' 카테고리의 다른 글

20진수 변환  (0) 2021.09.16
root-level 디렉토리에 폴더, symbolic link 생성 방법  (0) 2021.03.15
RSA key 파일 생성  (0) 2021.02.05
용어 정리  (0) 2021.02.05
Korea Bank Codes  (0) 2021.02.05
블로그 이미지

SKY STORY

,
반응형

Download Apache Commons Codec 다운로드 :

commons.apache.org/proper/commons-codec/download_codec.cgi

 

라이브러리 폴더에 복사

 

RSA key 파일 생성 클래스 추가 

package com.rsatest.keypair;

import java.io.File;
import java.io.FileOutputStream;
import java.io.IOException;
import java.security.KeyPair;
import java.security.KeyPairGenerator;
import java.security.NoSuchAlgorithmException;
import java.security.NoSuchProviderException;
import java.security.PrivateKey;
import java.security.PublicKey;


//
// RSA Key 파일 생성
//
// Created by netcanis on 2019/04/29.
// Copyright © 2019 netcanis. All rights reserved.
//


public class GenKeys
{
	private KeyPairGenerator keyGen;
	private KeyPair pair;
	private PrivateKey privateKey;
	private PublicKey publicKey;

	// RSA 초기화 및 키 생성 
	public GenKeys(int keysize) throws NoSuchAlgorithmException, NoSuchProviderException {
		this.keyGen = KeyPairGenerator.getInstance("RSA");
		this.keyGen.initialize(keysize);
		this.pair = this.keyGen.generateKeyPair();
		this.publicKey = pair.getPublic();
		this.privateKey = pair.getPrivate();
	}

	public PublicKey getPublicKey() {
		return this.publicKey;
	}
	
	public PrivateKey getPrivateKey() {
		return this.privateKey;
	}
	
	public void writeToFile(String path, byte[] key) throws IOException {
		File f = new File(path);
		f.getParentFile().mkdirs();

		FileOutputStream fos = new FileOutputStream(f);
		fos.write(key);
		fos.flush();
		fos.close();
	}

	
	
	public static void main(String[] args) {
		GenKeys genKeys;
		try {
			// 1024bit key pair 생성  
			genKeys = new GenKeys(1024);
			
			System.out.println(genKeys.publicKey);
			System.out.println(genKeys.privateKey);
			
			// 바이너리 파일로 저장 
			genKeys.writeToFile("KeyPair/public.key", genKeys.getPublicKey().getEncoded());
			genKeys.writeToFile("KeyPair/private.key", genKeys.getPrivateKey().getEncoded());
			
		} catch (NoSuchAlgorithmException | NoSuchProviderException e) {
			System.err.println(e.getMessage());
		} catch (IOException e) {
			System.err.println(e.getMessage());
		}
	}
}

 

결과 로그

 

결과물 확인

 

2021/02/05 - [개발노트] - 용어 정리

2021/02/05 - [iOS/Objective-C] - ARC or Non-ARC Compile Flag 설정

2021/02/05 - [개발노트] - Korea Bank Codes

2021/02/05 - [OS/Mac OS X] - NVRAM / PRAM 재설정

2021/02/05 - [OS/Mac OS X] - Mac OS 재설치

2021/01/06 - [iOS/Swift] - String to CGFloat

2021/01/05 - [iOS/Tips] - SceneDelegate 포인터 구하기

2021/01/05 - [iOS/Tips] - 앱 호출 (URL scheme)

2020/12/24 - [개발노트] - 라이선스 종류

2020/12/24 - [OS/Mac OS X] - MacBook을 AP로 설정하는 방법

2020/12/18 - [Arduino] - Bit Rate, Baud Rate

2020/12/18 - [Arduino] - RS232 Serial 통신 불량체크

2020/12/17 - [프로그래밍/Java] - Java HotSpot(TM) 64-Bit Server VM warning: Sharing is only supported for boot loader classes because bootstrap classpath has been appended

2020/12/17 - [프로그래밍/Java] - RSA 암복호화

반응형

'개발 > Note' 카테고리의 다른 글

root-level 디렉토리에 폴더, symbolic link 생성 방법  (0) 2021.03.15
RSA 암복호화 테스트  (0) 2021.02.05
용어 정리  (0) 2021.02.05
Korea Bank Codes  (0) 2021.02.05
NVRAM / PRAM 재설정  (0) 2021.02.05
블로그 이미지

SKY STORY

,

RSA 암복호화

개발/Note 2020. 12. 17. 16:18
반응형

결제 관련 API 연동(VAN, PG, 간편결제 등) 할 경우 RSA암복호화 과정을 거치게되는데

이 부분에 대한 샘플 코드를 작성해 보았다.

 

Apache Commons Codec 다운로드

commons.apache.org/proper/commons-codec/

 

Codec – Home

Apache Commons Codec Apache Commons Codec (TM) software provides implementations of common encoders and decoders such as Base64, Hex, Phonetic and URLs. Impetus Codec was formed as an attempt to focus development effort on one definitive implementation of

commons.apache.org

 

프로젝트 라이브러리에 추가. 

 

PublicKey와 PrivateKey 파일을 생성

package com.ubpay.keypair;

import java.io.File;
import java.io.FileOutputStream;
import java.io.IOException;
import java.security.KeyPair;
import java.security.KeyPairGenerator;
import java.security.NoSuchAlgorithmException;
import java.security.NoSuchProviderException;
import java.security.PrivateKey;
import java.security.PublicKey;

//
// RSA Key 파일 생성
//
// Created by netcanis on 2019/04/29.
// Copyright © 2019 netcanis. All rights reserved.
//

// Download Apache Commons Codec
// https://commons.apache.org/proper/commons-codec/download_codec.cgi

public class GenKeys
{
	private KeyPairGenerator keyGen;
	private KeyPair pair;
	private PrivateKey privateKey;
	private PublicKey publicKey;

	// RSA 초기화 및 키 생성 
	public GenKeys(int keysize) throws NoSuchAlgorithmException, NoSuchProviderException {
		this.keyGen = KeyPairGenerator.getInstance("RSA");
		this.keyGen.initialize(keysize);
		this.pair = this.keyGen.generateKeyPair();
		this.publicKey = pair.getPublic();
		this.privateKey = pair.getPrivate();
	}

	public PublicKey getPublicKey() {
		return this.publicKey;
	}
	
	public PrivateKey getPrivateKey() {
		return this.privateKey;
	}
	
	public void writeToFile(String path, byte[] key) throws IOException {
		File f = new File(path);
		f.getParentFile().mkdirs();

		FileOutputStream fos = new FileOutputStream(f);
		fos.write(key);
		fos.flush();
		fos.close();
	}

	
	
	public static void main(String[] args) {
		GenKeys genKeys;
		try {
			// 1024bit key pair 생성  
			genKeys = new GenKeys(1024);
			
			System.out.println(genKeys.publicKey);
			System.out.println(genKeys.privateKey);
			
			// 바이너리 파일로 저장 
			genKeys.writeToFile("KeyPair/public.key", genKeys.getPublicKey().getEncoded());
			genKeys.writeToFile("KeyPair/private.key", genKeys.getPrivateKey().getEncoded());
			
		} catch (NoSuchAlgorithmException | NoSuchProviderException e) {
			System.err.println(e.getMessage());
		} catch (IOException e) {
			System.err.println(e.getMessage());
		}
	}
}

 

생성 결과

 

생성된 키를 이용하여 암복호화 테스트

package com.ubpay.rsaTest;

import java.io.File;
import java.io.FileInputStream;
import java.io.IOException;
import java.io.UnsupportedEncodingException;
import java.nio.file.Files;
import java.security.InvalidKeyException;
import java.security.KeyFactory;
import java.security.NoSuchAlgorithmException;
import java.security.PrivateKey;
import java.security.PublicKey;
import java.security.spec.DSAPrivateKeySpec;
import java.security.spec.DSAPublicKeySpec;
import java.security.spec.EncodedKeySpec;
import java.security.spec.PKCS8EncodedKeySpec;
import java.security.spec.X509EncodedKeySpec;
import javax.crypto.BadPaddingException;
import javax.crypto.Cipher;
import javax.crypto.IllegalBlockSizeException;
import javax.crypto.NoSuchPaddingException;
import org.apache.commons.codec.binary.Base64;


//
// RSA 암복호화 및 테스트
//
// Created by netcanis on 2019/04/29.
// Copyright © 2019 netcanis. All rights reserved.
//

public class RSAEncryption
{
	private Cipher cipher;
	
	public RSAEncryption() throws NoSuchAlgorithmException, NoSuchPaddingException{
		this.cipher = Cipher.getInstance("RSA");
	}
	
	// 주어진 파일을 byte array로 읽기 
	public byte[] getFileInBytes(File f) throws IOException{
		FileInputStream fis = new FileInputStream(f);
		byte[] fbytes = new byte[(int) f.length()];
		fis.read(fbytes);
		fis.close();
		return fbytes;
	}
		
	// X509EncodedKey
	public PublicKey getPublic(String filename) throws Exception {
		byte[] keyBytes = Files.readAllBytes(new File(filename).toPath());
		X509EncodedKeySpec spec = new X509EncodedKeySpec(keyBytes);
		KeyFactory kf = KeyFactory.getInstance("RSA");
		return kf.generatePublic(spec);
	}

	// PKCS8EncodedKeySpec
	public PrivateKey getPrivate(String filename) throws Exception {
		byte[] keyBytes = Files.readAllBytes(new File(filename).toPath());
		
		//byte[] decoded = Base64.getDecoder().decode(keyBytes);
		//println(new String(decoded));    // Outputs "Hello"
		
		//Base64 codec = new Base64();
		//byte[] decoded = codec.decode(keyBytes);
		//System.out.println( new String(decoded) );    // Outputs "Hello"
		
		PKCS8EncodedKeySpec spec = new PKCS8EncodedKeySpec(keyBytes);
		KeyFactory kf = KeyFactory.getInstance("RSA");
		return kf.generatePrivate(spec);
	}
	
	// public key로 암호화 
	public String encrypt(String str, PublicKey key) throws NoSuchAlgorithmException, NoSuchPaddingException, UnsupportedEncodingException, IllegalBlockSizeException, BadPaddingException, InvalidKeyException{
		this.cipher.init(Cipher.ENCRYPT_MODE, key);
		return Base64.encodeBase64String(cipher.doFinal(str.getBytes("UTF-8")));
	}
	
	// private key로 복호화 
	public String decrypt(String str, PrivateKey key) throws InvalidKeyException, UnsupportedEncodingException, IllegalBlockSizeException, BadPaddingException{
		this.cipher.init(Cipher.DECRYPT_MODE, key);
		return new String(cipher.doFinal(Base64.decodeBase64(str)), "UTF-8");
	}

	// hex to byte[]
	public byte[] hexStringToByteArray(String s) {
	    int len = s.length();
	    byte[] data = new byte[len / 2];
	    for (int i = 0; i < len; i += 2) {
	        data[i / 2] = (byte) ((Character.digit(s.charAt(i), 16) << 4)
	                             + Character.digit(s.charAt(i+1), 16));
	    }
	    return data;
	}
	
	// byte[] to hex
	public String byteArrayToHexString(byte[] bytes){ 
		StringBuilder sb = new StringBuilder(); 
		for(byte b : bytes){ 
			sb.append(String.format("%02X", b&0xff)); 
		} 
		return sb.toString(); 
	} 

	
    
	public static void main(String[] args) throws Exception {
		RSAEncryption ac = new RSAEncryption();
		
		// 공개키
		PublicKey publicKey = ac.getPublic("KeyPair/public.key");
		// 개인키 
		PrivateKey privateKey = ac.getPrivate("KeyPair/private.key");
		
		// 원문 
		String msg = "test message";
		
		
		System.out.println("----------------------------------------------------");
		System.out.println(":::: TEST 암호화 및 복호화 ::::");
		
		// 암호화 원문 BASE64
		String encryptedString = ac.encrypt(msg, publicKey);
		// 복호화
		String decryptedString = ac.decrypt(encryptedString, privateKey);
		
		System.out.println("----------------------------------------------------");
		System.out.println(
				"원문 = " + msg + "\n" +
				"공개키 암호화 = " + encryptedString + "\n" +
				"개인키 복호화 = " + decryptedString
				);
		System.out.println("----------------------------------------------------");
	}
}




결과 :
--------------------------------------------------------------------------
:::: TEST 암호화 및 복호화 ::::
--------------------------------------------------------------------------
원문 = test message
공개키 암호화 = gz2WQHCyHxsPV5IB0xehk8RSbGrhGR86nQRGj09CphxiIAjRsCony8myWfRGJgDVyK6ixuK13gtL/20j4K5c1GcCKxPT9xqYaa6tBxTakho9klHNAO6KhQJK0nGeIQRDpZ1qecB6pPMsRqVVO5rb81NFqbjLKMoqi2tO1f55/iM=
개인키 복호화 = test message
--------------------------------------------------------------------------

 

2020/12/17 - [OS/Mac OS X] - OpenSSL을 이용한 Key 정보 Text 변환

2020/12/17 - [iOS/Tips] - URL query 파싱 및 json string 변환

2020/12/16 - [개발노트] - Code 128 Barcode의 Check Digit 계산방법

2020/12/15 - [iOS/Tips] - 디버깅 차단 처리 (Anti Debug)

2020/12/14 - [iOS/Tips] - bundle id 알아내기

2020/12/12 - [AI/Algorithm] - 2D 충돌처리

2020/12/11 - [iOS/Swift] - UIViewController 스위칭

2020/12/11 - [개발노트] - PlantUML 설치 (Mac OS X)

2020/12/11 - [개발노트] - 특수문자 발음

2020/12/10 - [iOS/Objective-C] - 웹뷰에서 javascript 함수 동기식 호출

2020/12/10 - [iOS/Tips] - Fat Static Library 빌드 (2/2)

2020/12/10 - [iOS/Tips] - Fat Static Library 빌드 (1/2)

2020/12/10 - [iOS/Tips] - Custom UserAgent 설정

2020/12/10 - [iOS/Tips] - CocoaPods 설치 및 제거

2020/12/10 - [iOS/Tips] - Clang diagnostic 경고 무시하기

2020/12/10 - [개발노트] - Bluetooth UUID

 

반응형
블로그 이미지

SKY STORY

,