public static void Init ( int poolSize, string ip, int port, int threshold ) { _ip = ip; _port = port; initialPoolSize = poolSize; _threshold = threshold; for (int i=0; i<poolSize; i++) { QueueClient qc = new QueueClient(ip, port); qc.ConnectionClosed += queue_ConnectionClosed; qc.Connect(); clients.Enqueue(qc); } run = true; runner = new Thread(new ThreadStart(Process)); runner.Start(); }
public IAsyncResult BeginProcessRequest ( HttpContext context, AsyncCallback cb, object extraData ) { m_stopwatch.Start(); FileInfo fileInfo = new FileInfo(context.Request.MapPath(context.Request.CurrentExecutionFilePath)); this.LogDebug("File Date: {0}; File Length: {1}", fileInfo.LastWriteTimeUtc, fileInfo.Length); m_CONTENT_IS_MEMCACHED = false; m_USE_MEMCACHED = false; m_httpContext = context; m_returnOutput = true; m_httpMethod = m_httpContext.Request.HttpMethod; m_memcachedClient = (Client)context.Application["memcached"]; m_encoding = (UTF8Encoding)context.Application["encoding"]; m_queueClient = (QueueClient)context.Application["queueclient"]; m_hashkey = (string)context.Application["hashkey"]; m_xmlServiceOperationManager = (XPathServiceOperationManager)context.Application["xmlServiceOperationManager"]; m_xslTransformationManager = (XsltTransformationManager)context.Application["xslTransformationManager"]; m_transform = m_xslTransformationManager.Transform; m_xsltParams = (Hashtable)context.Application["globalXsltParams"]; m_transformContext = new Transform.Context(context, m_hashAlgorithm, (string)context.Application["hashkey"], fileInfo, (Hashtable)m_xsltParams.Clone(), fileInfo.LastWriteTimeUtc, fileInfo.Length); m_namedXsltHashtable = (Hashtable)context.Application["namedXsltHashtable"]; m_xmlSourceETagDictionary = m_xmlServiceOperationManager.XmlSourceETagDictionary; m_xmlReaderDictionary = m_xmlServiceOperationManager.XmlReaderDictionary; m_context = new Context(context, m_hashAlgorithm, m_hashkey, fileInfo, fileInfo.LastWriteTimeUtc, fileInfo.Length); this.LogDebug("File Date: {0}; File Length: {1}", m_context.RequestXmlFileInfo.LastWriteTimeUtc, m_context.RequestXmlFileInfo.Length); m_nuxleusAsyncResult = new Nuxleus.Core.NuxleusAsyncResult(cb, extraData); m_callback = cb; m_nuxleusAsyncResult.m_context = context; m_builder = new StringBuilder(); m_CONTENT_IS_MEMCACHED = false; m_USE_MEMCACHED = (bool)context.Application["usememcached"]; Uri requestUri = new Uri(m_context.RequestUri); m_requestHashcode = m_context.GetRequestHashcode(true).ToString(); m_lastModifiedKey = String.Format("LastModified:{0}", m_context.RequestUri.GetHashCode()); m_lastModifiedDate = String.Empty; m_request = new TransformRequest(); m_response = new TransformResponse(); Guid requestGuid = Guid.NewGuid(); m_request.ID = requestGuid; context.Response.ContentType = "text/xml"; IEnumerator headers = context.Request.Headers.GetEnumerator(); for (int i = 0; headers.MoveNext(); i++) { string local = context.Request.Headers.AllKeys[i].ToString(); this.LogDebug("KeyName: {0}, KeyValue: {1}", local, context.Request.Headers[local]); } bool hasXmlSourceChanged = m_xmlServiceOperationManager.HasXmlSourceChanged(m_context.RequestXmlETag, requestUri); //if (m_USE_MEMCACHED) { // string obj = (string)m_memcachedClient.Get(m_context.GetRequestHashcode(true).ToString()); // if (obj != null && !hasXmlSourceChanged) { // m_response.TransformResult = (string)obj; // m_CONTENT_IS_MEMCACHED = true; // if ((bool)context.Application["debug"]) { // context.Response.ContentType = "text"; // } // } else { // //m_writer = new StringWriter(m_builder); // m_CONTENT_IS_MEMCACHED = false; // } //} else { // m_writer = new StringWriter(m_builder); //} m_writer = new StringWriter(m_builder); try { switch (m_httpMethod) { case "GET": case "HEAD": case "POST": { string name = String.Format("Name: {0}", context.Request.QueryString["name"]); this.LogDebug("QueryString Length: {0}", context.Request.QueryString.Count); this.LogDebug(name); this.LogDebug("If-None-Match: {0}, RequestHashCode: {1}", context.Request.Headers["If-None-Match"], m_requestHashcode); this.LogDebug(context.Request.Path); if (context.Request.Headers["If-None-Match"] == m_requestHashcode) { object lastModified; this.LogDebug("They matched."); this.LogDebug("Use memcached: {0}, KeyExists: {1}, XmlSource Changed: {2}", m_USE_MEMCACHED, m_memcachedClient.TryGet(m_lastModifiedKey, out lastModified), hasXmlSourceChanged); this.LogDebug("Last Modified Key Value: {0}", m_lastModifiedKey); if (m_USE_MEMCACHED && m_memcachedClient.TryGet(m_lastModifiedKey, out lastModified) && !hasXmlSourceChanged) { m_lastModifiedDate = (string)m_memcachedClient.Get(m_lastModifiedKey); this.LogDebug("Last Modified Date: {0}", m_lastModifiedDate); if (context.Request.Headers["If-Modified-Since"] == m_lastModifiedDate) { context.Response.StatusCode = 304; m_returnOutput = false; goto CompleteCall; } else { goto Process; } } else if (m_CONTENT_IS_MEMCACHED) { goto CompleteCall; } else { goto Process; } } else { this.LogDebug("Headers do not match. Beginning transformation process..."); m_returnOutput = true; goto Process; } } case "PUT": { goto CompleteCall; } case "DELETE": { goto CompleteCall; } default: { goto CompleteCall; } } } catch (Exception ex) { m_exception = ex; WriteError(); goto CompleteCall; } Process: try { this.LogDebug("Processing Transformation"); this.LogDebug("Request XML ETag Value: {0}, Request URI: {1}", m_context.RequestXmlETag, requestUri); XPathNavigator navigator = m_xmlServiceOperationManager.GetXPathNavigator(m_context.RequestXmlETag, requestUri); //if (initialReader == null) { // initialReader = reader; //} else { // this.LogDebug("XmlReaders are the same object: {0}", initialReader.Equals(reader)); //} //this.LogDebug("XML Reader Value: {0}", reader.ReadOuterXml()); //this.LogDebug("XML Reader Hash: {0}", reader.GetHashCode()); XPathServiceOperationNavigator serviceOperationReader = new XPathServiceOperationNavigator(context, m_context, m_transformContext, navigator, m_request, m_response, m_xslTransformationManager); m_response = serviceOperationReader.Process(); } catch (Exception e) { this.LogDebug("Error: {0} in transformation.", e.Message); m_exception = e; WriteError(); } goto CompleteCall; CompleteCall: this.LogDebug("CompleteCall reached"); if (m_lastModifiedDate == String.Empty) { m_lastModifiedDate = DateTime.UtcNow.ToString("r"); } context.Response.AppendHeader("Cache-Control", "max-age=86400"); context.Response.AddHeader("Last-Modified", m_lastModifiedDate); context.Response.AddHeader("ETag", String.Format("\"{0}\"", m_requestHashcode)); m_nuxleusAsyncResult.CompleteCall(); return m_nuxleusAsyncResult; }
public IAsyncResult BeginProcessRequest(HttpContext context, AsyncCallback cb, object extraData) { FileInfo fileInfo = new FileInfo(context.Request.MapPath(context.Request.CurrentExecutionFilePath)); m_CONTENT_IS_MEMCACHED = false; m_USE_MEMCACHED = false; m_context = context; m_httpMethod = m_context.Request.HttpMethod; m_memcachedClient = (Client)context.Application["memcached"]; m_queueClient = (QueueClient)context.Application["queueclient"]; m_xslTransformationManager = (XsltTransformationManager)context.Application["xslTransformationManager"]; m_transform = m_xslTransformationManager.Transform; m_xsltParams = (Hashtable)context.Application["globalXsltParams"]; m_namedXsltHashtable = (Hashtable)context.Application["namedXsltHashtable"]; m_transformContext = new Transform.Context(context, m_hashAlgorithm, (string)context.Application["hashkey"], fileInfo, (Hashtable)m_xsltParams.Clone(), fileInfo.LastWriteTimeUtc, fileInfo.Length); m_transformAsyncResult = new NuxleusAsyncResult(cb, extraData); m_callback = cb; m_transformAsyncResult.m_context = context; m_builder = new StringBuilder(); m_CONTENT_IS_MEMCACHED = false; m_USE_MEMCACHED = (bool)context.Application["usememcached"]; bool hasXmlSourceChanged = m_xslTransformationManager.HasXmlSourceChanged(m_transformContext.RequestXmlETag); bool hasBaseXsltSourceChanged = m_xslTransformationManager.HasBaseXsltSourceChanged(); if (m_USE_MEMCACHED) { string obj = (string)m_memcachedClient.Get(m_transformContext.GetRequestHashcode(true)); if (obj != null && !(hasXmlSourceChanged || hasBaseXsltSourceChanged) && !(m_context.Request.CurrentExecutionFilePath.StartsWith("/service/session") && !(m_context.Request.CurrentExecutionFilePath.StartsWith("/service/geo")))) { m_builder.Append(obj); m_CONTENT_IS_MEMCACHED = true; if ((bool)context.Application["debug"]) context.Response.ContentType = "text"; else context.Response.ContentType = "text/xml"; } else { m_writer = new StringWriter(m_builder); m_CONTENT_IS_MEMCACHED = false; } } else { m_writer = new StringWriter(m_builder); } //if ((bool)context.Application["debug"]) //{ // context.Response.Write("<debug>"); // context.Response.Write("<file-info>"); // context.Response.Write("Has Xml Changed: " + hasXmlSourceChanged + ":" + m_transformContext.RequestXmlETag + "<br/>"); // context.Response.Write("Has Xslt Changed: " + hasBaseXsltSourceChanged + "<br/>"); // context.Response.Write("Xml ETag: " + m_transformContext.GetRequestHashcode(true) + "<br/>"); // context.Response.Write("XdmNode Count: " + m_xslTransformationManager.GetXdmNodeHashtableCount() + "<br/>"); // context.Response.Write("</file-info>"); // context.Application["debugOutput"] = (string)("<DebugOutput>" + WriteDebugOutput(m_transformContext, m_xslTransformationManager, new StringBuilder(), m_CONTENT_IS_MEMCACHED).ToString() + "</DebugOutput>"); // context.Response.Write("</debug>"); //} try { switch (m_httpMethod) { case "GET": case "HEAD": { if (m_CONTENT_IS_MEMCACHED) { m_transformAsyncResult.CompleteCall(); return m_transformAsyncResult; } else { try { string file = m_context.Request.FilePath; string baseXslt; if (file.EndsWith("index.page")) { baseXslt = "precompile-atomictalk"; } else if (file.EndsWith("service.op")) baseXslt = "base"; else baseXslt = m_xslTransformationManager.BaseXsltName; //m_transform.BeginTransformProcess(m_transformContext, context, m_xslTransformationManager, m_writer, baseXslt, m_transformAsyncResult); return m_transformAsyncResult; } catch (Exception e) { m_exception = e; WriteError(); m_transformAsyncResult.CompleteCall(); return m_transformAsyncResult; } } } case "PUT": { return m_transformAsyncResult; } case "POST": { return m_transformAsyncResult; } case "DELETE": { return m_transformAsyncResult; } default: { return m_transformAsyncResult; } } } catch (Exception ex) { m_exception = ex; WriteError(); m_transformAsyncResult.CompleteCall(); return m_transformAsyncResult; } }
public static void Process () { while (run) { // if we don't have any messages le'ts just pause and try again if (messages.Count == 0) { Thread.Sleep(1000); continue; } for (int i=0; i<clients.Count; i++) { MessageEvent me = null; if (messages.Count > 0) { me = (MessageEvent)messages.Dequeue(); if ((me != null) && (me.Message != null)) { QueueClient qc = null; qc = (QueueClient)clients.Dequeue(); me.Client = qc; me.MessageReceived += new MessageEventHandler(queue_MessageReceived); QueueClient.AsyncSend(me); QueueClient.AsyncRecv(me); } } } if (!run) { break; } if ((messages.Count > initialPoolSize) && (clients.Count < _threshold)) { // we may need to increase the queue clients pool QueueClient qc = new QueueClient(_ip, _port); qc.ConnectionClosed += queue_ConnectionClosed; try { qc.Connect(); clients.Enqueue(qc); } catch (SocketException se) { // we should find a way to warn that we can't create more connections // but this could be one of only so let's try give it a chance to recover Thread.Sleep(5000); } } else if ((messages.Count == 0) && (clients.Count > initialPoolSize)) { // or reduce it QueueClient qc = (QueueClient)clients.Dequeue(); qc.Disconnect(); } } }