LongCut logo

REST API Crash Course - Introduction + Full Python API Tutorial

By Caleb Curry

Summary

Topics Covered

  • APIs Enable Secure Cross-Language Communication
  • Never Expose Database to Client JavaScript
  • REST Setup Unlocks Multi-Frontend Versatility
  • PUT Idempotent Replaces POST Creates

Full Transcript

Hey everyone, welcome to your REST API crash course. My name is Caleb. In this

crash course. My name is Caleb. In this

video, we're going to talk about everything you need to know to get started with REST APIs. We're going to first talk about the concepts, then we're going to talk about how to consume an API, and then we're going to build

our very own API in Python. So, it's a lot of useless or it's a lot of useful information. So, if you need a reference

information. So, if you need a reference of all this, I created a PDF that you guys can get for free with a link in the description. So go check that out if you

description. So go check that out if you just need to like, you know, look at the definitions and study or whatever. But

anyways, we're going to jump in by first talking about what a REST API is, why you should care, and where this is used in software. And if you're watching this

in software. And if you're watching this video and you're not really doing anything with software, not really sure why you're here, but you can probably move on to one of my other videos. So

which all of my videos are about software. So anywh who, API stands for

software. So anywh who, API stands for application programming interface.

So, I tried talking and explaining this last time I recorded this and it just didn't go so well because I cannot talk and write very well at the same time.

Application programming interface. It's

basically a fancy way to say a way two pieces of software can communicate with one another. So, if we have this

one another. So, if we have this software over here, this is some really cool software system we built. And here

is another one. And let's say these are built in different programming languages. That's where an API is going

languages. That's where an API is going to come in and save the day. It allows

different applications that aren't built exactly the same to communicate. So

we'll say this one was built in Python and this one was built in JavaScript. Poor developer. I'm so

JavaScript. Poor developer. I'm so

sorry. Well, an API allows us to build functionality in this application to make a request to this other application

and then this application can give a response back to this application. And

that is where the API comes in. We're

building this interface for these pieces of software to communicate with one another. Now, in general, it's a one-way

another. Now, in general, it's a one-way thing. So this app is not going to

thing. So this app is not going to request information from this app and get it back. Instead, it's always we have a a server and then a client. The

client consumes information given from the server. So this is a very common

the server. So this is a very common setup you'll see in all of computing.

The same way when you go to get a website, you know, you go to youtube.com, you're making a request and then that server gives back a response.

It works exactly the same way with our REST API, although instead of getting HTML, you're going to get JSON.

So, JSON is a language or a notation of describing information. It's just like

describing information. It's just like text and it stands for JavaScript object notation. So, it's a way to notate what

notation. So, it's a way to notate what objects look like. But, it doesn't have to be done with JavaScript. It's

actually supported in pretty much every language. And this is now the standard

language. And this is now the standard for APIs. You may run into APIs that use

for APIs. You may run into APIs that use XML. However, this is kind of

XML. However, this is kind of old-fashioned and probably not what you would want to use going forward. So, I

would recommend even if you're more familiar with XML for some reason to learn JSON or JSON. You'll hear both.

So, JSON's not complicated. Don't feel

like you have to learn another programming language or something. It's

just a series of key value pairs just like an object in JavaScript, hence the word JavaScript object notation or like a dictionary in Python where you have a

key and then an associated value. So,

it's pretty much just an associative array. We'll get into what JSON looks

array. We'll get into what JSON looks like and how to use it soon when we go build our own API, but don't worry too much about that. So JSON is basically

the the language of communication and the API is you know what things we can communicate you know maybe you want to get a list of users or maybe you want to

update some comments whatever you want to do that's all defined as API end points. So, you know, right here where

points. So, you know, right here where we're making that request, that's an example of an end point. We're going to talk about the

point. We're going to talk about the different types of endpoints that we can create. Now, what about this rest thing

create. Now, what about this rest thing here? Well, that stands for um I think

here? Well, that stands for um I think representational state transfer. I had

to look that up a little bit ago because I was like represent what was it?

Anyways, this is the means of communication. So, you know, I can talk

communication. So, you know, I can talk to you in English, but how am I talking to you? Am I talking to you over the

to you? Am I talking to you over the phone? Am I texting you? Am I talking to

phone? Am I texting you? Am I talking to you face to face? Well, that is describing how we're communicating. And

this REST aspect is communicating over the web or the internet. So, this is all going to be

internet. So, this is all going to be done by making requests similar to how you would request a website, but instead of HTML, you're requesting JSON. just as

I mentioned earlier. So to make this a little bit more concrete, let's go over an example of an app I'm working on. So

I have some software written in Python and this is the server software.

You may also hear it as the backend software. And this is the software

software. And this is the software that's going to communicate with a database. That's where all of our

database. That's where all of our information and data is going to be stored. So this talks to the

stored. So this talks to the database. Now, we want other pieces of

database. Now, we want other pieces of software to be able to communicate to this back-end software, but we don't just want them to be able to access anything. We don't want to give direct

anything. We don't want to give direct access to this database. So, instead, we expose different API endpoints. So, an

example of an API endpoint would be forward slash and this I haven't described what the actual app is for, but forward

