Teknisk artikel

Exportera Excel-arbetsböcker till PDF/A från Delphi

HotXLS exporterar en arbetsbok eller ett enskilt kalkylblad direkt till PDF/A från Delphi och C++Builder, utan Excel och utan en PDF-skrivardrivrutin. Ange UsePDFA och välj en profil på TXLSPDFExport, så bär den exporterade filen en inbäddad sRGB ICC-profil som sin utdataavsikt, blocket pdfaid för identifiering i sin XMP-metadata, och ett PDF-versionssidhuvud som passar konformitetsnivån

Kravet kommer vanligtvis från en policy för bevarande av handlingar snarare än från en utvecklare. Finansiella rapporter, laboratorieresultat, myndighetsanmälningar och allt en offentlig instans måste behålla i decennier måste lagras i ett format som renderas identiskt om femtio år, och det är vad PDF/A, ISO 19005, existerar för att garantera. Ett kalkylblad är en levande beräkning; en arkiverad kopia av ett kalkylblad måste vara en fast bild av en sådan

Vad gör en PDF till en arkiv-PDF?

Tre krav gör mesta arbetet. Filen måste vara självständig, så varje typsnitt den använder är inbäddat och ingen extern resurs refereras. Dess färg måste vara entydig, vilket betyder en utdataavsikt som namnger den färgrymd filen förberetts för. Och den måste identifiera sig själv, genom XMP-metadata som deklarerar delnumret och konformitetsnivån

HotXLS levererar alla tre. sRGB-profilen bäddas in som ett strömobjekt med tre komponenter och DeviceRGB som sitt alternativ, refererad från en GTS_PDFA1-utdataavsikt vars villkor och identifierare båda namnger sRGB IEC61966-2.1. XMP-paketet bär posterna pdfaid del och konformitet. Profilbyten kompileras in i biblioteket snarare än laddas vid körning, så det finns inget distributionssteg och ingen risk att en saknad fil förvandlar en arkivexport till en vanlig sådan

Diagram över de tre PDF/A-arkiveringskraven och apparaten HotXLS skriver från Delphi: inbäddade FontFile2-delmängder, en GTS_PDFA1 sRGB output intent och pdfaid XMP-identifiering
En PDF/A-fil måste vara självförsörjande, färgentydig och självidentifierande, och HotXLS skriver den matchande utrustningen från egenskapsparet UsePDFA
uses
  lxHandleX, lxPDF;

var
  Book: TXLSXWorkbook;
  Exporter: TXLSPDFExport;
begin
  Book := TXLSXWorkbook.Create;
  Exporter := TXLSPDFExport.Create;
  try
    if Book.Open('quarterly-results.xlsx') <> 1 then
      Exit;

    Exporter.UsePDFA := True;
    Exporter.PDFAProfile := xlsPdfA2b;      // ISO 19005-2 nivå B
    Exporter.DocumentLanguage := 'en-GB';
    Exporter.TagMode := xlsPdfTagsAutomatic;

    if Exporter.SaveAsPDF(Book, 'quarterly-results-archive.pdf') <> 1 then
      raise Exception.Create('archival export failed');
  finally
    Exporter.Free;
    Book.Free;
  end;
end;

Vilken profil bör du välja?

Profiluppräkningen täcker PDF/A-1, PDF/A-2 och PDF/A-3, var och en i en tillgänglig variant och en grundläggande variant. De praktiska skillnaderna är smalare än listan antyder

Nivå B, den grundläggande varianten, garanterar att det visuella utseendet är reproducerbart. Nivå A lägger till strukturella och semantiska krav, huvudsakligen ett taggat strukturträd och en definierad läsordning, så att dokumentet blir tillgängligt för hjälpmedelsteknik. Del 2 lättar på vissa restriktioner i del 1 och tillåter objektströmmar och JPEG 2000; del 3 tillåter dessutom godtyckliga inbäddade filer, vilket är vad format för elektronisk fakturering använder för att bära maskinläsbar XML tillsammans med den mänskligt läsbara sidan

För ett arkiverat kalkylblad är PDF/A-2b det pragmatiska standardvalet: det accepteras brett av arkiv, det kräver inte den taggningsdisciplin nivå A påtvingar ett rutnät av celler, och det tillåter de kompakta strukturer som håller en export av en arbetsbok på 200 sidor från att svälla. Välj del 3 när arkivet också måste bära källdatan som en bilaga, vilket exportören stödjer via AddAttachment

Typsnittsregeln som fångar de flesta

Varje glyf en PDF/A-fil ritar måste komma från ett inbäddat typsnitt. Detta är den enskilt vanligaste anledningen till att en annars korrekt export misslyckas i validering, och felläget är subtilt: filen ser rätt ut på maskinen som skapade den, eftersom den maskinen har typsnittet installerat

