Skip to content

Instantly share code, notes, and snippets.

@madmonkey
Created April 17, 2024 20:14
Show Gist options
  • Save madmonkey/c5ed95360ea4c4887e779ef405608032 to your computer and use it in GitHub Desktop.
Save madmonkey/c5ed95360ea4c4887e779ef405608032 to your computer and use it in GitHub Desktop.
public static class FileContentResultGenerator
{
public static byte[] ToCsv(this DataSet ds)
{
var sb = new StringBuilder();
for (var i = 0; i < ds.Tables[0].Columns.Count; i++)
{
sb.Append(ds.Tables[0].Columns[i]);
if (i < ds.Tables[0].Columns.Count - 1)
{
sb.Append(",");
}
}
sb.AppendLine();
foreach (DataRow dr in ds.Tables[0].Rows)
{
for (var i = 0; i < ds.Tables[0].Columns.Count; i++)
{
/* for debugging - turns out I wasn't crazy */
//Console.WriteLine($@"{ds.Tables[0].Columns[i]} :: {dr[i]}");
if (!Convert.IsDBNull(dr[i]))
{
var value = dr[i].ToString().ToCsvCell();
sb.Append(value);
}
if (i < ds.Tables[0].Columns.Count - 1)
{
sb.Append(",");
}
}
sb.AppendLine();
}
return Encoding.UTF8.GetBytes(sb.ToString());
}
public static byte[] ToTsv(this DataSet ds)
{
var sb = new StringBuilder();
for (var i = 0; i < ds.Tables[0].Columns.Count; i++)
{
sb.Append(ds.Tables[0].Columns[i]);
if (i < ds.Tables[0].Columns.Count - 1)
{
sb.Append("\t");
}
}
sb.AppendLine();
foreach (DataRow dr in ds.Tables[0].Rows)
{
for (var i = 0; i < ds.Tables[0].Columns.Count; i++)
{
if (!Convert.IsDBNull(dr[i]))
{
var value = dr[i].ToString().Contains("\t")
? $"{dr[i].ToString().Replace("\t", " ")}"
: dr[i];
sb.Append(value);
}
if (i < ds.Tables[0].Columns.Count - 1)
{
sb.Append("\t");
}
}
sb.AppendLine();
}
return Encoding.UTF8.GetBytes(sb.ToString());
}
public static byte[] ToPdf(this DataSet ds, string identifier = "Report")
{
var dataTable = ds.Tables[0];
var pdfDoc = new Document(PageSize.A4, 25, 25, 25, 50);
if (dataTable.Columns.Count > 4) //<-- change to landscape if big enough
{
pdfDoc = new Document(PageSize.A4.Rotate(), 25, 25, 25, 50);
}
var mStream = new MemoryStream();
int pageModOnData = 100;
var writer = PdfWriter.GetInstance(pdfDoc, mStream);
var cols = dataTable.Columns.Count;
var rows = dataTable.Rows.Count;
var pageEventHandler = new TwoColumnHeaderFooter();
writer.PageEvent = pageEventHandler;
pdfDoc.Open();
var para = new Paragraph($"{identifier} as of: " + DateTime.UtcNow.ToString("MM/dd/yyyy"),
new Font(Font.HELVETICA, 12, Font.BOLD))
{
Alignment = Element.ALIGN_CENTER
};
pdfDoc.Add(para);
var pdfTable = new Table(cols, rows)
{
BorderWidth = 1,
Width = 100,
Padding = 1,
Spacing = 1
};
//creating table headers
for (int i = 0; i < cols; i++)
{
Cell cellCols = new Cell();
Font colFont = FontFactory.GetFont(FontFactory.HELVETICA, 8, Font.BOLD);
Chunk chunkCols = new Chunk(dataTable.Columns[i].ColumnName, colFont);
cellCols.Add(chunkCols);
cellCols.Width = 250;
pdfTable.AddCell(cellCols);
}
Int64 rowCount = 0;
for (int k = 0; k < rows; k++)
{
if (rowCount % pageModOnData == 0 && rowCount != 0)
{
rowCount = 0;
pdfDoc.Add(pdfTable);
pdfTable.DeleteAllRows();
}
for (int j = 0; j < cols; j++)
{
Cell cellRows = new Cell();
Font rowFont = FontFactory.GetFont(FontFactory.HELVETICA, 8);
Chunk chunkRows = new Chunk(dataTable.Rows[k][j].ToString(), rowFont);
cellRows.Add(chunkRows);
pdfTable.AddCell(cellRows);
}
rowCount++;
}
pdfDoc.Add(pdfTable);
pdfDoc.Close();
return mStream.ToArray();
}
public static byte[] ToXlsx(this DataSet ds)
{
var excelApp = OfficeOpenXML.GetInstance();
return excelApp.GetExcelStream(ds)?.ToArray() ?? Array.Empty<byte>();
}
public static byte[] GetRequestedBytes(this DataSet ds, enumDownloadType downloadType, string identifier = "")
{
switch (downloadType)
{
case enumDownloadType.CSV:
return ds.ToCsv();
case enumDownloadType.PDF:
return ds.ToPdf(identifier);
case enumDownloadType.XLS:
case enumDownloadType.XLSX:
return ds.ToXlsx();
case enumDownloadType.TSV:
return ds.ToTsv();
default:
throw new ArgumentOutOfRangeException(nameof(downloadType), downloadType, null);
}
}
public static FileContentResult Generate(byte[] data,
string filePrefix = "",
enumDownloadType downloadType = enumDownloadType.XLSX)
{
switch (downloadType)
{
case enumDownloadType.CSV:
return new FileContentResult(data, "text/csv")
{
FileDownloadName = $@"{filePrefix}-{DateTime.Now.ToUniversalIso8601()}.csv",
};
case enumDownloadType.PDF:
return new FileContentResult(data, "application/pdf")
{
FileDownloadName = $@"{filePrefix}-{DateTime.Now.ToUniversalIso8601()}.pdf",
};
case enumDownloadType.XLS:
case enumDownloadType.XLSX:
return new FileContentResult(data,
"application/vnd.openxmlformats-officedocument.spreadsheetml.sheet")
{
FileDownloadName =
$@"{filePrefix}-{DateTime.Now.ToUniversalIso8601()}{(downloadType == enumDownloadType.XLSX
? ".xlsx"
: ".xls")}",
};
case enumDownloadType.TSV:
return new FileContentResult(data, "text/tab-separated-values")
{
FileDownloadName = $@"{filePrefix}-{DateTime.Now.ToUniversalIso8601()}.tsv",
};
default:
throw new ArgumentOutOfRangeException(nameof(downloadType), downloadType, null);
}
}
public static bool IsValidExcelFile(this HttpPostedFileBase file)
{
/* technically all of these file formats can be understood by the reader */
if (file != null)
{
switch (file.ContentType)
{
/* xlsx */
case "application/vnd.openxmlformats-officedocument.spreadsheetml.sheet":
/* xls */
case "application/vnd.ms-excel":
/* xlst */
case "application/vnd.openxmlformats-officedocument.spreadsheetml.template":
/* xlsm */
case "application/vnd.ms-excel.sheet.macroEnabled.12":
/* xltm */
case "application/vnd.ms-excel.template.macroEnabled.12":
/* xlsb */
case "application/vnd.ms-excel.sheet.binary.macroEnabled.12":
return file.ContentLength > 0;
}
}
return false;
}
private static string ToCsvCell(this string column)
{
/* Additional handling required for 'importing' csv into something like excel format*/
var mustQuote = (column.Contains(",") || column.Contains("\"") || column.Contains("\r") ||
column.Contains("\n"));
if (mustQuote)
{
var sb = new StringBuilder();
sb.Append("\"");
foreach (char nextChar in column)
{
sb.Append(nextChar);
if (nextChar == '"')
sb.Append("\"");
}
sb.Append("\"");
return sb.ToString();
}
return column;
}
}
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment