LoginSignup
3
3

More than 1 year has passed since last update.

Javaで無料のタイムスタンプサービスに接続する

Last updated at Posted at 2023-01-18

タイムスタンプサービス

無料でタイムスタンプトークンを発行するサービス、Free TSA Project に接続します。タイムスタンプリクエスト、タイムスタンプレスポンス、タイムスタンプトークンの生成、解析にはBouncy Castle Crypto APIsを使用しました。

タイムスタンププロトコル

タイムスタンプに関わる仕様は、RFC3161RFC5816 で 定義されています。

HTTP通信で行う際の仕様が RFC3161 の 3.4 Time-Stamp Protocol via HTTP に記載されています。

Bouncy Castle Crypto APIs のダウンロード

LATEST JAVA RELEASESから最新版をダウンロードします。

必要なjarファイルは、Provider, ASN.1 Utility Classes, PKIX/CMS/EAC/PKCS/OCSP/TSP/OPENSSL の jar ファイルになります。

タイムスタンプサービスへの接続

今回は、HttpClientクラスを使用して、タイムスタンプサービスへ接続しました。

Content-Type に application/timestamp-query を指定し、ボディ句にDERエンコードした タイムスタンプリクエストを設定し、Postメソッドでタイムスタンプサービスに送ります。

サンプルプログラム

以下は、タイムスタンプサービスに接続し、タイムスタンプレスポンス、タイムスタンプトークンを出力するサンプルプログラムです。

import java.io.FileOutputStream;
import java.io.IOException;
import java.net.URI;
import java.net.http.HttpClient;
import java.net.http.HttpClient.Version;
import java.net.http.HttpRequest;
import java.net.http.HttpResponse;
import java.security.MessageDigest;
import java.security.NoSuchAlgorithmException;

import org.bouncycastle.tsp.TSPAlgorithms;
import org.bouncycastle.tsp.TimeStampRequest;
import org.bouncycastle.tsp.TimeStampRequestGenerator;
import org.bouncycastle.tsp.TimeStampResponse;
import org.bouncycastle.tsp.TimeStampToken;

public class TimeStampHttpClient {

	public static void main(String[] args) {
		
		try {
			//ハッシュ値の生成 SHA-256
			MessageDigest sha256 = MessageDigest.getInstance("SHA-256");
			byte[] sha256Byte = sha256.digest("Hello World".getBytes());
		
			//タイムスタンプリクエストの作成
			TimeStampRequestGenerator reqGen = new TimeStampRequestGenerator();
			reqGen.setCertReq(true);
			TimeStampRequest timeStampReq = reqGen.generate(TSPAlgorithms.SHA256, sha256Byte);
			
			FileOutputStream fos1 = new FileOutputStream("HelloWorld.req");
			fos1.write(timeStampReq.getEncoded());
			fos1.close();
			
			
			//タイムスタンプサービスに接続
		    HttpClient client = HttpClient.newBuilder().version(Version.HTTP_1_1).build();
		    
		    HttpRequest req = HttpRequest.newBuilder()
		      .uri(URI.create("http://eswg.jnsa.org/freetsa")) 
		      .header("Content-Type","application/timestamp-query")
		      .POST(HttpRequest.BodyPublishers.ofByteArray(timeStampReq.getEncoded()))
		      .build();
		    
		    var res = client.send(req, HttpResponse.BodyHandlers.ofByteArray());
		    
		    if ( res.statusCode() != 200 ) {
		    	System.out.println("Error");
		    	System.out.println(res.statusCode());
		    	System.exit(-1);
		    }
		    
		    //タイムスタンプレスポンスの出力
		    FileOutputStream fos2 = new FileOutputStream("HelloWorld.tsr");
		    byte[] resArray = res.body();
		    fos2.write(resArray);
			fos2.close();
			
			TimeStampResponse resp = new TimeStampResponse(resArray);
			TimeStampToken token = resp.getTimeStampToken();
			
			//タイムスタンプトークンの出力
		    FileOutputStream fos3 = new FileOutputStream("HelloWorld.tst");
		    fos3.write(token.getEncoded());
			fos3.close();
			
		}
		catch (NoSuchAlgorithmException e) {
			e.printStackTrace();
		} 
		catch (IOException e) {
			e.printStackTrace();
		}
		catch (Throwable e) {
			e.printStackTrace();
		}
	}
}
3
3
0

Register as a new user and use Qiita more conveniently

  1. You get articles that match your needs
  2. You can efficiently read back useful information
  3. You can use dark theme
What you can do with signing up
3
3