1
00:00:02,140 --> 00:00:04,600
Now sending back data is one thing,

2
00:00:04,660 --> 00:00:07,960
typically you also want to be able to receive data.

3
00:00:08,170 --> 00:00:10,970
Now for that we need to send back different HTML code,

4
00:00:10,990 --> 00:00:18,810
we need to send back HTML code which includes something that allows the user to send us a request.

5
00:00:18,820 --> 00:00:24,160
Now with that I'm not talking about a script where we used the fetch API, we could do that but would be

6
00:00:24,160 --> 00:00:25,820
a lot of code we have to write here,

7
00:00:25,930 --> 00:00:28,820
we can instead start simple and sent back a form.

8
00:00:28,840 --> 00:00:34,720
You might remember that a form had this default behavior that when a button was pressed, we actually

9
00:00:34,720 --> 00:00:40,030
had the browser default of a request being sent to the server that served the page and we had to prevent

10
00:00:40,060 --> 00:00:41,890
this with Javascript.

11
00:00:41,890 --> 00:00:43,850
Now here, I don't want to prevent it,

12
00:00:43,870 --> 00:00:49,120
I want to have this default behavior so that the request is sent to the server because that's simply

13
00:00:49,120 --> 00:00:54,760
another way of building web applications. Instead of having client side Javascript do more of the work,

14
00:00:54,850 --> 00:01:00,310
we could take the more traditional approach with less client side Javascript because we maybe don't

15
00:01:00,310 --> 00:01:05,470
need it here, we don't want to validate the user input here on the client side and instead we let the

16
00:01:05,470 --> 00:01:11,230
browser do its default thing and send the request to the server so that on the server we then validate

17
00:01:11,230 --> 00:01:17,420
the input and so on, both is possible and of course both can also be connected as you will see later. So

18
00:01:17,420 --> 00:01:23,210
here we could render a simple form with an input of type text, like this and with a button in there

19
00:01:23,450 --> 00:01:29,570
and make sure you get these opening and closing tags right. Now in this button here, we could have a send

20
00:01:29,570 --> 00:01:33,950
text and the type of the button, and that's important, should be of type submit.

21
00:01:34,670 --> 00:01:36,170
So now here I have a form element,

22
00:01:36,170 --> 00:01:37,490
then we have an input element,

23
00:01:37,580 --> 00:01:43,700
then we have a button and then we have the closing form tag of course. If we save that and we reload,

24
00:01:45,100 --> 00:01:46,950
now you see that here.

25
00:01:46,990 --> 00:01:51,880
Now if we enter something here and we hit send, you see the page reloads right, you'll see that here in

26
00:01:51,880 --> 00:01:57,360
the network tab, tis flickers because the page reloads and you briefly see a second request,

27
00:01:57,400 --> 00:02:01,140
that's the outgoing request before the page reloads.

28
00:02:01,140 --> 00:02:06,830
Now the outgoing request by default is a get request, on form we can set a method attribute and set

29
00:02:06,830 --> 00:02:09,610
this to post to send a post request instead

30
00:02:09,840 --> 00:02:12,510
and we can set an action attribute and point at slash

31
00:02:12,510 --> 00:02:18,910
nothing to tell the browser to which URL to send this HttpRequest and then to encode the data of

32
00:02:18,910 --> 00:02:25,480
the form properly, we should add a name attribute to the input and for example give this the user name

33
00:02:25,690 --> 00:02:26,380
identifier,

34
00:02:26,390 --> 00:02:32,020
this is totally up to you though. With that the browser is able to parse that form,

35
00:02:32,020 --> 00:02:36,940
have a look at all inputs that have a name and basically create a data object behind the scenes where

36
00:02:36,940 --> 00:02:43,060
it stores the data entered here under a user name key and then sends a post request with that data object

37
00:02:43,210 --> 00:02:48,160
to this URL, that's what the browser now does and that's a default browser behavior, has nothing

38
00:02:48,160 --> 00:02:53,980
to do with Node.js, has nothing to do with Javascript in general. We could just prevent this with client

39
00:02:53,980 --> 00:02:59,380
side Javascript where we listen to the form submission and prevent the default but I don't want to do

40
00:02:59,380 --> 00:03:01,910
that here, I want to use that default behavior instead.

41
00:03:02,950 --> 00:03:09,610
So now we'll send this request to the server, if I now reload here and I enter something here and I hit

42
00:03:09,610 --> 00:03:10,420
send,

43
00:03:10,570 --> 00:03:14,590
well we get the same behavior as before but actually we will get a request here,

44
00:03:14,590 --> 00:03:16,850
we just have to parse it now

45
00:03:17,110 --> 00:03:21,790
and for that here, let's work with that request object which we haven't used thus far.

46
00:03:22,460 --> 00:03:29,180
Parsing the body of an incoming requests can be a bit tricky or strange at first but we'll later learn

