Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

How to use the loading property in a watchQuery when using the Apollo client for GraphQl

So when i get the response from my query, i can see there is a loading property. But i don't really get why they would pass it along. Because when you get the response it means that the loading is finished, hence the loading will always be false.

Is there a way that i can use this loading property so that i can for example make a loading icon appear when the call is still loading?

I have the following code in an Angular 2 environment:

public apolloQuery = gql`
    query {
        apolloQuery 
    }`;

const sub = this.apollo.watchQuery<QueryResponse>({
    query: this.apolloQuery 
}).subscribe(data => {
    console.log(data);
    sub.unsubscribe();
});

And the log from the data object contains the loading property i was talking about, which is always false.

I know i can make my own boolean property and check this way, but i was just wondering if i could use the built-in loading property that Apollo provides?

like image 635
Martijn van den Bergh Avatar asked May 18 '18 09:05

Martijn van den Bergh


People also ask

How do you use Apollo client to fetch data?

You pass a query object to ApolloClient#fetch(query:) to send the query to the server, execute it, and receive typed results. By default, Apollo will deliver query results on the main thread, which is probably what you want if you're using them to update the UI.

How does Apollo GraphQL cache work?

Apollo Client stores the results of your GraphQL queries in a local, normalized, in-memory cache. This enables Apollo Client to respond almost immediately to queries for already-cached data, without even sending a network request. The Apollo Client cache is highly configurable.

Does Apollo client use Websockets?

Setting up the transport. Because subscriptions usually maintain a persistent connection, they shouldn't use the default HTTP transport that Apollo Client uses for queries and mutations. Instead, Apollo Client subscriptions most commonly communicate over WebSocket, via the graphql-ws library.

How do I use Apollo client With GraphQL?

Anything you can type into the GraphQL query IDE, you can also put into your Apollo Client code. When we are using a basic query, we can use the Apollo.watchQuery method in a very simple way. We simply need to parse our query into a GraphQL document using the graphql-tag library.

How do I use usequery to render an Apollo client component?

When your component renders, useQuery returns an object from Apollo Client that contains loading, error, and data properties you can use to render your UI. Let's look at an example. First, we'll create a GraphQL query named GET_DOGS. Remember to wrap query strings in the gql function to parse them into query documents:

How does watchquery work in Apollo?

Rather, it uses Apollo's store in order to reactively deliver updates to your query results. For example, suppose you call watchQuery on a GraphQL query that fetches a person's first and last name and this person has a particular object identifier, provided by dataIdFromObject.

What should I know about query syntax when using Apollo client?

When using Apollo Client, you don't have to learn anything special about the query syntax, since everything is just standard GraphQL. Anything you can type into the GraphQL query IDE, you can also put into your Apollo Client code. Basic Queries#


3 Answers

It is posible, you need to set the option notifyOnNetworkStatusChange: true, it is explained in this documentation and then use the loading prop:

this.querySubscription = this.apollo.watchQuery<any>({
  query: CurrentUserForProfile
  ,notifyOnNetworkStatusChange: true <-- This will make the trick
})
  .valueChanges
  .subscribe(({ data, loading }) => {
    this.loading = loading; <-- now this will change to false at the start of the request
    this.currentUser = data.currentUser;
  });
like image 136
nanitohb Avatar answered Oct 07 '22 21:10

nanitohb


Your subscription has the loading parameter:

import { Component, OnInit } from '@angular/core';
import { Apollo } from 'apollo-angular';
import gql from 'graphql-tag';

// We use the gql tag to parse our query string into a query document
const CurrentUserForProfile = gql`
  query CurrentUserForProfile {
    currentUser {
  login
  avatar_url
}
  }
`;

@Component({ ... })
class ProfileComponent implements OnInit, OnDestroy {
  loading: boolean;
  currentUser: any;

  private querySubscription: Subscription;

  constructor(private apollo: Apollo) {}

  ngOnInit() {
    this.querySubscription = this.apollo.watchQuery<any>({
      query: CurrentUserForProfile
    })
      .valueChanges
      .subscribe(({ data, loading }) => {
        this.loading = loading;
        this.currentUser = data.currentUser;
      });
  }

  ngOnDestroy() {
    this.querySubscription.unsubscribe();
  }
}

https://www.apollographql.com/docs/angular/basics/queries.html

like image 4
Rubén Soler Avatar answered Oct 07 '22 20:10

Rubén Soler


Here is the WatchQueryOptions in ApolloClient 3

export interface WatchQueryOptions<TVariables> extends CoreWatchQueryOptions<TVariables> {
    /**
     * Observable starts with `{ loading: true }`.
     * There's a big chance the next major version will enable that by default.
     *
     * Disabled by default
     */
    useInitialLoading?: boolean;
}

meaning you still need to explicitly tell you want to be notified of the "loading" statuschange flagging (useInitialLoading: true), otherwise you will only get false.

const variables = {};
return apollo
   .watch(variables, { useInitialLoading: true })
   .valueChanges
   .subscribe(({data, loading})=> console.log(loading)));

Note: If you still experience problems, use a version greater than the 2.4

like image 2
Flavien Volken Avatar answered Oct 07 '22 21:10

Flavien Volken