角度Firestoreから観察可能なのフィルタリング

Bwizard:

私は、データベースの呼び出しにフィルタを適用し、これにいくつかの回答を見てきました。私は一度だけのデータベースを呼び出す必要がありますがFirebaseによって返された観察可能な内にある配列をフィルタリングする方法を考え出すことはできません。

私は、タグのリストで2つの選択ボックスを持っています。私はFirestoreからのアイテムのセット全体を取得したいと観測可能な項目に保存します。次に、選択ボックスの一つは、私はこれらのタグで観察ので項目のみが表示されていることをフィルタしたい変更したとき。

items: Observable<any[]>;
  selectedTag1;
  selectedTag2;

  filteredItems: Observable<any[]>;

  tagName1 = ['', 'TAG1', 'TAG2', 'TAG3', 'TAG4'];
  tagName2 = ['', 'TAG5', 'TAG6', 'TAG7',

  constructor(db: AngularFirestore) {
  this.items = db.collection('items').valueChanges();
  }

  ngOnInit() {
    this.filteredItems = this.items.pipe(
      map((arr => arr.filter(item =>
        item.tags.some(s => s === this.selectedTag1) &&
        item.tags.some(s => s === this.selectedTag2))
        )));
  }

私は、テンプレート上のすべての上映ではアイテムを取得していません。私は、選択ボックスを使用してselectedTagを変更するとき。私はまた、アイテムのないフィルタリングを取得していません。缶誰かが、私はこれを正しく行う方法を提案します。私は一つだけが値を持っている場合、フィルタにselectBoxesを必要とするか、または両方の場合は、値を持っています。

HTML

<select [(ngModel)]="selectedTag1">
  <option  *ngFor="let item of tagName1">{{ item }}</option>
</select>

<select [(ngModel)]="selectedTag2">
  <option  *ngFor="let item of tagName2">{{ item }}</option>
</select>

<ul>
  <li class="text" *ngFor="let item of filteredItems | async">
    {{item.name}}
    <ul>
      <li *ngFor="let tags of item.tags">
        {{tags}}
      </li>
    </ul>
  </li>
</ul>

ITEMS

[
  {
    "name": "Item 1",
    "tags": [
      "TAG1",
      "TAG4",
      "TAG5",
      "TAG6"
    ]
  },
  {
    "name": "Item 2",
    "tags": [
      "TAG2",
      "TAG3",
      "TAG5",
      "TAG7",
    ]
  }
]

私は、選択ボックスが変更されたときに実行される機能を追加しようとしました。

selectChanges() {
    this.filteredItems = this.items.pipe(
      map((arr => {
        console.log(arr);
        console.log(this.selectedTag1);
        arr.filter(item => {
        console.log(item.tags);
        item.tags.some(s => s === this.selectedTag1);} );
      })));
  }

しかし、私はまだ任意のフィルタ処理結果を得ていないのです。

Cshrvn:

あなたは既に推測したように、選択したタグをフィルタリングするべきではない未定義または空です。下に示すように、ちょうどあなたのフィルタリングロジックを微調整:

  filter() {
    this.filteredItems = this.items.pipe(
      map(arr =>
        arr.filter(item => {
          // return true if selectedTag1 or selectedTag2 is empty

          const matchesForTagName1 = this.selectedTag1
            ? item.tags.indexOf(this.selectedTag1) >= 0
            : true;
          const matchesForTagName2 = this.selectedTag2
            ? item.tags.indexOf(this.selectedTag2) >= 0
            : true;
          return matchesForTagName1 && matchesForTagName2;
        })
      )
    );
  }

あなたはStackblitzに完全な例を見ることができるここに

おすすめ

転載: http://43.154.161.224:23101/article/api/json?id=33515&siteId=1