1
1

00:00:01,480  -->  00:00:03,470 line:15% 
<v Jose>Hi guys welcome back.</v>
2

2

00:00:03,470  -->  00:00:07,652
In this video we're going to start working on our web.
3

3

00:00:07,652  -->  00:00:09,930
Now I know this is a web application that we're building.
4

4

00:00:09,930  -->  00:00:12,290
So far we've been doing a lot of the things
5

5

00:00:12,290  -->  00:00:16,080
that we needed to do in order to get it to work.
6

6

00:00:16,080  -->  00:00:18,330
Now we're starting with the interface
7

7

00:00:18,330  -->  00:00:19,830
that the user is going to see.
8

8

00:00:20,850  -->  00:00:23,790
So we're gonna start by creating a template.
9

9

00:00:23,790  -->  00:00:26,340
And by the way, this init py file here
10

10

00:00:26,340  -->  00:00:28,670
in the templates folder is not needed,
11

11

00:00:28,670  -->  00:00:30,237
so I'm going to delete it.
12

12

00:00:30,237  -->  00:00:32,510
And we don't need that because this folder
13

13

00:00:32,510  -->  00:00:34,590
is actually going to hold HTML files.
14

14

00:00:34,590  -->  00:00:36,930
It's not going to have Python files,
15

15

00:00:36,930  -->  00:00:40,640
so we don't need an init py file in there.
16

16

00:00:40,640  -->  00:00:42,079
I'm gonna create an HTML file
17

17

00:00:42,079  -->  00:00:44,413
and I'm gonna call it base.html.
18

18

00:00:45,590  -->  00:00:49,832
And this HTML file will have the information
19

19

00:00:49,832  -->  00:00:53,690
that will be shared across all our pages.
20

20

00:00:53,690  -->  00:00:56,810
So all the things our pages will have,
21

21

00:00:56,810  -->  00:00:58,420
then they're gonna be in this page.
22

22

00:00:58,420  -->  00:00:59,440
And then the other pages
23

23

00:00:59,440  -->  00:01:02,140
are going to sort of inherit from it
24

24

00:01:02,140  -->  00:01:03,430
so that they don't have to have
25

25

00:01:03,430  -->  00:01:05,720
all the duplicate information in them.
26

26

00:01:05,720  -->  00:01:08,394
So what can be duplicate information.
27

27

00:01:08,394  -->  00:01:10,440
The DOCTYPE for example.
28

28

00:01:10,440  -->  00:01:12,350
All our pages are gonna be HTML,
29

29

00:01:12,350  -->  00:01:16,680
so we don't need this DOCTYPE html in all our pages.
30

30

00:01:16,680  -->  00:01:19,150
By the way this DOCTYPE just tells the browser
31

31

00:01:19,150  -->  00:01:22,759
that they're about to look at an HTML file.
32

32

00:01:22,759  -->  00:01:26,180
The html tag will be in all our pages
33

33

00:01:26,180  -->  00:01:28,080
so we don't need that in all the pages,
34

34

00:01:28,080  -->  00:01:30,610
we can just have it on the base page.
35

35

00:01:30,610  -->  00:01:33,720
Similarly in the head, we're gonna have this stuff here.
36

36

00:01:33,720  -->  00:01:35,327
We don't need that in every page.
37

37

00:01:35,327  -->  00:01:38,260
And we can setup title, like something like Price Alerts
38

38

00:01:39,118  -->  00:01:42,606
and that will then be present on every page.
39

39

00:01:42,606  -->  00:01:45,814
We also need body tags in every page.
40

40

00:01:45,814  -->  00:01:50,814
So what is going to be unique to each page.
41

41

00:01:50,840  -->  00:01:53,370
Well inside my body I'm going to create a div
42

42

00:01:53,370  -->  00:01:57,111
and I'm gonna give it a class of content and container.
43

43

00:01:57,111  -->  00:02:01,440
And inside my div I'm going to put Jinja2 block,
44

44

00:02:01,440  -->  00:02:03,653
that I'm gonna call content.
45

45

00:02:05,321  -->  00:02:07,800
This is how you define a Jinja2 block.
46

46

00:02:07,800  -->  00:02:10,247
You use the curly brace, percentage
47

47

00:02:10,247  -->  00:02:12,560
to open up a block.
48

48

00:02:12,560  -->  00:02:14,600
Then you give you block name.
49

49

00:02:14,600  -->  00:02:15,853
I'm calling it content in this case,
50

50

00:02:15,853  -->  00:02:17,940
but you can call it whatever you want.
51

51

00:02:17,940  -->  00:02:20,080
And then at the end you use once again
52

52

00:02:20,080  -->  00:02:23,260
the same notation of curly brace, percentage sign
53

53

00:02:23,260  -->  00:02:26,410
and you put endblock, all one word.
54

54

00:02:26,410  -->  00:02:27,500
Make sure you don't miss any letters
55

55

00:02:27,500  -->  00:02:29,040
or anything like that.
56

56

00:02:29,040  -->  00:02:32,070
This stuff that is inside this block,
57

57

00:02:32,070  -->  00:02:36,330
is something that the children can modify.
58

58

00:02:36,330  -->  00:02:39,843
And we're gonna learn how to add children in here,
59

