Giới thiệu nhanh về bảo mật web

Tài liệu sơ lược của nhà phát triển web về CORS, CSP, HSTS và tất cả các từ viết tắt bảo mật web!

Có nhiều lý do để tìm hiểu về bảo mật web, chẳng hạn như:

  • Bạn là người dùng quan tâm lo lắng về việc dữ liệu cá nhân của mình bị rò rỉ
  • Bạn là một nhà phát triển web quan tâm đến người muốn làm cho các ứng dụng web của họ an toàn hơn
  • Bạn là nhà phát triển web đang nộp đơn xin việc và bạn muốn sẵn sàng nếu người phỏng vấn hỏi bạn câu hỏi về bảo mật web

và như thế.

Bài viết này sẽ giải thích một số từ viết tắt phổ biến về bảo mật web theo cách dễ hiểu nhưng vẫn chính xác.

Trước khi làm điều đó, hãy đảm bảo rằng chúng ta hiểu một vài khái niệm cốt lõi về bảo mật.

Hai khái niệm cốt lõi về bảo mật

Không ai an toàn 100%.

Không có khái niệm được bảo vệ 100% khỏi bị tấn công. Nếu ai đó từng nói với bạn điều đó, họ đã sai.

Một lớp bảo vệ là không đủ.

Bạn không thể chỉ nói…

Ồ, vì tôi đã triển khai CSP nên tôi an toàn. Tôi có thể loại bỏ kịch bản chéo trang web khỏi danh sách lỗ hổng bảo mật của mình vì điều đó không thể xảy ra bây giờ.

Có thể đó là điều được ban cho một số người, nhưng bạn rất dễ nhận ra mình đang suy nghĩ theo cách này. Tôi nghĩ một lý do mà các lập trình viên có thể dễ dàng nhận ra mình nghĩ theo cách này là bởi vì quá nhiều mã hóa là đen trắng, 0 hoặc 1, đúng hoặc sai. Bảo mật không đơn giản như vậy.

Chúng tôi sẽ bắt đầu với một cái mà mọi người đều gặp khá sớm trong hành trình phát triển web của họ. Và sau đó, bạn nhìn vào StackOverflow và tìm thấy một loạt câu trả lời cho bạn biết cách vượt qua nó.

Chia sẻ tài nguyên đa nguồn gốc (CORS)

Bạn đã bao giờ gặp lỗi trông giống như thế này chưa?

No 'Access-Control-Allow-Origin' header is present on the requested resource. Origin 'null' is therefore not allowed access.

Bạn chắc chắn không phải một mình. Và sau đó bạn Google nó, và một người nào đó nói với bạn rằng hãy tải tiện ích mở rộng này sẽ làm cho mọi vấn đề của bạn biến mất!

Tuyệt vời, phải không?

CORS ở đó để bảo vệ bạn, không làm tổn thương bạn!

Để giải thích CORS giúp bạn như thế nào, trước tiên hãy nói về cookie, cụ thể là cookie xác thực . Cookie xác thực được sử dụng để thông báo cho máy chủ biết rằng bạn đã đăng nhập và chúng sẽ tự động được gửi với bất kỳ yêu cầu nào bạn thực hiện với máy chủ đó.

Giả sử bạn đã đăng nhập vào Facebook và họ sử dụng cookie xác thực. Bạn nhấp vào bit.ly/r43nugichuyển hướng bạn đến superevilwebsite.rocks. Một tập lệnh bên trong superevilwebsite.rocksthực hiện một yêu cầu phía máy khách facebook.comgửi cookie xác thực của bạn đến đó!

Trong một thế giới không có CORS, họ có thể thực hiện các thay đổi đối với tài khoản của bạn mà bạn không hề biết. Tất nhiên, cho đến khi họ đăng bit.ly/r43nugitrên dòng thời gian của bạn và tất cả bạn bè của bạn nhấp vào đó, sau đó họ đăng bit.ly/r43nugilên dòng thời gian của tất cả bạn bè của bạn và sau đó chu kỳ tiếp tục theo một kế hoạch đầu tiên độc ác chinh phục tất cả người dùng của Facebook, và thế giới được tiêu thụ bởi superevilwebsite.rocks. ?

Tuy nhiên, trong thế giới CORS, Facebook sẽ chỉ cho phép các yêu cầu có nguồn gốc là facebook.comchỉnh sửa dữ liệu trên máy chủ của họ. Nói cách khác, họ sẽ hạn chế việc chia sẻ tài nguyên có nguồn gốc chéo. Sau đó, bạn có thể hỏi…

