0

I'm working on an Angular application where I display survey data in a table format. Each row of the table represents a survey response, and I have a timestamp field associated with each response that indicates when it was submitted.

I want to sort the table data based on the timestamp field in descending order, so that the most recent survey responses appear at the top of the table. I've tried a few approaches, but I'm having trouble getting the sorting to work correctly.

Here's a version of my component code:

import { Component, OnInit, inject } from '@angular/core';
import { Breakpoints, BreakpointObserver } from '@angular/cdk/layout';
import { map } from 'rxjs/operators';
import { LegendPosition } from '@swimlane/ngx-charts';
import { AngularFirestore } from '@angular/fire/compat/firestore';

interface SurveyDocument {
  answers: string[];
  lastAnswer: string[];
  // Add other fields if your Firestore documents have more fields
}

@Component({
  selector: 'app-my-dashboard',
  templateUrl: './my-dashboard.component.html',
  styleUrls: ['./my-dashboard.component.scss']
})
export class MyDashboardComponent implements OnInit {
  constructor(private firestore: AngularFirestore) { }

  ngOnInit(): void {
    this.getDataFromFirestore();
  }

  getDataFromFirestore(): void {
    // Initialize count variables
    let loveCount = 0;
    let goodCount = 0;
    let neutralCount = 0;
    let pensiveCount = 0;

    let lastString = "";
    let lastAnswerCounter = 0;

    // Initialize the lastAnswer array
    let lastAnswer: string[] = [];

    // Replace 'survey-data' with the actual name of the collection in your Firestore database
    const subscription = this.firestore.collection('survey-data').get().subscribe(querySnapshot => {
      querySnapshot.forEach(doc => {
        const data = doc.data() as SurveyDocument;
        if (data) {
          if (data.answers) {
            data.answers.forEach((answer, index) => {
              if (answer === 'love') {
                loveCount++;
              } else if (answer === 'good') {
                goodCount++;
              } else if (answer === 'neutral') {
                neutralCount++;
              } else if (answer === 'pensive') {
                pensiveCount++;
              } else {
                // push the answer to the lastAnswer array
                lastAnswer.push(answer);
                lastString = answer;
                lastAnswerCounter = index + 1;
                console.log(lastString);
              }
            });
          } else {
            console.log('The answers array does not exist in the document or is not properly formatted.');
          }
        } else {
          console.log('Document data is undefined.');
        }
      });
      this.chartData = [
        { name: '', value: loveCount },
        { name: '', value: goodCount },
        { name: '', value: neutralCount },
        { name: '', value: pensiveCount },
      ];
      // Update last tableData entry with the last answer data
      this.tableData = [
        ...this.tableData,
        // push data to the tableData array
        { name: `#${lastAnswerCounter}`, value: lastString }

      ];
      this.tableData = Object.keys(lastAnswer).map((key, index) => ({
        name: `#${index + 1}`,
        value: lastAnswer[index]
      }));

      // Log counts
      console.log("love " + loveCount);
      console.log("good " + goodCount);
      console.log("neutral " + neutralCount);
      console.log("pensive " + pensiveCount);

      subscription.unsubscribe();
    });
  }

  private breakpointObserver = inject(BreakpointObserver);
  showLabels: boolean = true;
  showLegend: boolean = true;
  isDoughnut: boolean = false;
  gradient: boolean = true;
  animations: boolean = true;
  colorScheme = {
    domain: ['#5AA454', '#A10A28', '#C7B42C', '#AAAAAA']
  };
  /** Based on the screen size, switch from standard to one column per row */
  cards = this.breakpointObserver.observe(Breakpoints.Handset).pipe(
    map(({ matches }) => {
      if (matches) {
        return [
          { title: 'Grafico Domande 1-3', cols: 2, rows: 1 },
          { title: 'Tabella domande', cols: 2, rows: 1 }
        ];
      }

      return [
        { title: 'Grafico Domande 1-3', cols: 1, rows: 1 },
        { title: 'Tabella domande', cols: 1, rows: 1 }
      ];
    })
  );
  /** Chart Data for Card 1 - Replace this with your actual data for the pie chart */
  chartData = [
    { name: '', value: 0 },
    { name: '', value: 0 },
    { name: '', value: 0 },
    { name: '', value: 0 },
  ];


  tableData: { name: string; value: string | number }[] = [
    { name: '#1', value: '' },
  ];

  tableColumns = ['name', 'value'];
}

How to properly sort the tableData array based on the timestamp field in descending order? Any code examples or step-by-step explanations would be greatly appreciated!

Frank van Puffelen
  • 565,676
  • 79
  • 828
  • 807
heloword
  • 1
  • 1
  • Did you see the documentation on [ordering data](https://firebase.google.com/docs/firestore/query-data/order-limit-data)? It should be someting like `const subscription = this.firestore.collection('survey-data').orderBy("timestamp", "desc").get().subscribe(...` – Frank van Puffelen Aug 06 '23 at 14:10
  • Probably you will have the answer here : https://stackoverflow.com/a/50228103/11472299 – Tim Aug 08 '23 at 11:38

0 Answers0