Skip to main content
0
DatabaseMySQL

Sequelize 103 กับเรื่องของ Association

Hi !!! ทุกคนนน วันนี้เราก็กลับมาอีกครั้งกับหัวข้อที่เราทิ้งไว้รอบที่แล้วกันนนนนั้นก็ คือออออออออออ คือออออออ Association หรือ Relation ของ SQL นั่นเองงงง และในครั้งนี้เราก็จะใช้ Schema ของ Database เดียวกันในรอบที่ผ่าน ๆ มากันนะครับ และใครที่เข้ามาอ่านครั้งแรกก็สามารถกลับไปอ่านบนความเก่า ๆ ได้ที่นี่ ( sequelize 101 ) และ ที่นี่ ( 5 function ที่เราได้ใช้แน่ๆใน sequelize ) โอเคเรามาเริ่มกันเลยยย

ประเภทของ Relations ถูกแบ่งออกเป็น 3 แบบได้แก่

1.ความสัมพันธ์แบบ One-to-One [1:1]
เป็นความสัมพันธ์แบบหนึ่งต่อหนี่ง เช่น คนหนึ่งคนสามารถมีบัตรประชาชนได้แค่ 1 ใบเท่านั้น ( ถ้าไม่ติดว่าเราทำหายอะนะ 5555 )

2.ความสัมพันธ์แบบ One-to-Many [1:N]
ความสัมพันธ์นี้เป็นความสัมพันธ์ที่เกิดขึ้นมากที่สุดในการสร้างฐานข้อมูล เป็นความสัมพันธ์ระหว่างหนึ่งสิ่งต่อหลาย ๆ สิ่ง เช่น ทีมฟุตบอล 1 ทีมสามารถมีนักฟุตบอลได้หลายคน

3.ความสัมพันธ์แบบ Many-to-Many [M:N]
เป็นความสัมพันธ์แบบหลายสิ่งต่อหลายสิ่ง เช่น 1 ข่าวสามารถทีได้หลายแท็ก และใน 1 แท็กก็มีได้หลายข่าว

แล้วในการที่เราจะสร้าง Relation ใน Sequelize เราจะสามารถสร้างได้โดยใช้ Association และ association ของ Sequelize จะแบ่งออกเป็น 4 แบบก็คือ

  • HasOne association
  • BelongsTo association
  • HasMany association
  • BelongsToMany association

โดยเราถ้าเราจะสร้าง 1:N relation เราก็จะใช้ HasMany คู่กับ BelongsTo โดยวิธีก็จะเป็นแบบ code ด้านล่างครับ

โดย db.team กับ db.player คือ model ที่เราสร้างไว้ในครั้งก่อน ๆ นะครับ

db.team.hasMany(
   db.player,
   {
      foreignKey: { name: 'tid', field: 'tid' }, //<- เป็นการกำหนดว่าใช้ FK ชื่ออะไรเวลาเราเรียกฝช่งานให้เราใช้ name ที่เราตั้ง ในการใช้งานแนะครับ เผื่อเวลาที่เราเปลี่ยนชื่อFKใน database จะได้ไม่งง
   }
);

db.player.belongsTo(db.team, { foreignKey: 'tid' });

จาก code ด้านบนจำทำการสร้าง FK ในตาราง player ให้เราโดยใช้ PK ของ team ( จริงๆเรามาสารถใช้ hasMay อย่างเดียวได้นะครับแต่เราจะทำได้แค่หาว่า team มี player คนไหนบ้าง แต่จะเราไม่สามารถใช้ในการหาย้อนกลับไปได้นั้นเองเลยต้องใช้ HasMany คู่กับ BelongsTo )

ต่อไปเราจะลองสร้าง relation แบบ [1:1] กันโดยใช้ HasOne คู่กับ BelongsTo นั่นเอง โดยก็ใช้งานคล้าย ๆ กันกับ [1:n] เลยแต่แค่มันจำกัดไว้แค่ 1 อย่างมีได้แค่ 1 อย่างเท่านั้น

db.people.hasOne (
   db.idCard,
   {     
      foreignKey: { name: 'pid', field: 'pid' }, 
   }
);

