Bring Core Groups up to current version

avinationmerge
root 2013-09-07 17:58:32 +02:00
parent 66715a69a7
commit 844ae7720e
12 changed files with 505 additions and 285 deletions

View File

@ -504,6 +504,30 @@ namespace OpenSim.Groups
return notice; return notice;
} }
public static Dictionary<string, object> DirGroupsReplyData(DirGroupsReplyData g)
{
Dictionary<string, object> dict = new Dictionary<string, object>();
dict["GroupID"] = g.groupID;
dict["Name"] = g.groupName;
dict["NMembers"] = g.members;
dict["SearchOrder"] = g.searchOrder;
return dict;
}
public static DirGroupsReplyData DirGroupsReplyData(Dictionary<string, object> dict)
{
DirGroupsReplyData g;
g.groupID = new UUID(dict["GroupID"].ToString());
g.groupName = dict["Name"].ToString();
Int32.TryParse(dict["NMembers"].ToString(), out g.members);
float.TryParse(dict["SearchOrder"].ToString(), out g.searchOrder);
return g;
}
} }
} }

View File

@ -39,6 +39,7 @@ using OpenSim.Region.Framework.Interfaces;
using OpenSim.Region.Framework.Scenes; using OpenSim.Region.Framework.Scenes;
using OpenSim.Services.Interfaces; using OpenSim.Services.Interfaces;
using PresenceInfo = OpenSim.Services.Interfaces.PresenceInfo; using PresenceInfo = OpenSim.Services.Interfaces.PresenceInfo;
using GridRegion = OpenSim.Services.Interfaces.GridRegion;
namespace OpenSim.Groups namespace OpenSim.Groups
{ {
@ -51,7 +52,7 @@ namespace OpenSim.Groups
private IPresenceService m_presenceService; private IPresenceService m_presenceService;
private IMessageTransferModule m_msgTransferModule = null; private IMessageTransferModule m_msgTransferModule = null;
private IUserManagement m_UserManagement = null;
private IGroupsServicesConnector m_groupData = null; private IGroupsServicesConnector m_groupData = null;
// Config Options // Config Options
@ -79,6 +80,10 @@ namespace OpenSim.Groups
private int m_usersOnlineCacheExpirySeconds = 20; private int m_usersOnlineCacheExpirySeconds = 20;
private Dictionary<UUID, List<string>> m_groupsAgentsDroppedFromChatSession = new Dictionary<UUID, List<string>>();
private Dictionary<UUID, List<string>> m_groupsAgentsInvitedToChatSession = new Dictionary<UUID, List<string>>();
#region Region Module interfaceBase Members #region Region Module interfaceBase Members
public void Initialise(IConfigSource config) public void Initialise(IConfigSource config)
@ -124,10 +129,12 @@ namespace OpenSim.Groups
m_sceneList.Add(scene); m_sceneList.Add(scene);
scene.EventManager.OnNewClient += OnNewClient; scene.EventManager.OnNewClient += OnNewClient;
scene.EventManager.OnMakeRootAgent += OnMakeRootAgent;
scene.EventManager.OnMakeChildAgent += OnMakeChildAgent;
scene.EventManager.OnIncomingInstantMessage += OnGridInstantMessage; scene.EventManager.OnIncomingInstantMessage += OnGridInstantMessage;
scene.EventManager.OnClientLogin += OnClientLogin; scene.EventManager.OnClientLogin += OnClientLogin;
} }
public void RegionLoaded(Scene scene) public void RegionLoaded(Scene scene)
{ {
if (!m_groupMessagingEnabled) if (!m_groupMessagingEnabled)
@ -155,6 +162,17 @@ namespace OpenSim.Groups
return; return;
} }
m_UserManagement = scene.RequestModuleInterface<IUserManagement>();
// No groups module, no groups messaging
if (m_UserManagement == null)
{
m_log.Error("[Groups.Messaging]: Could not get IUserManagement, GroupsMessagingModule is now disabled.");
RemoveRegion(scene);
return;
}
if (m_presenceService == null) if (m_presenceService == null)
m_presenceService = scene.PresenceService; m_presenceService = scene.PresenceService;
@ -227,87 +245,107 @@ namespace OpenSim.Groups
public void SendMessageToGroup(GridInstantMessage im, UUID groupID) public void SendMessageToGroup(GridInstantMessage im, UUID groupID)
{ {
List<GroupMembersData> groupMembers = m_groupData.GetGroupMembers(new UUID(im.fromAgentID).ToString(), groupID); UUID fromAgentID = new UUID(im.fromAgentID);
List<GroupMembersData> groupMembers = m_groupData.GetGroupMembers(UUID.Zero.ToString(), groupID);
int groupMembersCount = groupMembers.Count; int groupMembersCount = groupMembers.Count;
PresenceInfo[] onlineAgents = null;
if (m_messageOnlineAgentsOnly) // In V2 we always only send to online members.
// Sending to offline members is not an option.
string[] t1 = groupMembers.ConvertAll<string>(gmd => gmd.AgentID.ToString()).ToArray();
// We cache in order not to overwhlem the presence service on large grids with many groups. This does
// mean that members coming online will not see all group members until after m_usersOnlineCacheExpirySeconds has elapsed.
// (assuming this is the same across all grid simulators).
if (!m_usersOnlineCache.TryGetValue(groupID, out onlineAgents))
{ {
string[] t1 = groupMembers.ConvertAll<string>(gmd => gmd.AgentID.ToString()).ToArray(); onlineAgents = m_presenceService.GetAgents(t1);
m_usersOnlineCache.Add(groupID, onlineAgents, m_usersOnlineCacheExpirySeconds);
}
// We cache in order not to overwhlem the presence service on large grids with many groups. This does HashSet<string> onlineAgentsUuidSet = new HashSet<string>();
// mean that members coming online will not see all group members until after m_usersOnlineCacheExpirySeconds has elapsed. Array.ForEach<PresenceInfo>(onlineAgents, pi => onlineAgentsUuidSet.Add(pi.UserID));
// (assuming this is the same across all grid simulators).
PresenceInfo[] onlineAgents;
if (!m_usersOnlineCache.TryGetValue(groupID, out onlineAgents))
{
onlineAgents = m_presenceService.GetAgents(t1);
m_usersOnlineCache.Add(groupID, onlineAgents, m_usersOnlineCacheExpirySeconds);
}
HashSet<string> onlineAgentsUuidSet = new HashSet<string>(); groupMembers = groupMembers.Where(gmd => onlineAgentsUuidSet.Contains(gmd.AgentID.ToString())).ToList();
Array.ForEach<PresenceInfo>(onlineAgents, pi => onlineAgentsUuidSet.Add(pi.UserID));
groupMembers = groupMembers.Where(gmd => onlineAgentsUuidSet.Contains(gmd.AgentID.ToString())).ToList(); // if (m_debugEnabled)
// if (m_debugEnabled)
// m_log.DebugFormat( // m_log.DebugFormat(
// "[Groups.Messaging]: SendMessageToGroup called for group {0} with {1} visible members, {2} online", // "[Groups.Messaging]: SendMessageToGroup called for group {0} with {1} visible members, {2} online",
// groupID, groupMembersCount, groupMembers.Count()); // groupID, groupMembersCount, groupMembers.Count());
}
else
{
if (m_debugEnabled)
m_log.DebugFormat(
"[Groups.Messaging]: SendMessageToGroup called for group {0} with {1} visible members",
groupID, groupMembers.Count);
}
int requestStartTick = Environment.TickCount; int requestStartTick = Environment.TickCount;
im.imSessionID = groupID.Guid;
im.fromGroup = true;
IClientAPI thisClient = GetActiveClient(fromAgentID);
if (thisClient != null)
{
im.RegionID = thisClient.Scene.RegionInfo.RegionID.Guid;
}
// Send to self first of all
im.toAgentID = im.fromAgentID;
im.fromGroup = true;
ProcessMessageFromGroupSession(im);
List<UUID> regions = new List<UUID>();
List<UUID> clientsAlreadySent = new List<UUID>();
// Then send to everybody else
foreach (GroupMembersData member in groupMembers) foreach (GroupMembersData member in groupMembers)
{ {
if (m_groupData.hasAgentDroppedGroupChatSession(member.AgentID.ToString(), groupID)) if (member.AgentID.Guid == im.fromAgentID)
continue;
if (clientsAlreadySent.Contains(member.AgentID))
continue;
clientsAlreadySent.Add(member.AgentID);
if (hasAgentDroppedGroupChatSession(member.AgentID.ToString(), groupID))
{ {
// Don't deliver messages to people who have dropped this session // Don't deliver messages to people who have dropped this session
if (m_debugEnabled) m_log.DebugFormat("[Groups.Messaging]: {0} has dropped session, not delivering to them", member.AgentID); if (m_debugEnabled) m_log.DebugFormat("[Groups.Messaging]: {0} has dropped session, not delivering to them", member.AgentID);
continue; continue;
} }
// Copy Message im.toAgentID = member.AgentID.Guid;
GridInstantMessage msg = new GridInstantMessage();
msg.imSessionID = groupID.Guid;
msg.fromAgentName = im.fromAgentName;
msg.message = im.message;
msg.dialog = im.dialog;
msg.offline = im.offline;
msg.ParentEstateID = im.ParentEstateID;
msg.Position = im.Position;
msg.RegionID = im.RegionID;
msg.binaryBucket = im.binaryBucket;
msg.timestamp = (uint)Util.UnixTimeSinceEpoch();
msg.fromAgentID = im.fromAgentID;
msg.fromGroup = true;
msg.toAgentID = member.AgentID.Guid;
IClientAPI client = GetActiveClient(member.AgentID); IClientAPI client = GetActiveClient(member.AgentID);
if (client == null) if (client == null)
{ {
// If they're not local, forward across the grid // If they're not local, forward across the grid
// BUT do it only once per region, please! Sim would be even better!
if (m_debugEnabled) m_log.DebugFormat("[Groups.Messaging]: Delivering to {0} via Grid", member.AgentID); if (m_debugEnabled) m_log.DebugFormat("[Groups.Messaging]: Delivering to {0} via Grid", member.AgentID);
m_msgTransferModule.SendInstantMessage(msg, delegate(bool success) { });
bool reallySend = true;
if (onlineAgents != null)
{
PresenceInfo presence = onlineAgents.First(p => p.UserID == member.AgentID.ToString());
if (regions.Contains(presence.RegionID))
reallySend = false;
else
regions.Add(presence.RegionID);
}
if (reallySend)
{
// We have to create a new IM structure because the transfer module
// uses async send
GridInstantMessage msg = new GridInstantMessage(im, true);
m_msgTransferModule.SendInstantMessage(msg, delegate(bool success) { });
}
} }
else else
{ {
// Deliver locally, directly // Deliver locally, directly
if (m_debugEnabled) m_log.DebugFormat("[Groups.Messaging]: Passing to ProcessMessageFromGroupSession to deliver to {0} locally", client.Name); if (m_debugEnabled) m_log.DebugFormat("[Groups.Messaging]: Passing to ProcessMessageFromGroupSession to deliver to {0} locally", client.Name);
ProcessMessageFromGroupSession(msg);
ProcessMessageFromGroupSession(im);
} }
} }
// Temporary for assessing how long it still takes to send messages to large online groups. if (m_debugEnabled)
if (m_messageOnlineAgentsOnly)
m_log.DebugFormat( m_log.DebugFormat(
"[Groups.Messaging]: SendMessageToGroup for group {0} with {1} visible members, {2} online took {3}ms", "[Groups.Messaging]: SendMessageToGroup for group {0} with {1} visible members, {2} online took {3}ms",
groupID, groupMembersCount, groupMembers.Count(), Environment.TickCount - requestStartTick); groupID, groupMembersCount, groupMembers.Count(), Environment.TickCount - requestStartTick);
@ -324,9 +362,20 @@ namespace OpenSim.Groups
{ {
if (m_debugEnabled) m_log.DebugFormat("[Groups.Messaging]: OnInstantMessage registered for {0}", client.Name); if (m_debugEnabled) m_log.DebugFormat("[Groups.Messaging]: OnInstantMessage registered for {0}", client.Name);
client.OnInstantMessage += OnInstantMessage; ResetAgentGroupChatSessions(client.AgentId.ToString());
} }
void OnMakeRootAgent(ScenePresence sp)
{
sp.ControllingClient.OnInstantMessage += OnInstantMessage;
}
void OnMakeChildAgent(ScenePresence sp)
{
sp.ControllingClient.OnInstantMessage -= OnInstantMessage;
}
private void OnGridInstantMessage(GridInstantMessage msg) private void OnGridInstantMessage(GridInstantMessage msg)
{ {
// The instant message module will only deliver messages of dialog types: // The instant message module will only deliver messages of dialog types:
@ -335,21 +384,91 @@ namespace OpenSim.Groups
// Any other message type will not be delivered to a client by the // Any other message type will not be delivered to a client by the
// Instant Message Module // Instant Message Module
UUID regionID = new UUID(msg.RegionID);
if (m_debugEnabled) if (m_debugEnabled)
{ {
m_log.DebugFormat("[Groups.Messaging]: {0} called", System.Reflection.MethodBase.GetCurrentMethod().Name); m_log.DebugFormat("[Groups.Messaging]: {0} called, IM from region {1}",
System.Reflection.MethodBase.GetCurrentMethod().Name, regionID);
DebugGridInstantMessage(msg); DebugGridInstantMessage(msg);
} }
// Incoming message from a group // Incoming message from a group
if ((msg.fromGroup == true) && if ((msg.fromGroup == true) && (msg.dialog == (byte)InstantMessageDialog.SessionSend))
((msg.dialog == (byte)InstantMessageDialog.SessionSend)
|| (msg.dialog == (byte)InstantMessageDialog.SessionAdd)
|| (msg.dialog == (byte)InstantMessageDialog.SessionDrop)))
{ {
ProcessMessageFromGroupSession(msg); // We have to redistribute the message across all members of the group who are here
// on this sim
UUID GroupID = new UUID(msg.imSessionID);
Scene aScene = m_sceneList[0];
GridRegion regionOfOrigin = aScene.GridService.GetRegionByUUID(aScene.RegionInfo.ScopeID, regionID);
List<GroupMembersData> groupMembers = m_groupData.GetGroupMembers(UUID.Zero.ToString(), GroupID);
//if (m_debugEnabled)
// foreach (GroupMembersData m in groupMembers)
// m_log.DebugFormat("[Groups.Messaging]: member {0}", m.AgentID);
foreach (Scene s in m_sceneList)
{
s.ForEachScenePresence(sp =>
{
// If we got this via grid messaging, it's because the caller thinks
// that the root agent is here. We should only send the IM to root agents.
if (sp.IsChildAgent)
return;
GroupMembersData m = groupMembers.Find(gmd =>
{
return gmd.AgentID == sp.UUID;
});
if (m.AgentID == UUID.Zero)
{
if (m_debugEnabled)
m_log.DebugFormat("[Groups.Messaging]: skipping agent {0} because he is not a member of the group", sp.UUID);
return;
}
// Check if the user has an agent in the region where
// the IM came from, and if so, skip it, because the IM
// was already sent via that agent
if (regionOfOrigin != null)
{
AgentCircuitData aCircuit = s.AuthenticateHandler.GetAgentCircuitData(sp.UUID);
if (aCircuit != null)
{
if (aCircuit.ChildrenCapSeeds.Keys.Contains(regionOfOrigin.RegionHandle))
{
if (m_debugEnabled)
m_log.DebugFormat("[Groups.Messaging]: skipping agent {0} because he has an agent in region of origin", sp.UUID);
return;
}
else
{
if (m_debugEnabled)
m_log.DebugFormat("[Groups.Messaging]: not skipping agent {0}", sp.UUID);
}
}
}
UUID AgentID = sp.UUID;
msg.toAgentID = AgentID.Guid;
if (!hasAgentDroppedGroupChatSession(AgentID.ToString(), GroupID))
{
if (!hasAgentBeenInvitedToGroupChatSession(AgentID.ToString(), GroupID))
AddAgentToSession(AgentID, GroupID, msg);
else
{
if (m_debugEnabled) m_log.DebugFormat("[Groups.Messaging]: Passing to ProcessMessageFromGroupSession to deliver to {0} locally", sp.Name);
ProcessMessageFromGroupSession(msg);
}
}
});
}
} }
} }
@ -359,82 +478,40 @@ namespace OpenSim.Groups
UUID AgentID = new UUID(msg.fromAgentID); UUID AgentID = new UUID(msg.fromAgentID);
UUID GroupID = new UUID(msg.imSessionID); UUID GroupID = new UUID(msg.imSessionID);
UUID toAgentID = new UUID(msg.toAgentID);
switch (msg.dialog) switch (msg.dialog)
{ {
case (byte)InstantMessageDialog.SessionAdd: case (byte)InstantMessageDialog.SessionAdd:
m_groupData.AgentInvitedToGroupChatSession(AgentID.ToString(), GroupID); AgentInvitedToGroupChatSession(AgentID.ToString(), GroupID);
break; break;
case (byte)InstantMessageDialog.SessionDrop: case (byte)InstantMessageDialog.SessionDrop:
m_groupData.AgentDroppedFromGroupChatSession(AgentID.ToString(), GroupID); AgentDroppedFromGroupChatSession(AgentID.ToString(), GroupID);
break; break;
case (byte)InstantMessageDialog.SessionSend: case (byte)InstantMessageDialog.SessionSend:
if (!m_groupData.hasAgentDroppedGroupChatSession(AgentID.ToString(), GroupID) // User hasn't dropped, so they're in the session,
&& !m_groupData.hasAgentBeenInvitedToGroupChatSession(AgentID.ToString(), GroupID) // maybe we should deliver it.
) IClientAPI client = GetActiveClient(new UUID(msg.toAgentID));
if (client != null)
{ {
// Agent not in session and hasn't dropped from session // Deliver locally, directly
// Add them to the session for now, and Invite them if (m_debugEnabled) m_log.DebugFormat("[Groups.Messaging]: Delivering to {0} locally", client.Name);
m_groupData.AgentInvitedToGroupChatSession(AgentID.ToString(), GroupID);
UUID toAgentID = new UUID(msg.toAgentID); if (!hasAgentDroppedGroupChatSession(toAgentID.ToString(), GroupID))
IClientAPI activeClient = GetActiveClient(toAgentID);
if (activeClient != null)
{ {
GroupRecord groupInfo = m_groupData.GetGroupRecord(UUID.Zero.ToString(), GroupID, null); if (!hasAgentBeenInvitedToGroupChatSession(toAgentID.ToString(), GroupID))
if (groupInfo != null) // This actually sends the message too, so no need to resend it
{ // with client.SendInstantMessage
if (m_debugEnabled) m_log.DebugFormat("[Groups.Messaging]: Sending chatterbox invite instant message"); AddAgentToSession(toAgentID, GroupID, msg);
else
// Force? open the group session dialog??? client.SendInstantMessage(msg);
// and simultanously deliver the message, so we don't need to do a seperate client.SendInstantMessage(msg);
IEventQueue eq = activeClient.Scene.RequestModuleInterface<IEventQueue>();
eq.ChatterboxInvitation(
GroupID
, groupInfo.GroupName
, new UUID(msg.fromAgentID)
, msg.message
, new UUID(msg.toAgentID)
, msg.fromAgentName
, msg.dialog
, msg.timestamp
, msg.offline == 1
, (int)msg.ParentEstateID
, msg.Position
, 1
, new UUID(msg.imSessionID)
, msg.fromGroup
, OpenMetaverse.Utils.StringToBytes(groupInfo.GroupName)
);
eq.ChatterBoxSessionAgentListUpdates(
new UUID(GroupID)
, new UUID(msg.fromAgentID)
, new UUID(msg.toAgentID)
, false //canVoiceChat
, false //isModerator
, false //text mute
);
}
} }
} }
else if (!m_groupData.hasAgentDroppedGroupChatSession(AgentID.ToString(), GroupID)) else
{ {
// User hasn't dropped, so they're in the session, m_log.WarnFormat("[Groups.Messaging]: Received a message over the grid for a client that isn't here: {0}", msg.toAgentID);
// maybe we should deliver it.
IClientAPI client = GetActiveClient(new UUID(msg.toAgentID));
if (client != null)
{
// Deliver locally, directly
if (m_debugEnabled) m_log.DebugFormat("[Groups.Messaging]: Delivering to {0} locally", client.Name);
client.SendInstantMessage(msg);
}
else
{
m_log.WarnFormat("[Groups.Messaging]: Received a message over the grid for a client that isn't here: {0}", msg.toAgentID);
}
} }
break; break;
@ -444,6 +521,53 @@ namespace OpenSim.Groups
} }
} }
private void AddAgentToSession(UUID AgentID, UUID GroupID, GridInstantMessage msg)
{
// Agent not in session and hasn't dropped from session
// Add them to the session for now, and Invite them
AgentInvitedToGroupChatSession(AgentID.ToString(), GroupID);
IClientAPI activeClient = GetActiveClient(AgentID);
if (activeClient != null)
{
GroupRecord groupInfo = m_groupData.GetGroupRecord(UUID.Zero.ToString(), GroupID, null);
if (groupInfo != null)
{
if (m_debugEnabled) m_log.DebugFormat("[Groups.Messaging]: Sending chatterbox invite instant message");
// Force? open the group session dialog???
// and simultanously deliver the message, so we don't need to do a seperate client.SendInstantMessage(msg);
IEventQueue eq = activeClient.Scene.RequestModuleInterface<IEventQueue>();
eq.ChatterboxInvitation(
GroupID
, groupInfo.GroupName
, new UUID(msg.fromAgentID)
, msg.message
, AgentID
, msg.fromAgentName
, msg.dialog
, msg.timestamp
, msg.offline == 1
, (int)msg.ParentEstateID
, msg.Position
, 1
, new UUID(msg.imSessionID)
, msg.fromGroup
, OpenMetaverse.Utils.StringToBytes(groupInfo.GroupName)
);
eq.ChatterBoxSessionAgentListUpdates(
new UUID(GroupID)
, AgentID
, new UUID(msg.toAgentID)
, false //canVoiceChat
, false //isModerator
, false //text mute
);
}
}
}
#endregion #endregion
@ -469,7 +593,7 @@ namespace OpenSim.Groups
if (groupInfo != null) if (groupInfo != null)
{ {
m_groupData.AgentInvitedToGroupChatSession(AgentID.ToString(), GroupID); AgentInvitedToGroupChatSession(AgentID.ToString(), GroupID);
ChatterBoxSessionStartReplyViaCaps(remoteClient, groupInfo.GroupName, GroupID); ChatterBoxSessionStartReplyViaCaps(remoteClient, groupInfo.GroupName, GroupID);
@ -495,7 +619,7 @@ namespace OpenSim.Groups
m_log.DebugFormat("[Groups.Messaging]: Send message to session for group {0} with session ID {1}", GroupID, im.imSessionID.ToString()); m_log.DebugFormat("[Groups.Messaging]: Send message to session for group {0} with session ID {1}", GroupID, im.imSessionID.ToString());
//If this agent is sending a message, then they want to be in the session //If this agent is sending a message, then they want to be in the session
m_groupData.AgentInvitedToGroupChatSession(AgentID.ToString(), GroupID); AgentInvitedToGroupChatSession(AgentID.ToString(), GroupID);
SendMessageToGroup(im, GroupID); SendMessageToGroup(im, GroupID);
} }
@ -566,12 +690,12 @@ namespace OpenSim.Groups
{ {
if (!sp.IsChildAgent) if (!sp.IsChildAgent)
{ {
if (m_debugEnabled) m_log.WarnFormat("[Groups.Messaging]: Found root agent for client : {0}", sp.ControllingClient.Name); if (m_debugEnabled) m_log.DebugFormat("[Groups.Messaging]: Found root agent for client : {0}", sp.ControllingClient.Name);
return sp.ControllingClient; return sp.ControllingClient;
} }
else else
{ {
if (m_debugEnabled) m_log.WarnFormat("[Groups.Messaging]: Found child agent for client : {0}", sp.ControllingClient.Name); if (m_debugEnabled) m_log.DebugFormat("[Groups.Messaging]: Found child agent for client : {0}", sp.ControllingClient.Name);
child = sp.ControllingClient; child = sp.ControllingClient;
} }
} }
@ -590,5 +714,71 @@ namespace OpenSim.Groups
} }
#endregion #endregion
#region GroupSessionTracking
public void ResetAgentGroupChatSessions(string agentID)
{
foreach (List<string> agentList in m_groupsAgentsDroppedFromChatSession.Values)
agentList.Remove(agentID);
foreach (List<string> agentList in m_groupsAgentsInvitedToChatSession.Values)
agentList.Remove(agentID);
}
public bool hasAgentBeenInvitedToGroupChatSession(string agentID, UUID groupID)
{
// If we're tracking this group, and we can find them in the tracking, then they've been invited
return m_groupsAgentsInvitedToChatSession.ContainsKey(groupID)
&& m_groupsAgentsInvitedToChatSession[groupID].Contains(agentID);
}
public bool hasAgentDroppedGroupChatSession(string agentID, UUID groupID)
{
// If we're tracking drops for this group,
// and we find them, well... then they've dropped
return m_groupsAgentsDroppedFromChatSession.ContainsKey(groupID)
&& m_groupsAgentsDroppedFromChatSession[groupID].Contains(agentID);
}
public void AgentDroppedFromGroupChatSession(string agentID, UUID groupID)
{
if (m_groupsAgentsDroppedFromChatSession.ContainsKey(groupID))
{
// If not in dropped list, add
if (!m_groupsAgentsDroppedFromChatSession[groupID].Contains(agentID))
{
m_groupsAgentsDroppedFromChatSession[groupID].Add(agentID);
}
}
}
public void AgentInvitedToGroupChatSession(string agentID, UUID groupID)
{
// Add Session Status if it doesn't exist for this session
CreateGroupChatSessionTracking(groupID);
// If nessesary, remove from dropped list
if (m_groupsAgentsDroppedFromChatSession[groupID].Contains(agentID))
{
m_groupsAgentsDroppedFromChatSession[groupID].Remove(agentID);
}
// Add to invited
if (!m_groupsAgentsInvitedToChatSession[groupID].Contains(agentID))
m_groupsAgentsInvitedToChatSession[groupID].Add(agentID);
}
private void CreateGroupChatSessionTracking(UUID groupID)
{
if (!m_groupsAgentsDroppedFromChatSession.ContainsKey(groupID))
{
m_groupsAgentsDroppedFromChatSession.Add(groupID, new List<string>());
m_groupsAgentsInvitedToChatSession.Add(groupID, new List<string>());
}
}
#endregion
} }
} }