59

00:02:40,830  -->  00:02:41,663
which is the next part.
60

60

00:02:41,663  -->  00:02:42,756
So now I'm going to,
61

61

00:02:42,756  -->  00:02:43,890
now that I have my base template,
62

62

00:02:43,890  -->  00:02:45,930
we're gonna go and create a new HTML file
63

63

00:02:45,930  -->  00:02:50,190
and I'm gonna call this something like new_item.html.
64

64

00:02:52,760  -->  00:02:55,700
Notice that PyCharm is putting this stuff
65

65

00:02:55,700  -->  00:02:56,880
into the page for me.
66

66

00:02:56,880  -->  00:02:58,160
But I actually don't need it,
67

67

00:02:58,160  -->  00:02:59,460
so I'm going to delete it
68

68

00:02:59,460  -->  00:03:01,580
and then once again using my curly brace,
69

69

00:03:01,580  -->  00:03:02,700
percentage sign notation,
70

70

00:03:02,700  -->  00:03:06,370
I'm gonna say extends and then base.html
71

71

00:03:07,520  -->  00:03:10,200
inside quotation marks, very important.
72

72

00:03:10,200  -->  00:03:13,630
So now this template, when we ask Jinja2
73

73

00:03:13,630  -->  00:03:16,480
to render the template,
74

74

00:03:16,480  -->  00:03:18,340
what Jinja2 is going to do is
75

75

00:03:18,340  -->  00:03:20,950
before sending any information to the user,
76

76

00:03:20,950  -->  00:03:22,380
it's going to take base.hmtl
77

77

00:03:23,230  -->  00:03:27,163
and essentially it's going to copy it into this file.
78

78

00:03:27,163  -->  00:03:31,040
Now how do we modify the content block.
79

79

00:03:31,040  -->  00:03:33,760
Well we do block content,
80

80

00:03:33,760  -->  00:03:36,729
exactly the same way as we did before,
81

81

00:03:36,729  -->  00:03:41,060
but inside this block we can put whatever HTML we want
82

82

00:03:41,060  -->  00:03:45,373
and what will happen is that HTML will then appear in here.
83

83

00:03:46,475  -->  00:03:49,640
So what are we gonna do inside this block?
84

84

00:03:49,640  -->  00:03:52,820
We'll I'm going to add a header tag.
85

85

00:03:52,820  -->  00:03:54,780
And this is gonna say inside
86

86

00:03:54,780  -->  00:03:57,110
an H1 we're gonna put create item.
87

87

00:03:57,110  -->  00:04:01,220
This is just going to be like a heading for the page.
88

88

00:04:01,220  -->  00:04:03,400
And then we're gonna have a section tag
89

89

00:04:03,400  -->  00:04:08,040
which will have a class name of create-item-form
90

90

00:04:08,961  -->  00:04:12,009
and a section tag HTML just defines
91

91

00:04:12,009  -->  00:04:14,470
a different part of the site,
92

92

00:04:14,470  -->  00:04:16,450
something that a screen reader can go to
93

93

00:04:16,450  -->  00:04:18,493
and say okay, this is a specific section the site,
94

94

00:04:18,493  -->  00:04:22,110
a specific part of the site that is more or less independent
95

95

00:04:22,110  -->  00:04:24,480
from everything else and it is self-contained.
96

96

00:04:24,480  -->  00:04:27,883
It contains something in it that we can look at.
97

97

00:04:30,150  -->  00:04:33,450
Inside the section we're gonna put our form.
98

98

00:04:33,450  -->  00:04:35,590
And this form is what we're going to use
99

99

00:04:35,590  -->  00:04:39,490
to send data to our view,
100

100

00:04:39,490  -->  00:04:41,503
which we haven't coded yet, but we will.
101

101

00:04:42,370  -->  00:04:45,000
So what sort of stuff can go in a form?
102

102

00:04:45,000  -->  00:04:47,870
Well we can put things like text fields,
103

103

00:04:47,870  -->  00:04:50,530
we can put text areas, we can put check boxes,
104

104

00:04:50,530  -->  00:04:53,360
we can put drop downs, we can put anything we want
105

105

00:04:53,360  -->  00:04:56,613
and all of that is part of the HTML standard.
106

106

00:04:57,760  -->  00:04:59,640
Now as we're defining forms,
107

107

00:04:59,640  -->  00:05:03,000
we're also going to be looking at Bootstrap.
108

108

00:05:03,000  -->  00:05:06,760
Bootstrap is a set of styles that we can use
109

109

00:05:06,760  -->  00:05:09,560
to make our websites look a bit nicer
110

110

00:05:09,560  -->  00:05:12,400
without us having to do a lot of the work.
111

111

00:05:12,400  -->  00:05:13,960
So if we wanna look at Bootstrap
112

112

00:05:13,960  -->  00:05:15,790
we can do that in the next video.
113

113

00:05:15,790  -->  00:05:20,790
For now we're gonna stick to good ol' non-styled forms.
114

114

00:05:20,810  -->  00:05:22,850
They're not gonna look very pretty.
115

115

00:05:22,850  -->  00:05:24,940
But we're gonna put a div
116

116

00:05:24,940  -->  00:05:27,432
and inside the div we're gonna put a label.
117