db.idCard.belongsTo(db. people, { foreignKey: 'id' });

อย่างตัวอย่างด้านบนจะได้ความหมายว่า people 1 คนจะมี idCard ได้แค่ 1 ใบเท่านั้นโดย code ด้านบนจะทำการถ้า FK ในตารางของ idCard นะครับถ้าอยากได้ แบบกลับกันก็สลับรูปแบบกันแค่นั้นเองเอาง่าย ๆ อะไรที่ใช้ has จะเป็นตัวที่สร้าง FK ในตารางอื่นนั่นเอง

ต่อมาเราก็มาถึง relation สุดถ้าแล้วว [m:n] โดย relation นี่จะสร้างแปลก ๆ หน่อย โดยส่วนใช้เราจะสร้างมันโดยมี table มาเป็น table ตรงกลางที่คอยเก็บ PK ของทั้ง 2 table ที่มี relation กัน เราจะยกตัวเอย่างเป็น news กับ tag แล้วกันนะครับ

db.news.belongsToMany(db.tag, {
   through: db.newsTag,
   foreignKey: 'news_id',
   otherKey: 'tag_id',
});

db.tag.belongsToMany(db.news, {
   through: db.newsTag,
   foreignKey: tag_id',
   otherKey: 'news_id',
});

เท่านี้เราก็จะได้ relation [m:n] ของ tag กับ news แล้วโดยผ่าน newsTag นั่นเอง

ต่อไปเราก็มาดูการใช้งานหลังจากสร้าง relation แล้วกันดีกว่า

await team.findOne({
   where: {
      tid: 1
   },
   include: {
      model: player
   }
})

โดย code ด้านบนทำการ query ข้อมูลของทีม team และมีข้อมูลของ player ที่อยู่ในทีมติดมาด้วยแบบนี้ ( อย่าไปใส่ใจเรื่องทีมจริง ๆ ของนักกีฬานะครับ 😀 )

{
   "tid": 1,
   "name": "Real Madrid",
   "league": "La Liga",
   "players": [
      {
         "pid": 4,
         "name": "Lionel Messi",
         "age": 34,
         "position": "ST",
         "tid": 1
      },
      {
         "pid": 14,
         "name": "Marcelo",
         "age": 33,
         "position": "DF",
         "tid": 1
      }
   ]
}

แล้วถ้าใครอยากจะ filter player ก็ใส่ where ใน include ได้เลย

await team.findOne({
   where: {
      tid: 1
   },
   include: {
      model: player,
	  where: { age: {[Op.gt]: 33} }
   }
})

และนี่ก็คือผลที่ได้ไงล่ะ เราใช้ Operation ก็อย่าลืม defined มันก่อนใช้นะครับบบ

{
   "tid": 1,
   "name": "Real Madrid",
   "league": "La Liga",
   "players": [
      {
         "pid": 4,
         "name": "Lionel Messi",
         "age": 34,
         "position": "ST",
         "tid": 1
      }
   ]
}

เอาล่ะแล้วก็จบไปแล้วสำหรับ เรื่องการใช้งาน Association ของ Sequelize หวังว่ามันจะช่วยเพื่อน ๆ ได้ไม่มากก็น้อยนะครับ สำหรับรอบหน้าจะเป็นเรื่องอะไรก็ขอให้รอติดตามกันนะครับบบ ( ถึงไม่รู้ว่าจะได้เขียนต่อหรือป่าวเถอะนะ5555 ) สำหรับใครที่อยากอ่าน Document ของ sequelize ก็กดไปอ่านได้ที่นี่เลย

thapanon

Author thapanon

More posts by thapanon
Close Menu

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

ตั้งค่าความเป็นส่วนตัว

คุณสามารถเลือกการตั้งค่าคุกกี้โดยเปิด/ปิด คุกกี้ในแต่ละประเภทได้ตามความต้องการ ยกเว้น คุกกี้ที่จำเป็น

ยอมรับทั้งหมด
จัดการความเป็นส่วนตัว
  • คุกกี้ที่จำเป็น
    เปิดใช้งานตลอด

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

  • คุกกี้สำหรับการติดตามทางการตลาด

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

บันทึกการตั้งค่า