DiscussionsDAO.getDiscussionsById(discussionIds, null, function(err, discussions) {
                    if (err) {
                        return callback(err);
                    }

                    // Emit an event indicating that the discussion library has been retrieved
                    DiscussionsAPI.emit(DiscussionsConstants.events.GET_DISCUSSION_LIBRARY, ctx, principalId, visibility, start, limit, discussions);

                    return callback(null, discussions, nextToken);
                });
    ResourceActions.create(ctx, roles, createFn, function(err, discussion, memberChangeInfo) {
        if (err) {
            return callback(err);
        }

        DiscussionsAPI.emit(DiscussionsConstants.events.CREATED_DISCUSSION, ctx, discussion, memberChangeInfo, function(errs) {
            if (errs) {
                return callback(_.first(errs));
            }

            return callback(null, discussion);
        });
    });
                AuthzAPI.updateRoles(discussionId, memberChangeInfo.changes, function(err) {
                    if (err) {
                        return callback(err);
                    }

                    DiscussionsAPI.emit(DiscussionsConstants.events.UPDATED_DISCUSSION_MEMBERS, ctx, discussion, memberChangeInfo, {}, function(errs) {
                        if (errs) {
                            return callback(_.first(errs));
                        }

                        return callback();
                    });
                });
                    DiscussionsDAO.deleteDiscussion(discussion.id, function(err) {
                        if (err) {
                            return callback(err);
                        }

                        DiscussionsAPI.emit(DiscussionsConstants.events.DELETED_DISCUSSION, ctx, discussion, removedMemberIds, function(errs) {
                            if (errs) {
                                return callback(_.first(errs));
                            }

                            return callback();
                        });
                    });
                MessageBoxAPI.deleteMessage(discussionId, messageCreatedDate, {'deleteType': MessageBoxConstants.deleteTypes.LEAF}, function(err, deleteType, deletedMessage) {
                    if (err) {
                        return callback(err);
                    }

                    DiscussionsAPI.emit(DiscussionsConstants.events.DELETED_DISCUSSION_MESSAGE, ctx, message, discussion, deleteType);

                    // If a soft-delete occurred, we want to inform the consumer of the soft-delete message model
                    if (deleteType === MessageBoxConstants.deleteTypes.SOFT) {
                        return callback(null, deletedMessage);
                    } else {
                        return callback();
                    }
                });
            PrincipalsUtil.getPrincipal(ctx, discussion.createdBy, function(err, creator) {
                if (err) {
                    log().warn({
                        'err': err,
                        'userId': discussion.createdBy,
                        'discussionId': discussion.id
                    }, 'An error occurred getting the creator of a discussion. Proceeding with empty user for full profile');
                } else if (creator) {
                    discussion.createdBy = creator;
                }

                DiscussionsAPI.emit(DiscussionsConstants.events.GET_DISCUSSION_PROFILE, ctx, discussion);
                return callback(null, discussion);
            });
        ResourceActions.setRoles(ctx, discussion, changes, function(err, memberChangeInfo) {
            if (err) {
                return callback(err);
            } else if (_.isEmpty(memberChangeInfo.changes)) {
                return callback();
            }

            DiscussionsAPI.emit(DiscussionsConstants.events.UPDATED_DISCUSSION_MEMBERS, ctx, discussion, memberChangeInfo, {}, function(errs) {
                if (errs) {
                    return callback(_.first(errs));
                }

                return callback(null, memberChangeInfo.roles.after);
            });
        });
        ResourceActions.share(ctx, discussion, principalIds, AuthzConstants.role.MEMBER, function(err, memberChangeInfo) {
            if (err) {
                return callback(err);
            } else if (_.isEmpty(memberChangeInfo.changes)) {
                return callback();
            }

            DiscussionsAPI.emit(DiscussionsConstants.events.UPDATED_DISCUSSION_MEMBERS, ctx, discussion, memberChangeInfo, {}, function(errs) {
                if (errs) {
                    return callback(_.first(errs));
                }

                return callback();
            });
        });
                PrincipalsUtil.getPrincipal(ctx, ctx.user().id, function(err, createdBy) {
                    if (err) {
                        return callback(err);
                    }

                    message.createdBy = createdBy;

                    // The message has been created in the database so we can emit the `created-message` event
                    DiscussionsAPI.emit(DiscussionsConstants.events.CREATED_DISCUSSION_MESSAGE, ctx, message, discussion, function(errs) {
                        if (errs) {
                            return callback(_.first(errs));
                        }

                        return callback(null, message);
                    });
                });
            DiscussionsDAO.updateDiscussion(discussion, profileFields, function(err, updatedDiscussion) {
                if (err) {
                    return callback(err);
                }

                // Fill in the full profile, the user has to have been a manager, so these are all true
                updatedDiscussion.isManager = true;
                updatedDiscussion.canPost = true;
                updatedDiscussion.canShare = true;

                DiscussionsAPI.emit(DiscussionsConstants.events.UPDATED_DISCUSSION, ctx, updatedDiscussion, discussion, function(errs) {
                    if (errs) {
                        return callback(_.first(errs));
                    }

                    return callback(null, updatedDiscussion);
                });
            });