1
00:00:00,480 --> 00:00:05,010
Now to focus on that, we do something which is called mocking,

2
00:00:05,250 --> 00:00:09,270
we mock features which means we replace features

3
00:00:09,300 --> 00:00:15,170
we don't want a test with some dummy implementations and how could this look here?

4
00:00:15,240 --> 00:00:24,600
Well in utiltest.js, we got load title and we want to test if that successfully transforms our title

5
00:00:24,600 --> 00:00:28,230
to be all uppercase, to be this text.

6
00:00:28,230 --> 00:00:34,050
Now to test this, what we need to do is we need to replace fetch data with a mock.

7
00:00:34,190 --> 00:00:40,100
Now jest gives us a great way of preventing us from using that fetch data method.

8
00:00:40,380 --> 00:00:47,730
We can create a new folder called __mocks, all lowercase, __ next

9
00:00:47,730 --> 00:00:51,060
to the files that contain our raw source code,

10
00:00:51,660 --> 00:00:53,850
so in this case in our root folder.

11
00:00:54,150 --> 00:01:01,320
Now here, we can add a http.js file, so the same file name as the file that has the

12
00:01:01,320 --> 00:01:08,520
function we want to replace and now in http.js, we can now do some magic to set up some functions

13
00:01:08,520 --> 00:01:13,760
that will replace our real functions when running the tests. For that,

14
00:01:13,770 --> 00:01:19,830
I'll copy my code from http.js, I'll get rid of axios though because I'll not use that here, I'll

15
00:01:19,830 --> 00:01:22,190
still export fetch data though

16
00:01:22,410 --> 00:01:30,210
but in fetch data, I'll simply return a promise which I instantly resolve with promise resolve to an

17
00:01:30,210 --> 00:01:35,960
object that has a title property with the text I want to test which I'll now convert to all lowercase

18
00:01:36,000 --> 00:01:38,880
though, so delectus aut autem

19
00:01:42,290 --> 00:01:44,630
and now that I'm exporting this here,

20
00:01:44,630 --> 00:01:50,750
something interesting will happen. In http.js, I added a console log statement to fetch data to

21
00:01:50,750 --> 00:01:54,140
see when we're hitting this API and when we're not.

22
00:01:54,140 --> 00:01:55,880
If I now run npm test,

23
00:02:01,770 --> 00:02:06,810
we are hitting the API as you can see here, we have that console log statement from the HTTP file

24
00:02:06,810 --> 00:02:07,630
in there.

25
00:02:07,650 --> 00:02:16,700
Now we can go to utiltest.js and in there, we want to add jest mock at the beginning and mock the

26
00:02:16,700 --> 00:02:19,510
http.js file like this,

27
00:02:19,760 --> 00:02:23,180
you can omit .js though. Now if I run npm test,

28
00:02:26,330 --> 00:02:31,760
you see it also took close to a second because it had to do some magic behind the scenes but you don't see

29
00:02:31,760 --> 00:02:37,880
that console log statement because what now happens is when this test gets executed, when this testing

30
00:02:37,880 --> 00:02:44,960
file gets executed, jest goes ahead and replaces the HTTP file with our mocked file,

31
00:02:44,960 --> 00:02:51,590
so all the functions that are export that here are then replacing the functions we are normally exporting

32
00:02:51,590 --> 00:02:58,230
in the real HTTP file for our tests only. So for the tests only, we use our mocked functions here,

33
00:02:58,280 --> 00:03:05,480
so this dummy fetch data which gives us back an object that allow us the other functions to work fine but

34
00:03:05,510 --> 00:03:11,000
which does not hit the API because we don't want to test the API response and we don't want to test

35
00:03:11,000 --> 00:03:17,690
the access get method, so we can rely on the API returning as an object that has a title property and

36
00:03:17,690 --> 00:03:24,080
we can rely on the access get method giving us an object and a response which has a data property, so

37
00:03:24,080 --> 00:03:31,280
we don't need to test that. We want to test whether our code in the util.js file correctly extracts

38
00:03:31,280 --> 00:03:34,880
the title and transforms it and that is the case

39
00:03:34,910 --> 00:03:42,470
otherwise this test would not have succeeded for our mocked implementation of fetch data where we return

40
00:03:42,470 --> 00:03:45,590
an object with a title that is all lowercase,

41
00:03:45,590 --> 00:03:52,910
so not what we test for lowercase this text and therefore since our test succeeds, we know that our transformation

42
00:03:52,910 --> 00:03:54,520
here does work.