117

00:05:27,432  -->  00:05:30,680
We're gonna say for which field this label is.
118

118

00:05:30,680  -->  00:05:35,090
I'm gonna say this label is for a url field,
119

119

00:05:35,090  -->  00:05:37,130
and inside we're gonna put URL
120

120

00:05:37,130  -->  00:05:40,360
and then we're gonna put an input of type text.
121

121

00:05:40,360  -->  00:05:42,138
This is a text field.
122

122

00:05:42,138  -->  00:05:46,100
The ID is gonna be url and more importantly than anything
123

123

00:05:46,100  -->  00:05:48,360
the name is going to be url.
124

124

00:05:48,360  -->  00:05:49,850
So why do we use labels?
125

125

00:05:49,850  -->  00:05:53,790
Why not just put the URL text like that?
126

126

00:05:53,790  -->  00:05:55,461
It would work more or less the same way,
127

127

00:05:55,461  -->  00:05:58,960
but again it is for the purposes of accessibility.
128

128

00:05:58,960  -->  00:06:01,030
Once you have a field,
129

129

00:06:01,030  -->  00:06:04,390
the accessibility reader can then go
130

130

00:06:04,390  -->  00:06:07,290
and find what label is assigned to that field
131

131

00:06:07,290  -->  00:06:10,853
so that it can more easily describe what the field is.
132

132

00:06:11,940  -->  00:06:14,330
And then we're gonna add a placeholder text,
133

133

00:06:14,330  -->  00:06:17,643
which is gonna be https://...
134

134

00:06:19,390  -->  00:06:22,220
And then we're gonna add a self closing tag at the end,
135

135

00:06:22,220  -->  00:06:25,680
because the input tag does not need a closing tag.
136

136

00:06:25,680  -->  00:06:27,480
As you can see, all of these other tags,
137

137

00:06:27,480  -->  00:06:29,010
have a closing tag at the end,
138

138

00:06:29,010  -->  00:06:31,881
but because we don't have anything inside the input,
139

139

00:06:31,881  -->  00:06:33,810
then it is self-closing.
140

140

00:06:33,810  -->  00:06:36,710
It just needs a forwards slash, crocodile clip at the end.
141

141

00:06:38,289  -->  00:06:40,300
And now we have our first
142

142

00:06:40,300  -->  00:06:42,190
sort of input group if you wish,
143

143

00:06:42,190  -->  00:06:44,940
a label and input combo.
144

144

00:06:44,940  -->  00:06:46,850
Now that we've got this, we're gonna try it out,
145

145

00:06:46,850  -->  00:06:49,220
make sure that it is displaying on our site.
146

146

00:06:49,220  -->  00:06:51,800
We do have to go over to app.py
147

147

00:06:51,800  -->  00:06:54,460
and make sure that we run our app.
148

148

00:06:54,460  -->  00:06:56,808
So we're going to delete everything that's in here
149

149

00:06:56,808  -->  00:07:01,098
and define a simple flask app.
150

150

00:07:01,098  -->  00:07:05,240
A simple flask app just needs to import flask
151

151

00:07:05,240  -->  00:07:08,793
and it's gonna define an app name here.
152

152

00:07:13,350  -->  00:07:15,800
And then we're going to define a simple route
153

153

00:07:15,800  -->  00:07:19,560
which will render this new item template.
154

154

00:07:19,560  -->  00:07:22,080
So we're gonna say something like new item
155

155

00:07:22,971  -->  00:07:25,700
and it's gonna return render_template of new_item.html.
156

156

00:07:27,870  -->  00:07:31,673
You do have import render template in there.
157

157

00:07:32,840  -->  00:07:35,520
And Python likes the two lines there.
158

158

00:07:35,520  -->  00:07:40,520
And finally if dot dot name equal main,
159

159

00:07:41,620  -->  00:07:43,070
then we're gonna do app.run.
160

160

00:07:43,070  -->  00:07:44,550
And very importantly we're gonna add
161

161

00:07:44,550  -->  00:07:46,430
debug equal True down there.
162

162

00:07:46,430  -->  00:07:47,510
And the reason for that is
163

163

00:07:47,510  -->  00:07:50,310
in case we have any problem in our templates
164

164

00:07:50,310  -->  00:07:52,330
or in our code debug equal True
165

165

00:07:52,330  -->  00:07:54,470
is going to give us a bit more information
166

166

00:07:54,470  -->  00:07:56,570
when a problem does happen.
167

167

00:07:56,570  -->  00:08:01,560
So it's good to put there until we put this app out
168

168

00:08:01,560  -->  00:08:02,400
to our users.
169

169

00:08:02,400  -->  00:08:05,183
Once our users have the app we wanna remove that.
170

170

00:08:06,050  -->  00:08:10,070
All right, let's run it and see what happens.
171

171

00:08:10,070  -->  00:08:13,030
So I brought the app here on the right
172

172

00:08:13,030  -->  00:08:14,330
and everything was quite big.
173

173

00:08:14,330  -->  00:08:17,160
Again, we are zoomed in to 175%,
174

174

00:08:17,160  -->  00:08:19,410
so this is much bigger than it would normally be.
175

175

00:08:19,410  -->  00:08:22,280
But you can see that we have our form.
176

