1 00:00:00,120 --> 00:00:04,120 In this lecture, we are going to finish the asynchronous validator. 2 00:00:04,140 --> 00:00:05,280 We've been working on. 3 00:00:05,640 --> 00:00:10,980 There are two problems with the validator, but they're not going to be evident until we've used the 4 00:00:10,980 --> 00:00:11,700 validator. 5 00:00:12,000 --> 00:00:13,950 Let's give our validator a try. 6 00:00:14,220 --> 00:00:16,290 Open the email taken file. 7 00:00:18,850 --> 00:00:23,320 The asynchronous validator we've created has a function called Validate. 8 00:00:23,740 --> 00:00:29,200 We've decided not to make this method static for reasons we discussed in an earlier lecture. 9 00:00:29,560 --> 00:00:33,790 We would not be able to use dependency injection from a static method. 10 00:00:34,120 --> 00:00:39,700 However, we are going to need to create an instance out of the email taking class. 11 00:00:40,270 --> 00:00:45,280 Instead of manually creating an instance, we should use dependency injection. 12 00:00:45,700 --> 00:00:48,640 The injectable decorator has two benefits. 13 00:00:48,970 --> 00:00:52,990 It'll enable Angular to inject services into our class. 14 00:00:53,410 --> 00:00:58,210 The second benefit is being able to inject this class into other classes. 15 00:00:58,600 --> 00:01:01,300 Dependency injection can go both ways. 16 00:01:01,600 --> 00:01:06,310 Let's inject this class inside the register component class file. 17 00:01:08,840 --> 00:01:13,100 At the top of the file, we will import the e-mail taken class. 18 00:01:15,530 --> 00:01:19,940 Next, we will inject an instance of this class into our component. 19 00:01:20,240 --> 00:01:23,630 The name of the property will be called e-mail taken. 20 00:01:26,270 --> 00:01:32,930 After injecting the service, we should add it to the email form control, the form control function 21 00:01:32,930 --> 00:01:36,380 has a third argument for asynchronous validators. 22 00:01:36,740 --> 00:01:41,870 Synchronous and asynchronous validators are passed in as separate arguments. 23 00:01:42,230 --> 00:01:45,410 The second argument is for synchronous validators. 24 00:01:45,770 --> 00:01:49,370 The third argument is for asynchronous validators. 25 00:01:49,700 --> 00:01:54,740 Let's pass an array with our email taken in validate function. 26 00:01:57,360 --> 00:02:01,830 Before we test our validator, let's set an error message to the template. 27 00:02:02,160 --> 00:02:04,470 Open the input template file. 28 00:02:07,040 --> 00:02:11,870 At the bottom of the template, we will make a copy of one of the error messages. 29 00:02:14,510 --> 00:02:21,170 The condition will be updated to check if the email taken property has been added to the as object. 30 00:02:23,790 --> 00:02:28,290 Lastly, let's update the message to the following email taken. 31 00:02:28,440 --> 00:02:30,180 Please try another email. 32 00:02:32,720 --> 00:02:37,070 Time to give our app a test in the browser, refresh the page. 33 00:02:39,580 --> 00:02:46,610 The app will become broken, we can't open the model to test the registration form to understand why. 34 00:02:46,630 --> 00:02:49,630 Let's check out the console in the developer tools. 35 00:02:49,930 --> 00:02:53,980 The error says the following no provider for email taken. 36 00:02:54,550 --> 00:02:56,650 The error is pointing to our class. 37 00:02:57,100 --> 00:03:00,970 Angular is unable to inject this class into our component. 38 00:03:01,360 --> 00:03:06,730 The reason it can't inject the class is because it doesn't know where to inject the class. 39 00:03:07,120 --> 00:03:09,010 Let's go back to our editors. 40 00:03:11,490 --> 00:03:13,860 Switch to the email taking class. 41 00:03:14,130 --> 00:03:20,880 We decorated the class with the injectable decorator, as we discussed before, this decorator will 42 00:03:20,880 --> 00:03:24,120 allow our class to be injected with services. 43 00:03:24,540 --> 00:03:27,840 But what if we want to inject this class into components? 44 00:03:28,140 --> 00:03:33,540 By default, Angular does not assume our class can be injected into our app. 45 00:03:34,140 --> 00:03:40,710 We must explicitly tell Angular our class can be injected into other areas of our app. 46 00:03:41,190 --> 00:03:47,880 The simplest way of making our class injectable is by passing in an object to the injectable decorator 47 00:03:47,880 --> 00:03:49,860 function in this object. 48 00:03:49,980 --> 00:03:53,490 We will set the provided in property to route. 49 00:03:56,050 --> 00:03:59,260 After making that change, let's refresh the page. 50 00:04:01,830 --> 00:04:04,260 The motel can be opened without a problem. 51 00:04:04,590 --> 00:04:11,370 We're able to move on to testing our validator inside the registration form type a valid email. 52 00:04:14,000 --> 00:04:21,560 After typing and signed the email field, we will encounter another error in the console this time Angular 53 00:04:21,560 --> 00:04:25,850 is unable to access the authentication service from our validator. 54 00:04:26,240 --> 00:04:29,300 This problem is caused by the JavaScript language. 55 00:04:29,570 --> 00:04:31,850 It's not a direct problem from angular. 56 00:04:32,090 --> 00:04:35,150 Let's go back to the register component class. 57 00:04:37,620 --> 00:04:40,980 We are passing in a reference to the validate function. 58 00:04:41,250 --> 00:04:45,570 As a result, the context of the validator will have changed. 59 00:04:45,870 --> 00:04:50,490 The this keyword does not point to the object's properties and methods. 60 00:04:50,850 --> 00:04:52,860 Fixing this issue will be simple. 61 00:04:53,220 --> 00:04:58,830 Back in the validator or file, we will convert the validate function into an arrow function. 62 00:05:01,400 --> 00:05:05,630 With this one simple change, we will fix the context issue. 63 00:05:06,020 --> 00:05:09,200 Switch back to the registration form in the browser. 64 00:05:11,870 --> 00:05:15,410 Typing taping inside the email field will not yield the same error. 65 00:05:15,740 --> 00:05:18,470 We fixed the problems with our validator. 66 00:05:18,800 --> 00:05:20,420 I'm going to type the email. 67 00:05:20,420 --> 00:05:23,030 I've registered an account within our app. 68 00:05:25,590 --> 00:05:30,030 After doing so, I will receive an error stating the email has been taken. 69 00:05:30,390 --> 00:05:33,240 Our validator is behaving as expected. 70 00:05:33,600 --> 00:05:37,440 If I were to modify the email value, the error would go away. 71 00:05:37,740 --> 00:05:39,840 We can assume the email is unique. 72 00:05:40,110 --> 00:05:45,240 There are a couple of points I want to make about asynchronous validators before moving on. 73 00:05:45,840 --> 00:05:53,400 Firstly, Angular doesn't fire the asynchronous validators until every synchronous validation is satisfied. 74 00:05:53,820 --> 00:05:57,540 Asynchronous validators require resources from a server. 75 00:05:57,840 --> 00:06:03,750 It's not considered good practice to initiate a request on every change made to the form control. 76 00:06:04,080 --> 00:06:10,620 Angular helps us from using fewer resources by waiting for these synchronous validations to be satisfied. 77 00:06:11,190 --> 00:06:14,160 For example, let's switch to the Network tab. 78 00:06:14,460 --> 00:06:18,510 Requests can be filtered by selecting the X H.R. option. 79 00:06:21,050 --> 00:06:27,800 We can view the requests made to Firebase by typing inside the field for every change we make, a new 80 00:06:27,800 --> 00:06:28,790 request is made. 81 00:06:29,120 --> 00:06:31,610 However, what if our email is invalid? 82 00:06:31,880 --> 00:06:33,860 Firebase would throw an error. 83 00:06:34,130 --> 00:06:37,340 There isn't a point in sending the email to Firebase. 84 00:06:37,820 --> 00:06:41,420 We've added a validator for checking the format of an email. 85 00:06:41,690 --> 00:06:47,810 If we were to remove the domain extension from the value, a request is not made to Firebase. 86 00:06:48,080 --> 00:06:52,220 At the same time, the email validator is throwing an error. 87 00:06:52,670 --> 00:06:58,520 Since the email validator throws an error, the asynchronous validator will never run. 88 00:06:59,090 --> 00:07:01,730 This behavior is incredibly beneficial. 89 00:07:02,030 --> 00:07:06,500 We are reducing the number of resources taken up by our validator. 90 00:07:06,800 --> 00:07:09,950 We don't have to do anything to enable this behavior. 91 00:07:10,220 --> 00:07:12,620 It's the default behavior of angular. 92 00:07:13,130 --> 00:07:15,680 We've successfully created a validator. 93 00:07:15,890 --> 00:07:18,250 We're finished validating our forums. 94 00:07:18,500 --> 00:07:21,740 We can start moving on to the other features of our app. 95 00:07:22,070 --> 00:07:26,240 We will begin to the element of the rest of the app in the next section.