aboutsummaryrefslogtreecommitdiffstatshomepage
path: root/OpenSim/Services/InventoryService/InventoryService.cs
diff options
context:
space:
mode:
Diffstat (limited to 'OpenSim/Services/InventoryService/InventoryService.cs')
-rw-r--r--OpenSim/Services/InventoryService/InventoryService.cs544
1 files changed, 544 insertions, 0 deletions
diff --git a/OpenSim/Services/InventoryService/InventoryService.cs b/OpenSim/Services/InventoryService/InventoryService.cs
new file mode 100644
index 0000000..b4e2549
--- /dev/null
+++ b/OpenSim/Services/InventoryService/InventoryService.cs
@@ -0,0 +1,544 @@
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
28using System.Collections.Generic;
29using System.Reflection;
30using log4net;
31using Nini.Config;
32using OpenMetaverse;
33using OpenSim.Data;
34using OpenSim.Framework;
35using OpenSim.Services.Interfaces;
36
37namespace OpenSim.Services.InventoryService
38{
39 /// <summary>
40 /// The Inventory service reference implementation
41 /// </summary>
42 public class InventoryService : InventoryServiceBase, IInventoryService
43 {
44 private static readonly ILog m_log
45 = LogManager.GetLogger(MethodBase.GetCurrentMethod().DeclaringType);
46
47 public InventoryService(IConfigSource config) : base(config)
48 {
49 }
50
51 #region IInventoryServices methods
52
53 public string Host
54 {
55 get { return "default"; }
56 }
57
58 public List<InventoryFolderBase> GetInventorySkeleton(UUID userId)
59 {
60// m_log.DebugFormat("[AGENT INVENTORY]: Getting inventory skeleton for {0}", userId);
61
62 InventoryFolderBase rootFolder = RequestRootFolder(userId);
63
64 // Agent has no inventory structure yet.
65 if (null == rootFolder)
66 {
67 return null;
68 }
69
70 List<InventoryFolderBase> userFolders = new List<InventoryFolderBase>();
71
72 userFolders.Add(rootFolder);
73
74 foreach (IInventoryDataPlugin plugin in m_plugins)
75 {
76 IList<InventoryFolderBase> folders = plugin.getFolderHierarchy(rootFolder.ID);
77 userFolders.AddRange(folders);
78 }
79
80// foreach (InventoryFolderBase folder in userFolders)
81// {
82// m_log.DebugFormat("[AGENT INVENTORY]: Got folder {0} {1}", folder.name, folder.folderID);
83// }
84
85 return userFolders;
86 }
87
88 // See IInventoryServices
89 public virtual bool HasInventoryForUser(UUID userID)
90 {
91 return false;
92 }
93
94 // See IInventoryServices
95 public virtual InventoryFolderBase RequestRootFolder(UUID userID)
96 {
97 // Retrieve the first root folder we get from the list of plugins.
98 foreach (IInventoryDataPlugin plugin in m_plugins)
99 {
100 InventoryFolderBase rootFolder = plugin.getUserRootFolder(userID);
101 if (rootFolder != null)
102 return rootFolder;
103 }
104
105 // Return nothing if no plugin was able to supply a root folder
106 return null;
107 }
108
109 // See IInventoryServices
110 public bool CreateNewUserInventory(UUID user)
111 {
112 InventoryFolderBase existingRootFolder = RequestRootFolder(user);
113
114 if (null != existingRootFolder)
115 {
116 m_log.WarnFormat(
117 "[AGENT INVENTORY]: Did not create a new inventory for user {0} since they already have "
118 + "a root inventory folder with id {1}",
119 user, existingRootFolder.ID);
120 }
121 else
122 {
123 UsersInventory inven = new UsersInventory();
124 inven.CreateNewInventorySet(user);
125 AddNewInventorySet(inven);
126
127 return true;
128 }
129
130 return false;
131 }
132
133 // See IInventoryServices
134 public void GetUserInventory(UUID userID, InventoryReceiptCallback callback)
135 {
136 m_log.InfoFormat("[LOCAL INVENTORY SERVICE]: Requesting inventory for user {0}", userID);
137
138 List<InventoryFolderImpl> folders = new List<InventoryFolderImpl>();
139 List<InventoryItemBase> items = new List<InventoryItemBase>();
140
141 List<InventoryFolderBase> skeletonFolders = GetInventorySkeleton(userID);
142
143 if (skeletonFolders != null)
144 {
145
146 InventoryFolderImpl rootFolder = null;
147
148 // Need to retrieve the root folder on the first pass
149 foreach (InventoryFolderBase folder in skeletonFolders)
150 {
151 if (folder.ParentID == UUID.Zero)
152 {
153 rootFolder = new InventoryFolderImpl(folder);
154 folders.Add(rootFolder);
155 items.AddRange(RequestFolderItems(rootFolder.ID));
156 break; // Only 1 root folder per user
157 }
158 }
159
160 if (rootFolder != null)
161 {
162 foreach (InventoryFolderBase folder in skeletonFolders)
163 {
164 if (folder.ID != rootFolder.ID)
165 {
166 folders.Add(new InventoryFolderImpl(folder));
167 items.AddRange(RequestFolderItems(folder.ID));
168 }
169 }
170 }
171
172 m_log.InfoFormat(
173 "[LOCAL INVENTORY SERVICE]: Received inventory response for user {0} containing {1} folders and {2} items",
174 userID, folders.Count, items.Count);
175 }
176 else
177 {
178 m_log.WarnFormat("[LOCAL INVENTORY SERVICE]: User {0} inventory not available", userID);
179 }
180
181 callback(folders, items);
182 }
183
184 public List<InventoryItemBase> GetActiveGestures(UUID userId)
185 {
186 List<InventoryItemBase> activeGestures = new List<InventoryItemBase>();
187 foreach (IInventoryDataPlugin plugin in m_plugins)
188 {
189 activeGestures.AddRange(plugin.fetchActiveGestures(userId));
190 }
191
192 return activeGestures;
193 }
194
195 #endregion
196
197 #region Methods used by GridInventoryService
198
199 public List<InventoryFolderBase> RequestSubFolders(UUID parentFolderID)
200 {
201 List<InventoryFolderBase> inventoryList = new List<InventoryFolderBase>();
202
203 foreach (IInventoryDataPlugin plugin in m_plugins)
204 {
205 inventoryList.AddRange(plugin.getInventoryFolders(parentFolderID));
206 }
207
208 return inventoryList;
209 }
210
211 public List<InventoryItemBase> RequestFolderItems(UUID folderID)
212 {
213 List<InventoryItemBase> itemsList = new List<InventoryItemBase>();
214
215 foreach (IInventoryDataPlugin plugin in m_plugins)
216 {
217 itemsList.AddRange(plugin.getInventoryInFolder(folderID));
218 }
219
220 return itemsList;
221 }
222
223 #endregion
224
225 // See IInventoryServices
226 public virtual bool AddFolder(InventoryFolderBase folder)
227 {
228 m_log.DebugFormat(
229 "[AGENT INVENTORY]: Adding folder {0} {1} to folder {2}", folder.Name, folder.ID, folder.ParentID);
230
231 foreach (IInventoryDataPlugin plugin in m_plugins)
232 {
233 plugin.addInventoryFolder(folder);
234 }
235
236 // FIXME: Should return false on failure
237 return true;
238 }
239
240 // See IInventoryServices
241 public virtual bool UpdateFolder(InventoryFolderBase folder)
242 {
243 m_log.DebugFormat(
244 "[AGENT INVENTORY]: Updating folder {0} {1} to folder {2}", folder.Name, folder.ID, folder.ParentID);
245
246 foreach (IInventoryDataPlugin plugin in m_plugins)
247 {
248 plugin.updateInventoryFolder(folder);
249 }
250
251 // FIXME: Should return false on failure
252 return true;
253 }
254
255 // See IInventoryServices
256 public virtual bool MoveFolder(InventoryFolderBase folder)
257 {
258 m_log.DebugFormat(
259 "[AGENT INVENTORY]: Moving folder {0} {1} to folder {2}", folder.Name, folder.ID, folder.ParentID);
260
261 foreach (IInventoryDataPlugin plugin in m_plugins)
262 {
263 plugin.moveInventoryFolder(folder);
264 }
265
266 // FIXME: Should return false on failure
267 return true;
268 }
269
270 // See IInventoryServices
271 public virtual bool AddItem(InventoryItemBase item)
272 {
273 m_log.DebugFormat(
274 "[AGENT INVENTORY]: Adding item {0} {1} to folder {2}", item.Name, item.ID, item.Folder);
275
276 foreach (IInventoryDataPlugin plugin in m_plugins)
277 {
278 plugin.addInventoryItem(item);
279 }
280
281 // FIXME: Should return false on failure
282 return true;
283 }
284
285 // See IInventoryServices
286 public virtual bool UpdateItem(InventoryItemBase item)
287 {
288 m_log.InfoFormat(
289 "[AGENT INVENTORY]: Updating item {0} {1} in folder {2}", item.Name, item.ID, item.Folder);
290
291 foreach (IInventoryDataPlugin plugin in m_plugins)
292 {
293 plugin.updateInventoryItem(item);
294 }
295
296 // FIXME: Should return false on failure
297 return true;
298 }
299
300 // See IInventoryServices
301 public virtual bool DeleteItem(InventoryItemBase item)
302 {
303 m_log.InfoFormat(
304 "[AGENT INVENTORY]: Deleting item {0} {1} from folder {2}", item.Name, item.ID, item.Folder);
305
306 foreach (IInventoryDataPlugin plugin in m_plugins)
307 {
308 plugin.deleteInventoryItem(item.ID);
309 }
310
311 // FIXME: Should return false on failure
312 return true;
313 }
314
315 public virtual InventoryItemBase QueryItem(InventoryItemBase item)
316 {
317 foreach (IInventoryDataPlugin plugin in m_plugins)
318 {
319 InventoryItemBase result = plugin.queryInventoryItem(item.ID);
320 if (result != null)
321 return result;
322 }
323
324 return null;
325 }
326
327 public virtual InventoryFolderBase QueryFolder(InventoryFolderBase item)
328 {
329 foreach (IInventoryDataPlugin plugin in m_plugins)
330 {
331 InventoryFolderBase result = plugin.queryInventoryFolder(item.ID);
332 if (result != null)
333 return result;
334 }
335
336 return null;
337 }
338
339 /// <summary>
340 /// Purge a folder of all items items and subfolders.
341 ///
342 /// FIXME: Really nasty in a sense, because we have to query the database to get information we may
343 /// already know... Needs heavy refactoring.
344 /// </summary>
345 /// <param name="folder"></param>
346 public virtual bool PurgeFolder(InventoryFolderBase folder)
347 {
348 m_log.DebugFormat(
349 "[AGENT INVENTORY]: Purging folder {0} {1} of its contents", folder.Name, folder.ID);
350
351 List<InventoryFolderBase> subFolders = RequestSubFolders(folder.ID);
352
353 foreach (InventoryFolderBase subFolder in subFolders)
354 {
355// m_log.DebugFormat("[AGENT INVENTORY]: Deleting folder {0} {1}", subFolder.Name, subFolder.ID);
356
357 foreach (IInventoryDataPlugin plugin in m_plugins)
358 {
359 plugin.deleteInventoryFolder(subFolder.ID);
360 }
361 }
362
363 List<InventoryItemBase> items = RequestFolderItems(folder.ID);
364
365 foreach (InventoryItemBase item in items)
366 {
367 DeleteItem(item);
368 }
369
370 // FIXME: Should return false on failure
371 return true;
372 }
373
374 private void AddNewInventorySet(UsersInventory inventory)
375 {
376 foreach (InventoryFolderBase folder in inventory.Folders.Values)
377 {
378 AddFolder(folder);
379 }
380 }
381
382 public InventoryItemBase GetInventoryItem(UUID itemID)
383 {
384 foreach (IInventoryDataPlugin plugin in m_plugins)
385 {
386 InventoryItemBase item = plugin.getInventoryItem(itemID);
387 if (item != null)
388 return item;
389 }
390
391 return null;
392 }
393
394 /// <summary>
395 /// Used to create a new user inventory.
396 /// </summary>
397 private class UsersInventory
398 {
399 public Dictionary<UUID, InventoryFolderBase> Folders = new Dictionary<UUID, InventoryFolderBase>();
400 public Dictionary<UUID, InventoryItemBase> Items = new Dictionary<UUID, InventoryItemBase>();
401
402 public virtual void CreateNewInventorySet(UUID user)
403 {
404 InventoryFolderBase folder = new InventoryFolderBase();
405
406 folder.ParentID = UUID.Zero;
407 folder.Owner = user;
408 folder.ID = UUID.Random();
409 folder.Name = "My Inventory";
410 folder.Type = (short)AssetType.Folder;
411 folder.Version = 1;
412 Folders.Add(folder.ID, folder);
413
414 UUID rootFolder = folder.ID;
415
416 folder = new InventoryFolderBase();
417 folder.ParentID = rootFolder;
418 folder.Owner = user;
419 folder.ID = UUID.Random();
420 folder.Name = "Animations";
421 folder.Type = (short)AssetType.Animation;
422 folder.Version = 1;
423 Folders.Add(folder.ID, folder);
424
425 folder = new InventoryFolderBase();
426 folder.ParentID = rootFolder;
427 folder.Owner = user;
428 folder.ID = UUID.Random();
429 folder.Name = "Body Parts";
430 folder.Type = (short)AssetType.Bodypart;
431 folder.Version = 1;
432 Folders.Add(folder.ID, folder);
433
434 folder = new InventoryFolderBase();
435 folder.ParentID = rootFolder;
436 folder.Owner = user;
437 folder.ID = UUID.Random();
438 folder.Name = "Calling Cards";
439 folder.Type = (short)AssetType.CallingCard;
440 folder.Version = 1;
441 Folders.Add(folder.ID, folder);
442
443 folder = new InventoryFolderBase();
444 folder.ParentID = rootFolder;
445 folder.Owner = user;
446 folder.ID = UUID.Random();
447 folder.Name = "Clothing";
448 folder.Type = (short)AssetType.Clothing;
449 folder.Version = 1;
450 Folders.Add(folder.ID, folder);
451
452 folder = new InventoryFolderBase();
453 folder.ParentID = rootFolder;
454 folder.Owner = user;
455 folder.ID = UUID.Random();
456 folder.Name = "Gestures";
457 folder.Type = (short)AssetType.Gesture;
458 folder.Version = 1;
459 Folders.Add(folder.ID, folder);
460
461 folder = new InventoryFolderBase();
462 folder.ParentID = rootFolder;
463 folder.Owner = user;
464 folder.ID = UUID.Random();
465 folder.Name = "Landmarks";
466 folder.Type = (short)AssetType.Landmark;
467 folder.Version = 1;
468 Folders.Add(folder.ID, folder);
469
470 folder = new InventoryFolderBase();
471 folder.ParentID = rootFolder;
472 folder.Owner = user;
473 folder.ID = UUID.Random();
474 folder.Name = "Lost And Found";
475 folder.Type = (short)AssetType.LostAndFoundFolder;
476 folder.Version = 1;
477 Folders.Add(folder.ID, folder);
478
479 folder = new InventoryFolderBase();
480 folder.ParentID = rootFolder;
481 folder.Owner = user;
482 folder.ID = UUID.Random();
483 folder.Name = "Notecards";
484 folder.Type = (short)AssetType.Notecard;
485 folder.Version = 1;
486 Folders.Add(folder.ID, folder);
487
488 folder = new InventoryFolderBase();
489 folder.ParentID = rootFolder;
490 folder.Owner = user;
491 folder.ID = UUID.Random();
492 folder.Name = "Objects";
493 folder.Type = (short)AssetType.Object;
494 folder.Version = 1;
495 Folders.Add(folder.ID, folder);
496
497 folder = new InventoryFolderBase();
498 folder.ParentID = rootFolder;
499 folder.Owner = user;
500 folder.ID = UUID.Random();
501 folder.Name = "Photo Album";
502 folder.Type = (short)AssetType.SnapshotFolder;
503 folder.Version = 1;
504 Folders.Add(folder.ID, folder);
505
506 folder = new InventoryFolderBase();
507 folder.ParentID = rootFolder;
508 folder.Owner = user;
509 folder.ID = UUID.Random();
510 folder.Name = "Scripts";
511 folder.Type = (short)AssetType.LSLText;
512 folder.Version = 1;
513 Folders.Add(folder.ID, folder);
514
515 folder = new InventoryFolderBase();
516 folder.ParentID = rootFolder;
517 folder.Owner = user;
518 folder.ID = UUID.Random();
519 folder.Name = "Sounds";
520 folder.Type = (short)AssetType.Sound;
521 folder.Version = 1;
522 Folders.Add(folder.ID, folder);
523
524 folder = new InventoryFolderBase();
525 folder.ParentID = rootFolder;
526 folder.Owner = user;
527 folder.ID = UUID.Random();
528 folder.Name = "Textures";
529 folder.Type = (short)AssetType.Texture;
530 folder.Version = 1;
531 Folders.Add(folder.ID, folder);
532
533 folder = new InventoryFolderBase();
534 folder.ParentID = rootFolder;
535 folder.Owner = user;
536 folder.ID = UUID.Random();
537 folder.Name = "Trash";
538 folder.Type = (short)AssetType.TrashFolder;
539 folder.Version = 1;
540 Folders.Add(folder.ID, folder);
541 }
542 }
543 }
544}