Allow GetMesh capability to be served directly by a server like GetTexture

To do this required GetMesh to be converted to a BaseStreamHandler
Unlike GetTexture connector, no redirect URL functionality yet (this wasn't present in the first place).
ghosts
Justin Clark-Casey (justincc) 2014-10-14 18:37:22 +01:00
parent 22020927c6
commit 493a86dfed
3 changed files with 45 additions and 57 deletions

View File

@ -30,6 +30,7 @@ using System.Collections;
using System.Collections.Specialized; using System.Collections.Specialized;
using System.Reflection; using System.Reflection;
using System.IO; using System.IO;
using System.Text;
using System.Web; using System.Web;
using log4net; using log4net;
using Nini.Config; using Nini.Config;
@ -43,41 +44,37 @@ using Caps = OpenSim.Framework.Capabilities.Caps;
namespace OpenSim.Capabilities.Handlers namespace OpenSim.Capabilities.Handlers
{ {
public class GetMeshHandler public class GetMeshHandler : BaseStreamHandler
{ {
// private static readonly ILog m_log = // private static readonly ILog m_log =
// LogManager.GetLogger(MethodBase.GetCurrentMethod().DeclaringType); // LogManager.GetLogger(MethodBase.GetCurrentMethod().DeclaringType);
private IAssetService m_assetService; private IAssetService m_assetService;
public GetMeshHandler(IAssetService assService) public GetMeshHandler(string path, IAssetService assService, string name, string description)
: base("GET", path, name, description)
{ {
m_assetService = assService; m_assetService = assService;
} }
public Hashtable ProcessGetMesh(Hashtable request, UUID AgentId, Caps cap) protected override byte[] ProcessRequest(string path, Stream request, IOSHttpRequest httpRequest, IOSHttpResponse httpResponse)
{ {
Hashtable responsedata = new Hashtable(); // Try to parse the texture ID from the request URL
responsedata["int_response_code"] = 400; //501; //410; //404; NameValueCollection query = HttpUtility.ParseQueryString(httpRequest.Url.Query);
responsedata["content_type"] = "text/plain"; string meshStr = query.GetOne("mesh_id");
responsedata["keepalive"] = false;
responsedata["str_response_string"] = "Request wasn't what was expected";
string meshStr = string.Empty; // m_log.DebugFormat("Fetching mesh {0}", meshStr);
if (request.ContainsKey("mesh_id"))
meshStr = request["mesh_id"].ToString();
UUID meshID = UUID.Zero; UUID meshID = UUID.Zero;
if (!String.IsNullOrEmpty(meshStr) && UUID.TryParse(meshStr, out meshID)) if (!String.IsNullOrEmpty(meshStr) && UUID.TryParse(meshStr, out meshID))
{ {
if (m_assetService == null) if (m_assetService == null)
{ {
responsedata["int_response_code"] = 404; //501; //410; //404; httpResponse.StatusCode = 404;
responsedata["content_type"] = "text/plain"; httpResponse.ContentType = "text/plain";
responsedata["keepalive"] = false; byte[] data = Encoding.UTF8.GetBytes("The asset service is unavailable. So is your mesh.");
responsedata["str_response_string"] = "The asset service is unavailable. So is your mesh."; httpResponse.Body.Write(data, 0, data.Length);
return responsedata; return null;
} }
AssetBase mesh = m_assetService.Get(meshID.ToString()); AssetBase mesh = m_assetService.Get(meshID.ToString());
@ -86,31 +83,32 @@ namespace OpenSim.Capabilities.Handlers
{ {
if (mesh.Type == (SByte)AssetType.Mesh) if (mesh.Type == (SByte)AssetType.Mesh)
{ {
responsedata["str_response_string"] = Convert.ToBase64String(mesh.Data); byte[] data = mesh.Data;
responsedata["content_type"] = "application/vnd.ll.mesh"; httpResponse.Body.Write(data, 0, data.Length);
responsedata["int_response_code"] = 200; httpResponse.ContentType = "application/vnd.ll.mesh";
httpResponse.StatusCode = 200;
} }
// Optionally add additional mesh types here // Optionally add additional mesh types here
else else
{ {
responsedata["int_response_code"] = 404; //501; //410; //404; httpResponse.StatusCode = 404;
responsedata["content_type"] = "text/plain"; httpResponse.ContentType = "text/plain";
responsedata["keepalive"] = false; byte[] data = Encoding.UTF8.GetBytes("Unfortunately, this asset isn't a mesh.");
responsedata["str_response_string"] = "Unfortunately, this asset isn't a mesh."; httpResponse.Body.Write(data, 0, data.Length);
return responsedata; httpResponse.KeepAlive = false;
} }
} }
else else
{ {
responsedata["int_response_code"] = 404; //501; //410; //404; httpResponse.StatusCode = 404;
responsedata["content_type"] = "text/plain"; httpResponse.ContentType = "text/plain";
responsedata["keepalive"] = false; byte[] data = Encoding.UTF8.GetBytes("Your Mesh wasn't found. Sorry!");
responsedata["str_response_string"] = "Your Mesh wasn't found. Sorry!"; httpResponse.Body.Write(data, 0, data.Length);
return responsedata; httpResponse.KeepAlive = false;
} }
} }
return responsedata; return null;
} }
} }
} }

View File

@ -65,15 +65,8 @@ namespace OpenSim.Capabilities.Handlers
if (m_AssetService == null) if (m_AssetService == null)
throw new Exception(String.Format("Failed to load AssetService from {0}; config is {1}", assetService, m_ConfigName)); throw new Exception(String.Format("Failed to load AssetService from {0}; config is {1}", assetService, m_ConfigName));
GetMeshHandler gmeshHandler = new GetMeshHandler(m_AssetService); server.AddStreamHandler(
IRequestHandler reqHandler new GetMeshHandler("/CAPS/GetMesh/" /*+ UUID.Random() */, m_AssetService, "GetMesh", null));
= new RestHTTPHandler(
"GET",
"/CAPS/" + UUID.Random(),
httpMethod => gmeshHandler.ProcessGetMesh(httpMethod, UUID.Zero, null),
"GetMesh",
null);
server.AddStreamHandler(reqHandler);
} }
} }
} }

