Building data-driven web apps with Flask and SQLAlchemy Transcripts
Chapter: Testing web apps
Lecture: Concept Testing view methods
0:00 Now let's move up one level
0:01 in the amount that we're testing at once
0:03 and the part of the application that we're testing.
0:06 'Cause we're using view models
0:07 we can basically assume
0:09 that all the validation is working just fine
0:11 and the data exchange is working fine
0:13 as long as we test that
0:14 but what we do need to test
0:16 is that the view method
0:18 is working with the view model's response correctly.
0:21 If an error comes back
0:22 that it actually shows the page with an error
0:25 rather than just ignores it
0:26 or that if it uses that data
0:28 to try to create our user
0:30 if that user can't be created
0:31 it still shows the error
0:33 instead of just redirecting you.
0:34 Things like that.
0:35 So, that's the layer we just tested
0:36 and we're going to review right now.
0:38 So, we're going to test the home page
0:40 and we're just going to ignore the database aspect
0:42 for just a moment.
0:43 We'll see a more realistic one in a second.
0:44 So, let's imagine that we don't need
0:46 to talk to the database
0:47 we're going to come in here
0:48 we're going to import the index view method from home views
0:52 and we're going to create a context manager
0:54 that is a test request just to slash.
0:57 Then we're going to do act
0:58 which is simply to call the function
1:01 and capture the response
1:02 so what we get back from these Flask methods
1:04 is always a response
1:06 and then we want to do some kind of assert
1:07 like that the status code is 200
1:09 and that the model contains packages
1:12 and that the length
1:13 because that's a list, the length of it
1:14 is greater than zero.
1:16 Right, that part actually probably came from the database
1:18 so keeping it simple right now.
1:20 But this is a totally reasonable test
1:23 that we might write for the index home page.
1:26 One quick side note that model
1:27 on the response, that is set by the @response decorator
1:32 that I created for this course
1:33 where you automatically have it pick up the view template.
1:37 If you don't do that
1:38 you have to find another day to capture that data.
1:40 You can look in the decorator, see how it's done there
1:43 and so on, all right?
1:44 So, we have this and it looks like it's working.
1:47 It does work just fine
1:49 but if we want a more realistic version
1:51 well, we need more space
1:53 because this time we don't want to talk to the database
1:55 and we're going to talk to a fairly complicated function.
1:58 We haven't seen this test written yet
1:59 so imagine we want to test
2:01 if we go to our package details page.
2:04 I want to go to like /project/sqlalchemy
2:08 and see what comes back
2:09 but actually not talk to the database.
2:11 Come over here, we're going to import project
2:15 the method project from the package views
2:17 and we're going to import the Package object itself
2:20 because we're going to have to create some test data
2:22 that we can then mock out
2:24 so the project view gets that from the mocked method calls.
2:29 Then we're going to create our test package
2:30 I'm going to set the id to sqlalchemy
2:33 we're going to give it a couple of releases.
2:36 The reason we want a beta release is because the
2:40 basically that package method assumes
2:43 that there are releases.
2:44 And then we'll going to mock a bunch of stuff out
2:47 we're going to say if you call package
2:49 package_service.get_package_by_id, you get this test SQLAlchemy package.
2:52 If you all releases for package
2:55 you get the releases that we set here
2:57 and the context is going to be set to /project/sqlalchemy.
3:03 The next thing to do is act.
3:04 We're going to call our project function
3:07 and remember, in Flask, it takes the argument
3:10 right, it's up to the Flask infrastructure
3:12 to pass that along
3:13 but we're calling it directly
3:14 so it's now our job to pass that along
3:17 and internally, that's going to be calling get package by ID
3:20 form package service and all the other stuff that happens inside.
3:23 That's why we had to mock it up.
3:25 And then we can just assert.
3:26 I say the web package, the one that we got back
3:29 inside the model
3:30 we're going to capture it
3:31 and I'm going to ask some questions.
3:33 Is the package.id actually sqlalchemy
3:35 and does it actually have two releases?
3:37 So, like this, we can do legitimate tests
3:40 against complex methods
3:42 that interact with the database
3:44 and inbound arguments, all that kind of stuff.