View File

@ -141,6 +141,8 @@ namespace OpenSim.Groups
if (m_debugEnabled) m_log.DebugFormat("[Groups]: {0} called", System.Reflection.MethodBase.GetCurrentMethod().Name); if (m_debugEnabled) m_log.DebugFormat("[Groups]: {0} called", System.Reflection.MethodBase.GetCurrentMethod().Name);
scene.EventManager.OnNewClient += OnNewClient; scene.EventManager.OnNewClient += OnNewClient;
scene.EventManager.OnMakeRootAgent += OnMakeRoot;
scene.EventManager.OnMakeChildAgent += OnMakeChild;
scene.EventManager.OnIncomingInstantMessage += OnGridInstantMessage; scene.EventManager.OnIncomingInstantMessage += OnGridInstantMessage;
// The InstantMessageModule itself doesn't do this, // The InstantMessageModule itself doesn't do this,
// so lets see if things explode if we don't do it // so lets see if things explode if we don't do it
@ -194,6 +196,8 @@ namespace OpenSim.Groups
if (m_debugEnabled) m_log.DebugFormat("[Groups]: {0} called", System.Reflection.MethodBase.GetCurrentMethod().Name); if (m_debugEnabled) m_log.DebugFormat("[Groups]: {0} called", System.Reflection.MethodBase.GetCurrentMethod().Name);
scene.EventManager.OnNewClient -= OnNewClient; scene.EventManager.OnNewClient -= OnNewClient;
scene.EventManager.OnMakeRootAgent -= OnMakeRoot;
scene.EventManager.OnMakeChildAgent -= OnMakeChild;
scene.EventManager.OnIncomingInstantMessage -= OnGridInstantMessage; scene.EventManager.OnIncomingInstantMessage -= OnGridInstantMessage;
lock (m_sceneList) lock (m_sceneList)
@ -232,16 +236,29 @@ namespace OpenSim.Groups
{ {
if (m_debugEnabled) m_log.DebugFormat("[Groups]: {0} called", System.Reflection.MethodBase.GetCurrentMethod().Name); if (m_debugEnabled) m_log.DebugFormat("[Groups]: {0} called", System.Reflection.MethodBase.GetCurrentMethod().Name);
client.OnUUIDGroupNameRequest += HandleUUIDGroupNameRequest;
client.OnAgentDataUpdateRequest += OnAgentDataUpdateRequest; client.OnAgentDataUpdateRequest += OnAgentDataUpdateRequest;
client.OnDirFindQuery += OnDirFindQuery;
client.OnRequestAvatarProperties += OnRequestAvatarProperties; client.OnRequestAvatarProperties += OnRequestAvatarProperties;
}
private void OnMakeRoot(ScenePresence sp)
{
if (m_debugEnabled) m_log.DebugFormat("[Groups]: {0} called", System.Reflection.MethodBase.GetCurrentMethod().Name);
sp.ControllingClient.OnUUIDGroupNameRequest += HandleUUIDGroupNameRequest;
// Used for Notices and Group Invites/Accept/Reject // Used for Notices and Group Invites/Accept/Reject
client.OnInstantMessage += OnInstantMessage; sp.ControllingClient.OnInstantMessage += OnInstantMessage;
// Send client their groups information. // Send client their groups information.
SendAgentGroupDataUpdate(client, client.AgentId); SendAgentGroupDataUpdate(sp.ControllingClient, sp.UUID);
}
private void OnMakeChild(ScenePresence sp)
{
if (m_debugEnabled) m_log.DebugFormat("[Groups]: {0} called", System.Reflection.MethodBase.GetCurrentMethod().Name);
sp.ControllingClient.OnUUIDGroupNameRequest -= HandleUUIDGroupNameRequest;
// Used for Notices and Group Invites/Accept/Reject
sp.ControllingClient.OnInstantMessage -= OnInstantMessage;
} }
private void OnRequestAvatarProperties(IClientAPI remoteClient, UUID avatarID) private void OnRequestAvatarProperties(IClientAPI remoteClient, UUID avatarID)
@ -287,21 +304,6 @@ namespace OpenSim.Groups
} }
*/ */
void OnDirFindQuery(IClientAPI remoteClient, UUID queryID, string queryText, uint queryFlags, int queryStart)
{
if (((DirFindFlags)queryFlags & DirFindFlags.Groups) == DirFindFlags.Groups)
{
if (m_debugEnabled)
m_log.DebugFormat(
"[Groups]: {0} called with queryText({1}) queryFlags({2}) queryStart({3})",
System.Reflection.MethodBase.GetCurrentMethod().Name, queryText, (DirFindFlags)queryFlags, queryStart);
// TODO: This currently ignores pretty much all the query flags including Mature and sort order
remoteClient.SendDirGroupsReply(queryID, m_groupData.FindGroups(GetRequestingAgentIDStr(remoteClient), queryText).ToArray());
}
}
private void OnAgentDataUpdateRequest(IClientAPI remoteClient, UUID dataForAgentID, UUID sessionID) private void OnAgentDataUpdateRequest(IClientAPI remoteClient, UUID dataForAgentID, UUID sessionID)
{ {
if (m_debugEnabled) m_log.DebugFormat("[Groups]: {0} called", System.Reflection.MethodBase.GetCurrentMethod().Name); if (m_debugEnabled) m_log.DebugFormat("[Groups]: {0} called", System.Reflection.MethodBase.GetCurrentMethod().Name);
@ -347,7 +349,7 @@ namespace OpenSim.Groups
{ {
if (m_debugEnabled) m_log.DebugFormat("[Groups]: {0} called", System.Reflection.MethodBase.GetCurrentMethod().Name); if (m_debugEnabled) m_log.DebugFormat("[Groups]: {0} called", System.Reflection.MethodBase.GetCurrentMethod().Name);
m_log.DebugFormat("[Groups]: IM From {0} to {1} msg {2} type {3}", im.fromAgentID, im.toAgentID, im.message, (InstantMessageDialog)im.dialog); //m_log.DebugFormat("[Groups]: IM From {0} to {1} msg {2} type {3}", im.fromAgentID, im.toAgentID, im.message, (InstantMessageDialog)im.dialog);
// Group invitations // Group invitations
if ((im.dialog == (byte)InstantMessageDialog.GroupInvitationAccept) || (im.dialog == (byte)InstantMessageDialog.GroupInvitationDecline)) if ((im.dialog == (byte)InstantMessageDialog.GroupInvitationAccept) || (im.dialog == (byte)InstantMessageDialog.GroupInvitationDecline))
{ {
@ -465,12 +467,12 @@ namespace OpenSim.Groups
} }
// Send notice out to everyone that wants notices // Send notice out to everyone that wants notices
// Build notice IIM
GridInstantMessage msg = CreateGroupNoticeIM(UUID.Zero, NoticeID, (byte)OpenMetaverse.InstantMessageDialog.GroupNotice);
foreach (GroupMembersData member in m_groupData.GetGroupMembers(GetRequestingAgentIDStr(remoteClient), GroupID)) foreach (GroupMembersData member in m_groupData.GetGroupMembers(GetRequestingAgentIDStr(remoteClient), GroupID))
{ {
if (member.AcceptNotices) if (member.AcceptNotices)
{ {
// Build notice IIM, one of reach, because the sending may be async
GridInstantMessage msg = CreateGroupNoticeIM(UUID.Zero, NoticeID, (byte)OpenMetaverse.InstantMessageDialog.GroupNotice);
msg.toAgentID = member.AgentID.Guid; msg.toAgentID = member.AgentID.Guid;
OutgoingInstantMessage(msg, member.AgentID); OutgoingInstantMessage(msg, member.AgentID);
} }
@ -485,7 +487,7 @@ namespace OpenSim.Groups
return; return;
//// 16 bytes are the UUID. Maybe. //// 16 bytes are the UUID. Maybe.
UUID folderID = new UUID(im.binaryBucket, 0); // UUID folderID = new UUID(im.binaryBucket, 0);
UUID noticeID = new UUID(im.imSessionID); UUID noticeID = new UUID(im.imSessionID);
GroupNoticeInfo notice = m_groupData.GetGroupNotice(remoteClient.AgentId.ToString(), noticeID); GroupNoticeInfo notice = m_groupData.GetGroupNotice(remoteClient.AgentId.ToString(), noticeID);
@ -766,14 +768,17 @@ namespace OpenSim.Groups
remoteClient.SendCreateGroupReply(UUID.Zero, false, "Insufficient funds to create a group."); remoteClient.SendCreateGroupReply(UUID.Zero, false, "Insufficient funds to create a group.");
return UUID.Zero; return UUID.Zero;
} }
money.ApplyCharge(remoteClient.AgentId, money.GroupCreationCharge, MoneyTransactionType.GroupCreate);
} }
string reason = string.Empty; string reason = string.Empty;
UUID groupID = m_groupData.CreateGroup(remoteClient.AgentId, name, charter, showInList, insigniaID, membershipFee, openEnrollment, UUID groupID = m_groupData.CreateGroup(remoteClient.AgentId, name, charter, showInList, insigniaID, membershipFee, openEnrollment,
allowPublish, maturePublish, remoteClient.AgentId, out reason); allowPublish, maturePublish, remoteClient.AgentId, out reason);
if (groupID != UUID.Zero) if (groupID != UUID.Zero)
{ {
if (money != null)
money.ApplyCharge(remoteClient.AgentId, money.GroupCreationCharge, MoneyTransactionType.GroupCreate);
remoteClient.SendCreateGroupReply(groupID, true, "Group created successfullly"); remoteClient.SendCreateGroupReply(groupID, true, "Group created successfullly");
// Update the founder with new group information. // Update the founder with new group information.
@ -904,23 +909,7 @@ namespace OpenSim.Groups
{ {
if (m_debugEnabled) m_log.DebugFormat("[Groups]: {0} called for notice {1}", System.Reflection.MethodBase.GetCurrentMethod().Name, groupNoticeID); if (m_debugEnabled) m_log.DebugFormat("[Groups]: {0} called for notice {1}", System.Reflection.MethodBase.GetCurrentMethod().Name, groupNoticeID);
//GroupRecord groupInfo = m_groupData.GetGroupRecord(GetRequestingAgentID(remoteClient), data.GroupID, null);
GridInstantMessage msg = CreateGroupNoticeIM(remoteClient.AgentId, groupNoticeID, (byte)InstantMessageDialog.GroupNoticeRequested); GridInstantMessage msg = CreateGroupNoticeIM(remoteClient.AgentId, groupNoticeID, (byte)InstantMessageDialog.GroupNoticeRequested);
//GridInstantMessage msg = new GridInstantMessage();
//msg.imSessionID = UUID.Zero.Guid;
//msg.fromAgentID = data.GroupID.Guid;
//msg.toAgentID = GetRequestingAgentID(remoteClient).Guid;
//msg.timestamp = (uint)Util.UnixTimeSinceEpoch();
//msg.fromAgentName = "Group Notice : " + groupInfo == null ? "Unknown" : groupInfo.GroupName;
//msg.message = data.noticeData.Subject + "|" + data.Message;
//msg.dialog = (byte)OpenMetaverse.InstantMessageDialog.GroupNoticeRequested;
//msg.fromGroup = true;
//msg.offline = (byte)0;
//msg.ParentEstateID = 0;
//msg.Position = Vector3.Zero;
//msg.RegionID = UUID.Zero.Guid;
//msg.binaryBucket = data.BinaryBucket;
OutgoingInstantMessage(msg, GetRequestingAgentID(remoteClient)); OutgoingInstantMessage(msg, GetRequestingAgentID(remoteClient));
} }
@ -1002,6 +991,10 @@ namespace OpenSim.Groups
// Should this send updates to everyone in the group? // Should this send updates to everyone in the group?
SendAgentGroupDataUpdate(remoteClient, GetRequestingAgentID(remoteClient)); SendAgentGroupDataUpdate(remoteClient, GetRequestingAgentID(remoteClient));
if (reason != string.Empty)
// A warning
remoteClient.SendAlertMessage("Warning: " + reason);
} }
else else
remoteClient.SendJoinGroupReply(groupID, false); remoteClient.SendJoinGroupReply(groupID, false);
@ -1186,6 +1179,11 @@ namespace OpenSim.Groups
} }
} }
public List<DirGroupsReplyData> FindGroups(IClientAPI remoteClient, string query)
{
return m_groupData.FindGroups(GetRequestingAgentIDStr(remoteClient), query);
}
#endregion #endregion
#region Client/Update Tools #region Client/Update Tools
@ -1225,12 +1223,16 @@ namespace OpenSim.Groups
{ {
if (m_debugEnabled) m_log.InfoFormat("[Groups]: {0} called", System.Reflection.MethodBase.GetCurrentMethod().Name); if (m_debugEnabled) m_log.InfoFormat("[Groups]: {0} called", System.Reflection.MethodBase.GetCurrentMethod().Name);
// NPCs currently don't have a CAPs structure or event queues. There is a strong argument for conveying this information
// to them anyway since it makes writing server-side bots a lot easier, but for now we don't do anything.
if (remoteClient.SceneAgent.PresenceType == PresenceType.Npc)
return;
OSDArray AgentData = new OSDArray(1); OSDArray AgentData = new OSDArray(1);
OSDMap AgentDataMap = new OSDMap(1); OSDMap AgentDataMap = new OSDMap(1);
AgentDataMap.Add("AgentID", OSD.FromUUID(dataForAgentID)); AgentDataMap.Add("AgentID", OSD.FromUUID(dataForAgentID));
AgentData.Add(AgentDataMap); AgentData.Add(AgentDataMap);
OSDArray GroupData = new OSDArray(data.Length); OSDArray GroupData = new OSDArray(data.Length);
OSDArray NewGroupData = new OSDArray(data.Length); OSDArray NewGroupData = new OSDArray(data.Length);
@ -1276,8 +1278,7 @@ namespace OpenSim.Groups
if (queue != null) if (queue != null)
{ {
queue.Enqueue(queue.BuildEvent("AgentGroupDataUpdate", llDataStruct), GetRequestingAgentID(remoteClient)); queue.Enqueue(queue.BuildEvent("AgentGroupDataUpdate", llDataStruct), GetRequestingAgentID(remoteClient));
} }
} }
private void SendScenePresenceUpdate(UUID AgentID, string Title) private void SendScenePresenceUpdate(UUID AgentID, string Title)
@ -1339,6 +1340,7 @@ namespace OpenSim.Groups
GroupMembershipData[] membershipArray = GetProfileListedGroupMemberships(remoteClient, dataForAgentID); GroupMembershipData[] membershipArray = GetProfileListedGroupMemberships(remoteClient, dataForAgentID);
SendGroupMembershipInfoViaCaps(remoteClient, dataForAgentID, membershipArray); SendGroupMembershipInfoViaCaps(remoteClient, dataForAgentID, membershipArray);
//remoteClient.SendAvatarGroupsReply(dataForAgentID, membershipArray); //remoteClient.SendAvatarGroupsReply(dataForAgentID, membershipArray);
if (remoteClient.AgentId == dataForAgentID) if (remoteClient.AgentId == dataForAgentID)
remoteClient.RefreshGroupMembership(); remoteClient.RefreshGroupMembership();
@ -1399,19 +1401,18 @@ namespace OpenSim.Groups
if (m_debugEnabled) m_log.DebugFormat("[Groups]: {0} called", System.Reflection.MethodBase.GetCurrentMethod().Name); if (m_debugEnabled) m_log.DebugFormat("[Groups]: {0} called", System.Reflection.MethodBase.GetCurrentMethod().Name);
// TODO: All the client update functions need to be reexamined because most do too much and send too much stuff // TODO: All the client update functions need to be reexamined because most do too much and send too much stuff
UserAccount account = m_sceneList[0].UserAccountService.GetUserAccount(remoteClient.Scene.RegionInfo.ScopeID, dataForAgentID); string firstname = "Unknown", lastname = "Unknown";
string firstname, lastname; string name = m_UserManagement.GetUserName(dataForAgentID);
if (account != null) if (!string.IsNullOrEmpty(name))
{ {
firstname = account.FirstName; string[] parts = name.Split(new char[] { ' ' });
lastname = account.LastName; if (parts.Length >= 2)
{
firstname = parts[0];
lastname = parts[1];
}
} }
else
{
firstname = "Unknown";
lastname = "Unknown";
}
remoteClient.SendAgentDataUpdate(dataForAgentID, activeGroupID, firstname, remoteClient.SendAgentDataUpdate(dataForAgentID, activeGroupID, firstname,
lastname, activeGroupPowers, activeGroupName, lastname, activeGroupPowers, activeGroupName,
activeGroupTitle); activeGroupTitle);

