Learn Next.js 13.4 Server Actions in 24 minutes (For beginners)

Video Statistics and Information

Video
Captions Word Cloud
Reddit Comments
Captions
yo what's going on guys welcome back to another video today you're gonna learn all about server actions and why they're so useful in next.js so server actions are currently an alpha feature in xjs they give us a couple of benefits they allow us to do server-side mutations without creating additional unnecessary API endpoints it reduces the amount of client-side JavaScript and it gives us something called progressively enhanced forms which means our forms are even more powerful without even needing JavaScript in the first place other actions work both inside of the next.js server component and inside of client components but let's jump into a demo and you'll see for yourself how useful they can be so here I have a blank nexjs 13 project and the first thing that we need to do is enable server action so it's currently an experimental feature so I head into the next config boom I pop it in just like so so it's an experimental feature we simply enable it and then you just want to go ahead and kick start your server so in this case I'm just going to go ahead and start my server by saying npm run Dev so this is what we're gonna see it's simply a nexjs star template I'm going to quickly clean things up so we have a basic starting template so I'm going to go ahead and remove everything inside of our project so that we have nothing to distract us so let's go ahead and get rid of everything so it's simply a empty project so let's get rid of this let's go into our globals let's get rid of all of the default stylings we just have Tailwind inside and then we are good with getting rid of most of our stars right here so I just want an empty project so that way I can demonstrate things for you and you can repeat it and try it for yourself so in this case we just simply have our Hello World app right so hit save and you should see Hello World in the top corner like so so we're going to go ahead and build a product Warehouse where we've got a form is simply going to go ahead and take a price and a description of the item and then we can simply add the product to our database and we should be able to see it in a list of products sounds simple enough right so let's go ahead and build that so then I'm going to go ahead and pop in a form so a form is very simple we simply have a form with two pieces of input so in this case this is our form we have input two text fields and then a button to Simply submit or in our case it's just going to be to add the product right so here is an example of a very very simple form Okay so we've got our products warehouse and then we've got our two forms like so so I'm going to give it a little bit of styling to go ahead and speed things up so each of the input Fields I'm going to go ahead and give a default styling like so so you can feel free to copy it we're simply using Tailwind to get some nice little styling here I'm going to give both of them a placeholder so that way we've got a nice little UI in front of ourselves we've got product name price name done okay now the next step is you're probably wondering we have to actually convert this to a client component to capture whatever the user is typing in the input Fields so that we can run our function add the product do some clever database stuff and actually add that somewhere this is where server actions is amazing right it makes it so simple we don't need to convert anything to a client component anymore instead all we simply do is go ahead and provide a action I'm also going to go ahead and style up our form so in this case I've just given it a little bit of flex rules and that way it looks a little bit nicer right let's style out the button finally boom just like so and there we have it very simple products Warehouse so the next thing is I need an API I need a backend so for this demo today we're going to use something called mock API so mock API is awesome I'm going to go ahead and delete the resource that I've currently created all you need to do is head over to mock API dot IO and then go ahead and create a new project I've already created the server actions demo project so I'm going to click into it and you'll get this nice little URL which is going to represent a your endpoint let's create a new resource and I'm going to call this products now I'm going to go ahead and get rid of all of these fields and I'm just going to have the ID which is already the object ID I'm going to have the product field and I'm going to have the price for it now for the auto complete I'm going to use something called faker.js this is pretty cool all you do is you basically pop in Faker and then you type in Commerce and now I've said that it's a product and a a price and it will automatically populate these for me and the resource name is products so let's click on Create and I'll show you something really cool here so I'm going to go ahead and create let's just say 50 or 49 products however you can just drag this around as much as you want and now this is actually created an API endpoint for me so in this case I'm going to go ahead and copy that paste it into my URL and do four slash products and this is going to do a get request to that URL and what we'll see here is literally 59 different products because we were able to go ahead and say that we wanted 59 different things now if I change this to 30 it will go ahead and update this if I refresh and you can see we've got 30 products so really really cool tool for practicing things just like this my tutorials I like to make them interactive so you can actually try out what we're doing and you can learn for yourself so we have a wicked API endpoint let's go ahead and copy that for ourselves or in fact let's copy the four slash products so the full URL let's head back over to our code and we're simply going to do a async away fetch call so as this is a server component we can actually run async away at the top level then I'm going to go ahead and fetch the product so I want to go ahead and simply do an await call here we're going to fetch that URL like so so we're going to go ahead and copy this URL so we copy that we pop this in like so and then we are going to make it a get request now this is by default already a get request when you have a fetch call but what we're going to do here is actually go ahead and say just for this demo we're going to actually say that the caching is off right so we're going to disable the caching because nextges by default we'll catch the results and then you might run into some issues with this demo because you might be wondering why is my data not updating don't worry I'm going to make a whole new video on xjs caching so I've got you back and afterwards I'm going to add it to this video somewhere and it'll pop up on the screen okay with that done I'm going to Simply Define what a product is in typescript so in this case I'm just saying the ID is optional but we do need the product and price when we submit that form and then I'm going to go ahead and pass the response right so in this case we can simply go ahead and get all of the products by awaiting res dot Json okay so this is our products like so and I'm going to simply pop it out at the bottom and then we map out through all the different products and showcase it so let's hit save and showcase our work of art and as you can see boom we have a products Warehouse with all of the items listed and as I mentioned before if you change this up go back to your page refresh we should see aha perfect Okay now what's really nice about this is I can make post requests to this endpoint and we can actually see this update so this is a real example of a mock API and we can actually go ahead and interact and actually apply our server actions logic that you will learn today to actually go ahead and see if this works for itself so typically I would have to go ahead and convert this entire component or just this form I would have to extract it into a separate component and make that a client component because I'll need to track what the user types in track what the user types in here then when they submit or click the button inside of the form I will then need to go ahead and handle some JavaScript which will then do a bunch of things right so typically we have our client and so in this case this is our website so we've got the website and then you've got these our form so in this case you've got your product your price and then you've got let's just call this the submit button over here okay so imagine this is our add button over here now typically what will happen is you would fill in the product you would fill in the price and then you would click on the add button now when you click the add button typically you would be like okay I need to make a post request in which case I need to actually create an API endpoint right and typically you would have something like you know API forward slash product and then it would be a request that will go towards your back end and you would have to create all of this right so you'd have to go ahead and pass in you know the body of the post request make sure you handle it and sort of interact with your database over there then you would get the response back and then you would probably have to you know go ahead and add that to your local state and then list it out and so forth it's a it's a lot right it's not it's not the hardest thing to do but it's just an extra step that you have to do every time to do things to avoid problems such as cause and all those annoying things so server actions saves ourselves a huge amount of work and in fact I'm going to show you how easy it is by demonstrating it right now the first thing you'll notice is we actually have an action property on a form this goes back to the PHP days right so we're actually going ahead and taking a step back to get ahead all right so a lot of people are subjective about this but I think it's pretty cool and and it's got its use cases the next step is pretty simple as we have the form data here we actually have to give our input Fields different names so in this case we have to say name for this one is product and this one will be simply price okay now that that's done I'm going to grab those values from our form data like so and they may or may not be undefined so in this case it's good practice generally to do something like a defensive programming statement like this so we say if there is no product or price just don't do anything so it's actually good thing to do that a lot of the time then we're going to go ahead and actually build out a new product so I'm going to go ahead and create a new product object like so and then we're going to go ahead and pass this to our endpoint that we've gone ahead and created on mock API right so in this case I'm going to do an await core patch over to that API endpoint that we previously had so that's simply going to be this endpoint right here so we pop that in I now need to make it a post request and then inside the body of that I'm going to stringify the new product okay and also it's worth mentioning in JavaScript es6 you don't have to have this repeater twice if the key and value is the same now you know a little extra tip all right we're also going to pass in the headers to be content type application Json as we're going to be passing in data in the form of Json and yeah that's pretty much it now we're not finished yet whenever we're using a server actions we have to actually go ahead and add in a special little directive here called use server by adding user server we've now converted this function into a server action right so this is now a server action which means it will essentially run on the server and we can use it inside of our server components also it works in client components I'll show you how to do that in a sec so let's go ahead and give this a try over to my app and I'm going to pop open my inspector and you can see in the network tab we have nothing at the moment but in this case I'm going to type in a MacBook Pro and we're going to say it's 1300 pounds and we're going to add the product now you will see that if we look inside of here we have a post request so this is a post request that has been sent to our backend and if we look inside the payload you will see that the product and the price was actually sent alongside it so this was sent inside the bodies the MacBook Pro and 1300 now if we you can see the UI didn't update so that's a bit of an issue but if we go to mock API and we actually inspect the data we should now see a MacBook Pro right so you can see it actually went ahead and done an entire server mutation with a very very little code just by including the server action we completely eradicated the need to go ahead and actually create a new API route and all that good stuff right so typically you would have an API route or using the news and xjs13 Convention you would have a route.ts file and then you would have to create a you know an endpoint and then you would have to have a sort of post and then you'd have to handle the response all that good stuff and uh yeah it's not fun for anyone right so there is a time and place for API endpoints but this is honestly simplifying things so much I'm here for it now we as I mentioned before it was not updating the UI that's a bit annoying that's a bit of a problem right so how can we actually go ahead and fix that well very simply actually so when we did the initial fetch we can now actually add something called Tags so so we simply go ahead pop in a new tag and this is simply an array of different tags string tags that we can pass into our fetch core and these tags are really cool because what we can do is inside of our server action all we need to do is after we've done our server mutation and we want the UI to be updated is revalidate tag this is being imported from next cache and then what we do is we simply pass in the tag that we want to go ahead and revalidate so using that one line of code if we hit save we can now go back to our app and let's go ahead and just do a little refresh to prove to you that everything is you know fresh we've even disabled cache I'm going to type in let's just say an iPhone 15 right and then we say uh price name maybe the 999 and let's add a product and as you can see boom ah it did it right so that was actually completely streamed in from a server component which is really really nice right so that means that we didn't have to go ahead and refresh the page or do any kind of you know annoying things like that all it did was essentially it burst our cache and it refetched this right by basically saying that after this fetch occurred we now revalidate that tag which means that any electrical which was labeled with that tag needs to be re-fetched so in this case it's not going to refetch all of the different fetch cores it would individually only refetch this one so it's actually quite an efficient way of working on your page now as you can see this works perfectly so we can go ahead and say iPhone 16 and I can pop in one two three add a product and boom just like that we have a perfectly working form and what's really cool about this is it supports something called Progressive enhancement out of the box this means that if your JavaScript was disabled for whatever reason it will actually operate and it will work this is similar to how PHP used to work back in the day but now it's support out of the box for next year's 13 which is pretty damn cool now the next cool thing to know about server actions are that they are composable now what does that even mean it means basically in a nutshell that we can we don't have to have this function inside of here right typically I want to keep my functions nice and clean this is not really that clean so I'm going to go ahead and neaten this right now by moving it out into a separate folder of its own so I'm going to go ahead and create a new folder called actions and this doesn't need to be called actions you can call it whatever you want I'm just simply going to call it my server actions folder so.ts and then I'm going to go ahead and copy or actually I'm going to cut my function from here go into my server actions and paste it so in order to get this working we're simply going to move the user server call to the top of the file and all this is doing is it essentially says that any function beneath that U server is now a server action okay and then all we can do is we can export that function and use it elsewhere things like you know our type definitions if you really want to make things neat you can go ahead and what I would recommend is you actually sort of export this create a new typings file so in this case typings.d.ts File and then you pop it in there and now you've got a much simpler code base and you simply import it when you need it okay so as you can see that works really nice we can get rid of that we can simply import from our server actions like so hit save go back over here we can do the same thing we can import from our typings and we can import our next cache revalidate tag just like that we've now shifted our server action outside and we can have several server actions in the same file really cool right there's minimal code and we have a full round trip we can actually have a server mutation we have a fully functioning form and we have the ability to revalidate the page now that's not the only way to revalidate it it can actually do a revalidate tag based on the tag or we can actually revalidate based on the path so if we was to revalidate the home screen for example in this case this would revalidate the entire page now why might you not want to do that well the fact is is that let's imagine I had several different fetch calls what would then happen is it would force all of those vegetables to actually refetch and that can be a bit of an annoying problem depending on if you've set up your caching correctly right so I would recommend that you actually just use tags that way you're specifically saying if this happens then revalidate only these products or only these students or users or whatever your tags are and it would only go ahead and bust that piece of cash and then refetch it accordingly now the next thing I mentioned was it's possible to use this inside of client components so let's go ahead and show you a nice little example of how we can do that so I'm going to create a add product button component so I'm going to create a new folder so this is a typical flow inside of an app we would have a components folder and then we would have something like this we'd have an add product button component so in this case add product.tsx and inside of here I have a component so we have our react functional component like so and this component is going to look something like this so it's going to be a button right instead of the div it's simply going to be a button and it's going to have a add product okay and we're going to convert this entire component to a client component like so so let's go ahead and import this into our app so at the top of our products Warehouse let's simply just make our life easier and have it right at the top we're going to add product button and this is just going to add a static MacBook Pro of a specific price purely to demonstrate the purpose of what we're trying to do here okay so if we want to use it inside of a client component firstly we would have to shift all of our server actions into their own file with a new server core at the top okay so that's the first step that way we can import it into our client components if we need it the second step is use something called the user transition hook so as we are now a client component we can use our hooks so let's go ahead and pop it in and we're going to import the use transition Hook from react this will give us two things from the already structured values we've got is pending and start transition the code is a little bit ugly here but I promise you it will make a little bit of sense once we actually play with it the whole point is is that we can actually now call it so if I want to go ahead and say on click all I would do is when I click this button I just need to go ahead and start the transition and what you want to do is you basically want to invoke it with a inner function and that inner function is actually the pro the server action that we're actually going to call so in this case I'm going to be calling the add product to database function now this is complaining because the added product to database function actually required the form there so I'm going to do here just for demonstration purposes is I'm going to go ahead and create a brand new form data item at the top right here so we're going to create a new form data item I'm going to Simply add in a MacBook Pro of a certain price and I'm simply going to pass in that form data object right obviously you can do a lot more complicated examples this is purely to damage straight the point I'm going to add in a bit of basic styling so that way that button is nice and fixed in the bottom right hand side and it's a nice little red button or green button in fact and then we're going to go ahead and hit save but you might notice this is pending this is pretty cool because when we actually go ahead and do that server mutation you saw that there was a post request that got fired off while that is happening what if we want to update the UI well we can actually use the is pending okay so it's pretty handy let's go ahead and actually instead of saying add product I want to say something like if it's pending then I'm going to go ahead and say adding otherwise it's going to go ahead and say something like add MacBook Pro okay simple as we're going to hit save and now let's go ahead and see what this looks like inside of our app so we've imported it at this point here so I'm going to go back to my code refresh and we should see an ad MacBook Pro button right here now what's really cool about this is this is a client component so it's rendered on the client after the server component has rendered and then we can go ahead and click on this and as you'll see when I click it if I go ahead and hide this now you'll see that we have the exact same interaction but we get a UI update at the same time so look at MacBook Pro it tells us it's adding it then it goes ahead and adds it and we have the same thing form date ago you know added into our post request and it was a 200 sent back right and then they revalidated the tags and everything was perfect so as you can see this is how we can use it inside of a client component and we can get an update um as to what it's doing at that point in time so we actually get the is pending State and then you can use that to reflect any UI changes that you wish now it's worth mentioning that you can actually add in more than one action inside of a form so in this case we've got the form action here by default it will trigger off the server action add product database well in that case it's very simple we can actually do it with things like input Fields where the type is image and we can go ahead and use the form action property to go ahead and create a new action so you would have to create this submap actually submit image action exactly the same way we created add product to database but when you select the image it will go ahead and actually fire that off instead it's worth giving the documentation a nice little read so in this case in the next year stocks you can actually see it works with input type submit input Type image and it works on a button as well so in this case the default form action was handle submit but if you went ahead and submitted via the input Type image so in that case when you select on you know click on select image and it pops up with the little window it will go ahead and actually trigger This Server action now remember I showed you these are composable so you can shift them out to keep things clean but it's always worth mentioning that you can go ahead and do this now I do want to mention an important note as well whenever you go ahead and actually use a direction inside of a client component it will actually go ahead and get rid of that Progressive enhancement if you use the transition hook right so the use challenge position Oak the reason for that is because it's actually requiring JavaScript to do a few of the clever things that it needs to do for example keep track of if it's pending and so forth so remember Progressive enhancement means that it essentially works if JavaScript is even disabled so basically at the raw rawest level you can imagine but if you want to know you know if it's pending and have that nice little interactive UI for example when we were messing around with things when I click this that little adding update then you're going to need to go ahead and it will actually disable it by default it does State this inside of the documentation as well so it's always worth giving a little bit of a read inside of the documentation okay now the final thing to know is that you can actually save this and keep your Progressive enhancement if you don't use the use transition at all right so it's actually fairly easy to do so so let's say we weren't going to use that and we still want to use the server action well in that case you can just simply do it like this right you can simply go ahead and get rid of this get rid of this we can go ahead and use it like so and where we have our own clicks in this case let's go ahead and get rid of this let's just type in ad for example like so and then let's go back to our application hit refresh and now you'll see that we've got an add button and when I click the add button we still get the same behavior as you can see this is a client component it's using a server action but we keep the progressive enhancement because we don't really care about the UI being updated so that way it allows it to basically run even if the JavaScript was disabled for whatever reason now if you notice when I click on ADD there's a slight little delay between the time when I clicked it and when it actually shows on the screen this is because there's that post request being sent out and then we have to wait for the response then it revalidates and so forth all of that happens in a round-trip fashion so if you don't want to have that delay you can simply go ahead into the docs and check out the use optimistic hook this is basically going to allow you to have optimistic updates which basically means when you click it it appears as if it's instant when really it's actually you're guessing what's going to happen first and then that provides the local state and then it does the back end call behind the scene means so I'm not going to explain that today but if you do want me to make a video and use optimistic cook be sure to drop a like if this video gets enough likes you know what I'll do I'll create a video all about it to explain it to you with that said this was your Deep dive into server actions in next year's 13.4 I hope you enjoyed this video and I hope you found it useful and I hope you understand now how you can use server actions in both client and server components how you can get your UI to update if you want to see what the current progress of this day is and how it saves you a lot of time as you no longer need to go ahead and create your separate API routes just to make a simple server mutation remember this is currently an alpha so things are likely to change things are likely to be you know a little bit different but by the time you may be watching this video make sure to always go ahead and refer to the documentation as well as these videos and don't forget if you want more content like this like comment and subscribe and as always guys I will see you in the next one peace foreign
Info
Channel: Sonny Sangha
Views: 14,205
Rating: undefined out of 5
Keywords: react, developer, reactjs, html, css, js, javascript, papa, papareact, papa-react, tutorial, frontend, webdev, dev, clone, backend, fullstack, motivation, reactnative, react-native, redux, typescript
Id: W6V91VeghjI
Channel Id: undefined
Length: 24min 44sec (1484 seconds)
Published: Thu Jul 06 2023
Related Videos
Note
Please note that this website is currently a work in progress! Lots of interesting data and statistics to come.