Would you like to inspect the original subtitles? These are the user uploaded subtitles that are being translated:
1
00:00:02,100 --> 00:00:04,050
Now, you can absolutely write
2
00:00:04,050 --> 00:00:07,230
this client side data fetching code on your own,
3
00:00:07,230 --> 00:00:10,330
as we did it here, there's nothing wrong with that.
4
00:00:10,330 --> 00:00:12,330
And you might have good reasons to do that
5
00:00:12,330 --> 00:00:15,340
because this, of course, gives you full control
6
00:00:15,340 --> 00:00:17,260
over the entire component state,
7
00:00:17,260 --> 00:00:20,380
and how exactly data is being fetched.
8
00:00:20,380 --> 00:00:23,320
But this is also such a common pattern
9
00:00:23,320 --> 00:00:27,040
that you could consider creating your own custom hook
10
00:00:27,040 --> 00:00:29,160
to outsource this logic into it,
11
00:00:29,160 --> 00:00:33,420
or to use a third-party hook created by someone else.
12
00:00:33,420 --> 00:00:37,320
And you can look into the SWR hook.
13
00:00:37,320 --> 00:00:42,320
If you Google for use SWR you will find swr.vercel.app.
14
00:00:43,860 --> 00:00:47,950
This is a React hook developed by the Next.js team,
15
00:00:47,950 --> 00:00:52,250
but you can use it in non-Next.js projects as well.
16
00:00:52,250 --> 00:00:53,770
In the end, this is a hook which,
17
00:00:53,770 --> 00:00:57,600
under the hood, still will send a HTTP request
18
00:00:57,600 --> 00:01:01,730
by default using the fetch API, which we also used,
19
00:01:01,730 --> 00:01:04,620
but it gives you a couple of nice built in features
20
00:01:04,620 --> 00:01:09,620
like caching and automatic revalidation retries on error.
21
00:01:10,970 --> 00:01:14,640
And you don't have to write all that code on your own.
22
00:01:14,640 --> 00:01:18,080
Instead, you can use this hook in a much simpler way.
23
00:01:18,080 --> 00:01:21,460
The strange name SWR, by the way, stands
24
00:01:21,460 --> 00:01:25,350
for stale-while-revalidate, which is the name of this hook
25
00:01:25,350 --> 00:01:30,060
because this hook has a built in features for caching data
26
00:01:30,060 --> 00:01:34,310
and revalidating data to give you the most up-to-date data
27
00:01:34,310 --> 00:01:38,740
without you noticing in a positive way, and so on.
28
00:01:38,740 --> 00:01:40,240
Now, you can dive into the docs
29
00:01:40,240 --> 00:01:42,350
of this hook to learn all about it
30
00:01:42,350 --> 00:01:45,210
because you can definitely also create
31
00:01:45,210 --> 00:01:47,320
a short course about this hook here,
32
00:01:47,320 --> 00:01:51,490
but getting started with it, thankfully, is super simple.
33
00:01:51,490 --> 00:01:54,990
In our project, we just need to quit the dev server
34
00:01:54,990 --> 00:01:57,400
and install it as a package.
35
00:01:57,400 --> 00:02:00,650
With npm install swr we install
36
00:02:00,650 --> 00:02:04,393
this SWR hook package into our project.
37
00:02:05,540 --> 00:02:09,400
Now, in last sales, if you want to use it, we can import it.
38
00:02:09,400 --> 00:02:14,400
We can import useSWR from 'swr' just like this.
39
00:02:16,470 --> 00:02:19,843
This imports the hook, it's the same example you see here.
40
00:02:20,710 --> 00:02:24,180
And now you can use this hook in your component,
41
00:02:24,180 --> 00:02:25,990
so not inside of useEffect,
42
00:02:25,990 --> 00:02:27,980
but directly in your component,
43
00:02:27,980 --> 00:02:30,770
all React hooks must be used directly
44
00:02:30,770 --> 00:02:33,880
in a component, not in some nested function.
45
00:02:33,880 --> 00:02:36,143
And we use it by simply executing it.
46
00:02:37,440 --> 00:02:40,140
Now, this hook wants at least one argument,
47
00:02:40,140 --> 00:02:43,950
which is an identifier for the request it should send,
48
00:02:43,950 --> 00:02:47,530
typically, the URL of that request.
49
00:02:47,530 --> 00:02:50,360
And it's also called an identifier
50
00:02:50,360 --> 00:02:53,540
because this hook will bundle multiple requests
51
00:02:53,540 --> 00:02:57,470
to the same URL, which are sent in a certain timeframe
52
00:02:57,470 --> 00:03:02,470
into one request to avoid sending dozens of small requests.
53
00:03:02,830 --> 00:03:07,230
Not an issue we'll have here, but nice to have in general.
54
00:03:07,230 --> 00:03:10,680
So, we can grab our URL here as an identifier
55
00:03:10,680 --> 00:03:12,860
because it will then conveniently use
56
00:03:12,860 --> 00:03:15,913
this identifier as a URL as well.
57
00:03:16,980 --> 00:03:20,603
And in the simplest form, this is all we have to do.
58
00:03:21,510 --> 00:03:25,750
You can add a second argument, which is a fetcher function
59
00:03:25,750 --> 00:03:27,670
which is a function that describes
60
00:03:27,670 --> 00:03:29,850
how the request should be sent.
61
00:03:29,850 --> 00:03:33,160
But the default is that it will use the fetch API.
62
00:03:33,160 --> 00:03:36,630
So, if we want to stick to that default, which I do here,
63
00:03:36,630 --> 00:03:39,000
we don't need to change anything.
64
00:03:39,000 --> 00:03:42,450
Instead, we just call useSWR, like this.
65
00:03:42,450 --> 00:03:45,760
And the request to this URL will be sent
66
00:03:45,760 --> 00:03:48,170
when this component is loaded.
67
00:03:48,170 --> 00:03:50,050
So, now, we can work with the data,
68
00:03:50,050 --> 00:03:52,180
which is returned by that hook.
69
00:03:52,180 --> 00:03:54,440
And that will be an object,
70
00:03:54,440 --> 00:03:57,280
which we can destructure therefore,
71
00:03:57,280 --> 00:04:01,420
which contains the data that was fetched eventually,
72
00:04:01,420 --> 00:04:04,320
and potential error information.
73
00:04:04,320 --> 00:04:08,140
So, I'll use the exact same object destructuring here
74
00:04:08,140 --> 00:04:11,120
and pull out the data, which we eventually get,
75
00:04:11,120 --> 00:04:13,183
and the error, which we might get.
76
00:04:14,050 --> 00:04:17,640
Down here, in our custom code, we have no error handling,
77
00:04:17,640 --> 00:04:19,740
but now we can easily implement it
78
00:04:19,740 --> 00:04:22,089
by just using this extra piece of data,
79
00:04:22,089 --> 00:04:24,703
which we get by the useSWR hook.
80
00:04:25,950 --> 00:04:29,440
So now, with that, we can comment out our custom hook.
81
00:04:29,440 --> 00:04:31,180
We could also delete it but I want
82
00:04:31,180 --> 00:04:33,450
to keep it around for a reference.
83
00:04:33,450 --> 00:04:37,030
We can also comment out our custom states though.
84
00:04:37,030 --> 00:04:40,260
And, now, we can work with data and error.
85
00:04:40,260 --> 00:04:44,630
If we don't have data yet, then we know that we're loading.
86
00:04:44,630 --> 00:04:48,020
So, here I'll check if not data,
87
00:04:48,020 --> 00:04:51,000
if we don't have data yet, then I return Loading...
88
00:04:51,910 --> 00:04:54,340
If we have an error, on the other hand,
89
00:04:54,340 --> 00:04:57,570
I wanna show an error message here, like Failed to load
90
00:04:58,920 --> 00:05:03,230
and we should move that in front of the, if data check
91
00:05:03,230 --> 00:05:06,480
because an error is more important than the loading state.
92
00:05:06,480 --> 00:05:08,503
If we have an error, I wanna show it.
93
00:05:10,050 --> 00:05:13,660
Now, if we don't have an error and we do have data,
94
00:05:13,660 --> 00:05:16,490
so if we make it past these two if checks,
95
00:05:16,490 --> 00:05:18,923
then we can output the data.
96
00:05:20,280 --> 00:05:22,580
Now, the problem we'll then face, however,
97
00:05:22,580 --> 00:05:25,460
is that, as I mentioned, the data we get back
98
00:05:25,460 --> 00:05:28,540
from Firebase is not in the right format.
99
00:05:28,540 --> 00:05:30,550
We need to transform it.
100
00:05:30,550 --> 00:05:34,290
Now, to work around that issue we got two main approaches.
101
00:05:34,290 --> 00:05:37,040
We could define our own fetcher function,
102
00:05:37,040 --> 00:05:40,760
you can learn about that here in the SWR docs,
103
00:05:40,760 --> 00:05:42,530
to basically fine tune
104
00:05:42,530 --> 00:05:45,830
how exactly data will be fetched and returned.
105
00:05:45,830 --> 00:05:48,370
Or we, again, use useEffect but,
106
00:05:48,370 --> 00:05:50,300
now, not for sending the request
107
00:05:50,300 --> 00:05:53,170
but for simply transforming the data.
108
00:05:53,170 --> 00:05:57,430
So then, here, our dependency would be the data which we get
109
00:05:57,430 --> 00:06:00,760
because I want to rerun this whenever we got new data.
110
00:06:00,760 --> 00:06:02,410
And in useEffect, I want to check
111
00:06:02,410 --> 00:06:05,350
if we do have data, because if we don't have data
112
00:06:05,350 --> 00:06:07,280
there is nothing we need to do.
113
00:06:07,280 --> 00:06:10,240
But if I do have data, then I wanna go
114
00:06:10,240 --> 00:06:12,970
through these transformation steps here.
115
00:06:12,970 --> 00:06:15,433
So, I'll copy this code from down there,
116
00:06:16,460 --> 00:06:21,460
comment this in, and then bring back my sales state here
117
00:06:21,680 --> 00:06:23,880
so that I can set this state
118
00:06:23,880 --> 00:06:27,410
after we transformed the data here in useEffect.
119
00:06:27,410 --> 00:06:30,450
So here, instead of this if check still,
120
00:06:30,450 --> 00:06:33,420
instead of useEffect, I'll then set my sales
121
00:06:33,420 --> 00:06:37,410
to the transform sales, which are now based
122
00:06:37,410 --> 00:06:41,547
on the data, the data key we're getting from useSWR.
123
00:06:43,140 --> 00:06:45,750
So, now, we have our own transformation logic here,
124
00:06:45,750 --> 00:06:48,963
which will be kicked off as soon as data was fetched.
125
00:06:50,070 --> 00:06:52,210
And that means that now, again, down there
126
00:06:52,210 --> 00:06:55,070
we can check that even if we have data
127
00:06:55,070 --> 00:06:57,540
it might not have been transformed yet.
128
00:06:57,540 --> 00:06:59,260
So, if we don't have sales yet,
129
00:06:59,260 --> 00:07:01,100
which is our transformed data,
130
00:07:01,100 --> 00:07:04,250
I still return a paragraph where I also say Loading...,
131
00:07:04,250 --> 00:07:06,630
for example, and of course, therefore,
132
00:07:06,630 --> 00:07:09,540
we can merge this and say if we don't have data
133
00:07:09,540 --> 00:07:13,530
or we don't have sales I want to return Loading...
134
00:07:13,530 --> 00:07:17,120
But if we do have both, then we can safely,
135
00:07:17,120 --> 00:07:18,833
again, output ours sales.
136
00:07:20,600 --> 00:07:22,940
And that's how we can now useSWR
137
00:07:22,940 --> 00:07:25,753
and still apply our own transformation logic.
138
00:07:26,940 --> 00:07:29,580
With all of that, if we now save this
139
00:07:29,580 --> 00:07:32,160
and restart the development server
140
00:07:32,160 --> 00:07:34,860
we should, again, have a working page.
141
00:07:34,860 --> 00:07:37,550
If we go back to last sales and reload,
142
00:07:37,550 --> 00:07:40,543
we see Loading... and, eventually, we see the data.
143
00:07:41,480 --> 00:07:43,340
And still, if I view the page source
144
00:07:43,340 --> 00:07:45,230
we don't see the data there,
145
00:07:45,230 --> 00:07:47,460
but instead we now see Loading...
146
00:07:47,460 --> 00:07:50,670
We see Loading... here because that is the starting state,
147
00:07:50,670 --> 00:07:53,170
the first initial version of this component,
148
00:07:53,170 --> 00:07:55,140
which is being rendered.
149
00:07:55,140 --> 00:07:57,980
Because initially error is undefined,
150
00:07:57,980 --> 00:07:59,810
so we don't return this.
151
00:07:59,810 --> 00:08:02,030
And data and sales are undefined,
152
00:08:02,030 --> 00:08:04,330
so we do return this and, therefore,
153
00:08:04,330 --> 00:08:07,530
that's what we see as part of the pre-rendered page.
154
00:08:07,530 --> 00:08:11,530
And, again, data fetching only happens on the client side.
155
00:08:11,530 --> 00:08:16,460
Now, using this hook, this useSWR hook, is not mandatory.
156
00:08:16,460 --> 00:08:19,170
As you saw, you can write your own logic,
157
00:08:19,170 --> 00:08:21,270
you don't need to use it.
158
00:08:21,270 --> 00:08:24,220
It just can be convenient to use this hook
159
00:08:24,220 --> 00:08:26,570
because you save a little bit of code,
160
00:08:26,570 --> 00:08:30,950
especially if you also would add error handling down there.
161
00:08:30,950 --> 00:08:34,530
And this hook, also has a bunch of other nice features,
162
00:08:34,530 --> 00:08:36,070
which we're not using here,
163
00:08:36,070 --> 00:08:38,720
but which can also be very handy.
164
00:08:38,720 --> 00:08:41,960
Like automatically re-fetching data when you lose
165
00:08:41,960 --> 00:08:45,580
and regain focus and other things like this.
166
00:08:45,580 --> 00:08:48,040
So that's something you can also look into.
167
00:08:48,040 --> 00:08:50,270
But, for the moment, that's all I wanted
168
00:08:50,270 --> 00:08:53,250
to show here because now we also know
169
00:08:53,250 --> 00:08:56,433
how we can implement client side data fetching.
13841
Can't find what you're looking for?
Get subtitles in any language from opensubtitles.com, and translate them here.