HotXLS bäddar in TrueType-delmängder för de typsnitt den använder, men reservvägen till bas-14 finns för fall då ett typsnitt inte kan lösas, och en bas-14-reserv är per definition inte inbäddad. För arkivutdata, konfigurera ett explicit Unicode-typsnittsfil så att reservvägen aldrig tas. Mekaniken bakom delmängdsbildning och reservkedjan beskrivs i TrueType-delmängdsbildning av typsnitt; den praktiska regeln är att testa exporten på en maskin som inte har dina företagstypsnitt installerade

Diagram över PDF/A-typsnittsregeln i HotXLS Delphi-exporter: lösta typsnitt blir inbäddade TrueType-delmängder som validerar överallt, medan base-14-reserven aldrig bäddas in och faller på maskiner utan typsnittet
Ett typsnitt som inte kan lösas faller tillbaka till ett base-14-typsnitt som aldrig bäddas in, så konfigurera en uttrycklig Unicode-typsnittsfil och testa på en maskin utan företagets typsnitt

Vad exportören garanterar, och vad den inte gör

Att vara precis här spelar större roll än att låta säker. Exporten producerar identifieringsapparaten för PDF/A — utdataavsikt, inbäddad ICC-profil, pdfaid-metadata, ett lämpligt versionssidhuvud — och den dirigerar text genom inbäddningsvägen. Den kör inte en fullständig validerare över sin egen utdata, så den genomdriver inte varje förbud i specifikationen, som reglerna kring transparens, vissa annoteringstyper och valfritt innehåll

För en kalkylbladsexport förekommer sådana konstruktioner sällan, vilket är varför den praktiska framgångsgraden är hög. Men hög är inte detsamma som garanterad, och för en genuin arkivpipeline är den korrekta arkitekturen att exportera och sedan validera med ett oberoende verktyg, och behandla ett valideringsmisslyckande som ett pipelinefel snarare än en varning. En jämförbar ansvarsfördelning för PDF-dokument beskrivs i PDF/A-preflight-validering

Layout är en del av arkivtrohet

Ett arkiverat kalkylblad som är tekniskt konformt och visuellt oläsligt har misslyckats med sitt egentliga jobb. Sidinställning väger tyngre i en arkivexport än i en vardaglig utskrift, eftersom ingen kommer att kunna flöda om den senare

Tre inställningar betalar sig själva. Anpassa till bredd förhindrar det klassiska misslyckandet där en tabell 14 kolumner bred anländer som sju sidor med två kolumner var. Upprepade rubrikrader håller varje sida läsbar isolerat. Och explicita utskriftsområden utesluter arbetsanteckningarna som ligger till höger om den verkliga datan. Den fullständiga uppsättningen utskrifts- och sidinställningskontroller täcks i skydd, sidinställning och utskrift

// Arkivklar sidinställning, tillämpad före exporten
Sheet := Book.Sheets[0];
Sheet.PageLandscape := True;
Sheet.FitToWidth := 1;
Sheet.FitToHeight := 0;                  // så många sidor höga som behövs
Sheet.SetPrintArea('A1:N480');
Sheet.PrintTitleRows := '$1:$3';

// Metadata hör hemma i arkivet också
Book.Title := 'Quarterly results 2026 Q2';
Book.Author := 'Finance';

En checklista före den första batchen körs

Bekräfta att filen identifierar sig själv: packa inte upp något, öppna bara PDF:en i en textredigerare och leta efter posterna pdfaid del och konformitet samt utdataavsikten GTS_PDFA1. Bekräfta typsnitten: kontrollera att varje typsnitt i dokumentet rapporterar som inbäddat. Bekräfta utseendet: jämför de exporterade sidorna mot en utskriven kopia, eftersom en anpassa-till-sida-inställning som tyst krymper text till fyra punkter är konform och oanvändbar

Kör sedan en oberoende validerare över ett representativt urval och behåll rapporten. Arkiv efterfrågar allt oftare valideringsbeviset, inte bara filen, och att generera det vid exporttillfället är betydligt billigare än att rekonstruera det år senare. För den vardagliga, icke-arkiverande exportvägen och dess renderingsalternativ, se export av kalkylblad till PDF

Arkivexport, sidinställning och renderingsmotorn bakom dem levereras i ett bibliotek för Delphi och C++Builder; den fullständiga funktionslistan finns på HotXLS Delphi kalkylbladskomponentsidan

Diagram över exportera-sedan-validera-arkitekturen för HotXLS Delphi PDF/A-utdata: exportören skriver identifieringsapparaten, och en oberoende validerare leder filen till arkivet eller väcker ett pipelinefel
Exportören bygger identifieringsapparaten medan en oberoende validator bevisar överensstämmelsen, och en misslyckad validering stoppar batchen i stället för att logga en varning