View File

@ -186,7 +186,6 @@ namespace OpenSim.Groups
public UUID CreateGroup(UUID RequestingAgentID, string name, string charter, bool showInList, UUID insigniaID, int membershipFee, bool openEnrollment, public UUID CreateGroup(UUID RequestingAgentID, string name, string charter, bool showInList, UUID insigniaID, int membershipFee, bool openEnrollment,
bool allowPublish, bool maturePublish, UUID founderID, out string reason) bool allowPublish, bool maturePublish, UUID founderID, out string reason)
{ {
m_log.DebugFormat("[Groups]: Creating group {0}", name);
reason = string.Empty; reason = string.Empty;
if (m_UserManagement.IsLocalGridUser(RequestingAgentID)) if (m_UserManagement.IsLocalGridUser(RequestingAgentID))
return m_LocalGroupsConnector.CreateGroup(RequestingAgentID, name, charter, showInList, insigniaID, return m_LocalGroupsConnector.CreateGroup(RequestingAgentID, name, charter, showInList, insigniaID,
@ -255,7 +254,10 @@ namespace OpenSim.Groups
{ {
string url = string.Empty, gname = string.Empty; string url = string.Empty, gname = string.Empty;
if (IsLocal(GroupID, out url, out gname)) if (IsLocal(GroupID, out url, out gname))
return m_LocalGroupsConnector.GetGroupMembers(AgentUUI(RequestingAgentID), GroupID); {
string agentID = AgentUUI(RequestingAgentID);
return m_LocalGroupsConnector.GetGroupMembers(agentID, GroupID);
}
else if (!string.IsNullOrEmpty(url)) else if (!string.IsNullOrEmpty(url))
{ {
ExtendedGroupMembershipData membership = m_LocalGroupsConnector.GetAgentGroupMembership(RequestingAgentID, RequestingAgentID, GroupID); ExtendedGroupMembershipData membership = m_LocalGroupsConnector.GetAgentGroupMembership(RequestingAgentID, RequestingAgentID, GroupID);
@ -397,17 +399,21 @@ namespace OpenSim.Groups
if (success) if (success)
{ {
// Here we always return true. The user has been added to the local group,
// independent of whether the remote operation succeeds or not
url = m_UserManagement.GetUserServerURL(uid, "GroupsServerURI"); url = m_UserManagement.GetUserServerURL(uid, "GroupsServerURI");
if (url == string.Empty) if (url == string.Empty)
{ {
reason = "User doesn't have a groups server"; reason = "You don't have an accessible groups server in your home world. You membership to this group in only within this grid.";
return false; return true;
} }
GroupsServiceHGConnector c = GetConnector(url); GroupsServiceHGConnector c = GetConnector(url);
if (c != null) if (c != null)
return c.CreateProxy(AgentUUI(RequestingAgentID), AgentID, token, GroupID, m_LocalGroupsServiceLocation, name, out reason); c.CreateProxy(AgentUUI(RequestingAgentID), AgentID, token, GroupID, m_LocalGroupsServiceLocation, name, out reason);
return true;
} }
return false;
} }
} }
else if (m_UserManagement.IsLocalGridUser(uid)) // local user else if (m_UserManagement.IsLocalGridUser(uid)) // local user
@ -544,7 +550,6 @@ namespace OpenSim.Groups
List<string> urls = new List<string>(); List<string> urls = new List<string>();
foreach (GroupMembersData m in members) foreach (GroupMembersData m in members)
{ {
UUID userID = UUID.Zero;
if (!m_UserManagement.IsLocalGridUser(m.AgentID)) if (!m_UserManagement.IsLocalGridUser(m.AgentID))
{ {
string gURL = m_UserManagement.GetUserServerURL(m.AgentID, "GroupsServerURI"); string gURL = m_UserManagement.GetUserServerURL(m.AgentID, "GroupsServerURI");
@ -592,28 +597,6 @@ namespace OpenSim.Groups
return m_LocalGroupsConnector.GetGroupNotices(AgentUUI(RequestingAgentID), GroupID); return m_LocalGroupsConnector.GetGroupNotices(AgentUUI(RequestingAgentID), GroupID);
} }
public void ResetAgentGroupChatSessions(string agentID)
{
}
public bool hasAgentBeenInvitedToGroupChatSession(string agentID, UUID groupID)
{
return false;
}
public bool hasAgentDroppedGroupChatSession(string agentID, UUID groupID)
{
return false;
}
public void AgentDroppedFromGroupChatSession(string agentID, UUID groupID)
{
}
public void AgentInvitedToGroupChatSession(string agentID, UUID groupID)
{
}
#endregion #endregion
#region hypergrid groups #region hypergrid groups
@ -685,6 +668,9 @@ namespace OpenSim.Groups
{ {
serviceLocation = string.Empty; serviceLocation = string.Empty;
name = string.Empty; name = string.Empty;
if (groupID.Equals(UUID.Zero))
return true;
ExtendedGroupRecord group = m_LocalGroupsConnector.GetGroupRecord(UUID.Zero.ToString(), groupID, string.Empty); ExtendedGroupRecord group = m_LocalGroupsConnector.GetGroupRecord(UUID.Zero.ToString(), groupID, string.Empty);
if (group == null) if (group == null)
{ {

View File

@ -47,7 +47,6 @@ namespace OpenSim.Groups
private static readonly ILog m_log = LogManager.GetLogger(MethodBase.GetCurrentMethod().DeclaringType); private static readonly ILog m_log = LogManager.GetLogger(MethodBase.GetCurrentMethod().DeclaringType);
private HGGroupsService m_GroupsService; private HGGroupsService m_GroupsService;
private string m_HomeURI = string.Empty;
private string m_ConfigName = "Groups"; private string m_ConfigName = "Groups";
// Called by Robust shell // Called by Robust shell
@ -209,7 +208,6 @@ namespace OpenSim.Groups
UUID groupID = new UUID(request["GroupID"].ToString()); UUID groupID = new UUID(request["GroupID"].ToString());
string agentID = request["AgentID"].ToString(); string agentID = request["AgentID"].ToString();
string token = request["AccessToken"].ToString(); string token = request["AccessToken"].ToString();
string reason = string.Empty;
m_GroupsService.RemoveAgentFromGroup(agentID, agentID, groupID, token); m_GroupsService.RemoveAgentFromGroup(agentID, agentID, groupID, token);
} }

View File

@ -92,12 +92,6 @@ namespace OpenSim.Groups
GroupNoticeInfo GetGroupNotice(string RequestingAgentID, UUID noticeID); GroupNoticeInfo GetGroupNotice(string RequestingAgentID, UUID noticeID);
List<ExtendedGroupNoticeData> GetGroupNotices(string RequestingAgentID, UUID GroupID); List<ExtendedGroupNoticeData> GetGroupNotices(string RequestingAgentID, UUID GroupID);
void ResetAgentGroupChatSessions(string agentID);
bool hasAgentBeenInvitedToGroupChatSession(string agentID, UUID groupID);
bool hasAgentDroppedGroupChatSession(string agentID, UUID groupID);
void AgentDroppedFromGroupChatSession(string agentID, UUID groupID);
void AgentInvitedToGroupChatSession(string agentID, UUID groupID);
} }
public class GroupInviteInfo public class GroupInviteInfo

View File

@ -320,28 +320,6 @@ namespace OpenSim.Groups
return m_GroupsService.GetGroupNotices(RequestingAgentID, GroupID); return m_GroupsService.GetGroupNotices(RequestingAgentID, GroupID);
} }
public void ResetAgentGroupChatSessions(string agentID)
{
}
public bool hasAgentBeenInvitedToGroupChatSession(string agentID, UUID groupID)
{
return false;
}
public bool hasAgentDroppedGroupChatSession(string agentID, UUID groupID)
{
return false;
}
public void AgentDroppedFromGroupChatSession(string agentID, UUID groupID)
{
}
public void AgentInvitedToGroupChatSession(string agentID, UUID groupID)
{
}
#endregion #endregion
} }
} }

