CSRF คืออะไร

CSRF หรือการปลอมแปลงทรัพยากรข้ามไซต์เป็นช่องโหว่ที่ใช้ประโยชน์จากโทเค็นเซสชันของผู้ใช้เมื่อพวกเขาเข้าสู่ระบบแอปพลิเคชันโดยที่ผู้ใช้ไม่รู้จักและดำเนินการในนามของพวกเขา

กล่าวอีกนัยหนึ่ง โดยทั่วไปเพื่อให้ผู้ใช้สามารถเข้าถึงและแก้ไขทรัพยากรของตนได้ แอปพลิเคชันจะสร้างโทเค็นให้พวกเขาระหว่างการเข้าสู่ระบบและบันทึกไว้ในที่เก็บข้อมูลของเบราว์เซอร์ โทเค็นนี้ใช้เพื่ออนุญาตคำขอของผู้ใช้ไปยังเซิร์ฟเวอร์เพื่อดึงหรือแก้ไขข้อมูลที่แอปพลิเคชันอนุญาตให้พวกเขาเข้าถึง

คอร์ส

ในอดีตเบราว์เซอร์เป็นไปตามนโยบายที่มีต้นกำเนิดเดียวกันซึ่งเป็นแนวคิดด้านความปลอดภัยที่เว็บเบราว์เซอร์อนุญาตให้สคริปต์ที่อยู่ในหน้าเว็บแรกเข้าถึงข้อมูลในหน้าเว็บที่สองได้ แต่เฉพาะในกรณีที่ทั้งสองหน้าเว็บมีต้นกำเนิดเดียวกัน - หมายความว่ามีที่มาที่เหมือนกัน โปรโตคอล ชื่อโฮสต์ และหมายเลขพอร์ต

แต่เมื่อเว็บเติบโตขึ้นและกลายเป็นนโยบายที่มีต้นกำเนิดเดียวกันที่เกี่ยวพันกันมากขึ้นอีกเล็กน้อย กลับกลายเป็นว่ามีการจำกัดมากเกินไป เนื่องจากเว็บไซต์ใช้เนื้อหาหรือทรัพยากรสำหรับ CSS หรือแบบอักษรจากไซต์ต่างๆ

ตามมาตรฐานแล้ว เว็บแอปสมัยใหม่จะแบ่งออกเป็นหน่วยต่างๆ ซึ่งทั้งหมดตอบสนองวัตถุประสงค์ของตนเอง โดยปกติแล้วจะมีเซิร์ฟเวอร์อย่างน้อย 2 เครื่องที่ทำงานอยู่ โดยเซิร์ฟเวอร์หนึ่งให้บริการบิตที่ผู้ใช้โต้ตอบด้วย และเซิร์ฟเวอร์ที่สองซึ่งแลกเปลี่ยนข้อมูลเกี่ยวกับสถานะปัจจุบันของฐานข้อมูลกับโลก และแต่ละเซิร์ฟเวอร์มีต้นกำเนิดของตัวเอง

ตอนนี้ เนื่องจากฉันเป็นแฮกเกอร์ที่ชั่วร้ายและมีศักยภาพในการเข้าถึงโทเค็นการอนุญาตของผู้ใช้สำหรับทรัพยากรที่สำคัญมาก (เช่น - ธนาคาร) ฉันสามารถเปลี่ยนสถานะของข้อมูลผู้ใช้นั้นของทรัพยากรนั้นผ่านความชั่วร้ายของฉันเอง เว็บไซต์.

มีการปฏิบัติอย่างไร?

สมมติว่าฉันมีเว็บไซต์ที่อนุญาตให้ผู้ใช้ที่ได้รับการรับรองความถูกต้องสามารถโพสต์ความคิดเห็นในหัวข้อที่เลือกสรรมาอย่างดี
แบ็กเอนด์ของแอปของฉันทำงานบน url “api-of-opinions-about-very-important-things.com” และส่วนหน้าทำงานบนเซิร์ฟเวอร์อื่นด้วย url “opinions.com”

