You can not select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.

subscriber.js 3.9KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125
  1. // @flow
  2. import { getCurrentConference } from '../base/conference';
  3. import { JitsiConferenceEvents } from '../base/lib-jitsi-meet';
  4. import { StateListenerRegistry } from '../base/redux';
  5. import {
  6. NOTIFICATION_TIMEOUT,
  7. NOTIFICATION_TYPE,
  8. showNotification
  9. } from '../notifications';
  10. import { receiveAnswer, receivePoll } from './actions';
  11. import { COMMAND_NEW_POLL, COMMAND_ANSWER_POLL, COMMAND_OLD_POLLS } from './constants';
  12. import type { Answer, Poll } from './types';
  13. const parsePollData = (pollData): Poll | null => {
  14. if (typeof pollData !== 'object' || pollData === null) {
  15. return null;
  16. }
  17. const { id, senderId, senderName, question, answers } = pollData;
  18. if (typeof id !== 'string' || typeof senderId !== 'string' || typeof senderName !== 'string'
  19. || typeof question !== 'string' || !(answers instanceof Array)) {
  20. return null;
  21. }
  22. const answersParsed = [];
  23. for (const answer of answers) {
  24. const voters = new Map();
  25. for (const [ voterId, voter ] of Object.entries(answer.voters)) {
  26. if (typeof voter !== 'string') {
  27. return null;
  28. }
  29. voters.set(voterId, voter);
  30. }
  31. answersParsed.push({
  32. name: answer.name,
  33. voters
  34. });
  35. }
  36. return {
  37. senderId,
  38. senderName,
  39. question,
  40. showResults: true,
  41. lastVote: null,
  42. answers: answersParsed
  43. };
  44. };
  45. StateListenerRegistry.register(
  46. state => getCurrentConference(state),
  47. (conference, store, previousConference) => {
  48. if (conference && conference !== previousConference) {
  49. const receiveMessage = (_, data) => {
  50. switch (data.type) {
  51. case COMMAND_NEW_POLL: {
  52. const { question, answers, pollId, senderId, senderName } = data;
  53. const poll = {
  54. senderId,
  55. senderName,
  56. showResults: false,
  57. lastVote: null,
  58. question,
  59. answers: answers.map(answer => {
  60. return {
  61. name: answer,
  62. voters: new Map()
  63. };
  64. })
  65. };
  66. store.dispatch(receivePoll(pollId, poll, true));
  67. store.dispatch(showNotification({
  68. appearance: NOTIFICATION_TYPE.NORMAL,
  69. titleKey: 'polls.notification.title',
  70. descriptionKey: 'polls.notification.description'
  71. }, NOTIFICATION_TIMEOUT));
  72. break;
  73. }
  74. case COMMAND_ANSWER_POLL: {
  75. const { pollId, answers, voterId, voterName } = data;
  76. const receivedAnswer: Answer = {
  77. voterId,
  78. voterName,
  79. pollId,
  80. answers
  81. };
  82. store.dispatch(receiveAnswer(pollId, receivedAnswer));
  83. break;
  84. }
  85. case COMMAND_OLD_POLLS: {
  86. const { polls } = data;
  87. for (const pollData of polls) {
  88. const poll = parsePollData(pollData);
  89. if (poll === null) {
  90. console.warn('[features/polls] Invalid old poll data');
  91. } else {
  92. store.dispatch(receivePoll(pollData.id, poll, false));
  93. }
  94. }
  95. break;
  96. }
  97. }
  98. };
  99. conference.on(JitsiConferenceEvents.ENDPOINT_MESSAGE_RECEIVED, receiveMessage);
  100. conference.on(JitsiConferenceEvents.NON_PARTICIPANT_MESSAGE_RECEIVED, receiveMessage);
  101. }
  102. }
  103. );