Assine seu primeiro documento em 5 minutos
Um guia completo desde um projeto VCL novo até um envelope XAdES assinado. Funciona com Delphi 7 ao RAD Studio 13 e C++Builder.
Um guia completo desde um projeto VCL novo até um envelope XAdES assinado. Funciona com Delphi 7 ao RAD Studio 13 e C++Builder.
Apenas duas coisas — sgcSign instalado na IDE e um certificado PFX para assinar.
# No PFX yet? Generate a self-signed test cert with OpenSSL:
openssl req -x509 -newkey rsa:2048 \
-keyout key.pem -out cert.pem \
-days 365 -nodes \
-subj "/CN=sgcSign Test"
openssl pkcs12 -export \
-inkey key.pem -in cert.pem \
-out test.pfx \
-password pass:secret
# Now you have test.pfx with password "secret".
Crie um aplicativo VCL Forms na sua IDE. Solte dois memos e um botão no formulário — essa é a interface completa.
TMemo, cole seu XML não assinado aqui.
TMemo, o XML assinado aparece aqui após o clique no botão.
TButton, conectado ao manipulador OnClick no passo 2.
object Form1: TForm1
Caption = 'sgcSign Início rápido'
ClientWidth = 800
ClientHeight = 600
object memoXML: TMemo
Left = 8
Top = 8
Width = 784
Height = 240
end
object memoSigned: TMemo
Left = 8
Top = 288
Width = 784
Height = 300
end
object btnSign: TButton
Left = 8
Top = 256
Caption = 'Sign XML'
end
end
Carregue um provedor PFX, aponte um assinador de documentos para ele com o perfil VeriFactu e chame SignXML.
TsgcPFXKeyProvider importa o .pfx via Windows CNG — assinatura SHA-256 moderna funciona independentemente do CSP original.
TsgcDocumentSigner escolhe o nível XAdES correto com base no perfil.
spVeriFactu seleciona o VeriFactu da AEAT espanhola — XAdES-EPES, B-B, RSA-SHA256, C14N exclusivo.
procedure TForm1.btnSignClick(Sender: TObject);
var
vKeyProvider: TsgcPFXKeyProvider;
vSigner: TsgcDocumentSigner;
begin
vKeyProvider := TsgcPFXKeyProvider.Create(nil);
try
vKeyProvider.FileName := 'certificate.pfx';
vKeyProvider.Password := 'secret';
vKeyProvider.LoadFromFile;
vSigner := TsgcDocumentSigner.Create(nil);
try
vSigner.KeyProvider := vKeyProvider;
vSigner.Profile := spVeriFactu;
memoSigned.Text := vSigner.SignXML(memoXML.Text);
finally
vSigner.Free;
end;
finally
vKeyProvider.Free;
end;
end;
__finally garante que os provedores sejam liberados mesmo se a assinatura lançar uma exceção.
UnicodeString é usado de ponta a ponta — sem conversão ANSI/UTF-8 com que se preocupar.
void __fastcall TForm1::btnSignClick(TObject *Sender)
{
TsgcPFXKeyProvider *vKeyProvider = new TsgcPFXKeyProvider(NULL);
try {
vKeyProvider->FileName = "certificate.pfx";
vKeyProvider->Password = "secret";
vKeyProvider->LoadFromFile();
TsgcDocumentSigner *vSigner = new TsgcDocumentSigner(NULL);
try {
vSigner->KeyProvider = vKeyProvider;
vSigner->Profile = spVeriFactu;
memoSigned->Text = vSigner->SignXML(memoXML->Text);
} __finally {
delete vSigner;
}
} __finally {
delete vKeyProvider;
}
}
Duas units na sua cláusula uses — o provedor PFX e o assinador de documentos.
uses no DelphiCada provedor de chave reside em sua própria unit para que você pague apenas pelo que referencia. sgcSign_DocumentSigner traz a camada de roteamento que escolhe XAdES, PAdES ou CAdES com base na entrada.
uses
Classes, SysUtils, Forms, StdCtrls, Controls,
// sgc
sgcSign_KeyProvider_PFX,
sgcSign_DocumentSigner;
As mesmas units, expostas como cabeçalhos .hpp. O linker do C++Builder resolve as bibliotecas estáticas subjacentes automaticamente.
#include "sgcSign_KeyProvider_PFX.hpp"
#include "sgcSign_DocumentSigner.hpp"
Pressione F9, cole uma nota fiscal no memo superior, clique em Sign XML. O envelope assinado aparece no memo inferior.
Pressione F9 na IDE. O formulário abre com dois memos e um botão. Sem exceções, sem units faltando.
Solte qualquer XML de nota fiscal (ou qualquer XML bem formado) em memoXML. O assinador o normaliza para UTF-8 internamente.
memoSigned agora contém seu XML com um elemento <ds:Signature> envelopado anexado. Salve-o, passe-o por qualquer verificador XAdES — ou use TsgcSignatureVerifier diretamente.
No Delphi 7, string é AnsiString. Use as sobrecargas WideString para transmitir caracteres poloneses, cirílicos ou gregos sem perda.
No Delphi 7, a sobrecarga string passa pelo ACP do sistema. Diacríticos em 'Jarosław' só são transmitidos corretamente quando o ACP do sistema é CP1250. Se o ACP for CP1252, os caracteres ficam corrompidos no XML assinado.
As sobrecargas WideString ignoram o ACP completamente — UTF-16 para UTF-8 via WideCharToMultiByte com CP_UTF8. No Delphi 2009+ ambas as sobrecargas são equivalentes; UnicodeString já é UTF-16.
var
Doc: IXMLDocument; // MSXML6
XML, Signed: WideString; // = MSXML6 DOMString
Sign: TsgcXAdESSigner;
begin
Doc.SaveToXML(XML); // WideString out, no ACP step
Signed := Sign.SignXML(XML); // resolves to WideString overload
// Polish, Cyrillic, Greek round-trip losslessly
end;
Todos os carimbos de hora X.509 / CRL / OCSP / TSA são armazenados como valores UTC TDateTime, correspondendo às especificações ASN.1 subjacentes.
Para exibições ao usuário final, use as propriedades *Local em cada componente (ex.: vCert.NotAfterLocal) ou converta manualmente com sgcUTCToLocal da unit sgcSign_Time.
Isso corresponde à RFC 5280 (X.509), RFC 3161 (TSA) e RFC 6960 (OCSP), que especificam UTC. O helper sgcUTCNow retorna o TDateTime UTC atual para código que precisa comparar carimbos de hora.
uses sgcSign_Time;
// Display certificate validity in local time
Memo1.Lines.Add('Cert expires: ' +
DateTimeToStr(vCert.NotAfterLocal));
Memo1.Lines.Add('Now (UTC): ' +
DateTimeToStr(sgcUTCNow));
// Or convert manually
vLocal := sgcUTCToLocal(vCert.NotAfter);
XAdES é apenas o começo. PAdES, CAdES, perfis, provedores de chave e o servidor centralizado estão todos a um clique.
Conheça toda a superfície da API XAdES, PAdES, CAdES e a infraestrutura de suporte de timestamp + OCSP.
Saiba mais →VeriFactu, FatturaPA, KSeF, FACTUR-X, mais 9 perfis de contratos de trabalho da UE. Troca de jurisdição em uma linha.
Saiba mais →PFX, PEM, repositório Windows, PKCS#11, Azure Trusted Signing, AWS KMS, Google KMS, Vault, Certum, CSC v2.
Saiba mais →Centralize a assinatura em todo o farm de build. API REST, administração web, GitHub Actions, Azure DevOps, Jenkins, Docker.
Saiba mais →