aboutsummaryrefslogtreecommitdiffstatshomepage
path: root/OpenSim/Region/CoreModules/Framework/UserManagement
diff options
context:
space:
mode:
authorDavid Walter Seikel2016-11-03 21:44:39 +1000
committerDavid Walter Seikel2016-11-03 21:44:39 +1000
commit134f86e8d5c414409631b25b8c6f0ee45fbd8631 (patch)
tree216b89d3fb89acfb81be1e440c25c41ab09fa96d /OpenSim/Region/CoreModules/Framework/UserManagement
parentMore changing to production grid. Double oops. (diff)
downloadopensim-SC_OLD-134f86e8d5c414409631b25b8c6f0ee45fbd8631.zip
opensim-SC_OLD-134f86e8d5c414409631b25b8c6f0ee45fbd8631.tar.gz
opensim-SC_OLD-134f86e8d5c414409631b25b8c6f0ee45fbd8631.tar.bz2
opensim-SC_OLD-134f86e8d5c414409631b25b8c6f0ee45fbd8631.tar.xz
Initial update to OpenSim 0.8.2.1 source code.
Diffstat (limited to 'OpenSim/Region/CoreModules/Framework/UserManagement')
-rw-r--r--OpenSim/Region/CoreModules/Framework/UserManagement/HGUserManagementModule.cs19
-rw-r--r--OpenSim/Region/CoreModules/Framework/UserManagement/Tests/HGUserManagementModuleTests.cs75
-rw-r--r--OpenSim/Region/CoreModules/Framework/UserManagement/UserManagementModule.cs619
3 files changed, 510 insertions, 203 deletions
diff --git a/OpenSim/Region/CoreModules/Framework/UserManagement/HGUserManagementModule.cs b/OpenSim/Region/CoreModules/Framework/UserManagement/HGUserManagementModule.cs
index 4ef57fe..7b89c2c 100644
--- a/OpenSim/Region/CoreModules/Framework/UserManagement/HGUserManagementModule.cs
+++ b/OpenSim/Region/CoreModules/Framework/UserManagement/HGUserManagementModule.cs
@@ -50,16 +50,15 @@ namespace OpenSim.Region.CoreModules.Framework.UserManagement
50 { 50 {
51 private static readonly ILog m_log = LogManager.GetLogger(MethodBase.GetCurrentMethod().DeclaringType); 51 private static readonly ILog m_log = LogManager.GetLogger(MethodBase.GetCurrentMethod().DeclaringType);
52 52
53
54 #region ISharedRegionModule 53 #region ISharedRegionModule
55 54
56 public new void Initialise(IConfigSource config) 55 public new void Initialise(IConfigSource config)
57 { 56 {
58 string umanmod = config.Configs["Modules"].GetString("UserManagementModule", base.Name); 57 string umanmod = config.Configs["Modules"].GetString("UserManagementModule", null);
59 if (umanmod == Name) 58 if (umanmod == Name)
60 { 59 {
61 m_Enabled = true; 60 m_Enabled = true;
62 RegisterConsoleCmds(); 61 Init();
63 m_log.DebugFormat("[USER MANAGEMENT MODULE]: {0} is enabled", Name); 62 m_log.DebugFormat("[USER MANAGEMENT MODULE]: {0} is enabled", Name);
64 } 63 }
65 } 64 }
@@ -71,7 +70,7 @@ namespace OpenSim.Region.CoreModules.Framework.UserManagement
71 70
72 #endregion ISharedRegionModule 71 #endregion ISharedRegionModule
73 72
74 protected override void AddAdditionalUsers(UUID avatarID, string query, List<UserData> users) 73 protected override void AddAdditionalUsers(string query, List<UserData> users)
75 { 74 {
76 if (query.Contains("@")) // First.Last@foo.com, maybe? 75 if (query.Contains("@")) // First.Last@foo.com, maybe?
77 { 76 {
@@ -131,7 +130,17 @@ namespace OpenSim.Region.CoreModules.Framework.UserManagement
131 } 130 }
132 131
133 UserAgentServiceConnector uasConn = new UserAgentServiceConnector(uriStr); 132 UserAgentServiceConnector uasConn = new UserAgentServiceConnector(uriStr);
134 UUID userID = uasConn.GetUUID(names[0], names[1]); 133
134 UUID userID = UUID.Zero;
135 try
136 {
137 userID = uasConn.GetUUID(names[0], names[1]);
138 }
139 catch (Exception e)
140 {
141 m_log.Debug("[USER MANAGEMENT MODULE]: GetUUID call failed ", e);
142 }
143
135 if (!userID.Equals(UUID.Zero)) 144 if (!userID.Equals(UUID.Zero))
136 { 145 {
137 UserData ud = new UserData(); 146 UserData ud = new UserData();
diff --git a/OpenSim/Region/CoreModules/Framework/UserManagement/Tests/HGUserManagementModuleTests.cs b/OpenSim/Region/CoreModules/Framework/UserManagement/Tests/HGUserManagementModuleTests.cs
new file mode 100644
index 0000000..4e3b7e5
--- /dev/null
+++ b/OpenSim/Region/CoreModules/Framework/UserManagement/Tests/HGUserManagementModuleTests.cs
@@ -0,0 +1,75 @@
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;
29using Nini.Config;
30using NUnit.Framework;
31using OpenMetaverse;
32using OpenSim.Framework;
33using OpenSim.Region.CoreModules.Framework.UserManagement;
34using OpenSim.Tests.Common;
35
36namespace OpenSim.Region.CoreModules.Framework.UserManagement.Tests
37{
38 [TestFixture]
39 public class HGUserManagementModuleTests : OpenSimTestCase
40 {
41 /// <summary>
42 /// Test that a new HG agent (i.e. one without a user account) has their name cached in the UMM upon creation.
43 /// </summary>
44 [Test]
45 public void TestCachedUserNameForNewAgent()
46 {
47 TestHelpers.InMethod();
48// TestHelpers.EnableLogging();
49
50 HGUserManagementModule hgumm = new HGUserManagementModule();
51 UUID userId = TestHelpers.ParseStem("11");
52 string firstName = "Fred";
53 string lastName = "Astaire";
54 string homeUri = "example.com";
55
56 IConfigSource config = new IniConfigSource();
57 config.AddConfig("Modules");
58 config.Configs["Modules"].Set("UserManagementModule", hgumm.Name);
59
60 SceneHelpers sceneHelpers = new SceneHelpers();
61 TestScene scene = sceneHelpers.SetupScene();
62 SceneHelpers.SetupSceneModules(scene, config, hgumm);
63
64 AgentCircuitData acd = SceneHelpers.GenerateAgentData(userId);
65 acd.firstname = firstName;
66 acd.lastname = lastName;
67 acd.ServiceURLs["HomeURI"] = "http://" + homeUri;
68
69 SceneHelpers.AddScenePresence(scene, acd);
70
71 string name = hgumm.GetUserName(userId);
72 Assert.That(name, Is.EqualTo(string.Format("{0}.{1} @{2}", firstName, lastName, homeUri)));
73 }
74 }
75} \ No newline at end of file
diff --git a/OpenSim/Region/CoreModules/Framework/UserManagement/UserManagementModule.cs b/OpenSim/Region/CoreModules/Framework/UserManagement/UserManagementModule.cs
index 77e8b00..7ecbd26 100644
--- a/OpenSim/Region/CoreModules/Framework/UserManagement/UserManagementModule.cs
+++ b/OpenSim/Region/CoreModules/Framework/UserManagement/UserManagementModule.cs
@@ -28,9 +28,11 @@ using System;
28using System.Collections.Generic; 28using System.Collections.Generic;
29using System.IO; 29using System.IO;
30using System.Reflection; 30using System.Reflection;
31using System.Threading;
31 32
32using OpenSim.Framework; 33using OpenSim.Framework;
33using OpenSim.Framework.Console; 34using OpenSim.Framework.Console;
35using OpenSim.Framework.Monitoring;
34using OpenSim.Region.ClientStack.LindenUDP; 36using OpenSim.Region.ClientStack.LindenUDP;
35using OpenSim.Region.Framework; 37using OpenSim.Region.Framework;
36using OpenSim.Region.Framework.Interfaces; 38using OpenSim.Region.Framework.Interfaces;
@@ -44,28 +46,24 @@ using log4net;
44using Nini.Config; 46using Nini.Config;
45using Mono.Addins; 47using Mono.Addins;
46 48
49using DirFindFlags = OpenMetaverse.DirectoryManager.DirFindFlags;
50
47namespace OpenSim.Region.CoreModules.Framework.UserManagement 51namespace OpenSim.Region.CoreModules.Framework.UserManagement
48{ 52{
49 public class UserData
50 {
51 public UUID Id { get; set; }
52 public string FirstName { get; set; }
53 public string LastName { get; set; }
54 public string HomeURL { get; set; }
55 public Dictionary<string, object> ServerURLs { get; set; }
56 }
57
58 [Extension(Path = "/OpenSim/RegionModules", NodeName = "RegionModule", Id = "UserManagementModule")] 53 [Extension(Path = "/OpenSim/RegionModules", NodeName = "RegionModule", Id = "UserManagementModule")]
59 public class UserManagementModule : ISharedRegionModule, IUserManagement 54 public class UserManagementModule : ISharedRegionModule, IUserManagement, IPeople
60 { 55 {
61 private static readonly ILog m_log = LogManager.GetLogger(MethodBase.GetCurrentMethod().DeclaringType); 56 private static readonly ILog m_log = LogManager.GetLogger(MethodBase.GetCurrentMethod().DeclaringType);
62 57
63 protected bool m_Enabled; 58 protected bool m_Enabled;
64 protected List<Scene> m_Scenes = new List<Scene>(); 59 protected List<Scene> m_Scenes = new List<Scene>();
65 60
61 protected IServiceThrottleModule m_ServiceThrottle;
66 // The cache 62 // The cache
67 protected Dictionary<UUID, UserData> m_UserCache = new Dictionary<UUID, UserData>(); 63 protected Dictionary<UUID, UserData> m_UserCache = new Dictionary<UUID, UserData>();
68 64
65 protected bool m_DisplayChangingHomeURI = false;
66
69 #region ISharedRegionModule 67 #region ISharedRegionModule
70 68
71 public void Initialise(IConfigSource config) 69 public void Initialise(IConfigSource config)
@@ -74,9 +72,20 @@ namespace OpenSim.Region.CoreModules.Framework.UserManagement
74 if (umanmod == Name) 72 if (umanmod == Name)
75 { 73 {
76 m_Enabled = true; 74 m_Enabled = true;
77 RegisterConsoleCmds(); 75 Init();
78 m_log.DebugFormat("[USER MANAGEMENT MODULE]: {0} is enabled", Name); 76 m_log.DebugFormat("[USER MANAGEMENT MODULE]: {0} is enabled", Name);
79 } 77 }
78
79 if(!m_Enabled)
80 {
81 return;
82 }
83
84 IConfig userManagementConfig = config.Configs["UserManagement"];
85 if (userManagementConfig == null)
86 return;
87
88 m_DisplayChangingHomeURI = userManagementConfig.GetBoolean("DisplayChangingHomeURI", false);
80 } 89 }
81 90
82 public bool IsSharedModule 91 public bool IsSharedModule
@@ -98,9 +107,13 @@ namespace OpenSim.Region.CoreModules.Framework.UserManagement
98 { 107 {
99 if (m_Enabled) 108 if (m_Enabled)
100 { 109 {
101 m_Scenes.Add(scene); 110 lock (m_Scenes)
111 {
112 m_Scenes.Add(scene);
113 }
102 114
103 scene.RegisterModuleInterface<IUserManagement>(this); 115 scene.RegisterModuleInterface<IUserManagement>(this);
116 scene.RegisterModuleInterface<IPeople>(this);
104 scene.EventManager.OnNewClient += new EventManager.OnNewClientDelegate(EventManager_OnNewClient); 117 scene.EventManager.OnNewClient += new EventManager.OnNewClientDelegate(EventManager_OnNewClient);
105 scene.EventManager.OnPrimsLoaded += new EventManager.PrimsLoaded(EventManager_OnPrimsLoaded); 118 scene.EventManager.OnPrimsLoaded += new EventManager.PrimsLoaded(EventManager_OnPrimsLoaded);
106 } 119 }
@@ -111,12 +124,17 @@ namespace OpenSim.Region.CoreModules.Framework.UserManagement
111 if (m_Enabled) 124 if (m_Enabled)
112 { 125 {
113 scene.UnregisterModuleInterface<IUserManagement>(this); 126 scene.UnregisterModuleInterface<IUserManagement>(this);
114 m_Scenes.Remove(scene); 127 lock (m_Scenes)
128 {
129 m_Scenes.Remove(scene);
130 }
115 } 131 }
116 } 132 }
117 133
118 public void RegionLoaded(Scene s) 134 public void RegionLoaded(Scene s)
119 { 135 {
136 if (m_Enabled && m_ServiceThrottle == null)
137 m_ServiceThrottle = s.RequestModuleInterface<IServiceThrottleModule>();
120 } 138 }
121 139
122 public void PostInitialise() 140 public void PostInitialise()
@@ -125,7 +143,10 @@ namespace OpenSim.Region.CoreModules.Framework.UserManagement
125 143
126 public void Close() 144 public void Close()
127 { 145 {
128 m_Scenes.Clear(); 146 lock (m_Scenes)
147 {
148 m_Scenes.Clear();
149 }
129 150
130 lock (m_UserCache) 151 lock (m_UserCache)
131 m_UserCache.Clear(); 152 m_UserCache.Clear();
@@ -133,7 +154,7 @@ namespace OpenSim.Region.CoreModules.Framework.UserManagement
133 154
134 #endregion ISharedRegionModule 155 #endregion ISharedRegionModule
135 156
136 157
137 #region Event Handlers 158 #region Event Handlers
138 159
139 void EventManager_OnPrimsLoaded(Scene s) 160 void EventManager_OnPrimsLoaded(Scene s)
@@ -143,7 +164,6 @@ namespace OpenSim.Region.CoreModules.Framework.UserManagement
143 s.ForEachSOG(delegate(SceneObjectGroup sog) { CacheCreators(sog); }); 164 s.ForEachSOG(delegate(SceneObjectGroup sog) { CacheCreators(sog); });
144 } 165 }
145 166
146
147 void EventManager_OnNewClient(IClientAPI client) 167 void EventManager_OnNewClient(IClientAPI client)
148 { 168 {
149 client.OnConnectionClosed += new Action<IClientAPI>(HandleConnectionClosed); 169 client.OnConnectionClosed += new Action<IClientAPI>(HandleConnectionClosed);
@@ -157,21 +177,52 @@ namespace OpenSim.Region.CoreModules.Framework.UserManagement
157 client.OnAvatarPickerRequest -= new AvatarPickerRequest(HandleAvatarPickerRequest); 177 client.OnAvatarPickerRequest -= new AvatarPickerRequest(HandleAvatarPickerRequest);
158 } 178 }
159 179
160 void HandleUUIDNameRequest(UUID uuid, IClientAPI remote_client) 180 void HandleUUIDNameRequest(UUID uuid, IClientAPI client)
161 { 181 {
182// m_log.DebugFormat(
183// "[USER MANAGEMENT MODULE]: Handling request for name binding of UUID {0} from {1}",
184// uuid, remote_client.Name);
185
162 if (m_Scenes[0].LibraryService != null && (m_Scenes[0].LibraryService.LibraryRootFolder.Owner == uuid)) 186 if (m_Scenes[0].LibraryService != null && (m_Scenes[0].LibraryService.LibraryRootFolder.Owner == uuid))
163 { 187 {
164 remote_client.SendNameReply(uuid, "Mr", "OpenSim"); 188 client.SendNameReply(uuid, "Mr", "OpenSim");
165 } 189 }
166 else 190 else
167 { 191 {
168 string[] names = GetUserNames(uuid); 192 UserData user;
169 if (names.Length == 2) 193 /* bypass that continuation here when entry is already available */
194 lock (m_UserCache)
170 { 195 {
171 //m_log.DebugFormat("[XXX] HandleUUIDNameRequest {0} is {1} {2}", uuid, names[0], names[1]); 196 if (m_UserCache.TryGetValue(uuid, out user))
172 remote_client.SendNameReply(uuid, names[0], names[1]); 197 {
198 if (!user.IsUnknownUser && user.HasGridUserTried)
199 {
200 client.SendNameReply(uuid, user.FirstName, user.LastName);
201 return;
202 }
203 }
173 } 204 }
174 205
206 // Not found in cache, queue continuation
207 m_ServiceThrottle.Enqueue("name", uuid.ToString(), delegate
208 {
209 //m_log.DebugFormat("[YYY]: Name request {0}", uuid);
210
211 // As least upto September 2013, clients permanently cache UUID -> Name bindings. Some clients
212 // appear to clear this when the user asks it to clear the cache, but others may not.
213 //
214 // So to avoid clients
215 // (particularly Hypergrid clients) permanently binding "Unknown User" to a given UUID, we will
216 // instead drop the request entirely.
217 if (GetUser(uuid, out user))
218 {
219 client.SendNameReply(uuid, user.FirstName, user.LastName);
220 }
221// else
222// m_log.DebugFormat(
223// "[USER MANAGEMENT MODULE]: No bound name for {0} found, ignoring request from {1}",
224// uuid, client.Name);
225 });
175 } 226 }
176 } 227 }
177 228
@@ -181,29 +232,7 @@ namespace OpenSim.Region.CoreModules.Framework.UserManagement
181 232
182 m_log.DebugFormat("[USER MANAGEMENT MODULE]: HandleAvatarPickerRequest for {0}", query); 233 m_log.DebugFormat("[USER MANAGEMENT MODULE]: HandleAvatarPickerRequest for {0}", query);
183 234
184 // searhc the user accounts service 235 List<UserData> users = GetUserData(query, 500, 1);
185 List<UserAccount> accs = m_Scenes[0].UserAccountService.GetUserAccounts(m_Scenes[0].RegionInfo.ScopeID, query);
186
187 List<UserData> users = new List<UserData>();
188 if (accs != null)
189 {
190 foreach (UserAccount acc in accs)
191 {
192 UserData ud = new UserData();
193 ud.FirstName = acc.FirstName;
194 ud.LastName = acc.LastName;
195 ud.Id = acc.PrincipalID;
196 users.Add(ud);
197 }
198 }
199
200 // search the local cache
201 foreach (UserData data in m_UserCache.Values)
202 if (users.Find(delegate(UserData d) { return d.Id == data.Id; }) == null &&
203 (data.FirstName.StartsWith(query) || data.LastName.StartsWith(query)))
204 users.Add(data);
205
206 AddAdditionalUsers(avatarID, query, users);
207 236
208 AvatarPickerReplyPacket replyPacket = (AvatarPickerReplyPacket)PacketPool.Instance.GetPacket(PacketType.AvatarPickerReply); 237 AvatarPickerReplyPacket replyPacket = (AvatarPickerReplyPacket)PacketPool.Instance.GetPacket(PacketType.AvatarPickerReply);
209 // TODO: don't create new blocks if recycling an old packet 238 // TODO: don't create new blocks if recycling an old packet
@@ -249,60 +278,62 @@ namespace OpenSim.Region.CoreModules.Framework.UserManagement
249 client.SendAvatarPickerReply(agent_data, data_args); 278 client.SendAvatarPickerReply(agent_data, data_args);
250 } 279 }
251 280
252 protected virtual void AddAdditionalUsers(UUID avatarID, string query, List<UserData> users) 281 protected virtual void AddAdditionalUsers(string query, List<UserData> users)
253 { 282 {
254 } 283 }
255 284
256 #endregion Event Handlers 285 #endregion Event Handlers
257 286
258 private void CacheCreators(SceneObjectGroup sog) 287 #region IPeople
259 {
260 //m_log.DebugFormat("[USER MANAGEMENT MODULE]: processing {0} {1}; {2}", sog.RootPart.Name, sog.RootPart.CreatorData, sog.RootPart.CreatorIdentification);
261 AddUser(sog.RootPart.CreatorID, sog.RootPart.CreatorData);
262
263 foreach (SceneObjectPart sop in sog.Parts)
264 {
265 AddUser(sop.CreatorID, sop.CreatorData);
266 foreach (TaskInventoryItem item in sop.TaskInventory.Values)
267 AddUser(item.CreatorID, item.CreatorData);
268 }
269 }
270 288
271 private string[] GetUserNames(UUID uuid) 289 public List<UserData> GetUserData(string query, int page_size, int page_number)
272 { 290 {
273 string[] returnstring = new string[2]; 291 // search the user accounts service
292 List<UserAccount> accs = m_Scenes[0].UserAccountService.GetUserAccounts(m_Scenes[0].RegionInfo.ScopeID, query);
274 293
275 lock (m_UserCache) 294 List<UserData> users = new List<UserData>();
295 if (accs != null)
276 { 296 {
277 if (m_UserCache.ContainsKey(uuid)) 297 foreach (UserAccount acc in accs)
278 { 298 {
279 returnstring[0] = m_UserCache[uuid].FirstName; 299 UserData ud = new UserData();
280 returnstring[1] = m_UserCache[uuid].LastName; 300 ud.FirstName = acc.FirstName;
281 return returnstring; 301 ud.LastName = acc.LastName;
302 ud.Id = acc.PrincipalID;
303 ud.HasGridUserTried = true;
304 ud.IsUnknownUser = false;
305 users.Add(ud);
282 } 306 }
283 } 307 }
284 308
285 UserAccount account = m_Scenes[0].UserAccountService.GetUserAccount(UUID.Zero, uuid); 309 // search the local cache
286 310 foreach (UserData data in m_UserCache.Values)
287 if (account != null)
288 { 311 {
289 returnstring[0] = account.FirstName; 312 if (data.Id != UUID.Zero && !data.IsUnknownUser &&
290 returnstring[1] = account.LastName; 313 users.Find(delegate(UserData d) { return d.Id == data.Id; }) == null &&
314 (data.FirstName.ToLower().StartsWith(query.ToLower()) || data.LastName.ToLower().StartsWith(query.ToLower())))
315 users.Add(data);
316 }
291 317
292 UserData user = new UserData(); 318 AddAdditionalUsers(query, users);
293 user.FirstName = account.FirstName;
294 user.LastName = account.LastName;
295 319
296 lock (m_UserCache) 320 return users;
297 m_UserCache[uuid] = user; 321
298 } 322 }
299 else 323
324 #endregion IPeople
325
326 private void CacheCreators(SceneObjectGroup sog)
327 {
328 //m_log.DebugFormat("[USER MANAGEMENT MODULE]: processing {0} {1}; {2}", sog.RootPart.Name, sog.RootPart.CreatorData, sog.RootPart.CreatorIdentification);
329 AddUser(sog.RootPart.CreatorID, sog.RootPart.CreatorData);
330
331 foreach (SceneObjectPart sop in sog.Parts)
300 { 332 {
301 returnstring[0] = "Unknown"; 333 AddUser(sop.CreatorID, sop.CreatorData);
302 returnstring[1] = "User"; 334 foreach (TaskInventoryItem item in sop.TaskInventory.Values)
335 AddUser(item.CreatorID, item.CreatorData);
303 } 336 }
304
305 return returnstring;
306 } 337 }
307 338
308 #region IUserManagement 339 #region IUserManagement
@@ -338,55 +369,56 @@ namespace OpenSim.Region.CoreModules.Framework.UserManagement
338 369
339 public string GetUserName(UUID uuid) 370 public string GetUserName(UUID uuid)
340 { 371 {
341 string[] names = GetUserNames(uuid); 372 UserData user;
342 if (names.Length == 2) 373 GetUser(uuid, out user);
343 { 374 return user.FirstName + " " + user.LastName;
344 string firstname = names[0];
345 string lastname = names[1];
346
347 return firstname + " " + lastname;
348
349 }
350 return "(hippos)";
351 } 375 }
352 376
353 public string GetUserHomeURL(UUID userID) 377 public string GetUserHomeURL(UUID userID)
354 { 378 {
355 lock (m_UserCache) 379 UserData user;
380 if(GetUser(userID, out user))
356 { 381 {
357 if (m_UserCache.ContainsKey(userID)) 382 return user.HomeURL;
358 return m_UserCache[userID].HomeURL;
359 } 383 }
360
361 return string.Empty; 384 return string.Empty;
362 } 385 }
363 386
364 public string GetUserServerURL(UUID userID, string serverType) 387 public string GetUserServerURL(UUID userID, string serverType)
365 { 388 {
366 UserData userdata; 389 UserData userdata;
367 lock (m_UserCache) 390 if(!GetUser(userID, out userdata))
368 m_UserCache.TryGetValue(userID, out userdata); 391 {
392 return string.Empty;
393 }
394
395 if (userdata.ServerURLs != null && userdata.ServerURLs.ContainsKey(serverType) && userdata.ServerURLs[serverType] != null)
396 {
397 return userdata.ServerURLs[serverType].ToString();
398 }
369 399
370 if (userdata != null) 400 if (!string.IsNullOrEmpty(userdata.HomeURL))
371 { 401 {
372// m_log.DebugFormat("[USER MANAGEMENT MODULE]: Requested url type {0} for {1}", serverType, userID); 402// m_log.DebugFormat("[USER MANAGEMENT MODULE]: Requested url type {0} for {1}", serverType, userID);
373 403
374 if (userdata.ServerURLs != null && userdata.ServerURLs.ContainsKey(serverType) && userdata.ServerURLs[serverType] != null) 404 UserAgentServiceConnector uConn = new UserAgentServiceConnector(userdata.HomeURL);
405 try
375 { 406 {
376 return userdata.ServerURLs[serverType].ToString(); 407 userdata.ServerURLs = uConn.GetServerURLs(userID);
377 } 408 }
378 409 catch(System.Net.WebException e)
379 if (userdata.HomeURL != null && userdata.HomeURL != string.Empty)
380 { 410 {
381 //m_log.DebugFormat( 411 m_log.DebugFormat("[USER MANAGEMENT MODULE]: GetServerURLs call failed {0}", e.Message);
382 // "[USER MANAGEMENT MODULE]: Did not find url type {0} so requesting urls from '{1}' for {2}", 412 userdata.ServerURLs = new Dictionary<string, object>();
383 // serverType, userdata.HomeURL, userID);
384
385 UserAgentServiceConnector uConn = new UserAgentServiceConnector(userdata.HomeURL);
386 userdata.ServerURLs = uConn.GetServerURLs(userID);
387 if (userdata.ServerURLs != null && userdata.ServerURLs.ContainsKey(serverType) && userdata.ServerURLs[serverType] != null)
388 return userdata.ServerURLs[serverType].ToString();
389 } 413 }
414 catch (Exception e)
415 {
416 m_log.Debug("[USER MANAGEMENT MODULE]: GetServerURLs call failed ", e);
417 userdata.ServerURLs = new Dictionary<string, object>();
418 }
419
420 if (userdata.ServerURLs != null && userdata.ServerURLs.ContainsKey(serverType) && userdata.ServerURLs[serverType] != null)
421 return userdata.ServerURLs[serverType].ToString();
390 } 422 }
391 423
392 return string.Empty; 424 return string.Empty;
@@ -394,13 +426,15 @@ namespace OpenSim.Region.CoreModules.Framework.UserManagement
394 426
395 public string GetUserUUI(UUID userID) 427 public string GetUserUUI(UUID userID)
396 { 428 {
397 UserAccount account = m_Scenes[0].UserAccountService.GetUserAccount(m_Scenes[0].RegionInfo.ScopeID, userID); 429 string uui;
398 if (account != null) 430 GetUserUUI(userID, out uui);
399 return userID.ToString(); 431 return uui;
432 }
400 433
434 public bool GetUserUUI(UUID userID, out string uui)
435 {
401 UserData ud; 436 UserData ud;
402 lock (m_UserCache) 437 bool result = GetUser(userID, out ud);
403 m_UserCache.TryGetValue(userID, out ud);
404 438
405 if (ud != null) 439 if (ud != null)
406 { 440 {
@@ -414,121 +448,251 @@ namespace OpenSim.Region.CoreModules.Framework.UserManagement
414 first = parts[0]; 448 first = parts[0];
415 last = parts[1]; 449 last = parts[1];
416 } 450 }
417 return userID + ";" + homeURL + ";" + first + " " + last; 451 uui = userID + ";" + homeURL + ";" + first + " " + last;
418 } 452 }
419 } 453 }
420 454
421 return userID.ToString(); 455 uui = userID.ToString();
456 return result;
422 } 457 }
423 458
424 public void AddUser(UUID uuid, string first, string last) 459 #region Cache Management
460 public bool GetUser(UUID uuid, out UserData userdata)
425 { 461 {
426 lock (m_UserCache) 462 lock (m_UserCache)
427 { 463 {
428 if (m_UserCache.ContainsKey(uuid)) 464 if (m_UserCache.TryGetValue(uuid, out userdata))
429 return; 465 {
466 if (userdata.HasGridUserTried)
467 {
468 return true;
469 }
470 }
471 else
472 {
473 userdata = new UserData();
474 userdata.HasGridUserTried = false;
475 userdata.Id = uuid;
476 userdata.FirstName = "Unknown";
477 userdata.LastName = "UserUMMAU42";
478 userdata.HomeURL = string.Empty;
479 userdata.IsUnknownUser = true;
480 userdata.HasGridUserTried = false;
481 }
482 }
483
484 /* BEGIN: do not wrap this code in any lock here
485 * There are HTTP calls in here.
486 */
487 if (!userdata.HasGridUserTried)
488 {
489 /* rewrite here */
490 UserAccount account = m_Scenes[0].UserAccountService.GetUserAccount(m_Scenes[0].RegionInfo.ScopeID, uuid);
491 if (account != null)
492 {
493 userdata.FirstName = account.FirstName;
494 userdata.LastName = account.LastName;
495 userdata.HomeURL = string.Empty;
496 userdata.IsUnknownUser = false;
497 userdata.HasGridUserTried = true;
498 }
430 } 499 }
431 500
432 UserData user = new UserData(); 501 if (!userdata.HasGridUserTried)
433 user.Id = uuid; 502 {
434 user.FirstName = first; 503 GridUserInfo uInfo = null;
435 user.LastName = last; 504 if (null != m_Scenes[0].GridUserService)
505 {
506 uInfo = m_Scenes[0].GridUserService.GetGridUserInfo(uuid.ToString());
507 }
508 if (uInfo != null)
509 {
510 string url, first, last, tmp;
511 UUID u;
512 if(uInfo.UserID.Length <= 36)
513 {
514 /* not a UUI */
515 }
516 else if (Util.ParseUniversalUserIdentifier(uInfo.UserID, out u, out url, out first, out last, out tmp))
517 {
518 if (url != string.Empty)
519 {
520 userdata.FirstName = first.Replace(" ", ".") + "." + last.Replace(" ", ".");
521 userdata.HomeURL = url;
522 try
523 {
524 userdata.LastName = "@" + new Uri(url).Authority;
525 userdata.IsUnknownUser = false;
526 }
527 catch
528 {
529 userdata.LastName = "@unknown";
530 }
531 userdata.HasGridUserTried = true;
532 }
533 }
534 else
535 m_log.DebugFormat("[USER MANAGEMENT MODULE]: Unable to parse UUI {0}", uInfo.UserID);
536 }
537 }
538 /* END: do not wrap this code in any lock here */
436 539
437 AddUserInternal(user); 540 lock (m_UserCache)
541 {
542 m_UserCache[uuid] = userdata;
543 }
544 return !userdata.IsUnknownUser;
438 } 545 }
439 546
440 public void AddUser(UUID uuid, string first, string last, string homeURL) 547 public void AddUser(UUID uuid, string first, string last)
441 { 548 {
442 //m_log.DebugFormat("[USER MANAGEMENT MODULE]: Adding user with id {0}, first {1}, last {2}, url {3}", uuid, first, last, homeURL); 549 lock(m_UserCache)
443 if (homeURL == string.Empty) 550 {
444 return; 551 if(!m_UserCache.ContainsKey(uuid))
445 552 {
446 AddUser(uuid, homeURL + ";" + first + " " + last); 553 UserData user = new UserData();
554 user.Id = uuid;
555 user.FirstName = first;
556 user.LastName = last;
557 user.IsUnknownUser = false;
558 user.HasGridUserTried = false;
559 m_UserCache.Add(uuid, user);
560 }
561 }
447 } 562 }
448 563
449 public void AddUser (UUID id, string creatorData) 564 public void AddUser(UUID uuid, string first, string last, string homeURL)
450 { 565 {
451 //m_log.DebugFormat("[USER MANAGEMENT MODULE]: Adding user with id {0}, creatorData {1}", id, creatorData); 566 //m_log.DebugFormat("[USER MANAGEMENT MODULE]: Adding user with id {0}, first {1}, last {2}, url {3}", uuid, first, last, homeURL);
452 567
453 UserData oldUser; 568 UserData oldUser;
454 //lock the whole block - prevent concurrent update
455 lock (m_UserCache) 569 lock (m_UserCache)
456 { 570 {
457 m_UserCache.TryGetValue (id, out oldUser); 571 if (m_UserCache.TryGetValue(uuid, out oldUser))
458 if (oldUser != null)
459 { 572 {
460 if (creatorData == null || creatorData == String.Empty) 573 if (!oldUser.IsUnknownUser)
461 { 574 {
462 //ignore updates without creator data 575 if (homeURL != oldUser.HomeURL && m_DisplayChangingHomeURI)
576 {
577 m_log.DebugFormat("[USER MANAGEMENT MODULE]: Different HomeURI for {0} {1} ({2}): {3} and {4}",
578 first, last, uuid.ToString(), homeURL, oldUser.HomeURL);
579 }
580 /* no update needed */
463 return; 581 return;
464 } 582 }
465 //try update unknown users 583 }
466 //and creator's home URL's 584 else if(!m_UserCache.ContainsKey(uuid))
467 if ((oldUser.FirstName == "Unknown" && !creatorData.Contains ("Unknown")) || (oldUser.HomeURL != null && !creatorData.StartsWith (oldUser.HomeURL))) 585 {
586 oldUser = new UserData();
587 oldUser.HasGridUserTried = false;
588 oldUser.IsUnknownUser = false;
589 if (homeURL != string.Empty)
468 { 590 {
469 m_UserCache.Remove (id); 591 oldUser.FirstName = first.Replace(" ", ".") + "." + last.Replace(" ", ".");
470// m_log.DebugFormat("[USER MANAGEMENT MODULE]: Re-adding user with id {0}, creatorData [{1}] and old HomeURL {2}", id, creatorData,oldUser.HomeURL); 592 try
593 {
594 oldUser.LastName = "@" + new Uri(homeURL).Authority;
595 oldUser.IsUnknownUser = false;
596 }
597 catch
598 {
599 oldUser.LastName = "@unknown";
600 }
471 } 601 }
472 else 602 else
473 { 603 {
474 //we have already a valid user within the cache 604 oldUser.FirstName = first;
475 return; 605 oldUser.LastName = last;
476 } 606 }
607 oldUser.HomeURL = homeURL;
608 oldUser.Id = uuid;
609 m_UserCache.Add(uuid, oldUser);
477 } 610 }
611 }
612 }
478 613
479 UserAccount account = m_Scenes[0].UserAccountService.GetUserAccount (m_Scenes [0].RegionInfo.ScopeID, id); 614 public void AddUser(UUID id, string creatorData)
615 {
616 // m_log.InfoFormat("[USER MANAGEMENT MODULE]: Adding user with id {0}, creatorData {1}", id, creatorData);
480 617
481 if (account != null) 618 if(string.IsNullOrEmpty(creatorData))
619 {
620 AddUser(id, string.Empty, string.Empty, string.Empty);
621 }
622 else
623 {
624 string homeURL;
625 string firstname = string.Empty;
626 string lastname = string.Empty;
627
628 //creatorData = <endpoint>;<name>
629
630 string[] parts = creatorData.Split(';');
631 if(parts.Length > 1)
482 { 632 {
483 AddUser (id, account.FirstName, account.LastName); 633 string[] nameparts = parts[1].Split(' ');
634 firstname = nameparts[0];
635 for(int xi = 1; xi < nameparts.Length; ++xi)
636 {
637 if(xi != 1)
638 {
639 lastname += " ";
640 }
641 lastname += nameparts[xi];
642 }
484 } 643 }
485 else 644 else
486 { 645 {
487 UserData user = new UserData (); 646 firstname = "Unknown";
488 user.Id = id; 647 lastname = "UserUMMAU5";
489 648 }
490 if (creatorData != null && creatorData != string.Empty) 649 if (parts.Length >= 1)
650 {
651 homeURL = parts[0];
652 if(Uri.IsWellFormedUriString(homeURL, UriKind.Absolute))
653 {
654 AddUser(id, firstname, lastname, homeURL);
655 }
656 else
491 { 657 {
492 //creatorData = <endpoint>;<name> 658 m_log.DebugFormat("[SCENE]: Unable to parse Uri {0} for CreatorID {1}", parts[0], creatorData);
493 659
494 string[] parts = creatorData.Split (';'); 660 lock (m_UserCache)
495 if (parts.Length >= 1)
496 { 661 {
497 user.HomeURL = parts [0]; 662 if(!m_UserCache.ContainsKey(id))
498 try
499 {
500 Uri uri = new Uri (parts [0]);
501 user.LastName = "@" + uri.Authority;
502 }
503 catch (UriFormatException)
504 { 663 {
505 m_log.DebugFormat ("[SCENE]: Unable to parse Uri {0}", parts [0]); 664 UserData newUser = new UserData();
506 user.LastName = "@unknown"; 665 newUser.Id = id;
666 newUser.FirstName = firstname + "." + lastname.Replace(' ', '.');
667 newUser.LastName = "@unknown";
668 newUser.HomeURL = string.Empty;
669 newUser.HasGridUserTried = false;
670 newUser.IsUnknownUser = true; /* we mark those users as Unknown user so a re-retrieve may be activated */
671 m_UserCache.Add(id, newUser);
507 } 672 }
508 } 673 }
509 if (parts.Length >= 2)
510 user.FirstName = parts [1].Replace (' ', '.');
511 } 674 }
512 else 675 }
676 else
677 {
678 lock(m_UserCache)
513 { 679 {
514 user.FirstName = "Unknown"; 680 if(!m_UserCache.ContainsKey(id))
515 user.LastName = "User"; 681 {
682 UserData newUser = new UserData();
683 newUser.Id = id;
684 newUser.FirstName = "Unknown";
685 newUser.LastName = "UserUMMAU4";
686 newUser.HomeURL = string.Empty;
687 newUser.IsUnknownUser = true;
688 newUser.HasGridUserTried = false;
689 m_UserCache.Add(id, newUser);
690 }
516 } 691 }
517
518 AddUserInternal (user);
519 } 692 }
520 } 693 }
521 } 694 }
522 695 #endregion
523 void AddUserInternal(UserData user)
524 {
525 lock (m_UserCache)
526 m_UserCache[user.Id] = user;
527
528 //m_log.DebugFormat(
529 // "[USER MANAGEMENT MODULE]: Added user {0} {1} {2} {3}",
530 // user.Id, user.FirstName, user.LastName, user.HomeURL);
531 }
532 696
533 public bool IsLocalGridUser(UUID uuid) 697 public bool IsLocalGridUser(UUID uuid)
534 { 698 {
@@ -541,36 +705,95 @@ namespace OpenSim.Region.CoreModules.Framework.UserManagement
541 705
542 #endregion IUserManagement 706 #endregion IUserManagement
543 707
708 protected void Init()
709 {
710 AddUser(UUID.Zero, "Unknown", "User");
711 RegisterConsoleCmds();
712 }
713
544 protected void RegisterConsoleCmds() 714 protected void RegisterConsoleCmds()
545 { 715 {
546 MainConsole.Instance.Commands.AddCommand("Users", true, 716 MainConsole.Instance.Commands.AddCommand("Users", true,
717 "show name",
718 "show name <uuid>",
719 "Show the bindings between a single user UUID and a user name",
720 String.Empty,
721 HandleShowUser);
722
723 MainConsole.Instance.Commands.AddCommand("Users", true,
547 "show names", 724 "show names",
548 "show names", 725 "show names",
549 "Show the bindings between user UUIDs and user names", 726 "Show the bindings between user UUIDs and user names",
550 String.Empty, 727 String.Empty,
551 HandleShowUsers); 728 HandleShowUsers);
729
730 MainConsole.Instance.Commands.AddCommand("Users", true,
731 "reset user cache",
732 "reset user cache",
733 "reset user cache to allow changed settings to be applied",
734 String.Empty,
735 HandleResetUserCache);
552 } 736 }
553 737
554 private void HandleShowUsers(string module, string[] cmd) 738 private void HandleResetUserCache(string module, string[] cmd)
555 { 739 {
556 lock (m_UserCache) 740 lock(m_UserCache)
557 { 741 {
558 if (m_UserCache.Count == 0) 742 m_UserCache.Clear();
559 { 743 }
560 MainConsole.Instance.Output("No users found"); 744 }
561 return; 745
562 } 746 private void HandleShowUser(string module, string[] cmd)
563 747 {
564 MainConsole.Instance.Output("UUID User Name"); 748 if (cmd.Length < 3)
565 MainConsole.Instance.Output("-----------------------------------------------------------------------------"); 749 {
566 foreach (KeyValuePair<UUID, UserData> kvp in m_UserCache) 750 MainConsole.Instance.OutputFormat("Usage: show name <uuid>");
567 {
568 MainConsole.Instance.Output(String.Format("{0} {1} {2} ({3})",
569 kvp.Key, kvp.Value.FirstName, kvp.Value.LastName, kvp.Value.HomeURL));
570 }
571
572 return; 751 return;
573 } 752 }
753
754 UUID userId;
755 if (!ConsoleUtil.TryParseConsoleUuid(MainConsole.Instance, cmd[2], out userId))
756 return;
757
758 UserData ud;
759
760 if(!GetUser(userId, out ud))
761 {
762 MainConsole.Instance.OutputFormat("No name known for user with id {0}", userId);
763 return;
764 }
765
766 ConsoleDisplayTable cdt = new ConsoleDisplayTable();
767 cdt.AddColumn("UUID", 36);
768 cdt.AddColumn("Name", 30);
769 cdt.AddColumn("HomeURL", 40);
770 cdt.AddRow(userId, string.Format("{0} {1}", ud.FirstName, ud.LastName), ud.HomeURL);
771
772 MainConsole.Instance.Output(cdt.ToString());
574 } 773 }
774
775 private void HandleShowUsers(string module, string[] cmd)
776 {
777 ConsoleDisplayTable cdt = new ConsoleDisplayTable();
778 cdt.AddColumn("UUID", 36);
779 cdt.AddColumn("Name", 30);
780 cdt.AddColumn("HomeURL", 40);
781 cdt.AddColumn("Checked", 10);
782
783 Dictionary<UUID, UserData> copyDict;
784 lock(m_UserCache)
785 {
786 copyDict = new Dictionary<UUID, UserData>(m_UserCache);
787 }
788
789 foreach(KeyValuePair<UUID, UserData> kvp in copyDict)
790 {
791 cdt.AddRow(kvp.Key, string.Format("{0} {1}", kvp.Value.FirstName, kvp.Value.LastName), kvp.Value.HomeURL, kvp.Value.HasGridUserTried ? "yes" : "no");
792 }
793
794 MainConsole.Instance.Output(cdt.ToString());
795 }
796
575 } 797 }
576} \ No newline at end of file 798
799}