slashdrinks. Now, the actual app is to

slashdrinks. Now, the actual app is to get a list of drinks and be able to rate these, you know, like zero to 10 or to put them in different categories of how good they are. And then you can

basically keep track of all your favorite drinks. It's a little silly,

favorite drinks. It's a little silly, but I thought it'd be a fun project. And

um basically, I I like to drink I don't like to drink. I like to drink non-alcoholic beverages like LCroy or like stevia drinks and energy drinks or whatever, but there's so many of them I

can't keep track of them all. So, I just wanted to build a little website to, you know, rank them, you know, and instead of just getting all of the drinks, you might want to get a specific drink. So,

in this situation, we would pass in an ID. So, in this situation, we are

ID. So, in this situation, we are getting data. And that's one of the

getting data. And that's one of the different methods of APIs. We're going

to talk about API methods here in a minute. But what this means is my

minute. But what this means is my software that I built over here. And in this situation, let's just

here. And in this situation, let's just say this is JavaScript. I can get all of the drinks

JavaScript. I can get all of the drinks or a specific drink from my backend software just by making a request to this web address. Now, you might be

looking at this like, what? That doesn't

look like a web address. Well, because

this is a web server, this is going to have either an IP address or a domain name. So, let's say I put this up on a

name. So, let's say I put this up on a website, Caleb's favorite drinks.com, not a real website to the extent of my knowledge, and then forward

slashdrinks forward slash and then you can pass in some ID such as five. Now,

the actual structure for these URLs and what data you want to get that is totally up to you. However, there are some general standards and I will describe why I went with this coming up

soon. But basically, we have the list of

soon. But basically, we have the list of data we're trying to get from and then we pass in which specific element we want. And this will return JSON of all

want. And this will return JSON of all the information about that drink. Now,

oftent times when you have a website, you're going to have web pages, you know, people can view on their web browser or you're going to have the API.

And often these will be split out into two subset applications. So you might have calebs favoritedrinks.com/drinks5. Or another

favoritedrinks.com/drinks5. Or another

common thing is to have a different domain such as api.calebsfeddrinks.com. You don't have

api.calebsfeddrinks.com. You don't have to. You can mix those together. However,

to. You can mix those together. However,

just for organizational sake, often the API is in some separate section, either a subdirectory or a subdomain. Now, you

might look at this setup, as I often do when I'm working on applications, and be like, why the complexity? Why do you need to have two applications and then the database? Why don't you just connect

the database? Why don't you just connect from this application all the way to the database, skipping all this junk? Well, obviously

you can do that. You can do whatever you want but this is not always advisable for various reasons. The most biggest importantest reason of not going from

the client application directly to the database is security specifically if you are using JavaScript. Now oftent times the client is going to be JavaScript

because that's used for web pages.

However, you could also make a console application or a mobile application. So,

it's not always going to be JavaScript, but if you go to a website, you can go into the developer tools and you can see all of this JavaScript or you can rightclick and view source and it'll

have the JavaScript files linked there and you can view all of that. So, you

don't really want to put sensitive information on the client here because it's all viewable to the person using your software, which means they could then go to the database themselves

directly, tinker around, you know, drop database, lol. We don't want them doing

database, lol. We don't want them doing that. So instead, we just expose

that. So instead, we just expose specific things that we want people to see, such as the list of drinks, but they can't go in there and see

everybody's user information or people's address or any of that. Now, beyond

security, the other big reason is versatility. So, right now, we have one

versatility. So, right now, we have one front-end application in JavaScript, but with this setup, we could very easily build a mobile application, and yes, this is a cell

phone. And we could also consume the

phone. And we could also consume the same API. So what happens now is both of

same API. So what happens now is both of these front-end applications are sharing the same backend which means these are always going to have the same data.

They're going to be synchronized. So that is how when you

synchronized. So that is how when you have applications on your phone, you can go in there and change data and then you can go log in on your computer and all of that stuff still exists. It's because

they all share the same backend. So, you

know, when you're messaging someone on social media, well, those messages are being sent to a back-end server that does all of the processing and all of the hard work of the application. And

that website you're looking at is really just a pretty cover to this backend. So,

you know, JavaScript, maybe your application here is in Swift, but ultimately we're hiding the back end of this application and separating those, which brings up the next good point,

which is modularity. Because the front end and the back end are separated and we're just defining this consistent way to communicate, we can actually swap

different things out and not necessarily break. I say necessarily because you

break. I say necessarily because you know in practice it's it could be difficult but in theory you should be able to swap out different things without breaking other pieces of the

application. So right now this is

application. So right now this is written in Python but I could be like eh I don't really feel like writing in Python you know and I decide to upgrade

to something like Visual Basic and in this situation we can expose the same exact API endpoint. So, this website and

this mobile phone app, they don't even need to know about those changes to the back end because they're still getting their list of drinks. That's all they care about. They just want their drinks.

care about. They just want their drinks.

This is great because you can change the back end of software without requiring an update to the app or requiring a new deployment of the website as long as

you're able to give a consistent interface to working with your backend.

Last reason and then I promise I'll stop rambling. Okay, I got a little bit more

