
วิธีเริ่มต้นใช้งาน VUE3.0 อย่างรวดเร็ว: เข้าสู่และเรียนรู้
Nest.js เป็นเฟรมเวิร์กแบ็คเอนด์ของ Nodejs โดยสรุปแพลตฟอร์ม Express และ http อื่นๆ เพื่อแก้ไขปัญหาทางสถาปัตยกรรม โดยมีคุณสมบัติ MVC, IOC, AOP และสถาปัตยกรรมอื่นๆ ที่ไม่มีใน Express ทำให้โค้ดง่ายต่อการบำรุงรักษาและขยาย
MVC, IOC และ AOP ที่นี่หมายถึงอะไร ลองดูแยกกัน:
MVC เป็นตัวย่อของ Model View Controller ภายใต้สถาปัตยกรรม MVC คำขอจะถูกส่งไปยังตัวควบคุมก่อน ซึ่งจะส่งบริการของเลเยอร์โมเดลเพื่อทำให้ตรรกะทางธุรกิจเสร็จสมบูรณ์ จากนั้นจึงส่งคืนมุมมองที่เกี่ยวข้อง

Nest.js จัดเตรียม @Controller มัณฑนากรเพื่อประกาศคอนโทรลเลอร์:

บริการจะถูกประกาศพร้อมกับมัณฑนากร @Injectable:

คลาสที่ประกาศผ่าน @Controller และ @Injectable ตกแต่งจะถูกสแกนโดย Nest.js อ็อบเจ็กต์ที่เกี่ยวข้องจะถูกสร้างขึ้นและเพิ่มลงในคอนเทนเนอร์ อ็อบเจ็กต์ทั้งหมดเหล่านี้จะถูกฉีดโดยอัตโนมัติตามการขึ้นต่อกันที่ประกาศในตัวสร้าง นั่นคือ DI (การขึ้นต่อกัน inject) ) แนวคิดนี้เรียกว่า IOC (Inverse Of Control)
ข้อดีของสถาปัตยกรรม IOC คือไม่จำเป็นต้องสร้างอ็อบเจ็กต์ด้วยตนเองและส่งต่อไปยังตัวสร้างของอ็อบเจ็กต์ต่างๆ ตามการขึ้นต่อกัน ทุกอย่างจะถูกสแกน สร้าง และฉีดโดยอัตโนมัติ
นอกจากนี้ Nest.js ยังให้ความสามารถของ AOP (Aspect Oriented Programming) ซึ่งเป็นความสามารถของการเขียนโปรแกรมเชิงแง่มุม:
AOP หมายถึงอะไร? การเขียนโปรแกรมเชิงแง่มุมคืออะไร?
คำขออาจใช้ตรรกะของตัวควบคุม บริการ และพื้นที่เก็บข้อมูล (การเข้าถึงฐานข้อมูล):

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

จุดขยายแนวนอนดังกล่าวเรียกว่าแง่มุม และวิธีการเขียนโปรแกรมที่เพิ่มตรรกะลักษณะบางอย่างอย่างโปร่งใสเรียกว่า AOP (การเขียนโปรแกรมเชิงลักษณะ)
ข้อดีของ AOP คือสามารถแยกตรรกะทั่วไปบางส่วนออกเป็นส่วนๆ และทำให้ตรรกะทางธุรกิจบริสุทธิ์ได้ ด้วยวิธีนี้ ตรรกะด้านสามารถนำกลับมาใช้ใหม่และเพิ่มและลบแบบไดนามิกได้
ที่จริงแล้ว โมเดลหัวหอมของมิดเดิลแวร์ของ Express ก็เป็นการใช้งานเช่นกัน ของ AOP เพราะคุณสามารถพันเลเยอร์ด้านนอกอย่างโปร่งใสและเพิ่มตรรกะบางอย่างได้ และเลเยอร์ด้านในจะไม่สามารถรับรู้ได้
Nest.js มีวิธีอื่นๆ ในการใช้ AOP โดยมีทั้งหมดห้าวิธี รวมถึง Middleware, Guard, Pipe, Inteceptor, ExceptionFilter:,
Nest.js ทำงานบน Express และสามารถใช้มิดเดิลแวร์ได้ตามปกติ แต่จะถูกแบ่งย่อยออกไปอีก แบ่งออกเป็นมิดเดิลแวร์ส่วนกลางและมิดเดิลแวร์การกำหนดเส้นทาง:
มิดเดิลแวร์ส่วนกลางคือมิดเดิลแวร์ของ Express