Có thể superevilwebsite.rocks chỉ thay đổi tiêu đề nguồn gốc theo yêu cầu của họ, để có vẻ như nó đến từ facebook.com không?

Họ có thể thử, nhưng nó sẽ không hoạt động vì trình duyệt sẽ bỏ qua nó và sử dụng nguồn gốc thực sự.

Ok, nhưng điều gì sẽ xảy ra nếu superevilwebsite.rocks thực hiện yêu cầu phía máy chủ?

Trong trường hợp này, họ có thể bỏ qua CORS, nhưng họ sẽ không giành chiến thắng vì họ sẽ không thể gửi cookie xác thực của bạn trong suốt chuyến đi. Tập lệnh sẽ cần thực thi ở phía máy khách để có quyền truy cập vào cookie phía máy khách của bạn.

Chính sách bảo mật nội dung (CSP)

Để hiểu CSP, trước tiên chúng ta cần nói về một trong những lỗ hổng phổ biến nhất trên web: XSS, viết tắt của cross-site scripting (yay - một từ viết tắt khác).

XSS là khi kẻ xấu nào đó đưa JavaScript vào mã phía máy khách của bạn. Bạn có thể nghĩ…

Họ định làm gì vậy? Thay đổi màu từ đỏ sang xanh?

Giả sử rằng ai đó đã chèn thành công JavaScript vào mã phía máy khách của trang web bạn đang truy cập.

Họ có thể làm gì mà có hại?

  • Họ có thể thực hiện các yêu cầu HTTP đến một trang web khác giả vờ là bạn.
  • Họ có thể thêm một thẻ liên kết đưa bạn đến một trang web trông giống hệt với trang bạn đang truy cập với một số đặc điểm hơi khác biệt, độc hại.
  • Họ có thể thêm một thẻ script với JavaScript nội tuyến.
  • Họ có thể thêm một thẻ script tìm nạp một tệp JavaScript từ xa ở đâu đó.
  • Họ có thể thêm iframe bao phủ trang và trông giống như một phần của trang web nhắc bạn nhập mật khẩu của mình.

Khả năng là vô tận.

CSP cố gắng ngăn điều này xảy ra bằng cách hạn chế:

  • những gì có thể được mở trong iframe
  • những bảng định kiểu nào có thể được tải
  • nơi có thể thực hiện các yêu cầu, v.v.

Vì vậy, làm thế nào nó hoạt động?

Khi bạn nhấp vào liên kết hoặc nhập URL trang web vào thanh địa chỉ của trình duyệt, trình duyệt của bạn sẽ đưa ra yêu cầu GET. Cuối cùng nó cũng đi đến một máy chủ phục vụ HTML cùng với một số tiêu đề HTTP. Nếu bạn tò mò về những tiêu đề bạn nhận được, hãy mở tab Mạng trong bảng điều khiển của bạn và truy cập một số trang web.

Bạn có thể thấy một tiêu đề phản hồi giống như sau:

content-security-policy: default-src * data: blob:;script-src *.facebook.com *.fbcdn.net *.facebook.net *.google-analytics.com *.virtualearth.net *.google.com 127.0.0.1:* *.spotilocal.com:* 'unsafe-inline' 'unsafe-eval' *.atlassolutions.com blob: data: 'self';style-src data: blob: 'unsafe-inline' *;connect-src *.facebook.com facebook.com *.fbcdn.net *.facebook.net *.spotilocal.com:* wss://*.facebook.com:* //fb.scanandcleanlocal.com:* *.atlassolutions.com attachment.fbsbx.com ws://localhost:* blob: *.cdninstagram.com 'self' chrome-extension://boadgeojelhgndaghljhdicfkmllpafd chrome-extension://dliochdbjfkdbacpmhlcpmleaejidimm;

Đó là chính sách bảo mật nội dung của facebook.com. Hãy định dạng lại nó để dễ đọc hơn:

content-security-policy: default-src * data: blob:; script-src *.facebook.com *.fbcdn.net *.facebook.net *.google-analytics.com *.virtualearth.net *.google.com 127.0.0.1:* *.spotilocal.com:* 'unsafe-inline' 'unsafe-eval' *.atlassolutions.com blob: data: 'self'; style-src data: blob: 'unsafe-inline' *; connect-src *.facebook.com facebook.com *.fbcdn.net *.facebook.net *.spotilocal.com:* wss://*.facebook.com:* //fb.scanandcleanlocal.com:* *.atlassolutions.com attachment.fbsbx.com ws://localhost:* blob: *.cdninstagram.com 'self' chrome-extension://boadgeojelhgndaghljhdicfkmllpafd chrome-extension://dliochdbjfkdbacpmhlcpmleaejidimm;