47
00:03:29,180 --> 00:03:30,860
how we can do it in an easier way.

48
00:03:31,830 --> 00:03:36,750
We first of all start by creating a variable, body and that should be an array actually because the body

49
00:03:36,750 --> 00:03:43,320
is received as chunks of data for efficiency reasons and we have to basically store all these chunks

50
00:03:43,470 --> 00:03:46,500
and then convert them to text thereafter.

51
00:03:46,500 --> 00:03:48,940
So here we get our chunks of data,

52
00:03:48,990 --> 00:03:54,600
now we need to extract the data from the request body actually. Now before we do that, let's see what's in

53
00:03:54,600 --> 00:03:55,830
the request.

54
00:03:55,830 --> 00:03:59,470
We could log the entire request object but this will be a huge object,

55
00:03:59,520 --> 00:04:05,130
so instead I want to start by logging the method which is one property we can read and the URL and

56
00:04:05,130 --> 00:04:10,650
then we at least see which requests reach this listener here, for which methods and which URLs.

57
00:04:11,140 --> 00:04:18,510
If we now save that and we restart this and we reload here without sending that, we already see some

58
00:04:18,510 --> 00:04:25,080
output here, get and /?, the question mark was added earlier to my URL when I hit

59
00:04:25,080 --> 00:04:27,390
send here before configuring the form,

60
00:04:27,510 --> 00:04:34,380
if I remove that and hit enter here, we see just get/. So we see by default when we visit the page,

61
00:04:34,710 --> 00:04:39,440
the browser sends a get request to ourdomain.com/,

62
00:04:39,450 --> 00:04:40,500
that's what we get here.

63
00:04:40,560 --> 00:04:44,530
The rest of URL simply is omitted here, on the URL property

64
00:04:44,580 --> 00:04:48,050
we just get the path on our server here.

65
00:04:48,150 --> 00:04:55,940
Now if I entered something here however, for example Anna and I hit send, you see now we also got a post request

66
00:04:55,940 --> 00:05:00,570
to slash nothing which makes sense because that is what we configured here in the end.

67
00:05:00,740 --> 00:05:06,470
So this is now some data we can get there but of course we want to get the body and to parse that, we

68
00:05:06,470 --> 00:05:12,740
need to add a listener on request which we do with the on method, not with add event listener but with

69
00:05:12,860 --> 00:05:17,930
on, there is an add listener method but that's not the right one here, we just want on.

70
00:05:18,170 --> 00:05:22,850
Now that's a difference to the browser because we're not working with a browser side API here and of

71
00:05:22,850 --> 00:05:26,460
course generally, every API can implement this the way it wants.

72
00:05:26,510 --> 00:05:32,720
Node.js typically works with on or with once if we only want to listen once instead of with add event

73
00:05:32,720 --> 00:05:33,110
listener

74
00:05:33,170 --> 00:05:35,520
but that's just something we have to get used to.

75
00:05:35,540 --> 00:05:39,500
So with on, we set up a listener here and I want to set up a listener

76
00:05:39,500 --> 00:05:42,100
first of all to the data event here.

77
00:05:42,270 --> 00:05:48,400
This is one event Node.js knows, just as the browser knows click on a button for example, Node.js knows

78
00:05:48,400 --> 00:05:53,450
the data event on the request and here we need to provide a second argument which is a function that

79
00:05:53,450 --> 00:06:01,430
should execute when this event occurs. There, we will get our chunk of data, will be passed in by Node.js

80
00:06:01,800 --> 00:06:07,460
and we can then add this to our array by pushing it into it. It's a normal Javascript array with the

81
00:06:07,460 --> 00:06:14,150
normal Javascript methods. By the way, on Node.js, you also have all these special methods like filter,

82
00:06:14,270 --> 00:06:17,200
map and so on you learned about in the arrays module,

83
00:06:17,210 --> 00:06:19,820
this is supported in Node.js as well.

84
00:06:19,940 --> 00:06:25,670
So now on every data piece we read in, so every data piece that's coming in on the request, we add it

85
00:06:25,670 --> 00:06:27,320
to this body array.

86
00:06:27,410 --> 00:06:33,080
Now we're interested in the point of time when we're done receiving data and for that we can add another

87
00:06:33,080 --> 00:06:36,220
listener to the end event.

88
00:06:36,260 --> 00:06:41,570
This will be fired when we're done reading in the request, so when it has been fully parsed, there we

89
00:06:41,570 --> 00:06:43,980
also have a function that should execute in this case

90
00:06:44,120 --> 00:06:49,390
and now we know the body array will be fully occupied now with our chunks of data,

91
00:06:49,400 --> 00:06:52,510
we will have all the chunks of data we got in this array.

92
00:06:52,580 --> 00:07:00,950
Now we just need to convert this body from an array of data chunks into some string data we can work

93
00:07:00,950 --> 00:07:08,240
with and for that, we can set b ody equal to buffer which is a global object available in Node.js, 