มิดเดิลแวร์การกำหนดเส้นทางมีไว้สำหรับเส้นทางบางเส้นทาง โดยมีขอบเขตที่เล็กกว่า:

แนวคิดนี้สืบทอด Express โดยตรงและเข้าใจง่ายกว่า
มาดูแนวคิดเพิ่มเติมของ Nest.js กัน เช่น Guard:
Guard หมายถึงตัวป้องกันการกำหนดเส้นทาง ซึ่งสามารถใช้เพื่อกำหนดสิทธิ์ก่อนเรียกใช้ Controller และส่งคืนค่าจริงหรือเท็จเพื่อตัดสินใจว่าจะปล่อยหรือไม่:

วิธีสร้าง Guard มีดังนี้:

Guard จำเป็นต้องใช้อินเทอร์เฟซ CanActivate และวิธีการ canActive โดยสามารถรับข้อมูลที่ร้องขอจากบริบท จากนั้นทำการตรวจสอบสิทธิ์และการประมวลผลอื่น ๆ ก่อนที่จะส่งคืนจริงหรือเท็จ
เพิ่มลงในคอนเทนเนอร์ IOC ผ่าน @Injectable มัณฑนากร จากนั้นเปิดใช้งานในคอนโทรลเลอร์:

ไม่จำเป็นต้องแก้ไขตัวควบคุม แต่เพิ่มตรรกะของการตัดสินสิทธิ์อย่างโปร่งใส นี่คือประโยชน์ของสถาปัตยกรรม AOP
และเช่นเดียวกับที่ Middleware รองรับระดับสากลและระดับเส้นทาง Guard ก็สามารถเปิดใช้งานได้ทั่วโลกเช่นกัน:

Guard สามารถสรุปตรรกะการควบคุมการเข้าถึงของการกำหนดเส้นทางได้ แต่ไม่สามารถแก้ไขคำขอและการตอบกลับได้ ตรรกะนี้สามารถใช้ Interceptor ได้:
Interceptor หมายถึง interceptor คุณสามารถเพิ่มตรรกะบางอย่างก่อนและหลังวิธีการควบคุมเป้าหมาย:

วิธีสร้าง Inteceptor มีดังนี้:

Interceptor จำเป็นต้องใช้อินเทอร์เฟซ NestInterceptor และวิธีการสกัดกั้น การเรียก next.handle() จะเรียกตัวควบคุมเป้าหมาย คุณสามารถเพิ่มตรรกะการประมวลผลบางส่วนก่อนและหลังได้
ตรรกะการประมวลผลก่อนและหลังคอนโทรลเลอร์อาจไม่ตรงกัน Nest.js จัดระเบียบผ่าน rxjs ดังนั้นคุณจึงใช้ตัวดำเนินการ rxjs ได้หลากหลาย
Interceptor รองรับแต่ละเส้นทางที่เปิดใช้งานแยกกัน ซึ่งจะมีผลกับคอนโทรลเลอร์บางตัวเท่านั้น และยังรองรับการเปิดใช้งานทั่วโลก ซึ่งส่งผลต่อคอนโทรลเลอร์ทั้งหมด:


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

วิธีสร้างท่อมีดังนี้:

ไปป์จำเป็นต้องใช้อินเทอร์เฟซ PipeTransform และวิธีการแปลง ซึ่งสามารถทำการตรวจสอบพารามิเตอร์กับค่าพารามิเตอร์ที่เข้ามาได้ เช่น รูปแบบและประเภทนั้นถูกต้องหรือไม่ จะมีข้อยกเว้นเกิดขึ้น คุณยังสามารถทำการแปลงและส่งกลับมูลค่าที่แปลงแล้วได้
มี Pipes ในตัว 8 แบบ และความหมายสามารถเห็นได้จากชื่อ:
ValidationPipeParseIntPipeParseBoolPipeParseArrayPipeParseUUIDPipeDefaultValuePipeParseEnumPipeParseFloatPipeในทำนองเดียวกัน Pipe สามารถมีผลกับเส้นทางที่แน่นอนเท่านั้น หรืออาจมีผลกับทุกเส้นทาง:


