- modify messages

This commit is contained in:
Richard Alam 2014-05-09 17:49:01 -07:00
parent 1e9c6e233e
commit 283a3fa3eb
19 changed files with 253 additions and 70 deletions

View File

@ -2,20 +2,25 @@ package org.bigbluebutton.conference.meeting.messaging.redis;
import java.util.HashMap;
import java.util.Map;
import org.bigbluebutton.conference.service.messaging.CreateMeetingMessage;
import org.bigbluebutton.conference.service.messaging.DestroyMeetingMessage;
import org.bigbluebutton.conference.service.messaging.EndMeetingMessage;
import org.bigbluebutton.conference.service.messaging.IMessage;
import org.bigbluebutton.conference.service.messaging.KeepAliveMessage;
import org.bigbluebutton.conference.service.messaging.MessageFromJsonConverter;
import org.bigbluebutton.conference.service.messaging.MessagingConstants;
import org.bigbluebutton.conference.service.messaging.RegisterUserMessage;
import org.bigbluebutton.conference.service.messaging.ValidateAuthTokenMessage;
import org.bigbluebutton.conference.service.messaging.redis.MessageHandler;
import org.bigbluebutton.core.api.IBigBlueButtonInGW;
import com.google.gson.Gson;
import com.google.gson.reflect.TypeToken;
import org.red5.logging.Red5LoggerFactory;
import org.slf4j.Logger;
public class MeetingMessageHandler implements MessageHandler {
private static Logger log = Red5LoggerFactory.getLogger(MeetingMessageHandler.class, "bigbluebutton");
private static final String KEEP_ALIVE_REQUEST = "KEEP_ALIVE_REQUEST";
private IBigBlueButtonInGW bbbGW;
@ -23,44 +28,39 @@ public class MeetingMessageHandler implements MessageHandler {
public void handleMessage(String pattern, String channel, String message) {
log.debug("Checking message: " + pattern + " " + channel + " " + message);
if (channel.equalsIgnoreCase(MessagingConstants.TO_MEETING_CHANNEL)) {
Gson gson = new Gson();
HashMap<String,String> map = gson.fromJson(message, new TypeToken<Map<String, String>>() {}.getType());
IMessage msg = MessageFromJsonConverter.convert(message);
String messageId = map.get("messageId");
if (messageId != null){
if (MessagingConstants.END_MEETING_REQUEST_EVENT.equalsIgnoreCase(messageId)){
String meetingId = map.get("meetingId");
log.info("Received end meeting request. Meeting id [{}]", meetingId);
bbbGW.endMeeting(meetingId);
} else if(MessagingConstants.CREATE_MEETING_REQUEST_EVENT.equalsIgnoreCase(messageId)){
String meetingID = map.get("meetingID");
log.info("Received create meeting request. Meeting id [{}]", meetingID);
Boolean record = Boolean.parseBoolean(map.get("record"));
String voiceBridge = map.get("voiceBridge");
String meetingName = map.get("meetingName");
Long duration = Long.parseLong(map.get("duration"));
bbbGW.createMeeting2(meetingID, meetingName, record, voiceBridge, duration);
} else if(MessagingConstants.DESTROY_MEETING_REQUEST_EVENT.equalsIgnoreCase(messageId)){
String meetingID = map.get("meetingID");
log.info("Received destroy meeting request. Meeting id [{}]", meetingID);
bbbGW.destroyMeeting(meetingID);
} else if (MessagingConstants.VALIDATE_AUTH_TOKEN.equals(messageId)) {
String meetingId = map.get("meeting_id");
String userId = map.get("user_id");
String token = map.get("auth_token");
String correlationId = map.get("correlation_id");
bbbGW.validateAuthToken(meetingId, userId, token, correlationId);
if (msg != null) {
if (msg instanceof EndMeetingMessage) {
EndMeetingMessage emm = (EndMeetingMessage) msg;
log.info("Received end meeting request. Meeting id [{}]", emm.meetingId);
bbbGW.endMeeting(emm.meetingId);
} else if (msg instanceof CreateMeetingMessage) {
CreateMeetingMessage emm = (CreateMeetingMessage) msg;
bbbGW.createMeeting2(emm.id, emm.name, emm.record, emm.voiceBridge, emm.duration);
} else if (msg instanceof RegisterUserMessage) {
RegisterUserMessage emm = (RegisterUserMessage) msg;
bbbGW.registerUser(emm.meetingID, emm.internalUserId, emm.fullname, emm.role, emm.externUserID, emm.authToken);
} else if (msg instanceof DestroyMeetingMessage) {
DestroyMeetingMessage emm = (DestroyMeetingMessage) msg;
log.info("Received destroy meeting request. Meeting id [{}]", emm.meetingId);
bbbGW.destroyMeeting(emm.meetingId);
} else if (msg instanceof ValidateAuthTokenMessage) {
ValidateAuthTokenMessage emm = (ValidateAuthTokenMessage) msg;
log.info("Received ValidateAuthTokenMessage toekn request. Meeting id [{}]", emm.meetingId);
bbbGW.validateAuthToken(emm.meetingId, emm.userId, emm.token, emm.replyTo);
}
}
} else if (channel.equalsIgnoreCase(MessagingConstants.TO_SYSTEM_CHANNEL)) {
Gson gson = new Gson();
HashMap<String,String> map = gson.fromJson(message, new TypeToken<Map<String, String>>() {}.getType());
String messageId = map.get("messageId");
if (messageId != null){
if(messageId.equalsIgnoreCase(KEEP_ALIVE_REQUEST)){
String keepAliveId = map.get("aliveId");
bbbGW.isAliveAudit(keepAliveId);
}
IMessage msg = MessageFromJsonConverter.convert(message);
if (msg != null) {
if (msg instanceof KeepAliveMessage) {
KeepAliveMessage emm = (KeepAliveMessage) msg;
log.info("Received KeepAliveMessage request. Meeting id [{}]", emm.keepAliveId);
bbbGW.isAliveAudit(emm.keepAliveId);
}
}
}
}

View File

@ -0,0 +1,88 @@
package org.bigbluebutton.conference.service.messaging;
public class Constants {
public static final String NAME = "name";
public static final String HEADER = "header";
public static final String PAYLOAD = "payload";
public static final String MEETING_ID = "meeting_id";
public static final String TIMESTAMP = "timestamp";
public static final String USER_ID = "userid";
public static final String RECORDED = "recorded";
public static final String MEETING_NAME = "meeting_name";
public static final String VOICE_CONF = "voice_conf";
public static final String DURATION = "duration";
public static final String AUTH_TOKEN = "auth_token";
public static final String ROLE = "role";
public static final String EXT_USER_ID = "external_user_id";
public static final String REQUESTER_ID = "requester_id";
public static final String REPLY_TO = "reply_to";
public static final String LOWERED_BY = "lowered_by";
public static final String STREAM = "stream";
public static final String LOCKED = "locked";
public static final String SETTINGS = "settings";
public static final String LOCK = "lock";
public static final String EXCEPT_USERS = "except_users";
public static final String STATUS = "status";
public static final String VALUE = "value";
public static final String NEW_PRESENTER_ID = "new_presenter_id";
public static final String NEW_PRESENTER_NAME = "new_presenter_name";
public static final String ASSIGNED_BY = "assigned_by";
public static final String RECORDING = "recording";
public static final String LAYOUT_ID = "layout_id";
public static final String POLL = "poll";
public static final String POLL_ID = "poll_id";
public static final String FORCE = "force";
public static final String RESPONSE = "response";
public static final String PRESENTATION_ID = "presentation_id";
public static final String X_OFFSET = "x_offset";
public static final String Y_OFFSET = "y_offset";
public static final String WIDTH_RATIO = "width_ratio";
public static final String HEIGHT_RATIO = "height_ratio";
public static final String PAGE = "page";
public static final String SHARE = "share";
public static final String PRESENTATIONS = "presentations";
public static final String MESSAGE_KEY = "message_key";
public static final String CODE = "code";
public static final String PRESENTATION_NAME = "presentation_name";
public static final String NUM_PAGES = "num_pages";
public static final String MAX_NUM_PAGES = "max_num_pages";
public static final String PAGES_COMPLETED = "pages_completed";
public static final String MUTE = "mute";
public static final String CALLER_ID_NUM = "caller_id_num";
public static final String CALLER_ID_NAME = "caller_id_name";
public static final String TALKING = "talking";
public static final String USER = "user";
public static final String MUTED = "muted";
public static final String VOICE_USER = "voice_user";
public static final String RECORDING_FILE = "recording_file";
public static final String ANNOTATION = "annotation";
public static final String WHITEBOARD_ID = "whiteboard_id";
public static final String ENABLE = "enable";
public static final String PRESENTER = "presenter";
public static final String USERS = "users";
public static final String RAISE_HAND = "raise_hand";
public static final String HAS_STREAM = "has_stream";
public static final String WEBCAM_STREAM = "webcam_stream";
public static final String PHONE_USER = "phone_user";
public static final String PERMISSIONS = "permissions";
public static final String VALID = "valid";
public static final String CHAT_HISTORY = "chat_history";
public static final String MESSAGE = "message";
public static final String SET_BY_USER_ID = "set_by_user_id";
public static final String POLLS = "polls";
public static final String REASON = "reason";
public static final String RESPONDER = "responder";
public static final String PRESENTATION_INFO = "presentation_info";
public static final String SHAPES = "shapes";
public static final String SHAPE = "shape";
public static final String SHAPE_ID = "shape_id";
public static final String PRESENTATION = "presentation";
public static final String ID = "id";
public static final String CURRENT = "current";
public static final String PAGES = "pages";
public static final String WEB_USER_ID = "web_user_id";
public static final String JOINED = "joined";
public static final String X_PERCENT = "x_percent";
public static final String Y_PERCENT = "y_percent";
public static final String KEEP_ALIVE_ID = "keep_alive_id";
}

View File

@ -1,5 +1,12 @@
package org.bigbluebutton.conference.service.messaging;
public class KeepAliveMessage implements IMessage {
public static final String KEEP_ALIVE_REQUEST = "keep_alive_request";
public static final String VERSION = "0.0.1";
public final String keepAliveId;
public KeepAliveMessage(String keepAliveId) {
this.keepAliveId = keepAliveId;
}
}

View File

@ -15,6 +15,43 @@ public class MessageFromJsonConverter {
if (header.has("name")) {
String messageName = header.get("name").getAsString();
switch (messageName) {
case CreateMeetingMessage.CREATE_MEETING_REQUEST_EVENT:
return processCreateMeeting(payload);
case DestroyMeetingMessage.DESTROY_MEETING_REQUEST_EVENT:
return processDestroyMeeting(payload);
case EndMeetingMessage.END_MEETING_REQUEST_EVENT:
return processEndMeetingMessage(payload);
case KeepAliveMessage.KEEP_ALIVE_REQUEST:
return processKeepAlive(payload);
}
}
}
return null;
}
private static IMessage processCreateMeeting(JsonObject payload) {
String id = payload.get(Constants.MEETING_ID).getAsString();
String name = payload.get(Constants.MEETING_ID).getAsString();
Boolean record = payload.get(Constants.RECORDED).getAsBoolean();
String voiceBridge = payload.get(Constants.VOICE_CONF).getAsString();
Long duration = payload.get(Constants.DURATION).getAsLong();
return new CreateMeetingMessage(id, name, record, voiceBridge, duration);
}
private static IMessage processDestroyMeeting(JsonObject payload) {
String id = payload.get(Constants.MEETING_ID).getAsString();
return new DestroyMeetingMessage(id);
}
private static IMessage processEndMeetingMessage(JsonObject payload) {
String id = payload.get(Constants.MEETING_ID).getAsString();
return new EndMeetingMessage(id);
}
private static IMessage processKeepAlive(JsonObject payload) {
String id = payload.get(Constants.KEEP_ALIVE_ID).getAsString();
return new KeepAliveMessage(id);
}
}

View File

@ -52,6 +52,4 @@ public class MessagingConstants {
public static final String SEND_POLLS_EVENT = "SendPollsEvent";
public static final String RECORD_STATUS_EVENT = "RecordStatusEvent";
public static final String VALIDATE_AUTH_TOKEN = "validate_auth_token";
}

View File

@ -9,12 +9,14 @@ public class RegisterUserMessage implements IMessage {
public final String fullname;
public final String role;
public final String externUserID;
public final String authToken;
public RegisterUserMessage(String meetingID, String internalUserId, String fullname, String role, String externUserID) {
public RegisterUserMessage(String meetingID, String internalUserId, String fullname, String role, String externUserID, String authToken) {
this.meetingID = meetingID;
this.internalUserId = internalUserId;
this.fullname = fullname;
this.role = role;
this.externUserID = externUserID;
this.externUserID = externUserID;
this.authToken = authToken;
}
}

View File

@ -0,0 +1,18 @@
package org.bigbluebutton.conference.service.messaging;
public class ValidateAuthTokenMessage implements IMessage {
public static final String VALIDATE_AUTH_TOKEN = "validate_auth_token";
public static final String VERSION = "0.0.1";
public final String meetingId;
public final String userId;
public final String token;
public final String replyTo;
public ValidateAuthTokenMessage(String meetingId, String userId, String token, String replyTo) {
this.meetingId = meetingId;
this.userId = userId;
this.token = token;
this.replyTo = replyTo;
}
}

View File

@ -44,7 +44,7 @@ public class ParticipantsListener implements MessageHandler{
String role = payloadObject.get("role").toString().replace("\"", "");
String externUserID = payloadObject.get("external_user_id").toString().replace("\"", "");
bbbInGW.registerUser(roomName, userID, username, role, externUserID);
}
else if(eventName.equalsIgnoreCase("participant_left")){ //TODO the event name is probably incorrect
String userID = payloadObject.get("user_id").toString().replace("\"", "");

16
bigbluebutton-web/build.gradle Executable file → Normal file
View File

@ -41,15 +41,15 @@ dependencies {
compile 'redis.clients:jedis:2.0.0'
compile 'commons-pool:commons-pool:1.5.6'
compile 'commons-lang:commons-lang:2.5'
compile 'com.google.code.gson:gson:1.7.1'
compile 'com.google.code.gson:gson:1.7.1'
// Logging
// compile 'ch.qos.logback:logback-core:1.0.9@jar'
// compile 'ch.qos.logback:logback-classic:1.0.9@jar'
// compile 'org.slf4j:log4j-over-slf4j:1.7.2@jar'
// compile 'org.slf4j:jcl-over-slf4j:1.7.2@jar'
// compile 'org.slf4j:jul-to-slf4j:1.7.2@jar'
// compile 'org.slf4j:slf4j-api:1.7.2@jar'
// Logging
compile 'ch.qos.logback:logback-core:1.0.9@jar'
compile 'ch.qos.logback:logback-classic:1.0.9@jar'
compile 'org.slf4j:log4j-over-slf4j:1.7.2@jar'
compile 'org.slf4j:jcl-over-slf4j:1.7.2@jar'
compile 'org.slf4j:jul-to-slf4j:1.7.2@jar'
compile 'org.slf4j:slf4j-api:1.7.2@jar'
//junit
compile 'junit:junit:4.8.2'

1
bigbluebutton-web/grails-app/conf/BuildConfig.groovy Executable file → Normal file
View File

@ -49,6 +49,7 @@ grails.project.dependency.resolution = {
dependencies {
// specify dependencies here under either 'build', 'compile', 'runtime', 'test' or 'provided' scopes e.g.
// runtime 'mysql:mysql-connector-java:5.1.24'
}
plugins {

View File

@ -109,7 +109,7 @@ disableRecordingDefault=false
#----------------------------------------------------
# This URL is where the BBB client is accessible. When a user sucessfully
# enters a name and password, she is redirected here to load the client.
bigbluebutton.web.serverURL=http://192.168.22.137
bigbluebutton.web.serverURL=http://192.168.153.146
#----------------------------------------------------
@ -133,7 +133,7 @@ defaultConfigURL=${bigbluebutton.web.serverURL}/client/conf/config.xml
apiVersion=0.81
# Salt which is used by 3rd-party apps to authenticate api calls
securitySalt=eb0a69fe5cb03ce81f81ed64b405ec2b
securitySalt=856a5d0d0bb3fe37b1e2e6ba3f4d8287
# Directory where we drop the <meeting-id-recorded>.done file
recordStatusDir=/var/bigbluebutton/recording/status/recorded

View File

@ -371,7 +371,7 @@ class ApiController {
meetingService.addUserSession(session['user-token'], us);
// Register user into the meeting.
meetingService.registerUser(us.meetingID, us.internalUserId, us.fullname, us.role, us.externUserID)
meetingService.registerUser(us.meetingID, us.internalUserId, us.fullname, us.role, us.externUserID, us.internalUserId /* authToken for now */)
log.info("Session user token for " + us.fullname + " [" + session['user-token'] + "]")
session.setMaxInactiveInterval(SESSION_TIMEOUT);

View File

@ -80,8 +80,8 @@ public class MeetingService implements MessageListener {
sessions.put(token, user);
}
public void registerUser(String meetingID, String internalUserId, String fullname, String role, String externUserID) {
messagingService.registerUser(meetingID, internalUserId, fullname, role, externUserID)
public void registerUser(String meetingID, String internalUserId, String fullname, String role, String externUserID, String authToken) {
messagingService.registerUser(meetingID, internalUserId, fullname, role, externUserID, authToken);
}
public UserSession getUserSession(String token) {

View File

@ -5,6 +5,7 @@ import java.util.HashMap;
import org.bigbluebutton.api.messaging.converters.messages.CreateMeetingMessage;
import org.bigbluebutton.api.messaging.converters.messages.DestroyMeetingMessage;
import org.bigbluebutton.api.messaging.converters.messages.EndMeetingMessage;
import org.bigbluebutton.api.messaging.converters.messages.KeepAliveMessage;
import org.bigbluebutton.api.messaging.converters.messages.RegisterUserMessage;
public class MessageToJson {
@ -16,6 +17,7 @@ public class MessageToJson {
payload.put(Constants.USER_ID, message.internalUserId);
payload.put(Constants.ROLE, message.role);
payload.put(Constants.EXT_USER_ID, message.externUserID);
payload.put(Constants.AUTH_TOKEN, message.authToken);
java.util.HashMap<String, Object> header = MessageBuilder.buildHeader(RegisterUserMessage.REGISTER_USER, message.VERSION, null);
@ -48,5 +50,15 @@ public class MessageToJson {
java.util.HashMap<String, Object> header = MessageBuilder.buildHeader(EndMeetingMessage.END_MEETING_REQUEST_EVENT, EndMeetingMessage.VERSION, null);
return MessageBuilder.buildJson(header, payload);
}
}
public static String keepAliveMessageToJson(KeepAliveMessage msg) {
HashMap<String, Object> payload = new HashMap<String, Object>();
payload.put(Constants.KEEP_ALIVE_ID, msg.keepAliveId);
java.util.HashMap<String, Object> header = MessageBuilder.buildHeader(KeepAliveMessage.KEEP_ALIVE_REQUEST, KeepAliveMessage.VERSION, null);
return MessageBuilder.buildJson(header, payload);
}
}

View File

@ -32,5 +32,6 @@ public interface MessagingService {
String storeSubscription(String meetingId, String externalMeetingID, String callbackURL);
boolean removeSubscription(String meetingId, String subscriptionId);
List<Map<String,String>> listSubscriptions(String meetingId);
void registerUser(String meetingID, String internalUserId, String fullname, String role, String externUserID);
void registerUser(String meetingID, String internalUserId, String fullname, String role, String externUserID, String authToken);
void sendKeepAlive(String keepAliveId);
}

View File

@ -27,16 +27,20 @@ import java.util.List;
import java.util.Set;
import java.util.concurrent.Executor;
import java.util.concurrent.Executors;
import javax.imageio.ImageIO;
import org.bigbluebutton.api.messaging.converters.messages.CreateMeetingMessage;
import org.bigbluebutton.api.messaging.converters.messages.DestroyMeetingMessage;
import org.bigbluebutton.api.messaging.converters.messages.EndMeetingMessage;
import org.bigbluebutton.api.messaging.converters.messages.KeepAliveMessage;
import org.bigbluebutton.api.messaging.converters.messages.RegisterUserMessage;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import com.google.gson.Gson;
import com.google.gson.reflect.TypeToken;
import redis.clients.jedis.Jedis;
import redis.clients.jedis.JedisPool;
import redis.clients.jedis.JedisPubSub;
@ -57,8 +61,8 @@ public class RedisMessagingService implements MessagingService {
sender.send(MessagingConstants.TO_MEETING_CHANNEL, json);
}
public void registerUser(String meetingID, String internalUserId, String fullname, String role, String externUserID) {
RegisterUserMessage msg = new RegisterUserMessage(meetingID, internalUserId, fullname, role, externUserID);
public void registerUser(String meetingID, String internalUserId, String fullname, String role, String externUserID, String authToken) {
RegisterUserMessage msg = new RegisterUserMessage(meetingID, internalUserId, fullname, role, externUserID, authToken);
String json = MessageToJson.registerUserToJson(msg);
sender.send(MessagingConstants.TO_MEETING_CHANNEL, json);
}
@ -75,6 +79,12 @@ public class RedisMessagingService implements MessagingService {
sender.send(MessagingConstants.TO_MEETING_CHANNEL, json);
}
public void sendKeepAlive(String keepAliveId) {
KeepAliveMessage msg = new KeepAliveMessage(keepAliveId);
String json = MessageToJson.keepAliveMessageToJson(msg);
sender.send(MessagingConstants.TO_SYSTEM_CHANNEL, json);
}
public void send(String channel, String message) {
sender.send(channel, message);
}

View File

@ -0,0 +1,12 @@
package org.bigbluebutton.api.messaging.converters.messages;
public class KeepAliveMessage {
public static final String KEEP_ALIVE_REQUEST = "keep_alive_request";
public static final String VERSION = "0.0.1";
public final String keepAliveId;
public KeepAliveMessage(String keepAliveId) {
this.keepAliveId = keepAliveId;
}
}

View File

@ -9,12 +9,14 @@ public class RegisterUserMessage {
public final String fullname;
public final String role;
public final String externUserID;
public final String authToken;
public RegisterUserMessage(String meetingID, String internalUserId, String fullname, String role, String externUserID) {
public RegisterUserMessage(String meetingID, String internalUserId, String fullname, String role, String externUserID, String authToken) {
this.meetingID = meetingID;
this.internalUserId = internalUserId;
this.fullname = fullname;
this.role = role;
this.externUserID = externUserID;
this.externUserID = externUserID;
this.authToken = authToken;
}
}

View File

@ -127,14 +127,9 @@ public class KeepAliveService implements MessageListener {
private void processPing(KeepAlivePing msg) {
if (pingMessages.size() < maxLives) {
HashMap<String,String> map = new HashMap<String,String>();
map.put("messageId", KEEP_ALIVE_REQUEST);
map.put("aliveId", msg.getId());
Gson gson = new Gson();
pingMessages.add(msg.getId());
log.debug("Sending keep alive message to bbb-apps. keep-alive id [{}]", msg.getId());
service.send(MessagingConstants.TO_SYSTEM_CHANNEL, gson.toJson(map));
service.sendKeepAlive(msg.getId());
} else {
// BBB-Apps has gone down. Mark it as unavailable and clear
// pending ping messages. This allows us to continue to send ping messages