diff --git a/bigbluebutton-html5/imports/api/meetings/server/modifiers/clearMeetings.js b/bigbluebutton-html5/imports/api/meetings/server/modifiers/clearMeetings.js
index 627b1491142927531b0726269441ce5c08d2a877..65e2e45fdc65e7986534990e60cb998e17e54d44 100755
--- a/bigbluebutton-html5/imports/api/meetings/server/modifiers/clearMeetings.js
+++ b/bigbluebutton-html5/imports/api/meetings/server/modifiers/clearMeetings.js
@@ -5,13 +5,12 @@ import removeMeeting from './removeMeeting';
 import { clearUsersCollection } from '/imports/api/users/server/modifiers/clearUsersCollection';
 import clearChats from '/imports/api/chat/server/modifiers/clearChats';
 import { clearShapesCollection } from '/imports/api/shapes/server/modifiers/clearShapesCollection';
-import { clearSlidesCollection } from '/imports/api/slides/server/modifiers/clearSlidesCollection';
+import clearSlides from '/imports/api/slides/server/modifiers/clearSlides';
 import { clearPollCollection } from '/imports/api/polls/server/modifiers/clearPollCollection';
 import { clearCursorCollection } from '/imports/api/cursor/server/modifiers/clearCursorCollection';
 import { clearCaptionsCollection }
   from '/imports/api/captions/server/modifiers/clearCaptionsCollection';
