* Added a hashtable based HTTP processor in preparation of the web_login_key
* Added the web_login_key to the users table * Added happy configurable http error message pages * This update is large enough to have 'awe' value.. so backup your users or weep. * Not tested on MSSQL, even though I added code to update the tables!afrisby
parent
bafdac7874
commit
e1aa83e965
|
@ -95,6 +95,22 @@ namespace OpenSim.Framework.Data.MSSQL
|
||||||
MainLog.Instance.Verbose("DATASTORE", "MSSQL Database doesn't exist... creating");
|
MainLog.Instance.Verbose("DATASTORE", "MSSQL Database doesn't exist... creating");
|
||||||
InitDB(conn);
|
InitDB(conn);
|
||||||
}
|
}
|
||||||
|
cmd = Query("select top 1 webLoginKey from users", new Dictionary<string, string>());
|
||||||
|
try
|
||||||
|
{
|
||||||
|
conn.Open();
|
||||||
|
cmd.ExecuteNonQuery();
|
||||||
|
cmd.Dispose();
|
||||||
|
conn.Close();
|
||||||
|
}
|
||||||
|
catch (Exception)
|
||||||
|
{
|
||||||
|
conn.Open();
|
||||||
|
cmd = Query("alter table users add column [webLoginKey] varchar(36) default NULL", new Dictionary<string, string>());
|
||||||
|
cmd.ExecuteNonQuery();
|
||||||
|
cmd.Dispose();
|
||||||
|
conn.Close();
|
||||||
|
}
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -380,6 +396,7 @@ namespace OpenSim.Framework.Data.MSSQL
|
||||||
|
|
||||||
retval.profileImage = new LLUUID((string) reader["profileImage"]);
|
retval.profileImage = new LLUUID((string) reader["profileImage"]);
|
||||||
retval.profileFirstImage = new LLUUID((string) reader["profileFirstImage"]);
|
retval.profileFirstImage = new LLUUID((string) reader["profileFirstImage"]);
|
||||||
|
retval.webLoginKey = new LLUUID((string)reader["webLoginKey"]);
|
||||||
}
|
}
|
||||||
else
|
else
|
||||||
{
|
{
|
||||||
|
@ -595,7 +612,7 @@ namespace OpenSim.Framework.Data.MSSQL
|
||||||
float homeLookAtX, float homeLookAtY, float homeLookAtZ, int created, int lastlogin,
|
float homeLookAtX, float homeLookAtY, float homeLookAtZ, int created, int lastlogin,
|
||||||
string inventoryURI, string assetURI, uint canDoMask, uint wantDoMask,
|
string inventoryURI, string assetURI, uint canDoMask, uint wantDoMask,
|
||||||
string aboutText, string firstText,
|
string aboutText, string firstText,
|
||||||
LLUUID profileImage, LLUUID firstImage)
|
LLUUID profileImage, LLUUID firstImage, LLUUID webLoginKey)
|
||||||
{
|
{
|
||||||
string sql = "INSERT INTO users ";
|
string sql = "INSERT INTO users ";
|
||||||
sql += "([UUID], [username], [lastname], [passwordHash], [passwordSalt], [homeRegion], ";
|
sql += "([UUID], [username], [lastname], [passwordHash], [passwordSalt], [homeRegion], ";
|
||||||
|
@ -603,14 +620,14 @@ namespace OpenSim.Framework.Data.MSSQL
|
||||||
"[homeLocationX], [homeLocationY], [homeLocationZ], [homeLookAtX], [homeLookAtY], [homeLookAtZ], [created], ";
|
"[homeLocationX], [homeLocationY], [homeLocationZ], [homeLookAtX], [homeLookAtY], [homeLookAtZ], [created], ";
|
||||||
sql +=
|
sql +=
|
||||||
"[lastLogin], [userInventoryURI], [userAssetURI], [profileCanDoMask], [profileWantDoMask], [profileAboutText], ";
|
"[lastLogin], [userInventoryURI], [userAssetURI], [profileCanDoMask], [profileWantDoMask], [profileAboutText], ";
|
||||||
sql += "[profileFirstText], [profileImage], [profileFirstImage]) VALUES ";
|
sql += "[profileFirstText], [profileImage], [profileFirstImage], [webLoginKey]) VALUES ";
|
||||||
|
|
||||||
sql += "(@UUID, @username, @lastname, @passwordHash, @passwordSalt, @homeRegion, ";
|
sql += "(@UUID, @username, @lastname, @passwordHash, @passwordSalt, @homeRegion, ";
|
||||||
sql +=
|
sql +=
|
||||||
"@homeLocationX, @homeLocationY, @homeLocationZ, @homeLookAtX, @homeLookAtY, @homeLookAtZ, @created, ";
|
"@homeLocationX, @homeLocationY, @homeLocationZ, @homeLookAtX, @homeLookAtY, @homeLookAtZ, @created, ";
|
||||||
sql +=
|
sql +=
|
||||||
"@lastLogin, @userInventoryURI, @userAssetURI, @profileCanDoMask, @profileWantDoMask, @profileAboutText, ";
|
"@lastLogin, @userInventoryURI, @userAssetURI, @profileCanDoMask, @profileWantDoMask, @profileAboutText, ";
|
||||||
sql += "@profileFirstText, @profileImage, @profileFirstImage);";
|
sql += "@profileFirstText, @profileImage, @profileFirstImage, @webLoginKey);";
|
||||||
|
|
||||||
Dictionary<string, string> parameters = new Dictionary<string, string>();
|
Dictionary<string, string> parameters = new Dictionary<string, string>();
|
||||||
parameters["UUID"] = uuid.ToString();
|
parameters["UUID"] = uuid.ToString();
|
||||||
|
@ -635,6 +652,7 @@ namespace OpenSim.Framework.Data.MSSQL
|
||||||
parameters["profileFirstText"] = "";
|
parameters["profileFirstText"] = "";
|
||||||
parameters["profileImage"] = LLUUID.Zero.ToString();
|
parameters["profileImage"] = LLUUID.Zero.ToString();
|
||||||
parameters["profileFirstImage"] = LLUUID.Zero.ToString();
|
parameters["profileFirstImage"] = LLUUID.Zero.ToString();
|
||||||
|
parameters["webLoginKey"] = LLUUID.Random().ToString();
|
||||||
|
|
||||||
bool returnval = false;
|
bool returnval = false;
|
||||||
|
|
||||||
|
|
|
@ -315,7 +315,7 @@ namespace OpenSim.Framework.Data.MSSQL
|
||||||
user.lastLogin, user.userInventoryURI, user.userAssetURI,
|
user.lastLogin, user.userInventoryURI, user.userAssetURI,
|
||||||
user.profileCanDoMask, user.profileWantDoMask,
|
user.profileCanDoMask, user.profileWantDoMask,
|
||||||
user.profileAboutText, user.profileFirstText, user.profileImage,
|
user.profileAboutText, user.profileFirstText, user.profileImage,
|
||||||
user.profileFirstImage);
|
user.profileFirstImage,user.webLoginKey);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
catch (Exception e)
|
catch (Exception e)
|
||||||
|
|
|
@ -27,6 +27,7 @@ CREATE TABLE [users] (
|
||||||
[profileFirstText] [ntext],
|
[profileFirstText] [ntext],
|
||||||
[profileImage] [varchar](36) default NULL,
|
[profileImage] [varchar](36) default NULL,
|
||||||
[profileFirstImage] [varchar](36) default NULL,
|
[profileFirstImage] [varchar](36) default NULL,
|
||||||
|
[webLoginKey] [varchar](36) default NULL,
|
||||||
PRIMARY KEY CLUSTERED
|
PRIMARY KEY CLUSTERED
|
||||||
(
|
(
|
||||||
[UUID] ASC
|
[UUID] ASC
|
||||||
|
|
|
@ -446,6 +446,7 @@ namespace OpenSim.Framework.Data.MySQL
|
||||||
|
|
||||||
retval.profileImage = new LLUUID((string) reader["profileImage"]);
|
retval.profileImage = new LLUUID((string) reader["profileImage"]);
|
||||||
retval.profileFirstImage = new LLUUID((string) reader["profileFirstImage"]);
|
retval.profileFirstImage = new LLUUID((string) reader["profileFirstImage"]);
|
||||||
|
retval.webLoginKey = new LLUUID((string)reader["webLoginKey"]);
|
||||||
}
|
}
|
||||||
else
|
else
|
||||||
{
|
{
|
||||||
|
@ -531,7 +532,7 @@ namespace OpenSim.Framework.Data.MySQL
|
||||||
float homeLookAtX, float homeLookAtY, float homeLookAtZ, int created, int lastlogin,
|
float homeLookAtX, float homeLookAtY, float homeLookAtZ, int created, int lastlogin,
|
||||||
string inventoryURI, string assetURI, uint canDoMask, uint wantDoMask,
|
string inventoryURI, string assetURI, uint canDoMask, uint wantDoMask,
|
||||||
string aboutText, string firstText,
|
string aboutText, string firstText,
|
||||||
LLUUID profileImage, LLUUID firstImage)
|
LLUUID profileImage, LLUUID firstImage, LLUUID webLoginKey)
|
||||||
{
|
{
|
||||||
string sql =
|
string sql =
|
||||||
"INSERT INTO users (`UUID`, `username`, `lastname`, `passwordHash`, `passwordSalt`, `homeRegion`, ";
|
"INSERT INTO users (`UUID`, `username`, `lastname`, `passwordHash`, `passwordSalt`, `homeRegion`, ";
|
||||||
|
@ -539,14 +540,14 @@ namespace OpenSim.Framework.Data.MySQL
|
||||||
"`homeLocationX`, `homeLocationY`, `homeLocationZ`, `homeLookAtX`, `homeLookAtY`, `homeLookAtZ`, `created`, ";
|
"`homeLocationX`, `homeLocationY`, `homeLocationZ`, `homeLookAtX`, `homeLookAtY`, `homeLookAtZ`, `created`, ";
|
||||||
sql +=
|
sql +=
|
||||||
"`lastLogin`, `userInventoryURI`, `userAssetURI`, `profileCanDoMask`, `profileWantDoMask`, `profileAboutText`, ";
|
"`lastLogin`, `userInventoryURI`, `userAssetURI`, `profileCanDoMask`, `profileWantDoMask`, `profileAboutText`, ";
|
||||||
sql += "`profileFirstText`, `profileImage`, `profileFirstImage`) VALUES ";
|
sql += "`profileFirstText`, `profileImage`, `profileFirstImage`, `webLoginKey`) VALUES ";
|
||||||
|
|
||||||
sql += "(?UUID, ?username, ?lastname, ?passwordHash, ?passwordSalt, ?homeRegion, ";
|
sql += "(?UUID, ?username, ?lastname, ?passwordHash, ?passwordSalt, ?homeRegion, ";
|
||||||
sql +=
|
sql +=
|
||||||
"?homeLocationX, ?homeLocationY, ?homeLocationZ, ?homeLookAtX, ?homeLookAtY, ?homeLookAtZ, ?created, ";
|
"?homeLocationX, ?homeLocationY, ?homeLocationZ, ?homeLookAtX, ?homeLookAtY, ?homeLookAtZ, ?created, ";
|
||||||
sql +=
|
sql +=
|
||||||
"?lastLogin, ?userInventoryURI, ?userAssetURI, ?profileCanDoMask, ?profileWantDoMask, ?profileAboutText, ";
|
"?lastLogin, ?userInventoryURI, ?userAssetURI, ?profileCanDoMask, ?profileWantDoMask, ?profileAboutText, ";
|
||||||
sql += "?profileFirstText, ?profileImage, ?profileFirstImage)";
|
sql += "?profileFirstText, ?profileImage, ?profileFirstImage, ?webLoginKey)";
|
||||||
|
|
||||||
Dictionary<string, string> parameters = new Dictionary<string, string>();
|
Dictionary<string, string> parameters = new Dictionary<string, string>();
|
||||||
parameters["?UUID"] = uuid.ToString();
|
parameters["?UUID"] = uuid.ToString();
|
||||||
|
@ -571,6 +572,7 @@ namespace OpenSim.Framework.Data.MySQL
|
||||||
parameters["?profileFirstText"] = "";
|
parameters["?profileFirstText"] = "";
|
||||||
parameters["?profileImage"] = LLUUID.Zero.ToString();
|
parameters["?profileImage"] = LLUUID.Zero.ToString();
|
||||||
parameters["?profileFirstImage"] = LLUUID.Zero.ToString();
|
parameters["?profileFirstImage"] = LLUUID.Zero.ToString();
|
||||||
|
parameters["?webLoginKey"] = LLUUID.Random().ToString();
|
||||||
|
|
||||||
bool returnval = false;
|
bool returnval = false;
|
||||||
|
|
||||||
|
|
|
@ -114,6 +114,12 @@ namespace OpenSim.Framework.Data.MySQL
|
||||||
database.ExecuteResourceSql("CreateUsersTable.sql");
|
database.ExecuteResourceSql("CreateUsersTable.sql");
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
else if (oldVersion.Contains("Rev. 1"))
|
||||||
|
{
|
||||||
|
database.ExecuteResourceSql("UpgradeUsersTableToVersion2.sql");
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
//MainLog.Instance.Verbose("DB","DBVers:" + oldVersion);
|
||||||
}
|
}
|
||||||
|
|
||||||
/// <summary>
|
/// <summary>
|
||||||
|
@ -512,7 +518,7 @@ namespace OpenSim.Framework.Data.MySQL
|
||||||
user.lastLogin, user.userInventoryURI, user.userAssetURI,
|
user.lastLogin, user.userInventoryURI, user.userAssetURI,
|
||||||
user.profileCanDoMask, user.profileWantDoMask,
|
user.profileCanDoMask, user.profileWantDoMask,
|
||||||
user.profileAboutText, user.profileFirstText, user.profileImage,
|
user.profileAboutText, user.profileFirstText, user.profileImage,
|
||||||
user.profileFirstImage);
|
user.profileFirstImage, user.webLoginKey);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
catch (Exception e)
|
catch (Exception e)
|
||||||
|
|
|
@ -25,9 +25,10 @@ CREATE TABLE `users` (
|
||||||
`profileFirstText` text,
|
`profileFirstText` text,
|
||||||
`profileImage` varchar(36) default NULL,
|
`profileImage` varchar(36) default NULL,
|
||||||
`profileFirstImage` varchar(36) default NULL,
|
`profileFirstImage` varchar(36) default NULL,
|
||||||
|
`webLoginKey` varchar(36) default NULL,
|
||||||
PRIMARY KEY (`UUID`),
|
PRIMARY KEY (`UUID`),
|
||||||
UNIQUE KEY `usernames` (`username`,`lastname`)
|
UNIQUE KEY `usernames` (`username`,`lastname`)
|
||||||
) ENGINE=InnoDB DEFAULT CHARSET=utf8 COMMENT='Rev. 1';
|
) ENGINE=InnoDB DEFAULT CHARSET=utf8 COMMENT='Rev. 2';
|
||||||
|
|
||||||
-- ----------------------------
|
-- ----------------------------
|
||||||
-- Records
|
-- Records
|
||||||
|
|
|
@ -0,0 +1,3 @@
|
||||||
|
ALTER TABLE `users`
|
||||||
|
ADD COLUMN `webLoginKey` varchar(36) default NULL,
|
||||||
|
COMMENT='Rev. 2';
|
|
@ -549,6 +549,7 @@ namespace OpenSim.Framework.Data.SQLite
|
||||||
createCol(users, "profileFirstText", typeof (String));
|
createCol(users, "profileFirstText", typeof (String));
|
||||||
createCol(users, "profileImage", typeof (String));
|
createCol(users, "profileImage", typeof (String));
|
||||||
createCol(users, "profileFirstImage", typeof (String));
|
createCol(users, "profileFirstImage", typeof (String));
|
||||||
|
createCol(users, "webLoginKey", typeof(String));
|
||||||
// Add in contraints
|
// Add in contraints
|
||||||
users.PrimaryKey = new DataColumn[] {users.Columns["UUID"]};
|
users.PrimaryKey = new DataColumn[] {users.Columns["UUID"]};
|
||||||
return users;
|
return users;
|
||||||
|
@ -635,6 +636,8 @@ namespace OpenSim.Framework.Data.SQLite
|
||||||
user.profileFirstText = (String) row["profileFirstText"];
|
user.profileFirstText = (String) row["profileFirstText"];
|
||||||
user.profileImage = new LLUUID((String) row["profileImage"]);
|
user.profileImage = new LLUUID((String) row["profileImage"]);
|
||||||
user.profileFirstImage = new LLUUID((String) row["profileFirstImage"]);
|
user.profileFirstImage = new LLUUID((String) row["profileFirstImage"]);
|
||||||
|
user.webLoginKey = new LLUUID((String) row["webLoginKey"]);
|
||||||
|
|
||||||
return user;
|
return user;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -681,6 +684,7 @@ namespace OpenSim.Framework.Data.SQLite
|
||||||
row["profileFirstText"] = user.profileFirstText;
|
row["profileFirstText"] = user.profileFirstText;
|
||||||
row["profileImage"] = user.profileImage;
|
row["profileImage"] = user.profileImage;
|
||||||
row["profileFirstImage"] = user.profileFirstImage;
|
row["profileFirstImage"] = user.profileFirstImage;
|
||||||
|
row["webLoginKey"] = user.webLoginKey;
|
||||||
|
|
||||||
// ADO.NET doesn't handle NULL very well
|
// ADO.NET doesn't handle NULL very well
|
||||||
foreach (DataColumn col in ds.Tables["users"].Columns)
|
foreach (DataColumn col in ds.Tables["users"].Columns)
|
||||||
|
@ -825,6 +829,23 @@ namespace OpenSim.Framework.Data.SQLite
|
||||||
MainLog.Instance.Verbose("DATASTORE", "SQLite Database doesn't exist... creating");
|
MainLog.Instance.Verbose("DATASTORE", "SQLite Database doesn't exist... creating");
|
||||||
InitDB(conn);
|
InitDB(conn);
|
||||||
}
|
}
|
||||||
|
conn.Open();
|
||||||
|
try
|
||||||
|
{
|
||||||
|
cmd = new SqliteCommand("select webLoginKey from users limit 1;", conn);
|
||||||
|
cmd.ExecuteNonQuery();
|
||||||
|
}
|
||||||
|
catch (SqliteSyntaxException)
|
||||||
|
{
|
||||||
|
cmd = new SqliteCommand("alter table users add column webLoginKey text default '00000000-0000-0000-0000-000000000000';", conn);
|
||||||
|
cmd.ExecuteNonQuery();
|
||||||
|
pDa.Fill(tmpDS, "users");
|
||||||
|
}
|
||||||
|
finally
|
||||||
|
{
|
||||||
|
conn.Close();
|
||||||
|
}
|
||||||
|
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
|
@ -46,6 +46,8 @@ namespace OpenSim.Framework.Servers
|
||||||
protected Dictionary<string, XmlRpcMethod> m_rpcHandlers = new Dictionary<string, XmlRpcMethod>();
|
protected Dictionary<string, XmlRpcMethod> m_rpcHandlers = new Dictionary<string, XmlRpcMethod>();
|
||||||
protected LLSDMethod m_llsdHandler = null;
|
protected LLSDMethod m_llsdHandler = null;
|
||||||
protected Dictionary<string, IRequestHandler> m_streamHandlers = new Dictionary<string, IRequestHandler>();
|
protected Dictionary<string, IRequestHandler> m_streamHandlers = new Dictionary<string, IRequestHandler>();
|
||||||
|
protected Dictionary<string, GenericHTTPMethod> m_HTTPHandlers = new Dictionary<string, GenericHTTPMethod>();
|
||||||
|
|
||||||
protected uint m_port;
|
protected uint m_port;
|
||||||
protected bool m_ssl = false;
|
protected bool m_ssl = false;
|
||||||
protected bool m_firstcaps = true;
|
protected bool m_firstcaps = true;
|
||||||
|
@ -92,6 +94,18 @@ namespace OpenSim.Framework.Servers
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
public bool AddHTTPHandler(string method, GenericHTTPMethod handler)
|
||||||
|
{
|
||||||
|
if (!m_HTTPHandlers.ContainsKey(method))
|
||||||
|
{
|
||||||
|
m_HTTPHandlers.Add(method, handler);
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
|
||||||
|
//must already have a handler for that path so return false
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
|
||||||
public bool SetLLSDHandler(LLSDMethod handler)
|
public bool SetLLSDHandler(LLSDMethod handler)
|
||||||
{
|
{
|
||||||
m_llsdHandler = handler;
|
m_llsdHandler = handler;
|
||||||
|
@ -145,6 +159,10 @@ namespace OpenSim.Framework.Servers
|
||||||
{
|
{
|
||||||
switch (request.ContentType)
|
switch (request.ContentType)
|
||||||
{
|
{
|
||||||
|
case null:
|
||||||
|
case "text/html":
|
||||||
|
HandleHTTPRequest(request, response);
|
||||||
|
break;
|
||||||
case "application/xml+llsd":
|
case "application/xml+llsd":
|
||||||
HandleLLSDRequests(request, response);
|
HandleLLSDRequests(request, response);
|
||||||
break;
|
break;
|
||||||
|
@ -184,6 +202,32 @@ namespace OpenSim.Framework.Servers
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
private bool TryGetHTTPHandler(string handlerKey, out GenericHTTPMethod HTTPHandler)
|
||||||
|
{
|
||||||
|
string bestMatch = null;
|
||||||
|
|
||||||
|
foreach (string pattern in m_HTTPHandlers.Keys)
|
||||||
|
{
|
||||||
|
if (handlerKey.StartsWith(pattern))
|
||||||
|
{
|
||||||
|
if (String.IsNullOrEmpty(bestMatch) || pattern.Length > bestMatch.Length)
|
||||||
|
{
|
||||||
|
bestMatch = pattern;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
if (String.IsNullOrEmpty(bestMatch))
|
||||||
|
{
|
||||||
|
HTTPHandler = null;
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
HTTPHandler = m_HTTPHandlers[bestMatch];
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
}
|
||||||
private void HandleXmlRpcRequests(HttpListenerRequest request, HttpListenerResponse response)
|
private void HandleXmlRpcRequests(HttpListenerRequest request, HttpListenerResponse response)
|
||||||
{
|
{
|
||||||
Stream requestStream = request.InputStream;
|
Stream requestStream = request.InputStream;
|
||||||
|
@ -204,27 +248,7 @@ namespace OpenSim.Framework.Servers
|
||||||
}
|
}
|
||||||
catch (XmlException e)
|
catch (XmlException e)
|
||||||
{
|
{
|
||||||
Hashtable keysvals = new Hashtable();
|
|
||||||
responseString = String.Format("XmlException:\n{0}", e.Message);
|
|
||||||
MainLog.Instance.Error("XML", responseString);
|
|
||||||
string[] querystringkeys = request.QueryString.AllKeys;
|
|
||||||
string[] rHeaders = request.Headers.AllKeys;
|
|
||||||
|
|
||||||
|
|
||||||
foreach (string queryname in querystringkeys)
|
|
||||||
{
|
|
||||||
keysvals.Add(queryname, request.QueryString[queryname]);
|
|
||||||
MainLog.Instance.Warn("HTTP", queryname + "=" + request.QueryString[queryname]);
|
|
||||||
}
|
|
||||||
foreach (string headername in rHeaders)
|
|
||||||
{
|
|
||||||
MainLog.Instance.Warn("HEADER", headername + "=" + request.Headers[headername]);
|
|
||||||
}
|
|
||||||
if (keysvals.ContainsKey("show_login_form"))
|
|
||||||
{
|
|
||||||
HandleHTTPRequest(keysvals, request, response);
|
|
||||||
return;
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|
||||||
if (xmlRprcRequest != null)
|
if (xmlRprcRequest != null)
|
||||||
|
@ -332,7 +356,7 @@ namespace OpenSim.Framework.Servers
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
public void HandleHTTPRequest(Hashtable keysvals, HttpListenerRequest request, HttpListenerResponse response)
|
public void HandleHTTPRequest(HttpListenerRequest request, HttpListenerResponse response)
|
||||||
{
|
{
|
||||||
// This is a test. There's a workable alternative.. as this way sucks.
|
// This is a test. There's a workable alternative.. as this way sucks.
|
||||||
// We'd like to put this into a text file parhaps that's easily editable.
|
// We'd like to put this into a text file parhaps that's easily editable.
|
||||||
|
@ -345,119 +369,146 @@ namespace OpenSim.Framework.Servers
|
||||||
// I depend on show_login_form being in the secondlife.exe parameters to figure out
|
// I depend on show_login_form being in the secondlife.exe parameters to figure out
|
||||||
// to display the form, or process it.
|
// to display the form, or process it.
|
||||||
// a better way would be nifty.
|
// a better way would be nifty.
|
||||||
|
Stream requestStream = request.InputStream;
|
||||||
|
|
||||||
if ((string) keysvals["show_login_form"] == "TRUE")
|
Encoding encoding = Encoding.UTF8;
|
||||||
|
StreamReader reader = new StreamReader(requestStream, encoding);
|
||||||
|
|
||||||
|
string requestBody = reader.ReadToEnd();
|
||||||
|
reader.Close();
|
||||||
|
requestStream.Close();
|
||||||
|
|
||||||
|
string responseString = String.Empty;
|
||||||
|
|
||||||
|
Hashtable keysvals = new Hashtable();
|
||||||
|
|
||||||
|
string[] querystringkeys = request.QueryString.AllKeys;
|
||||||
|
string[] rHeaders = request.Headers.AllKeys;
|
||||||
|
|
||||||
|
|
||||||
|
foreach (string queryname in querystringkeys)
|
||||||
{
|
{
|
||||||
string responseString =
|
keysvals.Add(queryname, request.QueryString[queryname]);
|
||||||
"<!DOCTYPE html PUBLIC \"-//W3C//DTD XHTML 1.0 Transitional//EN\" \"http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd\">";
|
MainLog.Instance.Warn("HTTP", queryname + "=" + request.QueryString[queryname]);
|
||||||
responseString = responseString + "<html xmlns=\"http://www.w3.org/1999/xhtml\">";
|
}
|
||||||
responseString = responseString + "<head>";
|
//foreach (string headername in rHeaders)
|
||||||
responseString = responseString +
|
//{
|
||||||
"<meta http-equiv=\"Content-Type\" content=\"text/html; charset=utf-8\" />";
|
//MainLog.Instance.Warn("HEADER", headername + "=" + request.Headers[headername]);
|
||||||
responseString = responseString + "<meta http-equiv=\"cache-control\" content=\"no-cache\">";
|
//}
|
||||||
responseString = responseString + "<meta http-equiv=\"Pragma\" content=\"no-cache\">";
|
if (keysvals.Contains("method"))
|
||||||
responseString = responseString + "<title>Second Life Login</title>";
|
{
|
||||||
responseString = responseString + "<body>";
|
MainLog.Instance.Warn("HTTP", "Contains Method");
|
||||||
responseString = responseString + "<div id=\"login_box\">";
|
string method = (string) keysvals["method"];
|
||||||
// Linden Grid Form Post
|
MainLog.Instance.Warn("HTTP", requestBody);
|
||||||
//responseString = responseString + "<form action=\"https://secure-web16.secondlife.com/app/login/go.php?show_login_form=True&show_grid=&show_start_location=\" method=\"POST\" id=\"login-form\">";
|
GenericHTTPMethod requestprocessor;
|
||||||
responseString = responseString + "<form action=\"/\" method=\"GET\" id=\"login-form\">";
|
bool foundHandler = TryGetHTTPHandler(method, out requestprocessor);
|
||||||
|
if (foundHandler)
|
||||||
responseString = responseString + "<div id=\"message\">";
|
|
||||||
responseString = responseString + "</div>";
|
|
||||||
responseString = responseString + "<fieldset id=\"firstname\">";
|
|
||||||
responseString = responseString + "<legend>First Name:</legend>";
|
|
||||||
responseString = responseString +
|
|
||||||
"<input type=\"text\" id=\"firstname_input\" size=\"15\" maxlength=\"100\" name=\"username\" value=\"" +
|
|
||||||
keysvals["username"] + "\" />";
|
|
||||||
responseString = responseString + "</fieldset>";
|
|
||||||
responseString = responseString + "<fieldset id=\"lastname\">";
|
|
||||||
responseString = responseString + "<legend>Last Name:</legend>";
|
|
||||||
responseString = responseString +
|
|
||||||
"<input type=\"text\" size=\"15\" maxlength=\"100\" name=\"lastname\" value=\"" +
|
|
||||||
keysvals["lastname"] + "\" />";
|
|
||||||
responseString = responseString + "</fieldset>";
|
|
||||||
responseString = responseString + "<fieldset id=\"password\">";
|
|
||||||
responseString = responseString + "<legend>Password:</legend>";
|
|
||||||
responseString = responseString + "<table cellspacing=\"0\" cellpadding=\"0\" border=\"0\">";
|
|
||||||
responseString = responseString + "<tr>";
|
|
||||||
responseString = responseString +
|
|
||||||
"<td colspan=\"2\"><input type=\"password\" size=\"15\" maxlength=\"100\" name=\"password\" value=\"" +
|
|
||||||
keysvals["password"] + "\" /></td>";
|
|
||||||
responseString = responseString + "</tr>";
|
|
||||||
responseString = responseString + "<tr>";
|
|
||||||
responseString = responseString +
|
|
||||||
"<td valign=\"middle\"><input type=\"checkbox\" name=\"remember_password\" id=\"remember_password\" value=\"" +
|
|
||||||
keysvals["remember_password"] + "\" checked style=\"margin-left:0px;\"/></td>";
|
|
||||||
responseString = responseString + "<td><label for=\"remember_password\">Remember password</label></td>";
|
|
||||||
responseString = responseString + "</tr>";
|
|
||||||
responseString = responseString + "</table>";
|
|
||||||
responseString = responseString + "</fieldset>";
|
|
||||||
responseString = responseString + "<input type=\"hidden\" name=\"show_login_form\" value=\"FALSE\" />";
|
|
||||||
responseString = responseString + "<input type=\"hidden\" id=\"grid\" name=\"grid\" value=\"" +
|
|
||||||
keysvals["grid"] + "\" />";
|
|
||||||
responseString = responseString + "<div id=\"submitbtn\">";
|
|
||||||
responseString = responseString + "<input class=\"input_over\" type=\"submit\" value=\"Connect\" />";
|
|
||||||
responseString = responseString + "</div>";
|
|
||||||
responseString = responseString +
|
|
||||||
"<div id=\"connecting\" style=\"visibility:hidden\"><img src=\"/_img/sl_logo_rotate_black.gif\" align=\"absmiddle\"> Connecting...</div>";
|
|
||||||
|
|
||||||
responseString = responseString + "<div id=\"helplinks\">";
|
|
||||||
responseString = responseString +
|
|
||||||
"<a href=\"http://www.secondlife.com/join/index.php\" target=\"_blank\">Create new account</a> | ";
|
|
||||||
responseString = responseString +
|
|
||||||
"<a href=\"http://www.secondlife.com/account/request.php\" target=\"_blank\">Forgot password?</a>";
|
|
||||||
responseString = responseString + "</div>";
|
|
||||||
|
|
||||||
responseString = responseString + "<div id=\"channelinfo\"> " + keysvals["channel"] + " | " +
|
|
||||||
keysvals["version"] + "=" + keysvals["lang"] + "</div>";
|
|
||||||
responseString = responseString + "</form>";
|
|
||||||
responseString = responseString + "<script language=\"JavaScript\">";
|
|
||||||
responseString = responseString + "document.getElementById('firstname_input').focus();";
|
|
||||||
responseString = responseString + "</script>";
|
|
||||||
responseString = responseString + "</div>";
|
|
||||||
responseString = responseString + "</div>";
|
|
||||||
responseString = responseString + "</body>";
|
|
||||||
responseString = responseString + "</html>";
|
|
||||||
response.AddHeader("Content-type", "text/html");
|
|
||||||
|
|
||||||
byte[] buffer = Encoding.UTF8.GetBytes(responseString);
|
|
||||||
|
|
||||||
response.SendChunked = false;
|
|
||||||
response.ContentLength64 = buffer.Length;
|
|
||||||
response.ContentEncoding = Encoding.UTF8;
|
|
||||||
try
|
|
||||||
{
|
{
|
||||||
response.OutputStream.Write(buffer, 0, buffer.Length);
|
Hashtable responsedata = requestprocessor(keysvals);
|
||||||
|
DoHTTPGruntWork(responsedata,response);
|
||||||
|
|
||||||
|
//SendHTML500(response);
|
||||||
|
|
||||||
}
|
}
|
||||||
catch (Exception ex)
|
else
|
||||||
{
|
{
|
||||||
MainLog.Instance.Warn("HTTPD", "Error - " + ex.Message);
|
MainLog.Instance.Warn("HTTP", "Handler Not Found");
|
||||||
|
SendHTML404(response);
|
||||||
}
|
}
|
||||||
finally
|
}
|
||||||
{
|
|
||||||
response.OutputStream.Close();
|
|
||||||
}
|
|
||||||
} // show_login_form == "TRUE"
|
|
||||||
else
|
else
|
||||||
{
|
{
|
||||||
// show_login_form is present but FALSE
|
MainLog.Instance.Warn("HTTP", "No Method specified");
|
||||||
//
|
SendHTML404(response);
|
||||||
// The idea here is that we're telling the client to log in immediately here using the following information
|
}
|
||||||
// For my testing, I'm hard coding the web_login_key temporarily.
|
}
|
||||||
// Telling the client to go to the new improved SLURL for immediate logins
|
|
||||||
|
|
||||||
// The fact that it says grid=Other is important
|
private void DoHTTPGruntWork(Hashtable responsedata, HttpListenerResponse response)
|
||||||
|
{
|
||||||
|
int responsecode = (int)responsedata["int_response_code"];
|
||||||
|
string responseString = (string)responsedata["str_response_string"];
|
||||||
|
|
||||||
|
// We're forgoing the usual error status codes here because the client
|
||||||
|
// ignores anything but 200 and 301
|
||||||
|
|
||||||
//
|
response.StatusCode = 200;
|
||||||
|
|
||||||
response.StatusCode = 301;
|
if (responsecode == 301)
|
||||||
response.RedirectLocation = "secondlife:///app/login?first_name=" + keysvals["username"] + "&last_name=" +
|
{
|
||||||
keysvals["lastname"] +
|
response.RedirectLocation = (string)responsedata["str_redirect_location"];
|
||||||
"&location=home&grid=other&web_login_key=796f2b2a-0131-41e4-af12-00f60c24c458";
|
response.StatusCode = responsecode;
|
||||||
|
}
|
||||||
|
response.AddHeader("Content-type", "text/html");
|
||||||
|
|
||||||
|
byte[] buffer = Encoding.UTF8.GetBytes(responseString);
|
||||||
|
|
||||||
|
response.SendChunked = false;
|
||||||
|
response.ContentLength64 = buffer.Length;
|
||||||
|
response.ContentEncoding = Encoding.UTF8;
|
||||||
|
try
|
||||||
|
{
|
||||||
|
response.OutputStream.Write(buffer, 0, buffer.Length);
|
||||||
|
}
|
||||||
|
catch (Exception ex)
|
||||||
|
{
|
||||||
|
MainLog.Instance.Warn("HTTPD", "Error - " + ex.Message);
|
||||||
|
}
|
||||||
|
finally
|
||||||
|
{
|
||||||
response.OutputStream.Close();
|
response.OutputStream.Close();
|
||||||
} // show_login_form == "FALSE"
|
}
|
||||||
|
|
||||||
|
|
||||||
|
}
|
||||||
|
public void SendHTML404(HttpListenerResponse response)
|
||||||
|
{
|
||||||
|
// I know this statuscode is dumb, but the client doesn't respond to 404s and 500s
|
||||||
|
response.StatusCode = 200;
|
||||||
|
response.AddHeader("Content-type", "text/html");
|
||||||
|
|
||||||
|
string responseString = GetHTTP404();
|
||||||
|
byte[] buffer = Encoding.UTF8.GetBytes(responseString);
|
||||||
|
|
||||||
|
response.SendChunked = false;
|
||||||
|
response.ContentLength64 = buffer.Length;
|
||||||
|
response.ContentEncoding = Encoding.UTF8;
|
||||||
|
try
|
||||||
|
{
|
||||||
|
response.OutputStream.Write(buffer, 0, buffer.Length);
|
||||||
|
}
|
||||||
|
catch (Exception ex)
|
||||||
|
{
|
||||||
|
MainLog.Instance.Warn("HTTPD", "Error - " + ex.Message);
|
||||||
|
}
|
||||||
|
finally
|
||||||
|
{
|
||||||
|
response.OutputStream.Close();
|
||||||
|
}
|
||||||
|
}
|
||||||
|
public void SendHTML500(HttpListenerResponse response)
|
||||||
|
{
|
||||||
|
// I know this statuscode is dumb, but the client doesn't respond to 404s and 500s
|
||||||
|
response.StatusCode = 200;
|
||||||
|
response.AddHeader("Content-type", "text/html");
|
||||||
|
|
||||||
|
string responseString = GetHTTP500();
|
||||||
|
byte[] buffer = Encoding.UTF8.GetBytes(responseString);
|
||||||
|
|
||||||
|
response.SendChunked = false;
|
||||||
|
response.ContentLength64 = buffer.Length;
|
||||||
|
response.ContentEncoding = Encoding.UTF8;
|
||||||
|
try
|
||||||
|
{
|
||||||
|
response.OutputStream.Write(buffer, 0, buffer.Length);
|
||||||
|
}
|
||||||
|
catch (Exception ex)
|
||||||
|
{
|
||||||
|
MainLog.Instance.Warn("HTTPD", "Error - " + ex.Message);
|
||||||
|
}
|
||||||
|
finally
|
||||||
|
{
|
||||||
|
response.OutputStream.Close();
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
public void Start()
|
public void Start()
|
||||||
|
@ -504,5 +555,46 @@ namespace OpenSim.Framework.Servers
|
||||||
{
|
{
|
||||||
m_streamHandlers.Remove(GetHandlerKey(httpMethod, path));
|
m_streamHandlers.Remove(GetHandlerKey(httpMethod, path));
|
||||||
}
|
}
|
||||||
|
|
||||||
|
public void RemoveHTTPHandler(string httpMethod, string path)
|
||||||
|
{
|
||||||
|
m_HTTPHandlers.Remove(GetHandlerKey(httpMethod, path));
|
||||||
|
}
|
||||||
|
|
||||||
|
public string GetHTTP404()
|
||||||
|
{
|
||||||
|
string file = Path.Combine(Util.configDir(), "http_404.html");
|
||||||
|
if (!File.Exists(file))
|
||||||
|
return getDefaultHTTP404();
|
||||||
|
|
||||||
|
StreamReader sr = File.OpenText(file);
|
||||||
|
string result = sr.ReadToEnd();
|
||||||
|
sr.Close();
|
||||||
|
return result;
|
||||||
|
}
|
||||||
|
|
||||||
|
public string GetHTTP500()
|
||||||
|
{
|
||||||
|
string file = Path.Combine(Util.configDir(), "http_500.html");
|
||||||
|
if (!File.Exists(file))
|
||||||
|
return getDefaultHTTP500();
|
||||||
|
|
||||||
|
StreamReader sr = File.OpenText(file);
|
||||||
|
string result = sr.ReadToEnd();
|
||||||
|
sr.Close();
|
||||||
|
return result;
|
||||||
|
}
|
||||||
|
|
||||||
|
// Fallback HTTP responses in case the HTTP error response files don't exist
|
||||||
|
private string getDefaultHTTP404()
|
||||||
|
{
|
||||||
|
return "<HTML><HEAD><TITLE>404 Page not found</TITLE><BODY><BR /><H1>Ooops!</H1><P>The page you requested has been obsconded with by knomes. Find hippos quick!</P></BODY></HTML>";
|
||||||
|
}
|
||||||
|
|
||||||
|
private string getDefaultHTTP500()
|
||||||
|
{
|
||||||
|
return "<HTML><HEAD><TITLE>500 Internal Server Error</TITLE><BODY><BR /><H1>Ooops!</H1><P>The server you requested is overun by knomes! Find hippos quick!</P></BODY></HTML>";
|
||||||
|
}
|
||||||
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
|
@ -0,0 +1,34 @@
|
||||||
|
/*
|
||||||
|
* Copyright (c) Contributors, http://opensimulator.org/
|
||||||
|
* See CONTRIBUTORS.TXT for a full list of copyright holders.
|
||||||
|
*
|
||||||
|
* Redistribution and use in source and binary forms, with or without
|
||||||
|
* modification, are permitted provided that the following conditions are met:
|
||||||
|
* * Redistributions of source code must retain the above copyright
|
||||||
|
* notice, this list of conditions and the following disclaimer.
|
||||||
|
* * Redistributions in binary form must reproduce the above copyright
|
||||||
|
* notice, this list of conditions and the following disclaimer in the
|
||||||
|
* documentation and/or other materials provided with the distribution.
|
||||||
|
* * Neither the name of the OpenSim Project nor the
|
||||||
|
* names of its contributors may be used to endorse or promote products
|
||||||
|
* derived from this software without specific prior written permission.
|
||||||
|
*
|
||||||
|
* THIS SOFTWARE IS PROVIDED BY THE DEVELOPERS ``AS IS'' AND ANY
|
||||||
|
* EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
|
||||||
|
* WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
|
||||||
|
* DISCLAIMED. IN NO EVENT SHALL THE CONTRIBUTORS BE LIABLE FOR ANY
|
||||||
|
* DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
|
||||||
|
* (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
|
||||||
|
* LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
|
||||||
|
* ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
|
||||||
|
* (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
|
||||||
|
* SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
||||||
|
*
|
||||||
|
*/
|
||||||
|
using System;
|
||||||
|
using System.Collections;
|
||||||
|
|
||||||
|
namespace OpenSim.Framework.Servers
|
||||||
|
{
|
||||||
|
public delegate Hashtable GenericHTTPMethod(Hashtable request);
|
||||||
|
}
|
|
@ -25,7 +25,7 @@
|
||||||
* SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
* SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
||||||
*
|
*
|
||||||
*/
|
*/
|
||||||
|
using System.Collections;
|
||||||
using System.IO;
|
using System.IO;
|
||||||
|
|
||||||
namespace OpenSim.Framework.Servers
|
namespace OpenSim.Framework.Servers
|
||||||
|
@ -40,6 +40,7 @@ namespace OpenSim.Framework.Servers
|
||||||
|
|
||||||
// Return path
|
// Return path
|
||||||
string Path { get; }
|
string Path { get; }
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
||||||
public interface IStreamedRequestHandler : IRequestHandler
|
public interface IStreamedRequestHandler : IRequestHandler
|
||||||
|
@ -53,4 +54,8 @@ namespace OpenSim.Framework.Servers
|
||||||
// Handle request stream, return byte array
|
// Handle request stream, return byte array
|
||||||
void Handle(string path, Stream request, Stream response);
|
void Handle(string path, Stream request, Stream response);
|
||||||
}
|
}
|
||||||
|
public interface IGenericHTTPHandler : IRequestHandler
|
||||||
|
{
|
||||||
|
Hashtable Handle(string path, Hashtable request);
|
||||||
|
}
|
||||||
}
|
}
|
|
@ -40,6 +40,10 @@ namespace OpenSim.Framework
|
||||||
/// </summary>
|
/// </summary>
|
||||||
public LLUUID UUID;
|
public LLUUID UUID;
|
||||||
|
|
||||||
|
/// <summary>
|
||||||
|
/// The last used Web_login_key
|
||||||
|
/// </summary>
|
||||||
|
public LLUUID webLoginKey;
|
||||||
/// <summary>
|
/// <summary>
|
||||||
/// The first component of a users account name
|
/// The first component of a users account name
|
||||||
/// </summary>
|
/// </summary>
|
||||||
|
|
|
@ -103,6 +103,7 @@ namespace OpenSim.Grid.UserServer
|
||||||
BaseHttpServer httpServer = new BaseHttpServer(Cfg.HttpPort);
|
BaseHttpServer httpServer = new BaseHttpServer(Cfg.HttpPort);
|
||||||
|
|
||||||
httpServer.AddXmlRPCHandler("login_to_simulator", m_loginService.XmlRpcLoginMethod);
|
httpServer.AddXmlRPCHandler("login_to_simulator", m_loginService.XmlRpcLoginMethod);
|
||||||
|
|
||||||
httpServer.SetLLSDHandler(m_loginService.LLSDLoginMethod);
|
httpServer.SetLLSDHandler(m_loginService.LLSDLoginMethod);
|
||||||
|
|
||||||
httpServer.AddXmlRPCHandler("get_user_by_name", m_userManager.XmlRPCGetUserMethodName);
|
httpServer.AddXmlRPCHandler("get_user_by_name", m_userManager.XmlRPCGetUserMethodName);
|
||||||
|
|
|
@ -0,0 +1 @@
|
||||||
|
<HTML><HEAD><TITLE>404 Page not found</TITLE><BODY><BR /><H1>Ooops!</H1><P>The page you requested has been obsconded with by knomes. Find hippos quick!</P></BODY></HTML>
|
|
@ -0,0 +1 @@
|
||||||
|
<HTML><HEAD><TITLE>500 Internal Server Error</TITLE><BODY><BR /><H1>Ooops!</H1><P>The server you requested is overun by knomes! Find hippos quick!</P></BODY></HTML>
|
Loading…
Reference in New Issue