Check out a free preview of the full API Design in Node.js (using Express & Mongo) course:
The "Testing Q&A" Lesson is part of the full, API Design in Node.js (using Express & Mongo) course featured in this preview video. Here's what you'd learn in this lesson:

Before moving on, Scott answers a number of audience questions on testing strategies and demonstrates a few alternative approaches.

Get Unlimited Access Now

Transcript from the "Testing Q&A" Lesson

[00:00:00]
>> [MUSIC]

[00:00:00]
>> Scott Moss: I'm curious what are some other strategies that people use? Anybody use something that's different?
>> Scott Moss: Everybody did it exactly like this? I doubt it. Unless you looked at the next branch. So I know you used provinces.
>> Student: I used provinces, yeah.
>> Scott Moss: Who else did something different?

[00:00:26] No.
>> Mark: Just asking on line five, the way you wrote line, is that a style thing?
>> Scott Moss: No it was just I don't know I'm just picky about how this stuff prints out in the terminal, and like if it didn't, like if I get rid of it. It just didn't show up well enough for me so just put brackets around it.

[00:00:46] That didn't show up well enough for me. I was like I'm gonna put brackets around it so it shows up better. That's it, yeah, it's just a style thing, so that's why I put brackets around it. Even then, I'm still not satisfied the way it looks, so I might change the color of it or something.

[00:01:04] What you could do you could NPM install colors and change the color of this thing to like yellow or something like which is pretty cool. So if I say require colors and then npm install save dev colors. And then now when I run this, it'll be yellow.
>> Student: That's cool.

[00:01:32]
>> Scott Moss: Yeah.
>> Scott Moss: Yes?
>> Mark: Is there a way to use test data like data stored externally for creating and inserting?
>> Scott Moss: Yeah, there's totally a way to do that. We will get to that after we get to actually creating the API for the. So yeah, we will be using databases for assertions, and having like a different test database versus a development database versus a production database.

[00:01:59] And how to switch those off, so you'll have to do it manually. Yes?
>> Student: Can you go back to the spec file?
>> Scott Moss: Yep.
>> Student: Line 12 there.
>> Scott Moss: Yup. This one?
>> Student: Yeah. What is that second parameter?
>> Scott Moss: That's a regex.
>> Student: Gotcha.
>> Scott Moss: So it's, so yeah.

[00:02:17]
>> Student: And then on line 13, it says expect and it just has the number 200. How does it know that that's a status code that [INAUDIBLE]?
>> Scott Moss: Well, the only thing I can think of that it knows it's a status code is cuz there's no other thing on this request that would just be a number than a status code.

[00:02:32] So I guess it just assumes that. Cuz I can't think of anything else that you would put just a number in, and it would be that. Like everything else has like you know a key value fair content type like headers. But status code is just a number so I'm guessing that's how they know.

[00:02:45]
>> Student: And then prior to line 14, you can't go digging through the response to start extracting JSON data, you have to be passed line 14 is that correct?
>> Scott Moss: You have to be in the .end callback, yeah. You have to be inside it to callback. So I could just get rid of all this.

[00:03:01] I don't need this stuff here. Oops, get out of here. I don't need any of this stuff here except for that. I just can't, I don't get access to the response till I call .end.
>> Scott Moss: All right, if I didn't wanna test, for instance let me show you.

[00:03:21] If I got rid of all that and I said console.log the response. I get all the stuff that I just got rid of. I get the status code, I get the headers, everything on the response is still here on the resp. Right here's the entire response object. It's huge.

[00:03:36] So I can look at that too if I wanna get the status code and everything else. It's just those methods are just as you can see the object was huge. So those methods just test it for us [INAUDIBLE] Yeah.
>> Scott Moss: Any other questions?
>> Scott Moss: Cool. All right, so that was testing.

[00:04:09] So, more of less that's how integration testing is. Of course it gets more difficult when you start dealing with things like databases and like authentication. Then you have to create fixtures and mocks and stuff like that. So yeah, it will get more complicated. But once you get past all those details, when you get to like, finally, I created my mocks, the database is good to go, all this stuff is here, my pictures are made.

[00:04:34] And when you get to actually testing, it'll be like that. It's like, make a request to the server, make some assertions on what the server responds back with and then you've gotta like clean up, now it cleans this stuff up. So for instance like if we go back to our test if we were actually like posting to a database, just to ensure that the next test had like fresh data that wasn't messing around with other data.

[00:04:58] We do like an after each and afterEach, drop the database or something like that. Or afterEach, get rid of all the lines in the database. So we know that it won't interfere with the next test coming out that needs it.
>> Scott Moss: That's why it's important to have a different testing database then a production database.