rambling. Okay, I got a little bit more rambling, but basically the last thing I wanted to share of why this setup is good is interoperability, which I think is a word. And basically what I'm saying

here is that these front-end applications, they don't all have to be built by you or the front-end development team for your company. You

can actually expose certain endpoints such as this one right here, and you could make this public.

So if you make certain endpoints public, you don't have to worry about authentication or authorization. And in

that situation, anybody could go ahead and create some new app, new and improved to consume your API. So you

know, if I don't like the way Instagram looks, I can go create my very own Instagram viewer because they have an API that can be consumed. Now, sometimes

you'll still need to get some kind of token or some way to authorize saying, "Hey, I'm okay to use this API." But a lot of the times these APIs are going to

be publicly available. So, the API we're going to consume soon is just a public API that anybody can use and it's really cool honestly. So, many websites you

cool honestly. So, many websites you might not even realize have APIs. So,

for example, if you wanted to do something like create a trading bot or like a cryptocurrency trading bot, well, oftent times different exchanges are

going to have APIs so you can automate different things in code. So, it's not always just about making a pretty interface, but it might be about automation. How can we connect these

automation. How can we connect these apps and make things happen automatically? So, if the thing's not

automatically? So, if the thing's not public, it might be private, but you can still access it. You just need a way to verify that it's you and not just

anybody's going on there and trading cryptocurrencies or spending your money.

So there the authorization aspect of this is like a whole another beast. But

a common thing you often see is OOTH 2.

That is an authentication technique that's fairly common. So if you want to look into how to protect your API and make you basically have to log in, you

can look into OOTH. That's o a u t h2. Now I want to take a moment to talk

h2. Now I want to take a moment to talk about the different methods of requesting data from the server. So

we've talked about get and this one's pretty simple. It's what's used to

pretty simple. It's what's used to retrieve data from the server. And these

are often written in all uppercase letters. So you're just like screaming

letters. So you're just like screaming like get me this information. All right.

So get is used to retrieve data.

I could just say get data but fancy here. All right, so there's a few other

here. All right, so there's a few other ones you should know about and that is post. Post is used to write data. So

post. Post is used to write data. So

anytime you want to write information to the server, you're going to use post.

And then there is delete. Almost didn't

use capitals there, but I fixed it. And this is used to, you know,

it. And this is used to, you know, delete stuff. Now there is another one

delete stuff. Now there is another one that's pretty common. Why do I always write like this way? I don't know. And

that is put. And this is actually fairly confusing if you're new. And the

difference between post and put is pretty gray. And people will even argue

pretty gray. And people will even argue about which you should use where. Here's

my opinion. Post should be used to write new data. Put should be used to write

new data. Put should be used to write but in this situation, we're going to update data.

So now I want to show you how these things correlate to the most popular things you have to do with the database which is CRUD. So the different things you need to do, we need to be able to

create data, post, read data, get, update data, put, and delete data, delete. Now, why exactly is there

delete. Now, why exactly is there confusion between post and put? That's

what I want to talk about now. Well,

first let's talk about how post and put are generally used. Post is used to add a resource. Put is used to replace a

a resource. Put is used to replace a resource. And that's why it's natural in

resource. And that's why it's natural in my mind to say you can use put to update data and post to add new data. But

replacing a resource requires some way to identify it. And often this is done with an ID. So my thoughts are if you're doing a post request, you want to add

data. So you might have the

data. So you might have the address of drinks and you want to add a new drink. With put, you're probably

new drink. With put, you're probably going to need to identify what resource you want to replace. So it might look

like drinks slash 6005 for an ID. Now,

with the setup I tend to do, I usually don't have this ID value until that's that data is already inserted in the database with a post. So when you're adding new data, you don't know what

that ID is going to be because that's auto incremented in the database. Then

if you want to update that data, then you use the ID. But there's another difference and this is more defined in the spec of how an API is supposed to work and less about pure functionality

because you're the one who defines the functionality. So if you want your API

functionality. So if you want your API to work correctly then you need to make sure you implement it in this way and that is put is designed to give the same

result every time if you make the same request. So for example if you're

request. So for example if you're replacing this drink with a new drink you can replace this ID over and over again as long as that new one has the

same exact ID. So, let's say you have a grape drink and you replace it with cola and then you replace cola again with

cola and then cola again with cola. No

matter how many times you do this, the same resource exists and it doesn't hurt if you accidentally put that request numerous times. Post is usually a little

numerous times. Post is usually a little bit different because that feature or capability is not guaranteed. So, what

that means is if you add a new drink, let's say you add cola and then you add cola again. Well, in

this situation, you're not replacing anything. So each time you add cola,

anything. So each time you add cola, it's making a new record in that table.

So put is guaranteed to be able to be executed numerous times without any kind of side effects. Post on the other hand is not guaranteed by the spec. And in

that situation, you could actually have duplicate records in the database or you could get an error on that second one if the drink name is defined to be unique.

Now, I'm probably going to mess this word up, but there's a word to describe this. Iden

this. Iden potent. It Yeah, I it potent. I don't

potent. It Yeah, I it potent. I don't

know. So, put is said to be this. I'm not even going to try anymore.