เมื่อผู้ใช้โพสต์ความคิดเห็นบนเว็บไซต์ของฉัน ความคิดเห็นนั้นจะถูกส่งไปยังแบ็กเอนด์เป็นคำขอ POST พร้อมด้วยเพย์โหลดของรหัสผู้ใช้ ความคิดเห็น และรหัสหัวข้อ และได้รับอนุญาตด้วยโทเค็นจากที่เก็บข้อมูลของเบราว์เซอร์

หากผู้ใช้รายนั้นเข้าสู่เว็บไซต์อื่นซึ่งส่งคำขอเดียวกันพร้อมความคิดเห็นที่ชั่วร้ายไปยังแบ็กเอนด์ ผู้ใช้จะได้รับอนุญาตและดูเหมือนว่าผู้ใช้ได้โพสต์ความคิดเห็นนั้น

ในตัวอย่างของฉัน ฉันไม่มีแบบฟอร์มแต่มีอินพุตและปุ่ม เมื่อคำขอถูกส่ง คุณสามารถดูเพย์โหลดคำขอไปยังเซิร์ฟเวอร์จากเครื่องมือ/เครือข่ายสำหรับนักพัฒนาเบราว์เซอร์ ซึ่งผู้โจมตีสามารถเลียนแบบในสคริปต์ที่เป็นอันตรายได้

หากเว็บไซต์ใช้แบบฟอร์มเพื่อส่งข้อมูล ก็เป็นไปได้ที่จะเห็นสิ่งที่ถูกส่งจากเครื่องมือ dev/เครือข่าย รับข้อมูลเชิงลึกเกี่ยวกับฐานข้อมูล คัดลอกแบบฟอร์มนั้นและส่งออกไปพร้อมกับอินพุตที่ผู้โจมตีชื่นชอบ

ตามตัวอย่าง ฉันเริ่มต้นเซิร์ฟเวอร์ของแหล่งกำเนิดอื่น (บนพอร์ตอื่นบน localhost) ด้วย create-react-app และเรียกใช้คำขอโพสต์ไปยังเซิร์ฟเวอร์แอปความคิดเห็นโดยใช้โทเค็นจาก localStorage เพื่อขออนุมัติ

โอเค เยี่ยมเลย วิธีนี้ได้ผล ความคิดเห็นแย่ๆ จบลงที่ไซต์ของฉัน แต่ไม่ใช่ด้วยเหตุผลที่ถูกต้อง

อย่างไรก็ตาม .. ขณะที่ฉันดูโค้ดส่วนหลังของฉัน ฉันสังเกตเห็นว่าตัวควบคุมความคิดเห็นไม่ได้ทำอะไรมากนักเกี่ยวกับการอนุญาต (นี่เป็นโปรเจ็กต์เก่า) จากนั้นฉันก็ออกจากระบบโทเค็นบน “เว็บไซต์ที่เป็นอันตราย” .. มันเป็นโมฆะ! เห็นได้ชัดว่าฉันมีบางอย่างผสมกันเกี่ยวกับ CSRF — ใช้งานได้กับคุกกี้เท่านั้น ใช้ JWT ! มันอาจจะยังปลอดภัยอยู่

ตกลง. มาเริ่มต้นใหม่อีกครั้ง CSRF ทำงานกับคุกกี้ และหากมีการบันทึกคุกกี้ คุณสามารถส่งแบบฟอร์มที่ซ่อนอยู่ซึ่งกรอกในเว็บไซต์ชั่วร้ายของคุณ โดยที่คุณล่อเหยื่อที่ไม่สงสัยโดยใช้วิศวกรรมสังคมที่ยอดเยี่ยม

อีกครั้ง แบบฟอร์มสามารถสร้างได้บนพื้นฐานของแบบฟอร์มจากเว็บไซต์ดั้งเดิม (สามารถซ่อนได้) กรอกข้อมูลใด ๆ และส่งเมื่อโหลดหน้าเว็บ เป็นไปได้มากว่าจะมีวิธีการโพสต์หรือลบ ฯลฯ ไม่ว่าผู้โจมตีจะรู้สึกถึงรสชาติของความชั่วร้ายก็ตาม