176

00:08:22,280  -->  00:08:23,620
It doesn't look very nice.
177

177

00:08:23,620  -->  00:08:25,660
I'll agree with you on that one.
178

178

00:08:25,660  -->  00:08:29,290
We're going to just make this like that.
179

179

00:08:29,290  -->  00:08:30,390
It doesn't look very nice because
180

180

00:08:30,390  -->  00:08:31,860
we don't have any styling on it.
181

181

00:08:31,860  -->  00:08:34,633
But for this video we're just going to focus on
182

182

00:08:34,633  -->  00:08:39,633
creating the inputs and not on making them look pretty.
183

183

00:08:40,150  -->  00:08:44,680
This form is going to be used to create new items.
184

184

00:08:44,680  -->  00:08:48,350
What else does an item need in order to be created?
185

185

00:08:48,350  -->  00:08:51,570
As well as the URL we need a tag name,
186

186

00:08:51,570  -->  00:08:53,360
and we need the query that we're gonna use
187

187

00:08:53,360  -->  00:08:56,720
to find the item on the page.
188

188

00:08:56,720  -->  00:08:58,810
We don't need and _id, because that's gonna be
189

189

00:08:58,810  -->  00:09:01,680
generated for us when we create new item object.
190

190

00:09:01,680  -->  00:09:03,553
So we just need tag name and query.
191

191

00:09:04,580  -->  00:09:06,623
The two other input groups we're gonna create
192

192

00:09:06,623  -->  00:09:10,120
will be for those two other properties that we need.
193

193

00:09:10,120  -->  00:09:12,040
So I'm just gonna copy and paste in here
194

194

00:09:12,040  -->  00:09:15,760
and now we're gonna change what's in each of these divs.
195

195

00:09:15,760  -->  00:09:17,913
The first one is gonna be the label.
196

196

00:09:17,913  -->  00:09:20,880
This one is gonna be for tag name
197

197

00:09:20,880  -->  00:09:22,883
and it's gonna say tag name.
198

198

00:09:25,250  -->  00:09:28,620
And this has to change to tag name.
199

199

00:09:28,620  -->  00:09:31,313
And this one here is gonna be for the query.
200

200

00:09:34,590  -->  00:09:36,890
The placeholders also have to change,
201

201

00:09:36,890  -->  00:09:39,520
so we are going to have a placeholder of
202

202

00:09:39,520  -->  00:09:41,070
span for the tag name
203

203

00:09:41,070  -->  00:09:43,451
and for the query we're going to have a placeholder
204

204

00:09:43,451  -->  00:09:45,460
which is gonna be slightly different,
205

205

00:09:45,460  -->  00:09:50,370
it's gonna be id is something, like that.
206

206

00:09:50,370  -->  00:09:51,640
Now notice that for the placeholder,
207

207

00:09:51,640  -->  00:09:55,350
I'm using single quotation marks around the text
208

208

00:09:55,350  -->  00:09:57,390
and that's because the query contents
209

209

00:09:57,390  -->  00:09:59,475
whatever that the user is going to give us
210

210

00:09:59,475  -->  00:10:03,719
is going to have to use double quotation marks.
211

211

00:10:03,719  -->  00:10:06,542
That's because we are going to turn
212

212

00:10:06,542  -->  00:10:08,480
what the user gives us,
213

213

00:10:08,480  -->  00:10:11,540
this sort dictionary like thing,
214

214

00:10:11,540  -->  00:10:15,050
we're gonna turn that into a proper Python dictionary
215

215

00:10:15,050  -->  00:10:17,134
that we can use in our item.
216

216

00:10:17,134  -->  00:10:20,930
In order to do that, we need to treat the text
217

217

00:10:20,930  -->  00:10:23,610
that the user sends us as JSON,
218

218

00:10:23,610  -->  00:10:26,500
as JavaScript Object Notation.
219

219

00:10:26,500  -->  00:10:30,340
And JSON text needs double quotation marks.
220

220

00:10:30,340  -->  00:10:32,430
So that's why we are putting the placeholder
221

221

00:10:32,430  -->  00:10:34,808
using the single quotation marks around the next
222

222

00:10:34,808  -->  00:10:36,540
and the double quotation marks
223

223

00:10:36,540  -->  00:10:40,863
as the strings that are within the JSON text.
224

224

00:10:42,280  -->  00:10:43,113
Don't worry too much about it.
225

225

00:10:43,113  -->  00:10:46,003
I'll show you later what happens if you don't do that.
226

226

00:10:47,310  -->  00:10:49,240
Now for each of these inputs,
227

227

00:10:49,240  -->  00:10:51,240
we're also gonna add a little bit of help text,
228

228

00:10:51,240  -->  00:10:53,750
just to tell users a bit more information
229

229

00:10:53,750  -->  00:10:56,350
about what they should be writing.
230

230

00:10:56,350  -->  00:10:57,510
And how we're gonna do that
231

231

00:10:57,510  -->  00:11:01,430
is we're gonna add a new property area, describedby,
232

232

00:11:01,430  -->  00:11:03,420
to each of these inputs.
233

233

00:11:03,420  -->  00:11:05,920
And then we're going to give it
234

234

00:11:05,920  -->  00:11:09,560
the id of the help text essentially.
235