this. I'm not even going to try anymore.

Just whatever that's called. Now, in

general, I think there's a lot of confusion between post and put. And you

can pretty much do the same behaviors with either one. So, I tend to just try to stick with post most of the time.

Even if I'm updating a resource, it you can do it with post just the same. You

can define it however you want. It's

sort of how with modern HTML, you can make a section be a div or you can be a little bit more specific and say, "Oh, this is a footer." Both kind of give the same results. And if you're not using

same results. And if you're not using footer, right, then you might just make things worse. So, a lot of people still

things worse. So, a lot of people still end up just using divs. So if you're using HTML, that's just maybe that kind of puts it in perspective. I don't know.

There's another method, patch, which is used to replace different pieces of a resource. So maybe you just want to

resource. So maybe you just want to update one field. However, in our situation, the data we're working with is so small that it's pretty much just easier to replace it with a new version.

So that way you don't have to keep track of individual changes. However, if

you're working with very large data, you can definitely look into patch. So my

theory is you basically keep the state of an object in the client side application and then once you save you just send that new state and replace the old state in the database. Hopefully

that makes sense. All right. So let's

get some practice with APIs by consuming an existing API. We're going to take a look at Stack Overflow. So all of the questions on here, you can get access to

this information through an API. So we

can build an application to work with Stack Overflow. So to do this, you

Stack Overflow. So to do this, you actually go to api.stackchange.com and in here you can

api.stackchange.com and in here you can see the documentation for all of this.

So here's the different API endpoints.

So we can get the answers, badges, comments, posts, which is just a uh combination of questions and answers.

And I'm going to take a look at the questions here. So we're going to get

questions here. So we're going to get all of the questions. And here is an example of how you would invoke this. So

you can hit run and you can see in this web address there's this question mark and then some variables with assigned values and then an and sign amperand and

sort. These are known as query

sort. These are known as query parameters and they can be used in this situation to modify the results of the API. Now, if you want to know how to

API. Now, if you want to know how to actually invoke this without it running it in this little test window, you basically just take this address here and you would paste it after api.stack

exchange.com uh like so. So, that's what it's going to look like. Hitting enter, you get a bunch of data here. Not exactly as

pretty as this, which by the way, this is JSON format. So, it's just key value pairs. And in the pairs you can have

pairs. And in the pairs you can have arrays or uh you could consider them lists if you're more familiar with Python. So we have items right here

Python. So we have items right here which is a list of questions. Each

question is surrounded by curly braces.

So there's the opening curly brace and it has tags owner bunch of other stuff and then it ends. And then we have another question which has tags owner a bunch of other stuff and it just repeats

in a list. So what we're going to do is we're going to work with this API. So, a

tool I would recommend you get is called Postman. And in here, you can work with

Postman. And in here, you can work with your APIs and it's just a little bit easier because you can customize the body and the different headers of your requests. And what we're going to do is

requests. And what we're going to do is we're just going to take this web address here and paste it on here. So, we're

going to have httpapi.stackchange.com

stack exchange.com and then forward slashquests and then all that other stuff. So hit send and we'll get a

stuff. So hit send and we'll get a response sort of like this. So basically

this is JSON here we have this items and then a list of the different questions.

So let's go ahead and we'll come back to Postman later but for now let's take this URL and try to work with this in a Python script. So, if you need help

Python script. So, if you need help setting up a Python environment, then you can check out my beginner Python programming all-in-one. However, I'm

programming all-in-one. However, I'm just going to assume you can at least get a Python environment set up. And

we're in a Python file. What we're going to do is we're going to need a few tools. So, we're going to say import

tools. So, we're going to say import requests and import JSON. So, if this is your first time working with requests, you might need to install it. So what we

can do is we can open a terminal and say pip 3 install requests. All right. So

now we have requests installed and we should be able to make a request to a web page by saying requests.get and pasting in a web

requests.get and pasting in a web address inside of a string here. So

let's just uh make sure this is nice and formatted properly like so. And that's

going to return a response. So we can assign that to a response variable. And

then what we'll do is we'll just print this response and see what we get. And

you can see we get a response 200 which means okay. Now we can actually see the

means okay. Now we can actually see the data that's returned by running.json as

a method here. And that's going to give us all of the data exactly as we would if we requested it in the web browser or with Postman. So we got the items and

with Postman. So we got the items and then a list of all of the different questions. So we can basically zoom in

questions. So we can basically zoom in on this and instead of just having one key value pair where we have items and then a giant list, we could actually

explore items specifically by passing in items here. So we're going to index

for items and then run this now. And we

have just a list now. So we're no longer working with the items. we just have a list of questions. So then what we could do is

questions. So then what we could do is we could iterate over these. So let's

get rid of this print and we'll say for data in items. Or if you want to be more specific, you could say for question in items. This will be good for now. And

then what we'll do is we'll just print data. And you can just print each one

data. And you can just print each one individually like so. Or you can be more specific and grab something like the title, which I know is an attribute of

it. So running this and you can see here

it. So running this and you can see here are all of the titles. So that's pretty cool. So basically that is

cool. So basically that is right right here, the title. We're going

to be grabbing each one of these. So

