.NET WebAPI生成Excel
Webform中,生成Excel,一般是设置response.Content.Headers.ContentType输出类型为application/vnd.ms-excel,思路都是这样的。
每一个API方法都这样做一下,也是可以的。参考:http://www.cnblogs.com/jizhong/p/3592088.html
更好的做法是,客户端请求的时候,设置Requst.Header的Accept:application/vnd.ms-excel。目的:客户端设置了什么类型,服务端针对性的去调用相应方法,返回相应类型的文件流,可配置,可扩展,Formatter相关不写死在具体方法中,剥离出来。
var _exportToExcel = function (clientId) {
var url = serviceBase + ‘api/clientStatusLog?clientId=‘+clientId;
return $http.get(url, { headers: { Accept: ‘application/vnd.ms-excel‘ }, responseType: ‘arraybuffer‘ }).then(function (response) {
return response;
});
}
服务端在WebApiConfig中添加一种Formatter,我们添加自己写的类的对象,类继承自System.Net.Http.Formatting.BufferedMediaTypeFormatter的MediaTypeFormatter。类中重写了父类的CanWriteType,设置type == typeof(ClientStatusLogReportDto)或者IEnumerable<ClientStatusLogReportDto>时候,CanWriteType方法返回true. 这样在Controller方法中,直接return ClientStatusLogReportDto或List<ClientStatusLogReportDto>, 自己写的Formatter方法会进行生成Excel的逻辑,调用重写父类的WriteToStream等方法,实现生成指定格式的数据,返回响应。
public static class WebApiConfig
{
public static void Register(HttpConfiguration config)
{
// Formatters
config.Formatters.Add(new ClientExcelormatter());
config.Formatters.Add(new ClientStatusLogExcelormatter());
}
}
public class ClientStatusLogExcelormatter: BufferedMediaTypeFormatter
{
private const string MIME_TYPE = "application/vnd.ms-excel";
private HSSFWorkbook workBook;
public ClientStatusLogExcelormatter()
{
// Add the supported media type.
SupportedMediaTypes.Add(new MediaTypeHeaderValue(MIME_TYPE));
}
public override bool CanWriteType(System.Type type)
{
if (type == typeof(ClientStatusLogReportDto))
{
return true;
}
else
{
Type enumerableType = typeof(IEnumerable<ClientStatusLogReportDto>);
return enumerableType.IsAssignableFrom(type);
}
}
public override void WriteToStream(Type type, object value, Stream writeStream, HttpContent content)
{
var clientList = value as IEnumerable<ClientStatusLogReportDto>;
var curRole = OwinContextHelper.GetUserRole();
if (clientList != null)
{
Initialize();
GenerateData(clientList);
workBook.Write(writeStream);
}
else
{
var singleObj = value as ClientStatusLogReportDto;
if (singleObj == null)
{
throw new InvalidOperationException("Cannot serialize type");
}
}
var filename = "clientStatusLog.xls";
content.Headers.ContentType = new MediaTypeHeaderValue(MIME_TYPE);
content.Headers.Add("x-filename", filename);
content.Headers.ContentDisposition = new System.Net.Http.Headers.ContentDispositionHeaderValue("attachment");
content.Headers.ContentDisposition.FileName = filename;
}
private void Initialize()
{
workBook = new HSSFWorkbook();
////create a entry of DocumentSummaryInformation
DocumentSummaryInformation dsi = PropertySetFactory.CreateDocumentSummaryInformation();
dsi.Company = "Centria Healthcare";
workBook.DocumentSummaryInformation = dsi;
////create a entry of SummaryInformation
SummaryInformation si = PropertySetFactory.CreateSummaryInformation();
si.Subject = "Client Status Log Export";
workBook.SummaryInformation = si;
}
private void GenerateData(IEnumerable<ClientStatusLogReportDto> clientList)
{
HSSFSheet oHSSFSheet = (HSSFSheet)workBook.CreateSheet("Client List");
//====================================
string[] columnList = { "Name", "Funding Source", "Current Status", "Status", "Timestamp", "Creator", "Updater"};
int colCount = columnList.Length;
int rowNum = 0;
int colNum = 0;
IFont fontHeader = workBook.CreateFont();
fontHeader.FontName = "Arial";
fontHeader.Boldweight = (short)FontBoldWeight.Bold;
fontHeader.FontHeightInPoints = 10;
IFont fontRow = workBook.CreateFont();
fontRow.FontName = "Arial";
fontRow.FontHeightInPoints = 10;
HSSFCellStyle headerStyle = (HSSFCellStyle)workBook.CreateCellStyle();
HSSFCellStyle normalRowStyle = (HSSFCellStyle)workBook.CreateCellStyle();
headerStyle.SetFont(fontHeader);
headerStyle.BorderBottom = BorderStyle.Thin;
headerStyle.BorderLeft = BorderStyle.Thin;
headerStyle.BorderRight = BorderStyle.Thin;
headerStyle.BorderTop = BorderStyle.Thin;
headerStyle.Alignment = HorizontalAlignment.Center;
headerStyle.VerticalAlignment = VerticalAlignment.Center;
headerStyle.FillForegroundColor = HSSFColor.Black.Index;
normalRowStyle.SetFont(fontRow);
normalRowStyle.BorderBottom = BorderStyle.Thin;
normalRowStyle.BorderLeft = BorderStyle.Thin;
normalRowStyle.BorderRight = BorderStyle.Thin;
normalRowStyle.BorderTop = BorderStyle.Thin;
normalRowStyle.Alignment = HorizontalAlignment.Center;
normalRowStyle.VerticalAlignment = VerticalAlignment.Center;
normalRowStyle.FillForegroundColor = HSSFColor.Black.Index;
HSSFRow header = (HSSFRow)oHSSFSheet.CreateRow(0);
for (int i = 0; i < colCount; i++)
{
HSSFCell oCell = (HSSFCell)header.CreateCell(i);
oCell.SetCellType(CellType.String);
oCell.SetCellValue(columnList[i]);
oCell.CellStyle = headerStyle;
}
//write each item.
foreach (ClientStatusLogReportDto client in clientList)
{
HSSFRow dataRow = (HSSFRow)oHSSFSheet.CreateRow(++rowNum);
colNum = 0;
foreach (PropertyInfo proInfo in typeof(ClientStatusLogReportDto).GetProperties())
{
object v = proInfo.GetValue(client);
string value = string.Empty;
if (v != null)
{
value = v.ToString();
}
HSSFCell cell = (HSSFCell)dataRow.CreateCell(colNum++);
cell.SetCellType(CellType.String);
cell.SetCellValue(value);
cell.CellStyle = normalRowStyle;
}
}
}
public override bool CanReadType(Type type)
{
return false;
}
}
public class ClientStatusLogController : ApiController
{
private readonly IClientStatusLogService _clientStatusLogService;
private readonly IMembershipService _membershipService;
public ClientStatusLogController(IClientStatusLogService clientStatusLogService, IMembershipService membershipService)
{
this._clientStatusLogService = clientStatusLogService;
this._membershipService = membershipService;
}
public List<ClientStatusLogReportDto> GetList(Guid clientId)
{
var list = _clientStatusLogService.GetList(clientId);
var listDto = new List<ClientStatusLogReportDto>();
foreach (var item in list)
{
var dto = Mapper.Map<ClientStatusLog, ClientStatusLogReportDto>(item);
dto.CreatedBy = _membershipService.GetUserRealName(dto.CreatedBy);
dto.CreatedBy = _membershipService.GetUserRealName(dto.ModifiedBy);
listDto.Add(dto);
}
return listDto;
}
}
原文:http://www.cnblogs.com/sen068/p/5557245.html