diff --git a/OpenSim/Region/CoreModules/Avatar/Attachments/Tests/AttachmentsModuleTests.cs b/OpenSim/Region/CoreModules/Avatar/Attachments/Tests/AttachmentsModuleTests.cs index 25444e5171..508743c786 100644 --- a/OpenSim/Region/CoreModules/Avatar/Attachments/Tests/AttachmentsModuleTests.cs +++ b/OpenSim/Region/CoreModules/Avatar/Attachments/Tests/AttachmentsModuleTests.cs @@ -833,11 +833,11 @@ namespace OpenSim.Region.CoreModules.Avatar.Attachments.Tests UserAccount ua1 = UserAccountHelpers.CreateUserWithInventory(sceneA, 0x1); AgentCircuitData acd = SceneHelpers.GenerateAgentData(ua1.PrincipalID); - TestClient tc = new TestClient(acd, sceneA, sh.SceneManager); + TestClient tc = new TestClient(acd, sceneA); List destinationTestClients = new List(); EntityTransferHelpers.SetUpInformClientOfNeighbour(tc, destinationTestClients); - ScenePresence beforeTeleportSp = SceneHelpers.AddScenePresence(sceneA, tc, acd, sh.SceneManager); + ScenePresence beforeTeleportSp = SceneHelpers.AddScenePresence(sceneA, tc, acd); beforeTeleportSp.AbsolutePosition = new Vector3(30, 31, 32); InventoryItemBase attItem = CreateAttachmentItem(sceneA, ua1.PrincipalID, "att", 0x10, 0x20); diff --git a/OpenSim/Region/Framework/Scenes/SceneObjectGroup.cs b/OpenSim/Region/Framework/Scenes/SceneObjectGroup.cs index 9e7a986f36..3b2f537e44 100644 --- a/OpenSim/Region/Framework/Scenes/SceneObjectGroup.cs +++ b/OpenSim/Region/Framework/Scenes/SceneObjectGroup.cs @@ -1221,11 +1221,11 @@ namespace OpenSim.Region.Framework.Scenes /// /// Delete this group from its scene. /// - /// + /// /// This only handles the in-world consequences of deletion (e.g. any avatars sitting on it are forcibly stood /// up and all avatars receive notification of its removal. Removal of the scene object from database backup /// must be handled by the caller. - /// + /// /// If true then deletion is not broadcast to clients public void DeleteGroupFromScene(bool silent) { @@ -1234,10 +1234,10 @@ namespace OpenSim.Region.Framework.Scenes { SceneObjectPart part = parts[i]; - Scene.ForEachRootScenePresence(delegate(ScenePresence avatar) + Scene.ForEachScenePresence(sp => { - if (avatar.ParentID == LocalId) - avatar.StandUp(); + if (!sp.IsChildAgent && sp.ParentID == LocalId) + sp.StandUp(); if (!silent) { @@ -1245,9 +1245,9 @@ namespace OpenSim.Region.Framework.Scenes if (part == m_rootPart) { if (!IsAttachment - || AttachedAvatar == avatar.ControllingClient.AgentId + || AttachedAvatar == sp.UUID || !HasPrivateAttachmentPoint) - avatar.ControllingClient.SendKillObject(m_regionHandle, new List { part.LocalId }); + sp.ControllingClient.SendKillObject(m_regionHandle, new List { part.LocalId }); } } }); diff --git a/OpenSim/Region/Framework/Scenes/Tests/SceneObjectDeRezTests.cs b/OpenSim/Region/Framework/Scenes/Tests/SceneObjectDeRezTests.cs index bde15cdb9c..f738ff188e 100644 --- a/OpenSim/Region/Framework/Scenes/Tests/SceneObjectDeRezTests.cs +++ b/OpenSim/Region/Framework/Scenes/Tests/SceneObjectDeRezTests.cs @@ -33,7 +33,9 @@ using NUnit.Framework; using OpenMetaverse; using OpenSim.Framework; using OpenSim.Framework.Communications; +using OpenSim.Region.CoreModules.Framework.EntityTransfer; using OpenSim.Region.CoreModules.Framework.InventoryAccess; +using OpenSim.Region.CoreModules.ServiceConnectorsOut.Simulation; using OpenSim.Region.CoreModules.World.Permissions; using OpenSim.Region.Framework.Scenes; using OpenSim.Services.Interfaces; @@ -52,6 +54,24 @@ namespace OpenSim.Region.Framework.Scenes.Tests [TestFixture] public class SceneObjectDeRezTests : OpenSimTestCase { + [TestFixtureSetUp] + public void FixtureInit() + { + // Don't allow tests to be bamboozled by asynchronous events. Execute everything on the same thread. + // This facility was added after the original async delete tests were written, so it may be possible now + // to not bother explicitly disabling their async (since everything will be running sync). + 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 deleting an object from a scene. /// @@ -63,7 +83,7 @@ namespace OpenSim.Region.Framework.Scenes.Tests UUID userId = UUID.Parse("10000000-0000-0000-0000-000000000001"); TestScene scene = new SceneHelpers().SetupScene(); - SceneHelpers.SetupSceneModules(scene, new object[] { new PermissionsModule() }); + SceneHelpers.SetupSceneModules(scene, new PermissionsModule()); IClientAPI client = SceneHelpers.AddScenePresence(scene, userId).ControllingClient; // Turn off the timer on the async sog deleter - we'll crank it by hand for this test. @@ -87,7 +107,59 @@ namespace OpenSim.Region.Framework.Scenes.Tests sogd.InventoryDeQueueAndDelete(); SceneObjectPart retrievedPart2 = scene.GetSceneObjectPart(part.LocalId); - Assert.That(retrievedPart2, Is.Null); + Assert.That(retrievedPart2, Is.Null); + } + + /// + /// Test that child and root agents correctly receive KillObject notifications. + /// + [Test] + public void TestDeRezSceneObjectToAgents() + { + TestHelpers.InMethod(); +// TestHelpers.EnableLogging(); + + SceneHelpers sh = new SceneHelpers(); + TestScene sceneA = sh.SetupScene("sceneA", TestHelpers.ParseTail(0x100), 1000, 1000); + TestScene sceneB = sh.SetupScene("sceneB", TestHelpers.ParseTail(0x200), 1000, 999); + + // We need this so that the creation of the root client for userB in sceneB can trigger the creation of a child client in sceneA + LocalSimulationConnectorModule lscm = new LocalSimulationConnectorModule(); + EntityTransferModule etmB = new EntityTransferModule(); + IConfigSource config = new IniConfigSource(); + IConfig modulesConfig = config.AddConfig("Modules"); + modulesConfig.Set("EntityTransferModule", etmB.Name); + modulesConfig.Set("SimulationServices", lscm.Name); + SceneHelpers.SetupSceneModules(new Scene[] { sceneA, sceneB }, config, lscm); + SceneHelpers.SetupSceneModules(sceneB, config, etmB); + + // We need this for derez + SceneHelpers.SetupSceneModules(sceneA, new PermissionsModule()); + + UserAccount uaA = UserAccountHelpers.CreateUserWithInventory(sceneA, "Andy", "AAA", 0x1, ""); + UserAccount uaB = UserAccountHelpers.CreateUserWithInventory(sceneA, "Brian", "BBB", 0x2, ""); + + TestClient clientA = (TestClient)SceneHelpers.AddScenePresence(sceneA, uaA).ControllingClient; + + // This is the more long-winded route we have to take to get a child client created for userB in sceneA + // rather than just calling AddScenePresence() as for userA + AgentCircuitData acd = SceneHelpers.GenerateAgentData(uaB); + TestClient clientB = new TestClient(acd, sceneB); + List childClientsB = new List(); + EntityTransferHelpers.SetUpInformClientOfNeighbour(clientB, childClientsB); + + SceneHelpers.AddScenePresence(sceneB, clientB, acd); + + SceneObjectGroup so = SceneHelpers.AddSceneObject(sceneA); + uint soLocalId = so.LocalId; + + sceneA.DeleteSceneObject(so, false); + + Assert.That(clientA.ReceivedKills.Count, Is.EqualTo(1)); + Assert.That(clientA.ReceivedKills[0], Is.EqualTo(soLocalId)); + + Assert.That(childClientsB[0].ReceivedKills.Count, Is.EqualTo(1)); + Assert.That(childClientsB[0].ReceivedKills[0], Is.EqualTo(soLocalId)); } /// @@ -106,7 +178,7 @@ namespace OpenSim.Region.Framework.Scenes.Tests UUID objectOwnerId = UUID.Parse("20000000-0000-0000-0000-000000000001"); TestScene scene = new SceneHelpers().SetupScene(); - SceneHelpers.SetupSceneModules(scene, new object[] { new PermissionsModule() }); + SceneHelpers.SetupSceneModules(scene, new PermissionsModule()); IClientAPI client = SceneHelpers.AddScenePresence(scene, userId).ControllingClient; // Turn off the timer on the async sog deleter - we'll crank it by hand for this test. diff --git a/OpenSim/Region/Framework/Scenes/Tests/ScenePresenceCrossingTests.cs b/OpenSim/Region/Framework/Scenes/Tests/ScenePresenceCrossingTests.cs index 8775949ff4..5a722398e2 100644 --- a/OpenSim/Region/Framework/Scenes/Tests/ScenePresenceCrossingTests.cs +++ b/OpenSim/Region/Framework/Scenes/Tests/ScenePresenceCrossingTests.cs @@ -95,11 +95,11 @@ namespace OpenSim.Region.Framework.Scenes.Tests SceneHelpers.SetupSceneModules(sceneB, config, new CapabilitiesModule(), etmB); AgentCircuitData acd = SceneHelpers.GenerateAgentData(userId); - TestClient tc = new TestClient(acd, sceneA, sh.SceneManager); + TestClient tc = new TestClient(acd, sceneA); List destinationTestClients = new List(); EntityTransferHelpers.SetUpInformClientOfNeighbour(tc, destinationTestClients); - ScenePresence originalSp = SceneHelpers.AddScenePresence(sceneA, tc, acd, sh.SceneManager); + ScenePresence originalSp = SceneHelpers.AddScenePresence(sceneA, tc, acd); originalSp.AbsolutePosition = new Vector3(128, 32, 10); // originalSp.Flying = true; diff --git a/OpenSim/Region/Framework/Scenes/Tests/ScenePresenceTeleportTests.cs b/OpenSim/Region/Framework/Scenes/Tests/ScenePresenceTeleportTests.cs index de4458dde3..297c66b023 100644 --- a/OpenSim/Region/Framework/Scenes/Tests/ScenePresenceTeleportTests.cs +++ b/OpenSim/Region/Framework/Scenes/Tests/ScenePresenceTeleportTests.cs @@ -139,7 +139,7 @@ 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, sh.SceneManager); + ScenePresence sp = SceneHelpers.AddScenePresence(sceneA, userId); sp.AbsolutePosition = new Vector3(30, 31, 32); List destinationTestClients = new List(); @@ -224,7 +224,7 @@ 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, sh.SceneManager); + ScenePresence sp = SceneHelpers.AddScenePresence(sceneA, userId); sp.AbsolutePosition = preTeleportPosition; // Make sceneB return false on query access @@ -300,7 +300,7 @@ 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, sh.SceneManager); + ScenePresence sp = SceneHelpers.AddScenePresence(sceneA, userId); sp.AbsolutePosition = preTeleportPosition; // Make sceneB refuse CreateAgent @@ -389,7 +389,7 @@ 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, sh.SceneManager); + ScenePresence sp = SceneHelpers.AddScenePresence(sceneA, userId); sp.AbsolutePosition = preTeleportPosition; sceneA.RequestTeleportLocation( @@ -428,7 +428,7 @@ namespace OpenSim.Region.Framework.Scenes.Tests public void TestSameSimulatorNeighbouringRegions() { TestHelpers.InMethod(); - TestHelpers.EnableLogging(); +// TestHelpers.EnableLogging(); UUID userId = TestHelpers.ParseTail(0x1); @@ -458,11 +458,11 @@ namespace OpenSim.Region.Framework.Scenes.Tests Vector3 teleportLookAt = new Vector3(20, 21, 22); AgentCircuitData acd = SceneHelpers.GenerateAgentData(userId); - TestClient tc = new TestClient(acd, sceneA, sh.SceneManager); + TestClient tc = new TestClient(acd, sceneA); List destinationTestClients = new List(); EntityTransferHelpers.SetUpInformClientOfNeighbour(tc, destinationTestClients); - ScenePresence beforeSceneASp = SceneHelpers.AddScenePresence(sceneA, tc, acd, sh.SceneManager); + ScenePresence beforeSceneASp = SceneHelpers.AddScenePresence(sceneA, tc, acd); beforeSceneASp.AbsolutePosition = new Vector3(30, 31, 32); Assert.That(beforeSceneASp, Is.Not.Null); diff --git a/OpenSim/Tests/Common/Helpers/EntityTransferHelpers.cs b/OpenSim/Tests/Common/Helpers/EntityTransferHelpers.cs index 6cc7ff259d..1b960b1f5d 100644 --- a/OpenSim/Tests/Common/Helpers/EntityTransferHelpers.cs +++ b/OpenSim/Tests/Common/Helpers/EntityTransferHelpers.cs @@ -82,7 +82,7 @@ namespace OpenSim.Tests.Common Scene neighbourScene; SceneManager.Instance.TryGetScene(x, y, out neighbourScene); - TestClient neighbourTc = new TestClient(newAgent, neighbourScene, SceneManager.Instance); + TestClient neighbourTc = new TestClient(newAgent, neighbourScene); neighbourTcs.Add(neighbourTc); neighbourScene.AddNewClient(neighbourTc, PresenceType.User); }; diff --git a/OpenSim/Tests/Common/Helpers/SceneHelpers.cs b/OpenSim/Tests/Common/Helpers/SceneHelpers.cs index bdd90939e7..d9bb85e006 100644 --- a/OpenSim/Tests/Common/Helpers/SceneHelpers.cs +++ b/OpenSim/Tests/Common/Helpers/SceneHelpers.cs @@ -447,9 +447,6 @@ 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. - /// /// XXX: Use the version of this method that takes the UserAccount structure wherever possible - this will /// make the agent circuit data (e.g. first, lastname) consistent with the user account data. /// @@ -461,22 +458,6 @@ 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 - /// - /// - /// XXX: Use the version of this method that takes the UserAccount structure wherever possible - this will - /// make the agent circuit data (e.g. first, lastname) consistent with the user account data. - /// - /// - /// - /// - /// - public static ScenePresence AddScenePresence(Scene scene, UUID agentId, SceneManager sceneManager) - { - return AddScenePresence(scene, GenerateAgentData(agentId), sceneManager); - } - /// /// Add a root agent. /// @@ -508,7 +489,7 @@ namespace OpenSim.Tests.Common /// public static ScenePresence AddScenePresence(Scene scene, AgentCircuitData agentData) { - return AddScenePresence(scene, agentData, null); + return AddScenePresence(scene, new TestClient(agentData, scene), agentData); } /// @@ -528,34 +509,9 @@ namespace OpenSim.Tests.Common /// /// /// - /// - /// - public static ScenePresence AddScenePresence(Scene scene, AgentCircuitData agentData, SceneManager sceneManager) - { - return AddScenePresence(scene, new TestClient(agentData, scene, sceneManager), agentData, sceneManager); - } - - /// - /// 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, IClientAPI client, AgentCircuitData agentData, SceneManager sceneManager) + Scene scene, IClientAPI client, AgentCircuitData agentData) { // We emulate the proper login sequence here by doing things in four stages @@ -578,10 +534,6 @@ namespace OpenSim.Tests.Common /// 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. - /// /// /// /// @@ -607,7 +559,7 @@ namespace OpenSim.Tests.Common acd.child = true; // XXX: ViaLogin may not be correct for child agents - TestClient client = new TestClient(acd, scene, null); + TestClient client = new TestClient(acd, scene); return IntroduceClientToScene(scene, client, acd, TeleportFlags.ViaLogin); } diff --git a/OpenSim/Tests/Common/Mock/TestClient.cs b/OpenSim/Tests/Common/Mock/TestClient.cs index 664ecb6059..3f9690f805 100644 --- a/OpenSim/Tests/Common/Mock/TestClient.cs +++ b/OpenSim/Tests/Common/Mock/TestClient.cs @@ -47,9 +47,9 @@ namespace OpenSim.Tests.Common.Mock EventWaitHandle wh = new EventWaitHandle (false, EventResetMode.AutoReset, "Crossing"); private Scene m_scene; - private SceneManager m_sceneManager; // Properties so that we can get at received data for test purposes + public List ReceivedKills { get; private set; } public List ReceivedOfflineNotifications { get; private set; } public List ReceivedOnlineNotifications { get; private set; } public List ReceivedFriendshipTerminations { get; private set; } @@ -431,36 +431,24 @@ namespace OpenSim.Tests.Common.Mock get { return new IPEndPoint(IPAddress.Loopback, (ushort)m_circuitCode); } } - /// - /// 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) : this(agentData, scene, null) {} - /// /// Constructor /// /// /// /// - public TestClient(AgentCircuitData agentData, Scene scene, SceneManager sceneManager) + public TestClient(AgentCircuitData agentData, Scene scene) { 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; + ReceivedKills = new List(); ReceivedOfflineNotifications = new List(); ReceivedOnlineNotifications = new List(); ReceivedFriendshipTerminations = new List(); @@ -534,11 +522,13 @@ namespace OpenSim.Tests.Common.Mock public virtual void SendKillObject(ulong regionHandle, List localID) { + ReceivedKills.AddRange(localID); } public virtual void SetChildAgentThrottle(byte[] throttle) { } + public byte[] GetThrottlesPacked(float multiplier) { return new byte[0];