every single item in this list. And you

could also get something like the link if you wanted. So we can say print data link and now we got a series of question and answers and let's just print a space

just to make it a little bit prettier.

There we go. So here is the question and then here is the link which we can control-click to open. And there you go.

So maybe you could build some kind of application to help you find good Stack Overflow questions to try to answer before anyone else does. So you can be a little bit more specific. You know, you

could go in here and you could check to see the answer count. Answer count is like two for this one. So maybe maybe you only want to print the ones where

the answer count is zero. So you could say if data and then ask for the answer

count is zero, then we want to print the data. And just to show you guys that

data. And just to show you guys that it's working, we'll say else print skipped. And also just print another

skipped. And also just print another space at the end. Actually, I'll just uh take that out of the loop. There we go.

So this is our setup now. And we can run this. And you can see skipped. And then

this. And you can see skipped. And then

we got a question and then skipped and then a question, another question. And

it seems to be working. So that's how you consume an API. Now I want to talk about how we can create our own API. So

what I want to do is X out of this file here and we are in a folder API and open a terminal which I have one here and we

can get the path. So just make sure you're in that

path. So just make sure you're in that directory and we're going to execute a sequence of commands in the terminal here. So the very first thing is we're

here. So the very first thing is we're going to create a virtual environment.

So to do that you say python 3-m virtual environment venv and then give it a name such asveenv and that's going to create a new

folder in here for your virtual directory which I talk about this in my uh previous video where we deployed a python web app but this is basically to isolate the dependencies for this

specific application. Now what we can do

specific application. Now what we can do is we can activate that by saying source and then traveling to it. So it's in the

uh venv folder bin activate. So that is how you

bin activate. So that is how you activate a virtual environment. Then we

can install our dependencies. pip 3

install flask and we're also going to install pip 3 install flask sql alchemy and that's going to be used to work with

the database. So this is an example of

the database. So this is an example of an OM which I think is object relational mapper and we can output all of our dependencies in a file if we want. So we

can say pip 3 freeze and put this in requirements.txt. So, anytime you uh add

requirements.txt. So, anytime you uh add a new dependency, you'll want to do that just so all of our requirements are in this text file. So, uh whoever uses this project in the future can get the

dependencies. Then we can just create

dependencies. Then we can just create our file. So, we'll say application. py

our file. So, we'll say application. py

and that's going to create this application. file, which is where we're

application. file, which is where we're going to do our coding. So, to start off, we'll just create a basic flask

application. So we'll say from flask

application. So we'll say from flask import flask and then we say app is flask_ame right there. So that's how we

set up flask and what we can do now is we can make a simple route basically an endpoint by saying app.root and giving it a path and then we can define a

method that we want hit when someone visits this route. So all we're going to do for right now is just return a string hello. All right. So let's just make

hello. All right. So let's just make sure this is working. So what we can do is run our application. To do this, we're going to create a few environment

variables real quick. So flask

app is application.

py and the flask environment is development. And you're going to need

is development. And you're going to need to do that anytime you open up your terminal. So if you X out of your

terminal. So if you X out of your terminal and then reopen it, those are going to go away. So you'll need to do those again. And then you just say flask

those again. And then you just say flask run. All right. So this is where our

run. All right. So this is where our website's located. And we'll just open

website's located. And we'll just open that. All right. Already made a stupid

that. All right. Already made a stupid mistake. We don't put the colon here

mistake. We don't put the colon here just after the uh method. So do a refresh. Now this needs to be uppercase.

refresh. Now this needs to be uppercase.

There we go. That should be everything.

All right. All right, we got our app up and ready to go. So, the very first thing I want to do is make a get request. So, we're going to make an app

request. So, we're going to make an app to store drinks. So, we'll say app route. And the path for this is just

route. And the path for this is just going to be drinks and we'll say defaf get drinks and it's going to return something. We'll just say drinks for

something. We'll just say drinks for right now. But that's not a thing. So,

right now. But that's not a thing. So,

what we need to do is we need to put some code here to make it a thing. If

you want to just test it out for right now, what you could do is you could return a dictionary. And let's just say we got drinks and we'll just put drink data for right

now. So we should be able to save that

now. So we should be able to save that and it'll automatically refresh. And

then when we refresh our page, well, we go to actually forward/drinks and we get some data back in JSON. So it's sort of working now. We just got to worry about

working now. We just got to worry about connecting to a database. So to do this with the object relational mapper, we basically define all of the things we

want to store in our database as models.

So we're going to create a class. So we

can do that up here. And all we're going to do is we're going to say class drink. And for SQL Alchemy, we just say DB domodel. So it's going to

inherit from this. So it's already going to have various built-in functionalities. And that's how we can

functionalities. And that's how we can use it with SQL uh alchemy. So then we define the columns and we're going to put three of them in here. So we're

going to have an ID and the way you create a column is by saying DB column and passing in any attributes of it. So

it's going to be an integer and then we set it as the primary key by saying primary key is true. Next up we're going to have a name

true. Next up we're going to have a name which is DB column. And this one is going to be a string. So to do that, you say db string and you can pass in a max length. We'll just say 80. And another

length. We'll just say 80. And another

