package org.demoiselle.signer.policy.impl.pades.pkcs7.impl;

import static org.junit.Assert.assertTrue;

import java.io.ByteArrayInputStream;
import java.io.ByteArrayOutputStream;
import java.io.File;
import java.io.FileInputStream;
import java.io.FileOutputStream;
import java.io.IOException;
import java.io.InputStream;
import java.security.KeyStore;
import java.security.PrivateKey;
import java.security.Provider;
import java.security.Security;
import java.security.KeyStore.Builder;
import java.security.cert.Certificate;
import java.util.Calendar;
import java.util.Enumeration;

import org.apache.commons.codec.binary.Base64;
import org.apache.pdfbox.pdmodel.PDDocument;
import org.apache.pdfbox.pdmodel.interactive.digitalsignature.PDSignature;
import org.apache.pdfbox.pdmodel.interactive.digitalsignature.SignatureInterface;
import org.demoiselle.signer.core.keystore.loader.KeyStoreLoader;
import org.demoiselle.signer.core.keystore.loader.factory.KeyStoreLoaderFactory;
import org.demoiselle.signer.cryptography.DigestAlgorithmEnum;
import org.demoiselle.signer.policy.engine.factory.PolicyFactory;
import org.demoiselle.signer.policy.impl.cades.SignerAlgorithmEnum;
import org.junit.Test;


@SuppressWarnings("unused")
public class PDFSigner {

	//@Test
	public void testComFile() {
		
		// INFORMAR o arquivo
		//
		//String fileDirName = "C:\\Users\\{usuario}\\arquivo_assinar";
		String fileDirName = "/";
		byte[] fileToSign = readContent(fileDirName);

		ByteArrayInputStream toSign = new ByteArrayInputStream(fileToSign);
		String filePDFAssinado = "/";
		
		try {
				this.doSigner(toSign, filePDFAssinado);
		} catch (Throwable e) {
			e.printStackTrace();
			assertTrue(false);
		}		
		assertTrue(true);
	}

	
	
	//@Test
	public void testComBase64() {
		
		String filePDFAssinado = "/home/signer/Documentos/novo_assinado.pdf";
		String imgPDF = "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MCBvYmoKPDwvSVRYVCgyLjEuNykvVHlwZS9QYWdlcy9Db3VudCAxL0tpZHNbNiAwIFJdPj4KZW5kb2JqCjcgMCBvYmoKPDwvVHlwZS9DYXRhbG9nL1BhZ2VzIDUgMCBSPj4KZW5kb2JqCjggMCBvYmoKPDwvUHJvZHVjZXIoaVRleHQgMi4xLjcgYnkgMVQzWFQpL01vZERhdGUoRDoyMDE3MTAzMDA5NDkxOC0wMicwMCcpL0NyZWF0aW9uRGF0ZShEOjIwMTcxMDMwMDk0OTE4LTAyJzAwJyk+PgplbmRvYmoKeHJlZgowIDkKMDAwMDAwMDAwMCA2NTUzNSBmIAowMDAwMDAwMDE1IDAwMDAwIG4gCjAwMDAwMDQzMTcgMDAwMDAgbiAKMDAwMDAwNDQxMCAwMDAwMCBuIAowMDAwMDAzNTE2IDAwMDAwIG4gCjAwMDAwMDQ0OTggMDAwMDAgbiAKMDAwMDAwNDEyOCAwMDAwMCBuIAowMDAwMDA0NTYxIDAwMDAwIG4gCjAwMDAwMDQ2MDYgMDAwMDAgbiAKdHJhaWxlcgo8PC9Sb290IDcgMCBSL0lEIFs8ZTE4NDQwM2JhY2FhNDVlMDAzYzEwNzY0M2E1OTk0Yjg+PGQwMGY0YTA3ZGQ2MjI2NmMyMTBmNDY0MDVhMTdjMjFhPl0vSW5mbyA4IDAgUi9TaXplIDk+PgpzdGFydHhyZWYKNDcyOAolJUVPRgo=";
		
		try {
				ByteArrayInputStream toSign = new ByteArrayInputStream(Base64.decodeBase64(imgPDF));
				this.doSigner(toSign, filePDFAssinado);
		} catch (Throwable e) {
			e.printStackTrace();
			assertTrue(false);
		}		
		assertTrue(true);
	}
	
