php - 如何将带有 formgroup 值的图像/文件上传到 API?

标签 php angular file-upload angular2-forms

当服务执行http.post时,如何上传图像并将其添加到表单中? 示例产品模块需要名称、价格、封面图片。 我尝试使用许多可以从互联网、论坛等获得的方法。 但对于这个问题仍然没有任何线索。

我正在使用模型驱动表单,并在选择图像时附加它,并且我尝试在发送到 API 之前打印出表单的值。 console.log 结果的附加图像:

enter image description here

仅供引用:我正在使用基于 PHP Laravel 的 API。我尝试从“$request->file('image');”获取图像

有人可以帮我解决这个案子吗? 谢谢。

最佳答案

第 1 部分:通过 FormData 将文件上传到 API

在像 upload.service.ts 这样的服务文件中,您需要创建通过 POST 方法上传文件的函数。以下是此函数的示例:

getUploadHeaders() {
    let headers = new Headers({'Accept': 'application/json'});
    headers.delete('Content-Type');
    return headers;
}    

addNewPost(newPost: FormData): Observable<FormData> {
    const endpoint = 'https://yourApiUrl.com'; 
    return this.http
        .post(endpoint, newPost, { headers: this.getUploadHeaders() })
        .catch((e) => this.handleError(e));
}

现在您应该在组件中创建上传函数,例如upload.component.ts。这是使用 FormData 进行上传功能的示例。

fileToUpload: File = null;

constructor(private uploadService: UploadService) { }

handleFileInput(files: FileList) {
  this.fileToUpload = files.item(0);
}


saveFileToApi() {
  const saveForm: FormData = new FormData();      
  if (this.fileToUpload) {
    // if you need/want to append other fields to API endpoint
    saveForm.append('name', this.name);
    saveForm.append('link', this.link);
    saveForm.append('description', this.description);
    // if you have to append number
    saveForm.append('age', this.age.toString());
    // append image
    saveForm.append('fileFieldNameOnYourApi', this.fileToUpload, this.fileToUpload.name);
  }

  this.uploadService.addNewPost(saveForm).subscribe(() => {
    console.log('Upload success!');
  }, error => {
    console.log('Upload failed!');
  });
}

saveFileToApi 函数中,您还可以附加表单的其他字段。请注意,您应该将数字字段转换为字符串。 Here您可以阅读有关 FormData 对象用法的更多信息。

要通过 FormData 上传文件,您需要 3 个参数:API 端点上的 propertyName、文件和该文件的名称。 在您的 upload.component.html 中,您需要具有如下形式:

<form (ngSubmit)="onSubmit()">     
    <label for="fileField">Chose file to upload</label>
    <input type="file"
           id="fileField"
           name="fileField"
           (change)="handleFileInput($event.target.files)">
    <button type="submit">Speichern</button>
</form>

有关 FormData 的更多详细信息,请阅读 this有关 FormData.append() 的更多信息,请阅读 this .

第 2 部分:从 API 获取上传的图像

您应该在 GET-Request 设置中设置 responseType: ResponseContentType.Blob,因为这样您就可以将图像获取为 blob,并稍后将其转换为 Base64 编码的源。你上面的代码不好。如果您想正确执行此操作,请创建单独的服务以从 API 获取图像。因为在组件中调用HTTP-Request是不好的。

这是一个工作示例:

创建 image.service.ts 或使用第 1 部分中的 upload.service.ts(也许您可以为该服务指定另一个名称)并输入以下代码:

    getImage(imageUrl: string): Observable<File> {
        return this.http
            .get(imageUrl, { responseType: ResponseContentType.Blob })
            .map((res: Response) => res.blob());
    }

现在您需要在 image.component.ts 中创建一些函数来获取图像并在 html 中显示它。

要从 Blob 创建图像,您需要使用 JavaScript 的 FileReader。 这是创建新的 FileReader 并监听 FileReader 的加载事件的函数。结果,该函数返回 base64 编码的图像,您可以在 img src-attribute 中使用该图像:

imageToShow: any;

createImageFromBlob(image: Blob) {
       let reader = new FileReader();
       reader.addEventListener("load", () => {
          this.imageToShow = reader.result;
       }, false);

       if (image) {
          reader.readAsDataURL(image);
       }
}

现在您应该使用您创建的 ImageService 从 api 获取图像。您应该订阅数据并将该数据提供给 createImageFromBlob 函数。这是一个示例函数:

getImageFromService() {
      this.isImageLoading = true;
      this.imageService.getImage(yourImageUrl).subscribe(data => {
        this.createImageFromBlob(data);
        this.isImageLoading = false;
      }, error => {
        this.isImageLoading = false;
        console.log(error);
      });
}

现在您可以在 HTML 模板中使用 imageToShow 变量,如下所示:

<img [src]="imageToShow"
     alt="Place image title"
     *ngIf="!isImageLoading; else noImageFound">
<ng-template #noImageFound>
     <img src="fallbackImage.png" alt="Fallbackimage">
</ng-template>

我希望这个描述很容易理解,并且您可以在您的项目中使用它。

关于php - 如何将带有 formgroup 值的图像/文件上传到 API?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/45690051/

相关文章:

java - 发出在 Java 中异步上传文件的 HTTP 请求的最简单方法是什么?

php - Magento 小计和总计在购物车页面中为空

javascript - 当客户端修改两个按钮的 javascript 函数参数相同时,SQL/PHP 会更新多行

angular - 模板解析错误 : 'ion-col' is not a known element:

html - 如何在primeng自动完成 Angular 8中对建议嵌套列表进行分组

javascript - 将文件输入设置为 HTML 元素的背景

php - Yii:GetText _() 与 Yii::t()

php - 单击 ajax 调用链接的事件处理程序

html - ng2-datepicker 选项不起作用

javascript - 没有服务器组件的文件上传进度条?