Astro และ Static site generator
/ 8 min read
สามารถดู video ของหัวข้อนี้ก่อนได้ ดู video
Astro คืออะไร ?
Ref: https://astro.build/
Astro เป็น Web framework สมัยใหม่ที่ช่วยให้นักพัฒนาสามารถสร้าง web app ที่เร็วขึ้นโดยพยายามให้ web ใช้การ render JavaScript ที่น้อยลง (จากความสามารถของ Server site generator) โดยมี feature เด่นๆหลักๆคือ
- Island Architecture Astro ใช้วิธีการที่เรียกว่า “islands architecture” ซึ่งหมายความว่าหน้าเว็บส่วนใหญ่เป็น HTML แบบ static แต่มี interactive components (เช่น chatbox, form) ที่สามารถยังคงใช้งานร่วมกันบน Client ได้ ซึ่ง feature นี้จะสามารถ render ของ 2 อย่างออกจากกัน (Static components และ interactive components) แต่ยังคงสามารถพูดคุยไปมาหากันได้เหมือนเดิม ผ่านความสามารถของ Island เพื่อลดปริมาณ JavaScript ที่ต้องส่งไปยัง Browser ทำให้หน้าเว็บโหลดเร็วขึ้นและใช้ bandwidth น้อยลงได้ (อ่านเพิ่มเติมได้ที่ https://docs.astro.build/en/concepts/islands/)
-
Static Site Generator (SSG) Astro มาพร้อมกับความสามารถสร้างเว็บไซต์แบบ Static ออกมาได้ ผ่านความสามารถ build อย่าง Static Site Generator ซึ่งเหมาะสำหรับเว็บ Content อย่าง Blog, documentation, และเว็บไซต์อื่นๆ ที่เนื้อหาไม่เปลี่ยนแปลงบ่อยๆ โดย SSG ยังช่วยให้หน้าเว็บโหลดเร็วขึ้นและ SEO ดีขึ้นด้วยเช่นกัน
-
Tailored JavaScript Delivery Astro ส่งเฉพาะ JavaScript ที่จำเป็นออกมาเท่านั้น ไม่เหมือนกับ Single Page Application อื่นๆ (SPA) ที่โหลด JavaScript ขนาดใหญ่มาแล้วจัดการทุกอย่างผ่าน Javascript แทน ไม่ว่าจะเป็นหน้าไหน Astro จะแบ่ง code ออกเป็นชิ้นเล็กๆ ที่ใช้กับแต่ละหน้าได้
ซึ่งสิ่งนี้ส่งผลต่อ Score ของ Pagespeed อย่างมากทั้งในเรื่องของ FCP, Blocking time เช่น mikelopster.dev
แห่งนี้ที่มีการเปลี่ยนมาใช้ Astro
Astro เหมาะสำหรับเว็บไซต์ที่เน้นประสิทธิภาพ SEO และประสบการณ์ผู้ใช้ที่รวดเร็วเป็นหลัก ไม่เหมาะสำหรับ web ที่จัดการ Content แบบ Dynamic ซึ่ง Framework SPA แบบดั้งเดิม (ไม่ว่าจะเป็น Vue, React, Angular, Svelte) อาจเหมาะสมกว่าในเคสนี้
สามารถอ่านเพิ่มเติมได้ที่ https://docs.astro.build/en/concepts/why-astro/
ในบทความนี้เราจะพูดถึงอะไรกันบ้าง
เราจะพาทุกคนมารู้จักกับ Astro กันตั้งแต่จุดเริ่มต้นว่า
- สามารถ Start project Astro ยังไงได้บ้าง
- แต่ละ Feature ของ Astro ตั้งแต่
- Astro Component / การส่ง Props ผ่าน Component / การ import Component
- Component Script
- การทำ Route / Parameter path
- การเขียน content ผ่าน markdown และการควบคุม content ผ่าน markdown
- การจัดการ Layout และ Style
- การ fetch ข้อมูลจาก Server
- Client Site Script (สำหรับจัดการฝั่ง Client)
มารู้จักไปพร้อมๆกันครับ (เพื่อความรวดเร็ว สามารถดูเป็นฉบับ Video เพื่อ overview ดูก่อนได้เช่นกัน)
Setup Astro
Ref: https://docs.astro.build/en/install/auto/
มาลองเล่น Astro กันดีกว่า ลง project Astro ด้วย cli ด้วยคำสั่งเหล่านี้ได้
สำหรับเริ่มต้นให้เลือกแบบ “Include sample file” เพื่อให้ project (เพื่อมาเรียกรู้ structure กัน) เลือก option ตามภาพนี้ได้
หลังจากลงตามนี้เรียบร้อยเราจะได้ structure file หน้าตาประมาณนี้ออกมา
โดย
- Folder หลักสำหรับจัดการ application คือ
src
astro.config.mjs
คือตัวจัดการ config หลักของ astro
** สำหรับใครอยากได้ Blog template แบบสำเร็จทีเดียว แนะนำให้เลือกแบบ Blog template
จะได้ส่วนของ Markdown ออกมาด้วย
หลังจาก create project เสร็จให้เข้ามาใน directory project แล้ว run ด้วยคำสั่ง
ก็จะได้ผลลัพธ์แบบนี้ออกมา (default port ของ Astro คือ localhost:4321
)
ถ้าสามารถได้ผลลัพธ์แบบนี้ออกมาได้ ถือว่า create project ได้ถูกต้องเป็นที่เรียบร้อย
พื้นฐาน Astro
เราจะมาทำเว็บ Blog อย่างง่ายไปทีละ step กัน โดยในท้ายที่สุดเราจะทำให้เว็บ Blog ของเราสามารถดึงข้อมูลจาก API และแสดงผลออกมาได้
- ที่สำคัญคือ Astro เองก็มี tutorial ภายใน document ของตัวเองไว้เช่นเดียวกัน สามารถเข้าไปอ่านและลองค่อยๆไล่ทีละ step ตาม document ของ Astro ได้เช่นกัน https://docs.astro.build/en/tutorial/0-introduction/
สร้าง astro component
Ref: https://docs.astro.build/en/tutorial/1-setup/3/
เราสามารถสร้างไฟล์ชื่อ .astro
เพื่อเป็นการสร้าง Component สำหรับใช้งานในเว็บออกมาได้
- ถ้าสร้างภายใน folder
pages
= เป็น Page Component ที่สามารถเปิดตาม Route ตามชื่อไฟล์ออกมาได้ (อ่านเพิ่มเติมได้ที่ https://docs.astro.build/en/core-concepts/astro-pages/ ซึ่งเดี๋ยวจะมีย้ำอีกทีในหัวข้อ markdown) - ถ้าสร้างภายนอก folder
pages
= เป็น Component ทั่วไปที่สามารถ import มาใช้ได้
เช่น หากเราสร้างไฟล์ที่ src/pages/about.astro
หน้าตาประมาณนี้
ก็จะสามารถเปิดผ่าน localhost:4321/about
ออกมาได้หน้าตาตาม html นี้ออกมา
เพิ่ม link ระหว่างหน้า
Ref: https://docs.astro.build/en/tutorial/2-pages/1/
ในการ link ไปยังแต่ละหน้าสามารถใช้ tag <a>
ในการ link ระหว่างหน้าได้เลย (เหมือน html ทั่วไปเลย) โดย
path
จะยังอ้างอิงตาม Page Component ที่สร้างไว้
เช่นแบบนี้ลองเพิ่มที่หน้า index.astro
ก็สามารถสร้าง link ไปยังหน้า localhost:4321/about
ได้
รู้จัก Component script
Ref: https://docs.astro.build/en/core-concepts/astro-components/#the-component-script
Astro ใช้สัญลักษณ์ ---
(เรียกว่า fence) ในการกำกับส่วนที่เป็น script ของ Astro component. (หน้าตาจะคล้ายๆการกำหนด properties ของ Markdown) โดยเราสามารถเขียน javascript ได้ระหว่าง fence เพื่อเป็นการกำหนด condition หรือข้อมูลก่อนการ render template ออกมาได้
โดยปกติ มักจะใช้ 2 เคสคือ
- กำหนดค่าเริิ่มต้นหรือ condition บางอย่างให้กับ component
- ดึง data ออกมาก่อนที่จะ render ตัว component ออกมา (เดี๋ยวมีิอธิบายเพิ่มเติมอีกที)
ตัวอย่างแบบง่ายๆ เช่น หากเราต้องการแสดงชื่อตัวแปร javascript เช่น name
จาก javascript ลง template ของ Astro สามารถทำได้ผ่าน {name}
โดยใน {}
เป็นการระบุตัวแปรของ javascript ที่ได้มีการสร้างเอาไว้
การ import Component
Ref: https://docs.astro.build/en/tutorial/3-components/1/
เราสามารถเรียกใช้ Component อื่นๆใน Astro ได้ผ่านการ import component เข้ามาได้เช่นเดียวกัน (เหมือนกับหลายๆ Framework ที่มีในท้องตลาด) โดยการใช้คำสั่ง import ตรงๆได้เลย
สมมุติเราสร้าง component ชื่อ Navigation
ไว้ใน components/Navigation.astro
หลังจากนั้นที่ pages/index.astro
ทำการ import component เข้ามา
ก็จะสามารถเรียกใช้ Astro component Navigation
เข้ามาได้
การส่ง Props เข้า Component
Ref: https://docs.astro.build/en/core-concepts/astro-components/#component-props
เช่นเดียวกันนอกเหนือจากการ import แล้ว ยังสามารถส่ง Properties (ค่าจากภายนอก component) เข้าไปใช้งานภายใน Component ได้เช่นเดียวกัน
เช่น หากเราปรับ Navigation
ให้ dynamic ตามตัวแปรที่ส่งไป แทนที่จะ fix ตามข้อมูลที่อยู่ใน Navigation
ก็สามารถสร้างตัวแปรภายใน pages/index.astro
และส่งเข้า component Navigation
เข้าไปได้
ที่ pages/index.astro
ที่ components/Navigation.astro
ก็จะได้ผลลัพธ์ที่เหมือนกับข้างบนออกมาได้ แต่เป็นการเพิ่มความสามารถให้ dynamic ตามตัวแปรใน component หลักออกมาได้
โดยสามารถเพิ่ม condition กับตัวแปรต่างๆได้เหมือน javascript ทั่วๆไปเลย สามารถดูตัวอย่างเพิ่มเติมของ Astro ได้ที่นี่ https://docs.astro.build/en/tutorial/2-pages/3/
ทำ Dynamic route (รับตัวแปรผ่าน Route)
Ref: https://docs.astro.build/en/tutorial/5-astro-api/2/
Page component นอกเหนือจากสามารถสร้าง path ตามชื่อไฟล์ได้แล้วยังสามารถสร้าง dynamic path ผ่านชื่อไฟล์ได้เช่นกัน โดย
- สามารถตั้งชื่อ parameter ที่ต้องการจะรับลงในชื่อไฟล์นั้นๆได้ โดยชื่อไฟล์จะต้องอยู่ภายใต้ blacket (
[parameter].astro
) - และสามารถเรียกใช้งานตัวแปรได้ผ่านคำสั่ง
getStaticParam
ออกมาได้
เช่น สมมุติเราต้องการสร้าง path สำหรับการดึง tag แต่ละตัวออกมา เราสร้าง path ชื่อ pages/tags/[tag].astro
เราจะสามารถดึงตัวแปร tag ออกมาได้ผ่าน Astro.param
เหมือนตัวอย่างนี้
เมื่อลองเปิด path localhost:4321/tags/mike
ก็จะสามารถแสดงผลลัพธ์ออกมาและเจอ path ได้ (และจะไม่เจอหากเราเปิดด้วย path อื่นที่ไม่ได้กำหนดเอาไว้)
getStaticPaths()
ต้องมีเสมอเมื่อมีการใช้ parameters function นี้จำเป็นต้องมี เนื่องจาก Astro คือ static site builder ที่จะทำการ bulid page ทั้งหมดตอนจังหวะ build ออกมา (ทุกหน้าจะโดนสร้างมาทันทีตอน run คำสั่ง build) = สิ่งนี้จะทำให้ Astro รู้ว่า site ของเรามีหน้าทั้งหมดคือหน้าไหนบ้างและทำให้เราสามารถทำเว็บแบบ SSG ออกมาได้
เพิ่ม markdown ทำ content แต่ละหน้า
Ref:
- https://docs.astro.build/en/tutorial/2-pages/2/
- https://docs.astro.build/en/core-concepts/astro-pages/
มาถึงจุดเด่นของ Astro กันบ้างดีกว่า จาก Page component ที่เราพูดถึงกันไปด้านบน นอกเหนือจากไฟล์ประเภท .astro
แล้ว Astro ยัง support file หลายประเภทสำหรับการเขียน Content ด้วย (ภายใต้ folder pages
) ตั้งแต่
.astro
.md
= Markdown.mdx
= Markdown แบบเสริม MDX Integration.html
.js/.ts
as API endpoints (ใช่ครับ Astro support การทำ proxy API สำหรับการดึง data เช่นกัน)
ซึ่งสำหรับคนที่เลือกใช้ Astro หลายๆคน เลือกใช้เพราะ support ภาษาอย่าง markdown
ที่ช่วย support การเขียน Content ให้ง่ายขึ้นด้วยเช่นกัน
Markdown คือ markup language แบบ lightweight ที่ใช้สำหรับเก็บ text แบบมี format เอาไว้ ถูก design ไว้เพื่อให้สามารถเขียนและอ่านออกมาได้ง่ายเมื่อต้องเขียนข้อความ plain text แบบมี style ออกมา
นี่คือตัวอย่างของ markdown
จุดเด่นใหญ่ๆจริงๆของ Markdown คือความสามารถในการแปลงภาษา Markdown ออกมาเป็น html ได้ง่าย มันจึงเป็นหนึ่งในภาษาสำหรับการเก็บ content เพื่อเตรียมแปลงเป็น style html ออกมาได้ (แม้แต่บทความของ mikelopster.dev
แห่งนี้เองก็ใช้ markdown เช่นกัน)
สามารถอ่านเพิ่มเติมเกี่ยวกับการเขียน markdown ได้ที่นี่ https://www.markdownguide.org/
ทีนี้เมื่อ Astro support markdown = สามารถที่จะ render markdown ออกมาเป็น html ได้เช่นกัน
เช่น หากเราลองสร้าง folder posts
และเอา markdown ด้านบนไปสร้างเป็นไฟล์ชื่อ posts/test.md
เมื่อเราลองเปิดด้วย path localhost:4321/posts/test
ก็จะสามารถเปิดหน้าเว็บออกมาได้ทันที โดยไม่ต้องลงอะไรเพิ่มเติมเลย !
ดังนั้นการใช้ Astro คู่กับ Markdown จึงช่วยอำนวยความสะดวกในการทำบทความ รวมถึงการทำ Content ที่ต้องใช้ style ร่วมกันมากๆ เราสามารถเขียน global style เพื่อแต่ง markdown ทุกๆหน้าออกมาได้ และสามารถควบคุมรูปแบบการแสดงผล content ให้ทุกๆหน้าออกมาได้เหมือนๆกันได้เช่นกัน
การทำ Layout กับ Markdown
Ref: https://docs.astro.build/en/core-concepts/layouts/#markdownmdx-layouts
เนื่องจาก Markdown นั่นเป็น pattern ที่มีลักษณะเหมือนๆกันอยู่แล้วในเรื่องของการวางโครงสร้าง ดังนั้น การวาง style หรือ Layout เองก็จะคล้ายๆกันในทุกๆหน้าเช่นเดียวกัน
Astro ได้มี feature Layouts
ที่สามารถกำกับ Layout ภาพรวมของทุกๆหน้า (เป็น Layout component ตัวใหญ่สุดที่คลุมเอาไว้) รวมถึงสามารถกำกับ Layout ของ Markdown ได้เช่นกัน
เช่น หากเราต้องการ Layout สำหรับการแสดงผลในหน้า markdown เราสามารถสร้างเป็น Layout component ออกมาได้ สมมุติว่าชื่อ layouts/BaseLayout.astro
เราจะสามารถ import layout นี้เข้ากับ markdown ตรงๆได้ผ่าน properties ของ Markdown ได้เลย
ก็จะได้ผลลัพธ์ออกมาเป็นการใช้ Layout ควบคุมและ markdown ก็จะไปแสดงผลตรง <slot></slot>
ออกมาได้
Concept Layout นี้สามารถใช้ได้หมดทั้ง markdown และ Page component (Astro component)
ทำหน้า List blog จากข้อมูล markdown
Ref: https://docs.astro.build/en/tutorial/5-astro-api/1/
เราจะลองดึงข้อมูล Blog ทั้งหมดออกมาจากตัว markdown กัน โดย
- ใน Astro ได้เตรียม
Astro.glob
ให้สามารถดึงข้อมูล Blog ออกมาได้ Astro.glob()
คือคำสั่งสำหรับการ load local files ลงมาที่เว็บของ static ได้ ในเคสนี้เราจะทำการดึงทุก file ออกมาจาก path ของ blog (ในทีนี้คือ/posts/*.md
)- โดยใน markdown file นั้นได้มีการ implement ตัว interface ไว้ชื่อ
frontmatter
(เหมือนตัว---
ใน astro component) ซึ่งตัวค่าอะไรก็ตามที่ประกาศไว้จุดเริ่มต้นของ markdown ตรงfrontmatter
จะสามารถเรียกใช้ผ่านตัวแปรที่คืนค่าออกมาจากAstro.glob()
ได้เลย
เช่นเคสนี้ ในตัว markdown ของ posts/test.md
มี frontmatter
หน้าตาแบบนี้อยู่
เมื่อมาดึงข้อมูลที่ Astro component ก็จะสามารถดึงตัวแปรผ่าน frontmatter
ออกมาได้ ผ่าน
post.frontmatter.title
= title ที่กำหนดใน markdown (“Mike Test”)post.frontmatter.author
= author ที่กำหนดใน markdown (“Mikelopster”)
เป็นต้น
เพียงเท่านี้เราก็จะสามารถ list blog ทั้งหมดออกมาได้และสามารถดึงข้อมูล Properties ของ markdown ออกมาได้
การเพิ่ม Style เข้า Astro
Ref: https://docs.astro.build/en/tutorial/2-pages/4/
เหมือนๆกับ Frontend framework ทั่วไป Astro สามารถเขียน style เข้าไปใน component ของ Astro โดยตรงได้ผ่าน tag <style></style>
ใน .astro
เช่นอย่างเคส Layout ด้านบนหรือเคสทั่วๆไปแบบนี้
เช่น ลองใส่ style ที่ pages/about.astro
โดยนอกเหนือจากการใส่ style เหมือน html, css ทั่วๆไปแล้ว Astro ยัง support การใส่ style จากตัวแปร javascript ด้วยเช่นกัน โดยสามารถส่งได้ผ่าน define:vars={ {...} }
กำกับคู่กับ tag <style></style>
โดยใส่ตัวแปรที่ต้องการใส่เข้าไป
เช่นเคสนี้ หากเราต้องการกำกับสีผ่านตัวแปรของ javascript
- เราจึงประกาศตัวแปร
const headColor='purple'
ขึ้นมาเพื่อเก็บสีม่วงเอาไว้ - และเรียกใช้สีม่วงผ่านตัวแปร
var(--headColor)
ภายใน tag<style></style>
ออกมาแทน
ก็จะได้ผลลัพธ์ที่เหมือนกันกับเคสด้านบนออกมาได้
ดังนั้นการพิจารณาใช้สิ่งนี้จะพิจารณาอยู่บนพื้นฐานว่า
- เราจะกำกับ style ผ่าน CSS ล้วนๆ
- หรือ จะกำกับ style ผ่าน config ตัวไหนใน javascript ก็สามารถที่จะเลือกใช้วิธีส่งตัวแปรแทนได้
รวมถึง tailwind เองก็ Support Astro เช่นกัน สามารถใช้ร่วมกันได้ (สำหรับคนที่ถนัด utility class style) https://tailwindcss.com/docs/guides/astro
จริงๆมีเรื่องอื่นๆเพิ่มเติมสามารถอ่านผ่าน Docs ของ Astro ได้ มันก็จะมีเพิ่มเติมตั้งแต่
- การทำ global style = style ให้กับทุกๆ component (เนื่องจาก default ของ Astro เป็น scoped style)
- การประยุกต์ใช้ร่วมกันระหว่าง Props กับ Style https://docs.astro.build/en/guides/styling/
ส่งตัวแปรจาก Server เข้า Component
Ref: https://docs.astro.build/en/guides/data-fetching/#fetch-in-astro
นอกเหนือจาก static content อย่าง markdown แล้ว Astro ยัง support การทำ Dynamic content เช่นเดียวกัน
- อย่างแรกสุด สามารถส่งตัวแปรจาก javascript มาแสดงผลที่ Component ได้ (เหมือนตัวอย่างด้านบน)
- อีกอย่างคือสามารถดึงข้อมูลจาก API มาไว้ก่อนและนำมาแสดงผลที่ Component ออกมาได้ (เป็นการดึงข้อมูลจากฝั่ง Server และส่งมาแสดงผลที่ Component ออกมา)
เช่นเคสนี้ เราจะดึงข้อมูล Blog จากแหล่งอื่นมาแสดงผ่าน Mock API (Endpoint ที่ได้เตรียมไว้สำหรับการดึงข้อมูล ex. https://<mock-api-id>.mockapi.io/blogs
) หน้าตาของผลลัพธ์ API จะเป็นประมาณนี้
ดังนั้น เมื่อมาใช้กับ Astro component เราจะต้องดึงข้อมูลใส่ตัวแปรหนึ่งไว้ก่อน (สมมุติชื่อ posts
) และนำมาแสดงผลผ่านตัวแปรนั้นออกมาได้ เช่น เคสนี้เราจะลองเพิ่มเติมไว้ที่ pages/external.astro
ออกมา
ผลลัพธ์ก็จะได้ออกมาหน้าตาประมาณนี้
การเพิ่ม script javascript สำหรับฝั่ง client
Ref: https://docs.astro.build/en/tutorial/3-components/4/
สำหรับ Javascript ของฝั่ง Client นั้น Astro จะใช้วิธีการ handle case แบบทั่วๆไปคือ ใส่ tag <script>
เหมือน html และทำการ access html ผ่าน javascript ตรงๆได้เลย เช่นแบบนี้
หากใครจะใช้ library Frontend framework ตัวอื่นๆเช่น React, Vue ก็สามารถ import มาใช้งานตรงๆได้เช่นเดียวกัน ดูตัวอย่างเพิ่มเติมในเอกสารของ Astro ได้ https://docs.astro.build/en/guides/client-side-scripts/#client-side-scripts
Shortcut ด้วยการหา theme
Ref: https://astro.build/themes/
สำหรับใครที่อยากเริ่มต้นแบบรวดเร็ว ใน Astro เองมี Theme Marketplace อยู่ ซึ่งสามารถ clone มาลองใช้งานดูก่อนได้ สามารถทำให้เราเห็นภาพรวมของหลายๆ project ได้ดีขึ้นเช่นกันว่าปกติวาง project structure กันยังไงบ้าง
mikelopster.dev
ใช้ cactus เป็น based หลัก (ที่กำลังค่อยๆทยอยเอา style เข้า-ออก อยู่)
การใช้ร่วมกับสิ่งอื่นๆ
-
เพิ่ม mermaid (diagram) https://code.juliancataldo.com/component/astro-diagram/
-
เพิ่ม latex (สำหรับแสดงสมการคณิตศาสตร์) https://blog.alexafazio.dev/blog/render-latex-in-astro/
-
เพิ่ม RSS Feed (เพื่อให้เว็บไซต์อื่นสามารถมาดูข้อมูล update blog จากเราได้) https://docs.astro.build/en/guides/rss/
-
Astro Island https://docs.astro.build/en/tutorial/6-islands/1/
-
Guildline สำหรับการต่อกับ CMS อื่นๆ https://docs.astro.build/en/guides/cms/
-
การ Deploy Astro โดย default ของ Astro จะ build web เป็น Server site อยู่แล้ว หากต้องการ config เป็น SSR แทนสามารถปรับได้จาก
astro.config.mjs
https://docs.astro.build/en/guides/deploy/vercel/#_top
- Caching design pattern กับ backendมี Video มี Github
บทความนี้จะเล่าเรื่อง Cache Pattern 3 แบบ lazy loading, write through และ write back ว่าเราสามารถเอา cache ไปใช้คู่กับ database ยังไงได้บ้าง
- รู้จักกับ Design Pattern - Behavioral (Part 3/3)มี Video
มาเรียนรู้รูปแบบการพัฒนา Software Design Pattern ประเภทที่สาม Behavioral กัน
- มารู้จักกับ SQL Transaction กันว่ามันคืออะไร ?มี Video
มารู้จักเรื่องราวของการทำ Transaction และ Deadlock ผ่าน SQL กันว่ามันคืออะไร
- NestJS และ Mongoมี Video
เรียนรู้การผสานพลังระหว่าง NestJS framework ยอดนิยมฝั่ง Node.js กับ MongoDB ฐานข้อมูล NoSQL สุดทรงพลังกัน