Fetch Data Using HTTP Client From Json-Server API in Angular
Fetch Data Using HTTP Client From Json-Server API in Angular

In this video you will learn how to fetch data using http client service from Angular. To create a mock API from where we will fetch data we will use json-server. It's a nice npm package which helps us to create a mock API in a matter of minutes.

In all previous videos we worked only with data which where inside our Angular application. In the real project we fetch almost all data from the backend via API. Angular allows us make make API calls in an easy way. But here is the problem. We don't have any API to make our call and of course I don't want to make it too complex with implementing real backend with API.

But there is a nice solution for building Fake API. It's an npm package which is called json-server. I used it a lot for simple backends without complex logic.

Let's install it now.

npm install -g json-server

Now all that we need to do is create db.json file. It's our fake database. In our project we have users so let's add our users there.

{
  "users": [
    {
      "id": "1",
      "name": "User 1",
      "age": 25
    },
    {
      "id": "2",
      "name": "User 2",
      "age": 27
    },
    {
      "id": "3",
      "name": "User 3",
      "age": 30
    }
  ]
}

The most important point is that it's a json. So we need to wrap everything is double quotes.

Now we can simply start our fake json server with

json-server --watch db.json

If we open browser in localhost:3000/users we can see our created users. The most important that it's not only 1 request. We can do PUT, PATCH, DELETE, POST also to this route and json-server will update our db.json file accordingly.

Now as our fake API is ready let's jump back to our Angular project. We have all users inside app.component. Now we want to get them from API and remove the raw data. Normally logic with API we move to services but I want to keep this video simple so we will write code without services for now just inside our component.

So what do we need to do? We want to fetch user data when our component is initialized. But we don't know anything about initialize yet. Here is how it looks like.

ngOnInit(): void {
  console.log('component is inited')
}

As you see in browser we get a console log now when our app.component is initialized. Now we need to make an API call. For this we need to use a httpClient service from Angular and inject it inside our component.

import { HttpClient } from '@angular/common/http';

export class AppComponent {
  constructor(private http: HttpClient) {}
}

So here we imported HttpClient service and injected it in constructor. To inject something inside our component we almost always use this notation: private something: Something. After this code http is available for us inside this.

Now let's make our fetch

ngOnInit(): void {
  this.http.get('http://localhost:3000/users').subscribe(res => {
    console.log('res', res)
  })
}

In javascript we normally write fetch.then but here we have subscribe. And this is one more thing why Angular is more difficult than other frameworks. Because it uses inside RxJs library and you also need to learn it at some point. So RxJS is the streams implementation in javascript. So our data flows like a stream and we can change them or subscribe to them to get new data again and again.

It is complicated but not in the case with simple API request. In this case it works exactly like .then in JavaScript. We just get a value from http.get inside subscribe and we can do something with it.

Now let's look in browser because we will for sure get an error.

NullInjectorError: R3InjectorError(AppModule)[HttpClient -> HttpClient -> HttpClient]:
  NullInjectorError: No provider for HttpClient!

So here we get an error that we don't have a provider for HttpClient. Such errors may be really confusing to debug but here the problem is that we need first to import HttpClientModule in app.module. Because HttClient is the part of the module and we need to define it as a dependency.

@NgModule({
  ...
  imports: [..., HttpClientModule, ...]
})
export class AppModule {}

As you can see, now we don't have any errors and we get our data in console. As you can see it's an array of users which we can save in our users variable.

users: UserInterface[] = []
ngOnInit(): void {
  this.http.get('http://localhost:3000/users').subscribe(res => {
    this.users = res
  })
}

I also removed our users array and assigned it with empty array as an initial value. In this case there won't be type mismatch when first the value is underfined and after fetch API an array.

Now there is also a Typescript error that we get back an Object from API. We need to specify the correct interface here in order to tell Typescript what are we getting from API.

this.http
  .get('http://localhost:3000/users')
  .subscribe((res: UserInterface[]) => {
    this.users = res
  })

As you can see in browser, everything is working as previously but now we are getting data from our json-server.

In this video you learned on the real example how to setup json-api and make get API call with HttpClient in Angular.

If angular for beginners is too easy for you or you want more advanced stuff check my 14 hours Angular course where we create a real project from beginning to the end. Link is also in the description.

📚 Source code of what we've done