View File

@ -110,32 +110,29 @@ namespace OpenSim.Region.ClientStack.Linden
#endregion #endregion
public void RegisterCaps(UUID agentID, Caps caps) public void RegisterCaps(UUID agentID, Caps caps)
{ {
// UUID capID = UUID.Random();
//caps.RegisterHandler("GetTexture", new StreamHandler("GET", "/CAPS/" + capID, ProcessGetTexture)); //caps.RegisterHandler("GetTexture", new StreamHandler("GET", "/CAPS/" + capID, ProcessGetTexture));
if (m_URL == "localhost") if (m_URL == "localhost")
{ {
// m_log.DebugFormat("[GETMESH]: /CAPS/{0} in region {1}", capID, m_scene.RegionInfo.RegionName); // m_log.DebugFormat("[GETTEXTURE]: /CAPS/{0} in region {1}", capID, m_scene.RegionInfo.RegionName);
GetMeshHandler gmeshHandler = new GetMeshHandler(m_AssetService);
IRequestHandler reqHandler
= new RestHTTPHandler(
"GET",
"/CAPS/" + UUID.Random(),
httpMethod => gmeshHandler.ProcessGetMesh(httpMethod, UUID.Zero, null),
"GetMesh",
agentID.ToString());
caps.RegisterHandler("GetMesh", reqHandler); UUID capID = UUID.Random();
caps.RegisterHandler(
"GetMesh",
new GetMeshHandler("/CAPS/" + capID + "/", m_AssetService, "GetMesh", agentID.ToString()));
} }
else else
{ {
// m_log.DebugFormat("[GETMESH]: {0} in region {1}", m_URL, m_scene.RegionInfo.RegionName); // m_log.DebugFormat("[GETTEXTURE]: {0} in region {1}", m_URL, m_scene.RegionInfo.RegionName);
IExternalCapsModule handler = m_scene.RequestModuleInterface<IExternalCapsModule>();
if (handler != null)
handler.RegisterExternalUserCapsHandler(agentID, caps, "GetMesh", m_URL);
else
caps.RegisterHandler("GetMesh", m_URL); caps.RegisterHandler("GetMesh", m_URL);
} }
} }
} }
} }