235

00:11:09,560  -->  00:11:11,433
And that's gonna be tag name help.
236

236

00:11:12,378  -->  00:11:14,120
And then at the bottom,
237

237

00:11:14,120  -->  00:11:15,260
underneath this input text,
238

238

00:11:15,260  -->  00:11:19,080
we're gonna add a small bit of text using the small tag.
239

239

00:11:19,080  -->  00:11:21,898
We're gonna give it the id of tag name help
240

240

00:11:21,898  -->  00:11:24,730
and we're going to describe here
241

241

00:11:24,730  -->  00:11:26,793
what we expect the user to enter.
242

242

00:11:32,860  -->  00:11:33,693
So I'm just gonna make this
243

243

00:11:33,693  -->  00:11:36,343
a little bit bigger there for us.
244

244

00:11:37,780  -->  00:11:40,240
And that contains, what is the HTML tag
245

245

00:11:40,240  -->  00:11:43,130
of the item that contains the item price?
246

246

00:11:43,130  -->  00:11:47,233
Just for users to understand a bit better what we want.
247

247

00:11:48,200  -->  00:11:52,863
And here in the query, we're also going to add a query help.
248

248

00:11:56,500  -->  00:11:58,930
So this tells users that they are gonna have to enter
249

249

00:11:58,930  -->  00:12:00,447
a JSON string in here.
250

250

00:12:00,447  -->  00:12:03,020
And remember that is a string that looks
251

251

00:12:03,020  -->  00:12:04,780
exactly like a Python dictionary,
252

252

00:12:04,780  -->  00:12:08,453
but must use double quotation marks inside it.
253

253

00:12:09,300  -->  00:12:13,403
And we're gonna ask users to enter that into the field.
254

254

00:12:15,440  -->  00:12:16,850
All right, so now that we have that,
255

255

00:12:16,850  -->  00:12:18,750
we can go and refresh this.
256

256

00:12:18,750  -->  00:12:21,400
And you can see that we've got our form in here.
257

257

00:12:21,400  -->  00:12:24,620
If the form does not reappear, just restart your app,
258

258

00:12:24,620  -->  00:12:27,313
as that can sometimes happen in flask as well.
259

259

00:12:29,010  -->  00:12:32,303
So you've got the three fields with three placeholders.
260

260

00:12:33,260  -->  00:12:36,690
And we are missing the most important part of any form,
261

261

00:12:36,690  -->  00:12:38,430
which is the button.
262

262

00:12:38,430  -->  00:12:39,970
Let's go and under the last div
263

263

00:12:39,970  -->  00:12:43,173
we're gonna add a button of type submit.
264

264

00:12:44,171  -->  00:12:46,813
And we're gonna say something like create.
265

265

00:12:47,750  -->  00:12:49,080
There we go.
266

266

00:12:49,080  -->  00:12:50,803
Now we have our button.
267

267

00:12:51,700  -->  00:12:55,930
Finally we need a way to receive the information
268

268

00:12:55,930  -->  00:12:59,000
in these three fields in our app.
269

269

00:12:59,000  -->  00:13:03,360
And for that we're going to need to go into app.py
270

270

00:13:03,360  -->  00:13:07,005
and define an endpoint that will receive the data
271

271

00:13:07,005  -->  00:13:09,920
and do something with it.
272

272

00:13:09,920  -->  00:13:12,670
So what we're gonna say is that in this route,
273

273

00:13:12,670  -->  00:13:17,670
we can access with either a get or a post.
274

274

00:13:20,120  -->  00:13:22,700
Now a browser makes a get request
275

275

00:13:22,700  -->  00:13:24,110
when they access an endpoint.
276

276

00:13:24,110  -->  00:13:26,990
So at the moment, when we access the default endpoint
277

277

00:13:26,990  -->  00:13:29,970
in our application, our browser is making a get request
278

278

00:13:29,970  -->  00:13:32,800
and this endpoint is responding to it,
279

279

00:13:32,800  -->  00:13:35,900
with the HTML that's already been rendered.
280

280

00:13:35,900  -->  00:13:37,030
We're gonna tell this endpoint
281

281

00:13:37,030  -->  00:13:39,430
that if we receive a post request,
282

282

00:13:39,430  -->  00:13:41,261
which is what the form is gonna make,
283

283

00:13:41,261  -->  00:13:45,293
to take the data in the form fields and process it.
284

284

00:13:46,150  -->  00:13:50,150
So we'd say if request.method equal post,
285

285

00:13:50,150  -->  00:13:53,970
we need to import request from the flask package by the way.
286

286

00:13:53,970  -->  00:13:57,383
Then we're going to process the data.
287

287

00:13:58,402  -->  00:14:02,440
And if not, if this doesn't happen,
288

288

00:14:02,440  -->  00:14:04,090
then we're going to return the
289

289

00:14:04,090  -->  00:14:06,313
render_template of new_item.html.
290

290

00:14:07,600  -->  00:14:09,750
So how do we process the data?
291

291

00:14:09,750  -->  00:14:11,140
We're gonna take the URL
292

292

00:14:11,140  -->  00:14:14,520
and we're gonna say request.form url.
293

293

00:14:14,520  -->  00:14:17,920
And what this is doing is it's accessing the URL field
294

