aboutsummaryrefslogtreecommitdiffstatshomepage
path: root/OpenSim/Region/Environment/Modules/Avatar/InstantMessage
diff options
context:
space:
mode:
Diffstat (limited to 'OpenSim/Region/Environment/Modules/Avatar/InstantMessage')
-rw-r--r--OpenSim/Region/Environment/Modules/Avatar/InstantMessage/InstantMessageModule.cs257
1 files changed, 246 insertions, 11 deletions
diff --git a/OpenSim/Region/Environment/Modules/Avatar/InstantMessage/InstantMessageModule.cs b/OpenSim/Region/Environment/Modules/Avatar/InstantMessage/InstantMessageModule.cs
index d9d2875..fdded90 100644
--- a/OpenSim/Region/Environment/Modules/Avatar/InstantMessage/InstantMessageModule.cs
+++ b/OpenSim/Region/Environment/Modules/Avatar/InstantMessage/InstantMessageModule.cs
@@ -27,7 +27,11 @@
27using System; 27using System;
28using System.Collections; 28using System.Collections;
29using System.Collections.Generic; 29using System.Collections.Generic;
30using System.Reflection;
31using System.Net;
32using System.Threading;
30using libsecondlife; 33using libsecondlife;
34using log4net;
31using Nini.Config; 35using Nini.Config;
32using Nwc.XmlRpc; 36using Nwc.XmlRpc;
33using OpenSim.Framework; 37using OpenSim.Framework;
@@ -38,11 +42,15 @@ namespace OpenSim.Region.Environment.Modules.Avatar.InstantMessage
38{ 42{
39 public class InstantMessageModule : IRegionModule 43 public class InstantMessageModule : IRegionModule
40 { 44 {
45 private static readonly ILog m_log = LogManager.GetLogger(MethodBase.GetCurrentMethod().DeclaringType);
46
41 private readonly List<Scene> m_scenes = new List<Scene>(); 47 private readonly List<Scene> m_scenes = new List<Scene>();
48 private Dictionary<LLUUID, ulong> m_userRegionMap = new Dictionary<LLUUID, ulong>();
42 49
43 #region IRegionModule Members 50 #region IRegionModule Members
44 51
45 private bool gridmode = false; 52 private bool gridmode = false;
53
46 54
47 public void Initialise(Scene scene, IConfigSource config) 55 public void Initialise(Scene scene, IConfigSource config)
48 { 56 {
@@ -150,14 +158,19 @@ namespace OpenSim.Region.Environment.Modules.Avatar.InstantMessage
150 return; 158 return;
151 } 159 }
152 } 160 }
161 if (gridmode)
162 {
163 // Still here, try send via Grid
164 // TODO
165 if (client != null)
166 {
167 if (dialog != (byte)InstantMessageDialog.StartTyping && dialog != (byte)InstantMessageDialog.StopTyping && dialog != (byte)InstantMessageDialog.SessionDrop)
168 client.SendInstantMessage(toAgentID, fromAgentSession, "Unable to send instant message", fromAgentID, imSessionID, "System", (byte)InstantMessageDialog.BusyAutoResponse, (uint)Util.UnixTimeSinceEpoch());// SendAlertMessage("Unable to send instant message");
169 }
170 }
153 } 171 }
154 172
155 if (gridmode) 173
156 {
157 // Still here, try send via Grid
158 // TODO
159
160 }
161 } 174 }
162 175
163 // Trusty OSG1 called method. This method also gets called from the FriendsModule 176 // Trusty OSG1 called method. This method also gets called from the FriendsModule
@@ -174,6 +187,7 @@ namespace OpenSim.Region.Environment.Modules.Avatar.InstantMessage
174 } 187 }
175 protected virtual XmlRpcResponse processXMLRPCGridInstantMessage(XmlRpcRequest request) 188 protected virtual XmlRpcResponse processXMLRPCGridInstantMessage(XmlRpcRequest request)
176 { 189 {
190 bool successful = false;
177 // various rational defaults 191 // various rational defaults
178 LLUUID fromAgentID = LLUUID.Zero; 192 LLUUID fromAgentID = LLUUID.Zero;
179 LLUUID fromAgentSession = LLUUID.Zero; 193 LLUUID fromAgentSession = LLUUID.Zero;
@@ -185,7 +199,7 @@ namespace OpenSim.Region.Environment.Modules.Avatar.InstantMessage
185 byte dialog = (byte)0; 199 byte dialog = (byte)0;
186 bool fromGroup = false; 200 bool fromGroup = false;
187 byte offline = (byte)0; 201 byte offline = (byte)0;
188 uint ParentEstateID; 202 uint ParentEstateID=0;
189 LLVector3 Position = LLVector3.Zero; 203 LLVector3 Position = LLVector3.Zero;
190 LLUUID RegionID = LLUUID.Zero ; 204 LLUUID RegionID = LLUUID.Zero ;
191 byte[] binaryBucket = new byte[0]; 205 byte[] binaryBucket = new byte[0];
@@ -303,12 +317,48 @@ namespace OpenSim.Region.Environment.Modules.Avatar.InstantMessage
303 317
304 Position = new LLVector3(pos_x, pos_y, pos_z); 318 Position = new LLVector3(pos_x, pos_y, pos_z);
305 binaryBucket = (byte[])requestData["binary_bucket"]; 319 binaryBucket = (byte[])requestData["binary_bucket"];
320 GridInstantMessage gim = new GridInstantMessage();
321 gim.fromAgentID = fromAgentID.UUID;
322 gim.fromAgentName = fromAgentName;
323 gim.fromAgentSession = fromAgentSession.UUID;
324 gim.fromGroup = fromGroup;
325 gim.imSessionID = imSessionID.UUID;
326 gim.RegionID = RegionID.UUID;
327 gim.timestamp = timestamp;
328 gim.toAgentID = toAgentID.UUID;
329 gim.message = message;
330 gim.dialog = dialog;
331 gim.offline = offline;
332 gim.ParentEstateID = ParentEstateID;
333 gim.Position = new sLLVector3(Position);
334 gim.binaryBucket = binaryBucket;
335
336
337 foreach (Scene scene in m_scenes)
338 {
339 if (scene.Entities.ContainsKey(toAgentID) && scene.Entities[toAgentID] is ScenePresence)
340 {
341 // Local message
342 ScenePresence user = (ScenePresence)scene.Entities[toAgentID];
343 if (!user.IsChildAgent)
344 {
345 scene.EventManager.TriggerGridInstantMessage(gim, InstantMessageReceiver.FriendsModule | InstantMessageReceiver.GroupsModule | InstantMessageReceiver.IMModule);
346 }
347 }
348 }
349 OnGridInstantMessage(gim);
350 successful = true;
306 } 351 }
307 352
308 return new XmlRpcResponse(); 353 XmlRpcResponse resp = new XmlRpcResponse();
309 //(string) 354 Hashtable respdata = new Hashtable();
310 //(string)requestData["message"]; 355 if (successful)
356 respdata["success"] = "TRUE";
357 else
358 respdata["success"] = "FALSE";
359 resp.Value = respdata;
311 360
361 return resp;
312 } 362 }
313 363
314 protected virtual void SendGridInstantMessageViaXMLRPC(IClientAPI client, LLUUID fromAgentID, 364 protected virtual void SendGridInstantMessageViaXMLRPC(IClientAPI client, LLUUID fromAgentID,
@@ -316,9 +366,194 @@ namespace OpenSim.Region.Environment.Modules.Avatar.InstantMessage
316 LLUUID imSessionID, uint timestamp, string fromAgentName, 366 LLUUID imSessionID, uint timestamp, string fromAgentName,
317 string message, byte dialog, bool fromGroup, byte offline, 367 string message, byte dialog, bool fromGroup, byte offline,
318 uint ParentEstateID, LLVector3 Position, LLUUID RegionID, 368 uint ParentEstateID, LLVector3 Position, LLUUID RegionID,
319 byte[] binaryBucket) 369 byte[] binaryBucket, ulong regionhandle, ulong prevRegionHandle)
370 {
371 UserAgentData upd = null;
372
373 bool lookupAgent = false;
374
375 lock (m_userRegionMap)
376 {
377 if (m_userRegionMap.ContainsKey(toAgentID) && prevRegionHandle == 0)
378 {
379 upd = new UserAgentData();
380 upd.AgentOnline = true;
381 upd.Handle = m_userRegionMap[toAgentID];
382
383 }
384 else
385 {
386 lookupAgent = true;
387
388
389 }
390 }
391
392 if (lookupAgent)
393 {
394 upd = m_scenes[0].CommsManager.UserService.GetAgentByUUID(toAgentID);
395
396 // check if we've tried this before..
397 if (upd.Handle == prevRegionHandle)
398 {
399 m_log.Error("[GRID INSTANT MESSAGE]: Unable to deliver an instant message");
400 if (client != null)
401 client.SendInstantMessage(toAgentID, fromAgentSession, "Unable to send instant message", fromAgentID, imSessionID, "System", (byte)InstantMessageDialog.MessageFromObject,(uint)Util.UnixTimeSinceEpoch());// SendAlertMessage("Unable to send instant message");
402 return;
403 }
404 }
405
406 if (upd != null)
407 {
408 if (upd.AgentOnline)
409 {
410 RegionInfo reginfo = m_scenes[0].CommsManager.GridService.RequestNeighbourInfo(upd.Handle);
411 if (reginfo != null)
412 {
413 GridInstantMessage msg = new GridInstantMessage();
414 msg.fromAgentID = fromAgentID.UUID;
415 msg.fromAgentSession = fromAgentSession.UUID;
416 msg.toAgentID = toAgentID.UUID;
417 msg.imSessionID = imSessionID.UUID;
418 msg.timestamp = timestamp;
419 msg.fromAgentName = fromAgentName;
420 msg.message = message;
421 msg.dialog = dialog;
422 msg.fromGroup = fromGroup;
423 msg.offline = offline;
424 msg.ParentEstateID = ParentEstateID;
425 msg.Position = new sLLVector3(Position);
426 msg.RegionID = RegionID.UUID;
427 msg.binaryBucket = binaryBucket;
428
429 Hashtable msgdata = ConvertGridInstantMessageToXMLRPC(msg);
430 msgdata["region_handle"] = getLocalRegionHandleFromUUID(RegionID);
431 bool imresult = doIMSending(reginfo, msgdata);
432 if (imresult)
433 {
434 lock (m_userRegionMap)
435 {
436 if (m_userRegionMap.ContainsKey(toAgentID))
437 {
438 m_userRegionMap[toAgentID] = upd.Handle;
439 }
440 else
441 {
442 m_userRegionMap.Add(toAgentID, upd.Handle);
443 }
444 }
445 m_log.Info("[GRID INSTANT MESSAGE]: Successfully sent a message");
446 }
447 else
448 {
449 // try again, but lookup user this time.
450 SendGridInstantMessageViaXMLRPC(client, fromAgentID,
451 fromAgentSession, toAgentID,
452 imSessionID, timestamp, fromAgentName,
453 message, dialog, fromGroup, offline,
454 ParentEstateID, Position, RegionID,
455 binaryBucket, regionhandle, upd.Handle);
456 }
457
458 }
459 }
460 else
461 {
462 // send Agent Offline message
463 if (client != null)
464 client.SendInstantMessage(toAgentID, fromAgentSession, "Unable to send instant message", fromAgentID, imSessionID, "System", (byte)InstantMessageDialog.MessageFromObject, (uint)Util.UnixTimeSinceEpoch());// SendAlertMessage("Unable to send instant message");
465 }
466 }
467 else
468 {
469 // send Agent Offline message
470 if (client != null)
471 client.SendInstantMessage(toAgentID, fromAgentSession, "Unable to send instant message", fromAgentID, imSessionID, "System", (byte)InstantMessageDialog.MessageFromObject, (uint)Util.UnixTimeSinceEpoch());// SendAlertMessage("Unable to send instant message");
472 }
473
474 }
475
476 private bool doIMSending(RegionInfo reginfo, Hashtable xmlrpcdata)
477 {
478
479 ArrayList SendParams = new ArrayList();
480 SendParams.Add(xmlrpcdata);
481 XmlRpcRequest GridReq = new XmlRpcRequest("grid_instant_message", SendParams);
482 try
483 {
484
485 XmlRpcResponse GridResp = GridReq.Send("http://" + reginfo.ExternalHostName + ":" + reginfo.HttpPort, 3000);
486
487 Hashtable responseData = (Hashtable)GridResp.Value;
488
489 if (responseData.ContainsKey("success"))
490 {
491 if ((string)responseData["success"] == "TRUE")
492 {
493 return true;
494 }
495 else
496 {
497 return false;
498 }
499 }
500 else
501 {
502 return false;
503 }
504 }
505 catch (WebException)
506 {
507 m_log.ErrorFormat("[GRID INSTANT MESSAGE]: Error sending message to {0} the host didn't respond", "http://" + reginfo.ExternalHostName + ":" + reginfo.HttpPort);
508 }
509
510 return false;
511 }
512
513 private ulong getLocalRegionHandleFromUUID(LLUUID regionID)
320 { 514 {
515 ulong returnhandle = 0;
321 516
517 lock (m_scenes)
518 {
519 foreach (Scene sn in m_scenes)
520 {
521 if (sn.RegionInfo.RegionID == regionID)
522 {
523 returnhandle = sn.RegionInfo.RegionHandle;
524 break;
525 }
526 }
527 }
528 return returnhandle;
322 } 529 }
530
531 private Hashtable ConvertGridInstantMessageToXMLRPC(GridInstantMessage msg)
532 {
533 Hashtable gim = new Hashtable();
534 gim["from_agent_id"] = msg.fromAgentID.ToString();
535 gim["from_agent_session"] = msg.fromAgentSession.ToString();
536 gim["to_agent_id"] = msg.toAgentID.ToString();
537 gim["im_session_id"] = msg.imSessionID.ToString();
538 gim["timestamp"] = msg.timestamp.ToString();
539 gim["from_agent_name"] = msg.fromAgentName;
540 gim["message"] = msg.message;
541 gim["dialog"] = msg.dialog;
542
543 if (msg.fromGroup)
544 gim["from_group"] = "TRUE";
545 else
546 gim["from_group"] = "FALSE";
547
548 gim["offline"] = msg.offline;
549 gim["parent_estate_id"] = msg.ParentEstateID.ToString();
550 gim["position_x"] = msg.Position.x.ToString();
551 gim["position_y"] = msg.Position.y.ToString();
552 gim["position_z"] = msg.Position.z.ToString();
553 gim["region_id"] = msg.RegionID.ToString();
554 gim["binary_bucket"] = msg.binaryBucket;
555 return gim;
556 }
557
323 } 558 }
324} \ No newline at end of file 559} \ No newline at end of file