3

I want to get all users from a Firebase realtime database and sort them by a score property. I've got this to work using the variable
users: FirebaseListObservable<any[]>;
but I get the errors:

Type 'Observable<any[]>' is not assignable to type 'FirebaseListObservable<any[]>'.
Property '_ref' is missing in type 'Observable<any[]>'.

If I change the variable to
users: Observable<any[]>;
then the errors go away, but then I can't use the Angularfire methods like .push() and .update().

My fetching and sorting code (which works) looks like:

this.users = this.af.database.list('/users')
  .map(items => items.sort((a, b) => b.score - a.score));

I would appreciate any advice on how this should be done to avoid the errors, or any preferred way, thank you!

2 Answers 2

11

The FirebaseListObservable implements lift, so RxJS operators - like map - will return a FirebaseListObservable instance.

It's just that - when using TypeScript - the RxJS operators are statically typed to return Observable, so you have to cast to FirebaseListObservable. (Using RxJS does not have to involve TypeScript and if you look at the guidance for adding operators you will see that types are not mentioned.)

You can verify that a FirebaseListObservable instance is returned by looking for the push and update functions you mentioned in your question:

this.users = this.af.database
  .list('/users')
  .map(items => items.sort((a, b) => b.score - a.score)) as FirebaseListObservable<any[]>;
console.log(this.users.push.toString());
console.log(this.users.update.toString());

Note, however, that this will not work for FirebaseListObservable instances that are created as queries. There is an as-yet-unanswered question regarding such instances.

Sign up to request clarification or add additional context in comments.

5 Comments

@LindsayWard This is done on the client side. For large set of data, you might want to sort on the server side. Angularfire2 support a 2nd parameter in list() for sort by.
Thanks @Sam. Good to know. I'll try that as well and see if I notice any difference.
I get the following error: [ts] Property 'map' does not exist on type 'FirebaseListObservable<any[]>'. Any ideas please? I am using: "angularfire2": "^2.0.0-beta.7-pre", and "firebase": "^3.6.4", More details: stackoverflow.com/questions/41550132/…
@sam i added the sortBy in the query parameter. how can i specify the sorting - desc or asc?
@Sam, can i use any sort function in the 2nd parameter in list()? Can you please see this quesion stackoverflow.com/q/50112214/4299527 ?
2

You need this example. To watch other opts see Query interface.

this.items = angularFire.database.list('/users', {
  query: {
    orderByChild: 'childPropertyName'
  }
});

export interface Query {
    [key: string]: any;
    orderByKey?: boolean | Observable<boolean>;
    orderByPriority?: boolean | Observable<boolean>;
    orderByChild?: string | Observable<string>;
    orderByValue?: boolean | Observable<boolean>;
    equalTo?: any | Observable<any>;
    startAt?: any | Observable<any>;
    endAt?: any | Observable<any>;
    limitToFirst?: number | Observable<number>;
    limitToLast?: number | Observable<number>;
}

1 Comment

Error: Argument of type '{ query: { orderByChild: string; }; }' is not assignable to parameter of type 'QueryFn'. Object literal may only specify known properties, and 'query' does not exist in type 'QueryFn'

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.