Попытка отобразить общее количество товаров в объекте корзины в FireBase - PullRequest
1 голос
/ 21 июня 2020

Цель состоит в том, чтобы перебрать все элементы в моей базе данных FireBase, прочитать количество каждого элемента, а затем отобразить итоговую сумму во внешнем интерфейсе. У меня проблемы с использованием asyn c каналов для чтения значения объекта. Поскольку использование asyn c, насколько я понимаю, требует массивов. Я попытался сделать cart$ наблюдаемым, чтобы asyn c мог его читать. Но компилятор сообщает мне, что он должен быть установлен как AngularFireObject, поскольку его наличие не позволяет читать его на внешнем интерфейсе. Ниже приведен соответствующий код.

bs-navbar.component.ts

import { Component, OnInit } from '@angular/core';
import { AuthService } from '../auth.service';
import { AppUser } from '../models/app.user';
import { ShoppingCartService } from '../shopping-cart.service';
import { Observable } from 'rxjs';
import { ShoppingCart } from '../models/shopping-cart';
import { AngularFireObject } from '@angular/fire/database/database';


@Component({
  selector: 'bs-navbar',
  templateUrl: './bs-navbar.component.html',
  styleUrls: ['./bs-navbar.component.css']
})
export class BsNavbarComponent implements OnInit {
  appUser: AppUser
  cart$: Observable<ShoppingCart>

  constructor(public auth: AuthService, private shoppingCartService: ShoppingCartService) {
    auth.appUser$.subscribe(appUser => this.appUser = appUser)
  }

  logout() {
    this.auth.logout()
  }

  async ngOnInit() {
    this.cart$ =  (await this.shoppingCartService.getCart())  
  }
}

В строке this.cart$ = (await this.shoppingCartService.getCart()) появляется следующая ошибка: Тип 'AngularFireObject' не содержит следующих свойств из типа «Наблюдаемый»: _isScalar, источник, оператор, лифт и еще 6.ts (2740)

shopping-cart.ts

import { ShoppingCartItem } from './shopping-cart-item';

export class ShoppingCart {
    items?: ShoppingCartItem[] = []

     get totalItemsCount() {
        let count = 0
        for (let productId in this.items) {
            count += this.items[productId].quantity
        }
        return count
    }
}

shopping-cart.service.ts

import { Injectable } from '@angular/core';
import { AngularFireDatabase, AngularFireObject } from '@angular/fire/database';
import { Product } from './models/product';
import { take, switchMap, map } from 'rxjs/operators';
import { Observable } from 'rxjs';
import { removeSummaryDuplicates } from '@angular/compiler';
import { ShoppingCart } from './models/shopping-cart';


@Injectable({
  providedIn: 'root'
})
export class ShoppingCartService {

  constructor(private db: AngularFireDatabase) { }

  private create() {
    console.log('Create a cart item was called')
    return this.db.list('/shopping-carts/').push({
      dateCreated: new Date().getTime()
    })
  }

  getItem(cartId: string, productId: string) {
    return this.db.object('/shopping-carts' + cartId + '/items' + productId)
  }

  async getCart(): Promise<AngularFireObject<ShoppingCart>> {
    let cartId = await this.getOrCreateCartId()
    console.log(this.db.object('/shopping-carts/' + cartId))
    return this.db.object('/shopping-carts/' + cartId)
  }

  private async getOrCreateCartId(): Promise<string> {
    let cartId = localStorage.getItem('cartId')
    if (cartId) return cartId

    let result = await this.create()
    localStorage.setItem('cartId', result.key)
    return result.key
  }

  async removeFromCart(product: Product) {
    let cartId = await this.getOrCreateCartId()
    let item$ = this.db.object('/shopping-carts/' + cartId + '/items/' + product.key)
    item$.snapshotChanges().pipe(take(1)).subscribe(item => {
      if (item.payload.exists()) item$.update({ product: product, quantity: item.payload.exportVal().quantity - 1 })
      else item$.set({ product: product, quantity: 1 })
    })
  }

  async addToCart(product: Product) {
    let cartId = await this.getOrCreateCartId()
    //Below we append the items to the shopping cart as a node below the original
    // shoppin-cart key
    let item$ = this.db.object('/shopping-carts/' + cartId + '/items/' + product.key)
    item$.snapshotChanges().pipe(take(1)).subscribe(item => {
      if (item.payload.exists()) item$.update({ product: product, quantity: item.payload.exportVal().quantity + 1 })
      else item$.set({ product: product, quantity: 1 })
    })
  }
}

shopping-cart.component. html

<h1>Shopping Cart</h1>
<ng-container *ngIf="cart$ | async as cart">
    <p>
        You have {{ cart.totalItemsCount}} items in your shopping cart.
    </p>
</ng-container>

Именно в {{ cart.totalItemsCount}} я пытаюсь отобразить общее количество товаров в этой конкретной корзине. Ниже прилагается База данных firebase в реальном времени для предметов и их количества

...