View File

@ -133,6 +133,36 @@ namespace OpenSim.Groups
return GroupsDataUtils.GroupRecord((Dictionary<string, object>)ret["RESULT"]); return GroupsDataUtils.GroupRecord((Dictionary<string, object>)ret["RESULT"]);
} }
public List<DirGroupsReplyData> FindGroups(string RequestingAgentID, string query)
{
List<DirGroupsReplyData> hits = new List<DirGroupsReplyData>();
if (string.IsNullOrEmpty(query))
return hits;
Dictionary<string, object> sendData = new Dictionary<string, object>();
sendData["Query"] = query;
sendData["RequestingAgentID"] = RequestingAgentID;
Dictionary<string, object> ret = MakeRequest("FINDGROUPS", sendData);
if (ret == null)
return hits;
if (!ret.ContainsKey("RESULT"))
return hits;
if (ret["RESULT"].ToString() == "NULL")
return hits;
foreach (object v in ((Dictionary<string, object>)ret["RESULT"]).Values)
{
DirGroupsReplyData m = GroupsDataUtils.DirGroupsReplyData((Dictionary<string, object>)v);
hits.Add(m);
}
return hits;
}
public GroupMembershipData AddAgentToGroup(string RequestingAgentID, string AgentID, UUID GroupID, UUID RoleID, string token, out string reason) public GroupMembershipData AddAgentToGroup(string RequestingAgentID, string AgentID, UUID GroupID, UUID RoleID, string token, out string reason)
{ {
reason = string.Empty; reason = string.Empty;
@ -226,6 +256,7 @@ namespace OpenSim.Groups
Dictionary<string, object> sendData = new Dictionary<string, object>(); Dictionary<string, object> sendData = new Dictionary<string, object>();
sendData["GroupID"] = GroupID.ToString(); sendData["GroupID"] = GroupID.ToString();
sendData["RequestingAgentID"] = RequestingAgentID; sendData["RequestingAgentID"] = RequestingAgentID;
Dictionary<string, object> ret = MakeRequest("GETGROUPMEMBERS", sendData); Dictionary<string, object> ret = MakeRequest("GETGROUPMEMBERS", sendData);
if (ret == null) if (ret == null)

View File

@ -199,7 +199,7 @@ namespace OpenSim.Groups
public List<DirGroupsReplyData> FindGroups(string RequestingAgentID, string search) public List<DirGroupsReplyData> FindGroups(string RequestingAgentID, string search)
{ {
// TODO! // TODO!
return new List<DirGroupsReplyData>(); return m_GroupsService.FindGroups(RequestingAgentID, search);
} }
public bool AddAgentToGroup(string RequestingAgentID, string AgentID, UUID GroupID, UUID RoleID, string token, out string reason) public bool AddAgentToGroup(string RequestingAgentID, string AgentID, UUID GroupID, UUID RoleID, string token, out string reason)
@ -406,28 +406,6 @@ namespace OpenSim.Groups
}); });
} }
public void ResetAgentGroupChatSessions(string agentID)
{
}
public bool hasAgentBeenInvitedToGroupChatSession(string agentID, UUID groupID)
{
return false;
}
public bool hasAgentDroppedGroupChatSession(string agentID, UUID groupID)
{
return false;
}
public void AgentDroppedFromGroupChatSession(string agentID, UUID groupID)
{
}
public void AgentInvitedToGroupChatSession(string agentID, UUID groupID)
{
}
#endregion #endregion
} }