	private void doSigner(ByteArrayInputStream toSign, final String signedFile) throws Throwable {
			
			
			ByteArrayOutputStream baos = new ByteArrayOutputStream();
			Long documentId = Long.parseLong("300");
			byte[] buf = new byte[1024];
			int n = 0;

			while ((n = toSign.read(buf)) >= 0) {
				baos.write(buf, 0, n);
			}
			byte[] bytes = baos.toByteArray();			
			InputStream contentForPDF = null;
			
			contentForPDF = new ByteArrayInputStream(bytes);
			
			PDDocument original = PDDocument.load(contentForPDF);
			//original.setVersion(1.5f);
						
			FileOutputStream fos = new FileOutputStream(new File(signedFile));
			PDSignature signature = new PDSignature();
			signature.setFilter(PDSignature.FILTER_ADOBE_PPKLITE);
			signature.setSubFilter(PDSignature.SUBFILTER_ADBE_PKCS7_DETACHED);
			//Calendar calendar =Calendar.getInstance();
			//calendar.set(2017, Calendar.NOVEMBER, 6, 11, 25,30);
			//signature.setSignDate(calendar);
			original.setDocumentId(documentId);
			original.addSignature(signature, new SignatureInterface() {
				public byte[] sign(InputStream contentToSign) throws IOException {
					ByteArrayOutputStream buffer = new ByteArrayOutputStream();
					int nRead;
					byte[] data = new byte[16384];
					while ((nRead = contentToSign.read(data, 0, data.length)) != -1)
					  buffer.write(data, 0, nRead);
					buffer.flush();
					byte[] content = buffer.toByteArray();		
					try {						
						java.security.MessageDigest md = java.security.MessageDigest.getInstance("SHA-512");
						// gera o hash do arquivo
						// devido a uma restrição do token branco, no windws só funciona com 256
						if (org.demoiselle.signer.core.keystore.loader.configuration.Configuration.getInstance().getSO().toLowerCase().indexOf("indows") > 0) {
							md = java.security.MessageDigest.getInstance(DigestAlgorithmEnum.SHA_256.getAlgorithm());
						}
	                	String contentEncoded = Base64.encodeBase64String(content);	                	
	                	System.out.println(contentEncoded);	                	
	                    byte[] hash = md.digest(content);	                    
	                    String hashEncoded = new String(Base64.encodeBase64(hash));	                    
	                    System.out.println(hashEncoded);

	                    //windows e NeoID
	                    KeyStore ks = getKeyStoreTokenBySigner(); 

	                    
	                    //KeyStore ks = getKeyStoreToken();
	                    String alias = getAlias(ks);
	                    
	                    PAdESSigner signer = new PAdESSigner();
	        			signer.setCertificates(ks.getCertificateChain(alias));

	        			// para token
	        			signer.setPrivateKey((PrivateKey) ks.getKey(alias, null));

	        			
	        			signer.setSignaturePolicy(PolicyFactory.Policies.AD_RB_PADES_1_1);
	        			// com carimbo de tempo
	          			//signer.setSignaturePolicy(PolicyFactory.Policies.AD_RT_PADES_1_1);

	        			
	        			// para mudar o algoritimo
	        			signer.setAlgorithm(SignerAlgorithmEnum.SHA512withRSA);
	        			if (org.demoiselle.signer.core.keystore.loader.configuration.Configuration.getInstance().getSO().toLowerCase().indexOf("indows") > 0) {
	        				signer.setAlgorithm(SignerAlgorithmEnum.SHA256withRSA);
	        			}	        			
	        			
	                    
						byte [] assinatura =signer.doHashSign(hash);
						
						return assinatura;
					} catch (Throwable error) {
						error.printStackTrace();
						return null;
					}
				}
			});
			original.saveIncremental(fos);
			original.close();
		}
		

	// Usa o Signer para leitura, funciona para windows e NeoID
	private KeyStore getKeyStoreTokenBySigner() {

		try {
			
			KeyStoreLoader keyStoreLoader = KeyStoreLoaderFactory.factoryKeyStoreLoader();
			KeyStore keyStore = keyStoreLoader.getKeyStore();

			return keyStore;

		} catch (Exception e1) {
			e1.printStackTrace();
			return null;
		} finally {
		}

	}
	
	
	/**
	 * 
	 * Faz a leitura do token em LINUX, precisa setar a lib (.SO) e a senha do token.
	 */
	@SuppressWarnings("restriction")
	private KeyStore getKeyStoreToken() {

		try {
			// ATENÇÃO ALTERAR CONFIGURAÇÃO ABAIXO CONFORME O TOKEN USADO

			// Para TOKEN Branco a linha abaixo
			// String pkcs11LibraryPath =
			// "/usr/lib/watchdata/ICP/lib/libwdpkcs_icp.so";

			// Para TOKEN Azul a linha abaixo
			String pkcs11LibraryPath = "/usr/lib/libeToken.so";

			StringBuilder buf = new StringBuilder();
			buf.append("library = ").append(pkcs11LibraryPath).append("\nname = Provedor\n");
			Provider p = new sun.security.pkcs11.SunPKCS11(new ByteArrayInputStream(buf.toString().getBytes()));
			Security.addProvider(p);
			// ATENÇÃO ALTERAR "SENHA" ABAIXO
			Builder builder = KeyStore.Builder.newInstance("PKCS11", p,	new KeyStore.PasswordProtection("senha".toCharArray()));
			KeyStore ks;
			ks = builder.getKeyStore();

			return ks;

		} catch (Exception e1) {
			e1.printStackTrace();
			return null;
		} finally {
		}

	}
	
	private KeyStore getKeyStoreFileBySigner() {

		try {
			
			// informar o caminho e nome do arquivo
			File filep12 = new File(".p12");
			KeyStoreLoader loader = KeyStoreLoaderFactory.factoryKeyStoreLoader(filep12);
			// Informar a senha
			KeyStore keystore = loader.getKeyStore("senha");
			return keystore;

		} catch (Exception e1) {
			e1.printStackTrace();
			return null;
		} finally {
		}

	}

	
	
	private String getAlias(KeyStore ks) {
		Certificate[] certificates = null;
		String alias = "";
		Enumeration<String> e;
		try {
			e = ks.aliases();
			while (e.hasMoreElements()) {
				alias = e.nextElement();
				System.out.println("alias..............: " + alias);
				System.out.println("iskeyEntry"+ ks.isKeyEntry(alias));
				System.out.println("containsAlias"+ks.containsAlias(alias));
				//System.out.println(""+ks.getKey(alias, null));
				certificates = ks.getCertificateChain(alias);
			}

		} catch (Exception ex) {
			ex.printStackTrace();
		}
		return alias;
	}
	
	private byte[] readContent(String parmFile) {
		byte[] result = null;
		try {
			File file = new File(parmFile);
			FileInputStream is = new FileInputStream(parmFile);
			result = new byte[(int) file.length()];
			is.read(result);
			is.close();
		} catch (IOException ex) {
			ex.printStackTrace();
		}
		return result;
	}
	
}