Skip to content

Commit 4ac9bec

Browse files
committed
minor
1 parent 0e08048 commit 4ac9bec

File tree

6 files changed

+87
-128
lines changed

6 files changed

+87
-128
lines changed

5-network/05-fetch-crossorigin/1-do-we-need-origin/solution.md

+1-1
Original file line numberDiff line numberDiff line change
@@ -2,7 +2,7 @@ We need `Origin`, because sometimes `Referer` is absent. For instance, when we `
22

33
The [Content Security Policy](http://en.wikipedia.org/wiki/Content_Security_Policy) may forbid sending a `Referer`.
44

5-
As we'll see, `fetch` also has options that prevent sending the `Referer` and even allow to change it (within the same site).
5+
As we'll see, `fetch` has options that prevent sending the `Referer` and even allow to change it (within the same site).
66

77
By specification, `Referer` is an optional HTTP-header.
88

5-network/05-fetch-crossorigin/article.md

+34-38
Original file line numberDiff line numberDiff line change
@@ -135,7 +135,7 @@ If a request is cross-origin, the browser always adds `Origin` header to it.
135135

136136
For instance, if we request `https://anywhere.com/request` from `https://javascript.info/page`, the headers will be like:
137137

138-
```
138+
```http
139139
GET /request
140140
Host: anywhere.com
141141
*!*
@@ -155,7 +155,7 @@ The browser plays the role of a trusted mediator here:
155155
![](xhr-another-domain.svg)
156156

