aboutsummaryrefslogtreecommitdiffstatshomepage
path: root/OpenSim/Tests
diff options
context:
space:
mode:
authorJustin Clark-Casey (justincc)2010-09-07 00:34:06 +0100
committerJustin Clark-Casey (justincc)2010-09-07 01:12:06 +0100
commit11f4a65f42dea66091cb08423479fa6ae46c98aa (patch)
treef16956aa3d2cac3ae325ffda621f2bd79b40310e /OpenSim/Tests
parentAdd test that checks correct persistence when an unlink is quickly followed b... (diff)
downloadopensim-SC-11f4a65f42dea66091cb08423479fa6ae46c98aa.zip
opensim-SC-11f4a65f42dea66091cb08423479fa6ae46c98aa.tar.gz
opensim-SC-11f4a65f42dea66091cb08423479fa6ae46c98aa.tar.bz2
opensim-SC-11f4a65f42dea66091cb08423479fa6ae46c98aa.tar.xz
Fix deletion persistence when freshly delinked prims are removed
Previously, Scene.Inventory.DeRezObjects() forced the persistence of prims before deletion. This is necessary so that freshly delinked prims can be deleted (otherwise they remain as parts of their old group and reappear on server restart). However, DeRezObjects() deleted to user inventory, which is required by llDie() or direct region module unlink and deletion. Therefore, forced persistence has been pushed down into Scene.UnlinkSceneObject() to be more general, this is still on the DeRezObjects() path. Uncommented TestDelinkPersistence() since this now passes. Tests required considerable elaboration of MockRegionDataPlugin to reflect underlying storing of parts.
Diffstat (limited to 'OpenSim/Tests')
-rw-r--r--OpenSim/Tests/Common/Mock/MockRegionDataPlugin.cs80
-rw-r--r--OpenSim/Tests/Common/Mock/TestInventoryDataPlugin.cs2
-rw-r--r--OpenSim/Tests/Common/Setup/UserInventoryTestUtils.cs2
3 files changed, 69 insertions, 15 deletions
diff --git a/OpenSim/Tests/Common/Mock/MockRegionDataPlugin.cs b/OpenSim/Tests/Common/Mock/MockRegionDataPlugin.cs
index 1c139c5..2a055cc 100644
--- a/OpenSim/Tests/Common/Mock/MockRegionDataPlugin.cs
+++ b/OpenSim/Tests/Common/Mock/MockRegionDataPlugin.cs
@@ -44,7 +44,7 @@ namespace OpenSim.Data.Null
44 private static readonly ILog m_log = LogManager.GetLogger(MethodBase.GetCurrentMethod().DeclaringType); 44 private static readonly ILog m_log = LogManager.GetLogger(MethodBase.GetCurrentMethod().DeclaringType);
45 45
46 protected Dictionary<UUID, RegionSettings> m_regionSettings = new Dictionary<UUID, RegionSettings>(); 46 protected Dictionary<UUID, RegionSettings> m_regionSettings = new Dictionary<UUID, RegionSettings>();
47 protected Dictionary<UUID, SceneObjectGroup> m_sceneObjects = new Dictionary<UUID, SceneObjectGroup>(); 47 protected Dictionary<UUID, SceneObjectPart> m_sceneObjectParts = new Dictionary<UUID, SceneObjectPart>();
48 protected Dictionary<UUID, ICollection<TaskInventoryItem>> m_primItems 48 protected Dictionary<UUID, ICollection<TaskInventoryItem>> m_primItems
49 = new Dictionary<UUID, ICollection<TaskInventoryItem>>(); 49 = new Dictionary<UUID, ICollection<TaskInventoryItem>>();
50 protected Dictionary<UUID, double[,]> m_terrains = new Dictionary<UUID, double[,]>(); 50 protected Dictionary<UUID, double[,]> m_terrains = new Dictionary<UUID, double[,]>();
@@ -85,18 +85,33 @@ namespace OpenSim.Data.Null
85 85
86 public void StoreObject(SceneObjectGroup obj, UUID regionUUID) 86 public void StoreObject(SceneObjectGroup obj, UUID regionUUID)
87 { 87 {
88 m_log.DebugFormat( 88 // We can't simply store groups here because on delinking, OpenSim will not update the original group
89 "[MOCK REGION DATA PLUGIN]: Storing object {0} {1} in {2}", obj.Name, obj.UUID, regionUUID); 89 // directly. Rather, the newly delinked parts will be updated to be in their own scene object group
90 m_sceneObjects[obj.UUID] = obj; 90 // Therefore, we need to store parts rather than groups.
91 foreach (SceneObjectPart prim in obj.Children.Values)
92 {
93 m_log.DebugFormat(
94 "[MOCK REGION DATA PLUGIN]: Storing part {0} {1} in object {2} {3} in region {4}",
95 prim.Name, prim.UUID, obj.Name, obj.UUID, regionUUID);
96
97 m_sceneObjectParts[prim.UUID] = prim;
98 }
91 } 99 }
92 100
93 public void RemoveObject(UUID obj, UUID regionUUID) 101 public void RemoveObject(UUID obj, UUID regionUUID)
94 { 102 {
95 m_log.DebugFormat( 103 // All parts belonging to the object with the uuid are removed.
96 "[MOCK REGION DATA PLUGIN]: Removing object {0} from {1}", obj, regionUUID); 104 List<SceneObjectPart> parts = new List<SceneObjectPart>(m_sceneObjectParts.Values);
97 105 foreach (SceneObjectPart part in parts)
98 if (m_sceneObjects.ContainsKey(obj)) 106 {
99 m_sceneObjects.Remove(obj); 107 if (part.ParentGroup.UUID == obj)
108 {
109 m_log.DebugFormat(
110 "[MOCK REGION DATA PLUGIN]: Removing part {0} {1} as part of object {2} from {3}",
111 part.Name, part.UUID, obj, regionUUID);
112 m_sceneObjectParts.Remove(part.UUID);
113 }
114 }
100 } 115 }
101 116
102 // see IRegionDatastore 117 // see IRegionDatastore
@@ -107,10 +122,49 @@ namespace OpenSim.Data.Null
107 122
108 public List<SceneObjectGroup> LoadObjects(UUID regionUUID) 123 public List<SceneObjectGroup> LoadObjects(UUID regionUUID)
109 { 124 {
110 m_log.DebugFormat( 125 Dictionary<UUID, SceneObjectGroup> objects = new Dictionary<UUID, SceneObjectGroup>();
111 "[MOCK REGION DATA PLUGIN]: Loading objects from {0}", regionUUID); 126
127 // Create all of the SOGs from the root prims first
128 foreach (SceneObjectPart prim in m_sceneObjectParts.Values)
129 {
130 if (prim.IsRoot)
131 {
132 m_log.DebugFormat(
133 "[MOCK REGION DATA PLUGIN]: Loading root part {0} {1} in {2}", prim.Name, prim.UUID, regionUUID);
134 objects[prim.UUID] = new SceneObjectGroup(prim);
135 }
136 }
137
138 // Add all of the children objects to the SOGs
139 foreach (SceneObjectPart prim in m_sceneObjectParts.Values)
140 {
141 SceneObjectGroup sog;
142 if (prim.UUID != prim.ParentUUID)
143 {
144 if (objects.TryGetValue(prim.ParentUUID, out sog))
145 {
146 int originalLinkNum = prim.LinkNum;
147
148 sog.AddPart(prim);
149
150 // SceneObjectGroup.AddPart() tries to be smart and automatically set the LinkNum.
151 // We override that here
152 if (originalLinkNum != 0)
153 prim.LinkNum = originalLinkNum;
154 }
155 else
156 {
157 m_log.WarnFormat(
158 "[MOCK REGION DATA PLUGIN]: Database contains an orphan child prim {0} {1} in region {2} pointing to missing parent {3}. This prim will not be loaded.",
159 prim.Name, prim.UUID, regionUUID, prim.ParentUUID);
160 }
161 }
162 }
163
164 // TODO: Load items. This is assymetric - we store items as a separate method but don't retrieve them that
165 // way!
112 166
113 return new List<SceneObjectGroup>(m_sceneObjects.Values); 167 return new List<SceneObjectGroup>(objects.Values);
114 } 168 }
115 169
116 public void StoreTerrain(double[,] ter, UUID regionID) 170 public void StoreTerrain(double[,] ter, UUID regionID)
diff --git a/OpenSim/Tests/Common/Mock/TestInventoryDataPlugin.cs b/OpenSim/Tests/Common/Mock/TestInventoryDataPlugin.cs
index b70b47d..b47ad5d 100644
--- a/OpenSim/Tests/Common/Mock/TestInventoryDataPlugin.cs
+++ b/OpenSim/Tests/Common/Mock/TestInventoryDataPlugin.cs
@@ -42,7 +42,7 @@ namespace OpenSim.Tests.Common.Mock
42 /// </summary> 42 /// </summary>
43 public class TestInventoryDataPlugin : IInventoryDataPlugin 43 public class TestInventoryDataPlugin : IInventoryDataPlugin
44 { 44 {
45 private static readonly ILog m_log = LogManager.GetLogger(MethodBase.GetCurrentMethod().DeclaringType); 45// private static readonly ILog m_log = LogManager.GetLogger(MethodBase.GetCurrentMethod().DeclaringType);
46 46
47 /// <value> 47 /// <value>
48 /// Inventory folders 48 /// Inventory folders
diff --git a/OpenSim/Tests/Common/Setup/UserInventoryTestUtils.cs b/OpenSim/Tests/Common/Setup/UserInventoryTestUtils.cs
index c57363a..915af7e 100644
--- a/OpenSim/Tests/Common/Setup/UserInventoryTestUtils.cs
+++ b/OpenSim/Tests/Common/Setup/UserInventoryTestUtils.cs
@@ -52,7 +52,7 @@ namespace OpenSim.Tests.Common
52 InventoryFolderBase objsFolder = scene.InventoryService.GetFolderForType(userId, AssetType.Object); 52 InventoryFolderBase objsFolder = scene.InventoryService.GetFolderForType(userId, AssetType.Object);
53 53
54 item.Folder = objsFolder.ID; 54 item.Folder = objsFolder.ID;
55 scene.AddInventoryItem(userId, item); 55 scene.AddInventoryItem(item);
56 56
57 return item; 57 return item;
58 } 58 }