javascript - 使用过滤器或管道将产品类别加载到 Ionic 2 的页面中?

标签 javascript angular typescript ionic2 ionic3

我想创建一个包含 6 个页面的 Ionic 2 应用程序,我不确定是对各个类别页面使用 Pipe 还是 Filter 以及我需要这样做的代码。

每个类别页面可以加载“applecat”类别定义的相关产品。下面是 API,通过 Google 表格以电子表格格式显示产品,以及一个非常快速的主页模型创意:

https://sheetsu.com/apis/v1.0/04c2d2906a10 https://docs.google.com/spreadsheets/d/1RNLXsxTFymqRwq_S538qX1p1PAEDIEA6s5sV8etkfLU/edit?usp=sharing

enter image description here

概述

6 页

  • 主页 - 无需加载任何产品 - 只需链接到页面
  • allproducts - 加载所有产品
  • ipad - 加载 applecat 类别下列为 ipad 的所有项目
  • iphone - 加载 applecat 类别下列为 iphone 的所有项目
  • 键盘 - 加载 applecat 类别下列为 iphone 的所有项目
  • laptop - 加载 applecat 类别下列为 iphone 的所有项目

场景(潜在用户流)

用户打开应用程序,点击主页,然后点击 Ipad 类别链接(加载所有 Ipad 产品) 然后回到首页决定点击All(Loads ALL products),返回并点击另一个页面....

问题

它会加载 2 个数组到内存/控制台吗? 类别页面应该使用过滤器还是管道?代码应如何查找与我现有的 API 调用和产品列表数组相关的管道/过滤器?

vendor

getRemoteData(): any{
        return this.http.get('https://sheetsu.com/apis/v1.0/04c2d2906a10')
                .map(res => res.json());
}

列表页

@Component({
selector: 'page-master',
templateUrl: 'master.html',
providers: [Sheetsu]
})
export class MasterPage {

// declare publicly accessible variable
public sheetsuData: any;

constructor(public navCtrl: NavController, public navParams: NavParams, public sheetsuService: Sheetsu) {}

ionViewDidLoad() {
    this.sheetsuService.getRemoteData()
    .subscribe(response => {
    // assign variable (async)
    this.sheetsuData = response;
    });
}

我看到了一个带有重置的过滤器示例,但不确定它是否适用于这种情况?

 resetData(){
    this.modifiedData = JSON.parse(JSON.stringify(this.originalData));
  }

  filterData(){
    this.modifiedData = this.modifiedData.filter((youtuber) => {
        return youtuber.subscribers > 1000000;
    }
  }

对于如此少的类别页面,也许 Pipe 是每个页面的最佳选择?如果用户浏览所有 6 个页面,则只是多个 API 调用的潜在问题。

首选赏金答案:管道/过滤器/服务的代码,关于最佳解决方案的建议及其原因,甚至更好的是 Github 中的基本工作示例(上面提供了对提供程序和列表 ts 代码的 API 调用)。

可以从 https://github.com/jones98/4cat 查看和 fork 此内容的 Github 存储库

可以在 https://drive.google.com/file/d/0B0QBawqyq1vPZ0o4WEpaa0o0azQ/view 查看当前状态下应用程序的视频(预分类页面工作)

最佳答案

您可以创建一个缓存数据的服务(可能是 5 分钟、30 分钟、1 小时,或任何在您的应用程序上下文中有意义的时间间隔)以避免发出如此多的 http 请求,并且将也只返回你需要的东西,这样你就可以直接在组件/ View 中使用它,而不需要过滤任何东西。

这不仅会减少对服务器发出的大量无用的 http 请求,而且还会使应用速度更快,因为用户打开产品页面的大部分时间都将使用本地数据。

假设您已经有一个产品类:

export class ProductModel {
    public aw_deep_link: string;
    public product_name: string;
    public apple_cat: string;
    //...
}

然后我们可以像这样创建我们的缓存模型:

class ProductCache {
    public products: Array<ProductModel>;
    public timestamp: number;

    public isValid(): boolean {
        if(!this.products) {
            return false;
        }

        let isExpired = Date.now() - this.timestamp > 1800000; // 30 min
        return !isExpired;
    }
}

然后我们可以在我们的 ProductCategoryService 中使用它

// Angular imports
import { Injectable } from '@angular/core';
import { Http } from '@angular/http';

// Rxjs imports
import { Observable } from 'rxjs';
import 'rxjs/add/operator/map';

@Injectable()
export class ProductCategoryService {

    private cache: ProductCache;
    private apiUrl: string = 'https://sheetsu.com/apis/v1.0/04c2d2906a10';

    constructor(private http: Http) {
        this.cache = new ProductCache();
    }

    public getAll(): Observable<Array<ProductModel>> {
        if(this.cache.isValid()) {
            // Return the products from the cache
            return Observable.of(this.cache.products);
        }

        // Cache is empty/expired, so we need to make the http request
        return this.http.get(this.apiUrl).map(res => res.json()).map(data => {
            // Save the data in the cache for the next time
            this.cache.products = data;
            this.cache.timestamp = Date.now();

            // Return the list of (all) products
            return this.cache.products;
        });
    }

    public getIpadProducts(): Observable<Array<ProductModel>> {
        return this.getAll().filter((product: ProductModel) => {
            return product.apple_cat.toLowerCase() === 'ipad';
        });
    }

    public getIphoneProducts(): Observable<Array<ProductModel>> {
        return this.getAll().filter((product: ProductModel) => {
            return product.apple_cat.toLowerCase() === 'iphone';
        });
    }

    // ...
}

然后只需在每个页面中调用正确的方法,由于产品的缓存,http 请求只会发出一次(或在本例中为每 30 分钟一次)。

可能存在语法错误或拼写错误(我直接在 SO 答案中编码),但这应该让您了解如何处理给定的场景。如果有什么地方不能正常工作,请告诉我,以便我可以帮助您解决问题...

更新:Here您可以找到一些信息(来自 Angular 2 Docs),说明为什么使用管道过滤数据不是一个很好的方法,这就是为什么我建议在服务中这样做,对其他人保持隐藏应用程序的(毕竟,每个类别页面只是想获得它需要显示的数据,它不应该处理所有产品然后只找到它需要在 View 中显示的产品)。

关于javascript - 使用过滤器或管道将产品类别加载到 Ionic 2 的页面中?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/42139522/

相关文章:

javascript - 在 angularjs 应用程序的主页上使用 fullPage.js,必须在路线更改时销毁

javascript - 视觉 : How to mock Auth0 for testing with Vitest

typescript - 如何区分受歧视的联合类型

node.js - 使用 typescript 从回调内部调用方法

javascript - 类型 'Observable<boolean | "“>' is not assignable to type ' 可观察< bool 值>” TS2322

javascript - 谷歌翻译使用链接点击

javascript - JS-replaceWith 不起作用

Angular 2 DI错误

angular - 在运行时读取 Angular 中的服务器环境变量

javascript - 使用 Google Maps API DistanceMatrixService 通过 API 计算我的当前位置和用户位置之间的距离