157157
Here's an example of a permissive server response:
158-
```
158+
```http
159159
200 OK
160160
Content-Type:text/html; charset=UTF-8
161161
*!*
@@ -186,7 +186,7 @@ To grant JavaScript access to any other response header, the server must send `
186186
187187
For example:
188188
189-
```
189+
```http
190190
200 OK
191191
Content-Type:text/html; charset=UTF-8
192192
Content-Length: 12345
@@ -209,8 +209,8 @@ So, to avoid misunderstandings, any "non-simple" request -- that couldn't be don
209209
210210
A preflight request uses method `OPTIONS`, no body and two headers:
211211
212-
- `Access-Control-Request-Method` header has the method of a non-simple request.
213-
- `Access-Control-Request-Headers` header provides a comma-separated list of non-simple HTTP-headers.
212+
- `Access-Control-Request-Method` header has the method of an the non-simple request.
213+
- `Access-Control-Request-Headers` header provides a comma-separated list of its non-simple HTTP-headers.
214214
215215
If the server agrees to serve the requests, then it should respond with empty body, status 200 and headers:
216216
@@ -234,14 +234,14 @@ let response = await fetch('https://site.com/service.json', {
234234
235235
There are three reasons why the request is not simple (one is enough):
236236
- Method `PATCH`
237-
- `Content-Type` is not one of: `application/x-www-form-urlencoded`, `multipart/form-data`, `text/plain`.
237+
- `Content-Type` is not one of: `application/x-www-form-urlencoded`, `multipart/form-data`, `text/plain`.
238238
- "Non-simple" `API-Key` header.
239239
240240
### Step 1 (preflight request)
241241
242-
Prior to sending our request, the browser, on its own, sends a preflight request that looks like this:
242+
Prior to sending such request, the browser, on its own, sends a preflight request that looks like this:
243243
244-
```
244+
```http
245245
OPTIONS /service.json
246246
Host: site.com
247247
Origin: https://javascript.info
@@ -264,26 +264,26 @@ The server should respond with status 200 and headers:
264264
265265
That allows future communication, otherwise an error is triggered.
266266
267-
If the server expects other methods and headers in the future, makes sense to allow them in advance by adding to the list:
267+
If the server expects other methods and headers in the future, it makes sense to allow them in advance by adding to the list:
268268
269-
```
269+
```http
270270
200 OK
271271
Access-Control-Allow-Methods: PUT,PATCH,DELETE
272272
Access-Control-Allow-Headers: API-Key,Content-Type,If-Modified-Since,Cache-Control
273273
Access-Control-Max-Age: 86400
274274
```
275275
276-
Now the browser can see that `PATCH` is in the list of allowed methods, and both headers are in the list too, so it sends out the main request.
276+
Now the browser can see that `PATCH` in `Access-Control-Allow-Methods` and `Content-Type,API-Key` are in the list `Access-Control-Allow-Headers`, so it sends out the main request.
277277
278-
Besides, the preflight response is cached for time, specified by `Access-Control-Max-Age` header (86400 seconds, one day), so subsequent requests will not cause a preflight. Assuming that they fit the allowances, they will be sent directly.
278+
Besides, the preflight response is cached for time, specified by `Access-Control-Max-Age` header (86400 seconds, one day), so subsequent requests will not cause a preflight. Assuming that they fit the cached allowances, they will be sent directly.
279279
280280
### Step 3 (actual request)
281281
282-
When the preflight is successful, the browser now makes the real request. Here the flow is the same as for simple requests.
282+
When the preflight is successful, the browser now makes the main request. The algorithm here is the same as for simple requests.
283283
284-
The real request has `Origin` header (because it's cross-origin):
284+
The main request has `Origin` header (because it's cross-origin):
285285
286-
```
286+
```http
287287
PATCH /service.json
288288
Host: site.com
289289
Content-Type: application/json
@@ -293,30 +293,35 @@ Origin: https://javascript.info
293293
294294
### Step 4 (actual response)
295295
296-
The server should not forget to add `Access-Control-Allow-Origin` to the response. A successful preflight does not relieve from that:
296+
The server should not forget to add `Access-Control-Allow-Origin` to the main response. A successful preflight does not relieve from that:
297297
298-
```
298+
```http
299299
Access-Control-Allow-Origin: https://javascript.info
300300
```
301301
302-
Now everything's correct. JavaScript is able to read the full response.
302+
Then JavaScript is able to read the main server response.
303303
304+
```smart
305+
Preflight request occurs "behind the scenes", it's invisible to JavaScript.
306+
307+
JavaScript only gets the response to the main request or an error if there's no server permission.
308+
```
304309
305310
## Credentials
306311
307312
A cross-origin request by default does not bring any credentials (cookies or HTTP authentication).
308313
309314
That's uncommon for HTTP-requests. Usually, a request to `http://site.com` is accompanied by all cookies from that domain. But cross-origin requests made by JavaScript methods are an exception.
310315
311-
For example, `fetch('http://another.com')` does not send any cookies, even those that belong to `another.com` domain.
316+
For example, `fetch('http://another.com')` does not send any cookies, even those (!) that belong to `another.com` domain.
312317
313318
Why?
314319
315-
That's because a request with credentials is much more powerful than an anonymous one. If allowed, it grants JavaScript the full power to act and access sensitive information on behalf of a user.
320+
That's because a request with credentials gives much more powerful than without them. If allowed, it grants JavaScript the full power to act on behalf of the user and access sensitive information using their credentials.
316321
317-
Does the server really trust pages from `Origin` that much? Then it must explicitly allow requests with credentials with an additional header.
322+
Does the server really trust the script that much? Then it must explicitly allow requests with credentials with an additional header.
318323
319-
To send credentials, we need to add the option `credentials: "include"`, like this:
324+
To send credentials in `fetch`, we need to add the option `credentials: "include"`, like this:
320325
321326
```js
322327
fetch('http://another.com', {
@@ -326,22 +331,21 @@ fetch('http://another.com', {
326331
327332
Now `fetch` sends cookies originating from `another.com` with out request to that site.
328333
329-
If the server wishes to accept the request with credentials, it should add a header `Access-Control-Allow-Credentials: true` to the response, in addition to `Access-Control-Allow-Origin`.
334+
If the server agrees to accept the request *with credentials*, it should add a header `Access-Control-Allow-Credentials: true` to the response, in addition to `Access-Control-Allow-Origin`.
330335
331336
For example:
332337
333-
```
338+
```http
334339
200 OK
335340
Access-Control-Allow-Origin: https://javascript.info
336341
Access-Control-Allow-Credentials: true
337342
```
338343
339-
Please note: `Access-Control-Allow-Origin` is prohibited from using a star `*` for requests with credentials. There must be exactly the origin there, like above. That's an additional safety measure, to ensure that the server really knows who it trusts.
340-
344+
Please note: `Access-Control-Allow-Origin` is prohibited from using a star `*` for requests with credentials. There must be exactly the origin there, like above. That's an additional safety measure, to ensure that the server really knows who it trusts to make such requests.
341345
342346
## Summary
343347
344-
Networking methods split cross-origin requests into two kinds: "simple" and all the others.
348+
From the browser point of view, there are to kinds of cross-origin requests: "simple" and all the others.
345349
346350
[Simple requests](http://www.w3.org/TR/cors/#terminology) must satisfy the following conditions:
347351
- Method: GET, POST or HEAD.
@@ -353,7 +357,7 @@ Networking methods split cross-origin requests into two kinds: "simple" and all
353357
354358
The essential difference is that simple requests were doable since ancient times using `<form>` or `<script>` tags, while non-simple were impossible for browsers for a long time.
355359
356-
So, practical difference is that simple requests are sent right away, with `Origin` header, but for other ones the browser makes a preliminary "preflight" request, asking for permission.
360+
So, the practical difference is that simple requests are sent right away, with `Origin` header, while for the other ones the browser makes a preliminary "preflight" request, asking for permission.
357361
358362
**For simple requests:**
359363
@@ -364,21 +368,13 @@ So, practical difference is that simple requests are sent right away, with `Orig
364368
- `Access-Control-Allow-Origin` to same value as `Origin`
365369
- `Access-Control-Allow-Credentials` to `true`
366370
367-
Additionally, if JavaScript wants to access non-simple response headers:
368-
- `Cache-Control`
369-
- `Content-Language`
370-
- `Content-Type`
371-
- `Expires`
372-
- `Last-Modified`
373-
- `Pragma`
374-
375-
...Then the server should list the allowed ones in `Access-Control-Expose-Headers` header.
371+
Additionally, to grant JavaScript access to any response headers except `Cache-Control`, `Content-Language`, `Content-Type`, `Expires`, `Last-Modified` or `Pragma`, the server should list the allowed ones in `Access-Control-Expose-Headers` header.
376372
377373
**For non-simple requests, a preliminary "preflight" request is issued before the requested one:**
378374
379375
- → The browser sends `OPTIONS` request to the same url, with headers:
380376
- `Access-Control-Request-Method` has requested method.
381-
- `Access-Control-Request-Headers` lists non-simple requested headers
377+
- `Access-Control-Request-Headers` lists non-simple requested headers.
382378
- ← The server should respond with status 200 and headers:
383379
- `Access-Control-Allow-Methods` with a list of allowed methods,
384380
- `Access-Control-Allow-Headers` with a list of allowed headers,

5-network/05-fetch-crossorigin/demo.view/index.html

-31
This file was deleted.

5-network/05-fetch-crossorigin/demo.view/server.js

-31
This file was deleted.

0 commit comments

Comments
 (0)