【问题标题】:Adding Data to Firebase Cloud Firestore and Angular向 Firebase Cloud Firestore 和 Angular 添加数据
【发布时间】:2018-04-17 01:53:43
【问题描述】:

首先我必须说我正在学习 Angular。也许答案太明显了,但我看不到。我在网上搜索过类似问题的回复,但没有找到适合我的答案。

我制作了一个 Angular 模板驱动表单来将产品存储在我的 Firebase Cloud Firestore 数据库中。我创建了一个名为“Product”的模型

product.ts

export class Product {
constructor(
    public code: string,
    public desc: string,
    public stock: number,
    public price: number,
    public off: number,
    public details?: string
) {}

}

然后,我有 product.component.ts

import { Component } from '@angular/core';
import { Product } from './product';
import { AngularFirestore, AngularFirestoreCollection } from 'angularfire2/firestore';
import { Observable } from 'rxjs/Observable';


@Component({
    selector: 'app-admin-product',
    templateUrl: 'product.component.html'
})

export class AdminProductComponent {

model = new Product('', '', 0, 0, 0);
successMsg = 'Data successfully saved.';

productsRef: AngularFirestoreCollection<Product>;
product: Observable<Product[]>;

constructor(private afs: AngularFirestore) {
    this.productsRef = this.afs.collection<Product>('productos');
}

save() {
    this.productsRef.add(this.model).then( _ => alert(this.successMsg));
}

TypeScript 根本不返回错误,一切似乎都正常。但是当我运行我的应用程序并尝试保存表单的数据时,控制台返回下一个错误:

AdminProductComponent.html:51 ERROR 错误:函数 CollectionReference.add() 要求其第一个参数是对象类型,但它是:自定义产品对象

我解决了将自定义对象传递给这样的简单对象的问题:

const product = {
    code: this.model.code,
    desc: this.model.desc,
    stock: this.model.stock,
    price: this.model.price,
    off: this.model.off,
    details: this.model.details
}

并像这样保存数据:

save() {
    this.productsRef.add(product).then( _ => alert(this.successMsg)); }

但我认为这不是正确的解决方案,可能会导致将来调用应用程序时出现问题。

【问题讨论】:

    标签: angular firebase object google-cloud-firestore


    【解决方案1】:

    我使用了 typescript 扩展运算符

      add(wizard: Wizard): Promise<DocumentReference> {
        return this.wizardCollection.add({...wizard});
      }
    

    【讨论】:

      【解决方案2】:

      你可以试试这个方法,希望你用的是最新的打字稿

      product.ts

      export interface Product {
         code: string;
         desc: string;
         stock: number;
         price: number;
         off: number;
         details?: string
      }
      

      在您的 product.component.ts

      export class AdminProductComponent {
      
      model:Product;
      successMsg = 'Data successfully saved.';
      
      productsRef: AngularFirestoreCollection<Product>;
      product: Observable<Product[]>;
      
      constructor(private afs: AngularFirestore) {
          this.productsRef = this.afs.collection<Product>('productos');
      
          this.model = {
            code:'',
            desc:'',
            stock:0,
            price:0,
            off:0
          }
      }
      
      save() {
          this.productsRef.add(this.model).then( _ => alert(this.successMsg));
      }
      

      我认为通过这样做model = new Product('', '', 0, 0, 0); 你会得到一个类的实例而不是对象。

      【讨论】:

      • 谢谢@Hareesh!我刚刚删除了每个 Product 接口索引的“公共”,并用逗号而不是分号分隔并且工作正常!
      【解决方案3】:

      我用过

      save() {
          const param = JSON.parse(JSON.stringify(this.model));
          this.productsRef.add(param).then( _ => alert(this.successMsg));
       }
      

      【讨论】:

      • 这对我也有用..不知道为什么要对对象进行字符串化.. :(
      • 使用 JSON.stringify 将自定义对象转换为字符串。 JSON.parse 解析 JSON 并返回一个对象。由于 JSON 没有(也不能)有任何类型信息,因此返回一个普通对象。
      • 这是个坏主意,因为它会破坏过程中的任何时间戳或 GeoPoints
      【解决方案4】:

      以下代码在您的 Product.component.ts 文件中对我有用

      export class AdminProductComponent {
      
      model:Product;
      successMsg = 'Data successfully saved.';
      
      productsRef: AngularFirestoreCollection<Product>;
      product: Observable<Product[]>;
      
      constructor(private afs: AngularFirestore) {
          this.productsRef = this.afs.collection<Product>('productos');
      }
      
      save() {
          const productData ={};
             
            productData['code']:'123',
            productData['desc']:'yes',
            productData['stock']:500,
            productData['price']:10000,
            productData['off']:10
        
          this.productsRef.add(productData).then( _ => alert(this.successMsg));
      }
      

      【讨论】:

        【解决方案5】:

        您还可以在 Product 类中创建一个深拷贝方法,但这不太优雅。

        export class Product {
          constructor(
            public code: string,
            public desc: string,
            public stock: number,
            public price: number,
            public off: number,
            public details?: string
          ) {}
        
          public getData(): object {
            const result = {};
            Object.keys(this).map((key) => (result[key] = this[key]));
            return result;
          }
        }
        

        然后将其用作:

        this.productsRef.add(product.getData()).then( _ => alert(this.successMsg)); }
        

        【讨论】:

          猜你喜欢
          • 2018-08-11
          • 2020-09-02
          • 2018-03-20
          • 2020-05-05
          • 2022-11-11
          • 1970-01-01
          • 2019-02-02
          • 2023-03-09
          • 1970-01-01
          相关资源
          最近更新 更多