attribute in here is unique true if you want the name to be unique. And you can also say nullable is false. So you can't have any nulls. And then the last one on

here we're going to use is description.

And we'll say dbc column. And this is going to be a string

column. And this is going to be a string as well. And we'll just give this 120

as well. And we'll just give this 120 characters. However, I'm not going to

characters. However, I'm not going to put any other attributes on the description. Now, we want to override

description. Now, we want to override another method in here and that is called the rep re reper method repr for uh representation probably. And for this

we we pass in self which refers to the object. So, we can grab the object's

object. So, we can grab the object's attributes by saying self dot something.

So, we're just going to return a string and this will be invoked whenever we try to print out the the drink in the list.

So you'll see what I mean here soon. So

we'll say f to make a parameterized string and we can say self.name and then maybe you know a

self.name and then maybe you know a hyphen and then self.escription. All right, cool. So

self.escription. All right, cool. So

that is how we create a model. And what

we're going to do is we're going to set up our database with a table for drinks.

And to do that the easiest way is to use the Python terminal. So what I'm going to do is I'm going to quit our server.

Crl + C and then I'm going to say Python 3. So that's going to open up the

3. So that's going to open up the interactive mode in Python. And what you can do is you can say from application import DB. So what we do is we import

import DB. So what we do is we import our database from application import database. However, all we did is define

database. However, all we did is define the model. We need to actually make this

the model. We need to actually make this connection to the database in our code first before we can reference it. So to

do that, we're going to go up here and say from flasks SQL alchemy imports SQL

alchemy. So all lowercase and then SQL

alchemy. So all lowercase and then SQL is capital here. Then to get that DB variable, we just say DB is an instance of SQL Alchemy and we're going to pass

in our Flask app. So that's the setup for SQL Alchemy. The last thing we have to do is we need to configure our database so we can connect to it. So we

say app.config and we're going to pass in a

app.config and we're going to pass in a string here. SQL

string here. SQL alchemy database urri. And you don't have to

database urri. And you don't have to have all of this stuff memorized. You

can find this in the documentation for flask fairly uh simply. And then we're going to say SQLite and then three forward slashes

data.

DB. So that's how we say we're going to create an SQL light database called data. DB in the same directory. And then

data. DB in the same directory. And then

I think this DB variable actually will come after this config. So we'll paste that there. And there we go. So we

that there. And there we go. So we

should be able to X out of the Python interactive mode. Restart it. And now

interactive mode. Restart it. And now

what we should be able to do is say from application which refers to our application because we named it application.

py import db. Great. We didn't get any errors. We

db. Great. We didn't get any errors. We

did get this warning here uh warning us about significant overhead and you can change some settings but you really don't have to worry about that. So to

create our tables we say db.createall.

create all hit enter and you can see it actually creates the database as well since we didn't have that. Now because

this is what's known as an object relational mapper the way we work with our relational database is with objects.

So if we want to create a new drink we create a drink object and we can assign it to a variable called drink. And the

way we pass in data to create a drink is we do named parameters. So we can say name is grape soda and then a comma

description uh I don't know tastes like grapes maybe seems pretty fitting. So that is how we create oh and you see when we do this

name drink is not defined. So anytime we want to use something from our file we have to import it. So this class drink needs imported as well. So from

application import drink and now we should be able to use the up arrow key to bring back our previous code. Hit

enter. And now we have a drink object.

And you can see it by typing in drink.

And it says grape soda tastes like grapes. And that is where this repr

grapes. And that is where this repr method comes in. It basically the name hyphen in the description. Now to add it

to our table, we say db session.add

add drink and then db.ession.comit. And that's an important

db.ession.comit. And that's an important step. Yeah, we want

step. Yeah, we want DB.Comit not

DB.Comit not doctor. So, db session

doctor. So, db session commit. Now, we should be able to get

commit. Now, we should be able to get all of our drinks by saying drink.query.all. Hit enter. And you can

drink.query.all. Hit enter. And you can see it's a list now with just one element, grape soda. So if you wanted to add another drink, what we can do is just go through that process again. So

we'll do this one in line. So we'll say db session add. And we'll create a drink. The name we'll call this one

drink. The name we'll call this one cherry. And we'll give it this

cherry. And we'll give it this description. And this cherry drink I

description. And this cherry drink I drink tastes exactly like this cherry ice cream. So that I used to eat. So it

ice cream. So that I used to eat. So it

tastes like that one ice cream. All

right. Perfect. Hit enter. and then db session.comit. Now let's check

session.comit. Now let's check drink.query.all. Hit enter. And now you

drink.query.all. Hit enter. And now you can see we have multiple elements. We

have grape soda and cherry. So then we can exit and go back to flask. Let's say

flask run. So we got our server running.

But now we need to create a way to get those drinks inside of this route right here. So, it's going to be pretty

here. So, it's going to be pretty similar to what we did earlier. If I can scroll up just a little bit. We said

bit. We said drinks.query.all. So, let's go ahead and

drinks.query.all. So, let's go ahead and do that. In this code right here, we

do that. In this code right here, we will say drinks is equal to drink query.all. And unfortunately, it's not

