1

I cannot get the document Id in Firestore. I create a randomly generated document id, however, to add a delete function I need that randomly generated ID and cant figure out how to access it. I could also create a custom document id, however, I cannot figure that out either and get errors. So im trying to either find a way to access the document ID the document ID for each item in the list that is printed out in the for loop of the html. Or to find a way to create the doc ids as something unique such as a parsed image url.

import { Component, OnInit } from '@angular/core';
import { Observable, Subject } from 'rxjs';
import { WebcamImage } from 'ngx-webcam';
import { HttpClient } from '@angular/common/http';
import { visionApi } from 'src/environments/environment';
import { Router } from '@angular/router';
import { AngularFireAuth } from '@angular/fire/auth';
import { AuthorizationService } from '../auth-service.service';
import { AngularFirestoreModule, AngularFirestore, AngularFirestoreCollection } from '@angular/fire/firestore';
import { BusinessCardServiceService } from '../business-card-service.service';

interface BusinessCard {

  imageUrl: string;
  name: string;
  email: string;
  phone: string;
  fullText: string;
}

@Component({
  selector: 'app-root',
  templateUrl: './web-cam.component.html',
  styleUrls: ['./web-cam.component.scss']
})
export class WebCamComponent implements OnInit {
  public showWebcam = true;
  public webcamImage: WebcamImage = null;
  private trigger: Subject<void> = new Subject<void>();
  public base64;
  public url = `https://vision.googleapis.com/v1/images:annotate?key=${visionApi.key}`;
  public parsedImage;
  email: string;
  fullText: string;
  name: string;
  phone: string;
  imageUrl: string;
  uid = JSON.parse(localStorage.getItem('uid'));

  private cardCollection: AngularFirestoreCollection<BusinessCard>;
  businessCards: Observable<BusinessCard[]>;

  constructor(private http: HttpClient,
              public afAuth: AngularFireAuth,
              public router: Router,
              private dashService: AuthorizationService,
              private afs: AngularFirestore,
              public bcService: BusinessCardServiceService) {

  }
  public handleImage(webcamImage: WebcamImage): void {
    this.webcamImage = webcamImage;
    this.base64 = this.webcamImage.imageAsBase64;
    this.imageUrl = this.webcamImage.imageAsDataUrl;
    this.parsedImage = this.base64.replace(/^data:image\/(png|jpg|jpeg);base64,/, '');
    const request: any = {
      'requests': [
        {
          'image': {
            'content': this.parsedImage
          },
          'features': [
            {
              'type': 'TEXT_DETECTION'
            }
          ]
        }
      ]
    };
    console.log(request);
    console.log(this.parsedImage);
    this.http.post(
      this.url,
      request
    ).subscribe((results: any) => {
      console.log('RESULTS');
      console.log(results);
      console.log(results.responses[0].fullTextAnnotation.text);
      this.fullText = results.responses[0].fullTextAnnotation.text;
      this.email = JSON.stringify(this.fullText.match(/[a-zA-Z0-9-_.]+@[a-zA-Z0-9-_.]+/));
      this.name = JSON.stringify(this.fullText.match(/([A-Za-z]+),\\s*([A-Za-z]+)\\s*([A-Za-z]+)/));
      this.phone = JSON.stringify(this.fullText.match(/\(?([0-9]{3})\)?([ .-]?)([0-9]{3})\2([0-9]{4})/));
      // tslint:disable-next-line: max-line-length
      this.bcService.create(this.fullText, this.email, this.name, this.phone, this.imageUrl, this.uid);



  });

  }
  public ngOnInit(): void {
      // tslint:disable-next-line: max-line-length
      this.cardCollection = this.afs.collection<BusinessCard>('Users/' + this.uid + '/BusinessCards' + this.uid);
      this.businessCards = this.cardCollection.valueChanges();

  }

  public triggerSnapshot(): void {
    this.trigger.next();
  }

  public get triggerObservable(): Observable<void> {
    return this.trigger.asObservable();
  }
}
import { Injectable } from '@angular/core';
import { AngularFirestoreModule, AngularFirestore, AngularFirestoreCollection, AngularFirestoreDocument } from '@angular/fire/firestore';
import { Observable } from 'rxjs';
import { WebcamImage } from 'ngx-webcam';

interface BusinessCard {

  imageUrl: string;
  name: string;
  email: string;
  phone: string;
  fullText: string;
}



@Injectable({
  providedIn: 'root'
})
export class BusinessCardServiceService {
  uid: string;
  email: string;
  fullText: string;
  name: string;
  phone: string;
  imageUrl: string;
  public webcamImage: WebcamImage = null;
  cardObj: string;
  cardref: AngularFirestoreCollection<BusinessCard>;
  constructor(private afs: AngularFirestore) { }

  cardRef: AngularFirestoreCollection<BusinessCard>;
  card$: Observable<BusinessCard[]>;

  create(fullText: string, email: string, name: string, phone: string, imageUrl: string, uid: string) {
    this.fullText = fullText;
    this.email = email;
    this.name = name;
    this.phone = phone;
    this.imageUrl = imageUrl;
    this.uid = uid;
    this.afs.doc('Users/' + this.uid).set({
    });
    this.afs.collection('Users/' + this.uid + '/BusinessCards' + this.uid).add({
      fullText: this.fullText,
      name: this.name,
      phone: this.phone,
      imageUrl: this.imageUrl,
      email: this.email,
      uid: this.uid
    });


  }

  getCard() {
    return this.afs.collection('Users/' + this.uid + '/BusinessCards' + this.uid).snapshotChanges();
  }

 // deletePolicy(cardId: string){
 //   this.cardId = cardId
 //   this.afs.doc('Users/' + this.uid + '/BusinessCards' + this.uid + this.cardId).delete();

}

<ul>
    <div *ngFor='let card of businessCards | async'>
        <div>{{card.name}} <button class="updateButton">Update Name</button></div>
        <div>{{card.email}} <button class="updateButton">Update Email</button></div>
        <div>{{card.phone}} <button class="updateButton">Update Phone Number</button></div>
        <img [src]='card.imageUrl' />
        <div><button class="DeleteButton">Delete Card</button></div>
    </div>
</ul>
robsiemb
  • 6,157
  • 7
  • 32
  • 46

2 Answers2

0

snapshotChanges() is the function that returns a document metadata containing the document id. Here is an implementation of that function in Angular. Once the ID is obtained, deleting data can be done following these guidelines. Take a look here for a few responses on a similar question.

PYB
  • 503
  • 6
  • 20
0

It looks like you are using valueChanges to subscribe to this query in WebCamComponent

this.cardCollection = this.afs.collection<BusinessCard>('Users/' + this.uid + '/BusinessCards' + this.uid);
this.businessCards = this.cardCollection.valueChanges();

But valueChanges doesn't return all the metadata, it only returns the value. You want to use snapshotChanges (see here) to get the key as well.

You will need to unpack the result, of course to include the id in the BusinessCard. The id will be on the doc.id member of the result, and the rest of the fields you already have will be doc.data member.

As this returns a lot more metadata (not only the id, but also what kind of change was involved, all in a DocumentChangeAction[]), you will need code similar to the example in the document above to unpack it (Note: I have not tested this exact example in the full context of your code, but the general form should work for you):

    this.businessCards = this.cardCollection.snapshotChanges().pipe(
      map(actions => actions.map(a => {
        const data = a.payload.doc.data() as BusinessCard;
        data.id = a.payload.doc.id;  // assumes member `id` is on BusinessCard
        return data;
      }))
    );
robsiemb
  • 6,157
  • 7
  • 32
  • 46