NSwag生成的Angular客户端向.NET Core传文件失败求助
.NET Core 6 + Angular NSwag 文件上传问题解决指引
问题场景
后端基于.NET Core 6开发,控制器通过[FromForm]接收包含IFormFile的模型,接口在Swagger UI中可正常调用,但NSwag生成的Angular客户端调用时抛出错误:FormData.append: Argument 2 is not an object。
相关代码
后端控制器代码
[HttpPost("single-file"), DisableRequestSizeLimit] public async Task<ActionResult<int>> Create([FromForm] CreateUploadedDocumentModel model) { // 业务逻辑实现 }
前端文件选择组件
<input (change)="selectFiles($event)" class="form-control" type="file" id="formFileMultiple">
前端调用客户端代码
this.uploadClient.create(1, file, file.name).subscribe( result => { console.log(result); }, err => { this.message = 'Could not upload the file:' + file.name; });
NSwag生成的客户端代码片段
create(consultantId: number | undefined, file: FileParameter | null | undefined, fileName: string | null | undefined): Observable<number> { let url_ = this.baseUrl + "/api/UploadedDocuments/single-file"; url_ = url_.replace(/[?&]$/, ""); const content_ = new FormData(); if (consultantId === null || consultantId === undefined) throw new Error("The parameter 'consultantId' cannot be null."); else content_.append("ConsultantId", consultantId.toString()); if (file !== null && file !== undefined) content_.append("File", file.data, file.fileName ? file.fileName : "File"); if (fileName !== null && fileName !== undefined) content_.append("FileName", fileName.toString()); // 后续请求逻辑 }
问题原因
NSwag生成的客户端方法期望接收FileParameter类型参数,但前端直接传入了原生File对象,导致客户端代码访问file.data时出现未定义的情况,触发FormData参数错误。
解决方案
1. 手动包装File对象为FileParameter
在调用客户端方法前,将原生File对象包装成客户端要求的FileParameter类型:
// 定义FileParameter结构(若生成代码未自动包含) interface FileParameter { data: File; fileName?: string; } // 文件选择后的处理逻辑 selectFiles(event: Event) { const fileList = (event.target as HTMLInputElement).files; if (fileList) { Array.from(fileList).forEach(file => { // 包装成符合要求的FileParameter const fileParam: FileParameter = { data: file, fileName: file.name }; // 调用客户端上传方法 this.uploadClient.create(1, fileParam, file.name).subscribe( result => console.log(result), err => this.message = `Could not upload the file: ${file.name}` ); }); } }
2. 优化NSwag生成配置(避免手动包装)
调整NSwag生成配置,让客户端直接支持原生File类型传入:
- 在
nswag.json中添加或修改以下配置:{ "runtime": "Net60", "documentGenerator": { "aspNetCoreToOpenApi": { "operationNameGenerator": "AspNetCoreOperationNameGenerator", "output": "swagger.json" } }, "codeGenerator": { "angular": { "generateClientClasses": true, "generateClientInterfaces": false, "formDataToClass": true, "generateHttpClientType": true, "useTransformOptionsMethod": true, "useGetBaseUrlMethod": true, "className": "{controller}Client", "moduleName": "App", "output": "src/app/api-client.ts" } } } - 重新生成客户端代码后,方法将直接支持传入原生
File对象,无需手动包装。
3. 校验后端模型属性名
确保CreateUploadedDocumentModel的属性名与客户端FormData的键名完全匹配:
public class CreateUploadedDocumentModel { public int ConsultantId { get; set; } public IFormFile File { get; set; } public string? FileName { get; set; } }
属性名需与客户端代码中content_.append的键名(如"ConsultantId"、"File")一致,避免因名称不匹配导致参数绑定失败。
内容的提问来源于stack exchange,提问作者Kasper Sölvström
相关产品推荐
相关产品推荐

