2

我知道已经有一个类似的问题,但它没有解决上述错误。

这是我在我的 API 控制器中的 PUT 操作,并且在以下环境中运行良好Swagger

[HttpPut("{id}/upload")]
public async Task<IActionResult> UploadFile(string id, IFormFile file)  
{
    // codes using id above are omitted, nothing to do with the error

    var path = Path.Combine(
        Directory.GetCurrentDirectory(),
        "wwwroot",
        file.FileName
    );

    using (var stream = new FileStream(path, FileMode.Create))  
    {  
        await file.CopyToAsync(stream);
    }

    return Ok();
}

以下是我的 Angular 网页中的代码:

HTML

<input type="file" (change)="setFile($event.target.files)"/>

<button (click)="save()"> Save </button>

打字稿

forUpload: File = null;
@Input() someModel: SomeModel;

// setting of file
setFile(myFile: File){
    if (myFile === null){
      return;
    }
    this.forUpload = myFile[0];
}

// saving
save() {
    const addFileFnc = this.theService.addFile.bind(this.theService);
    addFileFnc(this.someModel, this.forUpload).subscribe(
        () => { this.ref.close(); },
        (e) => { console.log(e); }
    );
}

而且,我的服务是:

addFile(someModel: SomeModel, myFile: File): Observable<any> {
    return this.http.put(`${api_url}/api/somemodels/${someModel.id}/upload`, {
        id: someModel.id,
        file: myFile
    });
}

我也曾经FormData尝试过上述问题的答案,我将我的forUpload文件附加到一个FormData但不幸的是,同样的错误。如果我在媒体类型中没有任何类型的设置,我该如何解决这个问题?

4

2 回答 2

5

您的代码与前面的答案几乎得到了它。我宁愿不更改控制器中的参数,但有一些东西要添加,那就是FromForm属性。所以这将是你的新控制器:

[HttpPut("{id}/upload")]
public async Task<IActionResult> UploadFile(string id, [FromForm] IFormFile file)  
{
    // codes here
}

我同意之前使用的答案FormData,但我会让你setFile()免于任何更改,只是对typescript进行一些添加:

forUpload: File = null;
@Input() someModel: SomeModel;

save() {

    const addFileFnc = this.theService.addFile.bind(this.theService);

    const formdata = new FormData();
    formdata.append("id", this.someModel.id);
    formdata.append("file", this.forUpload);

    addFileFnc(formdata).subscribe(
        () => { this.ref.close(); },
        (e) => { console.log(e); }
    );
}

我没有附加整个someModel,而是只做你的,someModel.id因为我注意到它是你在服务中使用的唯一东西,它将被更改为:

addFile(formdata: FormData): Observable<any> {
    return this.http.put(`${api_url}/api/somemodels/${formdata.get("id")}/upload`, formdata);
}

您的(如此处评论中Error 400 Bad Request所说)是因为在服务中,根据您所遵循的先前答案,正在发送JSONify而不是本身。formdata formdataFormData

于 2019-11-19T11:11:24.150 回答
0

这是我在 ASP.Net Core 和 Angular 中上传文件的方式

在角度方面,您将需要使用 FormData 提交

const formdata = new FormData();
formdata.append("SomeProp ", "somestring");
formdata.append("Image ", myFile); // change your code accordingly here

return this.http.put(`${api_url}/api/somemodels/${someModel.id}/upload`, {
    formdata
});

在服务器端

public class PostViewModel
{
    public string SomeProp { get; set; }
    public IFormFile Image { get; set; }
}

在我的控制器中,我使用FromForm属性

public async Task<IActionResult> SavePost([FromForm]PostViewModel viewModel)

更新:确保像这样在 ASP.Net Core 中启用 CORS 支持

启用 CORS

public void ConfigureServices(IServiceCollection services)
{
      services.AddCors();
      services.AddMvc();
}

public void Configure(IApplicationBuilder app, IHostingEnvironment env, ILoggerFactory loggerFactory)
{
    app.UseCors(
        options => options.AllowAnyOrigin().AllowAnyMethod().AllowAnyHeader()
    );

    app.UseMvc();
}
于 2019-11-18T09:05:46.870 回答