-import { clearPresentationsCollection }
-  from '/imports/api/presentations/server/modifiers/clearPresentationsCollection';
+import clearPresentations from '/imports/api/presentations/server/modifiers/clearPresentations';
 
 export default function clearMeetings() {
   return Meetings.remove({}, (err) => {
@@ -19,9 +18,9 @@ export default function clearMeetings() {
     clearChats();
     clearCursorCollection();
     clearPollCollection();
-    clearPresentationsCollection();
+    clearPresentations();
     clearShapesCollection();
-    clearSlidesCollection();
+    clearSlides();
     clearUsersCollection();
 
     return Logger.info('Cleared Meetings (all)');
diff --git a/bigbluebutton-html5/imports/api/meetings/server/modifiers/removeMeeting.js b/bigbluebutton-html5/imports/api/meetings/server/modifiers/removeMeeting.js
index 2fc7118f68df219f22593d9911f144e522454154..d3379a15f9bf197316763e50adf5245b9ee169ee 100755
--- a/bigbluebutton-html5/imports/api/meetings/server/modifiers/removeMeeting.js
+++ b/bigbluebutton-html5/imports/api/meetings/server/modifiers/removeMeeting.js
@@ -5,13 +5,12 @@ import Logger from '/imports/startup/server/logger';
 import { clearUsersCollection } from '/imports/api/users/server/modifiers/clearUsersCollection';
 import clearChats from '/imports/api/chat/server/modifiers/clearChats';
 import { clearShapesCollection } from '/imports/api/shapes/server/modifiers/clearShapesCollection';
-import { clearSlidesCollection } from '/imports/api/slides/server/modifiers/clearSlidesCollection';
+import clearSlides from '/imports/api/slides/server/modifiers/clearSlides';
 import { clearPollCollection } from '/imports/api/polls/server/modifiers/clearPollCollection';
 import { clearCursorCollection } from '/imports/api/cursor/server/modifiers/clearCursorCollection';
 import { clearCaptionsCollection }
   from '/imports/api/captions/server/modifiers/clearCaptionsCollection';
-import { clearPresentationsCollection }
-  from '/imports/api/presentations/server/modifiers/clearPresentationsCollection';
+import clearPresentations from '/imports/api/presentations/server/modifiers/clearPresentations';
 
 export default function removeMeeting(meetingId) {
   check(meetingId, String);
@@ -30,9 +29,9 @@ export default function removeMeeting(meetingId) {
       clearChats(meetingId);
       clearCursorCollection(meetingId);
       clearPollCollection(meetingId);
-      clearPresentationsCollection(meetingId);
+      clearPresentations(meetingId);
       clearShapesCollection(meetingId);
-      clearSlidesCollection(meetingId);
+      clearSlides(meetingId);
       clearUsersCollection(meetingId);
 
       return Logger.info(`Removed meeting id=${meetingId}`);
diff --git a/bigbluebutton-html5/imports/api/presentations/server/eventHandlers.js b/bigbluebutton-html5/imports/api/presentations/server/eventHandlers.js
new file mode 100644
index 0000000000000000000000000000000000000000..aebbffb09bdc455412ef6b1b0b45060eb4481b88
--- /dev/null
+++ b/bigbluebutton-html5/imports/api/presentations/server/eventHandlers.js
@@ -0,0 +1,8 @@
+import RedisPubSub from '/imports/startup/server/redis';
+import handlePresentationRemove from './handlers/presentationRemove';
+import handlePresentationChange from './handlers/presentationChange';
+import handlePresentationInfoReply from './handlers/presentationInfoReply';
+
+RedisPubSub.on('presentation_removed_message', handlePresentationRemove);
+RedisPubSub.on('presentation_shared_message', handlePresentationChange);
+RedisPubSub.on('get_presentation_info_reply', handlePresentationInfoReply);
diff --git a/bigbluebutton-html5/imports/api/presentations/server/handlers/presentationChange.js b/bigbluebutton-html5/imports/api/presentations/server/handlers/presentationChange.js
new file mode 100644
index 0000000000000000000000000000000000000000..3c1731aa1d3f4d4a3cee285a37791b9eb4537ef7
--- /dev/null
+++ b/bigbluebutton-html5/imports/api/presentations/server/handlers/presentationChange.js
@@ -0,0 +1,44 @@
+import { check } from 'meteor/check';
+import Logger from '/imports/startup/server/logger';
+import Presentations from '/imports/api/presentations';
+
+import addPresentation from '../modifiers/addPresentation';
+
+const clearCurrentPresentation = (meetingId, presentationId) => {
+  let selector = {
+    meetingId,
+    presentationId: { $ne: presentationId },
+    'presentation.current': true,
+  };
+
+  let modifier = {
+    $set: { 'presentation.current': false },
+  };
+
+  let cb = (err, numChanged) => {
+    if (err) {
+      return Logger.error(`Unsetting the current presentation: ${err}`);
+    }
+
+    if (numChanged) {
+      return Logger.info(`Unsetted as current presentation`);
+    }
+  };
+
+  return Presentations.update(selector, modifier, cb);
+};
+
+export default function handlePresentationChange({ payload }) {
+  const meetingId = payload.meeting_id;
+  const presentation = payload.presentation;
+
+  check(meetingId, String);
+  check(presentation, Object);
+
+  // We need to clear the flag of the older current presentation ¯\_(ツ)_/¯
+  if (presentation.current) {
+    clearCurrentPresentation(meetingId, presentation.id);
+  }
+
+  return addPresentation(meetingId, presentation);
+};
diff --git a/bigbluebutton-html5/imports/api/presentations/server/handlers/presentationInfoReply.js b/bigbluebutton-html5/imports/api/presentations/server/handlers/presentationInfoReply.js
new file mode 100644
index 0000000000000000000000000000000000000000..0b42afd2db713c7447a664ca502e4d6a6b797d7d
--- /dev/null
+++ b/bigbluebutton-html5/imports/api/presentations/server/handlers/presentationInfoReply.js
@@ -0,0 +1,24 @@
+import Logger from '/imports/startup/server/logger';
+import { check } from 'meteor/check';
+import { inReplyToHTML5Client } from '/imports/api/common/server/helpers';
+
+import addPresentation from '../modifiers/addPresentation';
+
+export default function handlePresentationInfoReply({ payload }) {
+  if (!inReplyToHTML5Client({ payload })) {
+    return;
+  }
+
+  const meetingId = payload.meeting_id;
+  const presentations = payload.presentations;
+
+  check(meetingId, String);
+  check(presentations, Array);
+
+  let presentationsAdded = [];
+  presentations.forEach(presentation => {
+    presentationsAdded.push(addPresentation(meetingId, presentation));
+  });
+
+  return presentationsAdded;
+};
diff --git a/bigbluebutton-html5/imports/api/presentations/server/handlers/presentationRemove.js b/bigbluebutton-html5/imports/api/presentations/server/handlers/presentationRemove.js
new file mode 100644
index 0000000000000000000000000000000000000000..ba589c6484ad4375e0a6d926ba736b15c8f309c2
--- /dev/null
+++ b/bigbluebutton-html5/imports/api/presentations/server/handlers/presentationRemove.js
@@ -0,0 +1,14 @@
+import Logger from '/imports/startup/server/logger';
+import { check } from 'meteor/check';
+
+import removePresentation from '../modifiers/removePresentation';
+
+export default function handlePresentationRemove({ payload }) {
+  const meetingId = payload.meeting_id;
+  const presentationId = payload.presentation_id;
+
+  check(meetingId, String);
+  check(presentationId, String);
+
+  return removePresentation(meetingId, presentationId);
+};
diff --git a/bigbluebutton-html5/imports/api/presentations/server/index.js b/bigbluebutton-html5/imports/api/presentations/server/index.js
new file mode 100644
index 0000000000000000000000000000000000000000..92451ac76bf27410726e8f3cd2eebac46cd7b83e
--- /dev/null
+++ b/bigbluebutton-html5/imports/api/presentations/server/index.js
@@ -0,0 +1,3 @@
+import './eventHandlers';
+import './methods';
+import './publishers';
diff --git a/bigbluebutton-html5/imports/api/presentations/server/methods.js b/bigbluebutton-html5/imports/api/presentations/server/methods.js
new file mode 100644
index 0000000000000000000000000000000000000000..1ce65c369863cac02b7c5224a46ab766a38cf8b3
--- /dev/null
+++ b/bigbluebutton-html5/imports/api/presentations/server/methods.js
@@ -0,0 +1,4 @@
+import { Meteor } from 'meteor/meteor';
+
+Meteor.methods({
+});
diff --git a/bigbluebutton-html5/imports/api/presentations/server/modifiers/addPresentation.js b/bigbluebutton-html5/imports/api/presentations/server/modifiers/addPresentation.js
new file mode 100755
index 0000000000000000000000000000000000000000..e87c110988f1f54a453921670c0be3074965af59
--- /dev/null
+++ b/bigbluebutton-html5/imports/api/presentations/server/modifiers/addPresentation.js
@@ -0,0 +1,55 @@
+import { check } from 'meteor/check';
+import Presentations from '/imports/api/presentations';
+import Logger from '/imports/startup/server/logger';
+
+import addSlide from '/imports/api/slides/server/modifiers/addSlide';
+
+const addSlides = (meetingId, presentationId, slides) => {
+  let slidesAdded = [];
+
+  slides.forEach(slide => {
+    slidesAdded.push(addSlide(meetingId, presentationId, slide));
+  });
+
+  return slidesAdded;
+};
+
+export default function addPresentation(meetingId, presentation) {
+  check(meetingId, String);
+  check(presentation, Object);
+
+  const selector = {
+    meetingId,
+    'presentation.id': presentation.id,
+  };
+
+  const modifier = {
+    $set: {
+      meetingId,
+      presentation: {
+        id: presentation.id,
+        name: presentation.name,
+        current: presentation.current,
+      },
+    },
+  };
+
+  const cb = (err, numChanged) => {
+    if (err) {
+      return Logger.error(`Adding presentation to collection: ${err}`);
+    }
+
+    addSlides(meetingId, presentation.id, presentation.pages);
+
+    const { insertedId } = numChanged;
+    if (insertedId) {
+      return Logger.info(`Added presentation id=${presentation.id} meeting=${meetingId}`);
+    }
+
+    if (numChanged) {
+      return Logger.info(`Upserted presentation id=${presentation.id} meeting=${meetingId}`);
+    }
+  };
+
+  return Presentations.upsert(selector, modifier, cb);
+};
diff --git a/bigbluebutton-html5/imports/api/presentations/server/modifiers/addPresentationToCollection.js b/bigbluebutton-html5/imports/api/presentations/server/modifiers/addPresentationToCollection.js
deleted file mode 100755
index 7ee32531da9fb7654ea37f287dfac3a928165e81..0000000000000000000000000000000000000000
--- a/bigbluebutton-html5/imports/api/presentations/server/modifiers/addPresentationToCollection.js
+++ /dev/null
@@ -1,23 +0,0 @@
-import Presentations from '/imports/api/presentations';
-
-export function addPresentationToCollection(meetingId, presentationObject) {
-  //check if the presentation is already in the collection
-  const presentationObj = Presentations.findOne({
-    meetingId: meetingId,
-    'presentation.id': presentationObject.id,
-  });
-  if (presentationObj == null) {
-    const entry = {
-      meetingId: meetingId,
-      presentation: {
-        id: presentationObject.id,
-        name: presentationObject.name,
-        current: presentationObject.current,
-      },
-    };
-    return Presentations.insert(entry);
-
-    //logger.info "presentation added id =[#{id}]:#{presentationObject.id} in #{meetingId}.
-    // Presentations.size is now #{Presentations.find({meetingId: meetingId}).count()}"
-  }
-};
diff --git a/bigbluebutton-html5/imports/api/presentations/server/modifiers/changeCurrentPresentation.js b/bigbluebutton-html5/imports/api/presentations/server/modifiers/changeCurrentPresentation.js
new file mode 100644
index 0000000000000000000000000000000000000000..8657e563aa397511e34c4c608b2ebf39fd0681b2
--- /dev/null
+++ b/bigbluebutton-html5/imports/api/presentations/server/modifiers/changeCurrentPresentation.js
@@ -0,0 +1,53 @@
+import { check } from 'meteor/check';
+import Presentations from '/imports/api/presentations';
+import Logger from '/imports/startup/server/logger';
+
+export default function changeCurrentPresentation(meetingId, presentationId) {
+  check(meetingId, String);
+  check(presentationId, String);
+
+  const oldCurrent = {
+    selector: {
+      meetingId,
+      'presentation.current': true,
+    },
+    modifier: {
+      $set: { 'presentation.current': false },
+    },
+    callback: (err) => {
+      if (err) {
+        return Logger.error(`Unsetting the current presentation: ${err}`);
+      }
+
+      return Logger.info(`Unsetted as current presentation`);
+    },
+  };
+
+  const newCurrent = {
+    selector: {
+      meetingId,
+      'presentation.id': presentationId,
+    },
+    modifier: {
+      $set: { 'presentation.current': true },
+    },
+    callback: (err) => {
+      if (err) {
+        return Logger.error(`Setting as current presentation id=${presentationId}: ${err}`);
+      }
+
+      return Logger.info(`Setted as current presentation id=${presentationId}`);
+    },
+  };
+
+  const oldPresentation = Presentations.findOne(oldCurrent.selector);
+  const newPresentation = Presentations.findOne(newCurrent.selector);
+
+  if (newPresentation) {
+    Presentations.update(newPresentation._id, newCurrent.modifier, newCurrent.callback);
+  }
+
+  if (oldPresentation) {
+    Presentations.update(oldPresentation._id, oldCurrent.modifier, oldCurrent.callback);
+  }
+};
diff --git a/bigbluebutton-html5/imports/api/presentations/server/modifiers/clearPresentations.js b/bigbluebutton-html5/imports/api/presentations/server/modifiers/clearPresentations.js
new file mode 100755
index 0000000000000000000000000000000000000000..4301e5185679553571e6c9010ab3e2f76cf22c4c
--- /dev/null
+++ b/bigbluebutton-html5/imports/api/presentations/server/modifiers/clearPresentations.js
@@ -0,0 +1,11 @@
+import Presentations from '/imports/api/slides';
+import Logger from '/imports/startup/server/logger';
+
+export default function clearPresentations(meetingId) {
+  if (meetingId) {
+    return Presentations.remove({ meetingId: meetingId },
+      Logger.info(`Cleared Presentations (${meetingId})`));
+  } else {
+    return Presentations.remove({}, Logger.info('Cleared Presentations (all)'));
+  }
+};
diff --git a/bigbluebutton-html5/imports/api/presentations/server/modifiers/clearPresentationsCollection.js b/bigbluebutton-html5/imports/api/presentations/server/modifiers/clearPresentationsCollection.js
deleted file mode 100755
index 2fb5af1d18dfd8a450e5847699d8c05e143a5c16..0000000000000000000000000000000000000000
--- a/bigbluebutton-html5/imports/api/presentations/server/modifiers/clearPresentationsCollection.js
+++ /dev/null
@@ -1,14 +0,0 @@
-import Presentations from '/imports/api/presentations';
-import { logger } from '/imports/startup/server/logger';
-
-// called on server start and meeting end
-export function clearPresentationsCollection() {
-  const meetingId = arguments[0];
-  if (meetingId != null) {
-    return Presentations.remove({
-      meetingId: meetingId,
-    }, logger.info(`cleared Presentations Collection (meetingId: ${meetingId}!`));
-  } else {
-    return Presentations.remove({}, logger.info('cleared Presentations Collection(all meetings)!'));
-  }
-};
diff --git a/bigbluebutton-html5/imports/api/presentations/server/modifiers/eventHandlers.js b/bigbluebutton-html5/imports/api/presentations/server/modifiers/eventHandlers.js
deleted file mode 100755
index 1808939f76a9e900eba3706e34cb62449e0f40f8..0000000000000000000000000000000000000000
--- a/bigbluebutton-html5/imports/api/presentations/server/modifiers/eventHandlers.js
+++ /dev/null
@@ -1,96 +0,0 @@
-import { eventEmitter } from '/imports/startup/server';
-import { removePresentationFromCollection } from './removePresentationFromCollection';
-import { addPresentationToCollection } from './addPresentationToCollection';
-import { appendMessageHeader, publish, inReplyToHTML5Client }
-  from '/imports/api/common/server/helpers';
-import addSlideToCollection from '/imports/api/slides/server/modifiers/addSlideToCollection';
-import Slides from '/imports/api/slides';
-import Presentations from '/imports/api/presentations';
-import { logger } from '/imports/startup/server/logger';
-
-eventEmitter.on('presentation_removed_message', function (arg) {
-  const meetingId = arg.payload.meeting_id;
-  const presentationId = arg.payload.presentation_id;
-  if (meetingId != null && presentationId != null) {
-    removePresentationFromCollection(meetingId, presentationId);
-  }
-
-  return arg.callback();
-});
-
-eventEmitter.on('presentation_shared_message', function (arg) {
-  const payload = arg.payload;
-  const meetingId = payload.meeting_id;
-  if (payload.presentation != null && payload.presentation.id != null && meetingId != null) {
-    const presentationId = payload.presentation.id;
-
-    // change the currently displayed presentation to presentation.current = false
-    Presentations.update({
-      'presentation.current': true,
-      meetingId: meetingId,
-    }, {
-      $set: {
-        'presentation.current': false,
-      },
-    });
-
-    //update(if already present) entirely the presentation with the fresh data
-    removePresentationFromCollection(meetingId, presentationId);
-    addPresentationToCollection(meetingId, payload.presentation);
-    const pages = payload.presentation.pages;
-    for (j = 0; j < pages.length; j++) {
-      const slide = pages[j];
-      addSlideToCollection(
-        meetingId,
-        presentationId,
-        slide
-      );
-    }
-  }
-
-  return arg.callback();
-});
-
-eventEmitter.on('get_presentation_info_reply', function (arg) {
-  const REDIS_CONFIG = Meteor.settings.redis;
-
-  if (inReplyToHTML5Client(arg)) {
-    const payload = arg.payload;
-    const meetingId = payload.meeting_id;
-    const presentations = payload.presentations;
-    for (let k = 0; k < payload.presentations.length; k++) {
-      const presentation = presentations[k];
-      addPresentationToCollection(meetingId, presentation);
-      const pages = presentation.pages;
-      for (let l = 0; l < pages.length; l++) {
-        const page = pages[l];
-
-        //add the slide to the collection
-        addSlideToCollection(meetingId, presentation.id, page);
-
-        //request for shapes
-        const whiteboardId = `${presentation.id}/${page.num}`;
-
-        //logger.info "the whiteboard_id here is:" + whiteboardId
-
-        const replyTo = `${meetingId}/nodeJSapp`;
-        let message = {
-          payload: {
-            meeting_id: meetingId,
-            requester_id: 'nodeJSapp',
-            whiteboard_id: whiteboardId,
-            reply_to: replyTo,
-          },
-        };
-        if (!!whiteboardId && !!meetingId) {
-          message = appendMessageHeader('request_whiteboard_annotation_history_request', message);
-          publish(REDIS_CONFIG.channels.toBBBApps.whiteboard, message);
-        } else {
-          logger.info('did not have enough information to send a user_leaving_request');
-        }
-      }
-    }
-  }
-
-  return arg.callback();
-});
diff --git a/bigbluebutton-html5/imports/api/presentations/server/modifiers/removePresentation.js b/bigbluebutton-html5/imports/api/presentations/server/modifiers/removePresentation.js
new file mode 100644
index 0000000000000000000000000000000000000000..5af60c05c38fe2818210111b2d54daa16c65afb8
--- /dev/null
+++ b/bigbluebutton-html5/imports/api/presentations/server/modifiers/removePresentation.js
@@ -0,0 +1,28 @@
+import { check } from 'meteor/check';
+import Presentations from '/imports/api/presentations';
+import Logger from '/imports/startup/server/logger';
+
+import clearSlidesPresentation from '/imports/api/slides/server/modifiers/clearSlidesPresentation';
+
+export default function removePresentation(meetingId, presentationId) {
+  check(meetingId, String);
+  check(presentationId, String);
+
+  const selector = {
+    meetingId,
+    presentationId,
+  };
+
+  const cb = (err, numChanged) => {
+    if (err) {
+      return Logger.error(`Removing presentation from collection: ${err}`);
+    }
+
+    if (numChanged) {
+      clearSlidesPresentation(meetingId, presentationId);
+      return Logger.info(`Removed presentation id=${presentationId} meeting=${meetingId}`);
+    }
+  };
+
+  return Presentations.remove(selector, cb);
+};
diff --git a/bigbluebutton-html5/imports/api/presentations/server/modifiers/removePresentationFromCollection.js b/bigbluebutton-html5/imports/api/presentations/server/modifiers/removePresentationFromCollection.js
deleted file mode 100755
index d0c74e774379382db54cfd1f16faacf924ac60ed..0000000000000000000000000000000000000000
--- a/bigbluebutton-html5/imports/api/presentations/server/modifiers/removePresentationFromCollection.js
+++ /dev/null
@@ -1,17 +0,0 @@
-import Slides from '/imports/api/slides';
-import Presentations from '/imports/api/presentations';
-import { logger } from '/imports/startup/server/logger';
-
-export function removePresentationFromCollection(meetingId, presentationId) {
-  const presentationObject = Presentations.findOne({
-    meetingId: meetingId,
-    'presentation.id': presentationId,
-  });
-  if (presentationObject != null) {
-    Slides.remove({
-      presentationId: presentationId,
-    }, logger.info(`cleared Slides Collection (presentationId: ${presentationId}!`));
-    Presentations.remove(presentationObject._id);
-    return logger.info(`----removed presentation[${presentationId}] from ${meetingId}`);
-  }
-};
diff --git a/bigbluebutton-html5/imports/api/presentations/server/publications.js b/bigbluebutton-html5/imports/api/presentations/server/publications.js
deleted file mode 100755
index ba6d95022f16969aaae3f2c1f5909d42af44637a..0000000000000000000000000000000000000000
--- a/bigbluebutton-html5/imports/api/presentations/server/publications.js
+++ /dev/null
@@ -1,10 +0,0 @@
-import Presentations from '/imports/api/presentations';
-import { logger } from '/imports/startup/server/logger';
-
-Meteor.publish('presentations', function (credentials) {
-  const { meetingId } = credentials;
-  logger.info(`publishing presentations for ${meetingId}`);
-  return Presentations.find({
-    meetingId: meetingId,
-  });
-});
diff --git a/bigbluebutton-html5/imports/api/presentations/server/publishers.js b/bigbluebutton-html5/imports/api/presentations/server/publishers.js
new file mode 100644
index 0000000000000000000000000000000000000000..cd6be803fdd53ced02ccdcd6c9b382df88202d40
--- /dev/null
+++ b/bigbluebutton-html5/imports/api/presentations/server/publishers.js
@@ -0,0 +1,22 @@
+import { Meteor } from 'meteor/meteor';
+import { check } from 'meteor/check';
+import Presentations from '/imports/api/presentations';
+import Logger from '/imports/startup/server/logger';
+import { isAllowedTo } from '/imports/startup/server/userPermissions';
+
+Meteor.publish('presentations', (credentials) => {
+  // TODO: Some publishers have ACL and others dont
+  // if (!isAllowedTo('@@@', credentials)) {
+  //   this.error(new Meteor.Error(402, "The user was not authorized to subscribe for 'presentations'"));
+  // }
+
+  const { meetingId, requesterUserId, requesterToken } = credentials;
+
+  check(meetingId, String);
+  check(requesterUserId, String);
+  check(requesterToken, String);
+
+  Logger.info(`Publishing Presentations for ${meetingId} ${requesterUserId} ${requesterToken}`);
+
+  return Presentations.find({ meetingId });
+});
diff --git a/bigbluebutton-html5/imports/api/slides/server/modifiers/addSlideToCollection.js b/bigbluebutton-html5/imports/api/slides/server/modifiers/addSlide.js
similarity index 52%
rename from bigbluebutton-html5/imports/api/slides/server/modifiers/addSlideToCollection.js
rename to bigbluebutton-html5/imports/api/slides/server/modifiers/addSlide.js
index 020ae8c8bbf5982e87b505375a48ba77b9b4270c..93b1e0571c72632af2dc9fbfe8abc96381e72e3f 100755
--- a/bigbluebutton-html5/imports/api/slides/server/modifiers/addSlideToCollection.js
+++ b/bigbluebutton-html5/imports/api/slides/server/modifiers/addSlide.js
@@ -1,12 +1,29 @@
 import probe from 'probe-image-size';
+import { Meteor } from 'meteor/meteor';
 import { check } from 'meteor/check';
+import RedisPubSub from '/imports/startup/server/redis';
 import Slides from '/imports/api/slides';
 import Logger from '/imports/startup/server/logger';
 import { SVG, PNG } from '/imports/utils/mimeTypes';
 
+const requestWhiteboardHistory = (meetingId, slideId) => {
+  const REDIS_CONFIG = Meteor.settings.redis;
+  const CHANNEL = REDIS_CONFIG.channels.toBBBApps.whiteboard;
+  const EVENT_NAME = 'request_whiteboard_annotation_history_request';
+
+  let payload = {
+    meeting_id: meetingId,
+    requester_id: 'nodeJSapp',
+    whiteboard_id: slideId,
+    reply_to: `${meetingId}/nodeJSapp`,
+  };
+
+  return RedisPubSub.publish(CHANNEL, EVENT_NAME, payload);
+};
+
 const SUPPORTED_TYPES = [SVG, PNG];
 
-export default function addSlideToCollection(meetingId, presentationId, slide) {
+export default function addSlide(meetingId, presentationId, slide) {
   check(meetingId, String);
   check(presentationId, String);
   check(slide, Object);
@@ -21,9 +38,10 @@ export default function addSlideToCollection(meetingId, presentationId, slide) {
 
   const modifier = {
     $set: {
-      meetingId: meetingId,
-      presentationId: presentationId,
+      meetingId,
+      presentationId,
       slide: {
+        id: slide.id,
         height_ratio: slide.height_ratio,
         y_offset: slide.y_offset,
         num: slide.num,
@@ -31,7 +49,6 @@ export default function addSlideToCollection(meetingId, presentationId, slide) {
         current: slide.current,
         img_uri: imageUri,
         txt_uri: slide.txt_uri,
-        id: slide.id,
         width_ratio: slide.width_ratio,
         swf_uri: slide.swf_uri,
         thumb_uri: slide.thumb_uri,
@@ -49,27 +66,37 @@ export default function addSlideToCollection(meetingId, presentationId, slide) {
     const { insertedId } = numChanged;
 
     if (insertedId) {
-      fetchImageSizes(insertedId, imageUri);
-      return Logger.info(`Added slide id=${insertedId} to presentation=${presentationId}`);
+      requestWhiteboardHistory(meetingId, slide.id);
+      return Logger.info(`Added slide id=${slide.id} to presentation=${presentationId}`);
+    }
+
+    if (numChanged) {
+      return Logger.info(`Upserted slide id=${slide.id} to presentation=${presentationId}`);
     }
   };
 
-  return Slides.upsert(selector, modifier, cb);
+  return fetchImageSizes(imageUri)
+    .then(({ width, height }) => {
+      modifier.$set.slide.width = width;
+      modifier.$set.slide.height = height;
+
+      return Slides.upsert(selector, modifier, cb);
+    })
+    .catch(reason =>
+      Logger.error(`Error parsing image size. ${reason}. slide=${slide.id} uri=${imageUri}`));
 };
 
-const fetchImageSizes = (slideId, imageUri) =>
+const fetchImageSizes = (imageUri) =>
   probe(imageUri)
   .then(result => {
     if (!SUPPORTED_TYPES.includes(result.mime)) {
       throw `Invalid image type, received ${result.mime} expecting ${SUPPORTED_TYPES.join()}`;
     }
 
-    return Slides.update(slideId, {
-      $set: {
-        width: result.width,
-        height: result.height,
-      },
-    });
+    return {
+      width: result.width,
+      height: result.height,
+    };
   })
   .catch(reason => {
     Logger.error(`Error parsing image size. ${reason}. slide=${slide.id} uri=${imageUri}`);
diff --git a/bigbluebutton-html5/imports/api/slides/server/modifiers/changeCurrentSlide.js b/bigbluebutton-html5/imports/api/slides/server/modifiers/changeCurrentSlide.js
index f3b6db32e7f5519efc96ea4f4eba50fe4b9b396f..c022d5f042f3952aa34ca579088fad7dd3ea9472 100755
--- a/bigbluebutton-html5/imports/api/slides/server/modifiers/changeCurrentSlide.js
+++ b/bigbluebutton-html5/imports/api/slides/server/modifiers/changeCurrentSlide.js
@@ -21,7 +21,7 @@ export default function changeCurrentSlide(meetingId, presentationId, slideId) {
         return Logger.error(`Unsetting the current slide: ${err}`);
       }
 
-      return Logger.info(`Unsetted as current slide`);
+      return Logger.info(`Unsetted the current slide`);
     },
   };
 
@@ -47,10 +47,10 @@ export default function changeCurrentSlide(meetingId, presentationId, slideId) {
   const newSlide = Slides.findOne(newCurrent.selector);
 
   if (newSlide) {
-    Slides.update(newSlide.id, newCurrent.modifier, newCurrent.callback);
+    Slides.update(newSlide._id, newCurrent.modifier, newCurrent.callback);
   }
 
   if (oldSlide) {
-    Slides.update(oldSlide.id, oldCurrent.modifier, oldCurrent.callback);
+    Slides.update(oldSlide._id, oldCurrent.modifier, oldCurrent.callback);
   }
 };
diff --git a/bigbluebutton-html5/imports/api/slides/server/modifiers/clearSlidesCollection.js b/bigbluebutton-html5/imports/api/slides/server/modifiers/clearSlides.js
similarity index 83%
rename from bigbluebutton-html5/imports/api/slides/server/modifiers/clearSlidesCollection.js
rename to bigbluebutton-html5/imports/api/slides/server/modifiers/clearSlides.js
index 9de4c1f04f7eaee32d3ed2d8edcc3398f1a16da0..868290d952268eff20ea244d83ed90ab40b0e945 100755
--- a/bigbluebutton-html5/imports/api/slides/server/modifiers/clearSlidesCollection.js
+++ b/bigbluebutton-html5/imports/api/slides/server/modifiers/clearSlides.js
@@ -1,7 +1,7 @@
 import Slides from '/imports/api/slides';
 import Logger from '/imports/startup/server/logger';
 
-export default function clearSlidesCollection(meetingId) {
+export default function clearSlides(meetingId) {
   if (meetingId) {
     return Slides.remove({ meetingId: meetingId }, Logger.info(`Cleared Slides (${meetingId})`));
   } else {
diff --git a/bigbluebutton-html5/imports/api/slides/server/modifiers/clearSlidesPresentation.js b/bigbluebutton-html5/imports/api/slides/server/modifiers/clearSlidesPresentation.js
index ff7be924fec446cf4356bf35dcd730e361321adc..4d65bab039ea40c351c76ca9b9eacdc832db190c 100644
--- a/bigbluebutton-html5/imports/api/slides/server/modifiers/clearSlidesPresentation.js
+++ b/bigbluebutton-html5/imports/api/slides/server/modifiers/clearSlidesPresentation.js
@@ -2,10 +2,12 @@ import Slides from '/imports/api/slides';
 import Logger from '/imports/startup/server/logger';
 import { check } from 'meteor/check';
 
-export default function clearSlidesPresentation(presentationId) {
+export default function clearSlidesPresentation(meetingId, presentationId) {
+  check(meetingId, String);
   check(presentationId, String);
 
   const selector = {
+    meetingId,
     presentationId,
   };
 
diff --git a/bigbluebutton-html5/imports/api/slides/server/modifiers/resizeSlide.js b/bigbluebutton-html5/imports/api/slides/server/modifiers/resizeSlide.js
index 80a5ebed30997dd0f3c26ff1f65d54b8c3b13dd3..6eae4cdc3cd19399e626fff1cf8a7f408e12b00f 100644
--- a/bigbluebutton-html5/imports/api/slides/server/modifiers/resizeSlide.js
+++ b/bigbluebutton-html5/imports/api/slides/server/modifiers/resizeSlide.js
@@ -17,21 +17,21 @@ export default function resizeSlide(meetingId, presentationId, slideId, slide) {
 
   const modifier = {
     $set: {
-      slide: {
-        width_ratio: slide.width_ratio,
-        height_ratio: slide.height_ratio,
-        x_offset: slide.x_offset,
-        y_offset: slide.y_offset,
-      },
+      'slide.width_ratio': slide.width_ratio,
+      'slide.height_ratio': slide.height_ratio,
+      'slide.x_offset': slide.x_offset,
+      'slide.y_offset': slide.y_offset,
     },
   };
 
-  const cb = (err) => {
+  const cb = (err, numChanged) => {
     if (err) {
       return Logger.error(`Resizing slide id=${slideId}: ${err}`);
     }
 
-    return Logger.info(`Resized slide id=${slideId}`);
+    if (numChanged) {
+      return Logger.info(`Resized slide id=${slideId}`);
+    }
   };
 
   return Slides.update(selector, modifier, cb);
diff --git a/bigbluebutton-html5/imports/api/slides/server/publishers.js b/bigbluebutton-html5/imports/api/slides/server/publishers.js
index d1c68318a583b0ced4bedaa1b0f0ca56a5538045..0c121386e08a7fea207a68b57c3d6704338c6689 100644
--- a/bigbluebutton-html5/imports/api/slides/server/publishers.js
+++ b/bigbluebutton-html5/imports/api/slides/server/publishers.js
@@ -18,5 +18,5 @@ Meteor.publish('slides', (credentials) => {
 
   Logger.info(`Publishing Slides for ${meetingId} ${requesterUserId} ${requesterToken}`);
 
-  return Slides.find({ meetingId: meetingId });
+  return Slides.find({ meetingId });
 });
diff --git a/bigbluebutton-html5/imports/ui/components/whiteboard/container.jsx b/bigbluebutton-html5/imports/ui/components/whiteboard/container.jsx
index 09b93f2688622b75473983752470493c4215db92..3f26411e353f320913c7f3fcabfaf8bc6e23535d 100755
--- a/bigbluebutton-html5/imports/ui/components/whiteboard/container.jsx
+++ b/bigbluebutton-html5/imports/ui/components/whiteboard/container.jsx
@@ -17,7 +17,9 @@ class WhiteboardContainer extends Component {
   }
 }
 
-export default createContainer(() => {
-  const data = WhiteboardService.getWhiteboardData();
-  return data;
-}, WhiteboardContainer);
+export default createContainer(() => ({
+  currentSlide: WhiteboardService.getCurrentSlide(),
+  shapes: WhiteboardService.getCurrentShapes(),
+  cursor: WhiteboardService.getCurrentCursor(),
+  userIsPresenter: WhiteboardService.isPresenter(),
+}), WhiteboardContainer);
diff --git a/bigbluebutton-html5/imports/ui/components/whiteboard/service.js b/bigbluebutton-html5/imports/ui/components/whiteboard/service.js
index 2bb735ab8207c9a62410f8cd827eca51f5be8d04..9d1b3cc356c76e5f7c3ee51692d3a411f3220131 100755
--- a/bigbluebutton-html5/imports/ui/components/whiteboard/service.js
+++ b/bigbluebutton-html5/imports/ui/components/whiteboard/service.js
@@ -3,48 +3,47 @@ import Shapes from '/imports/api/shapes';
 import Slides from '/imports/api/slides';
 import Cursor from '/imports/api/cursor';
 import Users from '/imports/api/users';
-import AuthSingleton from '/imports/ui/services/auth/index.js';
-
-let getWhiteboardData = () => {
-  let currentSlide;
-  let shapes;
-  let cursor;
-  let userIsPresenter;
-  let currentPresentation = Presentations.findOne({
-      'presentation.current': true,
-    });
-
-  if (currentPresentation != null) {
-    currentSlide = Slides.findOne({
-      presentationId: currentPresentation.presentation.id,
-      'slide.current': true,
-    });
+import Auth from '/imports/ui/services/auth';
+
+const getCurrentPresentation = () => Presentations.findOne({
+  'presentation.current': true,
+});
+
+const getCurrentSlide = () => {
+  const currentPresentation = getCurrentPresentation();
+
+  if (!currentPresentation) {
+    return null;
   }
 
-  if (currentSlide != null) {
-    shapes = Shapes.find({
-        whiteboardId: currentSlide.slide.id,
-      }).fetch();
+  return Slides.findOne({
+    presentationId: currentPresentation.presentation.id,
+    'slide.current': true,
+  });
+};
 
-    cursor = Cursor.findOne({
-      meetingId: currentSlide.meetingId,
-    });
+const getCurrentShapes = () => {
+  const currentSlide = getCurrentSlide();
 
-    // Get user to check if they are the presenter
-    userIsPresenter = Users.findOne({
-      meetingId: currentSlide.meetingId,
-      userId: AuthSingleton.getCredentials().requesterUserId,
-    }).user.presenter;
+  if (!currentSlide) {
+    return null;
   }
 
-  return {
-    currentSlide: currentSlide,
-    shapes: shapes,
-    cursor: cursor,
-    userIsPresenter: userIsPresenter,
-  };
+  return Shapes.find({
+    whiteboardId: currentSlide.slide.id,
+  }).fetch();
 };
 
+const getCurrentCursor = () => Cursor.findOne({});
+
+const isPresenter = () => Users.findOne({
+  userId: Auth.userID,
+}).user.presenter;
+
 export default {
-  getWhiteboardData,
+  getCurrentPresentation,
+  getCurrentSlide,
+  getCurrentShapes,
+  getCurrentCursor,
+  isPresenter,
 };
diff --git a/bigbluebutton-html5/server/main.js b/bigbluebutton-html5/server/main.js
index f0d0eca31a9ce6bde0aacfba78664a7a923b65b8..6d0a06ca788dcd2ab505c32a22fe2cf2b6971d67 100755
--- a/bigbluebutton-html5/server/main.js
+++ b/bigbluebutton-html5/server/main.js
@@ -24,11 +24,7 @@ import '/imports/api/polls/server/modifiers/clearPollCollection';
 import '/imports/api/polls/server/modifiers/updatePollCollection';
 import '/imports/api/polls/server/modifiers/eventHandlers';
 
-import '/imports/api/presentations/server/publications';
-import '/imports/api/presentations/server/modifiers/addPresentationToCollection';
-import '/imports/api/presentations/server/modifiers/clearPresentationsCollection';
-import '/imports/api/presentations/server/modifiers/removePresentationFromCollection';
-import '/imports/api/presentations/server/modifiers/eventHandlers';
+import '/imports/api/presentations/server';
 
 import '/imports/api/shapes/server/publications';
 import '/imports/api/shapes/server/modifiers/addShapeToCollection';