Learn React Testing Library by adding tests to a login form

Video Statistics and Information

Video
Captions Word Cloud
Reddit Comments
Captions
so for today's workshop well we were really gonna really go through is just testing and adding react testing library I feel that for front-end anything really a testing is really important and when you get to your interviews and whatnot right not talking about testing might actually deduct points from your overall experience so knowing about testing is really important not only that testing gives you a lot of confidence on your code it allows you to refactor with ease right and the reason I really like react testing library is because it really mimics Moore or it simulates the way the user really uses the app and ever since I started my career I've always taken more of a behavior driven approach to testing so I like to really test the way the user uses the components right and I think that's where we act testing library really shines here so we're just gonna really go over this app it's a really simple app that we have here it's just been logging for and very basic if they're the email is wrong pending that our mega good validation here just imagined that this is like NASA tap validation right here right and what we're gonna do is we're gonna validate our input and if it's not a valid email it's just gonna throw an error it's gonna display a message right so we're gonna be able to test a few different things here we're gonna be able to test just let's say a function we're gonna be able to test if the data that was input was correct we're gonna be able to test that event clicking event inputting tax changes and all that so you know because you are using Create react app here we don't really need to install it anything else it already comes with react testing library out-of-the-box it already comes with just aam basically setup for us if you want to overwrite this you can always override through adding your own just configuration and your own setup test files here so it even gives you an app test right so let's you know let's start digging in and let's start writing some tests so the first thing that we want to do right if you noticed we talked we have a function here which is being exported and we're also using styled components by the way I'm a mega fan and see if you've been to my workshops you know this already so let's import our valide input function so we're gonna call valide input and let's you know delete this image so when you write the scribe which by the way you don't need to import or anything because it is part of just we create a suite of tests and with this suite of tests we're gonna be able to add different tests which within those tests will have different checks and this will allow us to basically be able to debug our tests easier because we're gonna the more granular they become right and I'm not saying go full-on granular but I'm saying there's a balance and the more granular when you find that granularity sweet spot it becomes really easy to debug because you're able to identify which part of the test broke way faster right so what we're gonna do here is just gonna let's say we're gonna describe the login form so we're describing the entire suite the behavior of this form right and we're just gonna open a callback so a describe statement just very similar to a test statement the anatomy is very simple actually we have a string which is the first argument the second argument is a callback and in this case the contents of this callback are gonna be just more test statements they could also be described you could actually nest Suites within Suites so we're gonna go test and we're just gonna say should or validate function should I don't know vanity or should pass are correct email let's say or correct input let's just see just make it a little bit more generic then again similar to describe statement the second argument is a callback and what we're gonna do here is we're gonna say all right so let's just write some text text right and what are we're gonna say is text at first calm and then what we're gonna say is so the actual first statements that we use to create assertions ingest and this is part of just right is the expect statement so we can actually go and write expect and then we're gonna say validly input so if we pass text this should be true to be true right that should be your first test and what we're saying all right so let's look at our other function right and you know what let's let's just bring it over here you don't need to follow this part I'm just gonna bring it over here so what it does right the function takes a string as an argument and the argument we add the includes which is a string operator and what includes does is that as soon as it finds that piece that were specifying to it it'll return true or if it doesn't find it it will return false right so when we're saying expect validate input and we give it a string with an app sign it should be true right so because we are using create a react app and we don't need to install anything else we could just do NPM test and the reason why this happens is because because we're using create react app this already comes out of the box set up for us right so we're gonna do npm run test let me expand this see just already comes fully blown out of box set up giving us really nice detailed information so it passes awesome now in testing we also always want to test the the edge cases right we also want to make sure that this fails if we don't give it the right information right so we don't include an @ sign or something that causes this to be a false value right so we're gonna add another test statement and we're just gonna say validate function should fail on incorrect input right and now we're just gonna say Const text equals text and again we're just gonna write an assertion and what we're gonna say is validly input text and you know what just to add some fun to it here what we're gonna do is we're just gonna say not that to be true right if it's not true it's gonna be false so this should be return false at this moment and as soon as right we have this and it passes now see we have to test valid a function pass correct input and validate function should fail on our correct input and we've kind of already there just created a little bit of a function tester or or a unit test right but you know let's talk a little bit about the actual component and how we can go about actually doing that components and I just hit save and I don't know if you notice but my build start it kicked off again and that is because by default if we run in create react app just and test it'll just have the watch flag for us so it'll just keep watching and you know this really takes test-driven development to the word because you could actually have another console and I do this all the time where you have let's say it any terminal pain and in a terminal pain you have NPM run test and watch and as you're developing if you have this parallel to your vs code you can see if when you make a change if any tests fail you immediately know that your test broke something right so now we're gonna go ahead and add our first component test and this is more of a UI thing of a Dom thing but I first of all my first test and this is actually already a habit for me I like to make sure that the component in action is actually in the document right so we're gonna do this by obtaining this value so we're gonna get by text we're going to expose it Tom we're gonna get the node by the text and we're gonna assert that the DOM is actually in the document right so we're gonna say render test I'm sorry renders or login form should be in the document again first argument is the string and the second one is just going to be a callback and in this callback we're just gonna say Const then we are going to write this you know what I was going to structure but we'll just say component and I'm gonna say render and then we're gonna say all right so here is now where we're starting to use react testing library and will react testing library let me see if this is an error okay so what react testing library is gonna do for us is it's gonna provide us the render function and this render function we're gonna pass it a component and this is gonna take care of exposing the Dom for us and being in giving us the power and the accessibility to be able to reach into the nodes grab the nodes and perform exertion from them so what we're gonna do here is we're actually gonna say all right I'm gonna just show you what component is console dot log component right so let me expand this a little bit and this is a huge huge object therefore we're gonna have a lot of information and a lot of opportunities to test different things but right off the bat right it gives us all the selectors or queries that we can use so as you can see we could do query all by label text we can find all by label text but we can also do more specific things like get a text or get by role or just you know find by data test ID things like that so if you can see also we're gonna have a lot of information here right now that's just going to be normal but but a lot of information about the component itself right so let me minimize this and now which we're gonna do is we're gonna say alright Const and we're gonna say input node just I like to call them input or know what I mean or elements you can do either or it's fine and we're gonna say input element is component dot get by and we have some nice autocomplete here get by text and because we are being a little bit we're not adding any like a sensitivity or anything we're just gonna say email exactly as it is right and now we're gonna write our first assertion and we're gonna say expect input node to be in the document and essentially what this is doing is we're grabbing the input node so react testing library is gonna look for this input node by get by text then we're gonna expect that the input node is in the document and this is actually a added assertion from just Dom so if we go down here and we hit save this should be true cuz what's gonna happen is a we're looking that essentially email was rendered in the HTML content right cool sweet so now you know logging should be in the in the document let's try to another test statement right and you know we now know that a we have an input we have labels let's make sure that our label and our inputs are correctly related to each other right and we can actually do that a couple different ways well I think that the nice one here is that because we've labeled HTML 4 right and there is a relationship here between the input label in the foreign attribute and the name attribute or the ID attribute right they should be related together so if we look for the label email we should be able to find the input which corresponds to the name image so what we're gonna do is we're just going to you know what we're just going to copy this again and we're just gonna say test and then we're gonna say log it in email field should label oh well we're gonna say here this we're just gonna paste what we had up top right and obviously as you're writing this test I'm just repeating right now but as you're writing your test you don't need to learn copy paste you can use actually different lifecycle hooks that just brings like before test or before all or before each things like that so now that we're on the input node we're gonna say all right we're gonna change it here we're not gonna call it get by text we're actually gonna say get by label text right so if we go to wrap our label text is email and we're gonna say let's just call this one email input no all right this actually is not infant no this is more label node really now come to think about it so we are gonna reach to the email field by means of the label because we've labeled our no pun intended because we've labeled our labels and our inputs correctly we should be able to reach in into our input because of this so we're just gonna say alright we're gonna use another part of react testing library so we're just going to say alright expect and we could say I'd expect email input node dot attributes was it get attribute and we're gonna say that the attribute for right so if we're saying alright we're saying get label by text actually it should be the attribute in name I think alright so yes because we're looking at the input node we're just gonna say to be email just save that and let's see if this worked right if we correctly label their stuff in if not we just go back and we fix it up right but it worked so what this essentially is telling us is that a our accessibility is really on point at this point because we've actually related our our inputs and and our label correctly right and we can prove it because hey we went to the component app we grabbed the label we didn't even grab the input we grabbed the label which the email text and then we went we grabbed the attribute of what is related to that label we look for the name and it should be name and if we go to our input will see that our name is actually email so awesome now we're gonna start exploring a little bit of how react testing library manages events and we're gonna do that by writing another test and we're gonna say email input should accept text and now we are gonna open a statement and if you notice down here right we have for each of these so first of all we have the describe statement which is this right and just gonna write this crime statement this way we can actually see what's going on here in the reporting terminal right and now we're gonna say all right login describe statement login describe statement and each of this cases is down here right so if any of this test fails at any of this point we're gonna be able to identify where it happened quicker rather than if this was a big test to just want a space we'd actually have to go a lot of debugging right so that's what I'm meaning about finding the sweet point of granularity in your tests now we're gonna you know just actually this time we're gonna look for the input node and equals render and we're essentially just doing the same thing we did up here but now we're gonna say fire event then we're gonna say change and then we're gonna tell it in pull email input node then we're gonna pass in a second argument and in this argument what we're gonna say is target value and the value is gonna be testing right and also we before we do this we're just gonna say expect email input node dot value to match or to be too much just we're just gonna say too much just to show you something different and we're gonna copy this line right here I'll bring it down here and now we're gonna say down here that I should match testing so before I run this test I just want to walk you through what we're doing alright so we're just destructuring get labeled by text that way we don't have to write compound in that right and what we're essentially doing this we're just unpackaging what render from react testing library does for now once we grab that node we're gonna say a that no it should be empty right now there should be no texture and essentially that's what we're doing then we're using fire event which we imported from testing library react and we are using a method called change like on change right when you're writing your react apps and then we're saying that email so it's gonna take the email input node and then it's gonna grab the target value and it's gonna you know change it to testing then we're gonna expect that testing was actually input into the node so what I'm gonna do is we're gonna head save here right and voila there we go right so you know it's interesting because at this point we should also you know be able to notice that if our little mischievous validator you know came to be so if you remember we have this validator here so what this is saying a if if there is an email and the email is not valid meaning it doesn't have an @ sign we want you to display this error message which if not just no right and what we could say here is Const error message node equals and we could say let's see we could say email not valid here right you can say get by text it's a email not valid so if we do expect error message node to be in the document cool hopefully I should pass so this is so what we're saying now is that because the email was all right so we have a failure here all right it says get by text query selector all OH that's because we actually never imported cool so the reason we actually have this error here and I forgot here is because we actually I think never really import this right so get by text and hopefully I should pass now we're actually never importing that by text does it would fail right huh so now we are all passing so essentially what's going on is that because we've actually so we're again testing the validator but we're now testing that the validator validator integrates well with the component so now if we do fire event right and we just write fire event again and then we do change then we say email impaneled coma second argument open an object target open another object value and the key would be testing and now we would say ah now we could grab this same line 36 copy it paste it right after our new message and you could say not to be in the document right and essentially what's gonna happen now is we've gone through a little bit of a workflow right if you notice this is what the user does so the user goes and looks at a label it looks email Court finds the label is related to the input so it knows alright in this input I should input my email right now this we're gonna assert that this should be empty the user has not at this point added any any validate any text to it then we the user is gonna add test to it and that task text is going to be testing now we're gonna assert that the value of the input node was testing now because we didn't add an add sign meaning it'll fail our validation our handy mega error handling message should reveal itself and it is now in the document because email is not valid now exists in the now this present in the Dom then we're gonna say the user is gonna go in again and it's gonna type is email gun with an @ sign and the error message should not be in the document anymore meaning it went away right so that that's the beauty of react testing library I feel in the sense if you could see this is really how I would see a user more using or interacting with our application right rather than saying hey you bought in with the class one two three click yourself that's never happened so now what I want to go over is teaching you how to add another fire event and this time we'll be submitting the form and we actually want to test you know that the button was clicked the button works we're gonna add a spy which is a just function that will essentially integrate ourself into our code we will provide it to our code and it'll essentially you know be listening for any events that happens such as a click and then we can actually assert if it happen or not right so we're just gonna say test another argument and we're gonna say you know should be able to sue me for no we're gonna write the callback our second argument and this time around what we're gonna do is we're gonna say okay let's find another one just to if you notice so I created this button right and I say it is roll button and we have submit and that means that when it submits it should handle submit which is something a function or a callback that we're providing as a problem so we're gonna say and this is at this point it's just more convention for me I just do mock FN then we're just gonna say just dot FN and this is a spy and now what we're gonna do is component I mean constant spelling it out Const we're gonna do structure get by roll and then we're gonna say render NSA app we're going to do handles May which is the prop at handle submit we're gonna pass mark function and here we're gonna say you know we're just gonna close that then we're gonna go ahead and grab our components so button node and we're gonna say render and for render we're gonna do oops sorry get by rule and and get by rule we're gonna get five button nice now we should go ahead and say fire event stop sup me and we're gonna click a button no and let's just see what happens so by the way we are clicking a button but the action that we're actually performing it's submitting a form so what we're gonna do this time around is we're gonna use submit not click because if we click the button nothing's gonna happen with the form the events not gonna register right so we're gonna do fiery red dot submit and then we're just gonna say expect mock function and again this is a jest I mean a just Dom assertion we're gonna say to have been called times be careful with the case in here times 1 so essentially what we're saying is that a this function was clicked that the event was submitted and now we are expecting this pie that we installed in the components so just a function to have been called at least once right if we went ahead and we submitted this two times this would now fail because the event happened twice and we are saying a it only clicked once but you know maybe in the back maybe there's a plugin and two events got fired off right so now we could just say twice it was called twice if we actually intended to be called twice right and there's other assertions I'm pretty sure I think this is one where we could do to have been called it's just a it was called right we're not a specifying how many times how many nothing but there's plenty of those so you know just to recap we've we have six passing tests all of them are inside a described statement which is up here and then we have our email inputs are we're testing everything so
Info
Channel: Alejandro Roman Arguello
Views: 3,157
Rating: 5 out of 5
Keywords:
Id: hPOS6IRKJm0
Channel Id: undefined
Length: 28min 39sec (1719 seconds)
Published: Sat Jun 20 2020
Related Videos
Note
Please note that this website is currently a work in progress! Lots of interesting data and statistics to come.