You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

Angular 6多部分表单POST请求未携带附件文件问题求助

Fixing Angular 6 File + Form Data Upload Issues

Let's break down what's going wrong here and fix it step by step:

Core Problems

  1. Direct Object Serialization Fails for Files
    When you pass the Invoice object directly to HttpClient.post(), the File type invoicefile gets serialized to an empty object {} in the JSON payload. JSON doesn't natively support File objects, so this approach will never work for file uploads.

  2. Incorrect Content-Type Header for FormData
    Your revised FormData approach is the right direction, but manually setting Content-Type: multipart/form-data breaks the request. Angular's HttpClient automatically generates the correct multipart/form-data header including the boundary string when you pass a FormData object. If you override this header manually, the boundary is missing, and your backend can't parse the payload correctly (which explains the "all fields missing" error).

Fixed Service Code

Update your InvoiceService to remove the custom header and properly build the FormData:

import { Injectable } from '@angular/core';
import { HttpClient } from '@angular/common/http';
import { Invoice } from '../_models';

@Injectable({ providedIn: 'root' })
export class InvoiceService {
  constructor(private http: HttpClient) { }

  create(invoice: Invoice){
    let payload = new FormData();
    // Append all form fields
    payload.append('amount', invoice.amount);
    payload.append('debtor', invoice.debtor);
    payload.append('serial', invoice.serial);
    payload.append('dateout', invoice.dateout);
    payload.append('expiration', invoice.expiration);
    // Append file - optionally include filename as third parameter for clarity
    if (invoice.invoicefile) {
      payload.append('invoicefile', invoice.invoicefile, invoice.invoicefile.name);
    }

    // Don't set Content-Type header manually! Let Angular handle it automatically
    return this.http.post('/api/v1/invoices/', payload);
  }
}

Instead of relying on the Invoice object, you can directly extract values from your registerForm to avoid potential mismatches:

deliverForm(isValid: boolean) {
  this.submitted = true;
  if (!isValid) {
    return;
  }

  // Extract values directly from the form group
  const formValues = this.registerForm.value;
  const payload = new FormData();
  
  payload.append('amount', formValues.amount);
  payload.append('debtor', formValues.debtor);
  payload.append('serial', formValues.serial);
  payload.append('dateout', formValues.dateout);
  payload.append('expiration', formValues.expiration);
  
  if (this.fileToUpload) {
    payload.append('invoicefile', this.fileToUpload, this.fileToUpload.name);
  }

  this.invoiceService.create(payload as unknown as Invoice)
    .pipe(first())
    .subscribe(
      data => {
        this.alertService.success('Invoice successfully uploaded', true);
        this.router.navigate(['/profile']);
      },
      error => {
        this.alertService.error(error);
      });
}

Key Notes

  • Always use FormData for requests that include files in Angular—this is the standard way to handle multipart file uploads.
  • Never manually set the multipart/form-data header when using FormData—Angular handles this automatically with the correct boundary string, which is critical for backend parsing.
  • Double-check that your backend endpoint is configured to accept multipart/form-data payloads and maps the form field names (including invoicefile) correctly.

内容的提问来源于stack exchange,提问作者Marcus Grass

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.05.29 07:44:37