All notable changes to SheetStream. Versions follow Semantic Versioning.
- Package renamed to
SheetStream.NET(the repository is nowP4Software/SheetStream.NET, the docs live at https://p4software.github.io/SheetStream.NET/). The C# namespace staysSheetStreamandSheetStream.AspNetCorekeeps its name, so upgrading is one package reference:dotnet remove package SheetStreamthendotnet add package SheetStream.NET. The oldSheetStreampackage stays on nuget.org at 0.3.0, marked as renamed.
- Edit small existing workbooks:
ExcelPackage.Edit(path)(in place, atomic replace) orEdit(input, output), thenWorksheets.Edit(name)loads the sheet intoCells[...]: read values, change cells, add rows,Cells.Existing,Cells.Dimension,ExcelCell.Clear(). Untouched cells, rows, formulas (shared and array formulas included), charts, tables and other sheets are written back unchanged. Guarded byPackageOptions.MaxEditableCells(200,000 by default); large files keep using streaming or templates. - Trimming and Native AOT: the
net8.0build isIsTrimmableandIsAotCompatible. A bundled source generator turns[SheetRow] partialtypes into compile-time mappers (ISheetRowMapper<T>,SheetMappers), soLoadFromCollection<T>,LoadFromAsyncEnumerable<T>andExcelReader.Read<T>work without reflection orExpression.Compile; new overloads take a mapper explicitly. Reflection stays the fallback for unmarked types and is now annotated for the trimmer. - Roslyn analyzer shipped inside the package: SS0001 layout setting after rows were written, SS0002
Row()andCells[]mixed on one sheet, SS0003 rows written out of order. Warnings at design time instead of exceptions at run time. - Pivot tables:
Worksheet.AddPivotTableover a table or range written earlier, with row, column, filter and data fields (Sum, Count, Average, Max, Min and more), styles and grand totals. The cache is marked refresh-on-open, so Excel computes the pivot when the file opens; verified against Excel 16 through COM automation (tests/excel-check-pivot.ps1). - Cached formula results:
Worksheet.CacheFormulaResults()opts a sheet into a small evaluator (+ - * / %,SUM,AVERAGE,COUNT,COUNTA,MIN,MAX,ROUND,ABSover cells already written) so viewers that do not calculate show totals instead of blanks. Anything it cannot prove is written without a value, as before. - Async reading (.NET 8+):
ExcelReader.OpenAsync,ReadRowsAsync,ReadAsync<T>andReadDataTableAsync, with cancellation between rows; non-seekable uploads are buffered asynchronously and spill to a temp file above 64 MB. - From the first production migration (LogisticaHQ):
Worksheet.LoadFromArraysreplaces EPPlus'Cells.LoadFromArraysone for one;ExcelPackage.CreateBytesAsynclets a builder await a query per sheet; the migration guide gained "Things EPPlus did for you silently" (the code-page encoding provider that ExcelDataReader imports depend on, AutoFit timing, default date formats). - AutoFit measures columns with a Calibri 11 glyph table calibrated against Excel's own AutoFit (bold, font size, formatted numbers and dates as displayed) and Excel's column-width formula, instead of counting characters;
Worksheet.AutoFitColumns(Func<string, bool, double> measure, ...)andPackageOptions.TextMeasureraccept real font metrics in digit units. - Reader:
ReadMergedRangesandReadHyperlinks(issue #6) read a sheet's merged cells and links, external URLs resolved from the sheet relationships, without parsing the rows. - Benchmarks: 1,000,000-row and 1,000 × 10,000-column write scenarios, and read benchmarks against MiniExcel, ExcelDataReader, ClosedXML, EPPlus and NPOI.
- Web sample (
samples/SheetStream.Sample.Web): a minimal API with a download button, a 50,000-row streamed export and aCells[...]report with charts; double-clickrun.cmd. A DotNetFiddle runs the quick start in the browser. - Trust signals: OpenSSF Scorecard workflow and badge, an SPDX SBOM and a signed build-provenance attestation attached to every release (
gh attestation verify <nupkg> --owner P4Software), a coverage badge served from the docs site, and every GitHub Action pinned to a commit SHA.
- The release workflow signs provenance in a job that only sees the finished packages; the build job stays read-only.
- Template filling:
ExcelPackage.OpenTemplate(template, output)andWorksheets.Open(name)stream rows into a workbook designed in Excel. Everything not touched is copied unchanged; tables, filters, data validations and conditional formats on the first data row stretch over the new rows; template styles are reusable withTemplateStyle("D5"); new styles append to the template's style table; the calculation chain is dropped and the workbook recalculates on open. - Async loading (.NET 8+):
Worksheet.LoadFromAsyncEnumerable(...)streams anIAsyncEnumerable<T>such as an EF Core query, with cancellation. - SheetStream.AspNetCore package:
ExcelResults.Excel(...)andResults.Extensions.Excel(...)return a streamed download from minimal APIs and controllers, with flat memory, accurateContent-Length, correct non-ASCII file names and no synchronous I/O. - Documentation site at https://p4software.github.io/SheetStream.NET/ with guides and the API reference generated from the XML comments.
- Migration guide from EPPlus, built on a real production exporter and compiled as a test.
- Benchmarks project comparing SheetStream with EPPlus 4.5.3.3, ClosedXML, MiniExcel and NPOI.
- Reader fuzz tests, code coverage in CI,
SECURITY.mdand Dependabot.
Closes most of the gap with EPPlus while keeping the streaming, zero-dependency design.
- Excel tables with built-in styles, banding and filter buttons (
Worksheet.AddTable). - Charts: column, bar, line, area, pie, doughnut and scatter, with titles, axis titles, legends, data labels and series colours (
Worksheet.AddChart). - Pictures: PNG, JPEG and GIF, sized by pixels with the aspect ratio kept (
Worksheet.AddPicture). - Conditional formatting: cell value, expression, contains text, duplicates, unique, top / bottom, above / below average, colour scales, data bars and icon sets, with differential styles (
StyleSheet.CreateDifferential). - Data validation: lists, whole numbers, decimals, dates, text length and custom formulas, with prompts and error alerts.
- Hyperlinks to the web, e-mail and places in the workbook, using Excel's built-in Hyperlink style.
- Comments (notes), rich text cells and formulas with cached values.
- Protection: sheet and workbook protection with salted SHA-512 password hashes, plus locked / hidden-formula cell styles.
- Print setup: orientation, paper size, scale, fit to page, margins, header and footer, print titles, print area, gridlines and centering.
- Layout: AutoFit columns, tab colour, gridline visibility, zoom, right-to-left, row and column outlining, hidden rows, sheet visibility (hidden and very hidden).
- Defined names and document properties (title, author, company...).
- Load helpers:
LoadFromCollection(with[SheetColumn]and[DisplayName]),LoadFromDataTableandLoadFromDataReader, optionally as a table. - Random-access cells:
Worksheet.Cells[row, column]for small, irregular layouts. - Streaming reader (
SheetStream.Reading.ExcelReader):ReadRows,Read<T>andReadDataTable, with typed dates, durations and errors. - More cell style options: indent, text rotation and shrink to fit.
- The NuGet package now carries the official P4 Software logo as its icon.
- Marker colours on line and scatter series; the reader rejects cell references beyond column XFD.
- A workbook saved with no sheets now gets an empty "Sheet1", which Excel requires.
Disposeno longer retries a save that already failed, so the original exception is not masked.- Single-cell absolute references are written as
$B$2rather than$B$2:$B$2.
First release: streaming .xlsx writer with shared strings, styles (fonts, fills, borders, number formats, alignment), column widths, frozen panes, AutoFilter, merged cells, formulas and inline strings.