ไม่ว่าจะเป็น Pipe, Guard, Interceptor หรือ Controller ที่ถูกเรียกในที่สุด ข้อยกเว้นบางอย่างสามารถเกิดขึ้นได้ในระหว่างกระบวนการ จะตอบสนองต่อข้อยกเว้นบางอย่างได้อย่างไร
การแมปข้อยกเว้นกับการตอบกลับนี้เป็นตรรกะทั่วไป Nest.js จัดให้มี ExceptionFilter เพื่อรองรับ:
ExceptionFilter สามารถจัดการข้อยกเว้นที่ส่งออกมาและส่งคืนการตอบกลับที่เกี่ยวข้อง:

รูปแบบการสร้าง ExceptionFilter มีดังนี้:

ขั้นแรก คุณต้องใช้อินเทอร์เฟซ ExceptionFilter และวิธีการ catch เพื่อสกัดกั้นข้อยกเว้น อย่างไรก็ตาม ข้อยกเว้นใดที่คุณต้องการสกัดกั้นจำเป็นต้องได้รับการประกาศด้วย @Catch มัณฑนากร หลังจากสกัดกั้นข้อยกเว้นแล้ว คุณสามารถตอบกลับด้วยข้อยกเว้นที่เกี่ยวข้องเพื่อให้ ผู้ใช้พร้อมท์ที่เป็นมิตรมากขึ้น
แน่นอนว่าไม่ใช่ข้อยกเว้นทั้งหมดที่จะได้รับการจัดการ เฉพาะข้อยกเว้นที่สืบทอด HttpException เท่านั้นที่จะได้รับการจัดการโดย ExceptionFilter Nest.js มีคลาสย่อยในตัวจำนวนมากของ HttpException:
BadRequestExceptionUnauthorizedExceptionNotFoundExceptionForbiddenExceptionNotAcceptableExceptionRequestTimeoutExceptionConflictExceptionGoneExceptionPayloadTooLargeExceptionUnsupportedMediaTypeExceptionUnprocessableExceptionInternalServerErrorExceptionNotImplementedExceptionBadGatewayExceptionServiceUnavailableExceptionGatewayTimeoutExceptionแน่นอน คุณสามารถขยายได้ด้วยตัวเอง:

Nest.js ตระหนักถึงความสอดคล้องระหว่างข้อยกเว้นและการตอบกลับในลักษณะนี้ ตราบใดที่ HttpExceptions ที่แตกต่างกันถูกโยนลงไปในโค้ด การตอบกลับที่เกี่ยวข้องจะถูกส่งกลับ ซึ่งสะดวกมาก
ในทำนองเดียวกัน ExceptionFilter ยังสามารถเลือกที่จะมีผลทั่วโลกหรือมีผลกับบางเส้นทาง:
บางเส้นทาง:

ทั่วโลก:

เราเข้าใจกลไก AOP ที่จัดทำโดย Nest.js แต่ความสัมพันธ์ในการสั่งซื้อของพวกเขาคืออะไร
Middleware, Guard, Pipe, Interceptor และ ExceptionFilter สามารถเพิ่มตรรกะการประมวลผลบางอย่างให้กับเส้นทางบางเส้นทางหรือทุกเส้นทางได้อย่างโปร่งใส นี่คือประโยชน์ของ AOP
แต่ความสัมพันธ์ตามลำดับระหว่างพวกเขาคืออะไร?
ความสัมพันธ์ในการโทรขึ้นอยู่กับซอร์สโค้ด
ซอร์สโค้ดที่เกี่ยวข้องมีดังนี้:

แน่นอนว่าเมื่อเข้าสู่เส้นทางนี้ เจ้าหน้าที่จะถูกเรียกก่อนเพื่อตรวจสอบว่าได้รับอนุญาตหรือไม่ เป็นต้น หากไม่ได้รับอนุญาต จะมีการยกเว้นที่นี่:

HttpException ที่ถูกโยนออกไปจะถูกจัดการโดย ExceptionFilter
หากคุณได้รับอนุญาต interceptor จะถูกเรียก interceptor จะจัดระเบียบ chain เรียกทีละตัว และสุดท้ายจะเรียกเมธอด controller:

ก่อนที่จะเรียกใช้เมธอดคอนโทรลเลอร์ ไพพ์จะถูกใช้เพื่อประมวลผลพารามิเตอร์:

แต่ละพารามิเตอร์จะถูกแปลง:

เป็นเรื่องง่ายที่จะนึกถึงจังหวะการเรียกของ ExceptionFilter ซึ่งก็คือการจัดการข้อยกเว้นก่อนที่จะตอบสนอง
มิดเดิลแวร์เป็นแนวคิดในรูปแบบด่วน Nest.js สืบทอดมันมา และมันถูกเรียกที่เลเยอร์นอกสุด
นี่คือลำดับการเรียกของกลไก AOP เหล่านี้ เมื่อคุณจัดการสิ่งเหล่านี้ได้แล้ว คุณจะเข้าใจ Nest.js เป็นอย่างดี
Nest.js ได้รับการห่อหุ้มตามแพลตฟอร์ม http ด่วน และใช้แนวคิดทางสถาปัตยกรรม เช่น MVC, IOC และ AOP
MVC เป็นแผนกหนึ่งของ Model และ View Controller คำขอจะส่งผ่าน Controller ก่อน จากนั้นจึงเรียก Service และ Repository ของเลเยอร์ Model เพื่อให้ตรรกะทางธุรกิจสมบูรณ์ และสุดท้ายจะส่งคืน View ที่เกี่ยวข้อง
IOC หมายความว่า Nest.js จะสแกนคลาสโดยอัตโนมัติด้วย @Controller และ @Injectable ตกแต่ง สร้างอ็อบเจ็กต์ และฉีดอ็อบเจ็กต์ที่ขึ้นอยู่กับการขึ้นต่อกันโดยอัตโนมัติ ซึ่งช่วยขจัดปัญหาในการสร้างและประกอบอ็อบเจ็กต์ด้วยตนเอง
AOP แยกตรรกะทั่วไปและเพิ่มไปยังตำแหน่งใดตำแหน่งหนึ่งผ่านแง่มุมต่าง ๆ โดยสามารถนำกลับมาใช้ใหม่และเพิ่มและลบตรรกะด้านไดนามิกได้
Middleware, Guard, Interceptor, Pipe และ ExceptionFileter ของ Nest.js ล้วนแต่เป็นการนำแนวคิด AOP ไปใช้ในตำแหน่งต่างๆ
เราดูลำดับการโทรของพวกเขาผ่านซอร์สโค้ด Middleware เป็นแนวคิดของ Express ในเลเยอร์ชั้นนอกสุดหลังจากเข้าถึงเส้นทางใดเส้นทางหนึ่ง Guard จะถูกเรียกใช้เพื่อตรวจสอบว่าเส้นทางนั้นได้รับอนุญาตให้เข้าถึงหรือไม่ Interceptor จะถูกเรียก ขยายตรรกะบางส่วนกลับไปกลับมา และเรียก Pipe เพื่อตรวจสอบและแปลงพารามิเตอร์ก่อนถึงตัวควบคุมเป้าหมาย ข้อยกเว้น HttpException ทั้งหมดจะได้รับการจัดการโดย ExceptionFilter และส่งคืนการตอบกลับที่แตกต่างกัน
Nest.js ใช้สถาปัตยกรรม AOP นี้เพื่อให้ได้สถาปัตยกรรมที่เชื่อมต่อกันอย่างหลวมๆ บำรุงรักษาง่ายและขยายได้
คุณรู้สึกถึงประโยชน์ของสถาปัตยกรรม AOP หรือไม่?