[00:05:17] [LAUGH] Or even a development database. Should just separate those two.
>> Scott Moss: Any questions?
>> Mark: There were a couple that came in. Let's see a couple. In general, is unit testing node code done in real world applications, or do you mostly do integration testing?
>> Scott Moss: Yeah, I definitely do unit testing in the node world cuz, I mean, quite honestly, you just don't use node for servers, node is used for a lot of things.

[00:05:48] Like tooling, some of the most popular tooling out there today is built on node. Gulp, Grunt, they're not servers, they're all just command line tools so they are nothing but unit tested. So you definitely will use unit testing It's just that if you go look at the code that we wrote, for instance go look at lions.js, all the functionality that we care about is inside of a callback.

[00:06:10] It's kind of hard to unit test, right? Cuz this code doesn't even get ran until Express fires this. And Express doesn't fire this until you start the server and hit the route. So it's kinda hard to unit test so we didn't really write good code to be able to unit test.

[00:06:24] There's only one function in here that's not inside of a callback, and it's this update id, and it's not even being exported. So we still couldn't test it, we'd have to export it, alright, so we really can't write good unit test for our code. So integration test was our only option.

[00:06:38] We could write unit test, it would just be, we get to the point where we start unit testing express itself. We'll be like all right, I'm going to write a unit test on this router to make sure that it has these routes. Then you start to get into what the express is already doing.

[00:06:52] So, any other questions?
>> Mark: And then the next one is, is it a best practice to write separate describe statements for just crud operations? Or should you get more granular? For example, it should respond with JSON?
>> Scott Moss: Yeah you should be as granular as possible on your descriptions.

[00:07:10] And I think you can use as many describes as you want. I don't think there's a limit on that because whatever is right for you, you can do it. I would say if it makes sense organizational then do it. This example here is not the go-to. This is not exactly how you should write your test.

[00:07:28] This is just how you write tests. But I think it's gotta differ depending on what you're doing. So you can do nested. You can put another describe here and it will totally be the same. Then if you put a before each or it in here then that is gonna be scoped to this describe.

[00:07:48] So yeah, you can do whatever you want.
>> Mark: And then what's the difference between a mock and a fixture?
>> Scott Moss: A mock is like. So this lion is like a mock. This is a mock lion. So mock data. A fixture could have a mock in it, but a fixture is more like, I don't know the words to describe it.

[00:08:19] A fixture is more like your mocking not just the data you're sending in, but kinda like the environment, too. You wanna make sure that this code is gonna run exactly the same way in the certain environment. I don't really have a better way to explain it. I'll get back to that question.

[00:08:35] I wanna look up something better than that explanation.
>> Scott Moss: If somebody else has a better explanation that would be great, but if not I'll look it up.
>> Mark: And then the last one is, are there frameworks that support mocking objects?
>> Scott Moss: Yeah, Chai does. So Chai has, it is a mocking.

[00:08:55] Chai, mocks. Is it Sinon Chai? No, it's not Sinon Chai, it's just Chai. Let's see. The thing is that you have to download a plugin for it. Let's see. There's so may plugins for Chai, but yeah, Chai definitely has a mocking library that you can use. And that's why I use, if I use mocks.

[00:09:19] But there are tons of other ones out there too, that work very well. Sign on JS is a popular one. Sign on J. How could I forget that one? Sign on JS. Cool, and other questions? Cool all right.
>> Mark: One literally just came in.
>> Scott Moss: Okay.
>> Mark: When you run multiple tests are objects destroyed before each test?

[00:09:51] For example in this case if I run the sequence to create line only once. Get update delete, will it work or do I have to create a line for each test.
>> Scott Moss: Say that again let me see, so I think when they say each test I don't know if they're talking about each it block or each run through the test I'm not sure.

[00:10:13] But if we're talking about each test like if I run the test here and then I run it again. Does the stuff stay there? No. It doesn't stay there because we don't have a database. So the server starts, and then the server stops. So everything, all the lines that were held in that array in memory is gone cuz the server is shut down.

[00:10:32] But what we're talking about does the objects get destroyed between these different it's here? No, because the server's running the entire time. So, the server starts here, it's still running. I think the server is still running here because it's request started. It doesn't get destroyed until you destroy it or the server shuts down.

[00:11:06]
>> Scott Moss: All right, sweet. So, we got through testing. We will be doing more testing, but this is the first part of testing. How's everybody feel about testing? Okay. Feel good? Good, it's really not hard, Express makes it easy for testing. I really like testing with Express, it's almost fun, in my opinion.

[00:11:30]
>> Scott Moss: Especially if you have a good authentication system set up like JSON web tokens, it's really fun.