94
00:07:08,240 --> 00:07:15,790
.concat body, so body before we stored it here is an array of chunks, to string.

95
00:07:15,920 --> 00:07:21,110
This is the end just one way of converting this array of encoded chunks into a normal string and store

96
00:07:21,120 --> 00:07:23,690
that back in the body variable here,

97
00:07:23,690 --> 00:07:26,920
this is also why I use the variable here and not a constant.

98
00:07:27,260 --> 00:07:30,230
And once this is done, we know what's inside of the body,

99
00:07:30,230 --> 00:07:34,080
so let's console log body here then and see what is inside there.

100
00:07:34,190 --> 00:07:42,530
So if we now quit that server again and restart it and we reload here and send Anna to the server, we

101
00:07:42,530 --> 00:07:44,160
now see this is what was extracted,

102
00:07:44,200 --> 00:07:52,220
user name equals Anna. Well now we could parse this to do with it whatever we want, since it's such a string

103
00:07:52,220 --> 00:07:58,820
we could for example get a user name by using body, split it on the equal sign and then take the second

104
00:07:58,820 --> 00:08:03,740
element of the resulting array which is the concrete user name, so the thing after the equal sign and

105
00:08:03,740 --> 00:08:04,520
then work with it.

106
00:08:04,730 --> 00:08:09,330
So now we could send back a response and now it's important to send it back in the right place,

107
00:08:09,350 --> 00:08:15,530
currently what we're actually doing is we're sending back the response before we finished parsing the

108
00:08:15,530 --> 00:08:19,570
incoming request because this here is asynchronous code,

109
00:08:19,730 --> 00:08:25,430
This listener here triggers multiple times potentially, this listener also triggers at some point of

110
00:08:25,430 --> 00:08:28,360
time in the future when we're done parsing this in.

111
00:08:28,490 --> 00:08:34,550
So these functions here which we registered on these listeners don't execute right when this line executes,

112
00:08:34,760 --> 00:08:39,200
they execute when this event happens and that's the same as in the browser,

113
00:08:39,200 --> 00:08:45,820
the function you register on a click event only fires and runs when the click happens, not when Javascript

114
00:08:45,830 --> 00:08:48,450
parses the add event listener line.

115
00:08:48,710 --> 00:08:54,230
So therefore right now what actually happens is this line and this line is executed and then these lines

116
00:08:54,230 --> 00:08:58,700
are executed and only thereafter sometime in the future, these functions will execute.

117
00:08:58,820 --> 00:09:04,430
Of course I only want to send back the response once I'm done parsing the data, so we should move this

118
00:09:04,430 --> 00:09:08,840
code actually in here, into this request on end listener

119
00:09:08,840 --> 00:09:13,380
so that we don't send a response before we're done parsing this.

120
00:09:13,400 --> 00:09:18,430
So now if we save that and we reload this, we'll see no difference

121
00:09:18,500 --> 00:09:24,050
but this is technically cleaner and it is not just cleaner but absolutely required if we want to take

122
00:09:24,050 --> 00:09:27,740
that user name into account in the response you sent back.

123
00:09:27,740 --> 00:09:34,460
For example if I add a h1 tag here where I want to say hi user name, then we should convert it to a template

124
00:09:34,610 --> 00:09:41,330
literal with back ticks so that I can conveniently inject data here and then we can say hi user name

125
00:09:41,330 --> 00:09:41,860
here.

126
00:09:41,870 --> 00:09:46,670
Now of course to make sure that this also works before we submitted our form here, I will actually

127
00:09:46,670 --> 00:09:55,670
change user name to let here , cut this code and set this to a default of unknown user and then check

128
00:09:55,790 --> 00:10:05,530
if body is a thing, so if this is truthy and set user name equal to our split body or only if that's

129
00:10:05,530 --> 00:10:10,790
the case so that we have a fallback user name here in case we haven't set one yet

130
00:10:10,930 --> 00:10:16,570
and if we save that and restart our server, you need to hit enter here, just reloading will not

131
00:10:16,570 --> 00:10:20,780
work, you need to hit enter here in the URL to send a new get request

132
00:10:20,920 --> 00:10:24,020
otherwise you just reload these parsed post request.

133
00:10:24,130 --> 00:10:26,530
So let's hit enter here and you should see hi

134
00:10:26,530 --> 00:10:31,570
unknown user but as soon as you enter something here and click send, this will reload and show your data

135
00:10:31,570 --> 00:10:32,270
here.

136
00:10:32,290 --> 00:10:36,850
So this is then how you can parse incoming data and how you can send back a response

137
00:10:37,000 --> 00:10:43,600
but obviously this is quite cumbersome which is why we also have an easier or a better solution for that

138
00:10:43,760 --> 00:10:46,230
and which is why we have a framework for Node.js,

139
00:10:46,390 --> 00:10:50,890
just as we have frameworks and libraries for client side Javascript code as well.
