1.12 · ข่าว นโยบาย การแจ้งเตือน
บทนี้รวมฟีเจอร์ "content" ของระบบ — ข่าวสาร, นโยบายคุณภาพ, คลังเอกสาร, และระบบ push notification
ทั้งหมดเป็น content ที่ HR/admin สร้างและ publish ให้พนักงานเห็น — ไม่ใช่ข้อมูลธุรกรรม
Notification — push + in-app
vtrc-api/api/src/typeDefs/notification.js:1-197
ระบบ notification ทำ 2 หน้าที่พร้อมกัน
- Push notification ผ่าน Firebase Cloud Messaging (FCM) — ไปที่ mobile app
- In-app notification — เก็บใน VTRC ให้พนักงานเปิดดูในเว็บได้
Notification Group
notification.js:154-165 — แยกตามหมวด
| Group | ใช้สื่อสารเรื่อง |
|---|---|
NEWS | ข่าวสารทั่วไป |
POLICY | นโยบายใหม่ |
SCHEME | ระเบียบ/กฎระเบียบ |
SALARY | สลิปเงินเดือนพร้อมแล้ว |
EVENT | กิจกรรม |
ANNOUNCEMENT | ประกาศ |
RELEASE | release notes ของระบบเอง |
OTHER | อื่นๆ |
WELFARE | สวัสดิการ (เช่น รออนุมัติ, โอนสำเร็จ) |
MEETING | การประชุม |
TypeSend — broadcast vs targeted
| Type | พุ่งเป้า |
|---|---|
ALL | ทุกคน |
INDIVIDUAL | เฉพาะคน (ระบุ userId) |
การส่ง notification
| Mutation | ผู้ใช้ | หน้าที่ |
|---|---|---|
sendNotification(title, body, group, postId?, docId?, courseId?, isConfirm) | HR admin | ส่งจาก backoffice |
sendNotificationFrom3Party(notifications) | subsystem (CONICLE, Meeting, ฯลฯ) | ใช้โดยระบบอื่น และใช้โดย createWDHospital ด้วย |
sendNotificationFrom3Party เป็นพิเศษ — VTRC เรียกเองด้วยตอน create WDHospital (push WELFARE "รออนุมัติ" ให้ approver) — withdraw/hospital.js:1441-1462
Notification field — feature flags
notification.js — แต่ละ notification มี flag หลายตัว
| Field | หน้าที่ |
|---|---|
read (0/1) | อ่านแล้ว |
isConfirm (0/1) | บังคับให้กดยืนยันว่าอ่านแล้ว |
confirm (null/0/1) | user ยืนยันแล้วหรือยัง |
dateConfirm | timestamp ตอนยืนยัน |
notiFrom | ชื่อระบบที่ส่งมา (เช่น WELFARE, CONICLE) |
isConfirm = 1 ใช้สำหรับ notification สำคัญที่ HR อยาก tracking ว่าทุกคนเห็นแล้ว (เช่น นโยบายใหม่)
Models — ตาราง notification
vtrc-api/api/src/models/core/notification/
| Model | หน้าที่ |
|---|---|
notification.js | main row ของแต่ละ notification |
notificationRead.js | tracking ใครอ่านแล้วบ้าง |
notificationRequest.js | request ที่รอส่ง (queue) |
notificationResult.js | ผลลัพธ์การส่งแต่ละครั้ง |
notificationFail.js | log การส่งล้มเหลว |
notificationUserSetting.js | setting ของ user (ปิด group ใด group หนึ่งได้) |
notificationPublicDevice.js | device token สำหรับ anonymous push |
queueNotification.js | queue ก่อน FCM fan-out |
News / Post
vtrc-api/api/src/typeDefs/post.js:1-60+
fetchListPost(type, status, category)— พนักงานเห็นแค่ที่status = publishedfetchListPostBackoffice— HR เห็นทั้งหมดรวม draft
Visibility matrix
postDivision: [[String]] — config เลือก division ที่เห็นโพสต์
เช่น ถ้าตั้งเป็น [["01"], ["02", "03"]] หมายถึงเห็นเฉพาะคนใน division 01, 02, 03
ถ้าไม่ตั้งค่า → เห็นทุกคน
Mutation
createPost / updatePost ได้เฉพาะ backoffice (SUPER_ADMIN/ADMIN/STAFF)
Policy
vtrc-api/api/src/typeDefs/policy.js
โครงสร้างคล้าย Post — CRUD pattern เดียวกัน
ใช้สำหรับเผยแพร่ "นโยบายคุณภาพ" ของสภากาชาด — เอกสารระดับองค์กรที่ทุกคนควรรู้
Document + DocumentGroup
vtrc-api/api/src/typeDefs/document.js:1-269
Document
| Query | หน้าที่ |
|---|---|
fetchListDocument(docGroupId, docGroupCodeRef, search, offset, limit) | list หลัก |
Mutations
| Mutation | ผู้ใช้ | หน้าที่ |
|---|---|---|
createDocument / updateDocument / destroyDocument | admin | CRUD |
createDocumentFrom3Party(docType) | subsystem | 3rd-party ingestion |
docType enum (document.js:263-268)
| Type | ตัวอย่าง |
|---|---|
ANNOUNCE | ประกาศ |
DICTATION | คำสั่ง |
DECLARATION | ประกาศิต |
FORM | แบบฟอร์ม |
KCMH documents
กรณีพิเศษ — createKCMHDocumentByWorkSystem และ createKCMHDocumentByType (document.js:120-185)
ใช้สำหรับดึงเอกสารจากระบบคุณภาพของโรงพยาบาลจุฬาฯ (KCMH = King Chulalongkorn Memorial Hospital) — เป็น ingestion จากระบบภายนอกที่ KCMH ใช้เอง
ContactUs
vtrc-api/api/src/typeDefs/contactUs.js:1-229
เป็น directory ไม่ใช่ระบบป้ายคำถาม — เก็บข้อมูลติดต่อของ HR/หน่วยงาน
Entity
ContactUs— directory ของ HR/หน่วยงาน (เบอร์โทร, email, ชื่อหัวหน้า)ContactUsTelDivision— เบอร์โทรแยกตาม divisionContactUsCategory— หมวดหมู่
Read เปิดให้ทุกคน — write เฉพาะ admin
Notification fan-out — performance caveat
เมื่อ HR ส่ง notification แบบ TypeSend = ALL — VTRC ต้อง fan-out ไป user ทุกคน (~พัน devices)
ไม่มี background queue จริงจัง — fan-out เกิดใน GraphQL resolver inline ถ้า user จำนวนมาก request อาจ timeout
notification.sendNotificationByThirdParty ใน controller จัดการ fan-out — ดู lib/controllers/notification/
ถ้า HR บ่นว่า "ส่ง notification แล้วค้าง" — น่าจะเป็นปัญหานี้ ลองแบ่งเป็นหลาย batch
การ tracking อ่านแล้ว
notificationRead table เก็บ (notificationId, userId, readAt) — แต่ละคนที่กดอ่าน
HR สามารถ query ได้ว่า notification นี้มีคนอ่านกี่คนจากกี่คน — เห็นในหน้ารายงาน notification
User Setting — ปิด notification group
notificationUserSetting table — พนักงานเลือกปิด group ใด group หนึ่งได้ (เช่นปิด MEETING ถ้าไม่สนใจ)
แต่บาง group บังคับรับไม่ได้ปิด — SALARY, WELFARE, POLICY (กำหนดใน controller)
ข้อควรระวัง
- FCM token หมดอายุ — ถ้าพนักงานไม่เปิด mobile นานๆ token ถูก GC และ push ไม่ถึง
- ไม่มี retry queue — ถ้า FCM ล่มตอนส่ง notification นั้นหาย
notificationFailเก็บ log ล้มเหลว แต่ไม่มี UI สำหรับ re-send — ต้องดูโดยตรงใน database- ระบบ subsystems (CONICLE, Meeting) push ผ่าน
sendNotificationFrom3Party— ถ้า subsystem เหล่านี้ส่งมากเกินไป อาจกระทบ performance