43
00:03:54,560 --> 00:04:00,350
So this is how we can test async code or how we can replace code, how we can replace functionalities

44
00:04:00,560 --> 00:04:01,730
if we don't want to

45
00:04:01,730 --> 00:04:08,690
in this case hit the API, the same would be the case for let's say code that accesses the filesystem, you

46
00:04:08,690 --> 00:04:09,860
don't want to do that,

47
00:04:09,890 --> 00:04:16,970
instead you want to mock such functionalities. You can by the way also mock global packages, like axios

48
00:04:16,970 --> 00:04:28,100
itself. Instead of mocking our fetch data function, you could create an axios.js file here and there,

49
00:04:29,270 --> 00:04:32,990
we could export our own get function here

50
00:04:35,970 --> 00:04:37,920
which we of course have to define

51
00:04:41,820 --> 00:04:49,570
because remember in my https file, I am using the get method of the axios object.

52
00:04:49,680 --> 00:04:56,670
So here I want to export a get method and that would be a function that takes a URL as an argument

53
00:04:56,910 --> 00:05:06,180
but we don't care about that URL here, what we want to do here is we can return an object which

54
00:05:06,180 --> 00:05:10,490
in this case, since this is faking the response from axios,

55
00:05:10,590 --> 00:05:16,320
so we want to fake whatever get gives us back and that should be a response object which at least has

56
00:05:16,320 --> 00:05:18,600
a data key because we're extracting that,

57
00:05:18,660 --> 00:05:24,660
so here in the axios mock, we want to have a data object which should in turn be an object with the title

58
00:05:24,750 --> 00:05:25,820
we want to test,

59
00:05:25,950 --> 00:05:28,700
so that lowercase title we defined here.

60
00:05:28,710 --> 00:05:35,730
So basically we're now mocking a functionality which is one level above the last functionality, where

61
00:05:35,730 --> 00:05:38,160
we mocked our own function,

62
00:05:38,160 --> 00:05:44,140
now we're using we're mocking the function, this raw function so this function depends on.

63
00:05:44,700 --> 00:05:50,520
So now in the axios.js mock file I'm returning an object which has a data key which has an object as

64
00:05:50,520 --> 00:05:56,820
a value, which has a title key which is the lowercase version of our text and with that being mocked, we

65
00:05:56,820 --> 00:05:58,260
can go to our utiltest.js

66
00:05:58,260 --> 00:06:06,410
file, we can comment out this mocking of our HTTP implementation, so we'll now not use this HTTP file

67
00:06:06,420 --> 00:06:13,880
we created a second ago, Jest.js will automatically use mocks of global node modules though, so axios.js

68
00:06:13,890 --> 00:06:19,950
this module should be used automatically, we don't have to instruct jest to do that and now we

69
00:06:19,950 --> 00:06:23,420
can simply run npm test and here

70
00:06:26,650 --> 00:06:35,030
it fails because what I return here is not a promise and this already proves that this mocked file is

71
00:06:35,030 --> 00:06:41,210
being used, otherwise it would not have failed. I'm returning an object there and therefore calling then

72
00:06:41,210 --> 00:06:46,920
fails, I of course have to return a promise here by using promise resolve,

73
00:06:47,090 --> 00:06:54,320
so a promise that eventually yields this object and once I do that and therefore my mocked get method

74
00:06:54,590 --> 00:07:01,370
provides a promise as the real axios implementation does, once I do that, it passes again. We see fetching

75
00:07:01,370 --> 00:07:08,150
data here because we are now using my original fetch data implementation but the get method we're using

76
00:07:08,150 --> 00:07:11,690
here is not the real one, it's our mocked one,

77
00:07:11,690 --> 00:07:13,160
so this one here.

78
00:07:13,310 --> 00:07:20,240
Now this is how you can mock certain functionalities to test async code or code in general which might

79
00:07:20,240 --> 00:07:22,460
depend on third-party packages.

80
00:07:22,460 --> 00:07:24,780
Now there are other strategies as well,

81
00:07:24,780 --> 00:07:30,470
you'll also find the term spies or stops when you went deeper into testing and you can definitely also

82
00:07:30,470 --> 00:07:36,290
check out these alternative approaches to learn about alternative strategies for working with async

83
00:07:36,290 --> 00:07:41,780
code and third-party libraries. Attached to this lecture, you also find additional resources that allow

84
00:07:41,780 --> 00:07:47,120
you to dive deeper into these topics and into jest in general and learn more about testing and build

85
00:07:47,120 --> 00:07:48,980
up on the knowledge you gain here.