query.all. And unfortunately, it's not something that we could just put right here by saying drinks. That'd be nice.

Um, but I'll show you what happens. So,

what we can do is if we refresh this page and it says object of type drink is not JSON serializable. Uh, I've worked around trying to figure out how to make this as easy as possible. Uh, I I really

didn't come up with too many great ideas. Um, but here's basically what I

ideas. Um, but here's basically what I decided. We're just going to build a

decided. We're just going to build a list. Uh, so we're just going to

list. Uh, so we're just going to basically write out what the JSON should look like. So, we're going to say output

look like. So, we're going to say output is just an empty list. From here, what we're going to do is we're going to iterate through the drinks. So, we'll

say for drink in drinks and we're going to describe what it will look like inside of a dictionary. So, the end goal is to have a list of dictionaries. So,

we'll just say drink data is a dictionary where name comes from drink.name and the

drink.name and the description comes from drink.escription.

like so. And then once we got that dictionary, all we have to do is say output.append and pass in drink data. So

output.append and pass in drink data. So

that's going to add that dictionary to this list right here. And it's going to do that twice.

here. And it's going to do that twice.

One for each drink that's currently in in the database. And then what it'll do is we'll just say drinks and pass in output instead. So

now we have a nice list of dictionaries and that should be serializable. So what

we can do is do a refresh over here and there we go. We have an outer object and then key value pairs one key with the

pair of a list of dictionaries. So a

very similar format to how the API for Stack Overflow looked. Now what I want to do is I want to create the ability to pass in an ID in here. So, let's say we

passed in a one and we were able to get the first drink. So, let's go ahead and build that functionality. I'm going to clean up my screen just a little bit here because we're not going to need

this terminal right now. I'm just going to shrink that. And I'm going to hide our different files on the side there.

So, what we do now is we create a new route. So,

route. So, app.oute. And this is also going to be

app.oute. And this is also going to be to drinks. and then forward slash and

to drinks. and then forward slash and you can use less than and greater than signs to define a parameter here. So

that's going to be substituted for a specific number. Now a lot of people

specific number. Now a lot of people debate on whether this should be plural or singular since we're grabbing one drink. I decided to do it plural and

drink. I decided to do it plural and I'll show you why. So I found this stack overflow question singular or plural name of resource while creating it. And

this person talks in here and you know there's a bunch of different thoughts in here about the best way to do it. And as

I was reading this I looked up at the web address and I saw questions plural with the ID. So I was like I think I'm sold. I'm just going to keep it plural.

sold. I'm just going to keep it plural.

So that is why I decided that. So let's

go back to our code in here and we're going to create a new method. So we'll

say defaf get drink and this one's going to have a parameter ID. So instead of having a drinks variable, we're going to have a drink variable. And now we're just going to get a drink. So to do

that, we can say drink.query.get or

drink.query.get or

404. It's kind of a tongue twister there. And from here, we can pass in the

there. And from here, we can pass in the ID. That's going to give us a drink

ID. That's going to give us a drink object. And then we can just return that

object. And then we can just return that and build a quick dictionary. So we'll

say jsonify and we're going to build out the JSON. The key is going to be name.

the JSON. The key is going to be name.

That's going to come from drink.name. And then the second key is

drink.name. And then the second key is going to be description and that's going to come from drink.escription. So dictionaries are

drink.escription. So dictionaries are serializable instantly. You actually

serializable instantly. You actually don't even have to call JSONify here. So

you can just return uh dictionary like so. But sometimes

you'll need to call jsonify if you're not working with a dictionary. So I think that should work.

dictionary. So I think that should work.

Let's save and let's go back to our web page. And you can see we get one drink

page. And you can see we get one drink back. And we can try it again with ID2.

back. And we can try it again with ID2.

We get that second drink. And then we can try ID3. And we get not found because there's not a third drink in there. Now I wanted to show you real

there. Now I wanted to show you real quick. If you go back to ID2 here, you

quick. If you go back to ID2 here, you can rightclick inspect and get a little bit more information about this request.

So, hitting network and then do a little refresh. You can see this request here

refresh. You can see this request here and it's a get request. The response was 200. Okay. And you can see the content

200. Okay. And you can see the content type is application JSON. It's a little bit different than if you're on a web page. What we can do is we can inspect

page. What we can do is we can inspect on here and go to network. Get that first request on here.

network. Get that first request on here.

And that's 200. Okay. Also a get, but this time the content type is text/html. So yeah, just want to call

text/html. So yeah, just want to call that out for you guys. Let's go ahead and go back. And now I want to talk a little bit about adding a new drink. So

let's go ahead and create another route on here. We'll say

on here. We'll say app.oute. The path is going to be

app.oute. The path is going to be drinks. And you can actually have

drinks. And you can actually have another parameter in here which is methods and say post which is good to do if you're defining for a post request.

You can put any of the methods in here.

You could put get or delete or whatever.

And you can actually condition. So you

could check to see what method the person's requesting. So you could you

person's requesting. So you could you could in theory define all of this in one method and then you know check to see if

they're trying to get all the drinks or add all of the drinks. However, I like to just have a little bit more separate.

So I put them in separate methods here.

And we'll just create a separate method.

