ಲೋಡಿಂಗ್ ಸ್ಪಿನರ್ ನಿಮಗೆ ಏನನ್ನೂ ತಿಳಿಸುವುದಿಲ್ಲ. ಒಂದು AI ಕಾರ್ಯವು ನಿಮಿಷಗಳ ಕಾಲ ಮುಂದುವರಿದಾಗ—ಅಥವಾ ಮೂರನೇ ಬಾರಿ ಮರುಪ್ರಯತ್ನಕ್ಕಾಗಿ ಕ್ಯೂಗೆ ಮರಳಿದಾಗ—ನೀವು ಅದರ ಸ್ಥಿತಿಯನ್ನು (state) ನೋಡಬೇಕಾಗುತ್ತದೆ. Server-Sent Events ನಿಮಗೆ WebSockets ನ ಹ್ಯಾಂಡ್ಶೇಕ್ ಓವರ್ಹೆಡ್ ಅಥವಾ long polling ನ ಸಂಕೀರ್ಣತೆ ಇಲ್ಲದೆ ಅಂತಹ ದೃಶ್ಯತೆಯನ್ನು ನೀಡುತ್ತದೆ. ಸರ್ವರ್ ಒಂದೇ ಒಂದು HTTP ರೆಸ್ಪಾನ್ಸ್ ಅನ್ನು ತೆರೆದಿಟ್ಟುಕೊಳ್ಳುತ್ತದೆ ಮತ್ತು ಬದಲಾವಣೆಗಳಾದಂತೆ ಪ್ಲೇನ್-ಟೆಕ್ಸ್ಟ್ ಅಪ್ಡೇಟ್ಗಳನ್ನು ಪುಶ್ ಮಾಡುತ್ತದೆ. ಕ್ಲೈಂಟ್ ಅವುಗಳು ಬಂದ ತಕ್ಷಣ ಓದುತ್ತದೆ.
ಒಂದು ವೇಳೆ ಕನೆಕ್ಷನ್ ಕಡಿತಗೊಂಡರೆ, ನೀವು ಬಹುಶಃ ಮೊದಲಿನಿಂದಲೇ ಪ್ರಾರಂಭಿಸಲು ಬಯಸುವುದಿಲ್ಲ. ಚೆನ್ನಾಗಿ ನಿರ್ಮಿಸಲಾದ SSE ಸ್ಟ್ರೀಮ್ ನೀವು ಎಲ್ಲಿ ನಿಂತಿದ್ದೀರಿ ಎಂಬುದನ್ನು ನೆನಪಿಟ್ಟುಕೊಳ್ಳುತ್ತದೆ. ಕೇವಲ Node.js 20 ಮತ್ತು ಸ್ಟ್ಯಾಂಡರ್ಡ್ ಲೈಬ್ರರಿಯೊಂದಿಗೆ ನೀವು ಇದನ್ನು ಮಾಡಬಹುದು. ಯಾವುದೇ ಬಾಹ್ಯ ಪ್ಯಾಕೇಜ್ಗಳ ಅಗತ್ಯವಿಲ್ಲ.
ವೈರ್ ಫಾರ್ಮ್ಯಾಟ್ ಹೇಗಿರುತ್ತದೆ
SSE ಸಂದೇಶವು ಸರಳ ಪಠ್ಯವಾಗಿದೆ. ಸರ್ವರ್ ಮೂರು ವಿಷಯಗಳನ್ನು ಬರೆಯುತ್ತದೆ: ಐಚ್ಛಿಕ ಇವೆಂಟ್ ಹೆಸರು, ಅಗತ್ಯವಿರುವ data ಫೀಲ್ಡ್, ಮತ್ತು ನಿಮ್ಮ ಸೇವ್ ಪಾಯಿಂಟ್ ಆಗುವ id ಫೀಲ್ಡ್. ಪ್ರತಿ ರೆಕಾರ್ಡ್ ಎರಡು ನ್ಯೂಲೈನ್ ಕ್ಯಾರೆಕ್ಟರ್ಗಳೊಂದಿಗೆ ಕೊನೆಗೊಳ್ಳುತ್ತದೆ—ಇದು ಗಡಿ ಗುರುತಿಸುವ ಖಾಲಿ ಸಾಲಾಗಿರುತ್ತದೆ.
ಒಂದು ಆರೋಗ್ಯಕರ ಸ್ಟ್ರೀಮ್ ವೈರ್ನಲ್ಲಿ ಹೀಗೆ ಕಾಣಿಸಬಹುದು:
id: 14
event: status
data: {"phase":"testing","progress":43}
id: 15
event: status
data: {"phase":"retrying","attempt":2}
ಬ್ರೌಸರ್ನ EventSource ಕ್ಲೈಂಟ್ ಈ ಸಾಲುಗಳನ್ನು ಸ್ವಯಂಚಾಲಿತವಾಗಿ ಓದುತ್ತದೆ. ಇದು ಪ್ರತಿ ಬ್ಲಾಕ್ಗಾಗಿ ಒಂದು ಇವೆಂಟ್ ಅನ್ನು ಉಂಟುಮಾಡುತ್ತದೆ ಮತ್ತು ಇತ್ತೀಚಿನ id ಅನ್ನು ಆಂತರಿಕವಾಗಿ ಸಂಗ್ರಹಿಸುತ್ತದೆ. ಒಂದು ವೇಳೆ TCP ಕನೆಕ್ಷನ್ ಕಡಿತಗೊಂಡರೆ, ಕ್ಲೈಂಟ್ ಕಾಯುತ್ತದೆ, ಮರುಸಂಪರ್ಕಿಸುತ್ತದೆ ಮತ್ತು ಸಂಗ್ರಹಿಸಿದ ಐಡೆಂಟಿಫೈಯರ್ ಅನ್ನು Last-Event-ID ಹೆಡರ್ ಆಗಿ ಸರ್ವರ್ಗೆ ಮರಳಿ ಕಳುಹಿಸುತ್ತದೆ. ಈ ಪ್ಯಟರ್ನ್ ಕೆಲಸ ಮಾಡಲು ಆ ಹೆಡರ್ ಕಾರಣವಾಗಿದೆ. ಅದು ಇಲ್ಲದಿದ್ದರೆ, ನಿಮ್ಮ ಬಳಿ ಯಾವುದೇ ಸುಸ್ಥಿರ ಕರ್ಸರ್ (durable cursor) ಇರುವುದಿಲ್ಲ.
Node.js ನಲ್ಲಿ ಸರ್ವರ್ ಅನ್ನು ವೈರ್ ಮಾಡುವುದು
Node ನ ಬಿಲ್ಟ್-ಇನ್ http ಮಾಡ್ಯೂಲ್ ಇದನ್ನು ನೇರವಾಗಿ ನಿರ್ವಹಿಸಬಲ್ಲದು. ಒಂದು ರಿಕ್ವೆಸ್ಟ್ ಬಂದಾಗ, ಇದು ಪೇಜ್ ಅಲ್ಲ, ಬದಲಾಗಿ ಸ್ಟ್ರೀಮ್ ಎಂದು ಕ್ಲೈಂಟ್ಗೆ ತಿಳಿಸಲು ಸರಿಯಾದ ಹೆಡರ್ಗಳನ್ನು ಹೊಂದಿಸಿ:
Content-Type: text/event-stream
Cache-Control: no-cache
Connection: keep-alive
ಬಫರಿಂಗ್ ಅನ್ನು ತೆಗೆದುಹಾಕಿ. ಪ್ರೊಕ್ಸಿಗಳು ಮತ್ತು ಫ್ರೇಮ್ವರ್ಕ್ಗಳು ಕೆಲವೊಮ್ಮೆ ರೆಸ್ಪಾನ್ಸ್ಗಳನ್ನು ಬ್ಯಾಚ್ ಮಾಡಬಹುದು, ಇದು ರಿಯಲ್-ಟೈಮ್ ಅನುಭವವನ್ನು ಹಾಳುಮಾಡುತ್ತದೆ, ಆದ್ದರಿಂದ ಪ್ರತಿ ಚಂಕ್ ನಂತರ ಫ್ಲಶ್ ಮಾಡಿ.
ಮೊದಲು ID ಅನ್ನು ಕಳುಹಿಸಿ, ನಂತರ ಇವೆಂಟ್ ಟೈಪ್, ನಂತರ ಪೇಲೋಡ್ ಡೇಟಾ ಮತ್ತು ಕೊನೆಯಲ್ಲಿ ಖಾಲಿ ಸಾಲನ್ನು ಕಳುಹಿಸಿ. ID ಖಾಲಿ ಸಾಲಿಗೆ ಮೊದಲು ಬರಬೇಕು ಎಂಬುದು ಮಾತ್ರ ಇಲ್ಲಿ ಮುಖ್ಯ, ಇದರಿಂದ ಕ್ಲೈಂಟ್ ಅದನ್ನು ಕ್ಯಾಪ್ಚರ್ ಮಾಡಬಹುದು. ನೀವು ನೇರವಾಗಿ response.write() ಬಳಸುತ್ತಿದ್ದರೆ, ಔಟ್ಪುಟ್ ಹೀಗಿರುತ್ತದೆ:
response.write(`id: ${cursor}\n`);
response.write(`event: ${eventName}\n`);
response.write(`data: ${JSON.stringify(payload)}\n\n`);
ಆ ಕೊನೆಯಲ್ಲಿರುವ \n\n ಕೇವಲ ಅಲಂಕಾರಿಕವಲ್ಲ. SSE ಪಾರ್ಸರ್ಗಳು ಇದನ್ನು ರೆಕಾರ್ಡ್ ಟರ್ಮಿನೇಟರ್ ಆಗಿ ಪರಿಗಣಿಸುತ್ತವೆ. ಅದನ್ನು ಮರೆತರೆ, ಕ್ಲೈಂಟ್ ಹೆಚ್ಚಿನ ಡೇಟಾಕ್ಕಾಗಿ ಕಾಯುತ್ತಾ ಸ್ಥಗಿತಗೊಳ್ಳುತ್ತದೆ.
ಕರ್ಸರ್ ಎಲ್ಲವೂ
ಹೊಸ HTTP ಕನೆಕ್ಷನ್ ಹೊಸ ಸ್ಥಿತಿಯನ್ನು (fresh state) ಖಾತರಿಪಡಿಸುವುದಿಲ್ಲ. ಕ್ಲೈಂಟ್ ಮರುಸಂಪರ್ಕಿಸಿದಾಗ, ಅವರು ಸ್ವೀಕರಿಸಿದ ಕೊನೆಯ ಸಂದೇಶ ಯಾವುದು ಎಂಬುದನ್ನು Last-Event-ID ಹೆಡರ್ ನಿಮಗೆ ತಿಳಿಸುತ್ತದೆ. ನಿಮ್ಮ ಕೆಲಸವು ಮೊದಲಿನಿಂದ ಪ್ರಾರಂಭಿಸುವುದಲ್ಲ, ಬದಲಾಗಿ ಮುಂದಿನ ಸಂದೇಶದಿಂದ ಮುಂದುವರಿಯುವುದಾಗಿದೆ.
ಇದರರ್ಥ ಸರ್ವರ್ ಸೈಡ್ನಲ್ಲಿ ಇವೆಂಟ್ಗಳ ಕ್ರಮಬದ್ಧವಾದ ಲಾಗ್ ಅಥವಾ ಜರ್ನಲ್ ಅನ್ನು ನಿರ್ವಹಿಸುವುದು. ಡೆಮೊಗಾಗಿ ಇನ್-ಮೆಮರಿ ಅರೇ (in-memory array) ಕೆಲಸ ಮಾಡುತ್ತದೆ. ಪ್ರೊಡಕ್ಷನ್ನಲ್ಲಿ ನೀವು ಸುಸ್ಥಿರವಾದದ್ದನ್ನು ಬಯಸುತ್ತೀರಿ—ಡೇಟಾಬೇಸ್ ಲಾಗ್, Redis ಸ್ಟ್ರೀಮ್ ಅಥವಾ write-ahead journal ಗೆ ಸೇರಿಸಿ—ಏಕೆಂದರೆ ಸರ್ವರ್ ರೀಸ್ಟಾರ್ಟ್ ಆದಾಗ ಇತಿಹಾಸವು ಅಳಿಸಿಹೋಗಬಾರದು ಮತ್ತು ಪ್ರತಿಯೊಬ್ಬ ಕ್ಲೈಂಟ್ ಕೂಡ ಮೊದಲಿನಿಂದ ಪ್ರಾರಂಭಿಸಬೇಕಾದ ಅನಿವಾರ್ಯತೆ ಬರಬಾರದು.
ನಿಮ್ಮ ಇವೆಂಟ್ಗಳನ್ನು ಏರುತ್ತಾ ಹೋಗುವ ಇಂಟೆಜರ್ ಅಥವಾ ULID ಮೂಲಕ ಇಂಡೆಕ್ಸ್ ಮಾಡಿ. ಮರುಸಂಪರ್ಕ ಬಂದಾಗ, id > lastEventId ಇರುವ ಇವೆಂಟ್ಗಳಿಗಾಗಿ ಕ್ವೆರಿ ಮಾಡಿ ಮತ್ತು ಅವುಗಳನ್ನು ಕ್ರಮವಾಗಿ ಪ್ಲೇ ಮಾಡಿ. ನಿಮ್ಮ ಬಳಿ ನೂರಾರು ಬಾಕಿ ಇರುವ ಸಂದೇಶಗಳಿದ್ದರೆ, ಸ್ವಲ್ಪ ವಿಳಂಬ ಅಥವಾ ಬ್ಯಾಚ್ ಬಳಸಿ, ಆದರೆ ಅವುಗಳನ್ನು ಹಳೆಯದರಿಂದ ಹೊಸದಕ್ಕೆ ಕಳುಹಿಸಿ, ಇದರಿಂದ ಕ್ಲೈಂಟ್ ಕಾಲಾನುಕ್ರಮದಲ್ಲಿ ಸ್ಥಿತಿಯನ್ನು ಮರುನಿರ್ಮಿಸಬಹುದು.
ಡ್ಯೂಪ್ಲಿಕೇಟ್ಗಳನ್ನು ನಿರೀಕ್ಷಿಸಿ
ನೆಟ್ವರ್ಕ್ಗಳು ನಂಬಲರ್ಹವಲ್ಲ. ಸರ್ವರ್ ಒಂದು ಇವೆಂಟ್ ಅನ್ನು ಕಳುಹಿಸಬಹುದು, TCP ಅಕ್ನಾಲೆಡ್ಜ್ಮೆಂಟ್ ಕಳೆದುಕೊಳ್ಳಬಹುದು ಮತ್ತು ಟೈಮ್ಔಟ್ ನಂತರ ಅದನ್ನು ಮತ್ತೆ ಕಳುಹಿಸಬಹುದು. ಆರಂಭದಿಂದಲೇ at-least-once delivery ಗೆ ಅನುಗುಣವಾಗಿ ವಿನ್ಯಾಸಗೊಳಿಸಿ.
ಕ್ಲೈಂಟ್ನಲ್ಲಿ, ಡ್ಯೂಪ್ಲಿಕೇಶನ್ ತೆಗೆದುಹಾಕುವುದು ಸುಲಭ. ಇವೆಂಟ್ ID ಮೂಲಕ ಕೀ ಹೊಂದಿರುವ Map ಅನ್ನು ಇಟ್ಟುಕೊಳ್ಳಿ. ಹೊಸ ಇವೆಂಟ್ ಬಂದಾಗ, ಮ್ಯಾಪ್ ಅನ್ನು ಪರಿಶೀಲಿಸಿ. ID ಇದ್ದರೆ, ಡ್ಯೂಪ್ಲಿಕೇಟ್ ಅನ್ನು ಸುಮ್ಮನೆ ಬಿಟ್ಟುಬಿಡಿ. ನಿಮ್ಮ ಸರ್ವರ್ ನಿರ್ದಿಷ್ಟವಾದ (deterministic) IDಗಳನ್ನು ನೀಡುವ ಕಾರಣ, ಡ್ಯೂಪ್ಲಿಕೇಟ್ಗಳು ಹಾನಿಕಾರಕವಾಗಿರುವುದಿಲ್ಲ. ಮ್ಯಾಪ್ ಅನ್ನು ಸದಾ ಬೆಳೆಸುವ ಅಗತ್ಯವಿಲ್ಲ. ಒಂದು ಇವೆಂಟ್ ಸುರಕ್ಷಿತವಾಗಿ ಪ್ರೊಸೆಸ್ ಆಗಿದೆ ಎಂದು ಖಚಿತಪಡಿಸಿಕೊಂಡ ನಂತರ, ಹಳೆಯ IDಗಳನ್ನು ತೆಗೆದುಹಾಕಿ. ಬ್ರೌಸರ್ ಕ್ಲೈಂಟ್ಗಳಿಗೆ ಕೆಲವು ನೂರಾರು ಎಂಟ್ರಿಗಳ ಸ್ಲೈಡಿಂಗ್ ವಿಂಡೋ ಸಾಕು.
ಕರ್ಸರ್ ಅವಧಿ ಮುಗಿದಾಗ
ಅಂತಿಮವಾಗಿ, ಕ್ಲೈಂಟ್ ಗಂಟೆಗಟ್ಟಲೆ ಅಥವಾ ದಿನಗಳ ನಂತರ ಮರುಸಂಪರ್ಕಿಸಬಹುದು. ನಿಮ್ಮ ಇತಿಹಾಸ ಬಫರ್ ಕೇವಲ ಕಳೆದ ಸಾವಿರ ಇವೆಂಟ್ಗಳನ್ನು ಮಾತ್ರ ಒಳಗೊಂಡಿದ್ದರೆ ಮತ್ತು ಕ್ಲೈಂಟ್ ಎರಡು ಸಾವಿರ ಇವೆಂಟ್ಗಳ ಹಿಂದೆ ಇದ್ದರೆ, ಅಂತರವನ್ನು (gaps) ಪ್ಲೇ ಮಾಡುವುದು ಅಸಾಧ್ಯ.
ಅರೆಬರೆ ಇತಿಹಾಸವನ್ನು ಸ್ಟ್ರೀಮ್ ಮಾಡಬೇಡಿ. ಅದು ಕ್ಲೈಂಟ್ ಅನ್ನು ಅಸ್ಥಿರ ಸ್ಥಿತಿಯಲ್ಲಿ (inconsistent state) ಬಿಡುತ್ತದೆ. ಅದಕ್ಕೆ ಬದಲಾಗಿ, ಅವಧಿ ಮುಗಿದ ಕರ್ಸರ್ ಅನ್ನು ಪತ್ತೆಹಚ್ಚಿ ಮತ್ತು ಮುಂದಿನ ಇವೆಂಟ್ ಆಗಿ ಪೂರ್ಣ ಸ್ನ್ಯಾಪ್ಶಾಟ್ ಅನ್ನು ಕಳುಹಿಸಿ. ಸ್ನ್ಯಾಪ್ಶಾಟ್ ಹೊಸ ಕರ್ಸರ್ ಅನ್ನು ಹೊಂದಿರಬೇಕು, ಇದು ಕ್ಲೈಂಟ್ ಅನ್ನು ಪ್ರಸ್ತುತ ಸ್ಥಿತಿಗೆ ಜೋಡಿಸುತ್ತದೆ. ಅಲ್ಲಿಂದ, ಲೈವ್ ಡೆಲ್ಟಾಗಳು (live deltas) ಸಾಮಾನ್ಯ ರೀತಿಯಲ್ಲಿ ಮುಂದುವರಿಯುತ್ತವೆ. ನಿಮ್ಮ ಪ್ರೋಟೋಕಾಲ್ನಲ್ಲಿ ಈ ಗಡಿಯನ್ನು ಸ್ಪಷ್ಟವಾಗಿ ದಾಖಲಿಸಿ, ಇದರಿಂದ ಕ್ಲೈಂಟ್ ಕೋಡ್ ಡೇಟಾವನ್ನು ಸೇರಿಸುವ ಬದಲು ಯಾವಾಗ ತನ್ನ ಲೋಕಲ್ ಮಾಡೆಲ್ ಅನ್ನು ರಿಸೆಟ್ ಮಾಡಬೇಕೆಂದು ತಿಳಿಯುತ್ತದೆ.
ಸ್ಟ್ರೀಮ್ ಅನ್ನು ರಕ್ಷಿಸಿ
ಓಪನ್ SSE ಎಂಡ್ಪಾಯಿಂಟ್ಗಳು ಆಕರ್ಷಕ ಗುರಿಗಳಾಗಿವೆ. ಯಾರೇ ಆದರೂ ಕನೆಕ್ಷನ್ ಅನ್ನು ಹಿಡಿದಿಟ್ಟುಕೊಳ್ಳಬಹುದು ಮತ್ತು ರಿಪ್ಲೇ ರಿಕ್ವೆಸ್ಟ್ಗಳು ನಿಮ್ಮ ಸ್ಟೋರೇಜ್ ಮೇಲಿನ ರೀಡ್ ಲೋಡ್ ಅನ್ನು ಹೆಚ್ಚಿಸಬಹುದು.
ಎಂಡ್ಪಾಯಿಂಟ್ಗೆ ಸರಿಯಾದ ಅಧಿಕಾರೀಕರಣವನ್ನು (authorization) ಅನ್ವಯಿಸಿ. ಬ್ರೌಸರ್ನ EventSource ಕಸ್ಟಮ್ ಹೆಡರ್ಗಳನ್ನು ಬೆಂಬಲಿಸದ ಕಾರಣ, ಟೋಕನ್ ಅನ್ನು ಕ್ವೆರಿ ಸ್ಟ್ರಿಂಗ್ನಲ್ಲಿ (query string) ಕಳುಹಿಸಿ ಅಥವಾ ಕಟ್ಟುನಿಟ್ಟಾದ SameSite ನೀತಿಗಳಿರುವ ಕುಕೀಗಳನ್ನು ಬಳಸಿ. ಸ್ಟ್ರೀಮ್ ಸಂಪನ್ಮೂಲಗಳನ್ನು (stream resources) ಹಂಚಿಕೆ ಮಾಡುವ ಮೊದಲು ಟೋಕನ್ ಅನ್ನು ಪರಿಶೀಲಿಸಿ.
ಇತಿಹಾಸದ ಮಿತಿಗಳು (history limits) ಮತ್ತು ಪ್ರತಿ ಬಳಕೆದಾರನಿಗಿರುವ ಕೋಟಾಗಳನ್ನು (per-user quotas) ನಿಗದಿಪಡಿಸಿ. ಪ್ರತಿ ಕಾರ್ಯಕ್ಕೆ (task) ಸಂಗ್ರಹಿಸಲಾದ ಘಟನೆಗಳ ಸಂಖ್ಯೆ ಮತ್ತು ಪ್ರತಿ ಕ್ಲೈಂಟ್ಗೆ ಏಕಕಾಲಿಕ ಸಂಪರ್ಕಗಳ (concurrent connections) ಸಂಖ್ಯೆಯನ್ನು ಮಿತಿಗೊಳಿಸಿ. ಡಿಸ್ಕನೆಕ್ಟ್ಗಳು ಮತ್ತು ರಿಪ್ಲೇಗಳನ್ನು (replays) ಲಾಗ್ ಮಾಡಿ, ಇದರಿಂದ ನಿಮ್ಮ ಕರ್ಸರ್ ಎಂಡ್ಪಾಯಿಂಟ್ಗೆ ಅತಿಯಾದ ವಿನಂತಿಗಳನ್ನು ಕಳುಹಿಸುವ (hammering) ಅಸಹಜ ಕ್ಲೈಂಟ್ಗಳನ್ನು ನೀವು ಪತ್ತೆಹಚ್ಚಬಹುದು.
ಈ ಮಾದರಿಯು ಎಲ್ಲೆಡೆ ಅನ್ವಯಿಸುತ್ತದೆ
ಈ ವಿಧಾನವು ಕೇವಲ HTTP ಗೆ ಮಾತ್ರ ಸೀಮಿತವಾಗಿಲ್ಲ. ನೀವು WebSockets, ಮೆಸೇಜ್ ಕ್ಯೂಗಳು (message queues) ಅಥವಾ ಏಜೆಂಟ್-ಟು-ಏಜೆಂಟ್ ಇಂಟರ್ಫೇಸ್ಗಳಿಗೆ ಬದಲಾದಾಗಲೂ ಇದೇ ನಿಯಮಗಳು ಅನ್ವಯಿಸುತ್ತವೆ. ಸಾರಿಗೆ ವಿಧಾನವು (transport) ಬದಲಾಗಬಹುದು—ನೀವು ಬೈನರಿ ಫ್ರೇಮ್ಗಳು ಅಥವಾ ಟಾಪಿಕ್ ಸಬ್ಸ್ಕ್ರಿಪ್ಷನ್ಗಳನ್ನು ಬಳಸಬಹುದು—ಆದರೆ ಮೂಲ ಸಮಸ್ಯೆ ಮಾತ್ರ ಒಂದೇ ಆಗಿರುತ್ತದೆ. ನಿಮಗೆ ಒಂದು ಕರ್ಸರ್, ಸುಸ್ಥಿರ ಲಾಗ್ (durable log), at-least-once semantics, ಕ್ಲೈಂಟ್ ಡಿಡ್ಯೂಪ್ಲಿಕೇಶನ್ ಮತ್ತು ಕರ್ಸರ್ ಹಳೆಯದಾದಾಗ (stale) ಪೂರ್ಣ ಸ್ನ್ಯಾಪ್ಶಾಟ್ಗಳಿಗೆ ಫಾಲ್ಬ್ಯಾಕ್ ಅಗತ್ಯವಿರುತ್ತದೆ. ಸ್ಟೇಟ್ ಕನ್ವರ್ಜೆನ್ಸ್ (state convergence) ಸಮಸ್ಯೆಯನ್ನು ಒಮ್ಮೆ ಪರಿಹರಿಸಿದರೆ, ನೀವು ಕೋರ್ ಲಾಜಿಕ್ ಅನ್ನು ಮರು ವಿನ್ಯಾಸಗೊಳಿಸದೆ TCP, WebSocket ಅಥವಾ RabbitMQ ನಂತಹ ಬ್ರೋಕರ್ ಮೂಲಕ ಅದನ್ನು ಬಳಸಬಹುದು.
ಸರಳವಾಗಿಡಿ
Server-Sent Events ಸಾಮಾನ್ಯ HTTP ಮೇಲೆ ಕಾರ್ಯನಿರ್ವಹಿಸುವುದರಿಂದ ಸುಲಭವಾಗಿ ಕೆಲಸ ಮಾಡುತ್ತವೆ. ಪ್ರೊಕ್ಸಿಗಳು (Proxies) ಅವುಗಳನ್ನು ಅರ್ಥಮಾಡಿಕೊಳ್ಳುತ್ತವೆ. ಲೋಡ್ ಬ್ಯಾಲೆನ್ಸರ್ಗಳು ಅವುಗಳ ಆರೋಗ್ಯವನ್ನು (health-check) ಪರಿಶೀಲಿಸಬಹುದು. ಡಿಬಗ್ ಮಾಡುವುದು curl ನಷ್ಟೇ ಸುಲಭ. ಆದರೆ ನೀವು ಎಡ್ಜ್ ಕೇಸ್ಗಳನ್ನು (edge cases) ನಿರ್ಲಕ್ಷಿಸಿದರೆ ಆ ಸರಳತೆ ಮಾಯವಾಗುತ್ತದೆ. ಕರ್ಸರ್ ಅನ್ನು ನಿರ್ಮಿಸಿ. ರಿಪ್ಲೇಗಳನ್ನು ನಿರೀಕ್ಷಿಸಿ. ಕ್ಲೈಂಟ್ ಮಟ್ಟದಲ್ಲಿ ಡಿಡ್ಯೂಪ್ಲಿಕೇಶನ್ ಮಾಡಿ. ಇತಿಹಾಸ ಮುಗಿದಾಗ ಸ್ನ್ಯಾಪ್ಶಾಟ್ ತೆಗೆದುಕೊಳ್ಳಿ. ಹೀಗೆ ಮಾಡುವುದರಿಂದ, ಅಸ್ಥಿರ Wi-Fi, ಸರ್ವರ್ ರೀಸ್ಟಾರ್ಟ್ಗಳು ಮತ್ತು ರಾತ್ರಿಯ ಸಮಯದಲ್ಲಿ ಬ್ರೌಸರ್ ಸ್ಲೀಪ್ ಮೋಡ್ಗೆ ಹೋದರೂ ಸಹ, ನಿಮ್ಮ ದೀರ್ಘಕಾಲದ AI ಕಾರ್ಯಗಳು ತಮ್ಮ ಪ್ರಗತಿಯನ್ನು ನಿಖರವಾಗಿ ವರದಿ ಮಾಡುತ್ತವೆ.
ಮೂಲ: Build a Reconnecting SSE Task Stream with Node.js
ಚರ್ಚೆಯಲ್ಲಿ ಭಾಗವಹಿಸಿ: GyaanSetu AI Community
