
Lesson Description
The "Client-Side API Service" Lesson is part of the full, Build a Fullstack App with Vanilla JS and Go course featured in this preview video. Here's what you'd learn in this lesson:
Maximiliano explains how to create an API service in JavaScript using the fetch API. He demonstrates how to make API calls to a backend server and retrieve data using async/await and the fetch.json method. He also discusses the use of try/catch blocks to handle errors and suggests encapsulating the API service to prevent exposing it in the console or to unauthorized users.
Transcript from the "Client-Side API Service" Lesson
[00:00:00]
>> Maximiliano Firtman: The next step is C4 if you're following along with the documentation, we had C4 we need to create an API service. What is that? This is gonna be an object client side that will talk through HTTP, show our backend, okay? So we're going to create that file, API.
[00:00:22]
It's a service, and what's a service from a front-end perspective? Actually, nothing, it's a design pattern. So we don't have services in JavaScript as a concept, okay? It's just a design pattern. So I'm going to create inside public because we are in the front-end. A services folder and we're going to store there every script that has to do with services and we're going to have one called API.js, okay?
[00:00:53]
An API.js will export a constant that we can call API, that will have all the API calls. So for example, we can have getTopMovies. Little warning here, I'm going to refactor the code. So I'm going to write something and then I'm going to change, okay? So for example, getTopMovies will be a function, and what's the idea?
[00:01:23]
I want to call my API, my backend API, okay? So for that, I will use a fetch API. The fetch API receives a URL. So I need to say, well, I want API forward slash movies, forward slash top forward slash, okay? But that's a promise. So typically when we have a promise, we can use, say, sink await, right?
[00:01:49]
So I need to await for this, and that will give me actually the response. The problem is that, if I'm using await, I need to add the flag async to my function, okay? Now I have the response is that the array of movies? No, it's the HTTP response option, if I want the data, so the result of that.
[00:02:18]
I need to call fetch.json, so parse this adjacent and this is also receiving a promise. This is plain vanilla JavaScript, I'm not using any library. This is how JavaScript works, okay? The Fetch API works after I did the fetch, and I have the HTTP response. To get the result as a JSON object, I need to take the response and call JSON that will parse this as a JSON, and this also returns a promise.
[00:02:49]
So I need to await for the actual JSON, I don't want the promise. And then I can return the result, okay? So if this is working, I could go to my browser refresh, I can open the console,
>> Maximiliano Firtman: And try to call this, how? API, actually I can't, why?
[00:03:20]
Because this is exporting a constant. So I need to find a way to get here, okay? It's not a global variable. When I'm using modules, everything that you are creating in a file will not be available globally. So for now, for the bagging purposes only, okay? For the bagging purposes only, I will say API is equals to, and I will say API.
[00:03:53]
So you can see now it's importing API from this, okay? Big warning, really, big warning, when you're using VScode and JavaScript, by default, VScode thinks you're using a JavaScript bundler, okay? So a JavaScript bundler is something that typically you have when you are doing React and with your view JS, blah, blah, blah.
[00:04:22]
But we are not using a JavaScript bundler right now, which means if I run this, I'm getting an error 404, it says services API is 404 and say why it's 404 services API is there? Does anyone know why it's 404?
>> Speaker 2: The .JS.
>> Maximiliano Firtman: I don't have the full extension here, I need to add the.js, what happened?
[00:04:54]
VScode thinks that I have a bundler, and bundlers are solving that problem for you, but that's not how the browser works. The browser doesn't know that they have to add .js to actually get the file from the server, okay? Does it make sense? So be careful when you do a bundler JavaScript that you might have a problem, okay?
[00:05:19]
Every auto import that you get, at least not every, the first one. Because now what happens? If you have another one, VScode, realize that you're adding .js and it will add .js on the rest of the imports, but the first one profile will not have that .js. So that's a Vanilla JS problem.
[00:05:39]
So now it seems like I have exposed that API. So if I refresh, I have exposed that API through app, okay? So I can getTopMovies and it's a promise, because it's a promise, so I need to wait for it. Actually, I do have my 20 top movies, so it's working, okay?
[00:06:08]
I'm getting in my app the top movies. Does that make sense? Again, I'm exposing the API to the console is not a good idea, and I don't wanna do that, but at least for debugging, at this point, I think it works.
>> Maximiliano Firtman: Okay, does it make sense? Cool, well, now we need to also on the API, get random movies, get movie by ID, and everything looks kind of the same or very similar, okay?
[00:06:43]
We just changed the URL, right? So maybe we can try to make a general fetch from my API, and then we call that fetch, because, if not we will be copying and pasting and that's pretty bad. So let's say that fetch will be an async function that will receive the URL or the service URL, and maybe some arguments that we can add later.
[00:07:14]
And it will do this instead of this, maybe you will see that forward slash API. It's like a prefix that we need to use on every service, right? So maybe we can create a constant. It's not really a constant, but kind of a constant for that typically we call that base URL.
[00:07:41]
>> Maximiliano Firtman: Like that. So getTopMovies first, it's gonna just return the call to API fetch with movies top, just that part of the URL. Does that make sense? So then we'll receive this here, the fetch, and we're going to say, well, you know what? I'm going to take the base URL, I'm going to concatenate the service or the service name.
[00:08:10]
Let's call it however you want, service, service name. And then we may have some arguments at some point, okay? And I have a question for you. What happens if there is any error?
>> Maximiliano Firtman: How can I catch the error? I mean, the URL does not exceed, the server is down, the server is giving me 500.
[00:08:36]
>> Speaker 3: 500 error.
>> Maximiliano Firtman: Sorry, what?
>> Speaker 3: 500 error.
>> Maximiliano Firtman: But how? With async await, do you know how to catch errors? Try catch. So it's as simple as using try catch. So in JavaScript, you can use try catch, even from async operations, if it's a promise. So try catch, I don't need to receive the error now anymore, it's not mandatory.
[00:09:06]
But maybe I want it, because at least I wanna see in the console so I can say console error e, and later we'll see we do something else, okay? So now we have getTopMovies, and I just need to clone this for the rest, okay? So getRandomMovies is pretty similar, and we just change the URL.
[00:09:34]
GetMovieById, in this case, we received ID as an argument, we may receive the ID as an argument. We can check if the ID is a number or not. And then we return fetch movies, this is gonna be movies. And the ID, we can concatenate or use a template string.
[00:10:02]
And by the way, I'm returning the fetch, so the promise, also if you wanna return just the data, the JSON, we can also await on each of those. Does it make sense? So then whoever is calling you will receive the data, okay? GetMovieById, then we have search movies.
[00:10:28]
This one has a couple of arguments. So it's gonna be a little different. We're going to receive a query. Typically, we call this Q. I mean, you can call it however you want, but the argument, and I think that we are all copying Google here that they were using Q in the URL when you google something, it's google.com/q=, it's actually the query.
[00:10:53]
So we have the query, the order and the genre, okay, like that, and we have one more. So in this case, we are going to receive movies. It was search and actually, I wanna pass the arguments. I mean, I can do it manually, I can say query string, so question mark, query equals to query, I can do that, okay?
[00:11:26]
Or I can create a little tool where I can pass an object with the three arguments, and here I can just create the query string manually, okay? So if you have arguments that you wanna send over the query string, you just pass it as an object. And from this side, you say, if I do have an argument, I will say, new URLSearchParans, this is pure Vanilla JavaScript arguments, just a string.
[00:11:58]
And if I don't have arguments, I will just say empty string. So then I concatenate this with that query string, okay? Yeah.
>> Speaker 2: Why did you say it was not good to expose the API to the console? If it's client side, they can see the code anyway.
>> Maximiliano Firtman: Yeah, I mean, it's true it's client side, anyone can see the code.
[00:12:27]
But the thing is that when we're using modules, you can encapsulate objects and make them hidden to the lowest scope. I mean, if you have a bad actor, the bad actor can get into that anywhere. But it's like another barrier that you put there and also you're not exposing that in the console or to a plugin that is in Chrome, and things like that.
[00:12:54]
I mean, it's not like a very secure system, no, it's not. But every new barrier that you add makes things better. In this case, we are encapsulating this, and only our objects or only scripts that are actually importing API will be able to use it. But if you wanna hack into that, you can't pretty easily.
[00:13:14]
I mean, these days, in JavaScript, if you don't have access to something, you can always use import as a function. So you will be able to import, like services, api.js, like so it waits for it, and when you have it, actually we can do this. It's API services, API JS, yeah, well, I don't maybe we've removed that.
[00:13:44]
I'm not sure why features or modules specifier, something's wrong with the URL, no, it's not. But anyway, let's remove that and just explain that briefly. So even today with modern JavaScript, you can do live module import. So you can import a module like this, and then we would have access to it, if you have the right permission at the network layer.
[00:14:13]
But it doesn't matter, I mean, in this case, I think that from an organization point of view, it's a good idea to hide that, okay? Because that means that you have to explicitly have the API import when you need it, okay, makes sense? So now that means that we have the API service available from a client side point of view.
Learn Straight from the Experts Who Shape the Modern Web
- In-depth Courses
- Industry Leading Experts
- Learning Paths
- Live Interactive Workshops