aboutsummaryrefslogtreecommitdiffstatshomepage
path: root/OpenSim/Server/Handlers/Hypergrid/HGFriendsServerPostHandler.cs
diff options
context:
space:
mode:
Diffstat (limited to 'OpenSim/Server/Handlers/Hypergrid/HGFriendsServerPostHandler.cs')
-rw-r--r--OpenSim/Server/Handlers/Hypergrid/HGFriendsServerPostHandler.cs323
1 files changed, 323 insertions, 0 deletions
diff --git a/OpenSim/Server/Handlers/Hypergrid/HGFriendsServerPostHandler.cs b/OpenSim/Server/Handlers/Hypergrid/HGFriendsServerPostHandler.cs
new file mode 100644
index 0000000..841811e
--- /dev/null
+++ b/OpenSim/Server/Handlers/Hypergrid/HGFriendsServerPostHandler.cs
@@ -0,0 +1,323 @@
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 Nini.Config;
29using log4net;
30using System;
31using System.Reflection;
32using System.IO;
33using System.Net;
34using System.Text;
35using System.Text.RegularExpressions;
36using System.Xml;
37using System.Xml.Serialization;
38using System.Collections.Generic;
39using OpenSim.Server.Base;
40using OpenSim.Services.Interfaces;
41using FriendInfo = OpenSim.Services.Interfaces.FriendInfo;
42using OpenSim.Framework;
43using OpenSim.Framework.Servers.HttpServer;
44using OpenMetaverse;
45
46namespace OpenSim.Server.Handlers.Hypergrid
47{
48 public class HGFriendsServerPostHandler : BaseStreamHandler
49 {
50 private static readonly ILog m_log = LogManager.GetLogger(MethodBase.GetCurrentMethod().DeclaringType);
51
52 private IFriendsService m_FriendsService;
53 private IUserAgentService m_UserAgentService;
54
55 public HGFriendsServerPostHandler(IFriendsService service, IUserAgentService uservice) :
56 base("POST", "/hgfriends")
57 {
58 m_FriendsService = service;
59 m_UserAgentService = uservice;
60 m_log.DebugFormat("[HGFRIENDS HANDLER]: HGFriendsServerPostHandler is On");
61 }
62
63 public override byte[] Handle(string path, Stream requestData,
64 OSHttpRequest httpRequest, OSHttpResponse httpResponse)
65 {
66 StreamReader sr = new StreamReader(requestData);
67 string body = sr.ReadToEnd();
68 sr.Close();
69 body = body.Trim();
70
71 //m_log.DebugFormat("[XXX]: query String: {0}", body);
72
73 try
74 {
75 Dictionary<string, object> request =
76 ServerUtils.ParseQueryString(body);
77
78 if (!request.ContainsKey("METHOD"))
79 return FailureResult();
80
81 string method = request["METHOD"].ToString();
82
83 switch (method)
84 {
85 case "getfriendperms":
86 return GetFriendPerms(request);
87
88 case "newfriendship":
89 return NewFriendship(request);
90
91 case "deletefriendship":
92 return DeleteFriendship(request);
93 }
94 m_log.DebugFormat("[HGFRIENDS HANDLER]: unknown method {0} request {1}", method.Length, method);
95 }
96 catch (Exception e)
97 {
98 m_log.DebugFormat("[HGFRIENDS HANDLER]: Exception {0}", e);
99 }
100
101 return FailureResult();
102
103 }
104
105 #region Method-specific handlers
106
107 byte[] GetFriendPerms(Dictionary<string, object> request)
108 {
109 if (!VerifyServiceKey(request))
110 return FailureResult();
111
112 UUID principalID = UUID.Zero;
113 if (request.ContainsKey("PRINCIPALID"))
114 UUID.TryParse(request["PRINCIPALID"].ToString(), out principalID);
115 else
116 {
117 m_log.WarnFormat("[HGFRIENDS HANDLER]: no principalID in request to get friend perms");
118 return FailureResult();
119 }
120
121 UUID friendID = UUID.Zero;
122 if (request.ContainsKey("FRIENDID"))
123 UUID.TryParse(request["FRIENDID"].ToString(), out friendID);
124 else
125 {
126 m_log.WarnFormat("[HGFRIENDS HANDLER]: no friendID in request to get friend perms");
127 return FailureResult();
128 }
129
130 string perms = "0";
131 FriendInfo[] friendsInfo = m_FriendsService.GetFriends(principalID);
132 foreach (FriendInfo finfo in friendsInfo)
133 {
134 if (finfo.Friend.StartsWith(friendID.ToString()))
135 return SuccessResult(finfo.TheirFlags.ToString());
136 }
137
138 return FailureResult("Friend not found");
139 }
140
141 byte[] NewFriendship(Dictionary<string, object> request)
142 {
143 m_log.DebugFormat("[XXX] 1");
144 if (!VerifyServiceKey(request))
145 return FailureResult();
146
147 m_log.DebugFormat("[XXX] 2");
148 // OK, can proceed
149 FriendInfo friend = new FriendInfo(request);
150 UUID friendID;
151 string tmp = string.Empty;
152 m_log.DebugFormat("[XXX] 3");
153 if (!Util.ParseUniversalUserIdentifier(friend.Friend, out friendID, out tmp, out tmp, out tmp, out tmp))
154 return FailureResult();
155
156
157 m_log.DebugFormat("[HGFRIENDS HANDLER]: New friendship {0} {1}", friend.PrincipalID, friend.Friend);
158
159 // If the friendship already exists, return fail
160 FriendInfo[] finfos = m_FriendsService.GetFriends(friend.PrincipalID);
161 foreach (FriendInfo finfo in finfos)
162 if (finfo.Friend.StartsWith(friendID.ToString()))
163 return FailureResult();
164
165 // the user needs to confirm when he gets home
166 bool success = m_FriendsService.StoreFriend(friend.PrincipalID.ToString(), friend.Friend, 0);
167
168 if (success)
169 return SuccessResult();
170 else
171 return FailureResult();
172 }
173
174 byte[] DeleteFriendship(Dictionary<string, object> request)
175 {
176 FriendInfo friend = new FriendInfo(request);
177 string secret = string.Empty;
178 if (request.ContainsKey("SECRET"))
179 secret = request["SECRET"].ToString();
180
181 if (secret == string.Empty)
182 return FailureResult();
183
184 FriendInfo[] finfos = m_FriendsService.GetFriends(friend.PrincipalID);
185 foreach (FriendInfo finfo in finfos)
186 {
187 // We check the secret here
188 if (finfo.Friend.StartsWith(friend.Friend) && finfo.Friend.EndsWith(secret))
189 {
190 m_log.DebugFormat("[HGFRIENDS HANDLER]: Delete friendship {0} {1}", friend.PrincipalID, friend.Friend);
191 m_FriendsService.Delete(friend.PrincipalID, finfo.Friend);
192 m_FriendsService.Delete(finfo.Friend, friend.PrincipalID.ToString());
193
194 return SuccessResult();
195 }
196 }
197
198 return FailureResult();
199 }
200
201 #endregion
202
203 #region Misc
204
205 private bool VerifyServiceKey(Dictionary<string, object> request)
206 {
207 if (!request.ContainsKey("KEY") || !request.ContainsKey("SESSIONID"))
208 {
209 m_log.WarnFormat("[HGFRIENDS HANDLER]: ignoring request without Key or SessionID");
210 return false;
211 }
212
213 string serviceKey = request["KEY"].ToString();
214 string sessionStr = request["SESSIONID"].ToString();
215 UUID sessionID;
216 UUID.TryParse(sessionStr, out sessionID);
217
218 if (!m_UserAgentService.VerifyAgent(sessionID, serviceKey))
219 {
220 m_log.WarnFormat("[HGFRIENDS HANDLER]: Key {0} for session {1} did not match existing key. Ignoring request", serviceKey, sessionID);
221 return false;
222 }
223
224 m_log.DebugFormat("[XXX] Verification ok");
225 return true;
226 }
227
228 private byte[] SuccessResult()
229 {
230 XmlDocument doc = new XmlDocument();
231
232 XmlNode xmlnode = doc.CreateNode(XmlNodeType.XmlDeclaration,
233 "", "");
234
235 doc.AppendChild(xmlnode);
236
237 XmlElement rootElement = doc.CreateElement("", "ServerResponse",
238 "");
239
240 doc.AppendChild(rootElement);
241
242 XmlElement result = doc.CreateElement("", "Result", "");
243 result.AppendChild(doc.CreateTextNode("Success"));
244
245 rootElement.AppendChild(result);
246
247 return DocToBytes(doc);
248 }
249
250 private byte[] SuccessResult(string value)
251 {
252 XmlDocument doc = new XmlDocument();
253
254 XmlNode xmlnode = doc.CreateNode(XmlNodeType.XmlDeclaration,
255 "", "");
256
257 doc.AppendChild(xmlnode);
258
259 XmlElement rootElement = doc.CreateElement("", "ServerResponse",
260 "");
261
262 doc.AppendChild(rootElement);
263
264 XmlElement result = doc.CreateElement("", "Result", "");
265 result.AppendChild(doc.CreateTextNode("Success"));
266
267 rootElement.AppendChild(result);
268
269 XmlElement message = doc.CreateElement("", "Value", "");
270 message.AppendChild(doc.CreateTextNode(value));
271
272 rootElement.AppendChild(message);
273
274 return DocToBytes(doc);
275 }
276
277
278 private byte[] FailureResult()
279 {
280 return FailureResult(String.Empty);
281 }
282
283 private byte[] FailureResult(string msg)
284 {
285 XmlDocument doc = new XmlDocument();
286
287 XmlNode xmlnode = doc.CreateNode(XmlNodeType.XmlDeclaration,
288 "", "");
289
290 doc.AppendChild(xmlnode);
291
292 XmlElement rootElement = doc.CreateElement("", "ServerResponse",
293 "");
294
295 doc.AppendChild(rootElement);
296
297 XmlElement result = doc.CreateElement("", "Result", "");
298 result.AppendChild(doc.CreateTextNode("Failure"));
299
300 rootElement.AppendChild(result);
301
302 XmlElement message = doc.CreateElement("", "Message", "");
303 message.AppendChild(doc.CreateTextNode(msg));
304
305 rootElement.AppendChild(message);
306
307 return DocToBytes(doc);
308 }
309
310 private byte[] DocToBytes(XmlDocument doc)
311 {
312 MemoryStream ms = new MemoryStream();
313 XmlTextWriter xw = new XmlTextWriter(ms, null);
314 xw.Formatting = Formatting.Indented;
315 doc.WriteTo(xw);
316 xw.Flush();
317
318 return ms.ToArray();
319 }
320
321 #endregion
322 }
323}