Bây giờ, hãy chia nhỏ các chỉ thị.

  • default-src hạn chế tất cả các chỉ thị CSP khác không được liệt kê rõ ràng.
  • script-srchạn chế các tập lệnh có thể được tải.
  • style-src hạn chế các bảng định kiểu có thể được tải.
  • connect-src hạn chế các URL có thể được tải bằng giao diện tập lệnh, vì vậy hãy tìm nạp, XHR, ajax, v.v.

Lưu ý rằng có nhiều chỉ thị CSP hơn chỉ bốn chỉ thị được hiển thị ở trên. Trình duyệt sẽ đọc tiêu đề CSP và áp dụng các chỉ thị đó cho mọi thứ trong tệp HTML đã được phân phát. Nếu các chỉ thị được thiết lập thích hợp, chúng chỉ cho phép những gì cần thiết.

Nếu không có tiêu đề CSP nào thì mọi thứ sẽ diễn ra và không có gì bị hạn chế. Ở mọi nơi bạn thấy *, đó là một ký tự đại diện. Bạn có thể tưởng tượng thay thế *bằng bất cứ thứ gì và nó sẽ được phép.

HTTPS hoặc HTTP Secure

Chắc chắn bạn đã nghe nói về HTTPS. Có thể bạn đã nghe một số người nói…

Tại sao tôi quan tâm đến việc sử dụng HTTPS nếu tôi chỉ đang ở trên một trang web chơi trò chơi.

Hoặc có thể bạn đã nghe thấy phía bên kia…

Bạn thật điên rồ nếu trang web của bạn không có HTTPS. Đó là năm 2018! Đừng tin bất cứ ai nói khác.

Có thể bạn đã nghe nói rằng Chrome hiện sẽ đánh dấu trang web của bạn là không an toàn nếu nó không phải là HTTPS.

Về cốt lõi, HTTPS khá đơn giản. HTTPS được mã hóa còn HTTP thì không.

Vậy tại sao điều này lại xảy ra nếu bạn không gửi dữ liệu nhạy cảm?

Hãy sẵn sàng cho một từ viết tắt khác… MITM, viết tắt của Man in the Middle.

Nếu bạn đang sử dụng Wi-Fi công cộng không có mật khẩu tại một quán cà phê, rất dễ dàng để ai đó hoạt động giống như bộ định tuyến của bạn, để mọi yêu cầu và phản hồi đều được thực hiện. Nếu dữ liệu của bạn không được mã hóa, thì họ có thể làm bất cứ điều gì họ muốn với nó. Họ có thể chỉnh sửa HTML, CSS hoặc JavaScript trước khi nó được đưa vào trình duyệt của bạn. Với những gì chúng ta biết về XSS, bạn có thể tưởng tượng điều này có thể tồi tệ như thế nào.

Ok, nhưng làm thế nào mà máy tính của tôi và máy chủ biết cách mã hóa / giải mã nhưng MITM này thì không?

That’s where SSL (Secure Sockets Layer) and more recently, TLS (Transport Layer Security) come in. TLS took over for SSL in 1999 as the encryption technology used within HTTPS. Exactly how TLS works is outside of the scope of this post.

HTTP Strict-Transport-Security (HSTS)

This one is pretty straightforward. Let’s use Facebook’s header as an example again:

strict-transport-security: max-age=15552000; preload
  • max-age specifies how long a browser should remember to force the user to access a website using HTTPS.
  • preload is not important for our purposes. It is a service hosted by Google and not part of the HSTS specification.

This header only applies if you accessed the site using HTTPS. If you accessed the site via HTTP, the header is ignored. The reason is that, quite simply, HTTP is so insecure that it can’t be trusted.

Let’s use the Facebook example to further illustrate how this is helpful in practice. You are accessing facebook.com for the first time, and you know HTTPS is safer than HTTP, so you access it over HTTPS, //facebook.com. When your browser receives the HTML, it receives the header above which tells your browser to force-redirect you to HTTPS for future requests. One month later, someone sends you a link to Facebook using HTTP, //facebook.com, and you click on it. Since one month is less than the 15552000 seconds specified by the max-age directive, your browser will send the request as HTTPS, preventing a potential MITM attack.

Closing Thoughts

Bảo mật web rất quan trọng cho dù bạn đang ở đâu trong hành trình phát triển web của mình. Bạn càng tiếp xúc nhiều với nó, bạn sẽ càng trở nên tốt hơn. Bảo mật là thứ cần quan trọng đối với tất cả mọi người, không chỉ những người có nó rõ ràng trong chức danh công việc của họ! ?