From 9d2e1c67a8969e4769006c7347505b58a7827b3f Mon Sep 17 00:00:00 2001 From: "Justin Clark-Casey (justincc)" Date: Tue, 1 May 2012 23:14:12 +0100 Subject: [PATCH] Add regression test for teleporting between neighbouring regions on the same simulator This adds a non-advertised wait_for_callback option in [EntityTransfer]. Default is always true. Teleport tests disable the wait for callback from the destination region in order to run within a single thread. --- .../Linden/UDP/Tests/LLImageManagerTests.cs | 3 +- .../ClientStack/RegionApplicationBase.cs | 2 +- .../EntityTransfer/EntityTransferModule.cs | 30 ++++- .../Tests/InventoryAccessModuleTests.cs | 7 +- .../Region/Framework/Scenes/ScenePresence.cs | 4 +- .../Scenes/Tests/ScenePresenceAgentTests.cs | 3 +- .../Tests/ScenePresenceTeleportTests.cs | 112 ++++++++++++++++-- OpenSim/Tests/Common/Helpers/SceneHelpers.cs | 72 ++++++++++- OpenSim/Tests/Common/Mock/TestClient.cs | 39 +++++- OpenSim/Tests/Common/TestHelpers.cs | 9 +- 10 files changed, 248 insertions(+), 33 deletions(-) diff --git a/OpenSim/Region/ClientStack/Linden/UDP/Tests/LLImageManagerTests.cs b/OpenSim/Region/ClientStack/Linden/UDP/Tests/LLImageManagerTests.cs index 221f02bda9..5fcf376b84 100644 --- a/OpenSim/Region/ClientStack/Linden/UDP/Tests/LLImageManagerTests.cs +++ b/OpenSim/Region/ClientStack/Linden/UDP/Tests/LLImageManagerTests.cs @@ -79,7 +79,8 @@ namespace OpenSim.Region.ClientStack.LindenUDP.Tests J2KDecoderModule j2kdm = new J2KDecoderModule(); - scene = new SceneHelpers().SetupScene(); + SceneHelpers sceneHelpers = new SceneHelpers(); + scene = sceneHelpers.SetupScene(); SceneHelpers.SetupSceneModules(scene, j2kdm); tc = new TestClient(SceneHelpers.GenerateAgentData(userId), scene); diff --git a/OpenSim/Region/ClientStack/RegionApplicationBase.cs b/OpenSim/Region/ClientStack/RegionApplicationBase.cs index 6e3a58e63a..6e78d6d774 100644 --- a/OpenSim/Region/ClientStack/RegionApplicationBase.cs +++ b/OpenSim/Region/ClientStack/RegionApplicationBase.cs @@ -111,7 +111,7 @@ namespace OpenSim.Region.ClientStack server.Start(); } } - + base.StartupSpecific(); } diff --git a/OpenSim/Region/CoreModules/Framework/EntityTransfer/EntityTransferModule.cs b/OpenSim/Region/CoreModules/Framework/EntityTransfer/EntityTransferModule.cs index 230706e042..35486bb5c1 100644 --- a/OpenSim/Region/CoreModules/Framework/EntityTransfer/EntityTransferModule.cs +++ b/OpenSim/Region/CoreModules/Framework/EntityTransfer/EntityTransferModule.cs @@ -52,12 +52,20 @@ namespace OpenSim.Region.CoreModules.Framework.EntityTransfer private static readonly ILog m_log = LogManager.GetLogger(MethodBase.GetCurrentMethod().DeclaringType); public const int DefaultMaxTransferDistance = 4095; + public const bool EnableWaitForCallbackFromTeleportDestDefault = true; + /// /// The maximum distance, in standard region units (256m) that an agent is allowed to transfer. /// public int MaxTransferDistance { get; set; } + /// + /// If true then on a teleport, the source region waits for a callback from the destination region. If + /// a callback fails to arrive within a set time then the user is pulled back into the source region. + /// + public bool EnableWaitForCallbackFromTeleportDest { get; set; } + protected bool m_Enabled = false; protected Scene m_aScene; protected List m_Scenes = new List(); @@ -99,9 +107,16 @@ namespace OpenSim.Region.CoreModules.Framework.EntityTransfer { IConfig transferConfig = source.Configs["EntityTransfer"]; if (transferConfig != null) + { + EnableWaitForCallbackFromTeleportDest + = transferConfig.GetBoolean("wait_for_callback", EnableWaitForCallbackFromTeleportDestDefault); + MaxTransferDistance = transferConfig.GetInt("max_distance", DefaultMaxTransferDistance); + } else + { MaxTransferDistance = DefaultMaxTransferDistance; + } m_agentsInTransit = new List(); m_Enabled = true; @@ -499,6 +514,9 @@ namespace OpenSim.Region.CoreModules.Framework.EntityTransfer } else { + ICapabilitiesModule capModule = sp.Scene.CapsModule; + ulong regionHandle = reg.RegionHandle; + capModule.GetChildSeed(UUID.Zero, regionHandle); agentCircuit.CapsPath = sp.Scene.CapsModule.GetChildSeed(sp.UUID, reg.RegionHandle); capsPath = finalDestination.ServerURI + CapsUtil.GetCapsSeedPath(agentCircuit.CapsPath); } @@ -527,7 +545,8 @@ namespace OpenSim.Region.CoreModules.Framework.EntityTransfer sp.ControllingClient.SendTeleportProgress(teleportFlags | (uint)TeleportFlags.DisableCancel, "sending_dest"); m_log.DebugFormat( - "[ENTITY TRANSFER MODULE]: Sending new CAPS seed url {0} to client {1}", capsPath, sp.UUID); + "[ENTITY TRANSFER MODULE]: Sending new CAPS seed url {0} from {1} to {2}", + capsPath, sp.Scene.RegionInfo.RegionName, sp.Name); if (eq != null) { @@ -546,7 +565,7 @@ namespace OpenSim.Region.CoreModules.Framework.EntityTransfer // TeleportFinish makes the client send CompleteMovementIntoRegion (at the destination), which // trigers a whole shebang of things there, including MakeRoot. So let's wait for confirmation // that the client contacted the destination before we close things here. - if (!WaitForCallback(sp.UUID)) + if (EnableWaitForCallbackFromTeleportDest && !WaitForCallback(sp.UUID)) { m_log.WarnFormat( "[ENTITY TRANSFER MODULE]: Teleport of {0} to {1} failed due to no callback from destination region. Returning avatar to source region.", @@ -1286,7 +1305,6 @@ namespace OpenSim.Region.CoreModules.Framework.EntityTransfer { if (neighbour.RegionHandle != sp.Scene.RegionInfo.RegionHandle) { - AgentCircuitData currentAgentCircuit = sp.Scene.AuthenticateHandler.GetAgentCircuitData(sp.ControllingClient.CircuitCode); AgentCircuitData agent = sp.ControllingClient.RequestClientInfo(); agent.BaseFolder = UUID.Zero; @@ -1311,7 +1329,9 @@ namespace OpenSim.Region.CoreModules.Framework.EntityTransfer seeds.Add(neighbour.RegionHandle, agent.CapsPath); } else + { agent.CapsPath = sp.Scene.CapsModule.GetChildSeed(sp.UUID, neighbour.RegionHandle); + } cagents.Add(agent); } @@ -1926,7 +1946,7 @@ namespace OpenSim.Region.CoreModules.Framework.EntityTransfer int count = 200; while (m_agentsInTransit.Contains(id) && count-- > 0) { - //m_log.Debug(" >>> Waiting... " + count); +// m_log.Debug(" >>> Waiting... " + count); Thread.Sleep(100); } @@ -1934,6 +1954,8 @@ namespace OpenSim.Region.CoreModules.Framework.EntityTransfer return true; else return false; + + return true; } protected void SetInTransit(UUID id) diff --git a/OpenSim/Region/CoreModules/Framework/InventoryAccess/Tests/InventoryAccessModuleTests.cs b/OpenSim/Region/CoreModules/Framework/InventoryAccess/Tests/InventoryAccessModuleTests.cs index d6afaa9e75..21d8bd77a9 100644 --- a/OpenSim/Region/CoreModules/Framework/InventoryAccess/Tests/InventoryAccessModuleTests.cs +++ b/OpenSim/Region/CoreModules/Framework/InventoryAccess/Tests/InventoryAccessModuleTests.cs @@ -64,8 +64,9 @@ namespace OpenSim.Region.CoreModules.Framework.InventoryAccess.Tests IConfigSource config = new IniConfigSource(); config.AddConfig("Modules"); config.Configs["Modules"].Set("InventoryAccessModule", "BasicInventoryAccessModule"); - - m_scene = new SceneHelpers().SetupScene(); + + SceneHelpers sceneHelpers = new SceneHelpers(); + m_scene = sceneHelpers.SetupScene(); SceneHelpers.SetupSceneModules(m_scene, config, m_iam); // Create user @@ -76,7 +77,7 @@ namespace OpenSim.Region.CoreModules.Framework.InventoryAccess.Tests AgentCircuitData acd = new AgentCircuitData(); acd.AgentID = m_userId; - m_tc = new TestClient(acd, m_scene); + m_tc = new TestClient(acd, m_scene); } [Test] diff --git a/OpenSim/Region/Framework/Scenes/ScenePresence.cs b/OpenSim/Region/Framework/Scenes/ScenePresence.cs index f1d092616c..e5a9a996ba 100644 --- a/OpenSim/Region/Framework/Scenes/ScenePresence.cs +++ b/OpenSim/Region/Framework/Scenes/ScenePresence.cs @@ -2895,8 +2895,8 @@ namespace OpenSim.Region.Framework.Scenes x = x / Constants.RegionSize; y = y / Constants.RegionSize; - //m_log.Debug("---> x: " + x + "; newx:" + newRegionX + "; Abs:" + (int)Math.Abs((int)(x - newRegionX))); - //m_log.Debug("---> y: " + y + "; newy:" + newRegionY + "; Abs:" + (int)Math.Abs((int)(y - newRegionY))); +// m_log.Debug("---> x: " + x + "; newx:" + newRegionX + "; Abs:" + (int)Math.Abs((int)(x - newRegionX))); +// m_log.Debug("---> y: " + y + "; newy:" + newRegionY + "; Abs:" + (int)Math.Abs((int)(y - newRegionY))); if (Util.IsOutsideView(DrawDistance, x, newRegionX, y, newRegionY)) { byebyeRegions.Add(handle); diff --git a/OpenSim/Region/Framework/Scenes/Tests/ScenePresenceAgentTests.cs b/OpenSim/Region/Framework/Scenes/Tests/ScenePresenceAgentTests.cs index 2e46377901..1aa48d7520 100644 --- a/OpenSim/Region/Framework/Scenes/Tests/ScenePresenceAgentTests.cs +++ b/OpenSim/Region/Framework/Scenes/Tests/ScenePresenceAgentTests.cs @@ -128,7 +128,8 @@ namespace OpenSim.Region.Framework.Scenes.Tests IConfig config = configSource.AddConfig("Modules"); config.Set("SimulationServices", "LocalSimulationConnectorModule"); - TestScene scene = new SceneHelpers().SetupScene(); + SceneHelpers sceneHelpers = new SceneHelpers(); + TestScene scene = sceneHelpers.SetupScene(); SceneHelpers.SetupSceneModules(scene, configSource, lsc); UUID agentId = TestHelpers.ParseTail(0x01); diff --git a/OpenSim/Region/Framework/Scenes/Tests/ScenePresenceTeleportTests.cs b/OpenSim/Region/Framework/Scenes/Tests/ScenePresenceTeleportTests.cs index c750cc5d10..ea4fb66b4e 100644 --- a/OpenSim/Region/Framework/Scenes/Tests/ScenePresenceTeleportTests.cs +++ b/OpenSim/Region/Framework/Scenes/Tests/ScenePresenceTeleportTests.cs @@ -33,8 +33,9 @@ using OpenMetaverse; using OpenSim.Framework; using OpenSim.Framework.Communications; using OpenSim.Framework.Servers; -using OpenSim.Region.CoreModules.Framework.EntityTransfer; using OpenSim.Region.Framework.Interfaces; +using OpenSim.Region.CoreModules.Framework; +using OpenSim.Region.CoreModules.Framework.EntityTransfer; using OpenSim.Region.CoreModules.ServiceConnectorsOut.Simulation; using OpenSim.Tests.Common; using OpenSim.Tests.Common.Mock; @@ -49,6 +50,22 @@ namespace OpenSim.Region.Framework.Scenes.Tests [TestFixture] public class ScenePresenceTeleportTests { + [TestFixtureSetUp] + public void FixtureInit() + { + // Don't allow tests to be bamboozled by asynchronous events. Execute everything on the same thread. + Util.FireAndForgetMethod = FireAndForgetMethod.RegressionTest; + } + + [TestFixtureTearDown] + public void TearDown() + { + // We must set this back afterwards, otherwise later tests will fail since they're expecting multiple + // threads. Possibly, later tests should be rewritten so none of them require async stuff (which regression + // tests really shouldn't). + Util.FireAndForgetMethod = Util.DefaultFireAndForgetMethod; + } + [Test] public void TestSameRegionTeleport() { @@ -96,10 +113,14 @@ namespace OpenSim.Region.Framework.Scenes.Tests LocalSimulationConnectorModule lscm = new LocalSimulationConnectorModule(); IConfigSource config = new IniConfigSource(); - config.AddConfig("Modules"); - // Not strictly necessary since FriendsModule assumes it is the default (!) - config.Configs["Modules"].Set("EntityTransferModule", etm.Name); - config.Configs["Modules"].Set("SimulationServices", lscm.Name); + IConfig modulesConfig = config.AddConfig("Modules"); + modulesConfig.Set("EntityTransferModule", etm.Name); + modulesConfig.Set("SimulationServices", lscm.Name); + IConfig entityTransferConfig = config.AddConfig("EntityTransfer"); + + // In order to run a single threaded regression test we do not want the entity transfer module waiting + // for a callback from the destination scene before removing its avatar data. + entityTransferConfig.Set("wait_for_callback", false); SceneHelpers sh = new SceneHelpers(); TestScene sceneA = sh.SetupScene("sceneA", TestHelpers.ParseTail(0x100), 1000, 1000); @@ -110,12 +131,12 @@ namespace OpenSim.Region.Framework.Scenes.Tests Vector3 teleportPosition = new Vector3(10, 11, 12); Vector3 teleportLookAt = new Vector3(20, 21, 22); - ScenePresence sp = SceneHelpers.AddScenePresence(sceneA, userId); + ScenePresence sp = SceneHelpers.AddScenePresence(sceneA, userId, sh.SceneManager); sp.AbsolutePosition = new Vector3(30, 31, 32); // XXX: A very nasty hack to tell the client about the destination scene without having to crank the whole // UDP stack (?) - ((TestClient)sp.ControllingClient).TeleportTargetScene = sceneB; +// ((TestClient)sp.ControllingClient).TeleportTargetScene = sceneB; sceneA.RequestTeleportLocation( sp.ControllingClient, @@ -124,6 +145,8 @@ namespace OpenSim.Region.Framework.Scenes.Tests teleportLookAt, (uint)TeleportFlags.ViaLocation); + ((TestClient)sp.ControllingClient).CompleteTeleportClientSide(); + Assert.That(sceneA.GetScenePresence(userId), Is.Null); ScenePresence sceneBSp = sceneB.GetScenePresence(userId); @@ -137,5 +160,80 @@ namespace OpenSim.Region.Framework.Scenes.Tests // position instead). // Assert.That(sp.Lookat, Is.EqualTo(teleportLookAt)); } + + [Test] + public void TestSameSimulatorNeighbouringRegionsTeleport() + { + TestHelpers.InMethod(); +// TestHelpers.EnableLogging(); + + UUID userId = TestHelpers.ParseTail(0x1); + + EntityTransferModule etm = new EntityTransferModule(); + LocalSimulationConnectorModule lscm = new LocalSimulationConnectorModule(); + + IConfigSource config = new IniConfigSource(); + IConfig modulesConfig = config.AddConfig("Modules"); + modulesConfig.Set("EntityTransferModule", etm.Name); + modulesConfig.Set("SimulationServices", lscm.Name); + IConfig entityTransferConfig = config.AddConfig("EntityTransfer"); + + // In order to run a single threaded regression test we do not want the entity transfer module waiting + // for a callback from the destination scene before removing its avatar data. + entityTransferConfig.Set("wait_for_callback", false); + + SceneHelpers sh = new SceneHelpers(); + TestScene sceneA = sh.SetupScene("sceneA", TestHelpers.ParseTail(0x100), 1000, 1000); + TestScene sceneB = sh.SetupScene("sceneB", TestHelpers.ParseTail(0x200), 1001, 1000); + + SceneHelpers.SetupSceneModules(new Scene[] { sceneA, sceneB }, config, etm, lscm); + SceneHelpers.SetupSceneModules(sceneA, new CapabilitiesModule()); + SceneHelpers.SetupSceneModules(sceneB, new CapabilitiesModule()); + + Vector3 teleportPosition = new Vector3(10, 11, 12); + Vector3 teleportLookAt = new Vector3(20, 21, 22); + + ScenePresence originalSp = SceneHelpers.AddScenePresence(sceneA, userId, sh.SceneManager); + originalSp.AbsolutePosition = new Vector3(30, 31, 32); + + ScenePresence beforeSceneASp = sceneA.GetScenePresence(userId); + Assert.That(beforeSceneASp, Is.Not.Null); + Assert.That(beforeSceneASp.IsChildAgent, Is.False); + + ScenePresence beforeSceneBSp = sceneB.GetScenePresence(userId); + Assert.That(beforeSceneBSp, Is.Not.Null); + Assert.That(beforeSceneBSp.IsChildAgent, Is.True); + + // XXX: A very nasty hack to tell the client about the destination scene without having to crank the whole + // UDP stack (?) +// ((TestClient)beforeSceneASp.ControllingClient).TeleportTargetScene = sceneB; + + sceneA.RequestTeleportLocation( + beforeSceneASp.ControllingClient, + sceneB.RegionInfo.RegionHandle, + teleportPosition, + teleportLookAt, + (uint)TeleportFlags.ViaLocation); + + ((TestClient)beforeSceneASp.ControllingClient).CompleteTeleportClientSide(); + + ScenePresence afterSceneASp = sceneA.GetScenePresence(userId); + Assert.That(afterSceneASp, Is.Not.Null); + Assert.That(afterSceneASp.IsChildAgent, Is.True); + + ScenePresence afterSceneBSp = sceneB.GetScenePresence(userId); + Assert.That(afterSceneBSp, Is.Not.Null); + Assert.That(afterSceneBSp.IsChildAgent, Is.False); + Assert.That(afterSceneBSp.Scene.RegionInfo.RegionName, Is.EqualTo(sceneB.RegionInfo.RegionName)); + Assert.That(afterSceneBSp.AbsolutePosition, Is.EqualTo(teleportPosition)); + + // TODO: Add assertions to check correct circuit details in both scenes. + + // Lookat is sent to the client only - sp.Lookat does not yield the same thing (calculation from camera + // position instead). +// Assert.That(sp.Lookat, Is.EqualTo(teleportLookAt)); + +// TestHelpers.DisableLogging(); + } } } \ No newline at end of file diff --git a/OpenSim/Tests/Common/Helpers/SceneHelpers.cs b/OpenSim/Tests/Common/Helpers/SceneHelpers.cs index 8e547077fc..dc24418145 100644 --- a/OpenSim/Tests/Common/Helpers/SceneHelpers.cs +++ b/OpenSim/Tests/Common/Helpers/SceneHelpers.cs @@ -58,6 +58,11 @@ namespace OpenSim.Tests.Common /// public class SceneHelpers { + /// + /// We need a scene manager so that test clients can retrieve a scene when performing teleport tests. + /// + public SceneManager SceneManager { get; private set; } + private AgentCircuitManager m_acm = new AgentCircuitManager(); private ISimulationDataService m_simDataService = OpenSim.Server.Base.ServerUtils.LoadPlugin("OpenSim.Tests.Common.dll", null); @@ -76,6 +81,8 @@ namespace OpenSim.Tests.Common public SceneHelpers(CoreAssetCache cache) { + SceneManager = new SceneManager(); + m_assetService = StartAssetService(cache); m_authenticationService = StartAuthenticationService(); m_inventoryService = StartInventoryService(); @@ -186,6 +193,8 @@ namespace OpenSim.Tests.Common testScene.LoginsDisabled = false; testScene.RegisterRegionWithGrid(); + SceneManager.Add(testScene); + return testScene; } @@ -350,6 +359,7 @@ namespace OpenSim.Tests.Common List newModules = new List(); foreach (object module in modules) { +// Console.WriteLine("MODULE RAW {0}", module); if (module is IRegionModule) { IRegionModule m = (IRegionModule)module; @@ -367,6 +377,7 @@ namespace OpenSim.Tests.Common // for the new system, everything has to be initialised first, // shared modules have to be post-initialised, then all get an AddRegion with the scene IRegionModuleBase m = (IRegionModuleBase)module; +// Console.WriteLine("MODULE {0}", m.Name); m.Initialise(config); newModules.Add(m); } @@ -426,6 +437,10 @@ namespace OpenSim.Tests.Common /// /// Add a root agent where the details of the agent connection (apart from the id) are unimportant for the test /// + /// + /// This can be used for tests where there is only one region or where there are multiple non-neighbour regions + /// and teleport doesn't take place. + /// /// /// /// @@ -434,6 +449,18 @@ namespace OpenSim.Tests.Common return AddScenePresence(scene, GenerateAgentData(agentId)); } + /// + /// Add a root agent where the details of the agent connection (apart from the id) are unimportant for the test + /// + /// + /// + /// + /// + public static ScenePresence AddScenePresence(Scene scene, UUID agentId, SceneManager sceneManager) + { + return AddScenePresence(scene, GenerateAgentData(agentId), sceneManager); + } + /// /// Add a root agent. /// @@ -453,6 +480,30 @@ namespace OpenSim.Tests.Common /// /// public static ScenePresence AddScenePresence(Scene scene, AgentCircuitData agentData) + { + return AddScenePresence(scene, agentData, null); + } + + /// + /// Add a root agent. + /// + /// + /// This function + /// + /// 1) Tells the scene that an agent is coming. Normally, the login service (local if standalone, from the + /// userserver if grid) would give initial login data back to the client and separately tell the scene that the + /// agent was coming. + /// + /// 2) Connects the agent with the scene + /// + /// This function performs actions equivalent with notifying the scene that an agent is + /// coming and then actually connecting the agent to the scene. The one step missed out is the very first + /// + /// + /// + /// + /// + public static ScenePresence AddScenePresence(Scene scene, AgentCircuitData agentData, SceneManager sceneManager) { // We emulate the proper login sequence here by doing things in four stages @@ -463,7 +514,7 @@ namespace OpenSim.Tests.Common lpsc.m_PresenceService.LoginAgent(agentData.AgentID.ToString(), agentData.SessionID, agentData.SecureSessionID); // Stages 1 & 2 - ScenePresence sp = IntroduceClientToScene(scene, agentData, TeleportFlags.ViaLogin); + ScenePresence sp = IntroduceClientToScene(scene, sceneManager, agentData, TeleportFlags.ViaLogin); // Stage 3: Complete the entrance into the region. This converts the child agent into a root agent. sp.CompleteMovement(sp.ControllingClient, true); @@ -471,7 +522,20 @@ namespace OpenSim.Tests.Common return sp; } - private static ScenePresence IntroduceClientToScene(Scene scene, AgentCircuitData agentData, TeleportFlags tf) + /// + /// Introduce an agent into the scene by adding a new client. + /// + /// The scene presence added + /// + /// Scene manager. Can be null if there is only one region in the test or multiple regions that are not + /// neighbours and where no teleporting takes place. + /// + /// + /// + /// + private static ScenePresence IntroduceClientToScene( + Scene scene, SceneManager sceneManager, AgentCircuitData agentData, TeleportFlags tf) { string reason; @@ -480,7 +544,7 @@ namespace OpenSim.Tests.Common Console.WriteLine("NewUserConnection failed: " + reason); // Stage 2: add the new client as a child agent to the scene - TestClient client = new TestClient(agentData, scene); + TestClient client = new TestClient(agentData, scene, sceneManager); scene.AddNewClient(client, PresenceType.User); return scene.GetScenePresence(agentData.AgentID); @@ -492,7 +556,7 @@ namespace OpenSim.Tests.Common acd.child = true; // XXX: ViaLogin may not be correct for child agents - return IntroduceClientToScene(scene, acd, TeleportFlags.ViaLogin); + return IntroduceClientToScene(scene, null, acd, TeleportFlags.ViaLogin); } /// diff --git a/OpenSim/Tests/Common/Mock/TestClient.cs b/OpenSim/Tests/Common/Mock/TestClient.cs index cb9840e4f7..36049a1386 100644 --- a/OpenSim/Tests/Common/Mock/TestClient.cs +++ b/OpenSim/Tests/Common/Mock/TestClient.cs @@ -46,12 +46,10 @@ namespace OpenSim.Tests.Common.Mock EventWaitHandle wh = new EventWaitHandle (false, EventResetMode.AutoReset, "Crossing"); - // TODO: This is a really nasty (and temporary) means of telling the test client which scene to invoke setup - // methods on when a teleport is requested - public Scene TeleportTargetScene; private TestClient TeleportSceneClient; private Scene m_scene; + private SceneManager m_sceneManager; // Properties so that we can get at received data for test purposes public List ReceivedOfflineNotifications { get; private set; } @@ -432,15 +430,29 @@ namespace OpenSim.Tests.Common.Mock /// /// Constructor /// + /// + /// Can be used for a test where there is only one region or where there are multiple regions that are not + /// neighbours and where no teleporting takes place. In other situations, the constructor that takes in a + /// scene manager should be used. + /// /// /// - public TestClient(AgentCircuitData agentData, Scene scene) + public TestClient(AgentCircuitData agentData, Scene scene) : this(agentData, scene, null) {} + + /// + /// Constructor + /// + /// + /// + /// + public TestClient(AgentCircuitData agentData, Scene scene, SceneManager sceneManager) { m_agentId = agentData.AgentID; m_firstName = agentData.firstname; m_lastName = agentData.lastname; m_circuitCode = agentData.circuitcode; m_scene = scene; + m_sceneManager = sceneManager; SessionId = agentData.SessionID; SecureSessionId = agentData.SecureSessionID; CapsSeedUrl = agentData.CapsPath; @@ -590,8 +602,16 @@ namespace OpenSim.Tests.Common.Mock AgentCircuitData newAgent = RequestClientInfo(); // Stage 2: add the new client as a child agent to the scene - TeleportSceneClient = new TestClient(newAgent, TeleportTargetScene); - TeleportTargetScene.AddNewClient(TeleportSceneClient, PresenceType.User); + uint x, y; + Utils.LongToUInts(neighbourHandle, out x, out y); + x /= Constants.RegionSize; + y /= Constants.RegionSize; + + Scene neighbourScene; + m_sceneManager.TryGetScene(x, y, out neighbourScene); + + TeleportSceneClient = new TestClient(newAgent, neighbourScene, m_sceneManager); + neighbourScene.AddNewClient(TeleportSceneClient, PresenceType.User); } public virtual void SendRegionTeleport(ulong regionHandle, byte simAccess, IPEndPoint regionExternalEndPoint, @@ -601,6 +621,13 @@ namespace OpenSim.Tests.Common.Mock CapsSeedUrl = capsURL; + // We don't do this here so that the source region can complete processing first in a single-threaded + // regression test scenario. The test itself will have to call CompleteTeleportClientSide() after a teleport + // CompleteTeleportClientSide(); + } + + public void CompleteTeleportClientSide() + { TeleportSceneClient.CompleteMovement(); //TeleportTargetScene.AgentCrossing(newAgent.AgentID, new Vector3(90, 90, 90), false); } diff --git a/OpenSim/Tests/Common/TestHelpers.cs b/OpenSim/Tests/Common/TestHelpers.cs index 5030d4bf7f..6744fcac97 100644 --- a/OpenSim/Tests/Common/TestHelpers.cs +++ b/OpenSim/Tests/Common/TestHelpers.cs @@ -46,7 +46,8 @@ namespace OpenSim.Tests.Common - + + @@ -62,9 +63,9 @@ namespace OpenSim.Tests.Common Encoding.UTF8.GetBytes( // ""))); //""))); - //""))); - //""))); - //""))); +// "")); +// ""))); +// "")); "")); public static bool AssertThisDelegateCausesArgumentException(TestDelegate d)