View File

@ -133,6 +133,8 @@ namespace OpenSim.Groups
return HandleAddNotice(request); return HandleAddNotice(request);
case "GETNOTICES": case "GETNOTICES":
return HandleGetNotices(request); return HandleGetNotices(request);
case "FINDGROUPS":
return HandleFindGroups(request);
} }
m_log.DebugFormat("[GROUPS HANDLER]: unknown method request: {0}", method); m_log.DebugFormat("[GROUPS HANDLER]: unknown method request: {0}", method);
} }
@ -170,11 +172,16 @@ namespace OpenSim.Groups
} }
grec = m_GroupsService.GetGroupRecord(RequestingAgentID, grec.GroupID); if (grec.GroupID != UUID.Zero)
if (grec == null) {
NullResult(result, "Internal Error"); grec = m_GroupsService.GetGroupRecord(RequestingAgentID, grec.GroupID);
if (grec == null)
NullResult(result, "Internal Error");
else
result["RESULT"] = GroupsDataUtils.GroupRecord(grec);
}
else else
result["RESULT"] = GroupsDataUtils.GroupRecord(grec); NullResult(result, reason);
} }
string xmlString = ServerUtils.BuildXmlResponse(result); string xmlString = ServerUtils.BuildXmlResponse(result);
@ -264,7 +271,6 @@ namespace OpenSim.Groups
UUID groupID = new UUID(request["GroupID"].ToString()); UUID groupID = new UUID(request["GroupID"].ToString());
string agentID = request["AgentID"].ToString(); string agentID = request["AgentID"].ToString();
string requestingAgentID = request["RequestingAgentID"].ToString(); string requestingAgentID = request["RequestingAgentID"].ToString();
string reason = string.Empty;
m_GroupsService.RemoveAgentFromGroup(requestingAgentID, agentID, groupID); m_GroupsService.RemoveAgentFromGroup(requestingAgentID, agentID, groupID);
} }
@ -495,7 +501,6 @@ namespace OpenSim.Groups
else else
{ {
string op = request["OP"].ToString(); string op = request["OP"].ToString();
string reason = string.Empty;
bool success = false; bool success = false;
if (op == "ADD") if (op == "ADD")
@ -563,7 +568,6 @@ namespace OpenSim.Groups
else else
{ {
string op = request["OP"].ToString(); string op = request["OP"].ToString();
string reason = string.Empty;
if (op == "GROUP") if (op == "GROUP")
{ {
@ -626,7 +630,6 @@ namespace OpenSim.Groups
else else
{ {
string op = request["OP"].ToString(); string op = request["OP"].ToString();
string reason = string.Empty;
if (op == "ADD" && request.ContainsKey("GroupID") && request.ContainsKey("RoleID") && request.ContainsKey("AgentID")) if (op == "ADD" && request.ContainsKey("GroupID") && request.ContainsKey("RoleID") && request.ContainsKey("AgentID"))
{ {
@ -739,6 +742,32 @@ namespace OpenSim.Groups
return Util.UTF8NoBomEncoding.GetBytes(xmlString); return Util.UTF8NoBomEncoding.GetBytes(xmlString);
} }
byte[] HandleFindGroups(Dictionary<string, object> request)
{
Dictionary<string, object> result = new Dictionary<string, object>();
if (!request.ContainsKey("RequestingAgentID") || !request.ContainsKey("Query"))
NullResult(result, "Bad network data");
List<DirGroupsReplyData> hits = m_GroupsService.FindGroups(request["RequestingAgentID"].ToString(), request["Query"].ToString());
if (hits == null || (hits != null && hits.Count == 0))
NullResult(result, "No hits");
else
{
Dictionary<string, object> dict = new Dictionary<string, object>();
int i = 0;
foreach (DirGroupsReplyData n in hits)
dict["n-" + i++] = GroupsDataUtils.DirGroupsReplyData(n);
result["RESULT"] = dict;
}
string xmlString = ServerUtils.BuildXmlResponse(result);
return Util.UTF8NoBomEncoding.GetBytes(xmlString);
}
#region Helpers #region Helpers

View File

@ -53,7 +53,7 @@ namespace OpenSim.Groups
private ForeignImporter m_ForeignImporter; private ForeignImporter m_ForeignImporter;
private Dictionary<string, bool> m_ActiveRequests = new Dictionary<string, bool>(); private Dictionary<string, bool> m_ActiveRequests = new Dictionary<string, bool>();
private const int GROUPS_CACHE_TIMEOUT = 5 * 60; // 5 minutes private const int GROUPS_CACHE_TIMEOUT = 1 * 60; // 1 minutes
// This all important cache cahces objects of different types: // This all important cache cahces objects of different types:
// group-<GroupID> or group-<Name> => ExtendedGroupRecord // group-<GroupID> or group-<Name> => ExtendedGroupRecord
@ -209,13 +209,10 @@ namespace OpenSim.Groups
public void SetAgentActiveGroup(string AgentID, GroupMembershipDelegate d) public void SetAgentActiveGroup(string AgentID, GroupMembershipDelegate d)
{ {
GroupMembershipData activeGroup = d(); GroupMembershipData activeGroup = d();
if (activeGroup != null) string cacheKey = "active-" + AgentID.ToString();
{ lock (m_Cache)
string cacheKey = "active-" + AgentID.ToString(); if (m_Cache.Contains(cacheKey))
lock (m_Cache) m_Cache.AddOrUpdate(cacheKey, activeGroup, GROUPS_CACHE_TIMEOUT);
if (m_Cache.Contains(cacheKey))
m_Cache.AddOrUpdate(cacheKey, activeGroup, GROUPS_CACHE_TIMEOUT);
}
} }
public ExtendedGroupMembershipData GetAgentActiveMembership(string AgentID, GroupMembershipDelegate d) public ExtendedGroupMembershipData GetAgentActiveMembership(string AgentID, GroupMembershipDelegate d)

View File

@ -130,6 +130,13 @@ namespace OpenSim.Groups
{ {
reason = string.Empty; reason = string.Empty;
// Check if the group already exists
if (m_Database.RetrieveGroup(name) != null)
{
reason = "A group with that name already exists";
return UUID.Zero;
}
// Create the group // Create the group
GroupData data = new GroupData(); GroupData data = new GroupData();
data.GroupID = UUID.Random(); data.GroupID = UUID.Random();
@ -248,13 +255,20 @@ namespace OpenSim.Groups
return members; return members;
List<RoleData> rolesList = new List<RoleData>(roles); List<RoleData> rolesList = new List<RoleData>(roles);
// Is the requester a member of the group? // Check visibility?
bool isInGroup = false; // When we don't want to check visibility, we pass it "all" as the requestingAgentID
if (m_Database.RetrieveMember(GroupID, RequestingAgentID) != null) bool checkVisibility = !RequestingAgentID.Equals(UUID.Zero.ToString());
isInGroup = true;
if (!isInGroup) // reduce the roles to the visible ones if (checkVisibility)
rolesList = rolesList.FindAll(r => (UInt64.Parse(r.Data["Powers"]) & (ulong)GroupPowers.MemberVisible) != 0); {
// Is the requester a member of the group?
bool isInGroup = false;
if (m_Database.RetrieveMember(GroupID, RequestingAgentID) != null)
isInGroup = true;
if (!isInGroup) // reduce the roles to the visible ones
rolesList = rolesList.FindAll(r => (UInt64.Parse(r.Data["Powers"]) & (ulong)GroupPowers.MemberVisible) != 0);
}
MembershipData[] datas = m_Database.RetrieveMembers(GroupID); MembershipData[] datas = m_Database.RetrieveMembers(GroupID);
if (datas == null || (datas != null && datas.Length == 0)) if (datas == null || (datas != null && datas.Length == 0))
@ -723,12 +737,12 @@ namespace OpenSim.Groups
#region Actions without permission checks #region Actions without permission checks
private void _AddAgentToGroup(string RequestingAgentID, string AgentID, UUID GroupID, UUID RoleID) protected void _AddAgentToGroup(string RequestingAgentID, string AgentID, UUID GroupID, UUID RoleID)
{ {
_AddAgentToGroup(RequestingAgentID, AgentID, GroupID, RoleID, string.Empty); _AddAgentToGroup(RequestingAgentID, AgentID, GroupID, RoleID, string.Empty);
} }
public void _RemoveAgentFromGroup(string RequestingAgentID, string AgentID, UUID GroupID) protected void _RemoveAgentFromGroup(string RequestingAgentID, string AgentID, UUID GroupID)
{ {
// 1. Delete membership // 1. Delete membership
m_Database.DeleteMember(GroupID, AgentID); m_Database.DeleteMember(GroupID, AgentID);
@ -780,7 +794,7 @@ namespace OpenSim.Groups
} }
private bool _AddOrUpdateGroupRole(string RequestingAgentID, UUID groupID, UUID roleID, string name, string description, string title, ulong powers, bool add) protected bool _AddOrUpdateGroupRole(string RequestingAgentID, UUID groupID, UUID roleID, string name, string description, string title, ulong powers, bool add)
{ {
RoleData data = m_Database.RetrieveRole(groupID, roleID); RoleData data = m_Database.RetrieveRole(groupID, roleID);
@ -810,12 +824,12 @@ namespace OpenSim.Groups
return m_Database.StoreRole(data); return m_Database.StoreRole(data);
} }
private void _RemoveGroupRole(UUID groupID, UUID roleID) protected void _RemoveGroupRole(UUID groupID, UUID roleID)
{ {
m_Database.DeleteRole(groupID, roleID); m_Database.DeleteRole(groupID, roleID);
} }
private void _AddAgentToGroupRole(string RequestingAgentID, string AgentID, UUID GroupID, UUID RoleID) protected void _AddAgentToGroupRole(string RequestingAgentID, string AgentID, UUID GroupID, UUID RoleID)
{ {
RoleMembershipData data = m_Database.RetrieveRoleMember(GroupID, RoleID, AgentID); RoleMembershipData data = m_Database.RetrieveRoleMember(GroupID, RoleID, AgentID);
if (data != null) if (data != null)
@ -840,7 +854,7 @@ namespace OpenSim.Groups
} }
private List<GroupRolesData> _GetGroupRoles(UUID groupID) protected List<GroupRolesData> _GetGroupRoles(UUID groupID)
{ {
List<GroupRolesData> roles = new List<GroupRolesData>(); List<GroupRolesData> roles = new List<GroupRolesData>();
@ -865,7 +879,7 @@ namespace OpenSim.Groups
return roles; return roles;
} }
private List<ExtendedGroupRoleMembersData> _GetGroupRoleMembers(UUID GroupID, bool isInGroup) protected List<ExtendedGroupRoleMembersData> _GetGroupRoleMembers(UUID GroupID, bool isInGroup)
{ {
List<ExtendedGroupRoleMembersData> rmembers = new List<ExtendedGroupRoleMembersData>(); List<ExtendedGroupRoleMembersData> rmembers = new List<ExtendedGroupRoleMembersData>();