294

00:14:17,920  -->  00:14:21,605
in the form data that's come in the request.
295

295

00:14:21,605  -->  00:14:24,460
We're going to include the form data
296

296

00:14:24,460  -->  00:14:28,030
because this a form and HTML will do that for us.
297

297

00:14:28,030  -->  00:14:30,338
As soon as we press submit on a form,
298

298

00:14:30,338  -->  00:14:33,459
if there is a form tag around the button,
299

299

00:14:33,459  -->  00:14:37,277
that button will create a new request
300

300

00:14:37,277  -->  00:14:40,720
that will include the data in all the fields of the form
301

301

00:14:40,720  -->  00:14:43,033
and it will send it over to where we say.
302

302

00:14:44,040  -->  00:14:45,000
And we haven't specified
303

303

00:14:45,000  -->  00:14:47,660
where it's gonna send it over just yet.
304

304

00:14:47,660  -->  00:14:49,870
Then we're gonna say the tag name and it's also gonna be
305

305

00:14:49,870  -->  00:14:52,610
request for tag name.
306

306

00:14:52,610  -->  00:14:57,233
And finally the query which is gonna be request.form query.
307

307

00:14:58,546  -->  00:15:02,990
Finally we're gonna say item url tag_name query
308

308

00:15:04,550  -->  00:15:07,030
and we're gonna save_to_mongo.
309

309

00:15:07,030  -->  00:15:09,480
We do have to import item of course
310

310

00:15:09,480  -->  00:15:12,920
from models item import item.
311

311

00:15:12,920  -->  00:15:13,793
There we go.
312

312

00:15:15,330  -->  00:15:18,450
All right, so we have our three things.
313

313

00:15:18,450  -->  00:15:20,370
We have the URL, we have the tag name
314

314

00:15:20,370  -->  00:15:22,691
and we have the query.
315

315

00:15:22,691  -->  00:15:25,463
After we've saved the item to MongoDB,
316

316

00:15:26,570  -->  00:15:28,350
we're just gonna return the render template
317

317

00:15:28,350  -->  00:15:31,120
in case the user wants to create another item.
318

318

00:15:31,120  -->  00:15:33,460
Optionally we could return a different template
319

319

00:15:33,460  -->  00:15:35,680
after we create the item,
320

320

00:15:35,680  -->  00:15:38,440
so that if it is a post request,
321

321

00:15:38,440  -->  00:15:40,000
we can for example render a template
322

322

00:15:40,000  -->  00:15:41,840
that says thank you for creating the item
323

323

00:15:41,840  -->  00:15:43,190
or something like that.
324

324

00:15:43,190  -->  00:15:44,310
It's totally up to us,
325

325

00:15:44,310  -->  00:15:46,800
but for now if the request method is post,
326

326

00:15:46,800  -->  00:15:48,319
we're gonna do all this.
327

327

00:15:48,319  -->  00:15:49,980
And then of course we're gonna do this
328

328

00:15:49,980  -->  00:15:53,590
because it's not in the if statement, it's outside of it.
329

329

00:15:53,590  -->  00:15:56,460
If the request method is not post,
330

330

00:15:56,460  -->  00:15:57,990
then we're just gonna jump straight here
331

331

00:15:57,990  -->  00:16:00,023
and we're gonna render the template as well.
332

332

00:16:01,540  -->  00:16:03,360
All right, now the next thing to do
333

333

00:16:03,360  -->  00:16:06,330
is to go back to our new_item.html
334

334

00:16:06,330  -->  00:16:11,330
and we have to say that the form method is gonna be post.
335

335

00:16:12,040  -->  00:16:17,040
By default forms use get just like the browser does.
336

336

00:16:17,410  -->  00:16:20,393
But we wanna tell this form to use post instead.
337

337

00:16:21,490  -->  00:16:24,830
The second thing we can define is the action.
338

338

00:16:24,830  -->  00:16:27,850
And in this case we could define the action to be
339

339

00:16:27,850  -->  00:16:30,920
this end point, the forward slash endpoint.
340

340

00:16:30,920  -->  00:16:33,230
That is the endpoint that is currently accepting
341

341

00:16:33,230  -->  00:16:36,460
the data from the form and it's gonna process it.
342

342

00:16:36,460  -->  00:16:39,054
However, this is a special case,
343

343

00:16:39,054  -->  00:16:44,054
because this form is being presented to the user
344

344

00:16:44,580  -->  00:16:45,950
on this endpoint.
345

345

00:16:45,950  -->  00:16:48,900
Notice that this is a default endpoint for the page.
346

346

00:16:48,900  -->  00:16:51,733
Because the form is going to send the data
347

347

00:16:51,733  -->  00:16:55,014
to the same endpoint that its currently in,
348

348

00:16:55,014  -->  00:16:58,810
we actually don't need action, that is the default.
349

349

00:16:58,810  -->  00:17:01,377
So if the form is sending data to the same endpoint we're in
350

350

00:17:01,377  -->  00:17:03,720
we don't need to define an action,
351

351

00:17:03,720  -->  00:17:04,610
because that's the default.
352

352

00:17:04,610  -->  00:17:06,730
It will by default send it to the same endpoint
353

353

