ECommerce Web Shop - Build & Deploy an Amazing App | React.js, Commerce.js, Stripe

Video Statistics and Information

Video
Captions Word Cloud
Reddit Comments
Captions
hello everyone and welcome to another javascript mastery video this one is quite special because i have an extremely useful project to show you we're going to build a fully functional ecommerce application while building it you're going to learn many advanced react and javascript topics as well as how to use stripe for car transactions how to create an interface using material ui and how to create a scalable react folder structure on top of that at the end of this video you will have this unique and complex project that you will be able to add to your portfolio or who knows maybe use as your own ecommerce store and trust me e-commerce projects are impressive this video was made possible by commerce js usually to create a fully functioning webshop you'd need to spend weeks and even months building it thankfully using commerce.js we just have to build the front end and use their api for everything else it's amazing i'll show you how to use it in this video now allow me to give you a quick demo of the entire application as you can see we have all of our products visible in this modern storefront we'll be using material ui to achieve this look every item has its price and we can add as many of them as we want to our cart just by clicking this icon we just added one lamp let's add a keyboard and let's also add a mouse let's say we're done with chopping and we want to check what's inside of our cart in here you have a nice overview of all the items in the cart you can increase or decrease the quantity remove the product or empty the card completely after you're ready we can move to the checkout let's add all of our shipping details in this case our name is john wick we live in 47 paris hill lane in california what's really important to notice here is that we as the store owner can choose which countries do we ship to and what are the shipping costs by default i've set it to france here but of course you can switch to united states and then as you can see all of the subdivisions are populated so for example if we switch back to portugal in here you can see these subdivisions of portugal and the international shipping costs of 10 but if we switch back to united states these shipping subdivisions are repopulated we can choose california here and also the shipping options are changed to domestic finally we can go to payment details review our order and enter our payment information for this we're using stripe stripe has a demo card that we can test on and the demo cards card number is 424242-424242 and you guessed it for two then you can keep pressing four two for the cvv and for the zip code that's it after we entered our demo card or a real one you can click pay and that's it our transaction has been made but that's not the end commerce gs will also send a confirmation email both to our customer and to the store owner let me show you this is the email that the store owner gets it just lets him know that somebody made an order for 140 dollars but if we go to the john wick's email in here you can see all the details you can see if his item has been shipped you can see his name and shipping details and you can also see the complete order summary also just so i don't forget the application is fully mobile responsive it looks like it's made for mobile we can view all of our items here we can add them to the cart we can check out the card everything works and finally the form itself is fully mobile responsive and that's it this was a short demo of the application are you excited to start building it let's start right away [Music] as always we are starting completely from scratch so you can head to your desktop and create a new folder you can name it anything in this case let's do something like e underscore commerce just like that then what you want to do is open a clean visual studio code window and finally just drag and drop that ecommerce empty folder in here once that is done you can head up in here go to view and then finally to terminal that's going to open the built-in terminal inside of here as always you can just run mpx create react app dot slash this is going to initialize a new react application inside of the ecommerce folder you just created i'm going to wait just a minute for this to install and i'll be right back the first thing we're going to do is install all the necessary dependencies so we don't have to go back and forth installing one by one npm install and let's start with at material dash ui forward slash core and also add material dash ui forward slash icons then we can also install add ch ec forward slash commerce.js this dependency is going to be the most important one here that's going to be managing our commerce then we can also install at stripe forward slash react dash stripe dash js and add stripe forward slash stripe dash js then we also have react router dom as well as the react hook form and i think that's going to be it for now if we need anything else we're going to add it later and now that i noticed this line is quite long so i'm going to actually leave this in the description so you can just copy and paste and not bother with misspelling some of these names here i got you there again while this is installing i'll be gone for a second and i'll be right back and we're back to start off we're first going to delete the entire src folder because we don't need most of these files so just go ahead right click and delete it then we're going to create a new src folder and in there you can create a new index.js file we absolutely need to have this index.js file so just feel free to do that in here we'll do just the usual stuff import react from react and also import react dom from react-dom finally we're also going to import the app so that's going to be import app from dot slash app it doesn't exist yet but we're going to create it soon and finally react dom dot render in here the first parameter is our actual app component which is going to be our entire application and the second argument is document dot get element by id and that is going to point to our root div great that's it just for a second if you're not sure let me show you where this root div is so i'm going to head to public and then in here in this index html this is usually just a bit messy so i like to clean this up delete these delete all the comments and easily you'll be able to see that the only thing that we have in here is just a title and in here we have our div with an id of root while we're here let's also change this to e commerce and what you can do is also change this link to the icon feel free to add any favicon image you want great now that we're here we are ready to create our app.js component inside of here we're going to create a functional component we can do that using rafce which allows us to easily create functional components and most of you guys have been asking me which extensions do i use so let me go to extensions and let me show you in here i use some of the basic ones like autorename tag that's going to allow me to switch the name of the tag like this then i also use bracket pair colorizer that simply colorizes the brackets so i know where which one is ending we have a few for different programming languages but this is the one you want to have es7 react redux refuel snippets so after you install that you'll be able to run rafce and that's going to give you this component automatically great now that we're here let's say e-commerce and this is going to be our demo component now with this i think we are ready to start our application let's go ahead and simply say mpm start if we've done everything correctly our app should start on localhost 3000 and there we go we are live as you can see just small little title here ecommerce on the top left that means we're good to go now we can close our terminal and start creating the layout first things first we're going to create a components folder in the src and inside of there we're going to create a products folder great inside of that folder we're going to create a new file and the name is going to be products dot jsx inside of the product.jsx component we're going to start creating our products layout so we can import react from react we can also import grid from add material ui forward slash core and that's going to be it for now finally we can create our products component that's going to be cons products is equal to a functional component and don't forget to export it at the bottom export default products great now instead of here i'm going to create a main this is basically just like a div but it has some meaning to it then inside of there we're going to add a grid that is the material ui grid which allows you to kind of put your items in a grid this is going to be the grid container so you can type container in here and say justify is equal to center this is going to justify the content in the center and we're going to give them a spacing of four now inside of here we can put our actual products so for now we're going to just mock the products later on we'll be fetching them from the commerce.js api so in here let's create a few products just on the top i'm going to create a product array and then inside of that array we're going to have a few products each product is going to be an object and it's going to have its own id so we can say id1 it's also going to have a name so in here let's say choose it's also going to have a description so let's just say description is equal to running shoes great so this is our first product and the second one is going to be the same it's going to have the id of two it's going to be a macbook for example and inside of here we're gonna say apple macbook great now inside of our container we can use the opening and closing curly brace to indicate that we'll be writing javascript logic inside of the jsx and then inside of here we're gonna say products.map in here we get each product and now for each product we want to return something specific so what do we want to return for each product inside of there we're going to have a grid this time our grid is going to be of type item and it also needs to have a key in this case the key is going to be product.id every time that you're looping through something in jsx you need to have the id inside of there we're also going to say xs is equal to 12. this means that this is going to take full width on mobile devices for small devices it's going to take 6 spaces out of 12 which means that two of them will be in the same row and then for medium we can do something like four and finally for a large we can do three great so this is now our grid component we of course have to close it and inside of our grid we can put our product component so this here is going to be a singular product component which we didn't create yet we're going to create it soon so this is it now of course we have to create that component so just inside of here inside of components i'm going to create a new component which is going to be called product more specifically i'm going to put this product immediately inside of the products because that's the only place where we'll be using it in here you cannot see really well but what's happening our product is inside of the products folder our product is also going to have a product.jsx file inside of here we can use that trick i showed you r-a-f-c-e and that is immediately going to create a react functional component for us inside of our product we are actually going to have all the layout for one specific product meaning the image the description the title and everything else that goes with it so we'll have to import quite a few things from material ui in this case that's going to be card also card media card content card actions typography and finally icon button these are all the things that we're going to import from material ui in this file so we can say from add material ui forward slash core and also we'll be using one icon in this case that's going to be add shopping cart and this is coming from add material ui forward slash icons keep in mind that these are named imports so all of these have to be named exactly like this if you want to see what each component does i would strongly encourage you to take a look at the material ui documentation you'll be able to find more details about each one of these components and for the icons the same thing great now that we have these components let's start creating our card so our product is going to be a material ui card it is just a card component and also we'll start adding some classes right here for this whole project it's not about css right i don't want to bore you with css so i'm going to provide you with all the css styles for it for now i'm just going to let you know what are the names of the classes for each specific element so in here we're going to have a class name of classes.root then inside of the card we're going to have a card media which is going to be a self-closing tag that card media is going to have a class name of classes dot media finally our card media needs to have the actual image so we can say image is equal to and then in here we have to provide the image that our card is gonna have so this here is gonna be the image for a specific product unfortunately we don't have one so i'm just gonna leave this blank for now later on once you fetch the actual products you'll be able to see that image right here and also let's give it a title the title is going to be product that name you might be wondering where is this product coming from well since product is a sub component or a child component from a product jsx we're calling it right here and we can pass some props in this case it's only going to have one prop which is going to be the entire product we're looping over so you can see in here we have two mock products and we're looping over them and we're sending each one one by one so inside of the product jsx we'll have access to the product.name product.id and also product.description great so in here that's how we got this name moving further we're going to have a card content just below this card content is not going to be a self-closing tag inside of there we're going to have a div that div is going to have a class name of classes dot card content inside of there we're going to have a typography typography is used for any kind of text in material ui in this case this typography is going to be a variant of h5 which means that it's a medium large heading and also it's going to have a gutter bottom which simply means it's going to have some space on the bottom inside of there we want to render our product more specifically product dot name just below that we're going to have one identical typography so we can copy this one it's also going to be the variant of h5 it's not going to have the gutter bottom though and in here we want to render the price for now our products don't have the price so let's add it in here i'm going to add a price to each one of these products so i'm going to say price and we can do something like a string and we can say dollar five and this one is going to be dollar ten great now inside of here we know that we can reference product dot price and you can see it's red which means that we still haven't imported it of course it's coming through props so we could either do this props that product that name props that product that price but not repeat ourselves remember the dry principle don't repeat yourself we're going to simply the structure the product from the props great so now we have our products don't worry about the classes we're going to figure that out later moving on below this div we're going to have another typography this typography is going to have a variant of h2 and it's going to have a color of text secondary which means it's going to be a bit grayish finally in here we're going to have our product dot description great moving on below the card content we're gonna have card actions card actions is going to have a prop of disable spacing and also a class name of classes dot card actions inside of our card actions we're going to have an icon button and that icon button is going to have the area label and that's simply going to say add to cart so if for some reason we cannot see the button on some user screen they'll be able to read the text for most users we just want to show the icon so inside of the icon button i'm just going to call the add shopping cart and this is our icon later on we're going to hook this button to the add to cart function from commerce.js i see that i misspelled the icon button at the top so i'm going to solve that and now the last thing to solve is to import these classes so what are these classes and where are they coming from inside of our product folder i'm going to create a new file in this case that's going to be styles.js file this is going to be the file where we're going to style these components i'm going to write this only once for people who want to learn this but later on i'm just going to give you all the styles so you can simply copy and paste them the link is going to be in the description you'll be able to find each styles js file separately and also if you're stuck with absolutely any error the link to the github project is going to be down in the description even if you don't have any problems make sure to go there right now and give this project a star great so that's it we can import something known as make styles it's a named import from add material ui this time it's going to be forward slash core but also forward slash styles great now the only goal of this file is to say export default which means we'll be exporting something and that something is the call to the function make styles function make styles takes in one parameter and that is yet another callback function inside of there with an instant return so what you do with an instant return you wrap it in parentheses and then you return an object inside of this object we're going to write our styles and these styles are going to be written in css in js kind of way for example we have this classes that root let's see how that's going to look what you have to do is specify the name of the styles and then in there you need to say max width in this case and we're going to set it to 100 so this is how you do it not with dashes in between you do it in camel case and all of the things on the right need to be inside of strings i know i know it's not ideal but that's just how it is with material ui and trust me if you follow these rules your life is going to be so much easier great so now that we're exporting this we can go back inside of our product js and see how we can actually make use of these styles we created the only thing you have to do is import use styles from dot slash styles so these are our styles and then inside of there you can see this already starts like a hook right use styles so what do we do with hooks we say const something in this case classes is equal to use styles and then we call it this is going to allow us to have our styles if you save that you can see we have no more errors and that is it now if we go back to style.js just with a bit of copy and paste magic these are going to be the styles for our specific component only for the product js we're going to have a new specific styles.js file for each specific component this way you don't have one thousand lines css file you're gonna have multiple ones so you know which files refer to which component as i said from now on i'm gonna be just copy and pasting all the styles but don't worry just head the description and you can follow along great this is it for our product js file remember we're using it in here so we have to import it inside of our product js so inside of here import product from that's going to be dot slash product forward slash product if all of this is okay we can head back to the app and actually show the products component so we can say import and that's going to be products from dot slash components and then forward slash products forward slash products one more time to get into this component i told you we're gonna focus on the scalability and better folder structure so later on we're gonna definitely fix that and i'm gonna show you a much better way of importing components great but now we just wanna have one simple products component rendered right here let's save it and let's see if it appears in the browser okay so looks like we have just one small typo right there looks like that in the products we're using a default import where we should be using a named one specifying that we want to have a grid component from the material ui core if we save this we should be good to go that's it for the grid and of course in here we have to have a return statement so i'm gonna write a return statement and finally just put this main right there so that we know that our component is returning something let's see if our product is returned it is so when this compiles we should be able to see our products there we go our cards but this doesn't look too good we're missing the image and also our description is too big so give me a second and i'll find the images for both the macbook and the running shoes okay so the only thing i did was just add the image url right here as another property inside of our products array in here we have the image property and now going to the product what we're going to do in here instead of this empty image we're going to say product dot image and also i noticed that we put here h2 but this should be body two that way it's gonna be a bit smaller if we save this and go back there we go this looks much better but trust me once we add real products and real images this is going to look even better after the products are done we can of course create our navigation bar so right click the components and then inside of there create a navbar folder inside of the navbar folder create a navbar.jsx component you can use js you can use jsx but mostly for components that contain jsx i use the jsx extension inside of there you can write rafce as we always do or just simply create a normal functional component and then in here we're gonna create our navigation bar it's gonna be a bit of work because our navigation bar is going to be fully mobile responsive in here we'll also need to import quite a few things from material ui and that's going to be app bar toolbar icon button we already saw that something known as a badge that's the little thing representing how many notifications or how many items do you have then we have a menu item we also have the menu itself and finally typography as we learned we use that for any text element and all of that is coming from add material ui forward slash core inside of here we're also going to have one icon that's going to be import shopping cart from add material ui forward slash icons now let's create the layout of our nav bar in here we can leave this as a div but we can also put it as a just empty react fragment inside of there we're going to have a component called app bar which is basically a navigation bar it's going to have a few properties the position is going to be equal to fixed class name is going to be equal to classes dot app bar and color is going to be equal to inherit inside of there we're going to have a toolbar that toolbar is going to have a typography this is going to be our logo and our brand so in here we're going to have an image and also the name of our shop so what we can do is we can say image that's going to be a self-closing tag image of course needs an src which we don't have yet and then we can have an alt tag in here we can say the name of our shop i'm going to call mine commerce dot js and also it needs to have a height so i'm going to leave the height to 25 pixels and let's give it a class name we can say class name is equal to classes dot image this is our image and the just next to our image or below it i'm going to put the name of our brand commerce dot js you can call this anything you want this is your own shop feel free to make it your own great of course this typography has to have some kind of variant so it's going to have a variant of h6 and also it's going to have a class name of classes dot title as well as caller is equal to inherit now we got to figure out what are we going to use for our image i already prepared something but feel free to find your own image on the web usually what you do is inside of the src you create the assets folder and then inside of that assets you put your image so in this case i have a commerce.png just a simple icon image inside of here i'm gonna import that so import we can call it logo from dot slash assets and then slash commerce dot png i just noticed it's not going to be just dot slash is going to be dot slash dot slash and then assets and then commerce.png so now we can use this logo right in here great this is going to appear on the left side of our navigation bar in the middle we're going to have a self-closing div which is simply going to have a class name of classes dot grow that means that this div is going to take as much space as we need so we're going to have this on the left as much space as we need and then finally something on the right and the thing on the right is going to be another div in this case it's going to have a class name of classes dot button inside of there we're going to have an icon button that icon button is going to have an area label of show card items and it's also going to have a color of inherit inside of there we're going to have a badge our badge is going to have a badge content property and that is going to be equal to the number of items that we have so how can we know that well right now we cannot so let's just say 2 in here but later on that's going to be coming dynamically then the color of the badge is going to be secondary and inside of the badge itself we're gonna have the icon and the icon is simply shopping cart as we specified above let's not forget to import the styles so inside of the navbar i'm going to create a styles.js file and as we mentioned we're simply going to copy and paste all the styles then what we need to do is the same thing always just import use styles from dot slash styles you can just copy and paste this and finally as we mentioned you're going to get used to it const classes is equal to use styles and you call it as a function great this is only half of the navigation bar but let's go ahead and see how does it look like the first thing you have to do is import it inside of the app.js so what we can do is we can say import in here navbar from dot slash components forward slash navbar forward slash nav bar you can see that we have a lot of repetition here and later on once you have three four five ten or a hundred components this is going to get really really messy so let me show you a much better way to import all of the components inside of the app.js we're going to import it like this inside of here we're going to have just one import statement and we're not going to be importing components separately so how do we do it we can say import named import products and navbar named means that it's inside of these curly braces from dot slash components that's it take a look at how simple this is is it simply makes sense dot slash components give me the product and give me the navbar from the components so now we can get rid of this but for this to work we have to do one thing inside of our components we need to create an index.js file from this one index.js file we're going to export all the other components and this is how we do it export default as navbar and then outside of the braces from dot slash navbar forward slash navbar so now we're moving all this boilerplate code right inside of here and we can do the same thing to our products so in here export default as products from dot slash products forward slash products and now our app is gonna know where these things are coming from of course now we can render our navigation bar right on top of the products finally let's save it and go ahead and see how does it look like there we go take a look at this nice navigation bar we have our brand right here and we also have our cart looks pretty good it also has the number of elements in the card which we're gonna make dynamic of course and looks like i was wrong we were not half done with it we're fully done let's take a look how does it look like on mobile i'm gonna open inspect element and click toggle device toolbar and take a look this looks really responsive what we have to do is we have to add the height of this navigation bar as a margin to our products because as you can see right now our navbar is hiding our products and that's not something you want so let's head to products and see where the problem is coming from i just noticed that we don't even have the styles for the products so inside of the products folder i'm going to create a new styles.js file and you already know the drill copy and paste the styles go back inside of the products and then in here simply import import use styles from dot slash styles and then just on top of our products cons classes is equal to use styles and call it as a function now in here what styles do we want to add first of all our main is going to have a class name of classes dot content below that we're gonna have one self-closing div div that div is going to have a class name of classes dot toolbar and this is going to add the height the exact amount of pixels that the nav bar has so it's going to push our content just a bit below and looks like that's all that we need if we save this let's go ahead and take a look how does it look like and there we go our content is pushed just a bit down and we have this nice grayish background we're done with the navbar now that we're done with creating the basic layout we can start fetching real products from our commerce.js store to do that we can go back to our code and inside of here inside of the src folder you can create a new folder called lib as library inside of there you can create a new file called commerce.js inside of here we're going to import commerce with a capital c from add commerce.js like this this is what we installed previously now we can export const commerce with a lowercase c is equal to new commerce we're basically creating a new instance of that specific commerce and that is going to be our store now inside of here as the first parameter we need to put our public key from their store to do that of course we have to go and create a new account in the commerce.js so once you're on the commercejs.com i'm going to put the link in the description you can go ahead and click get started for you there's going to be one step prior to seeing this and that's going to be a question with what do you want to log in is it github is it google or simply by email and password i already did that so it's already asking me to create a store so just go ahead and register and you'll be right at this step which is creating the store in here you can specify the name of the store we can do something like commerce js then in here you have your merchant email and below you have your primary currency in this case it can stay as usd now you can click continue we're now in there they gave you this nice setup guide but we're not going to use that because i'm going to teach you how to do everything so inside of here we already have our orders the first thing that we have to do is find our own api key to do that you can go under developer and settings so that's on the left side fort icon and then settings in here you can find your own public key what you need to do for now is simply copy and paste it we're going to copy it go back to our code and now we're not simply going to paste it here that wouldn't be good we want to store all of our api keys somewhere else developers create a new file for that the file name is going to be dot env this is a special hidden file which is not going to be pushed to github it stands for environmental variables these are variables that only you can see on your pc in here we're going to create a new variable and that is going to be react underscore app underscore check underscore public underscore key just like that a long name but we know what it is and now in here you can paste your own key great now how do we get access to that key from here well you simply need to say process dot env dot and then the name of the key in our case that was react underscore app underscore check underscore public underscore key you can name it anything you want but it needs to start with capitalized react underscore app great now for this to take effect we have to restart our terminal so in here we're going to start npm start one more time you close it with ctrl c and then start it again with npm start we also need to pass one more argument to this new commerce and that is going to be a boolean value of true meaning that this is going to create a new commerce store great now we have this object that we can use all across our application so what can this commerce instance do well let me tell you usually for creating a fully functional webshop application you would need a full backend api with all the routes for fetching the products creating the products deleting them updating them selling them you need authentication and a lot more things all of that is stored in this little instance and that is going to be import commerce from now we know where it is dot slash lib forward slash commerce this is it we're gonna be using this commerce instance to do all of our back and stop for us allowing us to completely focus on the front end so first thing we want to do is maybe fetch the products so inside of here let's do exactly that inside of our app.js i'm going to create a new state cons products and then we also of course have the set products and that's going to be equal to use state and by default our products are going to be equal to an empty array of course we have to import the use state from react so let's do just that and now how do we populate these products well of course we sometimes have to fetch it so first let's also import the use effect we're gonna use that to fetch the products immediately on the application load so just right here we're going to create a new function called fetch products and that is going to be an asynchronous arrow function so async and then arrow function if you haven't worked with async functions before it is just like using that then and that catch but the code looks much more cleaner and looks much more like synchronous code so what do we want to do well we want to fetch something we want to fetch the response from a weight so we have to await something and that something is going to be a specific api call to this commerce instance and it's going to be as simple as saying commerce dot products dot list and then you call it as a function this is going to return a promise so we have to await to see what is inside of that promise once we get the response we can this structure the data from that response and this data is going to be our products so for now what i want to do is i simply want to say set products and then we're going to set the data inside of the products now our products are going to be populated but as you can see right now we're not using products they're never being used and we're also never calling this function so let's first call this function to do that i'm going to create a use effect call more specifically a use effect hook this use effect hook is going to have its dependency array set to empty which means that it's only going to run at the start on the render in class based components this was called a component that mount inside of here we can use that function call and simply say fetch products and call it this is going to call our commerce product list and set the products to the state now we can console log the products and we can head back to the browser and see if we have anything in here i'll open the console by right-clicking and then clicking inspect and there we go first we get an empty array and then we get back undefined so let's see what's wrong i wasn't even expecting anything because if we go back to our commerce.js and go to products right here the second icon you'll be able to see that our products array is completely empty we haven't added any products yet to create a product you can click this add product button on top right and then inside of here it is as simple as entering the name description sku which is just a specific id and the quantity of the product in this case may the product simply be something like a keyboard i'm gonna leave this sku empty it's gonna auto-populate it same thing for quantity if you don't put quantity there it's gonna have an unlimited quantity and description can be something like black magic keyboard in here you can set the price you can specify a price like 65 dollars but you can also specify pay what you want in this case we don't want that and now i'm simply going to grab an image of some kind of a keyboard let me do that and there we go as i told you it is as simple as that finally this is going to be a physical product so we have to choose the shipping options in this case by default we can enable it in the united states but let's say that you want to have worldwide delivery with some different shipping fees we're going to save this now and let's head to the shipping section to see what else can we do there to go there you can head to this fifth icon right here and click shipping in here you can see that we have one zone right now which is united states but you can add another zone in here we can say something like international for the international we can of course add countries let's add a few countries from europe that have a lot of regions for example albania we can do austria bosnia belgium and so on let's just scroll down and add a few more let's add switzerland germany denmark spain and i think that's going to be enough for now as you can see you can add absolutely any country in the world and their api automatically fetches all the regions for that specific country i'm going to show you what i mean in a second now we can add these countries they are now added to the international zone and finally you can specify the international shipping so in this case let's do something like ten dollars and you can click add shipping zone of course we have to specify the name we're gonna say international if you do that you're gonna see shipping zone added and now we have domestic zero dollars for shipping for united states and also international now we can head back to products we can head back to the keyboard we just created and inside of here now you can add that international shipping to all of these countries and as you can see it has a base rate of 10 and then you can specify additional shipping fees for this product but all products in the international zone are going to have the base rate of 10 for shipping great that's it for our keyboard let's save it and then head back to our website to see if we can see it there right here i'm gonna refresh and for now we just expect to see a kansa log and would you look at that in here i'm gonna make this just a bit bigger for you we have first an empty array on the load of course and then we have one object inside of there and as you can see this is our product commerce.js automatically created all of these things create a date description has digital delivery images is it active is it not the name the permalink the price even the formatted price the shipping options and everything else you might need so this is our product now let's add a few more products to make this look just a bit nicer i'm gonna head back to adding the products go back to the products and now i'm gonna add a few more i'll just add all the products that i had in my original shop but feel free to add absolutely any products you want your shop maybe can have a specific purpose it can only be for keyboards or only for headphones or only for absolutely anything you want maybe you sell some art as well so feel free to really personalize it add your own products play with it and see what else what other fields can you add to the products you can also see that they're covering seo so you can specify the search engine title description definitely something you need in your ecommerce store for now most likely i'm going to speed this process up for you i'm just going to add eight basic items [Music] [Applause] [Music] [Applause] [Music] [Applause] [Music] [Applause] [Music] [Applause] [Music] [Applause] and there we go our eight products are here of course you don't have to add all of them you can have just one for testing but it's nice actually seeing something in the shop while you're doing it if you want to i'll post the link to my deployed version online so you can take a screenshot and just copy all of these items but again just feel free to make it your own now if you refresh this page we should be able to see eight different products right here and as you can see our array is now filled with eight objects now instead of these two mock products let's actually display all of the real ones to display the products we have to pass them as props to our product component and you might be wondering why do we have our products in the app if we only use them in the products well we only use them in the products right now but later on our cart and most of the most important things are going to be inside of the app so are the products so with that said let's now pass our product as a prop inside of the products function we just did that and now if we go to products right here we can now get the products right here as props of course we can immediately destructure them and use them like so we no longer need these mock products so we can just delete them and now we're mapping to the real product for each product we are sending that specific product object inside of our product component so most of the work now is going to be done inside of the product component itself we can head there and see what's happening we are receiving the product and now maybe not all of the things that we had here like the name and the price are going to be identical so we have to check what does each one of these specific objects have which properties maybe it's not going to be the name maybe it's going to be product name or maybe title so let's take a look and see if everything is good this here should be product and just so we don't get an error right now i'm going to return simply a div that says test so we're not going to be returning this whole thing i just want to first see what is actually inside of the product great so now we can head back and if we refresh we should be able to see that we get eight different kinds of logs and there we go this looks quite bad right now but we actually do see eight tests and we can see each object so which properties do we need from each one of these objects well we're definitely going to use the name here the image is actually under media and then source and price where is the price price and then formatted with symbol or formatted with code now we have to actually use these properties so let's go back and make these changes i'm going to remove this now and in this case inside of our image the image is not going to be simply product that image it is going to be product dot media dot source product name stays the same then inside of here we have product.name that is the same in here we can say product dot price and then we have formatted with symbol so we can take that and we can simply say product dot formatted with symbol but i think i'm missing the price before great then inside of here we're getting product dot description so we can see how that looks like and for now i think that is going to be it so let's actually save it and see how does that look like there we go as you can see this already looks so much better you can see in here we have some html tags we don't want to have that we just want to have a simple description so how can we solve that well we need to render that html as a real html instead of simply rendering the description as it is it is being returned as html so we have to actually render these html tags to do that you can go inside of this typography and say dangerously set inner html that accepts an object so feel free to put one curly pair brace and then one object inside of it there we have underscore underscore html colon product dot description so this is basically going to say to render our description and then we can go ahead here and remove this description and make the typography a self-closing tag just like this great so now let's save that and see if our html tags are gone and would you look at that all the tags are gone this now looks like a real e-commerce shop one that sells keyboards kettles books coffees everything basically you need great so now what do you think is our next goal what would you do next in my opinion maybe making this button clickable and actually making the car dynamic makes sense we have to be able to actually add these items inside of our cart to start using the card we have to first of course create it and that's again done by commerce gs so right inside of here our cart is going to be yet another state in react more specifically it is going to be an object so in this case we can say use state and then say cart and set cart and by default that card is going to be equal to simply an empty object now we have to see what is in the cart so to do that we're going to create yet another function const fetch cart that is again going to be you guessed it an async function and inside of there we can basically do a really similar thing const in here we get some kind of a response we always do from an api call so what we can say is a weight commerce dot cart dot retrieve and then we call it as a function as you can see i think you can start noticing the pattern commerce that something that's something it is that easy to get the items from the list to get the cart items to actually add the item to the cart to buy everything it is as simple as using it is as simple as using the simplest api no need for back end at all great so in this case our actual response is the card so we can say khan's cart is equal to a weight commerce dot retrieve and now inside of there we of course do set cart and finally just set the card inside of here this is kind of redundant because we're creating a variable and then simply reusing it down there what you can do is not even create a variable but simply immediately use the value of this api and that's going to allow you to simply call setcart await commerce.cart.retrieve that is it this is basically getting the card and then immediately setting it to the state as you can see our fetch card is declared but never used so what we can do is just after we fetch the products we can immediately fetch the card as we did the last time let's simply console log the card to see what is in there here's our card at the start we get car does not exist but then later on our cart is populated our cart has a creation date the currency discount codes expires and a lot of different things but the thing we are looking for is line items in here are going to be all the items we actually add to our cart and the subtotal in the subtotal you're going to have the total price of the items that are currently in the cart to add the items to the cart we're going to create yet another function const handle add to cart this is going to be the function that's going to add the products to the card it is going to be an asynchronous function and it's going to accept two different parameters the first one is the product id and the second one is the quantity so how many products do we want to add to cart and what you have to do there is again do the same thing const we get some kind of a response is equal to a weight commerce dot cart dot add and what are we going to add to the card well we're going to add a product with the product id like this and how many products are we going to add we're going to add the quantity amount of products and i just took a look and i misspelled it so to recap our handle add to cart is expecting two different params the product id and the quantity and then we use these params to pass them over to the api and to add the product to the card the thing that we get back is going to be the item and then finally in here we can update our card so set card to item dot card so this is the card after the item has been added now we don't want to use this handle add to cart here because in the app you can see we have nothing we don't have any buttons where we want to use it is inside of products component more specifically product singular product but now let's pass it over as a prop to products in here we can say on add to cart is going to be equal to handle add to cart now we know that our products is accepting a on add to cart prop and that is the function that's going to add our item to the cart now where do we use it we don't have any buttons here as well well we're gonna pass it as a prop one level deeper into our product now if we go to the product in here we know that we are again getting the on add to cart handler and what we need to do is simply call that on the button click so right below this is our button card actions and then we have the icon button so on that icon button you can say on click and what is going to happen on click well we're going to call the on add to cart so we're going to add to cart our element on click now what i want to do is i want to actually console log the cart after we change that after we add one item so we're console logging it here and i'm interested in seeing if it's going to change once we click on that specific thing but i think we forgot something we don't want to call it like this because it's not going to know which thing are we adding so we have to make it a callback function so it doesn't call itself immediately in here we want to call the on add to cart and we need to pass two parameters remember the first one is the product id and we have that stored under product dot id this is a specific individual product so for each one this is going to be different that way when you click this button it's going to know that it's for the kettle or when you click on the keyboard it's going to be for the keyboard and then the second thing is the quantity and in our case the quantity is always going to be one we add items one by one of course you can modify this but for now this is all that we need now if we go back and refresh we should be able to update the cart depending on the click for now you can ignore this badge on top right remember this is still static we haven't changed that but now if you clear the console and click here we get a new card that has line items and in here you can see we have one item in there and that item is the kettle of course let's add a keyboard and then we get a new updated card that now has the line items of two and has that keyboard inside of it how simple is that now we have to use the data from the card to display a dynamic icon right here to do that we're of course going to head to the nav bar and then in there we somehow have to get the information about the card of course what we're going to do is go back to the app and then simply pass it as a prop so we can say total items is equal to cart dot total items that is simply going to be a number of items in the cart now that we are passing that we can go back to the navbar we are now expecting that prop right here and where is our badge there we go in here batch content we just change that to total items and that's going to be it if we now go back and refresh the page you're going to also notice one thing our cart is not going to be empty it remains it persists that's what api is doing for you that's why commerce.js stores everything you don't have to worry where you're going to store the items so now we already have two that is kind of deceiving because we had two fake ones before but take a look at this if i add the book the book gets added if i add the coffee or the mouse this number right here gets updated and our full cart also gets updated with the items that we add great now we have the data for the card but what we have to do is create the layout for the card so what happens once we click on this button we have to be able to see all the items that we currently have in the cart and we have to be able to add more items remove some items or just head to checkout let's start with creating our card layout inside of the components folder we're going to create one more folder which is going to be named cart inside of the cart we're gonna have a cart dot jsx file this is going to be our cart component and as always we can do a react arrow function component with exports rafce or simply import react create a constant and then finally export it at the top we're going to import container typography button and grid from add material ui core now let's create the layout of our cart inside of here we're going to wrap everything with a container component it is like a simple div but material ui provides some spacing paddings and so on we also have to have that div which is a self-closing div remember of a class name classes dot toolbar so this is going to be the same one the one that simply pushes the content a bit more down so that it appears under the navigation bar we're going to add the classes after we're done with the layout below that we're going to have a typography that typography is simply going to say your shopping cart and inside of there it's going to be of a class name classes.title and a variant is going to be equal to h3 below that we're going to have two different options we're going to have some kind of a variable which is going to say const is empty just like that const is empty and in here we'll have to figure out the logic if our cart is empty or not and then we'll display different content based on that if the variable is empty so if the card is empty then using the ternary operator we can show for example an empty card so i'm going to say empty card this is going to be a sub component we're going to create else we're going to show let's do filled cart so these are our two functional components and we can create them right here inside of our cart these are just going to be simple elements so what we can do is we can say const empty cart it should be cart not card empty cart is equal to a function or a functional component which is simply going to return some kind of jsx so let's render that if the card is empty in there we're going to have a typography that typography is going to be of a variant subtitle one this typography is going to say you have no items in your shopping cart start adding some exclamation mark there we go so this is if we have no items in the card and if we have some items in the cart then we want to render a normal cart and that cart is going to be a bit larger component so we can say const filled cart is going to be equal to a functional component don't let this layout mess with you these are not let's say sub components of a component functional components and so on this is just the normal function that returns some jsx and because of that we can call it like this what you could have done is simply say generate empty card and then call it in a different way but this way it is easy to see that these are like sub components at least they appear to be but this is just a function which is returning some jsx great so this here is our filled cart and that field card is going to have an empty fragment inside of that empty fragment we're going to have a grid because we'll have to render all of the items inside of that react fragment we're going to have a grid that grid is going to be of type container and it's going to have a spacing of three inside of there we'll have to loop through our cart items so right now we don't have any cart items but we don't even have the card here so let's pass our card through the props from app.js to our cart jsx inside of here we have our cart in the state as you can see right here so the only thing we have to do is first of all well call cart right here right so inside of here instead of the products now i'm gonna simply call the cart we're calling the cart component and we're gonna pass the cart as a prop right right now i commented out the products component but later on we're gonna implement react router so we can actually navigate between the products and the card so far we just wanna see how the card looks like and don't forget to import it at the top just like so how easy it is now that we have this system we can simply say card here and then back in the components index.js in here we can simply copy the line and say export card so we're now exporting the card and then inside of the app we can simply import it this way and now you know that you're passing the card as a prop so back in the card component we can expect that card right here as a prop so how do we know the card is empty well what we can do is we can say if cart dot line items this is an array so we have to say dot length is lower than or we can say is equal to zero right if it's equal to zero that means that our cart is empty what you can also do is simply put an exclamation mark at the start and then delete this why does this work well if the card is empty this is going to be zero right zero is falsy so not false is equal to true and we get empty if car that items that length is anything else other than zero like five ten or anything any number other than 0 is truthy so if you have true here not true is false that's why we can use the simplified logic to show if the card is empty and then based on that variable as we saw previously we can show either the cart or the filled cart now moving on we said that we have to loop through the cart items right here so how do we do that well we're going to open a curly brace and then inside of there we're going to say cart dot line underscore items dot map inside of here we have one callback function i'm going to put parentheses here to have an instantaneous return not curly braces and what do we get in there well we simply get one item or one product then for each product we want to show a grid this grid is going to be of type item so let me just finish up this grid and it's going to have a type of item on extra small devices it's going to take the full width but on small devices it's going to take 4 spaces out of 12 which means 1 in 3 is going to show up and then of course if you're looping we have to have the key key is going to be equal to item dot id and what are we going to show inside of this grid well we're going to show a completely new cart item component so we're going to create a new component which is going to be our cart item right now we don't have that component so instead of this i'm simply going to return just a simple div that's going to say something like line underscore item or just item dot name i think this should be good we should see a name for each specific item in the card and later on we're going to implement the card item component okay now below this container grid we're also going to implement a new div that div is going to have a class name of classes dot card details inside of there we're going to have a typography that typography is going to be of a variant h4 and it's simply going to say subtotal is going to be equal to cart dot subtotal dot formatted underscore with underscore symbol this is going to give us the amount with a dollar sign we can put all of this in one line it doesn't take too much space and now below that typography we're also going to have one more div that dev is not to have any classes but it is going to have two different buttons the first button is going to have a class name of classes dot empty button it's also going to have a size of large it's going to have a type of button and it's going to have a variant of contained but it's also going to have one more thing bear with me this button has a lot of things it's going to have a color of secondary so in here we can say color secondary now what is it going to say it's going to say empty cart so that's what we actually put inside of the button now i'm going to copy this button line below and in here this is going to be our different button this is going to be the button for the checkout so it's going to have a class name of checkout button the size is also going to be large the type is also going to be a button the variant is going to be contained but we need to change the color to primary and we have to change the empty cart text to be simply checkout these are our buttons and that is also it for our field card component now you can see it wants me to implement the classes so i think that's the next thing we can do you know the drill inside of the cart folder we're going to create a new file called styles.js and then inside of there with some magic we're simply going to copy and paste the styles the link is going to be somewhere next to this video i'm sure if you copy the previous files you should have no trouble with this one and finally what we have to do is in here we can say import use styles from dot slash styles and then we have to use that as a hook const classes is equal to use styles and we call it great so now let's format this a bit and let's see if we need anything else we're going to head back to the browser and see what we got this looks pretty good we have our shopping cart in here we have all of our items they don't look good yet because we didn't create the cart item component but we'll do that soon we have the subtotal and we have the empty cart and the checkout button this title looks a bit too small to me let's see why is that that is this title right here and as you can see i misspelled the variant so in here that should have been variant now if you go back that title should grow bigger as i reverse the page i noticed that it said cannot read property length of undefined that means that this line items wasn't fetched yet to fix that i would simply add one error check in here we can say if no cart dot line items so if it didn't yet fetch any items then we can simply return and we can return a string of loading just like this i think this should be able to save us from the error but we're still going to get an error because this line right here is still happening maybe we don't even need this variable i'm just going to take the value of that variable and then where we were using it down below i'm just going to simply copy the value or rather paste the value because that's it we sometimes have no need to create a variable if the content is meaningful enough on its own so now this line is not going to happen before this line and if there is no cart line items this is simply going to return loading until it fetches them so now if we get back and if you refresh just for a brief second maybe you saw maybe you didn't deloading and then we got our your shopping cart and we got everything else let's create a cart item component so that the items in our cart look good to do that we're going to create a new folder inside of our cart folder and we can name it cart item you might be wondering why did i create that folder inside of the cart and not inside of the components themselves well i just like to simplify it because this component the cart item is only going to be used inside of the cart so it doesn't make sense for it to be anywhere else same things goes for the product inside of the products with that said let's create a new cart item dot jsx file inside of the cart item folder inside of there we're going to create a new functional component with rafce and at the top we're going to import all of the things that we need from material ui that is going to be a typography we already learned how to use it it's also going to be a button card card actions card content and card media from add material ui for slash core while we're here we can also import the classes so we can say import use styles from dot slash styles and then we can create a styles.js file and simply copy and paste all the styles right in there now we can get back to the cart item and start creating the layout first we have to create the classes so const classes is equal to use styles we call it as a function and then inside of there we're gonna have one card component inside of that card we're gonna have a card media which is going to be a self-closing tag inside of there we're going to have an image and that image is going to be item dot media dot source that is the image of a specific product but as you might be wondering where is our item now well we're gonna send it over from the cart instead of this div we'll be calling our new functional component which is cart item and then we're gonna pass the entire item right here remember we're looping through all the items and then for each one we're passing the data for that specific item of course we have to import this component so just right here we're gonna say import card item from dot slash card item to get into the folder and one more card item to get into the specific file with that we can now go back into cart item and we know that we're receiving the item through props we can just destructure it our card media is also going to have an alt tag and that is going to be item dot name and the class name is going to be classes dot media below the card media we're going to have the card content card content is going to have a class name off you guessed it classes dot card content and that's gonna be card not card we're using card and cart interchangeably a lot inside of that card content we're gonna have two different typographies the first typography is going to be of variant h4 and in there we're going to say item dot name so this is going to be the name of our item in our cart and we can replicate this line and below this is going to be h5 and in here we can put the price remember the price is under item dot line underscore total dot formatted underscore with underscore symbol great so this is our card content below our card content we have card actions card actions are gonna have the class name of classes dot card actions and inside of there we're going to have a div that has a class name of classes dot buttons i know we're typing a lot guys but this is just the structure really really soon we'll be done with all the jsx and then we'll be moving on to payments authorization stripe and so much more so even if you made some mistakes here make sure to reference the github repository and then copy and paste the layout if you don't feel like typing it out or if this is too easy for you inside of here we're gonna have one button that button is going to have a type of button a size of small and also later on we're going to add an on click but for now that button is simply going to say this is going to be to decrement the amount of items in the cart then we're going to have one more identical button but in here we're going to say plus and then in between these we're going to have a typography that typography is going to have item dot quantity so in here we're gonna see what is the current quantity of our items and then we can decrement or increment the quantity great and then just one more thing below that container we're gonna have one more button that button is going to have a variant of contained and also a type of button i misspelled it here and a color of secondary this is going to be the button that is going to remove the item completely from the card so we can say remove and i would say this is it for now i think we can go back and see how our cart looks like with all the items in there right now and there we go this looks so much better now we have a proper cart i noticed we're missing a few things first of all we need some margin or padding below this typography and then we don't see the current number of items in the cart we just have the buttons so now let's go back and then inside of the cart first we're going to add that gutter bottom in here if you specify gutter bottom that simply adds some padding below this typography great so that's one thing fixed and the second thing is this quantity i noticed that i misspelled this so we're going to simply spell it correctly save it and go take a look and as you can see we have some space below the title and also we have the quantity for our products next thing that we need to do before we make these buttons functional is to implement the react router we need to be able to go back to all the products and then traverse between the products the main page and the card because right now we're always locked in the card remember what i did right now is simply comment out the product so we can never get back and we have the card but we need to be able to move between these pages using react router so that's exactly what we're going to do next in most applications react router is mostly going to be either in the app.js component or in the index component in this case we're going to be routing from the app.js component so we're gonna need a few things to implement the react router that's gonna be the browser router as router then we also need a switch and finally we need a route and we're importing that from react dash router dash dom so how do we use all of these well let's head to our jsx right here inside of the return statement we have to wrap our entire application with a router so inside of here i'm going to say router and simply wrap our entire application in this router coming from react router dom inside of here we have this div then inside of there we have a nav bar now navbar is always going to be showing what we have to do is switch between these two components and that's exactly what switch is for switch switch between these two or rather i can say show only one of these so are we gonna show the products or are we gonna show the card and what does that depend on well that depends on which route are we we're gonna have one route for the products and i'm gonna create another route for cart so now we have two different routes routes are gonna have something known as exact so we're going to say exact path and what path is that going to be so first product is going to be our root pad so our initial pad our home if you want to call it and the cart is going to be after the forward slash cart so what do we do well if we are on this path then render these products and if we are under the cart route then render the cart and that's basically the only thing you have to really do to enable routing using react router in react now if you save this and go back to the application let's see what do we currently have we are now on the root route and we have to refresh so right now we're refreshing and let's see where are we going to be taken to as you can see this is the home page in here we have all of the products and now if we head to forward slash cart then we are re-navigated to the cart and as you can see in here we have the subtotal and in here we have all of our items only the ones we've added to the cart now what we have to do is we have to implement going back and forth not changing the url but just by clicking simple buttons because users will not know how to go to forward slash card so the first button we want to add the link to is going to be this button right on the top corner that is going to be inside of the navigation bar so we can head to the navbar component inside of here we're going to import one thing and that thing is going to be the link from react router dom now where are we going to add that link to well we can add it to this button click usually you would do something like this you would just say link and then you would specify the property so two something and where are we heading well we're heading to forward slash cart and then also what you would do is you would said go to cart so this is a link that would show up in this case we already have some kind of clickable thing that we want to use as a button so in this case material ui allows us to say component is equal to link and now we can add all of the properties from this link to this exact component and is going to behave like a link so we just added a link to our icon button now we also have to add a link to our typography right here that's our brand that's where we head to so in this case we can do the same thing we can say component and cart we add these two things to our typography in this case we're not gonna go to forward slash cart we're just gonna go back to the slash that's our home route and then we also have to do one more thing and that is if we go back we want to remove this cart icon if we are already on the card so now that we're in the cart we don't want to see the cart again so how are we going to figure out the logic if we're currently on the cart well what we can do is import something else from the react router dom and that something is use location so we're importing the use location and that is a hook so we have to say const location is equal to use location and that location has one specific property that we need and that property is called path name so we want to check if location dot path name all lowercase is equal to only slash only then do we show the card if this is different than the root route then we don't show anything so if this is the same as the root in that case we want to show this icon button so in here what we can do is we can do some logic and then say this if this is the case if we are on the root route in that case show this whole component down below that's it and of course we can do it using the ternary so we can say if this exists then do this otherwise return null but in react there is a better way we can say if this is true then just use the end end operator and that's going to appear only if the first part is true so now let me explain what do we have only if we are currently on the home route only then are we going to show the button if we are not we're not going to show anything now let's go back to the browser and see if that worked there we go we're on the cart and there is no card button if we go back cart button is there one more thing i want to do is we cannot see it right now but if there are no items i want to add a link here saying go back and add some items and then come back to do that we have to go to the cart and then inside of here where we have cart empty what we can do is just inside of this typography we can also add a link import link from react router dom in this case we're going to use just a normal link so link opening and closing and inside of there we can add this text right there start adding some that's going to be the text of our link so we're going to remove it from here and then add an exclamation mark at the end so where is this link pointing to it's going to be 2 and then just slash and this is going to be it we can also add a class name classes dot link this is going to just normalize some styling so we don't have that ugly underline and everything else right now i cannot really show you how that button looks like because well none of our buttons are functional right so just right now we're gonna focus on implementing the logic for all of these buttons in the cart decrementing incrementing the quantity and also removing one specific item but also emptying the entire cart and heading to the checkout let's start working on functionalities for updating the quantity of a specific product we can go back to our app and we're going to go to the app.js in here we have our cart so here we'll call some of the api features from commerce.js more specifically just below the handle add to cart in here we'll have one really similar function to that one we're going to say const handle update card quantity we can say qty that's going to be equal to an async function and then what we're going to accept is going to be the product id and also the quantity now that we have that inside of there we again get the same thing which is always a response from an api call and then we're gonna say await commerce dot cart that this time it's not going to be add it's going to be update so in here we have to specify what do we want to update so that's going to be product id and in here the quantity what is going to be the quantity and we put it in a new object because quantity is only one of the things that we want to update now that we have that we again just set the card to be equal to response dot cart just above we also could have said response so we can say response just to keep it consistent response dot cart or now that i see it even better is to immediately destructure the cart just like this and then we don't have to mention the response we immediately just get the card because we destructured it from the response object okay while we're here let's also implement all the other functions so just below we can see const handle remove from cart this is also going to be an asynchronous function this one is going to accept only one thing and that is the product id and again we're going to get the card after we destructure it and that's going to be equal to await commerce dot cart dot remove and what do we pass in well we pass in the product id and i really want to stress the fact that this is truly revolutionary take a look at this we are adding things updating things removing things just using plain english commerce that card that remove and so on we don't have to create full backend systems and write the code for this ourselves this is really good and this is the main reason why i'm able to provide you with this video usually videos of this type would take tens and tens of hours but now i can do this in about i'm not sure about two hours right great so with that said let's continue we're gonna do the same thing set cart and we update the card and one last final thing is to handle the empty card so we want to empty the entire card so that's going to be const handle empty card and again that's going to be equal to an async function this function doesn't need any parameters it just removes the cart same thing again we get the card back after we call await commerce dot cart dot empty and we call it as a function don't forget to call it as a function finally set cart and we just set it equal to cart great now we have these three functions which are updating our state and we need to pass them to where we can actually call them so all of these if i'm not mistaken we'll be calling from from the cart item right yeah exactly so now in here i'm gonna pass them all to the cart yep we can do it just like this i'm gonna paste the names we can even stretch this card because it already has a lot of different things in there so i'm going to put it into multiple lines just like this and now what do we need well we need to pass the actual parameters now these are just the names of the props we have nothing in there so i'm going to use some keyboard shortcut magic and i'm going to set all of these equal to their counterparts which are the actual logic which are the actual functions for this now we're passing the card we're also passing the handle update card quantity handle remove from card and handle the empty card now going back to our card we know that we can expect all of these properties back in the cart i'm gonna just put them all here of course we have to use comma separated values now we have three extra params right here and where do we pass them well some of them we're calling from here but some of them we're not for example which ones are we calling from here well the empty button is definitely going to be called from here so what do we need to do with the empty button well just go to the end of it add an on click listener and what do we do on click we handle empty cart that is it great the other two we're gonna pass to our cart item as props so in here we can say on update card quantity is equal to on update card quantity and also on remove from cart is going to be equal to on remove from cart okay i just see that i call them handle update right there and handle remove so so i gotta make sure to rename that and after we're done now we know that we want to expect two new props inside of the card item so if we go back to the cart item in here now we're expecting two new props which are on update card quantity and on remove from cart at this point i would agree that we are kind of sending props too much like we are creating them in the app because we have to because they are updating the card state then we are sending them over to the cart right here and then finally we are sending them to cart item one more time this is known as props drilling and solution for this would be to use react context in this video we're not gonna focus on that because currently props drilling is not that big of a deal we are only doing that for a few properties if you have more of these then it might make sense to convert to context great now with that said let's actually see where do we need to use these first of all we're going to use them right here we're going to add an onclick listener so on click to both buttons in here we have to make it a callback function and what are we going to call on update card quantity we need to pass in the item.id and also we need to pass the new quantity that's going to be item dot quantity and we have to do -1 for the decrement and plus 1 for the increment this way we'll be sending the new updated quantity for this specific item and that's going to be immediately updated the last thing is to add the on click listener of onremove from cart to the remove item that's going to remove the full item quantity and in here we can do the same thing a callback function we call on remove from cart and the only thing we pass in is the item id with this done all of our buttons should be functional let's take a look we are back in our cart and let's try incrementing the kettle as you can see even the price is increased and we didn't even worry about the api is doing all of that for us we can increment again or we can simply decrement and then we can fully remove the item if you decrease one more time it goes away but also if you add a few items and then you want to remove all of them you can simply click the remove button and it removes them that's it now we know that remove button works now we know that the increment and decrement buttons work let's check the empty cart there we go now we finally managed to see our empty shopping cart page we can click start adding some that links works as well so now all the front part of our project is done now we have to focus on functionality of payments what's gonna happen after we click this checkout and let me tell you it's not going to be easy the easier part is behind us now we're focusing on payments stripe creating the layout for the form and much more interesting things to start with the checkout we're going to go back to the cart and then in here we have to implement another link more specifically you see this checkout button right there right now it isn't doing anything so what do we need to do with it we simply need to make it as a component that is equal to a link and the question is where is it pointing to well it's pointing to forward slash checkout of course this is the route we haven't created yet so to do that we can go back into the app.js and then in here we can add our third and the final route and that's going to be the checkout so following the structure we can simply create a route component it can have the exact and it can also have the path so path is going to be forward slash check out and what do you think we'll be showing off with on our checkout route well it's going to be the checkout component which we haven't created yet so let's first import it even though it doesn't exist yet so we'll just go ahead and create it right now to do that i'm going to collapse all the files close all the folders and let's do that inside of our components folder we're going to add one more folder and that is going to be checkout form inside of our checkout form we're going to put all the components that have something to do with the checkout let's start with a new folder the folder is going to be called simplycheckout inside of that checkout we can create a new file which is going to be called you guessed it checkout.jsx now what do we do in there well inside of here we're going to have some kind of a form that we're going to move through as we go through the purchasing process so let's start with a simple functional component rafce and then let's import all the things that we need from material ui so that's going to be import paper we also need a so-called stepper then the step step label our good old typography circular progress that's for our spinner when we load things then we need a divider and finally a button we're going to import all of that from add material ui forward slash core now inside of here we're going to create the actual layout first of all we're going to have one empty react fragment then right inside of there we're going to have a self-closing div that's going to act as that padding for the navbar so we're gonna say the same thing we always do classes dot toolbar that simply puts the content more below the nav bar so we can see it fully then below that we're gonna have a main component that main is going to have a class name of classes dot layout inside of the main we're gonna have a paper component that paper is gonna have a class name of classes dot paper inside of the paper we're also going to have a typography component this time our typography is going to be of a variant h4 and we're going to add a line which is equal to center and that is simply going to say check out below that we're going to have a stepper a stepper is a component that moves as you move through the steps of course that's our stepper so stepper needs to have a few things first of all it needs to have an active step which we don't yet have so i'm going to set it to zero later on we're going to update this using state and then it's also going to have a class name of classes.stepper now inside of the stepper we have to map through all the steps and what are the steps we're going to have well there won't be many we only have two so we can create them above our component const steps is equal to an array first step is shipping address and then the second step is payment in a string payment details these are our two steps so down in here inside of the stepper we can call steps dot map and then we can map through the steps in here we get one specific step and again i'm just gonna have an instant return arrow function this is not a curly brace it's a parenthesis there we're gonna have a step that step is gonna have a key of step and finally inside of the step we're gonna have a step label component which is going to have a step inside of it so we're using that step quite a lot this is going to generate a nicely looking stepper if you're not sure what i mean right now we're going to see it in just a moment now let's import the use state so we can actually traverse through the steps import use state from react and then just above we can say const active step is equal to or rather active step and then set active step that is equal to use state and by default we're going to leave it at 0. now in here instead of the 0 we can use the active step now let's save it and of course you can see we have a lot of errors we of course have to import classes so again let's create a new file inside of our checkout form more specifically inside of the checkout folder in here i'm going to create a styles.js file and then inside of here again magically we're just going to copy and paste all the styles and then back in the checkout in here we have to say import use styles from dot slash styles and then we have to say const classes is equal to use styles and then we call it now we have all of our styles and if we imported everything correctly if we are using our checkout right in here then we should be able to see it in the browser let's take a look okay we forgot to export the checkout from the dot slash components that's in this file index.js of the components so right there we have to say default as and that's going to be checkout but keep in mind this time we have one more extra folder checkout form so to get to the checkout we have to go to the checkout form then to the checkout folder and finally then to the specific file if we do that and then go back you should be able to see our checkout component let's refresh we are inside of the cart with a kettle and now let's click checkout and there we go we have a nice looking paper here in the middle of the screen and there is our shipping address the first step and then we have payment details which is the second step now we have to implement a lot of different steps of the form as we said the first step is the address form then we have the payment form and then finally review of the order let's start off by rendering two different components below the stepper depending on which step are we currently on how can we do that well we're gonna say something like const form is equal to a functional component and then in here we're going to return something based on which step are we currently on so let's do it like this if we're currently on the active step that is equal to zero then we wanna show let's see we wanna show the component called address form like this and i'm not sure why did this mess up right now this is some kind of extension i'm using but if we're not on the first step then we want to render the payment form payment form and these are going to be special components we're going to create now we have this form which doesn't have these components yet but just below the stepper still inside of the paper we're going to say something like this if active step is equal equal equal to steps dot length this means if we are on the last step then we want to show yet another new component and that component is going to be confirmation so we have three different components i know it's kind of messed up but but bear with me so we have the address form and the payment form which are for the first step they're just changing and then we have the confirmation form which comes after done with all the steps so if we're done with steps we show confirmation if not we're gonna simply show what we're gonna show the form and we can render that as a component of course like this great so now it's time to actually import and create these forms to do that i'm going to create them all in this checkout form folder inside of here we can create a new file and we can call it address form just like this dot jsx and we can also create payment form was it yeah payment form dot jsx so these are gonna be our two functional components for now in each one of them i'm gonna just create a simple functional component which is gonna say something like payment form and then in the other one we're going to say address form just so we can see how it looks like so address form don't forget to change the name and the export great so now we have these two forms and of course at the top we have to import them so just below this use styles we can say import address form from dot slash address form and below that we can also import payment form from payment form now we have these two components the last thing that we are missing is the actual confirmation confirmation for now is also going to be a simple functional component so cons confirmation but it's going to be simple for now so i'm going to declare it right here inside of this file and inside of here let's do something simple let's do a div that's going to simply say confirmation so now we have all the three pieces of the puzzle we have the address form and payment form which belong to the form and we also have the confirmation now if we've done everything correctly we should be able to see the first one and the first one is the address form so let's go back and see if we see anything and there we go there is the address form so now of course we cannot navigate yet because we don't have the buttons for updating set active step but if we had these buttons then we would be able to move along for now let's just try to change it manually use state active step is one as you can see we have payment form and the number two should be the last step so if we go back we shouldn't see payment form but we should see confirmation so let's go ahead and see if that's the thing that shows up and there we go confirmations so everything works and you can see with the steps even this thing changes so we have first step finish and the second step finished now we have to implement forms one by one the first one is going to be the address form so let's start with that considering our address form is going to have a lot of different fields i'm talking first name last name address email city zip code country and a lot of other things we'll be using something known as a react hook form to manage the inputs usually we would need to have many specific states for each specific field this way we'll be using react hook form and that's going to allow us to get the values outside of our inputs and also as you can see it is much more efficient using the react hook form and it is also better than native because there are less total re-renders with that said let's start with react hook form first of all we'll import some things so let's start by importing things from material ui we're going to import input label also a select menu item button grid and a typography from add material ui core then we're going to import again as a named import use form and form provider from react hook form great now that we have all that we need we have to set up our react hook form to do that first we're going to say const methods is equal to use form this is going to make sure to give us all the methods that we need to run our form now to create our form first we're going to use an empty react fragment we're going to say something like in here we're going to add a typography and that typography is going to be of a variant h6 and it's going to have a gutter bottom inside of there we're going to say shipping address and now below we're going to have that form provider which we imported from react hook form that provider is going to take in so we're going to put an object here which is not an object it's really just dynamic code and we're going to spread all the methods from react hook form now inside of there we're going to create a form that form is going to have an on submit for now we're going to leave it empty we're going to fill it in later and now inside of there we're going to have a grid that grid is going to be for separating or spacing out all of our input fields so in here this grid is going to be of type container and it's going to have a spacing of three now inside of each one of these we're gonna have a special material ui field because it has nice styling and it fits with our team so we have to find a way to connect react hook form with material ui text input for that reason we're going to create one more component inside of the checkout form and that is going to be custom text field i know you think that this might be a bit of extra work but trust me i've tried a lot of different solutions and this one seems to be the easiest so now inside of that custom text field we're going to create again a simple react arrow function component it can be custom text field and we're going to import some things from material ui and also some things from the react hook form from material ui we're going to get the text field and also the grid component so this is from material ui core and from react hook form we're going to get use form context as well as the controller with a capital c and we're importing all of that from react hook form great so what is this going to return and what is it going to take in well first of all the only thing is going to return is it's going to be a grid this time a grid of type item that's going to have xs 12 which means only one visible input on mobile and 2 per row on desktop or bigger devices and then inside of there we're going to have something known as a controller that controller is a special component belonging to react hook form which is a self-closing tag and it allows us to use any other input or text field as this controller so we can say as text field so it's going to take the look and feel and all the variables from the real text field we also want to give it control so we can say control is equal to control and that control we're getting from const and then with the structure control and then we call the hook use form context i know this might be a bit confusing if you have never used react hook form but just bear with me i i was also feeling this way when i first started learning it uh but again it really simplifies the process so even if you're struggling with this don't worry maybe just copy this part out but the rest is gonna be definitely a bit easier great so now we have the controller with text field and control and we need to have all other properties so each one of our inputs is going to have a full width it's going to be full then we also have to give it a name we're going to get that through props we don't have it yet then we have to have a label we're also going to get that through props and finally we have to know if the field is required or not so we're going to say required also coming from props now since we know that we're going to pass these from props we can simply destructure the props here and take in the name the label and the required field and if i'm not mistaken this is going to be it for our custom text field which we can now import in our address form let's call it something simpler like let's just call it form input because we're going to have a lot of these we don't want to have really a long name so now let's import this form input inside of our address form that's going to be import form input from dot slash form input great and now inside of here we can simply use it and now we're going to see how powerful this is and it's going to allow us to save a lot of lines of code just by using this method what we can do right now is we can simply say form input it can be a self-closing tag this is form right here and the only thing we have to do is pass two or three different things to each form input we don't have to worry about value we don't have to manage the state we don't have to do anything else we just have to say this is the field required if it is we just say that we have to specify the name of the field in this case the first one can be first name and also we have to specify the label so in this case we can say the label is going to be the first name and that is it we can use this logic to create as many inputs as we want you can see it is a simple one-liner now i'm going to put this as an empty string so it doesn't cause any errors and now if we save this we should be able to go back and see if he at least got something looks like we have one error here and that error is coming from the address form so looks like we're not correctly importing it in here we have the form input but we called it custom text field so let's do custom text field and that should solve our problem we should be able to refresh and take a look okay now we got confirmation because we changed our step to two so we have to go back to the checkout and reset the step to zero so we can see the address form and there we go i told you it's going to be simpler right now you cannot really see the purpose of using react hook form but let me show you how we're going to add a few more inputs right away i'm just going to duplicate this a few times more specifically like six times i think this is going to be last name and we're going to change the label to last name this here is going to be address 1 and the label can be addressed next field is going to be email and of course the label is going to be email finally we have the city so we can say city right here change the label to city and just below that we have the zip code so we can say zip and also change this to zip we can say zip or postal code this is just a name so it's going to be lowercase and this is also going to be lowercase now if you save this and go back you should be able to see how simple it is to add multiple inputs using this method we did spend a bit of time creating the the whole control field but now you can see it's much simpler because all the fields were added just with 6 simple lines and we don't have to manage the state it is automatically managed for us once we click the submit button these form inputs are not the only thing we're going to have if you remember from the demo at the start we also had some select fields so let's add those for a select field component we could also create a new separate component but in this case i'm gonna show you how it looks if you don't actually divide it into a new separate component it's gonna get just a bit messy but we have only three selects so it should be fine just below here just below this form input we're going to have a grid and that grid is going to be of type item it's going to have xs is equal to 12 and sm is equal to 6. we're going to have this code for each one of these three inputs one thing that we're also going to have for each input is going to be the input label for this first one we're going to say shipping country then just below that we're gonna have our select field select field is going to be not a self-closing tag it's going to accept a value in this case we don't yet know what is the value gonna be then we're gonna say it's going to be full width and then we have to specify the on change i'm also going to leave this blank for now inside of there we have to loop in some way through some of the values for our event fields for example these are going to be countries so for now i'm just going to leave one specific menu item here and not loop through them yet we're going to do that together later menu item is going to have a key property so inside of here i can say key is going to be equal to well we don't know yet now because we're not looping then we're going to have a value for each one as well so value is also going to be something and finally inside of there we're going to have something like select me so this is going to be each individual country so this is something we're going to copy three times one time two times three times first time it's going to be for shipping country second time it's going to be for shipping sub division and the third time it's going to be for shipping options and the only thing that's going to change is what values we have here here here and here and of course what we're mapping over let's think about this for a second and why is this going to be hard to implement well let's start from the end you don't know which shipping options you have until you actually know in which shipping division are you but you don't know which shipping divisions do you have until you know in which shipping country you are so for each change of the country we have to change these which is then going to change these so all of these three fields work really really closely together and that's gonna be a bit tougher to implement first we're gonna add all of these different states and there are gonna be many for these three inputs let's start from the beginning first we're gonna import the use state and now we're gonna have a lot of different states six i think so we have to say use state and our first state is going to be shipping countries and then set shipping countries by default our shipping countries are going to be set to an empty array below that we're going to have shipping country so only the one that's chosen not plural singular this time and that country is going to be set by default to an empty string below that we're going to have shipping subdivisions again plural so we're going to change this shipping sub divisions and we're going to add subdivisions in here as well to set shipping subdivisions and that's going to be again set to an empty array below that we want to fetch one shipping subdivision so we're going to remove the s and in here remove the s as well so we have shipping subdivisions and also shipping subdivision this is the chosen one and in here we're going to remove the array and put it as an empty string and one final pair is going to be shipping options so in here shipping options and then finally set shipping options that's again going to be set to an array and below that we're going to have shipping option and set shipping option which is going to be equal to just an empty string as well we now have access to all the state fields we're going to use now let's use the things from the api to actually fetch all the available countries to fetch all the subdivisions and to fetch all the shipping options for our customers and if you remember correctly these shipping countries subdivisions and options are the things that we set up directly in the commerce js dashboard we said that we can ship domestically in the united states and also that we can ship internationally to a few countries in europe now to be able to use all the api features we're going to import commerce as a named import from dot dot slash dot dot slash lib forward slash commerce remember this instance allows us to use all of the features now we're going to implement the functionality to fetch the shipping countries subdivisions and options using the commerce api let's start with countries of course the first function is going to be const fetch shipping countries of course we have to get the countries first that's going to be equal to an async function and that function is going to accept something known as checkout token id once we start with the order process we are going to get our own checkout token id like you come into the store and then you get a receipt we get checkout token id we don't have it yet but before we call this function we're gonna create this checkout token and pass it to fetch shipping countries so what is our fetch shipping country is going to do well first of all we're going to make an api call so we say const response is equal to await commerce dot services dot local list shipping countries it's a long name but there we go i told you how to write it and then in there we have to pass in the checkout token iv so what we get back from that well we get back the response and inside of that response if we destructure it we have the countries so the question is what are we going to do with those countries well we can say set shipping countries to countries of course later on in here we are also going to set the individual country but for now let's try to call this if you remember correctly i told you that we need to create a checkout token id before we call this so let's see where that is coming from the checkout token is going to be created in the checkout component where we have these steps and all the other parts of the form so inside of here you can create a new use effect so the first thing that we have to do is of course go to the checkout jsx import the use effect and then right inside of here we will actually create that checkout token so you can put the use effect here use effect initially we're going to leave it as a component bitmount which means it's only going to have an empty dependency array it's only going to happen at the start but later on we're going to change it when the card changes so in this case the question is what do we want to do with it and the answer is in here as soon as someone enters the checkout process we're gonna generate a checkout token so what we have to do to do that is create a new function which is going to be asynchronous const generate token is going to be an async arrow function and then inside of there we can have a try and catch block if the token is successfully created we'll do something in here if it's not we're going to simply send an error so how do we actually create a token well we first have to import the api in here as well so let's import the commerce import commerce from dot slash dot slash and i think one more time lib commerce just like this and then in here we can say const token is equal to await commerce dot checkout dot generate token and what we have to pass in there are two things first of all the cart id and second of all the type of the token we're generating so in here we need to have the cart the problem is right now our card is inside of the app.js we don't have access to it in here so the simplest solution is simply to pass the cart as a prop so inside of here we can say cart is equal to cart as simple as that we are passing the cart as a prop to the checkout we can use it in here and then what we have to pass into the generate token is going to be cart dot id and the second one is going to be options which is an object and then in there we say type is equal to a string of cart that is it this is going to generate our token we can console log it but let's also set it to the state so first i'm gonna log it this is our token and then i'm also gonna create a new state field for our token const checkout token set checkout token and that's going to be equal to use state and by default it's going to be set to null so just below this console log we can call the set checkout token and we're going to set it to the token great we're going to leave the catch empty for now we're going to focus on that later so of course we have this function here we have to call it generate token why did we have to create a function in the first place if we're only calling it immediately afterwards well in the use effect you cannot use async unless it's in a new function you cannot simply add async keyword here so for that reason you have to have a separate function great with that we should be able to go back and we should be able to see the token in the console we still get the same old error so just so we can see the token i'm going to go back to the address form and i'm just going to comment out all of these select fields for now just so we can focus on the token now if you save the file and if you go back make sure to open the console and let's go back to the main page one more time in here we're gonna add a few items go to the cart close this and click the checkout okay let's see what happened looks like we have some warnings here but there we go line 21 of the checkout jsx that should be around here and exactly that is our token so what does the token contain it contains some analytics card id it says what it collects when was it created when it expires the gateways we could be using for the payment all the items in the cart currently including the price and it even includes the shipping methods that you can use that's great so now that we have this token we have to of course set it to the state we did that but we have to pass it as a prop to our address form so inside of here we're gonna pass checkout token and that's it now inside of the address form if you scroll a bit up now we're getting the checkout token right here and now we can use it once we call this fetch shipping countries function and when are we calling that function well as soon as the address form renders we immediately want to get the countries so we're gonna use the use effect and we're gonna say run immediately when you render so in here that's going to be a use effect that's going to be of type simply component dead mount meaning that the dependency array is going to be left empty so inside of here what do we want to do well we want to call the fetch shipping countries function and we want to pass in the checkout token dot id now if we save this we should be able to get the shipping countries so inside of here i'm going to console.log countries and hopefully we can see something in the console i'm going to refresh the browser and there we go take a look at that we have all of the countries we added we currently have the problem that if you refresh the page is not going to render the checkout saying that in address form line 26 it cannot read property id of undefined that means that this checkout token is undefined and we gotta ask ourselves are we not including it correctly check out token that seems to be fine how are we passing it in the checkout well we're passing it right here as the checkout token so that seems all right to me but what we have to do is we have to make this update dynamically with the card so as soon as the card changes we also have to recall for another token let's see if this is the part that potentially fixes this issue that still didn't fix it that means we'll have to do some more debugging so inside of here i'm gonna console log the token one more time and see if it's even being generated so right there i'm gonna save this go back and refresh this unfortunately didn't do it let's see if it works when we go back to the card and then when we click on the checkout and usually i would skip through this debugging process solve it myself and then just show you the solution but i really want to guide you to the hardest thing of programming and that is getting stuck somewhere so now i'm trying to explain my own thought process of how am i going to fix this issue okay we obviously have the cart on line 49 of the app.js i'm going to clear the console click checkout and let's see what happens okay looks like we do get the token here so on line 21 of the checkout we do get the token but the problem occurs before that because it tries to render the address form while we still don't have the token and it depends on it so first what happens is this right here remember this is the render method so how react components work is that they first render everything so first render jsx then go to the component did mount or in this case the use effect and then re-render if it needs to so in this case at this point we still didn't call the checkout token so we still don't have it but our address form is depending on it so in this case we're going to add one more check to show this form in here i'm going to say if we have the checkout token so check out token and end form this is going to make sure that we need to have the checkout token and only if we have it only then render the form now if we save this hopefully it should work make sure to refresh the page and let's take a look and there we go we get our form and down below we also get all of our countries albania austria bosnia belgium switzerland germany denmark spain and finally the united states now we have to add back that select field for the country and then based on the country we'll be fetching all the other regions so we can go back to the address form we know that we're getting the countries but this is not exactly what we want because take a look these countries are in an object we kind of want to have them in an array to loop over them we have al is equal to albania a t equal to astria and so on so we want to have them in an array so how can we do that setting countries in an object right here is fine but how do we actually get the first element in that object with arrays it would be easy right we just do array zero but in this case how would we do it well i'm going to say this set shipping country so now we're setting the individual one and of course as i told you we cannot simply do this because this is an object nor we can do this because we cannot always choose the same one what if one country is missing we cannot make sure that the austria is always going to be there or albania we want to fetch the first thing from that object so to fix that we first have to call object dot keys and then we can say give me just the keys of the countries and the keys are gonna be these a l a t b a and so on so we're gonna get an array with a l at ba and so on and then we're going to say give me the first one of all of these so now we have this properly set up we have the set shipping countries and we also have the one specific country but if we go down there and if we try to uncomment only the first field so let's comment out the two remaining ones inside of here we want to have the value the value is of course going to be shipping country right so we can put shipping country right here on change what are we going to do on change well we want to manage that so we're going to say on change we get the event and then set shipping country and what do we set it to well e dot target dot value whatever is selected we set it to the shipping country now in here we want to map over something and the question is what do we want to map over remember countries are not an array so we cannot do countries.map that is impossible but what we can do is say object dot entries object entries is going to give us keys and values of these objects so what do we want to get the entries from that's going to be shipping countries then we have an array of arrays i know this might be confusing but now let's do a simple console log so i can show you what are we actually working with now this is not that hard when it comes to react but this is really hard just general javascript logic you have to be good at javascript to figure this out i'm gonna remove this menu item for now just so we get the console log now save this go back and it's going to show you what are we working with as you can see this is now an array of arrays and each array contains the key and the value for each specific country so why did we do that well now that we have an array we can officially loop over it so we can say dot map in here we get that one key value pair you can call it like that key value pair but what i prefer doing is destructuring this array where the first element is going to be the code and the second element is going to be the name of that country now that we have that we want to return it in a new format a new format is going to be an object so inside of here you can specify the instant return and then an object and there you can specify the id to be equal to the code and the label to be equal to the name so now we have yet another array with only the ids which are codes and the labels which are names i know this might be confusing but let's add another console log so you can see what are we working with now and then only one last step is remaining so we can officially loop over them looks like i'm missing a parenthesis somewhere it's going to be quite hard to find it right now as i'm getting lost with all these parentheses right here it would make sense for me to simply copy all of this and do it like a normal human being not inside of the jsx so i'm going to put this above create a const countries and then we can do it in here in peace so right here this is not going to be a kansa log what we do is object.entries we explain why we do that to convert it from an object into a 2d array then we have to map or it one more time to turn it into a normal array we get the code and the name in here i noticed one extra parenthesis and what we are returning is simply going to be an array with objects that have the id and the label we can even console.log to see how our countries look like right now okay save that and head back to the browser as you can see we have one array with nine different countries each one of them has the id and the label now we can use those countries map over them and show each one of the select fields inside of here we can open the logic block say countries dot map and then for each country what we want to do for each country we want to return a block of jsx and that block of jsx is actually going to be just this menu item in this case we can say country dot id is going to be the key the value is also going to be country dot id and finally the text is going to be country dot label great if we now save this we should be able to see countries under the select field so let's head back and refresh there we go you can see we have the entire form but most importantly we have this select field and we have all of the values populated right here you can choose from austria albania united states what is interesting about this is that we purposely made it a select field because if you remember correctly all of these countries were set up in our commerce.js dashboard so we're only getting the countries which we can ship to and then once we select the country we're going to dynamically populate all these subdivisions for that country and then all the shipping rates for those subdivisions so for example our next goal is when you click albania or united states all of the subdivisions need to be populated for some countries subdivisions are going to be something like counties for united states subdivisions are going to be the actual states so that is our next step now that we have the countries just below we can start fetching subdivisions so we're going to create another function which is going to be const fetch subdivisions that is going to be equal to an async function and this function is going to be accepting one parameter and that is going to be a country code now you know what i meant when i said we first have to have the country to be able to fetch the subdivisions so we're going to be fetching subdivisions for one specific country so in here the procedure is the same we get response and then we have to await commerce dot services dot local list subdivisions we call it as a function and give the country code argument right inside of there which we'll be getting when we call this function so instead of here what we're getting is the response of course but when we destructure that response inside of there we have subdivisions just as we had countries here in here we have the subdivisions so now we can follow the same procedure which is going to be set shipping subdivisions and in here make sure to put this as plural subdivisions and in there we just set the subdivisions just like so great we also want to set a singular subdivision and the situation is going to be the same as with the countries so we can say set shipping subdivision singular and then we have to do object dot keys we get the keys out of these subdivisions and then we get the first element this is going to be our selected subdivision you can see this is quite similar so that's great now when are we actually going to call this function fetch subdivisions well we cannot call it immediately after the fed shipping countries because at that time we won't yet have the country so what we have to do is create another use effect and maybe this is the first time you're seeing two different use effects in the same function well there isn't a single rule that forbids you from having multiple use effects that is completely legal and it's a good practice of course if you have the need for them so in this case this use effect is going to have one dependency and that is going to be a shipping country this says that whenever the shipping country changes we're going to recall our use effect so whenever our shipping country changes then we have to call our fetch subdivisions and of course we have to provide the shipping country which is in the state sometimes this is going to be empty so what i would like to do is simply provide an if statement so if shipping country if it exists only then call the fetch subdivisions that is it for the subdivisions now you can see we're calling it so what do we do with them so now we have to do the same thing we have to loop over all the subdivisions and then we have to display the select fields based on them the situation is going to be completely identical to countries so we can literally copy this line say subdivisions and in here we're going to do object.entries from shipping subdivisions and in here the situation is going to stay the same so if we scroll down we can now loop through the second grid or through the second select i'm going to uncomment those and let's focus on the shipping subdivision so in here what we can do is basically copy the select that we've been looping over and paste it in here of course the value is not going to be shipping country it is going to be shipping subdivision full width is going to stay the same and then on change we're not going to set the shipping country we're going to set the shipping subdivision singular make sure not to mess this with an s at the end in here we're looping through subdivisions not countries and then in here we get one single subdivision and we get the subdivision id subdivision id and subdivision label this isn't too long so we can even put this in one line just like this so now we have two different maps first we fetch this and only after the shipping country changes only then are we getting the subdivisions for that specific country if we now save this i think this should work we should be able to go back to the website and see if subdivisions are populated there we go albania berat and then if we switch to united states it's going to take a second and it's going to fetch all the different subdivisions this is great if we go to for example austria it's going to get all the subdivisions for austria as well this means that it works perfectly the last thing is to fetch the shipping options so for united states it's going to be free because it's domestic but for european countries it is going to be international so how do we do that well we're going to do a similar thing one final time just below i'm going to say const fetch shipping options that is again going to be equal to an async function this one is going to accept quite a few things it's going to accept a checkout token id also a country and also a region we can set the region to be equal to null if there is none great so now when we have that inside of here we'll be fetching the options so const options is equal to await commerce dot checkout dot get shipping options and then what do we have to pass well of course we have to pass the checkout token id that we're getting from parameters here and then we have to pass the options object right here we have to specify in which country we are so country is going to be equal to country and then we also have to specify the region this is going to make sure to get a specific shipping option for this country and for the specified region now that we have these options i'm going to say set shipping options to options of course and then we want to get the first shipping option available so we can say set shipping option this is an array so inside of here we can simply say zero and then dot id this is going to make sure to immediately select the first available shipping option now the question is when do we get the shipping options and the answer is we get them after we get the subdivisions so we first get the countries then we get the subdivisions and then we get the options so we can use another use effect here that use effect is also going to have a dependency and it's going to run once the shipping subdivision changes so in this case we're changing this once the country changes and in this case we're changing the options once the shipping subdivision changes so right inside of here we're going to say if shipping subdivision so if it exists then we want to fetch shipping options not countries options and we want to pass in checkout token dot id this is coming from the top of our function from props then we want to pass in the shipping country which is in our state and finally we want to pass shipping subdivisions or more specifically one singular shipping subdivision without the s at the end great that's it and finally we have to loop over it looping over this is going to be just a bit different but we're still going to do it at the top we're not going to copy the line but this is what we're going to do const options is going to be equal to in this case we have shipping options dot map so why are we immediately mapping over it and not doing object entries that's because shipping options are an array by default and maybe to show you that it would be best if we just simply console log the options immediately to see what they are so here i'm going to say shipping options so now if you're fetching this properly you should be able to see shipping options in the console and there we go address form jsx22 these are our shipping options as you can see we have an array and inside of an array right now we have only one element in this case we have all the countries and we also have the description international in this case we also got one more kinds of log this is the same thing but if we switch this to united states we're going to get a different shipping option in this case we always have just one option so now what we have to do is we have to map over them and for each option we want to merge together the name of the shipping domestic and also the price for that specific shipping so in this case what we're going to do is loop over the shipping option i'm going to call each specific shipping option so for shipping option and this is what we're going to do we want to return immediately one object and that object is going to contain the id id is going to be equal to shipping option dot id and the label is going to be equal to now bear with me a template string inside of there we have a shipping option dot description and then we're gonna add just a dash and i'm going to put this in parentheses another template string and then in there we're gonna say so dot price dot formatted underscore with underscore symbol this is going to give us the price for that specific shipping this is going to be it for this specific line it is already too long i know it's getting a bit complicated i told you this part is going to be a bit more complicated when it comes to just javascript because it is tough to do all of this complex logic but now we have these options and finally we can go to our last select and we can loop over it so for now what i'm going to do i'm going to take this part and simply paste it in here it's going to be almost the same thing value in this case is shipping option on change is going to be equal to e so we get the event and then set shipping option and then e dot target dot value finally in here we will be looping through options and then we get one specific option and everywhere where we have subdivision we change that to option this is it now we are properly looping through options and now i want to point your attention to the difference between these three selects and these six inputs all of these inputs are custom components they're one custom component and while we're talking i just noticed that we don't even need this required prop required is always going to be simply set to true because all of our fields are immediately required so we can get rid of this completely for all fields so again take a look six different fields and then we have three different selects the logic for these selects is much more complicated and we have much more duplicate code because we haven't separated it into a new specific component but then take a look we can even put this in one line because it's simple so this is it this is just to let you know that you can always create uh specific new components custom components that are going to accept some props and are going to make your jsx seem simpler as it should be in this case we're going to leave this select as they are because the logic for actually doing all of this with them is kind of complicated with that said let's take one final look at our address form we have our shipping address here we can input all of the values first name last name address email city and the postal code then you can choose from all of the countries your shop is shipping to let's choose united states all of these values are immediately populated for us let's choose california and then you can see the shipping should be zero it is automatically switched to zero but if we switch back to austria it's going to switch to international so now we know that our checkout or at least the first part of the checkout is absolutely fully functional we are ready to add the next button right there and then we can move to the payment details adding the button is going to be simple below all of this below this form we're going to add one break tag then we're going to have one div and that there we're going to do some inline styles in here this is going to be display is equal to flex and also justify content is equal to space between these are the only styles we are using in this file so just so i don't have to create a new style.js i'm going to do this inline now in here we're going to have two different buttons inside of that div we're gonna have two different buttons the first button is going to be of a variant outlined like this and then the second button which we're gonna have just below is going to be off variant contained the first button is going to say back to cart and the second one is going to say next great now of course when we have the back to cart in here we have to specify that component to a link so we have to say our component is a link and then we have to say go to and then go to forward slash cart but this one is going to be of a type is equal to submit which means that this is going to submit our form and we are ready to go to our next step of course this one is going to be of a caller primary and that is it now let's save it and let's see if our buttons work now let's import this link component so just at the top we can go ahead and say import link from react router dom now we can save the file and see if our buttons work the back to cart button is going to work perfectly but the next button is not going to work just yet because in here the only thing we did is we said this button is going to be of a type submit but what are we submitting in here if you take a look inside of our form our on submit is empty so it's not going to do anything what we have to do with react hook form is we have to say methods dot handle submit and that's going to accept one specific function more specifically callback function that callback function is going to have the data for all the fields populated right in here so this special handle submit belonging to methods of react hook form is going to have the data object that is going to contain the information for all of these specific fields then what do we want to do when we have that we want to call once function that's going to bring this data back to our checkout so we need this data right in here and how are we going to receive all of that data right here well we're going to create one new function so just below this use effect we're going to say const next is going to be equal to and then in here we're going to pass this function as a prop to our address form of course the function is going to accept the data so what are we going to do with that data well we're going to set it to the shipping data right here so all the shipping data that we get from the address form we're gonna create a new state field right here const shipping data and we can say set shipping data all of that data we're gonna set right here into one use state field that use state is at the beginning going to be an empty object okay so once we get that shipping data what we have to do to get that data populated is simply say set shipping data and then we use that data that we passed right in here of course once we set the shipping data we also want to move the set active step by one further so just above the next i'm gonna create two new functions one function is going to be called const next step and that function is simply going to set the active step to step plus one and when you're setting the state in react using the previous state you have to call it as a callback function and then in here you get previous active step so what you can say is simply return previous active step plus one this way we are not mutating the old state we are using it as a previous state plus one just below we can create back step and that way the only difference is that in here we put the minus so now we know that after we set the shipping data we're gonna call the next step okay and our next function we have to pass it into our address form so right here i'm going to say next is going to be equal to next now going back to our address form in here at the top we'll be receiving this next right here and then when do we actually call that next well we call it on the submit so right here on submit we need to call this next function and give it some of the parameters so what are we going to give it well first of all we're going to give it a new object and that object is going to have all of the properties from the current form spread so we want to spread this data into this object why are we simply not sending in the data well because data contains only the values for these six fields but we are managing these normally using state so we have to create a new object where we spread the properties of data and then we also pass shipping country singular shipping subdivision and also shipping option that's why we have these singular values so later on it's going to be easier because we are passing exactly what we need so what is currently happening we are calling this function from here passing all the necessary data the function declaration is right in here into the checkout we're getting all the data setting it to the shipping data and then now we have access to this state which we can then use to pass it to our second step of the form which is the payment form based on this shipping data our payment form will be able to finalize the order so our next step is to start working on the payment form in here we'll be using stripe starting with the payment form we are first going to import all the necessary things from material ui and in this case stripe from material ui we're going to need only a few things we're going to need a typography a button and a divider then we're going to import elements with a capital e card element and also elements consumer from add stripe react stripe js this is stripe react but we also need something for just general stripe and that is going to be import load stripe from add stripe and then just forward slash stripe.js so make sure to not mix these up now that we have that we can start creating the layout for our payment form inside of here we're going to have one react fragment and then below that we'll have one new and this is going to be trust me the last component of this project in this case this component is going to be called review so this is going to be just a general list of all the things that we have purchased so while we're here we can also import that that's going to be import review from dot slash review and of course we can go ahead and create it so right inside of the checkout form we can create a new file which is called review review.jsx that review is also going to be a react functional component so we can create a rafce and we're going to import a few things from material ui it's going to be a typography list list item and list item text from add material ui forward slash core then in here we're also going to have a react fragment at the top we're going to have a typography so typography it's going to be of a variant h6 and it's also going to have a gutter bottom it's going to simply say order summary below that we're going to have a list that list is going to have a property of disable padding and then just below that we have to loop through all the products that we have in our cart and if you remember correctly we have access to all the products inside of the checkout component inside of this generated token so now we can actually make use of this token it's stored right here inside of the state as the checkout token and we have to pass it over into our payment form so in here we're going to say checkout token is equal to checkout token now we can go back to the payment form we are expecting a checkout token here and we can then pass it as a prop right towards here so check out token now if we go back to the review in here we have access to our token what token allows us to do is to in here loop through all the items so we can say checkouttoken.live.line underscore items dot map then we get one specific product for each map iteration and what do we do with it well we want to display some jsx so in here you can put an instant return and for each product we're going to display a list item that list item is going to have some inline styles it's going to be style and then padding 10 pixels at the top and bottom and 0 on left and right and it's also going to have a key key is going to be equal to product dot name inside of that list item we're going to have a list item text that is a self-closing tag the primary text in there is going to be equal to product dot name and the secondary text in there is going to be equal to and we're going to put a template string that's going to be quantity and in here we can use that template string and say product dot quantity just below that we're going to have one more typography it's going to be of a variant body 2 and there we're going to simply say and there we're going to put the price of our product so that's going to be product dot line underscore total dot formatted underscore with underscore symbol below this map we're also going to have one more list item so in here list item this one is also going to have a style of padding 10 pixels on top and bottom and 0 on left and right and this list item is going to have a list item text the primary is going to be simply total just like that it's a self-closing tag and finally we can have one last typography this typography is going to be of a variant subtitle 1 and the style is going to be equal to font weight of 700. this is going to make our text appear bold inside of there we want to put the total price and we get the total price by doing checkout token dot live dot subtotal dot formatted with symbol this is going to give us the total price i noticed i have a typo here so if we fix that our review component should be good to go okay so let's go back and let's see if this actually works we have our cart we have all the details here i'm gonna fill in the name and the shipping address let's go for albania this time and let's click next there we go in our cart we have one kettle and one book oh unfortunately quantity is undefined so looks like i misspelled that let's fix the quantity so in here and somewhere else i guess there we go in here and in here if we now save this and go back let's see what are we gonna get one more time to the checkout next and we get quantity one and quantity one this means that all of this is working perfectly we now have our review of our order just below that we'll be using stripe elements to create a nice looking card input which stripe is going to process and then that's going to allow our users to pay with their cards we're going to divide this review with a divider so in here we have a self-closing divider tag and then below we're going to have a typography this time our typography is going to be of a variant h6 and also it's going to have a gutter bottom and a style of margin 20 pixels on top and bottom and zero pixels on left and right and in here we can simply say payment method so the first thing was the review of the order and the second thing is payment method just below that everything else is going to be done by stripe for us so inside of here we can use stripe elements these are pre-done elements and stripe simply does that for us inside of the elements we're going to pass the stripe property so stripe and that is going to be equal to the stripe promise we didn't yet create that try promise so we can do that right now just above our payment form in here we're going to create a stripe promise const stripe promise and that is going to be equal to load stripe in here i misspelled it this should have been load stripe and now we need to pass our public key from stripe store i'm going to leave this b just for a second and then later on in here we're going to put our own public key so that the stripe knows what's our public key moving forward with the layout just below this elements we're going to have something known as elements consumer that elements consumer is going to have this javascript block of code in there and it's going to have a callback function that's simply how it works that callback function is going to have one more return so just take a second look at this code and feel free to write it down not to make any mistakes we do this because in here as parameters we accept something from stripe we're going to structure that and we're going to get elements and we also get stripe from here all of this you can find in the official stripe documentation for stripe elements so now that we have elements and we have stripe inside of here we can create our form so just like this form later on we're going to add the on submit to this form inside of here we can specify this card element it's going to be a self-closing tag we imported that right here at the top also coming from stripe i'm going to add a two break tags here so we can have some space between the card and finally we're gonna have some buttons so just below i'm gonna create a div this div is also gonna have some inline styling so style display is going to be equal to flex and also justify content is going to be equal to space between now we're going to have two different buttons first button is going to have a variant of outlined and it's simply going to say back so we're going to go step back maybe we didn't add everything we need to the card so we simply say back the second button we're going to create it it's going to have a type of submit and it's also going to have a variant of contained the button is going to be disabled if we have no access to this stripe so this is going to make sure that people cannot just smash the button if we don't yet have the stripe instance the color of this button is going to be primary the button is going to say now we're going to put this into multiple lines and the button is going to say pay and now in here we can take the amount from the checkout token checkout token dot live dot subtotal dot formatted underscore with underscore symbol we're already used to this long string and there we go now we have two buttons so what are our buttons going to do well this one needs to have an on click and we're gonna add it on click what we wanna do we simply want to go back step this is a function that we're gonna pass from our checkout so if we go back to our checkout right here remember we created this back step function so we can pass it over as a prop to our payment form right here backstep is equal to backstep now if you go to payment form in here as a prop we'll be receiving the back step and we can call it that's going to make sure to go one step back let's save the file and see how our form looks like them this is already getting so much better and it is functional we can move back we can click next of course if you haven't filled it it's going to ask you to fill it and now you can click next and you can see there we go our form is right here automatically generated by stripe in here you can enter your credit card details the expiry date the cvc and the postcode and that's going to be it you're ready to pay but of course not yet there's one step before that and that is that we have to actually include our stripe so we have to enter our public stripe key for that we're gonna head to stripe.com and we'll create a free account once you go to this tribe.com of course you'll be able to create the account and get the public key but let's just for a moment appreciate this amazing looking website this is one of the best if not the best design i've ever seen looks really clean and modern with that said you can click this start button right here you can enter your email full name and password to create an account in this case i'll just sign in once you're in you'll most likely have to get your email verified so make sure to verify that email that you get back on your address so on left side sidebar you click developers once you're here you can go ahead and click the api keys and there we go this is our publishable key you can just click to copy and then we can head back to our code and paste it in there we're not going to simply paste it here because this should be private so what we're going to do is we're going to go to the dot env file in here we're going to say react app and we can say something like stripe public key and then in here you can paste that public key after you do that you have to open the terminal press ctrl c to close it and then restart it that way our variable is going to be generated then you can copy this and we can go back to our payment form now in here as we learned you can do process dot env dot and then name of the environmental variable in this case react app stripe public key now that we connected our stripe we can finally create that one handle submit function so const handle submit and this is going to be the final function that's going to finalize the order so when are we calling this function well we're calling it on the submit so right in here in this form we're going to say on submit is going to be equal to we get the event and then in here we want to call that handle submit function and we need to pass three different parameters the first one is going to be the event of the click or of the entire form then we're going to have the elements and then finally stripe so we need all of these stripe dependencies for this to work now that we have that we of course know that in here in the function we're getting the event we're getting the elements and we're also getting this stripe first of all always in react we do this event dot prevent default this is going to make sure for our website not to refresh after we click the button then we're going to do some error handling so we're going to say if no stripe or if no elements we're gonna simply return we're gonna go outside of this function we're not gonna do anything stripe cannot do anything if we don't have access to one of these two things then we're going to get our element and we can do that by saying const card element is going to be equal to elements dot get element and simply what we do is we pass in that card element the card element if remember we're importing from right here now we're going to use stripes api to create a payment method to do that we can say const this structure the error and the payment method from so equal to await stripe dot create payment method and we pass in the options object where type is going to be equal to in this case card and also the card is going to be equal to card element variable which we just created now that we have the error and the payment method we can do one if else check so if we have the error then we simply want to console log the error that's going to be enough else if we don't have the error we want to create one final object containing all of the data containing all of the items we have in our cart containing our customers so who are we who is buying it the first name the last name all of the address details containing all of the shipping details containing the shipping options and finally containing the payment information we need to store that in one final variable and we're going to call that order data that's going to be an object and in there let's start one by one first we have list items list items we'll be getting from checkout token.live.line underscore items then we want to know who is our customer so we can say customer is equal to an object customer has to have a first name and in here make sure to not use the camel case so make sure to have the name as lowercased first name is going to be equal to shipping data dot first name then last name also not uppercase is going to be equal to shipping data dot last name then we have the email email is also equal to shipping data dot email do we need anything else in our customer i think that's going to be it so you can add a comma at the end and then just below we can specify all of the shipping options so now we can say shipping and it has to have a name so in this case let's do name something like primary shipping just like that because we have only one option for international and for domestic then we can specify the street street is going to be equal to shipping data dot address one this address one is coming from our address form if you remember correctly there we go okay with that we also need to have the town underscore city and that is going to be equal to shipping data dot city moving further we have a few more things so we could even put this into multiple lines as it's getting too long in one line we have a county underscore state and that is going to be equal to shipping data dot shipping subdivision then below that we also have a postal zip code and that is going to be equal to shipping data dot zip and finally we have one final thing in our shipping object and that is going to be the country country is going to be equal to shipping data dot shipping country okay that was a long object below that we're going to have a fulfillment and in here this is also going to be an object in here we just specify the shipping underscore method and our shipping method is going to be shipping data dot shipping option so we're getting all the data from the shipping data from the checkout token from anywhere we can we have to have all of that data sent over to the commerce.js below the fulfillment we're also going to have a payment payment is going to be one more object and in here we're going to say gateway is going to be equal to stripe just a string of stripe and then stripe is going to be a nested object and stripe is simply going to have a payment underscore method underscore id and that is going to be equal to payment method dot id that payment method we're creating right here when we call stripe dot create payment method and that is going to be it we have this huge object and what we have to do is one last final time we have to call our commerce api that commerce api is going to be called inside of the app.js so inside of there we have to create that function for fulfilling an order so right here below the handle empty cart we can create a new function which is going to be called const handle capture checkout that is going to be an async function which is going to accept a checkout token id and also the new order it's going to have a try and a catch block if something goes wrong in the try block we're going to try to fetch the incoming order so we're going to say const incoming order is equal to a weight commerce dot checkout dot capture and as always we're going to pass in this checkout token id so that we know about which order are we talking about and then we're going to pass the new order once we have the order we want to set that to the state so just above we're going to create one final state field right here const order and set order is equal to use state and this is going to be just an empty object at the start now we can use this set order right here to set our incoming order to the state so we say set order incoming order once we create an order we also want to refresh the entire cart so if the order is done we cannot have all the items stay in the cart because the order is actually done so to solve that we're going to create one more function above which is going to be called const refresh cart and that's going to be equal to an async function in that function we're going to have a new cart and we just have to await commerce dot cart dot refresh after you do that we can finally set cart is equal to new card remember we already have the card in the state if you take a look at here we worked with that quite a lot but now after we actually finish the order we have to refresh the card so where are we going to call this function well just after the set order we're going to call refresh card of course it's good to have good error handling so just at the top we're going to create one more state field which is going to be error message and set error message which is going to be equal to use state and simply an empty string at the start then we can simply say in here set error message is going to be equal to error dot data dot error dot message i had to console.log this error a bit to come up with this but this is the final message in here we only get meaningful information why the error occurred so now that we have this handle capture checkout and that we have the order and error we have to pass all of these things to our checkout so right now in our checkout we're passing only the cart but what we want to pass is going to be the order as well so we say order is equal to order then on capture checkout we want to pass the handle capture checkout then we also want to pass the error so the error is going to be simply error message and now of course in the checkout component we have to get the order the on capture checkout and the error so now we can go back to our checkout in here at the top we know that we are expecting these fields so we can just add them in one line and some of them will have to pass over to our payment form let's think about which ones exactly in this case we only have to pass in the on capture checkout so just below let's find our payment form there it is and we're going to say on capture checkout on capture checkout so now if we go to our payment form scroll to the top now we're receiving what to do on capture checkout and the only thing that it accepts is going to be two parameters that we specified in that function if remember we're going to call on capture checkout the first thing is checkout token dot id and the second is order data so the full data for the entire order we need to have that to be able to fulfill the order and finally once we do that we also want to move to the next step so i kind of miss this we also want to pass the next step so in here i'm going to take in the next step as well go back to the checkout and we're going to pass this function next step we're gonna pass it right in here before the back step and save that that way we'll be able to move further once we actually complete the order i also noticed that i didn't declare this function as an async although we have the await so we definitely need to do that and with that i think our form should be ready to go we should be able to create a new order of course we don't yet have the actual like confirmation message you can see that we're missing that here but more importantly the logic for the actual completion of the order is fully done that should work what we can do right now is do one final test of the entire checkout process adding the items to the cart going to the cart and then finally adding them to the checkout and purchasing them but there's one more thing we have to do before we can do that you can go to the settings of your dashboard.check and then in here on the left side you should be able to see the settings icon there you're going to head to paymentgateways inside of here you'll have to enter your credit card information so that commerce.js can connect you with stripe this is required to finish the transaction process if you don't have a credit card or if you don't feel comfortable giving away credit card information don't worry at the end of this video i'm going to create a mock checkout process so that even if you don't really complete the purchase we're going to get some kind of a confirmation message with that said i would still strongly encourage you to follow along with this video with a credit card so that you can get the confirmation email and all the other features that the commerce.js offers don't worry absolutely no money is going to be taken from your account we can also open the stripes dashboard inside of here you can copy these two keys you can click on this one and paste it right here and then you need the second one which is the test key you can copy this one as well and then simply paste it right there as well once you do that you can save it and now there's only one more thing we have to do at the start of our project we added this public key check public key more specifically the commerce.js key what we had to do instead is go here to the fourth icon the same as before and then to the settings instead of here last time we took this key but what we should have copied was this sandbox public key this is going to make sure that all of our transactions are only sandbox only for testing so you can go ahead and paste that link right here so it's not going to be public key it's going to be public key underscore test with that said you can again close your terminal and then rerun the application and now our transaction process should be completely done and let's test our app out i'm going to add one keyboard one messenger bag and one mouse to my card looks like we had the book already and now we can check out if you go right here we can enter our standard information and then let's go with something like united states and our john wick is from california now you can click next in here you can see we have the total for all of our items and now you can enter your credit card number stripe's default demo credit card number is just 4242 keep pressing that and now you can click pay let's take a look and see what's going to happen this is really good we were taken to the confirmation but now let's go back to the commerce.js and see if our cart is cleaned and it actually is there are absolutely no items in the card and considering we are using commerce.js and they're doing an amazing job in e-commerce both the store owner and the user should receive a confirmation email there we go take a look at this i just opened my email and in there i found this all the information about the order all the items shipping details which card did we use everything is in here and ready to be shipped with that said there are only a few small things left for us to do let's start with the confirmation of course we don't want to just have the div that says confirmation we want to have something meaningful in this case i'm going to create an empty react fragment and then inside of there we're going to have a div inside of that div we're going to have a typography and that typography is going to be of a variant which is h5 inside of here let's leave a nice message thank you for your purchase and then in here we want to get the name of the user so we want to do something like first name and also last name later on we're going to fetch these from the order execution down below i'm going to put a divider right here and i'm going to give it a class name of classes dot divider below that we're gonna have one more typography and this typography is going to be of a variant subtitle two and this is simply going to give us the order reference of course we're going to get the reference number right here it needs to be dynamic below that we're going to have one break tag so this is going to be a break to add some space and finally we want to have one button that button is going to be of a variant outlined it's going to be type is equal to button and we want to have it as a link and it's going to say back to home so this button is going to simply navigate to the home we learned how to do that component is equal to link and now inside of there we say to and just forward slash this is our home this is our full confirmation but now we only want to show this if we have a fulfilled order so to do that we can just at the top say if order dot customer so if order dot customer exists only then do we want to show this otherwise we want to do something like this we're going to have a new jsx block and we're going to have one viv that div is going to have a class name of classes dot spinner and it's going to have one component inside of there and that is going to be our circular progress this simply means that while we don't yet have the order done we're going to have a spinner because taking the order takes some time maybe a second or two we don't want to have our user to stare at the blank screen we are going to give him something to look at that's going to be a little spinner now we have our confirmation but it's not always going to be all sunshine and rainbows sometimes there are going to be errors and that's normal but what we have to do as developers is we have to handle them properly so i'm going to change this from const to lead and then down below i'm going to check if there are errors and remember we're passing these errors through props from the app.js so if there are errors in that case i want to show something different we're going to show an empty react fragment and then inside of there we're going to have a typography that typography is going to be of a variant h5 and it's simply going to say error and then error just like this we're going to have one break tag to give some space and below we're going to have the same button that leads us to home so we can copy this button i just noticed that we don't have the link imported so just at the top we can import link from react router dom and now let's see where this error is coming from so let's go back to the app and see if we really do have that error in here we have error message and if i remember correctly we are passing that error message as an error so that should be good that's great in this catch we can simply console log the error and now we are nicely handling these errors i also notice in the console that we have one often appearing warning from material ui and that is that we need to add a default value to our controller so in here i'm just going to add a default value field and we're going to set it to be an empty string and one more thing we need to do before we do a final test of the entire checkout is to go right here to our confirmation and actually use our customers information i completely forgot about that so inside of here we can enter all of the details in here we're going to first spell this properly purchase first name is going to be stored under order dot customer dot first name all lower case and then the last name is going to be under order dot customer dot last name and also being lowercased inside of here the ref is stored under order dot customer underscore reference and i think that's going to be it let's save the file and let's go admire our great application we're going to go through the checkout process one more time add a few items go here try to remove an item increment the number of items remove it completely again our john wick is buying a lot of things recently but we're just testing with him we're gonna try with germany this time let's choose a specific subdivision and let's click next so far everything looks really really good we can enter our credit card information and finally we can click pay take a look at this nice looking spinner that looks really good and finally thank you for your purchase john wick and then we have our order reference and with that our john wick became a happy customer and he also received a confirmation email now we can go back to home and we can keep buying finally let's see how our app looks like on mobile considering we are using material ui it should look really really good straight out of the box and would you look at that we almost didn't have to do any extra work and it immediately looks like it has been made for mobile so we can add a few items we can go to the cart this also looks really really good we can go to the checkout okay our form is just a bit out of place it kind of goes outside of the screen but i think material ui has a really easy fix for us the only thing you have to do is go back into the checkout jsx import one more thing and that thing is called a css baseline that's really material ui's magic inside of here just below this opening react fragment you can do a self-closing css baseline component and if you hover over it it says kickstart an elegant consistent and simple baseline to build upon save the file go back to your browser and take a look at how material ui is doing its thing they provided us with this nice light grayish background and they put all of this in place this looks really really good now we can continue testing our mobile form let's go next and the second step of our checkout form looks extremely mobile friendly as well let's add our credit card details and go to the checkout there we go click pay here's our little spinner and thank you for a purchase john wick or the ref and we can go back to home you've just built a fully functional ecommerce store congrats before we deploy this application let's do two more things first is just a small fix i noticed that if you refresh the page after you complete the checkout you won't have the card anymore and that's going to cause the problems so what we have to do is right in here instead of this console log we're simply going to say history dot push and then we're going to push to just slash so we're going to let you know go back onto the home page if you're on the checkout but if there is an error okay of course to have the history we have to import use history from react router dom the same as with the location or with any other hook you have to say cons history is equal to use history and that's going to allow us to re-navigate this is basically like a link but you don't have to click it it just happens as soon as this block of code executes so if there is an error then we push you back to the home page and the error is mostly going to occur when you actually do the order but then refresh the page and then commerce.js will not be able to generate the token because the cart is empty and the second small thing we want to do before deployment is see how our application behaves if we don't have the credit card but now i deleted it and i want to see what's going to happen if you have no credit card entered so i added a few demo items i'm gonna click checkout and let's see what happens i'm gonna enter my first name and all the other information and click next now let's enter the credit card information and let's click pay in this case you'll be stuck with this never ending spinner and that's not something you want so we want to find a way to mock the successful transaction if you currently have no credit card enter and if the transaction cannot really be completed what i personally think is the best solution for this if you still want to have a complete application is to create a specific timeout so let's say that for example if two or three seconds pass then we're gonna say okay thank you for a purchase it is done in that case we have to start a timeout when we actually click the pay button so our pay button is if i'm not mistaken in the payment form right here and that is this handle submit so right in here we should be able to start a timeout and then after a few seconds pass then we want to change something so we're going to have a function in the checkout which is going to say something like const timeout and it's going to be equal to an arrow function inside of that function we're going to have a set timeout it looks like this you say set timeout you provided a callback function and specify what's going to happen after the timeout runs out in this case we're going to change a specific state field so i'm going to say const is finished and set is finished and use state and by default is finished is going to be equal to false so now what we can do is go right here instead of this console log i'm going to set is finished to be equal to true and then based on this is finished we can show something else in here but first of all we have to call this timeout function as soon as we click the pay button we can do that by passing it as a prop to our payment form so in here our last prop is going to be timeout we pass it like this and then in the payment form we receive it as a prop at the top and then we can call that timeout right in here after we're done with the checkout with the circular progress we're going to add one more ternary so we're going to say or and then in here is finished if this thing is finished we want to show a new block of code so i'm going to leave this here and if it's not we're going to show the same old circular progress now in here you should be able to enter the block of code which you want to happen once you mock the transaction so this transaction is not going to be real but we want to show something and in this case i'm going to copy the entire confirmation but we're going to remove all the order details so we're just going to have thank you for your purchase we're going to remove the names and the order ref and the button to the home is going to still be there this should work i know it's a bit of a complicated logic nested ternaries but this was just a fix for the people who didn't enter credit card details now if we go here click that we're gonna wait three seconds after we click the pay button but first of all let's enter our credit card and let's click pay one two and three thank you for your purchase this works perfectly if you're just using this to show it in portfolio but you don't want to enter your credit card details this is it this is the full flow of the application you have the purchase and now you can head back home amazing for the deployment process we'll be using netlify makes it so easy to deploy your front-end applications the only thing you have to do is log in or sign up and the process is going to take less than a minute to deploy your site after you log in or sign up you're going to go to your sites maybe you have none here i have a few and then in here you're going to see want to deploy a new site without connecting to good drag and drop your site folder here the only thing you have to do is drag and drop the folder but we cannot drop this entire react application what we have to do first is run npm run build this is going to put our whole application in a nice package that's going to be easy and fast to deploy and launch for the people on the web when your application is built you can go ahead and right click this build folder and click reveal in finder or open file explorer on windows that's going to open your folder and then you simply have to drag and drop your build folder right here now you're gonna see what i meant when i said it's gonna take a few seconds as i talk this should be uploaded and there we go it is before i launch the deployed application i'm gonna show you one trick head to site settings and then in here change the site name in my case i'm gonna do something like commerce js my store save it and there we go feel free to really change the name to anything you want make it personalized make it your own change the styling add your own items and that is it our application is deployed and fully functional if we weren't using test keys from commerce.js and stripe people would be able to buy these items immediately but if you want to make this into a real store changing the keys definitely is not a problem well after all you build this whole thing yourself to finish this video off i would like to show you a real commerce store created using commerce.js take a look at this see how much life can you give into a website and make it into a real commerce store with categories and with everything you need to launch your online business this looks really good let's click shop now and see what else does this offer take a look this is old built using commerce.js i just had a simple look but you learned all the functionalities so now if you want to give it your touch you can definitely do so for the end of this quite long video i would like to thank you guys so much for watching for sticking till the end and actually building this learning adding projects to portfolio if you came to this video and if you really liked it definitely feel free to leave a like comment and subscribe i would like to see you in the next one i also want to thank the theme from the commerce.js not only for sponsoring this video but for creating such an incredible piece of software using commerce.js even if you're not a backend or a full stack developer you can create a beautiful and a fully functional ecommerce store that was it for this video thank you so much for watching and have a wonderful day you
Info
Channel: JavaScript Mastery
Views: 455,255
Rating: 4.9704924 out of 5
Keywords: ecommerce react, ecommerce react js, ecommerce react app, e commerce tutorial, e commerce react app, e commerce react website, build an ecommerce website, e-commerce react, ecommerce website, ecommerce website react, react website, react website 2021, react, ecommerce, web development, web shop react, how to build an ecommerce website, build an e commerce website, build and deploy an ecommerce, build a web shop in react, ecommerce project, ecommerce application, ecommerce app
Id: 377AQ0y6LPA
Channel Id: undefined
Length: 209min 11sec (12551 seconds)
Published: Sat Nov 28 2020
Related Videos
Note
Please note that this website is currently a work in progress! Lots of interesting data and statistics to come.