ประเด็นสำคัญก็คือ ด้วยการโจมตี CSRF แฮ็กเกอร์จะไม่สามารถเข้าถึงเพื่ออ่านข้อมูลผู้ใช้ของคุณ สิ่งที่พวกเขาทำได้คือแก้ไขข้อมูล และเนื่องจากสิ่งนี้เกิดขึ้นในเบราว์เซอร์ของผู้ใช้ จึงดูเหมือนว่าเป็นผู้ใช้ที่สร้าง เปลี่ยน.

ข้อดีอีกอย่างหนึ่ง — อย่าเปิดเผยรหัสผู้ใช้จริงให้เข้ารหัสด้วยวิธีใดวิธีหนึ่ง เพื่อไม่ให้ใครก็ตามสามารถส่งคำขอโดยใช้รหัสผู้ใช้ที่น่าจะเริ่มต้นจาก 1 ถึงอะไรก็ได้

จะป้องกันอย่างไร.

  1. ให้ผู้ใช้ตรวจสอบตนเองอีกครั้งด้วยรหัสผ่านก่อนส่งแบบฟอร์มออกไป
  2. กำหนดค่าการควบคุมการเข้าถึงอนุญาตส่วนหัวของ Origin

เมื่อไคลเอนต์ส่งคำขอไปยังต้นทางอื่นเพื่อรับข้อมูลบางส่วนกลับมา เบราว์เซอร์จะมีส่วนหัวของคำขอ Origin ซึ่งระบุแหล่งที่มาของข้อมูลที่คำขอนั้นมาจาก

สภาพอากาศหรือไม่ข้อมูลใดที่ถูกส่งกลับนั้นขึ้นอยู่กับเซิร์ฟเวอร์ ตัวอย่างเช่น โดยค่าเริ่มต้น เมื่อแบ็กเอนด์ Ruby ถูกสร้างขึ้นด้วย Rails ใหม่ — api, Rack ใน application.rb ได้รับการกำหนดค่าให้อนุญาตต้นกำเนิดทั้งหมดตามค่าเริ่มต้น หากเป็นกรณีนี้ เซิร์ฟเวอร์จะส่ง backAccess-Control-Allow-Origin: * ในส่วนหัวการตอบกลับและเนื้อหาการตอบกลับ หากในตัวอย่างที่เสียหายของฉันอนุญาตให้ใช้เฉพาะ 'opinion.com' เท่านั้น ฉันคงไม่สามารถแก้ไขอะไรจากไซต์ที่ถูกแฮ็กของฉันได้

อาจมีบางกรณีที่ส่วนหัว Origin ไม่ปรากฏ ในกรณีนี้ ให้ตรวจสอบส่วนหัวของผู้อ้างอิง หากไม่มีอยู่ OWASP แนะนำว่าอย่าปล่อยให้คำขอผ่าน

3. ทุกครั้งที่ส่งแบบฟอร์มหรือขอเปลี่ยนสถานะแอปพลิเคชัน ให้ส่งโทเค็นแต่ละรายการซึ่งเป็นตัวเลขสุ่มหรือสตริงอักขระที่สร้างโดยการเข้ารหัสลับเฉพาะสำหรับเซสชัน

เมื่อมีการออกคำขอโดยผู้ใช้ปลายทาง ส่วนประกอบฝั่งเซิร์ฟเวอร์จะต้องตรวจสอบการมีอยู่และความถูกต้องของโทเค็นในคำขอเมื่อเปรียบเทียบกับโทเค็นที่พบในเซสชัน

สิ่งที่ต้องทำ :
* JWT ทำงานอย่างไร
* เหตุใดโทเค็น localStorage จึงไม่ปรากฏในแท็บอื่นและมองเห็นคุกกี้ได้
* วิธีปกป้องรหัสผู้ใช้อย่างแท้จริง