/// <summary> /// Constructor for this singleton web service. /// </summary> /// <param name="root">The web root where we want the web pages to be /// served from.</param> /// <param name="port">UNUSED: The port where we want clients to access /// Presenter from.</param> public WebService(string root, string port) { if (WebService.Instance == null) { // TODO(cmprince): Catch exceptions here and handle them appropriately. // Get the source web directory. string webDir = //System.IO.Path.Combine( // System.Windows.Forms.Application.StartupPath, // "Web\\Website\\"); System.IO.Path.GetFullPath( "C:\\Users\\cmprince\\prog\\school\\www\\school\\cp3client\\"); DirectoryInfo sourceDir = new DirectoryInfo(webDir); // Get the target web directory. if (root != null) { WebService.WebRoot = root; } string localWebDir = WebService.WebRoot; DirectoryInfo targetDir = new DirectoryInfo(localWebDir); // Copy over the local files if they are newer. CopyAllIfNewer(sourceDir, targetDir); // Create the Katana server. WebServer.Create("/cp", WebService.WebRoot); WebServer.RequestBuilder = this.RequestBuilder; WebServer.PostHandler = this.PostHandler; // Save the singleton instance. WebService.Instance = this; } else { throw new Exception("Attempting to create multiple instances of the singleton WebService."); } }
/// <summary> /// Handle data posted to up by th web client. /// </summary> /// <param name="parameters">The query string parameters.</param> /// <param name="postData">The post data string.</param> /// <returns>The response text.</returns> private string PostHandler(NameValueCollection parameters, string postData) { // Get the parts of the post data. string[] items = postData.Split(new char[] { '|' }); if (items[0] == STUDENT_SUBMISSION_REQUEST) // Handle student submission. // Deserialize the Array of SimpleStrokeModel from the post data. { int clientId = Convert.ToInt32(items[1]); int deck = Convert.ToInt32(items[2]); int slide = Convert.ToInt32(items[3]); object strokes = JSON.Decode(items[4]); if (strokes is List <object> ) { ArrayList deserializedStrokes = new ArrayList(); List <object> strokesArray = (List <object>)strokes; foreach (object stroke in strokesArray) { if (stroke is List <KeyValuePair <string, object> > ) { SimpleWebInk deserializedStroke = new SimpleWebInk(); List <KeyValuePair <string, object> > strokeObject = (List <KeyValuePair <string, object> >)stroke; foreach (KeyValuePair <string, object> field in strokeObject) { switch (field.Key) { case "c": // Color if (field.Value is List <KeyValuePair <string, object> > ) { List <KeyValuePair <string, object> > color = (List <KeyValuePair <string, object> >)field.Value; foreach (KeyValuePair <string, object> channel in color) { if (channel.Key == "r") { deserializedStroke.R = (byte)Math.Round((double)channel.Value); } else if (channel.Key == "g") { deserializedStroke.G = (byte)Math.Round((double)channel.Value); } else if (channel.Key == "b") { deserializedStroke.B = (byte)Math.Round((double)channel.Value); } } } break; case "w": // Width if (field.Value is double) { deserializedStroke.Width = (float)((double)field.Value); } break; case "o": // Opacity if (field.Value is double) { deserializedStroke.Opacity = (byte)Math.Round((double)field.Value); } break; case "k": // Points if (field.Value is List <object> ) { List <object> points = (List <object>)field.Value; int numPoints = points.Count / 2; System.Drawing.Point[] pts = new System.Drawing.Point[numPoints]; for (int i = 0; i < numPoints; i++) { pts[i].X = (int)((double)points[(i * 2)] * 26.37f); pts[i].Y = (int)((double)points[(i * 2) + 1] * 26.37f); } deserializedStroke.Pts = pts; } break; } } deserializedStrokes.Add(deserializedStroke); } } // Notify listeners that a student submission was received. WebService.Instance.SubmissionReceived(WebServer.Instance, deck, slide, deserializedStrokes); } // Log that we responded to a pong. this.LogSubmissionReceived(clientId, deck, slide); } else if (items[0] == QUICK_POLL_REQUEST) // Handle quick poll. // Notify listeners that a quick poll update was received. { WebService.Instance.QuickPollReceived(WebServer.Instance, new Guid(items[1]), items[2]); } else if (items[0] == PING_REQUEST) // Handle ping request. { String clientId = items[1]; String clientTimestamp = items[2]; String serverTimestamp = WebService.ToUnixTime(System.DateTime.Now).ToString(); // We should respond with the current timestamp. String pong = "{\"u\":" + clientId + ",\"c\":" + clientTimestamp + ",\"s\":" + serverTimestamp + "}"; // Log that we responded to a pong. this.LogPong(Convert.ToInt32(clientId), pong); return(pong); } else if (items[0] == LOG_DUMP_REQUEST) // Handle a client log dump. { String clientId = items[1]; String logDump = items[2]; // Print the dumped log to a file. StreamWriter logFile = new StreamWriter( System.IO.Path.Combine(System.IO.Path.GetTempPath(), "CP_ClientPerformanceLog_" + clientId.ToString() + ".txt")); logFile.Write(logDump); logFile.Close(); } // By default, return an empty json object. return("{}"); }