So add drink. Now this one's going to be a little bit more complicated because we actually have to get the request data.

So when the person calls this, they're going to pass in the structure of what a drink should look like. So we're going

to get this by creating a new drink. And where are the attributes for

drink. And where are the attributes for the drink going to come from? Well, the

name is going to come from request.json. So that's how you can

request.json. So that's how you can access the JSON data that they send.

It's through request.json. And we're going to be

request.json. And we're going to be looking for name. And we're going to do the same exact thing for the description. And that is going to come

description. And that is going to come from request.json

request.json description. There we

description. There we go. Now we can add these by saying

go. Now we can add these by saying db.ession.add and pass in the drink

db.ession.add and pass in the drink db.ession. Then what we could do, we can

db.ession. Then what we could do, we can return whatever we want. We could say successfully added. Um, or you could do

successfully added. Um, or you could do the ID. So if you wanted to return the

the ID. So if you wanted to return the ID, it's going to look like return ID colon drink ID. So that ID attribute is

going to be added to this drink object.

So that's pretty convenient. Save that.

And now let's give it a try. So we'll go over to here, but we can't really pass in the data for our requests really easily. So this is where Postman comes

easily. So this is where Postman comes in handy. So from here, what we can do

in handy. So from here, what we can do is we can define what a drink should look like in JSON inside of the body of our request.

And then we just set it to post. And

also, we'll want to update our web address. So you can copy that from right

address. So you can copy that from right here. Paste that there. And what we're

here. Paste that there. And what we're going to do is we're going to give this a name. Let's zoom in a little bit. What's

name. Let's zoom in a little bit. What's

the name going to be? Uh we'll call it cola. And then the

be? Uh we'll call it cola. And then the description is delicious. All right. So, just check

delicious. All right. So, just check everything is right. We got body, raw, JSON, post, and the correct web address.

Hit send. We got an error on line 42. Let's go back to our code real

42. Let's go back to our code real quick. Looks like we might have some

quick. Looks like we might have some kind of formatting issue here.

Unexpected name request. For request to work, I think we need to do another import from Flask. So, we'll say request there. And hopefully that'll do the

there. And hopefully that'll do the trick. I'm also getting another warning

trick. I'm also getting another warning down here. I think we need to uh take

down here. I think we need to uh take this and move it up a line. It wasn't

causing any issues, but best practice there. All right, let's scroll back down

there. All right, let's scroll back down in our code. And it looks like we don't have any more warnings. So, we will go back to Postman and hit send. And it

looks like uh we're making progress.

Okay. So the issue here is that we're not using the right web address. So we

need to go to drinks, no forward slash, and hit send. So that was nice that that worked. And in this situation, it

worked. And in this situation, it returns the ID of three. So now we can get all of the drinks. We can still keep this body here. We don't have to delete that. Hit send. And you can see all the

that. Hit send. And you can see all the drinks there. Or you could pass in the

drinks there. Or you could pass in the ID of three. Hit send and you can get that new one. Last thing I want to talk about is how to delete a drink. So let's

go ahead and go back to our code and create a new route. We'll say

app.oute. The path is going to be drinks and we're going to take the ID so that way we know which drink to delete. And then for the methods, we're

delete. And then for the methods, we're going to say delete. There we go. and

we'll say defaf delete drink. So for

this to delete a drink we're going to say db session delete and pass in the drink structure. The best way to get this

structure. The best way to get this drink structure I thought would just be to get it from the database. So we're

going to create a variable drink and say drink.query.get and pass in the ID. So

drink.query.get and pass in the ID. So

I'll take the ID as a parameter from this web address. And then after we delete, we say db.ession.comit. And I was having a

db.ession.comit. And I was having a little bit of an issue. Now in general, I haven't done a lot of like error checking and different edge cases.

However, I was getting it where I would delete a drink and it wouldn't exist and I would get an issue. So I decided just to add a little bit of extra casing here. So, if drink is none, what we're

here. So, if drink is none, what we're going to do is we're just going to return and I'm just going to say something like error not found or something. Or you could return a 404.

something. Or you could return a 404.

Just showing some different options here. And you know, if that doesn't

here. And you know, if that doesn't happen, then I'm just going to assume everything's good. And we're just going

everything's good. And we're just going to return uh we'll say message. And I don't know, we'll just say something like yeet.

There we go. Okay, let's test this one out. For this, what we're going to do is

out. For this, what we're going to do is we're going to do a delete. And we don't have to pass in anything with the body just to show you guys. I'll delete that just to make sure it's clear. We do pass

in the ID here, however. Hit send and it says yeet. If we hit send again, it says

says yeet. If we hit send again, it says error not found. So, that is how you do the most basic API calls. We have the

ability to get all the drinks, a specific drink, add a drink, or delete a drink. I didn't really do anything for

drink. I didn't really do anything for updating a drink, but a drink is so simple. Like, I feel like you could just

simple. Like, I feel like you could just delete a drink and then read it. Or if

you want to practice, you could try some uh put requests here. But that's all I got for you guys for the basics of creating an API in Python. It's a lot more to it, but hopefully that'll get you started.

Loading...

Loading video analysis...