generated from pagopa/pagopa-functions-template
-
Notifications
You must be signed in to change notification settings - Fork 0
Commit
This commit does not belong to any branch on this repository, and may belong to a fork outside of the repository.
feat: Onboarding SDK Crypto Module for Cryptographic Operations (#40)
- Loading branch information
Showing
21 changed files
with
827 additions
and
16 deletions.
There are no files selected for viewing
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,38 @@ | ||
target/ | ||
!.mvn/wrapper/maven-wrapper.jar | ||
!**/src/main/**/target/ | ||
!**/src/test/**/target/ | ||
|
||
### IntelliJ IDEA ### | ||
.idea/modules.xml | ||
.idea/jarRepositories.xml | ||
.idea/compiler.xml | ||
.idea/libraries/ | ||
*.iws | ||
*.iml | ||
*.ipr | ||
|
||
### Eclipse ### | ||
.apt_generated | ||
.classpath | ||
.factorypath | ||
.project | ||
.settings | ||
.springBeans | ||
.sts4-cache | ||
|
||
### NetBeans ### | ||
/nbproject/private/ | ||
/nbbuild/ | ||
/dist/ | ||
/nbdist/ | ||
/.nb-gradle/ | ||
build/ | ||
!**/src/main/**/build/ | ||
!**/src/test/**/build/ | ||
|
||
### VS Code ### | ||
.vscode/ | ||
|
||
### Mac OS ### | ||
.DS_Store |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,60 @@ | ||
# Onboarding SDK Crypto | ||
|
||
This module contains utilities to perform cryptographic operation, such digital signatures. | ||
|
||
See [Confluence page](https://pagopa.atlassian.net/wiki/spaces/SCP/pages/616857618/Firma+digitale+per+mezzo+dei+servizi+di+Aruba) | ||
for integration and documentation details | ||
|
||
|
||
### Hash signature sources | ||
|
||
It is possible to configure different hash signature sources. | ||
|
||
The sources available inside this repository are: | ||
|
||
* Pkcs7HashSignService | ||
|
||
## Pkcs7HashSignService | ||
|
||
It will use the provided private key and certificate, you must set these env variables. | ||
|
||
| Properties | Description | Default | | ||
|--------------------|---------------------------------------------------------------------------------|---------| | ||
| crypto.key.cert | The private key (PEM) used when the pkcs7 hash signature source is <i>local</i> | | | ||
| crypto.key.private | The certificate (PEM) used when the pkcs7 hash signature source is <i>local</i> | | | ||
|
||
|
||
## Installation | ||
|
||
To use this library in your projects, you can add the dependency to your pom.xml if you're using Maven: | ||
|
||
```shell script | ||
<dependency> | ||
<groupId>it.pagopa.selfcare</groupId> | ||
<artifactId>onboarding-sdk-crypto</artifactId> | ||
<version>0.1.0</version> | ||
</dependency> | ||
``` | ||
If you are using Gradle, you can add the dependency to your build.gradle file: | ||
|
||
```shell script | ||
dependencies { | ||
implementation 'it.pagopa.selfcare:onboarding-sdk-crypto:0.1.0' | ||
} | ||
``` | ||
|
||
## Usage | ||
|
||
You can inject the service in the context of Quarkus or Spring (replace @ApplicationScoped with @Bean). | ||
|
||
```java script | ||
@ApplicationScoped | ||
public Pkcs7HashSignService pkcs7HashSignService(){ | ||
return new Pkcs7HashSignServiceImpl(); | ||
} | ||
|
||
@ApplicationScoped | ||
public PadesSignService padesSignService(Pkcs7HashSignService pkcs7HashSignService){ | ||
return new PadesSignServiceImpl(pkcs7HashSignService); | ||
} | ||
``` |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,72 @@ | ||
<project xmlns="http://maven.apache.org/POM/4.0.0" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" | ||
xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/maven-v4_0_0.xsd"> | ||
<modelVersion>4.0.0</modelVersion> | ||
<parent> | ||
<groupId>it.pagopa.selfcare</groupId> | ||
<artifactId>onboarding-sdk-pom</artifactId> | ||
<version>0.1.0</version> | ||
<relativePath>../onboarding-sdk-pom</relativePath> | ||
</parent> | ||
<artifactId>onboarding-sdk-crypto</artifactId> | ||
<name>onboarding-sdk-crypto</name> | ||
<url>http://maven.apache.org</url> | ||
|
||
<dependencies> | ||
|
||
<dependency> | ||
<groupId>jakarta.xml.soap</groupId> | ||
<artifactId>jakarta.xml.soap-api</artifactId> | ||
<version>3.0.1</version> | ||
</dependency> | ||
<dependency> | ||
<groupId>jakarta.xml.ws</groupId> | ||
<artifactId>jakarta.xml.ws-api</artifactId> | ||
<version>4.0.1</version> | ||
</dependency> | ||
<dependency> | ||
<groupId>com.sun.xml.ws</groupId> | ||
<artifactId>jaxws-rt</artifactId> | ||
<version>4.0.2</version> | ||
</dependency> | ||
<dependency> | ||
<groupId>jakarta.activation</groupId> | ||
<artifactId>jakarta.activation-api</artifactId> | ||
</dependency> | ||
<dependency> | ||
<groupId>jakarta.xml.bind</groupId> | ||
<artifactId>jakarta.xml.bind-api</artifactId> | ||
</dependency> | ||
<dependency> | ||
<groupId>com.sun.xml.bind</groupId> | ||
<artifactId>jaxb-impl</artifactId> | ||
<version>4.0.1</version> | ||
</dependency> | ||
<dependency> | ||
<groupId>com.sun.xml.messaging.saaj</groupId> | ||
<artifactId>saaj-impl</artifactId> | ||
<version>3.0.0</version> | ||
</dependency> | ||
<dependency> | ||
<groupId>org.slf4j</groupId> | ||
<artifactId>slf4j-api</artifactId> | ||
</dependency> | ||
|
||
<dependency> | ||
<groupId>org.apache.pdfbox</groupId> | ||
<artifactId>pdfbox</artifactId> | ||
<version>2.0.27</version> | ||
</dependency> | ||
<dependency> | ||
<groupId>org.bouncycastle</groupId> | ||
<artifactId>bcprov-jdk18on</artifactId> | ||
</dependency> | ||
<dependency> | ||
<groupId>org.bouncycastle</groupId> | ||
<artifactId>bcpkix-jdk18on</artifactId> | ||
</dependency> | ||
<dependency> | ||
<groupId>org.apache.commons</groupId> | ||
<artifactId>commons-lang3</artifactId> | ||
</dependency> | ||
</dependencies> | ||
</project> |
10 changes: 10 additions & 0 deletions
10
...rding-sdk-crypto/src/main/java/it/pagopa/selfcare/onboarding/crypto/PadesSignService.java
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,10 @@ | ||
package it.pagopa.selfcare.onboarding.crypto; | ||
|
||
|
||
import it.pagopa.selfcare.onboarding.crypto.entity.SignatureInformation; | ||
|
||
import java.io.File; | ||
|
||
public interface PadesSignService { | ||
void padesSign(File pdfFile, File signedPdfFile, SignatureInformation signInfo); | ||
} |
43 changes: 43 additions & 0 deletions
43
...g-sdk-crypto/src/main/java/it/pagopa/selfcare/onboarding/crypto/PadesSignServiceImpl.java
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,43 @@ | ||
package it.pagopa.selfcare.onboarding.crypto; | ||
|
||
import it.pagopa.selfcare.onboarding.crypto.entity.SignatureInformation; | ||
import it.pagopa.selfcare.onboarding.crypto.utils.CryptoUtils; | ||
import org.apache.pdfbox.pdmodel.PDDocument; | ||
import org.apache.pdfbox.pdmodel.interactive.digitalsignature.PDSignature; | ||
import org.apache.pdfbox.pdmodel.interactive.digitalsignature.SignatureOptions; | ||
|
||
import java.io.File; | ||
import java.io.FileOutputStream; | ||
import java.util.Calendar; | ||
|
||
public class PadesSignServiceImpl implements PadesSignService { | ||
private final Pkcs7HashSignService pkcs7Signature; | ||
|
||
public PadesSignServiceImpl(Pkcs7HashSignService pkcs7Signature) { | ||
this.pkcs7Signature = pkcs7Signature; | ||
} | ||
|
||
public void padesSign(File pdfFile, File signedPdfFile, SignatureInformation signInfo) { | ||
CryptoUtils.createParentDirectoryIfNotExists(signedPdfFile); | ||
|
||
try (FileOutputStream fos = new FileOutputStream(signedPdfFile); | ||
PDDocument doc = PDDocument.load(pdfFile)){ | ||
|
||
PDSignature signature = new PDSignature(); | ||
signature.setFilter(PDSignature.FILTER_ADOBE_PPKLITE); | ||
signature.setSubFilter(PDSignature.SUBFILTER_ADBE_PKCS7_DETACHED); | ||
signature.setName(signInfo.getName()); | ||
signature.setLocation(signInfo.getLocation()); | ||
signature.setReason(signInfo.getReason()); | ||
signature.setSignDate(Calendar.getInstance()); | ||
SignatureOptions signatureOptions = new SignatureOptions(); | ||
signatureOptions.setPreferredSignatureSize(35944); | ||
doc.addSignature(signature, this.pkcs7Signature, signatureOptions); | ||
doc.saveIncremental(fos); | ||
|
||
} catch (Exception var12) { | ||
throw new IllegalStateException(String.format("Something gone wrong while signing input pdf %s and storing it into %s", pdfFile.getAbsolutePath(), signedPdfFile.getAbsolutePath()), var12); | ||
} | ||
} | ||
} | ||
|
6 changes: 6 additions & 0 deletions
6
...g-sdk-crypto/src/main/java/it/pagopa/selfcare/onboarding/crypto/Pkcs7HashSignService.java
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,6 @@ | ||
package it.pagopa.selfcare.onboarding.crypto; | ||
|
||
import org.apache.pdfbox.pdmodel.interactive.digitalsignature.SignatureInterface; | ||
|
||
public interface Pkcs7HashSignService extends SignatureInterface { | ||
} |
57 changes: 57 additions & 0 deletions
57
...k-crypto/src/main/java/it/pagopa/selfcare/onboarding/crypto/Pkcs7HashSignServiceImpl.java
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,57 @@ | ||
package it.pagopa.selfcare.onboarding.crypto; | ||
|
||
|
||
import it.pagopa.selfcare.onboarding.crypto.config.LocalCryptoConfig; | ||
import it.pagopa.selfcare.onboarding.crypto.config.LocalCryptoInitializer; | ||
import it.pagopa.selfcare.onboarding.crypto.utils.CMSTypedDataInputStream; | ||
import org.bouncycastle.cert.X509CertificateHolder; | ||
import org.bouncycastle.cert.jcajce.JcaCertStore; | ||
import org.bouncycastle.cms.*; | ||
import org.bouncycastle.cms.jcajce.JcaSignerInfoGeneratorBuilder; | ||
import org.bouncycastle.jce.provider.BouncyCastleProvider; | ||
import org.bouncycastle.operator.ContentSigner; | ||
import org.bouncycastle.operator.OperatorCreationException; | ||
import org.bouncycastle.operator.jcajce.JcaContentSignerBuilder; | ||
import org.bouncycastle.operator.jcajce.JcaDigestCalculatorProviderBuilder; | ||
import org.bouncycastle.util.Store; | ||
|
||
import java.io.*; | ||
import java.security.cert.CertificateEncodingException; | ||
import java.util.Collections; | ||
|
||
/** | ||
* Implementation of {@link Pkcs7HashSignService} which will use provided private and public keys to perform sign operations | ||
*/ | ||
public class Pkcs7HashSignServiceImpl implements Pkcs7HashSignService { | ||
|
||
private final CMSSignedDataGenerator cmsSignGenerator; | ||
|
||
public Pkcs7HashSignServiceImpl() { | ||
try { | ||
LocalCryptoConfig localCryptoConfig = LocalCryptoInitializer.initializeConfig(); | ||
BouncyCastleProvider bc = new BouncyCastleProvider(); | ||
Store<?> certStore = new JcaCertStore(Collections.singletonList(localCryptoConfig.getCertificate())); | ||
|
||
cmsSignGenerator = new CMSSignedDataGenerator(); | ||
ContentSigner sha512Signer = new JcaContentSignerBuilder("SHA256WithRSA").setProvider(bc).build(localCryptoConfig.getPrivateKey()); | ||
|
||
cmsSignGenerator.addSignerInfoGenerator(new JcaSignerInfoGeneratorBuilder( | ||
new JcaDigestCalculatorProviderBuilder().setProvider(bc).build()).build(sha512Signer, new X509CertificateHolder(localCryptoConfig.getCertificate().getEncoded()) | ||
)); | ||
cmsSignGenerator.addCertificates(certStore); | ||
} catch (CertificateEncodingException | OperatorCreationException | CMSException | IOException e) { | ||
throw new IllegalStateException("Something gone wrong while initializing CertStore using provided private and public key", e); | ||
} | ||
} | ||
|
||
public byte[] sign(InputStream is) throws IOException { | ||
try { | ||
CMSTypedDataInputStream msg = new CMSTypedDataInputStream(is); | ||
CMSSignedData signedData = cmsSignGenerator.generate(msg, false); | ||
return signedData.getEncoded(); | ||
} catch (CMSException e) { | ||
throw new IllegalArgumentException("Something gone wrong while performing pkcs7 hash sign", e); | ||
} | ||
} | ||
|
||
} |
26 changes: 26 additions & 0 deletions
26
...k-crypto/src/main/java/it/pagopa/selfcare/onboarding/crypto/config/LocalCryptoConfig.java
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,26 @@ | ||
package it.pagopa.selfcare.onboarding.crypto.config; | ||
|
||
import java.security.PrivateKey; | ||
import java.security.cert.Certificate; | ||
|
||
public class LocalCryptoConfig { | ||
|
||
private Certificate certificate; | ||
private PrivateKey privateKey; | ||
|
||
public Certificate getCertificate() { | ||
return certificate; | ||
} | ||
|
||
public void setCertificate(Certificate certificate) { | ||
this.certificate = certificate; | ||
} | ||
|
||
public PrivateKey getPrivateKey() { | ||
return privateKey; | ||
} | ||
|
||
public void setPrivateKey(PrivateKey privateKey) { | ||
this.privateKey = privateKey; | ||
} | ||
} |
29 changes: 29 additions & 0 deletions
29
...pto/src/main/java/it/pagopa/selfcare/onboarding/crypto/config/LocalCryptoInitializer.java
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,29 @@ | ||
package it.pagopa.selfcare.onboarding.crypto.config; | ||
|
||
import it.pagopa.selfcare.onboarding.crypto.utils.CryptoUtils; | ||
import org.apache.commons.lang3.StringUtils; | ||
|
||
|
||
public class LocalCryptoInitializer { | ||
|
||
private LocalCryptoInitializer(){} | ||
|
||
public static LocalCryptoConfig initializeConfig() { | ||
LocalCryptoConfig config = new LocalCryptoConfig(); | ||
String cert = System.getProperty("crypto.key.cert"); | ||
String pKey = System.getProperty("crypto.key.private"); | ||
|
||
try { | ||
if(StringUtils.isBlank(cert) || StringUtils.isBlank(pKey)){ | ||
throw new IllegalStateException("Define private and cert values in order to perform locally sign operations"); | ||
} | ||
|
||
config.setCertificate(CryptoUtils.getCertificate(cert)); | ||
config.setPrivateKey(CryptoUtils.getPrivateKey(pKey)); | ||
} catch (Exception e) { | ||
throw new IllegalStateException("Something gone wrong while loading crypto private and public keys", e); | ||
} | ||
|
||
return config; | ||
} | ||
} |
Oops, something went wrong.