0%

Abp swagger 上传文件

1. 通过DotNetCore.NPOI获取上传Execl的数据

为了封装一个通用的上传接口,所以返回值类型采用List<object>

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
/// <summary>
/// 将上传的execl文件转换为模型
/// </summary>
/// <param name="httpfile"></param>
/// <param name="isHasHead"></param>
/// <returns></returns>
public static List<object> ConvertExeclToListByHttpFile(HttpRequest httpfile, bool isHasHead = true)
{
var fileStream = httpfile.Form.Files.First();
var exName = Path.GetExtension(fileStream?.FileName);
var modelList = new List<object>();
IWorkbook workbook;
using (var fs = fileStream?.OpenReadStream())
{
workbook = CreateWorkbook(exName, fs);
if (workbook == null) return modelList;
}

var sheetConfig = workbook.GetSheet(ExcelModelConfig);
if (sheetConfig == null) return modelList;
var firstSheet = workbook.GetSheetAt(0);
if (firstSheet == null) return modelList;
var configRow = sheetConfig.GetRow(0);
var columnDictionary = GetColumnDictionary(configRow);
System.Collections.IEnumerator rows = firstSheet.GetRowEnumerator();
if (isHasHead)
{
rows.MoveNext();
}

while (rows.MoveNext())
{
var row = (IRow)rows.Current;
if (row == null) continue;
var model = SetValueToModelHasMsg(row, columnDictionary);

modelList.Add(model);
}

return modelList;
}

通过读取上传的Execl,Execl模板里需要配置一个模型配置的sheet,用于获取上传的字段,并且返回到前端.

通过上传的文件类型,获取execl版本

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
private static IWorkbook CreateWorkbook(string exName, Stream fs)
{
try
{
//2007
if (exName == ".xlsx")
{
return new XSSFWorkbook(fs);
}
// 2003版本
return new HSSFWorkbook(fs);
}
catch (Exception)
{
return null;
}
}

获取模型配置的字段名称

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
private static Dictionary<int, string> GetColumnDictionary(IRow row)
{
Dictionary<int, string> dic = new Dictionary<int, string>();
for (int i = 0; i < row.LastCellNum; i++)
{
ICell cell = row.GetCell(i);
if (cell == null)
{
continue;
}

dic.Add(i, cell.StringCellValue);
}

return dic;
}

根据模型配置,获取Execl中的一行数据

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
private static object SetValueToModelHasMsg(IRow row, Dictionary<int, string> columnDictionary)
{
dynamic d = new System.Dynamic.ExpandoObject();
var model = d as ICollection<KeyValuePair<string, object>>;
//创建属性,并赋值。
foreach (var dicConfig in columnDictionary)
{
try
{
if (string.IsNullOrEmpty(dicConfig.Value))
{
continue;
}

var cell = row.Cells.FirstOrDefault(a => a.ColumnIndex == dicConfig.Key);
if (cell != null)
{
string value = GetValueByCell(cell);
if (string.IsNullOrEmpty(value)) value = string.Empty;
var item = model.FirstOrDefault(a => a.Key == dicConfig.Value);
if (default(KeyValuePair<string, object>).Equals(item) == false)
{
//字段已经存在,覆盖
model.Remove(item);
}
model.Add(new KeyValuePair<string, object>(dicConfig.Value, value));
}
}
catch (Exception ex)
{
var errItem = model.FirstOrDefault(a => a.Key == "Msg");
if (default(KeyValuePair<string, object>).Equals(errItem))
{
model.Add(new KeyValuePair<string, object>("Msg", ex.Message));
}
}

}
var msgItem = model.FirstOrDefault(a => a.Key == "Msg");
if (default(KeyValuePair<string, object>).Equals(msgItem))
{
model.Add(new KeyValuePair<string, object>("Msg", "数据未校验!"));
}

return model;
}

1.1 在Web.Core分布式服务层添加导入控制器

1
2
3
4
5
6
7
8
9
10
11
[AbpMvcAuthorize]
[Route("api/[controller]/[action]")]
public class ExeclFileController : AbpController
{
[HttpPost]
public ActionResult<List<object>> ImportExeclToGetModel(IFormFile file)
{
return ExcelManager.ConvertExeclToListByHttpFile(Request);
}

}

由于在core3.1中添加AbpMvcAuthorize需要在Startup.cs注册

1
2
3
4
//启用校验
app.UseAuthentication();
//支持控制器[AbpMvcAuthorize]特性的权限验证
app.UseAuthorization();

2. 为swagger添加文件上传按钮

注: 目前swagger使用的版本为5.0的预览版
在swagger的AddSwaggerGen回调中,添加

1
options.MapType(typeof(IFormFile), () => new OpenApiSchema() { Type = "file" });