00:17:06,730  -->  00:17:07,980
that you're currently in.
354

354

00:17:09,210  -->  00:17:11,573
All right, let's refresh this.
355

355

00:17:12,640  -->  00:17:16,160
And at this point if you are not running in debug mode,
356

356

00:17:16,160  -->  00:17:18,580
you will most likely have to restart you app,
357

357

00:17:18,580  -->  00:17:20,100
just because we've changed the code here.
358

358

00:17:20,100  -->  00:17:22,000
So just do that if you have to.
359

359

00:17:22,000  -->  00:17:24,610
And if it's restarted for you like it has here,
360

360

00:17:24,610  -->  00:17:27,253
then you don't need to restart your app manually.
361

361

00:17:28,140  -->  00:17:32,090
Now we can go ahead and define the URL.
362

362

00:17:32,090  -->  00:17:35,550
We can say for example https://johnlewis.com.
363

363

00:17:35,550  -->  00:17:37,950
I know this is an incorrect URL.
364

364

00:17:37,950  -->  00:17:42,910
And the span and then we're gonna say id is price.
365

365

00:17:42,910  -->  00:17:44,790
This all incorrect by the way, it won't work,
366

366

00:17:44,790  -->  00:17:47,790
but we can delete it from the database in a moment.
367

367

00:17:47,790  -->  00:17:49,550
And there we have it.
368

368

00:17:49,550  -->  00:17:51,240
The page gets refreshed.
369

369

00:17:51,240  -->  00:17:52,720
Nothing on the fields anymore,
370

370

00:17:52,720  -->  00:17:55,550
because we've gone and we've re-rendered the template
371

371

00:17:55,550  -->  00:17:57,210
after saving to MongoDB.
372

372

00:17:57,210  -->  00:17:59,097
We don't have any errors.
373

373

00:17:59,097  -->  00:18:02,640
We can see that the post request that we made
374

374

00:18:02,640  -->  00:18:04,420
using the form succeeded.
375

375

00:18:04,420  -->  00:18:07,513
It was a code 200, which means okay.
376

376

00:18:08,720  -->  00:18:10,500
And that's it.
377

377

00:18:10,500  -->  00:18:13,900
Our item is saved into MongoDB.
378

378

00:18:13,900  -->  00:18:17,120
Now what we can do is we can go into MongoDB
379

379

00:18:17,120  -->  00:18:19,300
and have a look at the item.
380

380

00:18:19,300  -->  00:18:23,070
So make sure to open your terminal, go to MongoDB,
381

381

00:18:23,070  -->  00:18:27,363
the same database that you've got there.
382

382

00:18:30,450  -->  00:18:33,470
And now you'll see what the problem is
383

383

00:18:33,470  -->  00:18:36,750
with some of the things we've got there.
384

384

00:18:36,750  -->  00:18:39,530
So first of all, the item was created for us,
385

385

00:18:39,530  -->  00:18:40,363
which is good.
386

386

00:18:40,363  -->  00:18:42,900
It was given an id, which is excellent.
387

387

00:18:42,900  -->  00:18:46,880
The URL seems like a string, just like these are.
388

388

00:18:46,880  -->  00:18:49,050
Not really a valid item in this website,
389

389

00:18:49,050  -->  00:18:50,130
but that's beside the point,
390

390

00:18:50,130  -->  00:18:51,840
we have managed to create it
391

391

00:18:51,840  -->  00:18:54,400
and we've created the tag name as well.
392

392

00:18:54,400  -->  00:18:57,350
But look at the query how different it looks.
393

393

00:18:57,350  -->  00:18:59,400
The query for this item here
394

394

00:18:59,400  -->  00:19:01,773
than the query for this item there.
395

395

00:19:02,670  -->  00:19:06,160
The difference is that this query, when we saved it,
396

396

00:19:06,160  -->  00:19:08,960
we saved a Python dictionary.
397

397

00:19:08,960  -->  00:19:12,500
And PyMongo is able to take that dictionary
398

398

00:19:12,500  -->  00:19:17,250
and save it as a valid object into MongoDB,
399

399

00:19:17,250  -->  00:19:18,670
a valid document.
400

400

00:19:18,670  -->  00:19:21,990
But this query here was a string
401

401

00:19:21,990  -->  00:19:25,130
because this field gives back a string
402

402

00:19:25,130  -->  00:19:29,690
and all we did our app.py is we took that string,
403

403

00:19:29,690  -->  00:19:32,853
we put it item and then we saved it to MongoDB.
404

404

00:19:33,711  -->  00:19:36,510
Notice that the item init
405

405

00:19:37,830  -->  00:19:40,020
expects query to be dictionary
406

406

00:19:40,880  -->  00:19:43,970
and here we've passed a string.
407

407

00:19:43,970  -->  00:19:47,223
So this is not really what we wanted to begin with.
408

408

00:19:48,440  -->  00:19:50,525
What we wanna do is we wanna turn this string
409

409

00:19:50,525  -->  00:19:52,570
into a dictionary.
410

410

00:19:52,570  -->  00:19:55,923
And we're gonna do that with json.loads.
411

411

00:19:57,490  -->  00:20:01,180
So we're gonna import the JSON module.
412

412

00:20:01,180  -->  00:20:03,350
Type import json at the top.
413

