1 00:00:01,050 --> 00:00:01,883 Instructor: In the last section, 2 00:00:01,883 --> 00:00:04,890 we tried to create a new user account on our backend API, 3 00:00:04,890 --> 00:00:06,810 but we very quickly got an error message down here 4 00:00:06,810 --> 00:00:07,987 that said something like, 5 00:00:07,987 --> 00:00:10,290 "No access controlled, allow origin. 6 00:00:10,290 --> 00:00:13,050 Header is present on the requested resource." 7 00:00:13,050 --> 00:00:13,883 So in this section, 8 00:00:13,883 --> 00:00:16,290 we're gonna talk about what this error message means 9 00:00:16,290 --> 00:00:19,020 and then very quickly figure out how we're going to fix it. 10 00:00:19,020 --> 00:00:22,200 So first off, let's get a plain English definition 11 00:00:22,200 --> 00:00:24,090 of what's going on here. 12 00:00:24,090 --> 00:00:25,470 We're seeing this error message 13 00:00:25,470 --> 00:00:28,080 due to something called a CORS error, 14 00:00:28,080 --> 00:00:30,840 or a CORS request error. 15 00:00:30,840 --> 00:00:33,240 CORS, spelled C-O-R-S, 16 00:00:33,240 --> 00:00:36,543 stands for Cross Origin Resource Sharing. 17 00:00:37,440 --> 00:00:39,570 CORS is a security feature 18 00:00:39,570 --> 00:00:42,120 implemented inside of your browser. 19 00:00:42,120 --> 00:00:45,540 So, specifically whatever browser you are using right now, 20 00:00:45,540 --> 00:00:50,370 is what is really truly issuing this error message to us. 21 00:00:50,370 --> 00:00:51,720 Let's take a look at a quick diagram 22 00:00:51,720 --> 00:00:53,640 that's gonna help you get a better idea 23 00:00:53,640 --> 00:00:56,223 of why we're seeing a CORS message at all. 24 00:00:57,570 --> 00:01:00,090 Okay, so over here we're going to imagine for a second 25 00:01:00,090 --> 00:01:03,810 that we are working on a completely different application. 26 00:01:03,810 --> 00:01:05,129 I want you to imagine that you're working 27 00:01:05,129 --> 00:01:07,620 on a banking application of some sort. 28 00:01:07,620 --> 00:01:11,310 Maybe your application is hosted at my-bank.com. 29 00:01:11,310 --> 00:01:14,520 And the primary purpose of your banking application 30 00:01:14,520 --> 00:01:17,670 is to allow users to request to transfer money 31 00:01:17,670 --> 00:01:20,190 from one account to another account. 32 00:01:20,190 --> 00:01:22,530 So from my-bank.com, 33 00:01:22,530 --> 00:01:25,050 you might load up a JavaScript file. 34 00:01:25,050 --> 00:01:27,000 And whenever a user clicks on some button 35 00:01:27,000 --> 00:01:28,350 inside of your application, 36 00:01:28,350 --> 00:01:31,320 it runs some JavaScript that issues a request 37 00:01:31,320 --> 00:01:35,400 to transfer money to our bank backend API, 38 00:01:35,400 --> 00:01:40,380 hosted at my-bank.com/API/transfer. 39 00:01:40,380 --> 00:01:41,910 So, everything I've showed you right here 40 00:01:41,910 --> 00:01:44,763 ideally would be the way that our application would work. 41 00:01:45,630 --> 00:01:46,463 But, let's imagine 42 00:01:46,463 --> 00:01:49,290 that some really malicious person comes along. 43 00:01:49,290 --> 00:01:52,950 And this is a person who wants to trick our customers 44 00:01:52,950 --> 00:01:55,530 into creating requests to transfer money. 45 00:01:55,530 --> 00:01:58,890 To send money from their account to the malicious person, 46 00:01:58,890 --> 00:02:00,843 or the hacker's account instead. 47 00:02:01,800 --> 00:02:04,860 So, maybe in an attack, some user, 48 00:02:04,860 --> 00:02:06,873 or some very malicious person, 49 00:02:07,860 --> 00:02:12,480 creates a new website called malicious-site.com. 50 00:02:12,480 --> 00:02:15,240 Yeah, I know it should be pretty obvious it's a bad website. 51 00:02:15,240 --> 00:02:17,730 But, let's imagine they create this website right here 52 00:02:17,730 --> 00:02:20,970 and they trick some of our users going over to it. 53 00:02:20,970 --> 00:02:22,110 So, some of our users, 54 00:02:22,110 --> 00:02:23,640 for our banking application, 55 00:02:23,640 --> 00:02:27,420 go over to this website and when this website loads up, 56 00:02:27,420 --> 00:02:29,940 the user gets tricked into clicking a button 57 00:02:29,940 --> 00:02:32,790 that makes that exact same request. 58 00:02:32,790 --> 00:02:35,370 So, a user gets tricked into clicking a button 59 00:02:35,370 --> 00:02:37,740 that tries to request to transfer money 60 00:02:37,740 --> 00:02:41,430 from their account over to the hacker's account. 61 00:02:41,430 --> 00:02:42,660 Now, the key thing to notice here 62 00:02:42,660 --> 00:02:45,900 is that we are now at some different URL up here. 63 00:02:45,900 --> 00:02:48,570 Some, malicious-site.com. 64 00:02:48,570 --> 00:02:51,810 and we're going to try to issue a request to transfer money 65 00:02:51,810 --> 00:02:53,520 over to our backend API, 66 00:02:53,520 --> 00:02:56,610 hosted at my-bank.com. 67 00:02:56,610 --> 00:02:58,260 So, in this situation right here, 68 00:02:58,260 --> 00:03:01,260 we would want this request to fail. 69 00:03:01,260 --> 00:03:02,670 We would want to figure out some way 70 00:03:02,670 --> 00:03:05,430 to prevent a user, or some malicious person, 71 00:03:05,430 --> 00:03:07,710 from making this impersonator website 72 00:03:07,710 --> 00:03:10,020 and trying to make a request to transfer money 73 00:03:10,020 --> 00:03:11,643 over to our backend API. 74 00:03:12,750 --> 00:03:16,260 So, the mechanism that we use to disallow this behavior, 75 00:03:16,260 --> 00:03:18,150 and this is just one mechanism 76 00:03:18,150 --> 00:03:19,800 or one approach of many that we have 77 00:03:19,800 --> 00:03:22,200 to prevent this sort of exploit right here, 78 00:03:22,200 --> 00:03:26,190 are CORS requests or CORS restrictions. 79 00:03:26,190 --> 00:03:28,920 So, let's talk about how we can use a CORS request, 80 00:03:28,920 --> 00:03:30,210 or a CORS restriction, 81 00:03:30,210 --> 00:03:31,890 to make sure that someone cannot make 82 00:03:31,890 --> 00:03:35,040 this malicious-site.com website 83 00:03:35,040 --> 00:03:37,410 and trick our users into making a request 84 00:03:37,410 --> 00:03:39,153 over to our backend API. 85 00:03:40,410 --> 00:03:43,140 Okay, so here's what happens behind the scenes. 86 00:03:43,140 --> 00:03:45,060 Let's imagine that a user has been tricked 87 00:03:45,060 --> 00:03:48,060 into going to malicious-site.com. 88 00:03:48,060 --> 00:03:51,690 Some JavaScript code loads up inside that browser, 89 00:03:51,690 --> 00:03:55,533 and it tries to make a request over to my-bank.com. 90 00:03:56,400 --> 00:03:57,510 Now, our browser, 91 00:03:57,510 --> 00:04:00,000 or your user's browser to be more precise, 92 00:04:00,000 --> 00:04:01,140 is going to see 93 00:04:01,140 --> 00:04:04,320 that specifically some JavaScript code 94 00:04:04,320 --> 00:04:08,640 has tried to initiate a request to a different domain 95 00:04:08,640 --> 00:04:11,430 than what the browser is currently at. 96 00:04:11,430 --> 00:04:12,263 So right now, 97 00:04:12,263 --> 00:04:17,089 this browser window is at the address of malicious-site.com. 98 00:04:18,480 --> 00:04:21,269 Because this JavaScript code is trying to issue 99 00:04:21,269 --> 00:04:24,330 a request over to our backend bank API, 100 00:04:24,330 --> 00:04:27,240 which is hosted at a completely different domain, 101 00:04:27,240 --> 00:04:29,283 so my-bank.com. 102 00:04:30,150 --> 00:04:32,430 Our browser is gonna get suspicious. 103 00:04:32,430 --> 00:04:34,890 The browser is gonna say, "You know what? 104 00:04:34,890 --> 00:04:36,240 Something seems off here. 105 00:04:36,240 --> 00:04:38,040 We're at this website, 106 00:04:38,040 --> 00:04:39,870 but you're trying to make a request 107 00:04:39,870 --> 00:04:42,390 over to this completely different website. 108 00:04:42,390 --> 00:04:45,090 Something about that seems a little bit off." 109 00:04:45,090 --> 00:04:47,190 So again, really important right here to understand 110 00:04:47,190 --> 00:04:49,590 that this is our browser, specifically, 111 00:04:49,590 --> 00:04:51,960 that is implementing the security rule. 112 00:04:51,960 --> 00:04:52,800 The security rule, 113 00:04:52,800 --> 00:04:55,290 and the fact that the browser finds this suspicious, 114 00:04:55,290 --> 00:04:57,240 cannot be overridden. 115 00:04:57,240 --> 00:04:59,790 It is hard-coded into your Chrome browser. 116 00:04:59,790 --> 00:05:02,490 It is hard-coded into Internet Explorer, Firefox, 117 00:05:02,490 --> 00:05:05,250 every other browser out there is hard-coded 118 00:05:05,250 --> 00:05:08,670 to think that this is suspicious behavior. 119 00:05:08,670 --> 00:05:10,717 So before, your browser says, 120 00:05:10,717 --> 00:05:13,500 "Okay, you know, I'll process the request." 121 00:05:13,500 --> 00:05:15,067 Your browser instead says, 122 00:05:15,067 --> 00:05:17,040 "You know what? This seems really fishy. 123 00:05:17,040 --> 00:05:18,210 I'm gonna follow up on this, 124 00:05:18,210 --> 00:05:21,060 I'm gonna see if something just feels off here. 125 00:05:21,060 --> 00:05:24,150 I wanna figure out what is going on with this request." 126 00:05:24,150 --> 00:05:25,620 So before your browser 127 00:05:25,620 --> 00:05:29,070 attempts to actually make that money transfer request, 128 00:05:29,070 --> 00:05:32,850 the browser itself is going to do an initial request 129 00:05:32,850 --> 00:05:35,010 over to our API. 130 00:05:35,010 --> 00:05:36,810 This is the browser talking right here. 131 00:05:36,810 --> 00:05:37,910 It's not our JavaScript code, 132 00:05:37,910 --> 00:05:40,537 it is the browser talking and it says, 133 00:05:40,537 --> 00:05:43,233 "Hey, API, banking API, 134 00:05:44,220 --> 00:05:46,320 I'm trying to make a request over to you, 135 00:05:46,320 --> 00:05:50,130 and the request is coming from a website 136 00:05:50,130 --> 00:05:52,770 at malicious-site.com." 137 00:05:52,770 --> 00:05:56,040 So, the browser specifically communicates to our backend API 138 00:05:56,040 --> 00:05:57,060 and says, "You know, 139 00:05:57,060 --> 00:05:58,560 I'm trying to make a request over to you, 140 00:05:58,560 --> 00:05:59,940 it seems strange. 141 00:05:59,940 --> 00:06:01,470 What do you think?" 142 00:06:01,470 --> 00:06:05,850 So then, our backend API has the option, 143 00:06:05,850 --> 00:06:09,270 it has the ability, to either allow the request 144 00:06:09,270 --> 00:06:10,953 or disallow the request. 145 00:06:12,360 --> 00:06:16,057 So, in this case, we might program our backend API to say, 146 00:06:16,057 --> 00:06:17,430 "Hey, you know what browser? 147 00:06:17,430 --> 00:06:19,440 I agree with you that does seem fishy, 148 00:06:19,440 --> 00:06:22,350 and you should really only allow that request 149 00:06:22,350 --> 00:06:26,370 if you're making it from my-bank.com." 150 00:06:26,370 --> 00:06:29,700 And so, the backend API's response 151 00:06:29,700 --> 00:06:31,560 goes back over to the browser, 152 00:06:31,560 --> 00:06:35,040 and the browser says back to our JavaScript code, 153 00:06:35,040 --> 00:06:36,600 it says, "Hey, you know what? 154 00:06:36,600 --> 00:06:38,160 I'm so sorry about this, 155 00:06:38,160 --> 00:06:40,470 but the server says that you cannot make a request 156 00:06:40,470 --> 00:06:43,710 over to them at my-bank.com 157 00:06:43,710 --> 00:06:46,350 while we, here inside the browser, 158 00:06:46,350 --> 00:06:48,600 are at malicious-site.com. 159 00:06:48,600 --> 00:06:50,370 That is seen as suspicious behavior, 160 00:06:50,370 --> 00:06:51,750 something is off there, 161 00:06:51,750 --> 00:06:53,220 and we're not gonna allow that to happen. 162 00:06:53,220 --> 00:06:55,350 So, I'm sorry JavaScript code, 163 00:06:55,350 --> 00:06:58,230 but we are not allowed to make that request." 164 00:06:58,230 --> 00:07:00,210 So, that is exactly what's happening 165 00:07:00,210 --> 00:07:02,613 inside of our application right now. 166 00:07:03,660 --> 00:07:07,890 Our browser is currently looking at localhost:3000. 167 00:07:07,890 --> 00:07:10,260 We have loaded up some JavaScript code 168 00:07:10,260 --> 00:07:14,250 that is trying to make a request to a different domain. 169 00:07:14,250 --> 00:07:15,420 Well, let's be precise here, 170 00:07:15,420 --> 00:07:16,860 I wanna clarify that. 171 00:07:16,860 --> 00:07:17,693 Just a second. 172 00:07:17,693 --> 00:07:19,920 In both cases, we are at local host, 173 00:07:19,920 --> 00:07:21,810 but the real comparison here, 174 00:07:21,810 --> 00:07:23,400 the browser is gonna look to see 175 00:07:23,400 --> 00:07:25,470 if there's a different sub-domain, 176 00:07:25,470 --> 00:07:28,770 a different domain, or a different port. 177 00:07:28,770 --> 00:07:30,330 If any of those things are different, 178 00:07:30,330 --> 00:07:32,610 then this CORS stuff starts to kick in. 179 00:07:32,610 --> 00:07:36,540 So in our case, we are at port 3000, 180 00:07:36,540 --> 00:07:40,290 and we're trying to make a request over to port 3090. 181 00:07:40,290 --> 00:07:41,850 And so our browser kicks in 182 00:07:41,850 --> 00:07:43,867 and the browser specifically says, 183 00:07:43,867 --> 00:07:46,470 "Something about this seems really off, 184 00:07:46,470 --> 00:07:48,990 something is not right here." 185 00:07:48,990 --> 00:07:51,780 So, the browser makes an initial request, 186 00:07:51,780 --> 00:07:54,750 referred to as the pre-flight request right here, 187 00:07:54,750 --> 00:07:57,240 and it asks our API, "Hey, you know what? 188 00:07:57,240 --> 00:07:58,543 We are over on port 3000. 189 00:07:58,543 --> 00:08:01,110 Is it okay if we make this request?" 190 00:08:01,110 --> 00:08:02,190 And by default, 191 00:08:02,190 --> 00:08:04,500 our express server is, by default, 192 00:08:04,500 --> 00:08:08,010 configured to disallow CORS requests. 193 00:08:08,010 --> 00:08:12,630 So, in response to our, excuse me, pre-flight request, 194 00:08:12,630 --> 00:08:15,817 our express API essentially says back in return, 195 00:08:15,817 --> 00:08:18,840 "You know, I'm so sorry, but you're on a different port. 196 00:08:18,840 --> 00:08:20,760 I don't know what you're doing over on that website, 197 00:08:20,760 --> 00:08:23,040 but definitely you can't make that request 198 00:08:23,040 --> 00:08:26,670 over from that different domain or that different port." 199 00:08:26,670 --> 00:08:28,117 And so our backend replies and says, 200 00:08:28,117 --> 00:08:30,270 "Sorry can't do it, can't allow it." 201 00:08:30,270 --> 00:08:32,616 And so, the browser in response says, 202 00:08:32,616 --> 00:08:34,950 "Because of that, I'm sorry JavaScript code, 203 00:08:34,950 --> 00:08:39,240 but the origin 3000 that you're at, looking at right now, 204 00:08:39,240 --> 00:08:44,240 is not allowed access to that API running on port 3090." 205 00:08:44,910 --> 00:08:46,230 Okay, so that is the summary. 206 00:08:46,230 --> 00:08:48,540 That is like we've spoken about the initial theory 207 00:08:48,540 --> 00:08:49,373 in this diagram 208 00:08:49,373 --> 00:08:50,670 and then we've kind of applied it 209 00:08:50,670 --> 00:08:52,950 over to our current running application. 210 00:08:52,950 --> 00:08:53,970 So, that gives you a better idea 211 00:08:53,970 --> 00:08:56,580 of why we're seeing this message. 212 00:08:56,580 --> 00:08:58,710 Now, just some things I really wanna harp on here, 213 00:08:58,710 --> 00:09:00,990 because this is some really important knowledge 214 00:09:00,990 --> 00:09:02,640 and I can almost guarantee you, 215 00:09:02,640 --> 00:09:03,570 I can almost promise you 216 00:09:03,570 --> 00:09:05,820 that some aspects of all this stuff, 217 00:09:05,820 --> 00:09:08,220 you might get asked at the job interview someday. 218 00:09:08,220 --> 00:09:10,470 And I say that specifically 'cause I know I have. 219 00:09:10,470 --> 00:09:12,780 So, some things I just really wanna clarify 220 00:09:12,780 --> 00:09:14,880 about this one more time. 221 00:09:14,880 --> 00:09:17,970 Again, the browser checks to see if the domain, 222 00:09:17,970 --> 00:09:20,910 the sub-domain, or the port are different 223 00:09:20,910 --> 00:09:23,340 when it makes a request over to this other API, 224 00:09:23,340 --> 00:09:26,460 running on a different sub-domain, domain, or port. 225 00:09:26,460 --> 00:09:28,080 If any of those things are different, 226 00:09:28,080 --> 00:09:30,150 then this CORS stuff kicks into play. 227 00:09:30,150 --> 00:09:32,610 That's step number one, that's important fact number one. 228 00:09:32,610 --> 00:09:33,840 Important fact number two, 229 00:09:33,840 --> 00:09:36,300 is to understand that this is specifically 230 00:09:36,300 --> 00:09:39,900 a browser implemented security precaution. 231 00:09:39,900 --> 00:09:42,000 So, it's solely the fact 232 00:09:42,000 --> 00:09:43,140 that we are trying to execute 233 00:09:43,140 --> 00:09:45,960 some JavaScript code inside of our browser, 234 00:09:45,960 --> 00:09:47,640 that this CORS stuff kicks in. 235 00:09:47,640 --> 00:09:50,190 And it is specifically the browser 236 00:09:50,190 --> 00:09:53,220 that is making this limitation, or making this restriction. 237 00:09:53,220 --> 00:09:54,870 That's why you probably see online, 238 00:09:54,870 --> 00:09:57,120 if you go look at a lot of Stack Overflow posts, 239 00:09:57,120 --> 00:09:58,747 you will see a lot of people saying like, 240 00:09:58,747 --> 00:10:00,360 "How do I circumvent this error?" 241 00:10:00,360 --> 00:10:02,280 You'll see people saying, "How do I get around this? 242 00:10:02,280 --> 00:10:05,040 How do I make the browser just allow this request?" 243 00:10:05,040 --> 00:10:06,750 And the answer is, you can't. 244 00:10:06,750 --> 00:10:09,570 The entire idea behind these CORS restrictions, 245 00:10:09,570 --> 00:10:12,240 are to keep developers, from you and I, 246 00:10:12,240 --> 00:10:14,550 from trying to make nasty requests 247 00:10:14,550 --> 00:10:18,030 over to some backend API that we don't control. 248 00:10:18,030 --> 00:10:20,250 So, it is specifically your browser 249 00:10:20,250 --> 00:10:22,440 that is doing the security check. 250 00:10:22,440 --> 00:10:23,610 The reason that's so important, 251 00:10:23,610 --> 00:10:24,720 is that it also explains 252 00:10:24,720 --> 00:10:28,170 why you and I were able to make requests from Postman 253 00:10:28,170 --> 00:10:31,110 when we were putting together our server. 254 00:10:31,110 --> 00:10:32,940 When you make a request from Postman, 255 00:10:32,940 --> 00:10:35,640 Postman says, "Hey, you know what? I don't care. 256 00:10:35,640 --> 00:10:37,200 I don't care if you try to make a request 257 00:10:37,200 --> 00:10:38,490 to this different API. 258 00:10:38,490 --> 00:10:40,020 I'm not really the browser 259 00:10:40,020 --> 00:10:42,900 and you can do anything you want." 260 00:10:42,900 --> 00:10:45,270 So API clients like Postman, 261 00:10:45,270 --> 00:10:47,460 or if you're running curl at the terminal, 262 00:10:47,460 --> 00:10:50,220 they do not have this CORS stuff implemented. 263 00:10:50,220 --> 00:10:52,173 So they don't care about this stuff. 264 00:10:53,430 --> 00:10:55,170 It's specifically your browser 265 00:10:55,170 --> 00:10:58,110 that tries to implement this security stuff, 266 00:10:58,110 --> 00:11:01,050 solely on behalf of your users, 267 00:11:01,050 --> 00:11:02,880 who probably have no idea 268 00:11:02,880 --> 00:11:05,133 what web security is in the first place. 269 00:11:06,570 --> 00:11:09,810 Alright, so that's it, that's my spiel on CORS. 270 00:11:09,810 --> 00:11:12,900 So, now that we've got a better idea of what's going on, 271 00:11:12,900 --> 00:11:14,250 we're gonna continue the next section 272 00:11:14,250 --> 00:11:15,120 and we'll talk about 273 00:11:15,120 --> 00:11:17,520 how we're going to solve this whole big issue. 274 00:11:17,520 --> 00:11:20,853 So quick, quake and I will see you in just a minute.