Streams en bestandsbijlagen
Streams en bestandsbijlagen
Voorbij de basis Document.Open/Document.Save overloads, geeft Aspose.PDF FOSS voor .NET je fijnere controle over hoe bytes in en uit een document bewegen — uitbreidbare in-memory buffers voor zeer grote bestanden, en een toegewijde API voor het insluiten, inspecteren en extraheren van bestandsbijlagen via FileSpecification en EmbeddedFileCollection.
In-memory buffers uitbreiden voorbij 2GB
MemoryStream slaat zijn gegevens op in één doorlopend array, wat een limiet heeft rond de 2GB. OptimizedMemoryStream slaat gegevens op in blokken van vaste grootte, zodat het veel grotere documenten kan bevatten wanneer je een PDF volledig in het geheugen opslaat of bouwt.
using Aspose.Pdf;
using var doc = Document.Open("large-input.pdf");
using var buffer = new OptimizedMemoryStream();
doc.Save(buffer);
buffer.Seek(0, SeekOrigin.Begin);
byte[] allBytes = buffer.ToArray();
Console.WriteLine($"Buffer length: {buffer.Length}");Je kunt er ook direct naar schrijven, op dezelfde manier als met elke Stream:
using var buffer = new OptimizedMemoryStream();
byte[] chunk = System.Text.Encoding.UTF8.GetBytes("raw content chunk");
buffer.Write(chunk, 0, chunk.Length);
buffer.WriteByte(0x0A);
buffer.SetLength(buffer.Length);Een bestand direct insluiten vanuit een stream
FileSpecification kan een Stream omsluiten in plaats van dat je de bijlage eerst in een byte[] moet bufferen. Dit is handig wanneer de bron van de bijlage zelf een stream is, zoals een geopende bestandshandle.
using Aspose.Pdf;
using var doc = Document.Open("input.pdf");
using var attachmentStream = File.OpenRead("report.csv");
using var spec = new FileSpecification(attachmentStream, "report.csv", "Quarterly report data");
spec.MimeType = "text/csv";
spec.AFRelationship = AFRelationship.Data;
spec.Encoding = FileEncoding.Zip;
doc.EmbeddedFiles.Add(spec);
doc.Save("with-attachment.pdf");Een bestand insluiten vanuit ruwe bytes
Document.AddEmbeddedFile is een handige methode om een bestand direct vanuit een byte array in te sluiten, zonder rechtstreeks een FileSpecification te construeren.
using Aspose.Pdf;
using var doc = Document.Open("input.pdf");
byte[] fileData = File.ReadAllBytes("appendix.docx");
doc.AddEmbeddedFile(
"appendix.docx",
fileData,
"Supporting appendix",
"application/vnd.openxmlformats-officedocument.wordprocessingml.document",
true,
DateTime.Now,
DateTime.Now);
doc.Save("with-appendix.pdf");Opsommen en extraheren van ingebedde bestanden
Document.EmbeddedFiles is een EmbeddedFileCollection die je kunt opsommen. Elke entry is een FileSpecification, en GetData() retourneert de ruwe bytes van de bijlage.
using Aspose.Pdf;
using var doc = Document.Open("with-attachment.pdf");
if (doc.HasEmbeddedFiles)
{
foreach (FileSpecification file in doc.EmbeddedFiles)
{
Console.WriteLine($"{file.Name} ({file.Size} bytes, {file.MimeType})");
byte[] contents = file.GetData();
File.WriteAllBytes(file.Name, contents);
}
}Vinden, inspecteren en verwijderen van bijlagen
Gebruik FindByName om een enkele bijlage op te zoeken, Params om de metadata ervan te lezen, en Delete/DeleteByKey om deze te verwijderen.
using Aspose.Pdf;
using var doc = Document.Open("with-attachment.pdf");
FileSpecification? found = doc.EmbeddedFiles.FindByName("report.csv");
if (found?.Params is FileParams info)
{
Console.WriteLine($"{found.Name}: {info.Size} bytes, checksum {info.CheckSum}, modified {info.ModDate}");
}
doc.EmbeddedFiles.Delete("report.csv");
Console.WriteLine($"Remaining attachments: {doc.EmbeddedFiles.Count}");
doc.Save("cleaned.pdf");Tips en best practices
- Geef de voorkeur aan
OptimizedMemoryStreambovenMemoryStreamwanneer een in-memory document groter kan worden dan 2GB —MemoryStreamgooit een uitzondering zodra de onderliggende array die limiet bereikt. - Verwijder
FileSpecificationinstanties (en eventuele streams die je handmatig voor hen hebt geopend) –FileSpecificationimplementeertIDisposable. - Controleer
Document.HasEmbeddedFilesvoordat jeEmbeddedFilesitereert om onnodige enumeratie op documenten zonder bijlagen over te slaan. - Stel
MimeTypeenAFRelationshipin op elkeFileSpecificationzodat downstream PDF-consumenten bijlagen correct kunnen classificeren. - Gebruik
EmbeddedFileCollection.FindByNamevoor een enkele benoemde opzoekactie in plaats van een handmatige lus te schrijven.
Veelvoorkomende problemen
| Probleem | Oorzaak | Oplossing |
|---|---|---|
OutOfMemoryException opslaan van een groot document naar een stream | MemoryStream is beperkt tot één enkele ~2GB onderliggende array | Sla in plaats daarvan op naar OptimizedMemoryStream |
FileSpecification.GetData() retourneert een lege array | De positie van de bronstream werd niet gereset voordat de FileSpecification werd aangemaakt | Stel de stream in op positie0 (of open hem opnieuw) voordat je deze doorgeeft aan FileSpecification |
EmbeddedFiles.FindByName retourneert null | De naam van de bijlage komt niet exact overeen (opzoeken is op naam gebaseerd) | Itereer over doc.EmbeddedFiles en vergelijk de waarden van Name, of controleer Keys |
| Het verwijderen van een bijlage verwijdert de verkeerde vermelding | Meerdere bijlagen hebben dezelfde naam | Gebruik DeleteByKey met de exacte sleutel uit Keys voor ondubbelzinnige verwijdering |
FAQ
Wat is het verschil tussen MemoryStream en OptimizedMemoryStream?
MemoryStream slaat zijn bytes op in één aaneengesloten array die beperkt is tot ongeveer 2GB. OptimizedMemoryStream slaat data op in vaste-grootte blokken in plaats daarvan, zodat het die limiet kan overschrijden – nuttig voor Document.Save operaties die volledig in het geheugen worden uitgevoerd op zeer grote bestanden.
Kan ik een bestand insluiten zonder het eerst in een byte[] te laden?
Ja. FileSpecification(stream, name, description) accepteert een Stream direct, zodat je kunt insluiten vanaf File.OpenRead(...) of elke andere stream zonder het zelf in het geheugen te bufferen.
Hoe haal ik een ingebed bestand weer uit een document?
Itereer doc.EmbeddedFiles en roep GetData() aan op elke FileSpecification om de ruwe bytes op te halen.
Verwijdert EmbeddedFileCollection.Delete(name) elke bijlage met die naam?
Nee — richt je precies op één bijlage met DeleteByKey en de specifieke sleutel uit Keys als meerdere bijlagen dezelfde naam hebben.
Is FileSpecification veilig om opnieuw te gebruiken in meerdere documenten?
Nee. FileSpecification implementeert IDisposable en omsluit een enkele embedded-file-stream; maak een nieuw exemplaar per bijlage per document.
API Reference Samenvatting
| Klasse / Methode | Beschrijving |
|---|---|
OptimizedMemoryStream | Uitbreidbare in-memory stream die de 2GB-limiet van MemoryStream overschrijdt |
OptimizedMemoryStream.Write | Schrijf bytes naar de buffer |
OptimizedMemoryStream.ToArray | Retourneer de gebufferde bytes als een byte-array |
FileSpecification | Ingebedde bestandsbijlage-descriptor, ondersteund door een stream of byte-data |
FileSpecification.GetData | Haal de ruwe bytes van een ingesloten bestand op |
FileSpecification.Params | Metadata (grootte, checksum, datums) voor het ingesloten bestand |
EmbeddedFileCollection | Collectie van FileSpecification bijlagen op een Document |
EmbeddedFileCollection.FindByName | Zoek een bijlage op naam |
EmbeddedFileCollection.Delete | Verwijder een bijlage op naam |
Document.AddEmbeddedFile | Gemaksmethode om een bestand in te sluiten vanuit ruwe bytes |
Document.EmbeddedFiles | De ingesloten bestandscollectie van het document |
Document.HasEmbeddedFiles | Of het document ingesloten bestanden bevat |
FileParams | Verpakt grootte/checksum/datum metadata voor een ingebedde bestandsstroom |