413

00:20:03,350  -->  00:20:06,939
And json.loads takes in string,
414

414

00:20:06,939  -->  00:20:09,330
that's what the s stands for,
415

415

00:20:09,330  -->  00:20:13,863
and loads it, turning it into Python dictionary.
416

416

00:20:14,740  -->  00:20:17,910
This string must be valid JSON
417

417

00:20:19,000  -->  00:20:22,630
in order for json.loads to be able to read it
418

418

00:20:22,630  -->  00:20:24,130
and turn it into a dictionary.
419

419

00:20:25,010  -->  00:20:30,010
That is why we need the quotation marks inside the string.
420

420

00:20:30,290  -->  00:20:31,750
Because if it doesn't have quotation marks,
421

421

00:20:31,750  -->  00:20:32,993
it's not valid JSON.
422

422

00:20:34,280  -->  00:20:35,720
Now restart your app,
423

423

00:20:35,720  -->  00:20:38,053
and we're gonna type another one.
424

424

00:20:40,810  -->  00:20:44,750
And now we're going to do id is price,
425

425

00:20:44,750  -->  00:20:46,420
same as we did before.
426

426

00:20:46,420  -->  00:20:47,800
We're gonna create a new one.
427

427

00:20:47,800  -->  00:20:50,543
Instantly you know what happens
428

428

00:20:50,543  -->  00:20:55,238
and if we go back to MongoDB in our terminal,
429

429

00:20:55,238  -->  00:20:59,960
I'm gonna, clear doesn't work in MongoDB of course.
430

430

00:20:59,960  -->  00:21:01,320
We're gonna find there
431

431

00:21:01,320  -->  00:21:03,010
and now you can see that the latest item
432

432

00:21:03,010  -->  00:21:07,503
that we inserted has a valid query that is no longer
433

433

00:21:07,503  -->  00:21:12,233
this single string, it is now a full object in MongoDB.
434

434

00:21:13,660  -->  00:21:14,513
Another trial.
435

435

00:21:15,370  -->  00:21:20,343
What happens if we use single quotation marks?
436

436

00:21:23,170  -->  00:21:28,170
Well you get one big error: json.decoder.JSONDecodeError.
437

437

00:21:29,850  -->  00:21:32,010
What happens here is,
438

438

00:21:32,010  -->  00:21:35,870
there was an error understanding that JSON text
439

439

00:21:35,870  -->  00:21:38,156
that we're trying to convert into a Python dictionary
440

440

00:21:38,156  -->  00:21:41,913
and that's what we were doing here, json.loads.
441

441

00:21:42,830  -->  00:21:44,100
And the error is pretty nice,
442

442

00:21:44,100  -->  00:21:45,617
and it tells you, "Expecting property name
443

443

00:21:45,617  -->  00:21:47,260
"enclosed in double quotes".
444

444

00:21:47,260  -->  00:21:50,263
But we used single quotes and it doesn't like that.
445

445

00:21:51,100  -->  00:21:54,071
So that is why we need the double quotation marks
446

446

00:21:54,071  -->  00:21:56,870
and not the single quotation marks.
447

447

00:21:56,870  -->  00:21:58,393
If we refresh the page,
448

448

00:22:00,272  -->  00:22:03,350
Chrome will automatically try to resend the form,
449

449

00:22:03,350  -->  00:22:05,640
which gives us the same error.
450

450

00:22:05,640  -->  00:22:07,120
Of course essentially what we've done
451

451

00:22:07,120  -->  00:22:09,690
is we've just sent the same faulty data again.
452

452

00:22:09,690  -->  00:22:11,784
So what you have to do is you have to go up here
453

453

00:22:11,784  -->  00:22:16,100
and press enter again in order for the page to be loaded
454

454

00:22:16,100  -->  00:22:21,100
using a get request again and not resending the form.
455

455

00:22:21,380  -->  00:22:23,380
So that, just make sure you keep that in mind
456

456

00:22:23,380  -->  00:22:24,980
when you're loading these pages.
457

457

00:22:26,576  -->  00:22:30,900
All right, we are now able to create items
458

458

00:22:30,900  -->  00:22:32,691
using this web interface.
459

459

00:22:32,691  -->  00:22:34,190
Over the next few videos,
460

460

00:22:34,190  -->  00:22:36,170
we're going to be looking at some styling.
461

461

00:22:36,170  -->  00:22:39,716
We're also going to be splitting this into a blueprint
462

462

00:22:39,716  -->  00:22:43,420
and we're going to be making it just a little bit nicer.
463

463

00:22:43,420  -->  00:22:45,090
We're gonna be able to look at
464

464

00:22:45,090  -->  00:22:46,210
all the items that we've got
465

465

00:22:46,210  -->  00:22:49,000
currently saved in the database and so on.
466

466

00:22:49,000  -->  00:22:51,550
And of course over the whole application
467

467

00:22:51,550  -->  00:22:53,853
we will be able to delete items and so on.
468

468

00:22:55,370  -->  00:22:56,900
Thanks for joining me in this video.
469

469

00:22:56,900  -->  00:22:58,140
Hope you've learned something
470

470

00:22:58,140  -->  00:23:00,257
and I'll see you on the next one.
