clockwerk-opensim – Blame information for rev 1

Subversion Repositories:
Rev:
Rev Author Line No. Line
1 vero 1 /*
2 * Copyright (c) Contributors, http://opensimulator.org/
3 * See CONTRIBUTORS.TXT for a full list of copyright holders.
4 *
5 * Redistribution and use in source and binary forms, with or without
6 * modification, are permitted provided that the following conditions are met:
7 * * Redistributions of source code must retain the above copyright
8 * notice, this list of conditions and the following disclaimer.
9 * * Redistributions in binary form must reproduce the above copyright
10 * notice, this list of conditions and the following disclaimer in the
11 * documentation and/or other materials provided with the distribution.
12 * * Neither the name of the OpenSimulator Project nor the
13 * names of its contributors may be used to endorse or promote products
14 * derived from this software without specific prior written permission.
15 *
16 * THIS SOFTWARE IS PROVIDED BY THE DEVELOPERS ``AS IS'' AND ANY
17 * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
18 * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
19 * DISCLAIMED. IN NO EVENT SHALL THE CONTRIBUTORS BE LIABLE FOR ANY
20 * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
21 * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
22 * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
23 * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
24 * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
25 * SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
26 */
27  
28 using System;
29 using System.Collections.Generic;
30 using System.Reflection;
31 using System.Text;
32 using System.Threading;
33 using System.Timers;
34 using System.Xml;
35 using Timer=System.Timers.Timer;
36 using Nini.Config;
37 using NUnit.Framework;
38 using OpenMetaverse;
39 using OpenSim.Framework;
40 using OpenSim.Framework.Communications;
41 using OpenSim.Framework.Servers;
42 using OpenSim.Framework.Servers.HttpServer;
43 using OpenSim.Region.CoreModules.Avatar.Attachments;
44 using OpenSim.Region.CoreModules.Framework;
45 using OpenSim.Region.CoreModules.Framework.EntityTransfer;
46 using OpenSim.Region.CoreModules.Framework.InventoryAccess;
47 using OpenSim.Region.CoreModules.Scripting.WorldComm;
48 using OpenSim.Region.CoreModules.ServiceConnectorsOut.Simulation;
49 using OpenSim.Region.CoreModules.World.Serialiser;
50 using OpenSim.Region.Framework.Scenes;
51 using OpenSim.Region.Framework.Interfaces;
52 using OpenSim.Region.ScriptEngine.Interfaces;
53 using OpenSim.Region.ScriptEngine.XEngine;
54 using OpenSim.Services.Interfaces;
55 using OpenSim.Tests.Common;
56 using OpenSim.Tests.Common.Mock;
57  
58 namespace OpenSim.Region.CoreModules.Avatar.Attachments.Tests
59 {
60 /// <summary>
61 /// Attachment tests
62 /// </summary>
63 [TestFixture]
64 public class AttachmentsModuleTests : OpenSimTestCase
65 {
66 private AutoResetEvent m_chatEvent = new AutoResetEvent(false);
67 // private OSChatMessage m_osChatMessageReceived;
68  
69 // Used to test whether the operations have fired the attach event. Must be reset after each test.
70 private int m_numberOfAttachEventsFired;
71  
72 [TestFixtureSetUp]
73 public void FixtureInit()
74 {
75 // Don't allow tests to be bamboozled by asynchronous events. Execute everything on the same thread.
76 Util.FireAndForgetMethod = FireAndForgetMethod.None;
77 }
78  
79 [TestFixtureTearDown]
80 public void TearDown()
81 {
82 // We must set this back afterwards, otherwise later tests will fail since they're expecting multiple
83 // threads. Possibly, later tests should be rewritten not to worry about such things.
84 Util.FireAndForgetMethod = Util.DefaultFireAndForgetMethod;
85 }
86  
87 private void OnChatFromWorld(object sender, OSChatMessage oscm)
88 {
89 // Console.WriteLine("Got chat [{0}]", oscm.Message);
90  
91 // m_osChatMessageReceived = oscm;
92 m_chatEvent.Set();
93 }
94  
95 private Scene CreateTestScene()
96 {
97 IConfigSource config = new IniConfigSource();
98 List<object> modules = new List<object>();
99  
100 AddCommonConfig(config, modules);
101  
102 Scene scene
103 = new SceneHelpers().SetupScene(
104 "attachments-test-scene", TestHelpers.ParseTail(999), 1000, 1000, config);
105 SceneHelpers.SetupSceneModules(scene, config, modules.ToArray());
106  
107 scene.EventManager.OnAttach += (localID, itemID, avatarID) => m_numberOfAttachEventsFired++;
108  
109 return scene;
110 }
111  
112 private Scene CreateScriptingEnabledTestScene()
113 {
114 IConfigSource config = new IniConfigSource();
115 List<object> modules = new List<object>();
116  
117 AddCommonConfig(config, modules);
118 AddScriptingConfig(config, modules);
119  
120 Scene scene
121 = new SceneHelpers().SetupScene(
122 "attachments-test-scene", TestHelpers.ParseTail(999), 1000, 1000, config);
123 SceneHelpers.SetupSceneModules(scene, config, modules.ToArray());
124  
125 scene.StartScripts();
126  
127 return scene;
128 }
129  
130 private void AddCommonConfig(IConfigSource config, List<object> modules)
131 {
132 config.AddConfig("Modules");
133 config.Configs["Modules"].Set("InventoryAccessModule", "BasicInventoryAccessModule");
134  
135 AttachmentsModule attMod = new AttachmentsModule();
136 attMod.DebugLevel = 1;
137 modules.Add(attMod);
138 modules.Add(new BasicInventoryAccessModule());
139 }
140  
141 private void AddScriptingConfig(IConfigSource config, List<object> modules)
142 {
143 IConfig startupConfig = config.AddConfig("Startup");
144 startupConfig.Set("DefaultScriptEngine", "XEngine");
145  
146 IConfig xEngineConfig = config.AddConfig("XEngine");
147 xEngineConfig.Set("Enabled", "true");
148 xEngineConfig.Set("StartDelay", "0");
149  
150 // These tests will not run with AppDomainLoading = true, at least on mono. For unknown reasons, the call
151 // to AssemblyResolver.OnAssemblyResolve fails.
152 xEngineConfig.Set("AppDomainLoading", "false");
153  
154 modules.Add(new XEngine());
155  
156 // Necessary to stop serialization complaining
157 // FIXME: Stop this being necessary if at all possible
158 // modules.Add(new WorldCommModule());
159 }
160  
161 /// <summary>
162 /// Creates an attachment item in the given user's inventory. Does not attach.
163 /// </summary>
164 /// <remarks>
165 /// A user with the given ID and an inventory must already exist.
166 /// </remarks>
167 /// <returns>
168 /// The attachment item.
169 /// </returns>
170 /// <param name='scene'></param>
171 /// <param name='userId'></param>
172 /// <param name='attName'></param>
173 /// <param name='rawItemId'></param>
174 /// <param name='rawAssetId'></param>
175 private InventoryItemBase CreateAttachmentItem(
176 Scene scene, UUID userId, string attName, int rawItemId, int rawAssetId)
177 {
178 return UserInventoryHelpers.CreateInventoryItem(
179 scene,
180 attName,
181 TestHelpers.ParseTail(rawItemId),
182 TestHelpers.ParseTail(rawAssetId),
183 userId,
184 InventoryType.Object);
185 }
186  
187 [Test]
188 public void TestAddAttachmentFromGround()
189 {
190 TestHelpers.InMethod();
191 // TestHelpers.EnableLogging();
192  
193 m_numberOfAttachEventsFired = 0;
194  
195 Scene scene = CreateTestScene();
196 UserAccount ua1 = UserAccountHelpers.CreateUserWithInventory(scene, 0x1);
197 ScenePresence sp = SceneHelpers.AddScenePresence(scene, ua1);
198  
199 string attName = "att";
200  
201 SceneObjectGroup so = SceneHelpers.AddSceneObject(scene, attName, sp.UUID);
202  
203 m_numberOfAttachEventsFired = 0;
204 scene.AttachmentsModule.AttachObject(sp, so, (uint)AttachmentPoint.Chest, false, true, false);
205  
206 // Check status on scene presence
207 Assert.That(sp.HasAttachments(), Is.True);
208 List<SceneObjectGroup> attachments = sp.GetAttachments();
209 Assert.That(attachments.Count, Is.EqualTo(1));
210 SceneObjectGroup attSo = attachments[0];
211 Assert.That(attSo.Name, Is.EqualTo(attName));
212 Assert.That(attSo.AttachmentPoint, Is.EqualTo((byte)AttachmentPoint.Chest));
213 Assert.That(attSo.IsAttachment);
214 Assert.That(attSo.UsesPhysics, Is.False);
215 Assert.That(attSo.IsTemporary, Is.False);
216  
217 // Check item status
218 Assert.That(
219 sp.Appearance.GetAttachpoint(attSo.FromItemID),
220 Is.EqualTo((int)AttachmentPoint.Chest));
221  
222 InventoryItemBase attachmentItem = scene.InventoryService.GetItem(new InventoryItemBase(attSo.FromItemID));
223 Assert.That(attachmentItem, Is.Not.Null);
224 Assert.That(attachmentItem.Name, Is.EqualTo(attName));
225  
226 InventoryFolderBase targetFolder = scene.InventoryService.GetFolderForType(sp.UUID, AssetType.Object);
227 Assert.That(attachmentItem.Folder, Is.EqualTo(targetFolder.ID));
228  
229 Assert.That(scene.GetSceneObjectGroups().Count, Is.EqualTo(1));
230  
231 // Check events
232 Assert.That(m_numberOfAttachEventsFired, Is.EqualTo(1));
233 }
234  
235 [Test]
236 public void TestWearAttachmentFromGround()
237 {
238 TestHelpers.InMethod();
239 // TestHelpers.EnableLogging();
240  
241 Scene scene = CreateTestScene();
242 UserAccount ua1 = UserAccountHelpers.CreateUserWithInventory(scene, 0x1);
243 ScenePresence sp = SceneHelpers.AddScenePresence(scene, ua1);
244  
245 SceneObjectGroup so2 = SceneHelpers.AddSceneObject(scene, "att2", sp.UUID);
246  
247 {
248 SceneObjectGroup so = SceneHelpers.AddSceneObject(scene, "att1", sp.UUID);
249  
250 m_numberOfAttachEventsFired = 0;
251 scene.AttachmentsModule.AttachObject(sp, so, (uint)AttachmentPoint.Default, false, true, false);
252  
253 // Check status on scene presence
254 Assert.That(sp.HasAttachments(), Is.True);
255 List<SceneObjectGroup> attachments = sp.GetAttachments();
256 Assert.That(attachments.Count, Is.EqualTo(1));
257 SceneObjectGroup attSo = attachments[0];
258 Assert.That(attSo.Name, Is.EqualTo(so.Name));
259 Assert.That(attSo.AttachmentPoint, Is.EqualTo((byte)AttachmentPoint.LeftHand));
260 Assert.That(attSo.IsAttachment);
261 Assert.That(attSo.UsesPhysics, Is.False);
262 Assert.That(attSo.IsTemporary, Is.False);
263  
264 // Check item status
265 Assert.That(
266 sp.Appearance.GetAttachpoint(attSo.FromItemID),
267 Is.EqualTo((int)AttachmentPoint.LeftHand));
268  
269 InventoryItemBase attachmentItem = scene.InventoryService.GetItem(new InventoryItemBase(attSo.FromItemID));
270 Assert.That(attachmentItem, Is.Not.Null);
271 Assert.That(attachmentItem.Name, Is.EqualTo(so.Name));
272  
273 InventoryFolderBase targetFolder = scene.InventoryService.GetFolderForType(sp.UUID, AssetType.Object);
274 Assert.That(attachmentItem.Folder, Is.EqualTo(targetFolder.ID));
275  
276 Assert.That(scene.GetSceneObjectGroups().Count, Is.EqualTo(2));
277  
278 // Check events
279 Assert.That(m_numberOfAttachEventsFired, Is.EqualTo(1));
280 }
281  
282 // Test wearing a different attachment from the ground.
283 {
284 scene.AttachmentsModule.AttachObject(sp, so2, (uint)AttachmentPoint.Default, false, true, false);
285  
286 // Check status on scene presence
287 Assert.That(sp.HasAttachments(), Is.True);
288 List<SceneObjectGroup> attachments = sp.GetAttachments();
289 Assert.That(attachments.Count, Is.EqualTo(1));
290 SceneObjectGroup attSo = attachments[0];
291 Assert.That(attSo.Name, Is.EqualTo(so2.Name));
292 Assert.That(attSo.AttachmentPoint, Is.EqualTo((byte)AttachmentPoint.LeftHand));
293 Assert.That(attSo.IsAttachment);
294 Assert.That(attSo.UsesPhysics, Is.False);
295 Assert.That(attSo.IsTemporary, Is.False);
296  
297 // Check item status
298 Assert.That(
299 sp.Appearance.GetAttachpoint(attSo.FromItemID),
300 Is.EqualTo((int)AttachmentPoint.LeftHand));
301  
302 InventoryItemBase attachmentItem = scene.InventoryService.GetItem(new InventoryItemBase(attSo.FromItemID));
303 Assert.That(attachmentItem, Is.Not.Null);
304 Assert.That(attachmentItem.Name, Is.EqualTo(so2.Name));
305  
306 InventoryFolderBase targetFolder = scene.InventoryService.GetFolderForType(sp.UUID, AssetType.Object);
307 Assert.That(attachmentItem.Folder, Is.EqualTo(targetFolder.ID));
308  
309 Assert.That(scene.GetSceneObjectGroups().Count, Is.EqualTo(1));
310  
311 // Check events
312 Assert.That(m_numberOfAttachEventsFired, Is.EqualTo(3));
313 }
314  
315 // Test rewearing an already worn attachment from ground. Nothing should happen.
316 {
317 scene.AttachmentsModule.AttachObject(sp, so2, (uint)AttachmentPoint.Default, false, true, false);
318  
319 // Check status on scene presence
320 Assert.That(sp.HasAttachments(), Is.True);
321 List<SceneObjectGroup> attachments = sp.GetAttachments();
322 Assert.That(attachments.Count, Is.EqualTo(1));
323 SceneObjectGroup attSo = attachments[0];
324 Assert.That(attSo.Name, Is.EqualTo(so2.Name));
325 Assert.That(attSo.AttachmentPoint, Is.EqualTo((byte)AttachmentPoint.LeftHand));
326 Assert.That(attSo.IsAttachment);
327 Assert.That(attSo.UsesPhysics, Is.False);
328 Assert.That(attSo.IsTemporary, Is.False);
329  
330 // Check item status
331 Assert.That(
332 sp.Appearance.GetAttachpoint(attSo.FromItemID),
333 Is.EqualTo((int)AttachmentPoint.LeftHand));
334  
335 InventoryItemBase attachmentItem = scene.InventoryService.GetItem(new InventoryItemBase(attSo.FromItemID));
336 Assert.That(attachmentItem, Is.Not.Null);
337 Assert.That(attachmentItem.Name, Is.EqualTo(so2.Name));
338  
339 InventoryFolderBase targetFolder = scene.InventoryService.GetFolderForType(sp.UUID, AssetType.Object);
340 Assert.That(attachmentItem.Folder, Is.EqualTo(targetFolder.ID));
341  
342 Assert.That(scene.GetSceneObjectGroups().Count, Is.EqualTo(1));
343  
344 // Check events
345 Assert.That(m_numberOfAttachEventsFired, Is.EqualTo(3));
346 }
347 }
348  
349 /// <summary>
350 /// Test that we do not attempt to attach an in-world object that someone else is sitting on.
351 /// </summary>
352 [Test]
353 public void TestAddSatOnAttachmentFromGround()
354 {
355 TestHelpers.InMethod();
356 // TestHelpers.EnableLogging();
357  
358 m_numberOfAttachEventsFired = 0;
359  
360 Scene scene = CreateTestScene();
361 UserAccount ua1 = UserAccountHelpers.CreateUserWithInventory(scene, 0x1);
362 ScenePresence sp = SceneHelpers.AddScenePresence(scene, ua1);
363  
364 string attName = "att";
365  
366 SceneObjectGroup so = SceneHelpers.AddSceneObject(scene, attName, sp.UUID);
367  
368 UserAccount ua2 = UserAccountHelpers.CreateUserWithInventory(scene, 0x2);
369 ScenePresence sp2 = SceneHelpers.AddScenePresence(scene, ua2);
370  
371 // Put avatar within 10m of the prim so that sit doesn't fail.
372 sp2.AbsolutePosition = new Vector3(0, 0, 0);
373 sp2.HandleAgentRequestSit(sp2.ControllingClient, sp2.UUID, so.UUID, Vector3.Zero);
374  
375 scene.AttachmentsModule.AttachObject(sp, so, (uint)AttachmentPoint.Chest, false, true, false);
376  
377 Assert.That(sp.HasAttachments(), Is.False);
378 Assert.That(scene.GetSceneObjectGroups().Count, Is.EqualTo(1));
379  
380 // Check events
381 Assert.That(m_numberOfAttachEventsFired, Is.EqualTo(0));
382 }
383  
384 [Test]
385 public void TestRezAttachmentFromInventory()
386 {
387 TestHelpers.InMethod();
388 // log4net.Config.XmlConfigurator.Configure();
389  
390 Scene scene = CreateTestScene();
391 UserAccount ua1 = UserAccountHelpers.CreateUserWithInventory(scene, 0x1);
392 ScenePresence sp = SceneHelpers.AddScenePresence(scene, ua1.PrincipalID);
393  
394 InventoryItemBase attItem = CreateAttachmentItem(scene, ua1.PrincipalID, "att", 0x10, 0x20);
395  
396 {
397 scene.AttachmentsModule.RezSingleAttachmentFromInventory(
398 sp, attItem.ID, (uint)AttachmentPoint.Chest);
399  
400 // Check scene presence status
401 Assert.That(sp.HasAttachments(), Is.True);
402 List<SceneObjectGroup> attachments = sp.GetAttachments();
403 Assert.That(attachments.Count, Is.EqualTo(1));
404 SceneObjectGroup attSo = attachments[0];
405 Assert.That(attSo.Name, Is.EqualTo(attItem.Name));
406 Assert.That(attSo.AttachmentPoint, Is.EqualTo((byte)AttachmentPoint.Chest));
407 Assert.That(attSo.IsAttachment);
408 Assert.That(attSo.UsesPhysics, Is.False);
409 Assert.That(attSo.IsTemporary, Is.False);
410  
411 // Check appearance status
412 Assert.That(sp.Appearance.GetAttachments().Count, Is.EqualTo(1));
413 Assert.That(sp.Appearance.GetAttachpoint(attItem.ID), Is.EqualTo((int)AttachmentPoint.Chest));
414 Assert.That(scene.GetSceneObjectGroups().Count, Is.EqualTo(1));
415  
416 // Check events
417 Assert.That(m_numberOfAttachEventsFired, Is.EqualTo(1));
418 }
419  
420 // Test attaching an already attached attachment
421 {
422 scene.AttachmentsModule.RezSingleAttachmentFromInventory(
423 sp, attItem.ID, (uint)AttachmentPoint.Chest);
424  
425 // Check scene presence status
426 Assert.That(sp.HasAttachments(), Is.True);
427 List<SceneObjectGroup> attachments = sp.GetAttachments();
428 Assert.That(attachments.Count, Is.EqualTo(1));
429 SceneObjectGroup attSo = attachments[0];
430 Assert.That(attSo.Name, Is.EqualTo(attItem.Name));
431 Assert.That(attSo.AttachmentPoint, Is.EqualTo((byte)AttachmentPoint.Chest));
432 Assert.That(attSo.IsAttachment);
433 Assert.That(attSo.UsesPhysics, Is.False);
434 Assert.That(attSo.IsTemporary, Is.False);
435  
436 // Check appearance status
437 Assert.That(sp.Appearance.GetAttachments().Count, Is.EqualTo(1));
438 Assert.That(sp.Appearance.GetAttachpoint(attItem.ID), Is.EqualTo((int)AttachmentPoint.Chest));
439 Assert.That(scene.GetSceneObjectGroups().Count, Is.EqualTo(1));
440  
441 // Check events
442 Assert.That(m_numberOfAttachEventsFired, Is.EqualTo(1));
443 }
444 }
445  
446 /// <summary>
447 /// Test wearing an attachment from inventory, as opposed to explicit choosing the rez point
448 /// </summary>
449 [Test]
450 public void TestWearAttachmentFromInventory()
451 {
452 TestHelpers.InMethod();
453 // TestHelpers.EnableLogging();
454  
455 Scene scene = CreateTestScene();
456 UserAccount ua1 = UserAccountHelpers.CreateUserWithInventory(scene, 0x1);
457 ScenePresence sp = SceneHelpers.AddScenePresence(scene, ua1.PrincipalID);
458  
459 InventoryItemBase attItem1 = CreateAttachmentItem(scene, ua1.PrincipalID, "att1", 0x10, 0x20);
460 InventoryItemBase attItem2 = CreateAttachmentItem(scene, ua1.PrincipalID, "att2", 0x11, 0x21);
461  
462 {
463 m_numberOfAttachEventsFired = 0;
464 scene.AttachmentsModule.RezSingleAttachmentFromInventory(sp, attItem1.ID, (uint)AttachmentPoint.Default);
465  
466 // default attachment point is currently the left hand.
467 Assert.That(sp.HasAttachments(), Is.True);
468 List<SceneObjectGroup> attachments = sp.GetAttachments();
469 Assert.That(attachments.Count, Is.EqualTo(1));
470 SceneObjectGroup attSo = attachments[0];
471 Assert.That(attSo.Name, Is.EqualTo(attItem1.Name));
472 Assert.That(attSo.AttachmentPoint, Is.EqualTo((byte)AttachmentPoint.LeftHand));
473 Assert.That(attSo.IsAttachment);
474  
475 // Check appearance status
476 Assert.That(sp.Appearance.GetAttachments().Count, Is.EqualTo(1));
477 Assert.That(sp.Appearance.GetAttachpoint(attItem1.ID), Is.EqualTo((int)AttachmentPoint.LeftHand));
478 Assert.That(scene.GetSceneObjectGroups().Count, Is.EqualTo(1));
479  
480 // Check events
481 Assert.That(m_numberOfAttachEventsFired, Is.EqualTo(1));
482 }
483  
484 // Test wearing a second attachment at the same position
485 // Until multiple attachments at one point is implemented, this will remove the first attachment
486 // This test relies on both attachments having the same default attachment point (in this case LeftHand
487 // since none other has been set).
488 {
489 scene.AttachmentsModule.RezSingleAttachmentFromInventory(sp, attItem2.ID, (uint)AttachmentPoint.Default);
490  
491 // default attachment point is currently the left hand.
492 Assert.That(sp.HasAttachments(), Is.True);
493 List<SceneObjectGroup> attachments = sp.GetAttachments();
494 Assert.That(attachments.Count, Is.EqualTo(1));
495 SceneObjectGroup attSo = attachments[0];
496 Assert.That(attSo.Name, Is.EqualTo(attItem2.Name));
497 Assert.That(attSo.AttachmentPoint, Is.EqualTo((byte)AttachmentPoint.LeftHand));
498 Assert.That(attSo.IsAttachment);
499  
500 // Check appearance status
501 Assert.That(sp.Appearance.GetAttachments().Count, Is.EqualTo(1));
502 Assert.That(sp.Appearance.GetAttachpoint(attItem2.ID), Is.EqualTo((int)AttachmentPoint.LeftHand));
503 Assert.That(scene.GetSceneObjectGroups().Count, Is.EqualTo(1));
504  
505 // Check events
506 Assert.That(m_numberOfAttachEventsFired, Is.EqualTo(3));
507 }
508  
509 // Test wearing an already attached attachment
510 {
511 scene.AttachmentsModule.RezSingleAttachmentFromInventory(sp, attItem2.ID, (uint)AttachmentPoint.Default);
512  
513 // default attachment point is currently the left hand.
514 Assert.That(sp.HasAttachments(), Is.True);
515 List<SceneObjectGroup> attachments = sp.GetAttachments();
516 Assert.That(attachments.Count, Is.EqualTo(1));
517 SceneObjectGroup attSo = attachments[0];
518 Assert.That(attSo.Name, Is.EqualTo(attItem2.Name));
519 Assert.That(attSo.AttachmentPoint, Is.EqualTo((byte)AttachmentPoint.LeftHand));
520 Assert.That(attSo.IsAttachment);
521  
522 // Check appearance status
523 Assert.That(sp.Appearance.GetAttachments().Count, Is.EqualTo(1));
524 Assert.That(sp.Appearance.GetAttachpoint(attItem2.ID), Is.EqualTo((int)AttachmentPoint.LeftHand));
525 Assert.That(scene.GetSceneObjectGroups().Count, Is.EqualTo(1));
526  
527 // Check events
528 Assert.That(m_numberOfAttachEventsFired, Is.EqualTo(3));
529 }
530 }
531  
532 /// <summary>
533 /// Test specific conditions associated with rezzing a scripted attachment from inventory.
534 /// </summary>
535 [Test]
536 public void TestRezScriptedAttachmentFromInventory()
537 {
538 TestHelpers.InMethod();
539  
540 Scene scene = CreateScriptingEnabledTestScene();
541 UserAccount ua1 = UserAccountHelpers.CreateUserWithInventory(scene, 0x1);
542 ScenePresence sp = SceneHelpers.AddScenePresence(scene, ua1);
543  
544 SceneObjectGroup so = SceneHelpers.CreateSceneObject(1, sp.UUID, "att-name", 0x10);
545 TaskInventoryItem scriptItem
546 = TaskInventoryHelpers.AddScript(
547 scene,
548 so.RootPart,
549 "scriptItem",
550 "default { attach(key id) { if (id != NULL_KEY) { llSay(0, \"Hello World\"); } } }");
551  
552 InventoryItemBase userItem = UserInventoryHelpers.AddInventoryItem(scene, so, 0x100, 0x1000);
553  
554 // FIXME: Right now, we have to do a tricksy chat listen to make sure we know when the script is running.
555 // In the future, we need to be able to do this programatically more predicably.
556 scene.EventManager.OnChatFromWorld += OnChatFromWorld;
557  
558 scene.AttachmentsModule.RezSingleAttachmentFromInventory(sp, userItem.ID, (uint)AttachmentPoint.Chest);
559  
560 m_chatEvent.WaitOne(60000);
561  
562 // TODO: Need to have a test that checks the script is actually started but this involves a lot more
563 // plumbing of the script engine and either pausing for events or more infrastructure to turn off various
564 // script engine delays/asychronicity that isn't helpful in an automated regression testing context.
565 SceneObjectGroup attSo = scene.GetSceneObjectGroup(so.Name);
566 Assert.That(attSo.ContainsScripts(), Is.True);
567  
568 TaskInventoryItem reRezzedScriptItem = attSo.RootPart.Inventory.GetInventoryItem(scriptItem.Name);
569 IScriptModule xengine = scene.RequestModuleInterface<IScriptModule>();
570 Assert.That(xengine.GetScriptState(reRezzedScriptItem.ItemID), Is.True);
571 }
572  
573 [Test]
574 public void TestDetachAttachmentToGround()
575 {
576 TestHelpers.InMethod();
577 // log4net.Config.XmlConfigurator.Configure();
578  
579 Scene scene = CreateTestScene();
580 UserAccount ua1 = UserAccountHelpers.CreateUserWithInventory(scene, 0x1);
581 ScenePresence sp = SceneHelpers.AddScenePresence(scene, ua1.PrincipalID);
582  
583 InventoryItemBase attItem = CreateAttachmentItem(scene, ua1.PrincipalID, "att", 0x10, 0x20);
584  
585 ISceneEntity so
586 = scene.AttachmentsModule.RezSingleAttachmentFromInventory(
587 sp, attItem.ID, (uint)AttachmentPoint.Chest);
588  
589 m_numberOfAttachEventsFired = 0;
590 scene.AttachmentsModule.DetachSingleAttachmentToGround(sp, so.LocalId);
591  
592 // Check scene presence status
593 Assert.That(sp.HasAttachments(), Is.False);
594 List<SceneObjectGroup> attachments = sp.GetAttachments();
595 Assert.That(attachments.Count, Is.EqualTo(0));
596  
597 // Check appearance status
598 Assert.That(sp.Appearance.GetAttachments().Count, Is.EqualTo(0));
599  
600 // Check item status
601 Assert.That(scene.InventoryService.GetItem(new InventoryItemBase(attItem.ID)), Is.Null);
602  
603 // Check object in scene
604 Assert.That(scene.GetSceneObjectGroup("att"), Is.Not.Null);
605  
606 // Check events
607 Assert.That(m_numberOfAttachEventsFired, Is.EqualTo(1));
608 }
609  
610 [Test]
611 public void TestDetachAttachmentToInventory()
612 {
613 TestHelpers.InMethod();
614  
615 Scene scene = CreateTestScene();
616 UserAccount ua1 = UserAccountHelpers.CreateUserWithInventory(scene, 0x1);
617 ScenePresence sp = SceneHelpers.AddScenePresence(scene, ua1.PrincipalID);
618  
619 InventoryItemBase attItem = CreateAttachmentItem(scene, ua1.PrincipalID, "att", 0x10, 0x20);
620  
621 SceneObjectGroup so
622 = (SceneObjectGroup)scene.AttachmentsModule.RezSingleAttachmentFromInventory(
623 sp, attItem.ID, (uint)AttachmentPoint.Chest);
624  
625 m_numberOfAttachEventsFired = 0;
626 scene.AttachmentsModule.DetachSingleAttachmentToInv(sp, so);
627  
628 // Check status on scene presence
629 Assert.That(sp.HasAttachments(), Is.False);
630 List<SceneObjectGroup> attachments = sp.GetAttachments();
631 Assert.That(attachments.Count, Is.EqualTo(0));
632  
633 // Check item status
634 Assert.That(sp.Appearance.GetAttachpoint(attItem.ID), Is.EqualTo(0));
635  
636 Assert.That(scene.GetSceneObjectGroups().Count, Is.EqualTo(0));
637  
638 // Check events
639 Assert.That(m_numberOfAttachEventsFired, Is.EqualTo(1));
640 }
641  
642 /// <summary>
643 /// Test specific conditions associated with detaching a scripted attachment from inventory.
644 /// </summary>
645 [Test]
646 public void TestDetachScriptedAttachmentToInventory()
647 {
648 TestHelpers.InMethod();
649 // TestHelpers.EnableLogging();
650  
651 Scene scene = CreateScriptingEnabledTestScene();
652 UserAccount ua1 = UserAccountHelpers.CreateUserWithInventory(scene, 0x1);
653 ScenePresence sp = SceneHelpers.AddScenePresence(scene, ua1);
654  
655 SceneObjectGroup so = SceneHelpers.CreateSceneObject(1, sp.UUID, "att-name", 0x10);
656 TaskInventoryItem scriptTaskItem
657 = TaskInventoryHelpers.AddScript(
658 scene,
659 so.RootPart,
660 "scriptItem",
661 "default { attach(key id) { if (id != NULL_KEY) { llSay(0, \"Hello World\"); } } }");
662  
663 InventoryItemBase userItem = UserInventoryHelpers.AddInventoryItem(scene, so, 0x100, 0x1000);
664  
665 // FIXME: Right now, we have to do a tricksy chat listen to make sure we know when the script is running.
666 // In the future, we need to be able to do this programatically more predicably.
667 scene.EventManager.OnChatFromWorld += OnChatFromWorld;
668  
669 SceneObjectGroup rezzedSo
670 = scene.AttachmentsModule.RezSingleAttachmentFromInventory(sp, userItem.ID, (uint)AttachmentPoint.Chest);
671  
672 // Wait for chat to signal rezzed script has been started.
673 m_chatEvent.WaitOne(60000);
674  
675 scene.AttachmentsModule.DetachSingleAttachmentToInv(sp, rezzedSo);
676  
677 InventoryItemBase userItemUpdated = scene.InventoryService.GetItem(userItem);
678 AssetBase asset = scene.AssetService.Get(userItemUpdated.AssetID.ToString());
679  
680 // TODO: It would probably be better here to check script state via the saving and retrieval of state
681 // information at a higher level, rather than having to inspect the serialization.
682 XmlDocument soXml = new XmlDocument();
683 soXml.LoadXml(Encoding.UTF8.GetString(asset.Data));
684  
685 XmlNodeList scriptStateNodes = soXml.GetElementsByTagName("ScriptState");
686 Assert.That(scriptStateNodes.Count, Is.EqualTo(1));
687  
688 // Re-rez the attachment to check script running state
689 SceneObjectGroup reRezzedSo = scene.AttachmentsModule.RezSingleAttachmentFromInventory(sp, userItem.ID, (uint)AttachmentPoint.Chest);
690  
691 // Wait for chat to signal rezzed script has been started.
692 m_chatEvent.WaitOne(60000);
693  
694 TaskInventoryItem reRezzedScriptItem = reRezzedSo.RootPart.Inventory.GetInventoryItem(scriptTaskItem.Name);
695 IScriptModule xengine = scene.RequestModuleInterface<IScriptModule>();
696 Assert.That(xengine.GetScriptState(reRezzedScriptItem.ItemID), Is.True);
697  
698 // Console.WriteLine(soXml.OuterXml);
699 }
700  
701 /// <summary>
702 /// Test that attachments don't hang about in the scene when the agent is closed
703 /// </summary>
704 [Test]
705 public void TestRemoveAttachmentsOnAvatarExit()
706 {
707 TestHelpers.InMethod();
708 // log4net.Config.XmlConfigurator.Configure();
709  
710 Scene scene = CreateTestScene();
711 UserAccount ua1 = UserAccountHelpers.CreateUserWithInventory(scene, 0x1);
712 InventoryItemBase attItem = CreateAttachmentItem(scene, ua1.PrincipalID, "att", 0x10, 0x20);
713  
714 AgentCircuitData acd = SceneHelpers.GenerateAgentData(ua1.PrincipalID);
715 acd.Appearance = new AvatarAppearance();
716 acd.Appearance.SetAttachment((int)AttachmentPoint.Chest, attItem.ID, attItem.AssetID);
717 ScenePresence presence = SceneHelpers.AddScenePresence(scene, acd);
718  
719 SceneObjectGroup rezzedAtt = presence.GetAttachments()[0];
720  
721 m_numberOfAttachEventsFired = 0;
722 scene.CloseAgent(presence.UUID, false);
723  
724 // Check that we can't retrieve this attachment from the scene.
725 Assert.That(scene.GetSceneObjectGroup(rezzedAtt.UUID), Is.Null);
726  
727 // Check events
728 Assert.That(m_numberOfAttachEventsFired, Is.EqualTo(0));
729 }
730  
731 [Test]
732 public void TestRezAttachmentsOnAvatarEntrance()
733 {
734 TestHelpers.InMethod();
735 // TestHelpers.EnableLogging();
736  
737 Scene scene = CreateTestScene();
738 UserAccount ua1 = UserAccountHelpers.CreateUserWithInventory(scene, 0x1);
739 InventoryItemBase attItem = CreateAttachmentItem(scene, ua1.PrincipalID, "att", 0x10, 0x20);
740  
741 AgentCircuitData acd = SceneHelpers.GenerateAgentData(ua1.PrincipalID);
742 acd.Appearance = new AvatarAppearance();
743 acd.Appearance.SetAttachment((int)AttachmentPoint.Chest, attItem.ID, attItem.AssetID);
744  
745 m_numberOfAttachEventsFired = 0;
746 ScenePresence presence = SceneHelpers.AddScenePresence(scene, acd);
747  
748 Assert.That(presence.HasAttachments(), Is.True);
749 List<SceneObjectGroup> attachments = presence.GetAttachments();
750  
751 Assert.That(attachments.Count, Is.EqualTo(1));
752 SceneObjectGroup attSo = attachments[0];
753 Assert.That(attSo.Name, Is.EqualTo(attItem.Name));
754 Assert.That(attSo.AttachmentPoint, Is.EqualTo((byte)AttachmentPoint.Chest));
755 Assert.That(attSo.IsAttachment);
756 Assert.That(attSo.UsesPhysics, Is.False);
757 Assert.That(attSo.IsTemporary, Is.False);
758  
759 // Check appearance status
760 List<AvatarAttachment> retreivedAttachments = presence.Appearance.GetAttachments();
761 Assert.That(retreivedAttachments.Count, Is.EqualTo(1));
762 Assert.That(retreivedAttachments[0].AttachPoint, Is.EqualTo((int)AttachmentPoint.Chest));
763 Assert.That(retreivedAttachments[0].ItemID, Is.EqualTo(attItem.ID));
764 Assert.That(retreivedAttachments[0].AssetID, Is.EqualTo(attItem.AssetID));
765 Assert.That(presence.Appearance.GetAttachpoint(attItem.ID), Is.EqualTo((int)AttachmentPoint.Chest));
766  
767 Assert.That(scene.GetSceneObjectGroups().Count, Is.EqualTo(1));
768  
769 // Check events. We expect OnAttach to fire on login.
770 Assert.That(m_numberOfAttachEventsFired, Is.EqualTo(1));
771 }
772  
773 [Test]
774 public void TestUpdateAttachmentPosition()
775 {
776 TestHelpers.InMethod();
777  
778 Scene scene = CreateTestScene();
779 UserAccount ua1 = UserAccountHelpers.CreateUserWithInventory(scene, 0x1);
780 InventoryItemBase attItem = CreateAttachmentItem(scene, ua1.PrincipalID, "att", 0x10, 0x20);
781  
782 AgentCircuitData acd = SceneHelpers.GenerateAgentData(ua1.PrincipalID);
783 acd.Appearance = new AvatarAppearance();
784 acd.Appearance.SetAttachment((int)AttachmentPoint.Chest, attItem.ID, attItem.AssetID);
785 ScenePresence sp = SceneHelpers.AddScenePresence(scene, acd);
786  
787 SceneObjectGroup attSo = sp.GetAttachments()[0];
788  
789 Vector3 newPosition = new Vector3(1, 2, 4);
790  
791 m_numberOfAttachEventsFired = 0;
792 scene.SceneGraph.UpdatePrimGroupPosition(attSo.LocalId, newPosition, sp.ControllingClient);
793  
794 Assert.That(attSo.AbsolutePosition, Is.EqualTo(sp.AbsolutePosition));
795 Assert.That(attSo.RootPart.AttachedPos, Is.EqualTo(newPosition));
796  
797 // Check events
798 Assert.That(m_numberOfAttachEventsFired, Is.EqualTo(0));
799 }
800  
801 [Test]
802 public void TestSameSimulatorNeighbouringRegionsTeleportV1()
803 {
804 TestHelpers.InMethod();
805 // TestHelpers.EnableLogging();
806  
807 BaseHttpServer httpServer = new BaseHttpServer(99999);
808 MainServer.AddHttpServer(httpServer);
809 MainServer.Instance = httpServer;
810  
811 AttachmentsModule attModA = new AttachmentsModule();
812 AttachmentsModule attModB = new AttachmentsModule();
813 EntityTransferModule etmA = new EntityTransferModule();
814 EntityTransferModule etmB = new EntityTransferModule();
815 LocalSimulationConnectorModule lscm = new LocalSimulationConnectorModule();
816  
817 IConfigSource config = new IniConfigSource();
818 IConfig modulesConfig = config.AddConfig("Modules");
819 modulesConfig.Set("EntityTransferModule", etmA.Name);
820 modulesConfig.Set("SimulationServices", lscm.Name);
821 IConfig entityTransferConfig = config.AddConfig("EntityTransfer");
822  
823 // In order to run a single threaded regression test we do not want the entity transfer module waiting
824 // for a callback from the destination scene before removing its avatar data.
825 entityTransferConfig.Set("wait_for_callback", false);
826  
827 modulesConfig.Set("InventoryAccessModule", "BasicInventoryAccessModule");
828  
829 SceneHelpers sh = new SceneHelpers();
830 TestScene sceneA = sh.SetupScene("sceneA", TestHelpers.ParseTail(0x100), 1000, 1000);
831 TestScene sceneB = sh.SetupScene("sceneB", TestHelpers.ParseTail(0x200), 1001, 1000);
832  
833 SceneHelpers.SetupSceneModules(new Scene[] { sceneA, sceneB }, config, lscm);
834 SceneHelpers.SetupSceneModules(
835 sceneA, config, new CapabilitiesModule(), etmA, attModA, new BasicInventoryAccessModule());
836 SceneHelpers.SetupSceneModules(
837 sceneB, config, new CapabilitiesModule(), etmB, attModB, new BasicInventoryAccessModule());
838  
839 // FIXME: Hack - this is here temporarily to revert back to older entity transfer behaviour
840 lscm.ServiceVersion = "SIMULATION/0.1";
841  
842 UserAccount ua1 = UserAccountHelpers.CreateUserWithInventory(sceneA, 0x1);
843  
844 AgentCircuitData acd = SceneHelpers.GenerateAgentData(ua1.PrincipalID);
845 TestClient tc = new TestClient(acd, sceneA);
846 List<TestClient> destinationTestClients = new List<TestClient>();
847 EntityTransferHelpers.SetupInformClientOfNeighbourTriggersNeighbourClientCreate(tc, destinationTestClients);
848  
849 ScenePresence beforeTeleportSp = SceneHelpers.AddScenePresence(sceneA, tc, acd);
850 beforeTeleportSp.AbsolutePosition = new Vector3(30, 31, 32);
851  
852 InventoryItemBase attItem = CreateAttachmentItem(sceneA, ua1.PrincipalID, "att", 0x10, 0x20);
853  
854 sceneA.AttachmentsModule.RezSingleAttachmentFromInventory(
855 beforeTeleportSp, attItem.ID, (uint)AttachmentPoint.Chest);
856  
857 Vector3 teleportPosition = new Vector3(10, 11, 12);
858 Vector3 teleportLookAt = new Vector3(20, 21, 22);
859  
860 m_numberOfAttachEventsFired = 0;
861 sceneA.RequestTeleportLocation(
862 beforeTeleportSp.ControllingClient,
863 sceneB.RegionInfo.RegionHandle,
864 teleportPosition,
865 teleportLookAt,
866 (uint)TeleportFlags.ViaLocation);
867  
868 destinationTestClients[0].CompleteMovement();
869  
870 // Check attachments have made it into sceneB
871 ScenePresence afterTeleportSceneBSp = sceneB.GetScenePresence(ua1.PrincipalID);
872  
873 // This is appearance data, as opposed to actually rezzed attachments
874 List<AvatarAttachment> sceneBAttachments = afterTeleportSceneBSp.Appearance.GetAttachments();
875 Assert.That(sceneBAttachments.Count, Is.EqualTo(1));
876 Assert.That(sceneBAttachments[0].AttachPoint, Is.EqualTo((int)AttachmentPoint.Chest));
877 Assert.That(sceneBAttachments[0].ItemID, Is.EqualTo(attItem.ID));
878 Assert.That(sceneBAttachments[0].AssetID, Is.EqualTo(attItem.AssetID));
879 Assert.That(afterTeleportSceneBSp.Appearance.GetAttachpoint(attItem.ID), Is.EqualTo((int)AttachmentPoint.Chest));
880  
881 // This is the actual attachment
882 List<SceneObjectGroup> actualSceneBAttachments = afterTeleportSceneBSp.GetAttachments();
883 Assert.That(actualSceneBAttachments.Count, Is.EqualTo(1));
884 SceneObjectGroup actualSceneBAtt = actualSceneBAttachments[0];
885 Assert.That(actualSceneBAtt.Name, Is.EqualTo(attItem.Name));
886 Assert.That(actualSceneBAtt.AttachmentPoint, Is.EqualTo((uint)AttachmentPoint.Chest));
887  
888 Assert.That(sceneB.GetSceneObjectGroups().Count, Is.EqualTo(1));
889  
890 // Check attachments have been removed from sceneA
891 ScenePresence afterTeleportSceneASp = sceneA.GetScenePresence(ua1.PrincipalID);
892  
893 // Since this is appearance data, it is still present on the child avatar!
894 List<AvatarAttachment> sceneAAttachments = afterTeleportSceneASp.Appearance.GetAttachments();
895 Assert.That(sceneAAttachments.Count, Is.EqualTo(1));
896 Assert.That(afterTeleportSceneASp.Appearance.GetAttachpoint(attItem.ID), Is.EqualTo((int)AttachmentPoint.Chest));
897  
898 // This is the actual attachment, which should no longer exist
899 List<SceneObjectGroup> actualSceneAAttachments = afterTeleportSceneASp.GetAttachments();
900 Assert.That(actualSceneAAttachments.Count, Is.EqualTo(0));
901  
902 Assert.That(sceneA.GetSceneObjectGroups().Count, Is.EqualTo(0));
903  
904 // Check events
905 Assert.That(m_numberOfAttachEventsFired, Is.EqualTo(0));
906 }
907  
908 [Test]
909 public void TestSameSimulatorNeighbouringRegionsTeleportV2()
910 {
911 TestHelpers.InMethod();
912 // TestHelpers.EnableLogging();
913  
914 BaseHttpServer httpServer = new BaseHttpServer(99999);
915 MainServer.AddHttpServer(httpServer);
916 MainServer.Instance = httpServer;
917  
918 AttachmentsModule attModA = new AttachmentsModule();
919 AttachmentsModule attModB = new AttachmentsModule();
920 EntityTransferModule etmA = new EntityTransferModule();
921 EntityTransferModule etmB = new EntityTransferModule();
922 LocalSimulationConnectorModule lscm = new LocalSimulationConnectorModule();
923  
924 IConfigSource config = new IniConfigSource();
925 IConfig modulesConfig = config.AddConfig("Modules");
926 modulesConfig.Set("EntityTransferModule", etmA.Name);
927 modulesConfig.Set("SimulationServices", lscm.Name);
928  
929 modulesConfig.Set("InventoryAccessModule", "BasicInventoryAccessModule");
930  
931 SceneHelpers sh = new SceneHelpers();
932 TestScene sceneA = sh.SetupScene("sceneA", TestHelpers.ParseTail(0x100), 1000, 1000);
933 TestScene sceneB = sh.SetupScene("sceneB", TestHelpers.ParseTail(0x200), 1001, 1000);
934  
935 SceneHelpers.SetupSceneModules(new Scene[] { sceneA, sceneB }, config, lscm);
936 SceneHelpers.SetupSceneModules(
937 sceneA, config, new CapabilitiesModule(), etmA, attModA, new BasicInventoryAccessModule());
938 SceneHelpers.SetupSceneModules(
939 sceneB, config, new CapabilitiesModule(), etmB, attModB, new BasicInventoryAccessModule());
940  
941 UserAccount ua1 = UserAccountHelpers.CreateUserWithInventory(sceneA, 0x1);
942  
943 AgentCircuitData acd = SceneHelpers.GenerateAgentData(ua1.PrincipalID);
944 TestClient tc = new TestClient(acd, sceneA);
945 List<TestClient> destinationTestClients = new List<TestClient>();
946 EntityTransferHelpers.SetupInformClientOfNeighbourTriggersNeighbourClientCreate(tc, destinationTestClients);
947  
948 ScenePresence beforeTeleportSp = SceneHelpers.AddScenePresence(sceneA, tc, acd);
949 beforeTeleportSp.AbsolutePosition = new Vector3(30, 31, 32);
950  
951 Assert.That(destinationTestClients.Count, Is.EqualTo(1));
952 Assert.That(destinationTestClients[0], Is.Not.Null);
953  
954 InventoryItemBase attItem = CreateAttachmentItem(sceneA, ua1.PrincipalID, "att", 0x10, 0x20);
955  
956 sceneA.AttachmentsModule.RezSingleAttachmentFromInventory(
957 beforeTeleportSp, attItem.ID, (uint)AttachmentPoint.Chest);
958  
959 Vector3 teleportPosition = new Vector3(10, 11, 12);
960 Vector3 teleportLookAt = new Vector3(20, 21, 22);
961  
962 // Here, we need to make clientA's receipt of SendRegionTeleport trigger clientB's CompleteMovement(). This
963 // is to operate the teleport V2 mechanism where the EntityTransferModule will first request the client to
964 // CompleteMovement to the region and then call UpdateAgent to the destination region to confirm the receipt
965 // Both these operations will occur on different threads and will wait for each other.
966 // We have to do this via ThreadPool directly since FireAndForget has been switched to sync for the V1
967 // test protocol, where we are trying to avoid unpredictable async operations in regression tests.
968 tc.OnTestClientSendRegionTeleport
969 += (regionHandle, simAccess, regionExternalEndPoint, locationID, flags, capsURL)
970 => ThreadPool.UnsafeQueueUserWorkItem(o => destinationTestClients[0].CompleteMovement(), null);
971  
972 m_numberOfAttachEventsFired = 0;
973 sceneA.RequestTeleportLocation(
974 beforeTeleportSp.ControllingClient,
975 sceneB.RegionInfo.RegionHandle,
976 teleportPosition,
977 teleportLookAt,
978 (uint)TeleportFlags.ViaLocation);
979  
980 // Check attachments have made it into sceneB
981 ScenePresence afterTeleportSceneBSp = sceneB.GetScenePresence(ua1.PrincipalID);
982  
983 // This is appearance data, as opposed to actually rezzed attachments
984 List<AvatarAttachment> sceneBAttachments = afterTeleportSceneBSp.Appearance.GetAttachments();
985 Assert.That(sceneBAttachments.Count, Is.EqualTo(1));
986 Assert.That(sceneBAttachments[0].AttachPoint, Is.EqualTo((int)AttachmentPoint.Chest));
987 Assert.That(sceneBAttachments[0].ItemID, Is.EqualTo(attItem.ID));
988 Assert.That(sceneBAttachments[0].AssetID, Is.EqualTo(attItem.AssetID));
989 Assert.That(afterTeleportSceneBSp.Appearance.GetAttachpoint(attItem.ID), Is.EqualTo((int)AttachmentPoint.Chest));
990  
991 // This is the actual attachment
992 List<SceneObjectGroup> actualSceneBAttachments = afterTeleportSceneBSp.GetAttachments();
993 Assert.That(actualSceneBAttachments.Count, Is.EqualTo(1));
994 SceneObjectGroup actualSceneBAtt = actualSceneBAttachments[0];
995 Assert.That(actualSceneBAtt.Name, Is.EqualTo(attItem.Name));
996 Assert.That(actualSceneBAtt.AttachmentPoint, Is.EqualTo((uint)AttachmentPoint.Chest));
997  
998 Assert.That(sceneB.GetSceneObjectGroups().Count, Is.EqualTo(1));
999  
1000 // Check attachments have been removed from sceneA
1001 ScenePresence afterTeleportSceneASp = sceneA.GetScenePresence(ua1.PrincipalID);
1002  
1003 // Since this is appearance data, it is still present on the child avatar!
1004 List<AvatarAttachment> sceneAAttachments = afterTeleportSceneASp.Appearance.GetAttachments();
1005 Assert.That(sceneAAttachments.Count, Is.EqualTo(1));
1006 Assert.That(afterTeleportSceneASp.Appearance.GetAttachpoint(attItem.ID), Is.EqualTo((int)AttachmentPoint.Chest));
1007  
1008 // This is the actual attachment, which should no longer exist
1009 List<SceneObjectGroup> actualSceneAAttachments = afterTeleportSceneASp.GetAttachments();
1010 Assert.That(actualSceneAAttachments.Count, Is.EqualTo(0));
1011  
1012 Assert.That(sceneA.GetSceneObjectGroups().Count, Is.EqualTo(0));
1013  
1014 // Check events
1015 Assert.That(m_numberOfAttachEventsFired, Is.EqualTo(0));
1016 }
1017 }
1018 }