diff --git a/lib/js/Gruntfile.js b/lib/js/Gruntfile.js
index 9a8bb0d..321063f 100644
--- a/lib/js/Gruntfile.js
+++ b/lib/js/Gruntfile.js
@@ -40,8 +40,14 @@
       InstallThriftJS: {
         command: 'mkdir test/build; mkdir test/build/js; cp src/thrift.js test/build/js/thrift.js'
       },
+      InstallThriftNodeJSDep: {
+        command: 'cd ../nodejs; npm install'
+      },
       ThriftGen: {
         command: 'thrift -gen js -gen js:node -o test ../../test/ThriftTest.thrift'
+      },
+      ThriftGenJQ: {
+        command: 'thrift -gen js:jquery -gen js:node -o test ../../test/ThriftTest.thrift'
       }
     },
     external_daemon: {
@@ -50,19 +56,73 @@
           startCheck: function(stdout, stderr) {
             return (/Thrift Server running on port/).test(stdout);
           },
-          nodeSpawnOptions: {cwd: "test"}
+          nodeSpawnOptions: {
+                              cwd: "test",
+                              env: {NODE_PATH: "../../nodejs/lib:../../nodejs/node_modules"}
+                            }
         },
         cmd: "node",
         args: ["server_http.js"]
+      },
+      ThriftTestServer_TLS: {
+        options: {
+          startCheck: function(stdout, stderr) {
+            return (/Thrift Server running on port/).test(stdout);
+          },
+          nodeSpawnOptions: {
+                              cwd: "test",
+                              env: {NODE_PATH: "../../nodejs/lib:../../nodejs/node_modules"}
+                            }
+        },
+        cmd: "node",
+        args: ["server_https.js"]
       }
     },
     qunit: {
-      all: {
+      ThriftJS: {
         options: {
           urls: [
             'http://localhost:8088/test-nojq.html'
           ]
         }
+      },
+      ThriftJSJQ: {
+        options: {
+          urls: [
+            'http://localhost:8088/test.html'
+          ]
+        }
+      },
+      ThriftWS: {
+        options: {
+          urls: [
+            'http://localhost:8088/testws.html'
+          ]
+        }
+      },
+      ThriftJS_TLS: {
+        options: {
+          '--ignore-ssl-errors': true,
+          urls: [
+            'https://localhost:8089/test-nojq.html'
+          ]
+        }
+      },
+      ThriftJSJQ_TLS: {
+        options: {
+          '--ignore-ssl-errors': true,
+          urls: [
+            'https://localhost:8089/test.html'
+          ]
+        }
+      },
+      ThriftWS_TLS: {
+        options: {
+          '--ignore-ssl-errors': true,
+          urls: [
+            'https://localhost:8089/testws.html'
+          ]
+        }
       }
     },
     jshint: {
@@ -87,6 +147,15 @@
   grunt.loadNpmTasks('grunt-external-daemon');
   grunt.loadNpmTasks('grunt-shell');
 
-  grunt.registerTask('test', ['jshint', 'shell', 'external_daemon', 'qunit']);
-  grunt.registerTask('default', ['jshint', 'shell', 'external_daemon', 'qunit', 'concat', 'uglify', 'jsdoc']);
+  grunt.registerTask('test', ['jshint', 'shell:InstallThriftJS', 'shell:InstallThriftNodeJSDep', 'shell:ThriftGen', 
+                              'external_daemon:ThriftTestServer', 'external_daemon:ThriftTestServer_TLS', 
+                              'qunit:ThriftJS', 'qunit:ThriftJS_TLS',
+                              'shell:ThriftGenJQ', 'qunit:ThriftJSJQ', 'qunit:ThriftJSJQ_TLS'
+                             ]);
+  grunt.registerTask('default', ['jshint', 'shell:InstallThriftJS', 'shell:InstallThriftNodeJSDep', 'shell:ThriftGen', 
+                                 'external_daemon:ThriftTestServer', 'external_daemon:ThriftTestServer_TLS', 
+                                 'qunit:ThriftJS', 'qunit:ThriftJS_TLS',
+                                 'shell:ThriftGenJQ', 'qunit:ThriftJSJQ', 'qunit:ThriftJSJQ_TLS',
+                                 'concat', 'uglify', 'jsdoc'
+                                ]);
 };
diff --git a/lib/js/README b/lib/js/README
index 971f6da..07b188b 100644
--- a/lib/js/README
+++ b/lib/js/README
@@ -1,7 +1,8 @@
 Thrift Javascript Library
 =========================
 This browser based Apache Thrift implementation supports
-RPC clients using the JSON protocol over Http[s] with XHR.
+RPC clients using the JSON protocol over Http[s] with XHR
+and WebSocket.
 
 License
 -------
@@ -22,13 +23,44 @@
 specific language governing permissions and limitations
 under the License.
 
-Example
--------
+Grunt Build
+------------
+The is the base directory for the Apache Thrift JavaScript
+library. This directory contains a Gruntfile.js and a
+package.json. Many of the build and test tools used here
+require a recent version of Node.js to be installed. To 
+install the support files for the Grunt build tool execute
+the command:
+   $ npm install
+This reads the package.json and pulls in the appropriate
+sources from the internet. To build the JavaScript branch
+of Apache Thrift execute the command:
+   $ grunt
+This runs the grunt build tool, linting all of the source 
+files, setting up and running the tests, concatenating and
+minifying the main libraries and generating the html 
+documentation.
+
+Tree
+----
+The following directories are present (some only after the
+grunt build):
+  /src  - The JavaScript Apache Thrift source
+  /doc - HTML documentation
+  /dist - Distribution files (thrift.js and thrift.min.js)
+  /test - Various tests, this is a good place to look for
+          example code
+  /node_modules - Build support files installed by npm
+
+
+Example JavaScript Client and Server
+------------------------------------
 The listing below demonstrates a simple browser based JavaScript
 Thrift client and Node.js JavaScript server for the hello_svc 
 service. 
 
-### hello.thrift - Service IDL
+### hello.thrift - Service IDL 
+### build with: $ thrift -gen js -gen js:node hello.thrift
     service hello_svc {
       string get_message(1: string name)
     }
@@ -92,7 +124,8 @@
       }
     }
     
-    var server = Thrift.createStaticHttpThriftServer(server_opt);
+    var server = Thrift.createThriftWebServer(server_opt);
     var port = 9099;
     server.listen(port);
-    console.log("Http/Thrift Server running on port: " + port);`
+    console.log("Http/Thrift Server running on port: " + port);
+
diff --git a/lib/js/src/thrift.js b/lib/js/src/thrift.js
index d605ab7..411eead 100644
--- a/lib/js/src/thrift.js
+++ b/lib/js/src/thrift.js
@@ -22,8 +22,16 @@
 /**
  * The Thrift namespace houses the Apache Thrift JavaScript library 
  * elements providing JavaScript bindings for the Apache Thrift RPC 
- * system. Users will typically only directly make use of the 
- * Transport and Protocol constructors.
+ * system. End users will typically only directly make use of the 
+ * Transport (TXHRTransport/TWebSocketTransport) and Protocol 
+ * (TJSONPRotocol/TBinaryProtocol) constructors.
+ * 
+ * Object methods beginning with a __ (e.g. __onOpen()) are internal 
+ * and should not be called outside of the object's own methods.
+ * 
+ * This library creates one global object: Thrift
+ * Code in this library must never create additional global identifiers,
+ * all features must be scoped within the Thrift namespace.
  * @namespace
  * @example
  *     var transport = new Thrift.Transport("http://localhost:8585");
@@ -108,7 +116,6 @@
                 length++;
             }
         }
-
         return length;
     },
 
@@ -266,19 +273,20 @@
 };
 
 /**
- * Initializes a Thrift Http[s] transport instance.
- * Note: If you do not specify a url then you must handle XHR on your own
- *       (this is how to use js bindings in a async fashion).
+ * Constructor Function for the XHR transport.
+ * If you do not specify a url then you must handle XHR operations on
+ * your own. This type can also be constructed using the Transport alias
+ * for backward compatibility.
  * @constructor
  * @param {string} [url] - The URL to connect to.
- * @classdesc The Apache Thrift Transport layer performs byte level I/O between RPC
- * clients and servers. The JavaScript Transport object type uses Http[s]/XHR and is
- * the sole browser based Thrift transport. Target servers must implement the http[s] 
- * transport (see: node.js example server).
+ * @classdesc The Apache Thrift Transport layer performs byte level I/O 
+ * between RPC clients and servers. The JavaScript TXHRTransport object 
+ * uses Http[s]/XHR. Target servers must implement the http[s] transport
+ * (see: node.js example server_http.js).
  * @example
- *     var transport = new Thrift.Transport("http://localhost:8585");
+ *     var transport = new Thrift.TXHRTransport("http://localhost:8585");
  */
-Thrift.Transport = function(url) {
+Thrift.Transport = Thrift.TXHRTransport = function(url) {
     this.url = url;
     this.wpos = 0;
     this.rpos = 0;
@@ -287,7 +295,7 @@
     this.recv_buf = '';
 };
 
-Thrift.Transport.prototype = {
+Thrift.TXHRTransport.prototype = {
     /**
      * Gets the browser specific XmlHttpRequest Object.
      * @returns {object} the browser XHR interface object
@@ -301,17 +309,17 @@
     },
 
     /**
-     * Sends the current XRH request if the transport was created with a URL and
-     * the async parameter if false. If the transport was not created with a URL
-     * or the async parameter is True or the URL is an empty string, the current 
-     * send buffer is returned.
+     * Sends the current XRH request if the transport was created with a URL 
+     * and the async parameter is false. If the transport was not created with
+     * a URL, or the async parameter is True and no callback is provided, or 
+     * the URL is an empty string, the current send buffer is returned.
      * @param {object} async - If true the current send buffer is returned.
-     * @param {object} callback - Optional async callback function, receives the call result.
+     * @param {object} callback - Optional async completion callback 
      * @returns {undefined|string} Nothing or the current send buffer.
      * @throws {string} If XHR fails.
      */
     flush: function(async, callback) {
-        //async mode
+        var self = this;
         if ((async && !callback) || this.url === undefined || this.url === '') {
             return this.send_buf;
         }
@@ -323,7 +331,18 @@
         }
 
         if (callback) {
-            xreq.onreadystatechange = callback;
+            //Ignore XHR callbacks until the data arrives, then call the
+            //  client's callback
+            xreq.onreadystatechange = 
+              (function() {
+                var clientCallback = callback;    
+                return function() {
+                  if (this.readyState == 4 && this.status == 200) {
+                    self.setRecvBuffer(this.responseText);
+                    clientCallback();
+                  }
+                };
+              }());
         }
 
         xreq.open('POST', this.url, !!async);
@@ -350,7 +369,7 @@
      * Creates a jQuery XHR object to be used for a Thrift server call.
      * @param {object} client - The Thrift Service client object generated by the IDL compiler.
      * @param {object} postData - The message to send to the server.
-     * @param {function} args - The function to call if the request suceeds.
+     * @param {function} args - The original call arguments with the success call back at the end.
      * @param {function} recv_method - The Thrift Service Client receive method for the call.
      * @returns {object} A new jQuery XHR object.
      * @throws {string} If the jQuery version is prior to 1.5 or if jQuery is not found.
@@ -385,6 +404,180 @@
     },
 
     /**
+     * Sets the buffer to provide the protocol when deserializing.
+     * @param {string} buf - The buffer to supply the protocol.
+     */
+    setRecvBuffer: function(buf) {
+        this.recv_buf = buf;
+        this.recv_buf_sz = this.recv_buf.length;
+        this.wpos = this.recv_buf.length;
+        this.rpos = 0;
+    },
+
+    /**
+     * Returns true if the transport is open, XHR always returns true.
+     * @readonly
+     * @returns {boolean} Always True.
+     */    
+    isOpen: function() {
+        return true;
+    },
+
+    /**
+     * Opens the transport connection, with XHR this is a nop.
+     */    
+    open: function() {},
+
+    /**
+     * Closes the transport connection, with XHR this is a nop.
+     */    
+    close: function() {},
+
+    /**
+     * Returns the specified number of characters from the response
+     * buffer.
+     * @param {number} len - The number of characters to return.
+     * @returns {string} Characters sent by the server.
+     */
+    read: function(len) {
+        var avail = this.wpos - this.rpos;
+
+        if (avail === 0) {
+            return '';
+        }
+
+        var give = len;
+
+        if (avail < len) {
+            give = avail;
+        }
+
+        var ret = this.read_buf.substr(this.rpos, give);
+        this.rpos += give;
+
+        //clear buf when complete?
+        return ret;
+    },
+
+    /**
+     * Returns the entire response buffer.
+     * @returns {string} Characters sent by the server.
+     */
+    readAll: function() {
+        return this.recv_buf;
+    },
+
+    /**
+     * Sets the send buffer to buf.
+     * @param {string} buf - The buffer to send.
+     */    
+    write: function(buf) {
+        this.send_buf = buf;
+    },
+
+    /**
+     * Returns the send buffer.
+     * @readonly
+     * @returns {string} The send buffer.
+     */ 
+    getSendBuffer: function() {
+        return this.send_buf;
+    }
+
+};
+
+
+/**
+ * Constructor Function for the WebSocket transport.
+ * @constructor
+ * @param {string} [url] - The URL to connect to.
+ * @classdesc The Apache Thrift Transport layer performs byte level I/O 
+ * between RPC clients and servers. The JavaScript TWebSocketTransport object 
+ * uses the WebSocket protocol. Target servers must implement WebSocket.
+ * (see: node.js example server_http.js).
+ * @example
+ *   var transport = new Thrift.TWebSocketTransport("http://localhost:8585");
+ */
+Thrift.TWebSocketTransport = function(url) {
+    this.__reset(url);
+};
+
+Thrift.TWebSocketTransport.prototype = {
+    __reset: function(url) {
+      this.url = url;             //Where to connect
+      this.socket = null;         //The web socket
+      this.callbacks = [];        //Pending callbacks
+      this.send_pending = [];     //Buffers/Callback pairs waiting to be sent
+      this.send_buf = '';         //Outbound data, immutable until sent
+      this.recv_buf = '';         //Inbound data
+      this.rb_wpos = 0;           //Network write position in receive buffer
+      this.rb_rpos = 0;           //Client read position in receive buffer
+    },
+
+    /**
+     * Sends the current WS request and registers callback. The async 
+     * parameter is ignored (WS flush is always async) and the callback 
+     * function parameter is required.
+     * @param {object} async - Ignored.
+     * @param {object} callback - The client completion callback.
+     * @returns {undefined|string} Nothing (undefined) 
+     */
+    flush: function(async, callback) {
+      var self = this;
+      if (this.isOpen()) {
+        //Send data and register a callback to invoke the client callback
+        this.socket.send(this.send_buf); 
+        this.callbacks.push((function() {
+          var clientCallback = callback;    
+          return function(msg) {
+            self.setRecvBuffer(msg);
+            clientCallback();
+          };
+        }()));
+      } else {
+        //Queue the send to go out __onOpen
+        this.send_pending.push({
+          buf: this.send_buf,
+          cb:  callback
+        });
+      }
+    },
+
+    __onOpen: function() { 
+       var self = this;
+       if (this.send_pending.length > 0) {
+          //If the user made calls before the connection was fully 
+          //open, send them now
+          this.send_pending.forEach(function(elem) {
+             this.socket.send(elem.buf);
+             this.callbacks.push((function() {
+               var clientCallback = elem.cb;    
+               return function(msg) {
+                  self.setRecvBuffer(msg);
+                  clientCallback();
+               };
+             }()));
+          });
+          this.send_pending = [];
+       }
+    },
+    
+    __onClose: function(evt) { 
+      this.__reset(this.url);
+    },
+     
+    __onMessage: function(evt) {
+      if (this.callbacks.length) {
+        this.callbacks.shift()(evt.data);
+      }
+    },
+     
+    __onError: function(evt) { 
+      console.log("Thrift WebSocket Error: " + evt.toString());
+      this.socket.close();
+    },
+
+    /**
      * Sets the buffer to use when receiving server responses.
      * @param {string} buf - The buffer to receive server responses.
      */
@@ -396,26 +589,36 @@
     },
 
     /**
-     * Returns true if the transport is open, in browser based JavaScript
-     * this function always returns true.
+     * Returns true if the transport is open
      * @readonly
-     * @returns {boolean} Always True.
+     * @returns {boolean} 
      */    
     isOpen: function() {
-        return true;
+        return this.socket && this.socket.readyState == this.socket.OPEN;
     },
 
     /**
-     * Opens the transport connection, in browser based JavaScript
-     * this function is a nop.
+     * Opens the transport connection
      */    
-    open: function() {},
+    open: function() {
+      //If OPEN/CONNECTING/CLOSING ignore additional opens
+      if (this.socket && this.socket.readyState != this.socket.CLOSED) {
+        return;
+      }
+      //If there is no socket or the socket is closed:
+      this.socket = new WebSocket(this.url);
+      this.socket.onopen = this.__onOpen.bind(this); 
+      this.socket.onmessage = this.__onMessage.bind(this); 
+      this.socket.onerror = this.__onError.bind(this); 
+      this.socket.onclose = this.__onClose.bind(this); 
+    },
 
     /**
-     * Closes the transport connection, in browser based JavaScript
-     * this function is a nop.
+     * Closes the transport connection
      */    
-    close: function() {},
+    close: function() {
+      this.socket.close();
+    },
 
     /**
      * Returns the specified number of characters from the response
@@ -1161,3 +1364,4 @@
 };
 
 
+
diff --git a/lib/js/test/README b/lib/js/test/README
new file mode 100644
index 0000000..6923794
--- /dev/null
+++ b/lib/js/test/README
@@ -0,0 +1,63 @@
+Thrift Javascript Library
+=========================
+This browser based Apache Thrift implementation supports
+RPC clients using the JSON protocol over Http[s] with XHR.
+
+License
+-------
+Licensed to the Apache Software Foundation (ASF) under one
+or more contributor license agreements. See the NOTICE file
+distributed with this work for additional information
+regarding copyright ownership. The ASF licenses this file
+to you under the Apache License, Version 2.0 (the
+"License"); you may not use this file except in compliance
+with the License. You may obtain a copy of the License at
+
+  http://www.apache.org/licenses/LICENSE-2.0
+
+Unless required by applicable law or agreed to in writing,
+software distributed under the License is distributed on an
+"AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+KIND, either express or implied. See the License for the
+specific language governing permissions and limitations
+under the License.
+
+Test Servers
+------------
+drwxr-xr-x 2 randy randy  4096 Feb  8 15:44 sec
+-rw-r--r-- 1 randy randy  2183 Feb  9 04:01 server_http.js
+-rw-r--r-- 1 randy randy  2386 Feb  9 05:39 server_https.js
+
+server_http.js is a Node.js web server which support the
+standard Apache Thrift test suite (thrift/test/ThriftTest.thrift).
+The server supports Apache Thrift XHR and WebSocket clients.
+
+server_https.js is the same but uses SSL/TLS. The sec directory
+contains the server key and certificate used by the ssl server.
+Both of these servers support WebSocket (the http: supports ws:,
+and the https: support wss:).
+
+To run the test servers use: $ make check (requires
+the Apache Thrift Java branch and make check must have
+been run in thrift/lib/java previously) or run the grunt
+ build in the parent js directory (see README there).
+ 
+Test Clients
+------------
+-rw-r--r-- 1 randy randy 13558 Feb  9 07:18 test-async.js
+-rw-r--r-- 1 randy randy  5724 Feb  9 03:45 test_handler.js
+-rwxr-xr-x 1 randy randy  2719 Feb  9 06:04 test.html
+-rw-r--r-- 1 randy randy  4611 Feb  9 06:05 test-jq.js
+-rwxr-xr-x 1 randy randy 12153 Feb  9 06:04 test.js
+-rw-r--r-- 1 randy randy  2593 Feb  9 06:16 test-nojq.html
+-rw-r--r-- 1 randy randy  1450 Feb  9 06:14 test-nojq.js
+-rw-r--r-- 1 randy randy  2847 Feb  9 06:31 testws.html
+
+There are three html test driver files, all of which are
+QUnit based. test.html test the Apache Thrift jQuery
+generated code (thrift -gen js:jquery). The test-nojq.html
+Runs almost identical tests against normal JavaScript builds
+(thrift -gen js). Both of the previous tests use the XHR 
+transport. The testws.html runs similar tests using the
+WebSocket transport. The test*.js files are loaded by the
+html drivers and contain the actualApache Thrift tests.
diff --git a/lib/js/test/server_http.js b/lib/js/test/server_http.js
index 623a979..01174bc 100644
--- a/lib/js/test/server_http.js
+++ b/lib/js/test/server_http.js
@@ -39,14 +39,14 @@
 	handler: ThriftTestHandler
 };
 
-var StaticHttpThriftServerOptions = {
+var ThriftWebServerOptions = {
 	staticFilePath: ".",
 	services: {
 		"/service": ThriftTestSvcOpt
 	}
 };
 
-var server = thrift.createStaticHttpThriftServer(StaticHttpThriftServerOptions);
+var server = thrift.createWebServer(ThriftWebServerOptions);
 var port = 8088;
 server.listen(port);
 console.log("Serving files from: " + __dirname);
diff --git a/lib/js/test/server_https.js b/lib/js/test/server_https.js
new file mode 100644
index 0000000..28f0585
--- /dev/null
+++ b/lib/js/test/server_https.js
@@ -0,0 +1,62 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements. See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership. The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License. You may obtain a copy of the License at
+ *
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing,
+ * software distributed under the License is distributed on an
+ * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ * KIND, either express or implied. See the License for the
+ * specific language governing permissions and limitations
+ * under the License.
+ */
+
+//This HTTP server is designed to server the test.html browser
+//  based JavaScript test page (which must be in the current directory). 
+//  This server also supplies the Thrift based test service, which depends
+//  on the standard ThriftTest.thrift IDL service (which must be compiled
+//  for Node and browser based JavaScript in ./gen-nodejs and ./gen-js
+//  respectively). The current directory must also include the browser
+//  support libraries for test.html (jquery.js, qunit.js and qunit.css
+//  in ./build/js/lib).
+
+var fs = require("fs");
+var thrift = require('../../nodejs/lib/thrift');
+var TBufferedTransport = require('../../nodejs/lib/thrift/transport').TBufferedTransport;
+var TJSONProtocol = require('../../nodejs/lib/thrift/protocol').TJSONProtocol;
+var ThriftTestSvc = require('./gen-nodejs/ThriftTest.js');
+var ThriftTestHandler = require('./test_handler').ThriftTestHandler;
+
+//Setup the I/O stack options for the ThriftTest service
+var ThriftTestSvcOpt = {
+	transport: TBufferedTransport,
+	protocol: TJSONProtocol,
+	cls: ThriftTestSvc,
+	handler: ThriftTestHandler
+};
+
+var ThriftWebServerOptions = {
+	staticFilePath: ".",
+	tlsOptions: {
+      key: fs.readFileSync("../../../test/keys/server.key"),
+      cert: fs.readFileSync("../../../test/keys/server.crt")
+    },	
+	services: {
+		"/service": ThriftTestSvcOpt
+	}
+};
+
+var server = thrift.createWebServer(ThriftWebServerOptions);
+var port = 8089;
+server.listen(port);
+console.log("Serving files from: " + __dirname);
+console.log("Http/Thrift Server running on port: " + port);
+
+
+
diff --git a/lib/js/test/test-async.js b/lib/js/test/test-async.js
new file mode 100644
index 0000000..4935fea
--- /dev/null
+++ b/lib/js/test/test-async.js
@@ -0,0 +1,347 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements. See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership. The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License. You may obtain a copy of the License at
+ *
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing,
+ * software distributed under the License is distributed on an
+ * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ * KIND, either express or implied. See the License for the
+ * specific language governing permissions and limitations
+ * under the License.
+ */
+ /* jshint -W100 */
+ 
+/*
+ * Fully Async JavaScript test suite for ThriftTest.thrift. 
+ * These tests are designed to exercise the WebSocket transport
+ * (which is exclusively async).
+ *
+ * To compile client code for this test use:
+ *      $ thrift -gen js ThriftTest.thrift
+ */
+
+
+
+// all Languages in UTF-8
+var stringTest = "Afrikaans, Alemannisch, Aragonés, العربية, مصرى, Asturianu, Aymar aru, Azərbaycan, Башҡорт, Boarisch, Žemaitėška, Беларуская, Беларуская (тарашкевіца), Български, Bamanankan, বাংলা, Brezhoneg, Bosanski, Català, Mìng-dĕ̤ng-ngṳ̄, Нохчийн, Cebuano, ᏣᎳᎩ, Česky, Словѣ́ньскъ / ⰔⰎⰑⰂⰡⰐⰠⰔⰍⰟ, Чӑвашла, Cymraeg, Dansk, Zazaki, ދިވެހިބަސް, Ελληνικά, Emiliàn e rumagnòl, English, Esperanto, Español, Eesti, Euskara, فارسی, Suomi, Võro, Føroyskt, Français, Arpetan, Furlan, Frysk, Gaeilge, 贛語, Gàidhlig, Galego, Avañe'ẽ, ગુજરાતી, Gaelg, עברית, हिन्दी, Fiji Hindi, Hrvatski, Kreyòl ayisyen, Magyar, Հայերեն, Interlingua, Bahasa Indonesia, Ilokano, Ido, Íslenska, Italiano, 日本語, Lojban, Basa Jawa, ქართული, Kongo, Kalaallisut, ಕನ್ನಡ, 한국어, Къарачай-Малкъар, Ripoarisch, Kurdî, Коми, Kernewek, Кыргызча, Latina, Ladino, Lëtzebuergesch, Limburgs, Lingála, ລາວ, Lietuvių, Latviešu, Basa Banyumasan, Malagasy, Македонски, മലയാളം, मराठी, Bahasa Melayu, مازِرونی, Nnapulitano, Nedersaksisch, नेपाल भाषा, Nederlands, ‪Norsk (nynorsk)‬, ‪Norsk (bokmål)‬, Nouormand, Diné bizaad, Occitan, Иронау, Papiamentu, Deitsch, Norfuk / Pitkern, Polski, پنجابی, پښتو, Português, Runa Simi, Rumantsch, Romani, Română, Русский, Саха тыла, Sardu, Sicilianu, Scots, Sámegiella, Simple English, Slovenčina, Slovenščina, Српски / Srpski, Seeltersk, Svenska, Kiswahili, தமிழ், తెలుగు, Тоҷикӣ, ไทย, Türkmençe, Tagalog, Türkçe, Татарча/Tatarça, Українська, اردو, Tiếng Việt, Volapük, Walon, Winaray, 吴语, isiXhosa, ייִדיש, Yorùbá, Zeêuws, 中文, Bân-lâm-gú, 粵語";
+  
+function checkRecursively(map1, map2) {
+  if (typeof map1 !== 'function' && typeof map2 !== 'function') {
+    if (!map1 || typeof map1 !== 'object') {
+        equal(map1, map2);
+    } else {
+      for (var key in map1) {
+        checkRecursively(map1[key], map2[key]);
+      }
+    }
+  }
+}
+
+module("Base Types");
+
+  asyncTest("Void", function() {
+    expect( 1 );
+    client.testVoid(function(result) {
+      equal(result, undefined);
+      QUnit.start();
+    });
+  });
+  
+  
+  asyncTest("String", function() {
+    expect( 3 );
+    QUnit.stop(2);
+    client.testString('', function(result){
+       equal(result, '');
+       QUnit.start();
+    });
+    client.testString(stringTest, function(result){
+       equal(result, stringTest);
+       QUnit.start();
+    });
+
+    var specialCharacters = 'quote: \" backslash:' +
+          ' forwardslash-escaped: \/ ' +
+          ' backspace: \b formfeed: \f newline: \n return: \r tab: ' +
+          ' now-all-of-them-together: "\\\/\b\n\r\t' +
+          ' now-a-bunch-of-junk: !@#$%&()(&%$#{}{}<><><';
+    client.testString(specialCharacters, function(result){
+       equal(result, specialCharacters);
+       QUnit.start();
+    });
+  });
+  asyncTest("Double", function() {
+    expect( 4 );
+    QUnit.stop(3);
+    client.testDouble(0, function(result){
+       equal(result, 0);
+       QUnit.start();
+    });
+    client.testDouble(-1, function(result){
+       equal(result, -1);
+       QUnit.start();
+    });
+    client.testDouble(3.14, function(result){
+       equal(result, 3.14);
+       QUnit.start();
+    });
+    client.testDouble(Math.pow(2,60), function(result){
+       equal(result, Math.pow(2,60));
+       QUnit.start();
+    });
+  });
+  asyncTest("Byte", function() {
+    expect( 2 );
+    QUnit.stop();
+    client.testByte(0, function(result) {
+       equal(result, 0);
+       QUnit.start();
+    });
+    client.testByte(0x01, function(result) {
+       equal(result, 0x01);
+       QUnit.start();
+    });
+  });
+  asyncTest("I32", function() {
+    expect( 3 );
+    QUnit.stop(2);
+    client.testI32(0, function(result){
+       equal(result, 0);
+       QUnit.start();
+    });
+    client.testI32(Math.pow(2,30), function(result){
+       equal(result, Math.pow(2,30));
+       QUnit.start();
+    });
+    client.testI32(-Math.pow(2,30), function(result){
+       equal(result, -Math.pow(2,30));
+       QUnit.start();
+    });
+  });
+  asyncTest("I64", function() {
+    expect( 3 );
+    QUnit.stop(2);
+    client.testI64(0, function(result){
+       equal(result, 0);
+       QUnit.start();
+    });
+    //This is usually 2^60 but JS cannot represent anything over 2^52 accurately
+    client.testI64(Math.pow(2,52), function(result){
+       equal(result, Math.pow(2,52));
+       QUnit.start();
+    });
+    client.testI64(-Math.pow(2,52), function(result){
+       equal(result, -Math.pow(2,52));
+       QUnit.start();
+    });
+  });
+  
+
+  
+
+module("Structured Types");
+
+  asyncTest("Struct", function() {
+    expect( 5 );
+    var structTestInput = new ThriftTest.Xtruct();
+    structTestInput.string_thing = 'worked';
+    structTestInput.byte_thing = 0x01;
+    structTestInput.i32_thing = Math.pow(2,30);
+    //This is usually 2^60 but JS cannot represent anything over 2^52 accurately
+    structTestInput.i64_thing = Math.pow(2,52);
+
+    client.testStruct(structTestInput, function(result){
+      equal(result.string_thing, structTestInput.string_thing);
+      equal(result.byte_thing, structTestInput.byte_thing);
+      equal(result.i32_thing, structTestInput.i32_thing);
+      equal(result.i64_thing, structTestInput.i64_thing);
+      equal(JSON.stringify(result), JSON.stringify(structTestInput));
+      QUnit.start();      
+    });
+  });
+
+  asyncTest("Nest", function() {
+    expect( 7 );
+    var xtrTestInput = new ThriftTest.Xtruct();
+    xtrTestInput.string_thing = 'worked';
+    xtrTestInput.byte_thing = 0x01;
+    xtrTestInput.i32_thing = Math.pow(2,30);
+    //This is usually 2^60 but JS cannot represent anything over 2^52 accurately
+    xtrTestInput.i64_thing = Math.pow(2,52);
+    
+    var nestTestInput = new ThriftTest.Xtruct2();
+    nestTestInput.byte_thing = 0x02;
+    nestTestInput.struct_thing = xtrTestInput;
+    nestTestInput.i32_thing = Math.pow(2,15);
+    
+    client.testNest(nestTestInput, function(result){
+      equal(result.byte_thing, nestTestInput.byte_thing);
+      equal(result.struct_thing.string_thing, nestTestInput.struct_thing.string_thing);
+      equal(result.struct_thing.byte_thing, nestTestInput.struct_thing.byte_thing);
+      equal(result.struct_thing.i32_thing, nestTestInput.struct_thing.i32_thing);
+      equal(result.struct_thing.i64_thing, nestTestInput.struct_thing.i64_thing);
+      equal(result.i32_thing, nestTestInput.i32_thing);  
+      equal(JSON.stringify(result), JSON.stringify(nestTestInput));
+      QUnit.start();      
+    });
+  });
+
+  asyncTest("Map", function() {
+    expect( 3 );
+    var mapTestInput = {7:77, 8:88, 9:99};
+
+    client.testMap(mapTestInput, function(result){
+      for (var key in result) {
+        equal(result[key], mapTestInput[key]);
+      }
+      QUnit.start();  
+    });
+  });
+
+  asyncTest("StringMap", function() {
+    expect( 6 );
+    var mapTestInput = {
+      "a":"123", "a b":"with spaces ", "same":"same", "0":"numeric key",
+      "longValue":stringTest, stringTest:"long key"
+    };
+
+    client.testStringMap(mapTestInput, function(result){
+      for (var key in result) {
+        equal(result[key], mapTestInput[key]);
+      }
+      QUnit.start();
+    });
+  });
+
+  asyncTest("Set", function() {
+    expect( 1 );
+    var setTestInput = [1,2,3];
+    client.testSet(setTestInput, function(result){
+      ok(result, setTestInput);
+      QUnit.start();
+    });
+  });
+
+  asyncTest("List", function() {
+    expect( 1 );
+    var listTestInput = [1,2,3];
+    client.testList(listTestInput, function(result){
+      ok(result, listTestInput);
+      QUnit.start();
+    });
+  });
+
+  asyncTest("Enum", function() {
+    expect( 1 );
+    client.testEnum(ThriftTest.Numberz.ONE, function(result){
+      equal(result, ThriftTest.Numberz.ONE);
+      QUnit.start();
+    });
+  });
+
+  asyncTest("TypeDef", function() {
+    expect( 1 );
+    client.testTypedef(69, function(result){
+      equal(result, 69);
+      QUnit.start();
+    });
+  });
+
+
+module("deeper!");
+
+  asyncTest("MapMap", function() {
+    expect( 16 );
+    var mapMapTestExpectedResult = {
+      "4":{"1":1,"2":2,"3":3,"4":4},
+      "-4":{"-4":-4, "-3":-3, "-2":-2, "-1":-1}
+    };
+
+    client.testMapMap(1, function(result){
+      for (var key in result) {
+        for (var key2 in result[key]) {
+          equal(result[key][key2], mapMapTestExpectedResult[key][key2]);
+        }
+      }
+      checkRecursively(result, mapMapTestExpectedResult);
+      QUnit.start();
+    });
+  });
+
+
+module("Exception");
+
+  asyncTest("Xception", function() {
+    expect(2);
+    client.testException("Xception", function(e){
+      equal(e.errorCode, 1001);
+      equal(e.message, "Xception");
+      QUnit.start();
+    });
+  });
+
+  asyncTest("no Exception", 0, function() {
+    expect( 1 );
+    client.testException("no Exception", function(e){
+      ok(!e);
+      QUnit.start();
+    });
+  });
+
+module("Insanity");
+
+  asyncTest("testInsanity", function() {
+    expect( 24 );
+    var insanity = {
+      "1":{
+        "2":{
+          "userMap":{ "5":5, "8":8 },
+          "xtructs":[{
+              "string_thing":"Goodbye4",
+              "byte_thing":4,
+              "i32_thing":4,
+              "i64_thing":4
+            },
+            {
+              "string_thing":"Hello2",
+              "byte_thing":2,
+              "i32_thing":2,
+              "i64_thing":2
+            }
+          ]
+        },
+        "3":{
+          "userMap":{ "5":5, "8":8 },
+          "xtructs":[{
+              "string_thing":"Goodbye4",
+              "byte_thing":4,
+              "i32_thing":4,
+              "i64_thing":4
+            },
+            {
+              "string_thing":"Hello2",
+              "byte_thing":2,
+              "i32_thing":2,
+              "i64_thing":2
+            }
+          ]
+        }
+      },
+      "2":{ "6":{ "userMap":null, "xtructs":null } }
+    };
+    client.testInsanity(new ThriftTest.Insanity(), function(res){
+      ok(res, JSON.stringify(res));
+      ok(insanity, JSON.stringify(insanity));
+      checkRecursively(res, insanity);
+      QUnit.start();
+    });
+  });
+
+
diff --git a/lib/js/test/test-jq.js b/lib/js/test/test-jq.js
index ed658e4..64608fe 100644
--- a/lib/js/test/test-jq.js
+++ b/lib/js/test/test-jq.js
@@ -29,9 +29,6 @@
  * ++ test-nojq.js for "-gen js" only tests
  */
 
-var transport = new Thrift.Transport("/service");
-var protocol  = new Thrift.Protocol(transport);
-var client    = new ThriftTest.ThriftTestClient(protocol);
 
 //////////////////////////////////
 //jQuery asynchronous tests
diff --git a/lib/js/test/test-nojq.js b/lib/js/test/test-nojq.js
index f67ea62..19f9e61 100644
--- a/lib/js/test/test-nojq.js
+++ b/lib/js/test/test-nojq.js
@@ -29,9 +29,6 @@
  * ++ test-jq.js for "-gen js:jquery" only tests
  */
 
-var transport = new Thrift.Transport("/service");
-var protocol  = new Thrift.Protocol(transport);
-var client    = new ThriftTest.ThriftTestClient(protocol);
 
 //////////////////////////////////
 //Async exception tests
diff --git a/lib/js/test/test.html b/lib/js/test/test.html
index 8f9e7ee..91d1a97 100755
--- a/lib/js/test/test.html
+++ b/lib/js/test/test.html
@@ -27,13 +27,18 @@
   <script src="gen-js/ThriftTest.js"       type="text/javascript" charset="utf-8"></script>
 
   <!-- jQuery -->
-  <script type="text/javascript" src="build/js/lib/jquery-1.7.2.js" charset="utf-8"></script>
+  <script type="text/javascript" src="http://code.jquery.com/jquery-1.7.2.js" charset="utf-8"></script>
   
   <!-- QUnit Test framework-->
-  <script type="text/javascript" src="build/js/lib/qunit.js" charset="utf-8"></script>
-  <link rel="stylesheet" href="build/js/lib/qunit.css" type="text/css" media="screen" />
+  <script type="text/javascript" src="http://code.jquery.com/qunit/qunit-1.14.0.js" charset="utf-8"></script>
+  <link rel="stylesheet" href="http://code.jquery.com/qunit/qunit-1.14.0.css" type="text/css" media="screen" />
   
   <!-- the Test Suite-->
+  <script>
+    var transport = new Thrift.Transport("/service");
+    var protocol  = new Thrift.Protocol(transport);
+    var client    = new ThriftTest.ThriftTestClient(protocol);
+  </script>
   <script type="text/javascript" src="test.js" charset="utf-8"></script>
   <script type="text/javascript" src="test-jq.js" charset="utf-8"></script>
 </head>
diff --git a/lib/js/test/test_handler.js b/lib/js/test/test_handler.js
index 33c8941..17d22cf 100644
--- a/lib/js/test/test_handler.js
+++ b/lib/js/test/test_handler.js
@@ -21,7 +21,7 @@
 //  Apache Thrift test service.
 
 var ttypes = require('./gen-nodejs/ThriftTest_types');
-var TException = require('thrift/thrift').TException;
+var TException = require('../../nodejs/lib/thrift').TException;
 
 var ThriftTestHandler = exports.ThriftTestHandler = {
   testVoid: function(result) {
diff --git a/lib/js/test/testws.html b/lib/js/test/testws.html
new file mode 100644
index 0000000..15ee195
--- /dev/null
+++ b/lib/js/test/testws.html
@@ -0,0 +1,60 @@
+﻿<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Strict//EN" "http://www.w3.org/TR/xhtml1/DTD/xhtml1-strict.dtd">
+<!--
+  Licensed to the Apache Software Foundation (ASF) under one
+  or more contributor license agreements. See the NOTICE file
+  distributed with this work for additional information
+  regarding copyright ownership. The ASF licenses this file
+  to you under the Apache License, Version 2.0 (the
+  "License"); you may not use this file except in compliance
+  with the License. You may obtain a copy of the License at
+
+    http://www.apache.org/licenses/LICENSE-2.0
+
+  Unless required by applicable law or agreed to in writing,
+  software distributed under the License is distributed on an
+  "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+  KIND, either express or implied. See the License for the
+  specific language governing permissions and limitations
+  under the License.
+-->
+<html xmlns="http://www.w3.org/1999/xhtml" xml:lang="en" lang="en">
+<head>
+  <meta http-equiv="Content-Type" content="text/html; charset=utf-8" />
+  <title>Thrift Javascript Bindings: Unit Test</title>
+
+  <script src="build/js/thrift.js"         type="text/javascript" charset="utf-8"></script>
+  <script src="gen-js/ThriftTest_types.js" type="text/javascript" charset="utf-8"></script>
+  <script src="gen-js/ThriftTest.js"       type="text/javascript" charset="utf-8"></script>
+
+  <!-- jQuery -->
+  <script type="text/javascript" src="https://code.jquery.com/jquery-1.7.2.js" charset="utf-8"></script>
+  
+  <!-- QUnit Test framework-->
+  <script type="text/javascript" src="https://code.jquery.com/qunit/qunit-1.14.0.js" charset="utf-8"></script>
+  <link rel="stylesheet" href="https://code.jquery.com/qunit/qunit-1.14.0.css" type="text/css" media="screen" />
+  
+  <!-- the Test Suite-->
+  <script>
+    var loc = window.location;
+    var ws_uri = ((loc.protocol === "https:") ? "wss://" : "ws://") + 
+                   loc.hostname + ":" + loc.port + loc.pathname;
+    var transport = new Thrift.TWebSocketTransport(ws_uri);
+    var protocol  = new Thrift.Protocol(transport);
+    var client    = new ThriftTest.ThriftTestClient(protocol);
+    transport.open();
+  </script>
+  <script type="text/javascript" src="test-async.js" charset="utf-8"></script>
+</head>
+<body>
+  <h1 id="qunit-header">Thrift Javascript Bindings: Unit Test (<a href="https://git-wip-us.apache.org/repos/asf?p=thrift.git;a=blob;f=test/ThriftTest.thrift;hb=HEAD">ThriftTest.thrift</a>)</h1>
+  <h2 id="qunit-banner"></h2>
+  <div id="qunit-testrunner-toolbar"></div> 
+  <h2 id="qunit-userAgent"></h2>
+  <ol id="qunit-tests"><li><!-- get valid xhtml strict--></li></ol>
+  <p>
+      <a href="http://validator.w3.org/check/referer"><img
+          src="http://www.w3.org/Icons/valid-xhtml10"
+          alt="Valid XHTML 1.0!" height="31" width="88" /></a>
+  </p>
+</body>
+</html>
diff --git a/lib/nodejs/lib/thrift/index.js b/lib/nodejs/lib/thrift/index.js
index 8499f9a..8487464 100644
--- a/lib/nodejs/lib/thrift/index.js
+++ b/lib/nodejs/lib/thrift/index.js
@@ -35,8 +35,8 @@
 exports.createMultiplexServer = server.createMultiplexServer;
 exports.createMultiplexSSLServer = server.createMultiplexSSLServer;
 
-var static_server = require('./static_server');
-exports.createStaticHttpThriftServer = static_server.createStaticHttpThriftServer;
+var web_server = require('./web_server');
+exports.createWebServer = web_server.createWebServer;
 
 exports.Int64 = require('node-int64');
 exports.Q = require('q');
diff --git a/lib/nodejs/lib/thrift/static_server.js b/lib/nodejs/lib/thrift/static_server.js
deleted file mode 100644
index b61bd30..0000000
--- a/lib/nodejs/lib/thrift/static_server.js
+++ /dev/null
@@ -1,162 +0,0 @@
-/*
- * Licensed to the Apache Software Foundation (ASF) under one
- * or more contributor license agreements. See the NOTICE file
- * distributed with this work for additional information
- * regarding copyright ownership. The ASF licenses this file
- * to you under the Apache License, Version 2.0 (the
- * "License"); you may not use this file except in compliance
- * with the License. You may obtain a copy of the License at
- *
- *   http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing,
- * software distributed under the License is distributed on an
- * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
- * KIND, either express or implied. See the License for the
- * specific language governing permissions and limitations
- * under the License.
- */
-var http = require('http');
-var url = require("url");
-var path = require("path");
-var fs = require("fs");
-
-var ttransport = require('./transport');
-var TBinaryProtocol = require('./protocol').TBinaryProtocol;
-
-/**
- * @class
- * @name StaticHttpThriftServerOptions
- * @property {string} staticFilePath - Path to serve static files from, default
- *                                is ".", use "" to disable static file service.
- * @property {object} services - An object hash mapping service URIs to 
- *                               ThriftServiceOptions objects.
- * @see {@link ThriftServiceOptions}
- */
-
-/**
- * @class
- * @name ThriftServiceOptions
- * @property {object} transport - The layered transport to use (defaults to none).
- * @property {object} protocol - The Thrift Protocol to use (defaults to TBinaryProtocol).
- * @property {object} cls - The Thrift Service class generated by the IDL Compiler for the service.
- * @property {object} handler - The handler methods for the Thrift Service.
- */
-
-/** 
- * Creates a Thrift server which can serve static files and/or one or
- * more Thrift Services. 
- * @param {StaticHttpThriftServerOptions} - The server configuration.
- * @returns {object} - The Thrift server.
- */
-exports.createStaticHttpThriftServer = function(options) {
-  //Set the static dir to serve files from
-  var baseDir = typeof options.staticFilePath != "string" ? process.cwd() : options.staticFilePath;
-  var contentTypesByExtension = {
-    '.html': "text/html",
-    '.css':  "text/css",
-    '.js':   "text/javascript"
-  };
-
-  //Setup all of the services
-  var services = options.services;
-  for (svc in services) {
-    var svcObj = services[svc];
-    var processor = svcObj.cls.Processor || svcObj.cls;
-    svcObj.processor = new processor(svcObj.handler);
-    svcObj.transport = svcObj.transport ? svcObj.transport : ttransport.TBufferedTransport;
-    svcObj.protocol = svcObj.protocol ? svcObj.protocol : TBinaryProtocol;
-  }
-
-  //Handle POST methods
-  function processPost(request, response) {
-    var uri = url.parse(request.url).pathname;
-    var svc = services[uri];
-    if (!svc) {
-      //Todo: add support for non Thrift posts
-      response.writeHead(500);
-      response.end();
-      return;
-    }
-
-    request.on('data', svc.transport.receiver(function(transportWithData) {
-      var input = new svc.protocol(transportWithData);
-      var output = new svc.protocol(new svc.transport(undefined, function(buf) {
-        try {
-          response.writeHead(200);
-          response.end(buf);
-        } catch (err) {
-          response.writeHead(500);
-          response.end();
-        }
-      }));
-
-      try {
-        svc.processor.process(input, output);
-        transportWithData.commitPosition();
-      }
-      catch (err) {
-        if (err instanceof ttransport.InputBufferUnderrunError) {
-          transportWithData.rollbackPosition();
-        }
-        else {
-          response.writeHead(500);
-          response.end();
-        }
-      }
-    }));
-  }
-
-  //Handle GET methods
-  function processGet(request, response) {
-    //An empty string base directory means do not serve static files
-    if ("" == baseDir) {
-      response.writeHead(404);
-      response.end();
-      return;      
-    }
-    //Locate the file requested
-    var uri = url.parse(request.url).pathname;
-    var filename = path.join(baseDir, uri);
-    fs.exists(filename, function(exists) {
-      if(!exists) {
-        response.writeHead(404);
-        response.end();
-        return;
-      }
-     
-      if (fs.statSync(filename).isDirectory()) {
-        filename += '/index.html';
-      }
-     
-      fs.readFile(filename, "binary", function(err, file) {
-        if (err) {
-          response.writeHead(500);
-          response.end(err + "\n");
-          return;
-        }
-        var headers = {};
-        var contentType = contentTypesByExtension[path.extname(filename)];
-        if (contentType) {
-          headers["Content-Type"] = contentType;
-        }
-        response.writeHead(200, headers);
-        response.write(file, "binary");
-        response.end();
-      });
-    });
-  }
-
-  //Return the server
-  return http.createServer(function(request, response) {
-    if (request.method === 'POST') {
-      processPost(request, response);
-    } else if (request.method === 'GET') {
-      processGet(request, response);
-    } else {
-      response.writeHead(500);
-      response.end();
-    }
-  });
-};
-
diff --git a/lib/nodejs/lib/thrift/web_server.js b/lib/nodejs/lib/thrift/web_server.js
new file mode 100644
index 0000000..c888a80
--- /dev/null
+++ b/lib/nodejs/lib/thrift/web_server.js
@@ -0,0 +1,427 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements. See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership. The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License. You may obtain a copy of the License at
+ *
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing,
+ * software distributed under the License is distributed on an
+ * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ * KIND, either express or implied. See the License for the
+ * specific language governing permissions and limitations
+ * under the License.
+ */
+var http = require('http');
+var https = require('https');
+var url = require("url");
+var path = require("path");
+var fs = require("fs");
+var crypto = require("crypto");
+
+var TTransport = require('./transport');
+var TBufferedTransport = require('./transport').TBufferedTransport;
+var TBinaryProtocol = require('./protocol').TBinaryProtocol;
+
+
+// WSFrame constructor and prototype 
+/////////////////////////////////////////////////////////////////////
+
+/** Apache Thrift RPC Web Socket Frame Layout
+ *  Conforming to RFC 6455 circa 12/2011
+ *
+ * Theoretical frame size limit is 4GB*4GB, however the Node Buffer
+ * limit is 1GB as of v0.10. The frame length encoding is also
+ * configured for a max of 4GB presently and needs to be adjusted
+ * if Node/Browsers become capabile of > 4GB frames.
+ *
+ * data - buffer to send (data.length is length to transmit)
+ * mask - Must be null if sending to client or mask-key if sending to server
+ * binEncoding - true for binary, false for text (the default)
+ *
+ *  - FIN is always 1, ATRPC messages are sent in a single frame
+ *  - RSV1/2/3 are always 0
+ *  - Opcode is 1(TEXT) for TJSONProtocol and 2(BIN) for TBinaryProtocol
+ *  - Mask Present bit is 1 sending to-server and 0 sending to-client
+ *  - Payload Len:
+ *        + If < 126: then represented directly 
+ *        + If >=126: but within range of an unsigned 16 bit integer
+ *             then Payload Len is 126 and the two following bytes store 
+ *             the length
+ *        + Else: Payload Len is 127 and the following 8 bytes store the 
+ *             length as an unsigned 64 bit integer
+ *  - Masking key is a 32 bit key only present when sending to the server
+ *  - Payload follows the masking key or length
+ *
+ *     0                   1                   2                   3
+ *     0 1 2 3 4 5 6 7 8 9 0 1 2 3 4 5 6 7 8 9 0 1 2 3 4 5 6 7 8 9 0 1
+ *    +-+-+-+-+-------+-+-------------+-------------------------------+
+ *    |F|R|R|R| opcode|M| Payload len |    Extended payload length    |
+ *    |I|S|S|S|  (4)  |A|     (7)     |             (16/64)           |
+ *    |N|V|V|V|       |S|             |   (if payload len==126/127)   |
+ *    | |1|2|3|       |K|             |                               |
+ *    +-+-+-+-+-------+-+-------------+ - - - - - - - - - - - - - - - +
+ *    |     Extended payload length continued, if payload len == 127  |
+ *    + - - - - - - - - - - - - - - - +-------------------------------+
+ *    |                               |Masking-key, if MASK set to 1  |
+ *    +-------------------------------+-------------------------------+
+ *    | Masking-key (continued)       |          Payload Data         |
+ *    +-------------------------------- - - - - - - - - - - - - - - - +
+ *    :                     Payload Data continued ...                :
+ *    + - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - +
+ *    |                     Payload Data continued ...                |
+ *    +---------------------------------------------------------------+
+ */
+var wsFrame = {
+  /** Encodes a WebSocket frame 
+   *
+   * @param {Buffer} data - The raw data to encode 
+   * @param {Buffer} mask - The mask to apply when sending to server, null for no mask
+   * @param {Boolean} binEncoding - True for binary encoding, false for text encoding
+   * @returns {Buffer} - The WebSocket frame, ready to send
+   */
+  encode: function(data, mask, binEncoding) {
+      var frame = new Buffer(wsFrame.frameSizeFromData(data, mask));
+      //Byte 0 - FIN & OPCODE
+      frame[0] = wsFrame.fin.FIN + 
+          (binEncoding ? wsFrame.frameOpCodes.BIN : wsFrame.frameOpCodes.TEXT);
+      //Byte 1 or 1-3 or 1-9 - MASK FLAG & SIZE
+      var payloadOffset = 2;
+      if (data.length < 0x7E) {
+        frame[1] = data.length + (mask ? wsFrame.mask.TO_SERVER : wsFrame.mask.TO_CLIENT);
+      } else if (data.length < 0xFFFF) {
+        frame[1] = 0x7E + (mask ? wsFrame.mask.TO_SERVER : wsFrame.mask.TO_CLIENT);  
+        frame.writeUInt16BE(data.length, 2, true);
+        payloadOffset = 4;
+      } else {
+        frame[1] = 0x7F + (mask ? wsFrame.mask.TO_SERVER : wsFrame.mask.TO_CLIENT);  
+        frame.writeUInt32BE(0, 2, true);
+        frame.writeUInt32BE(data.length, 6, true);
+        payloadOffset = 10;
+      }
+      //MASK
+      if (mask) {
+        mask.copy(frame, payloadOffset, 0, 4);
+        payloadOffset += 4;
+      }
+      //Payload
+      data.copy(frame, payloadOffset);
+      if (mask) {
+        wsFrame.applyMask(frame.slice(payloadOffset), frame.slice(payloadOffset-4,payloadOffset));
+      }
+      return frame;
+  },
+
+  /** Decodes a WebSocket frame 
+   *
+   * @param {Buffer} frame - The raw inbound frame
+   * @returns {WSDecodeResult} - The decoded payload
+   */
+  decode: function(frame) {
+      var result = {
+        data: null,
+        mask: null,
+        binEncoding: false,
+        nextFrame: null
+      };
+      //Byte 0 - FIN & OPCODE
+      if (wsFrame.fin.FIN != (frame[0] & wsFrame.fin.FIN)) {
+        console.log("WebSocket frame error: Received a frame without fin set.");
+      }
+      result.binEncoding = (wsFrame.frameOpCodes.BIN == (frame[0] & wsFrame.frameOpCodes.BIN));
+      //Byte 1 or 1-3 or 1-9 - SIZE
+      var lenByte = (frame[1] & 0x0000007F);
+      var len = lenByte;
+      var dataOffset = 2;
+      if (lenByte == 0x7E) {
+        len = frame.readUInt16BE(2);
+        dataOffset = 4;
+      } else if (lenByte == 0x7F) {
+        len = frame.readUInt32BE(6);
+        dataOffset = 10;
+      }
+      //MASK
+      if (wsFrame.mask.TO_SERVER == (frame[1] & wsFrame.mask.TO_SERVER)) {
+        result.mask = new Buffer(4);
+        frame.copy(result.mask, 0, dataOffset, dataOffset + 4);
+        dataOffset += 4;
+      }
+      //Payload
+      result.data = new Buffer(len);
+      frame.copy(result.data, 0, dataOffset, dataOffset+len);
+      wsFrame.applyMask(result.data, result.mask);
+      
+      //Residual Frames
+      if (frame.length > dataOffset+len) {
+        result.nextFrame = new Buffer(frame.length - (dataOffset+len));
+        frame.copy(result.nextFrame, 0, dataOffset+len, frame.length);
+      }
+
+      return result;
+  },
+
+  /** Masks/Unmasks data 
+   *
+   * @param {Buffer} data - data to mask/unmask in place
+   * @param {Buffer} mask - the mask
+   */
+  applyMask: function(data, mask){
+    //TODO: look into xoring words at a time
+    var dataLen = data.length;
+    var maskLen = mask.length;
+    for (var i = 0; i < dataLen; i++) {
+      data[i] = data[i] ^ mask[i%maskLen];
+    }
+  },
+
+  /** Computes frame size on the wire from data to be sent
+   *
+   * @param {Buffer} data - data.length is the assumed payload size
+   * @param {Boolean} mask - true if a mask will be sent (TO_SERVER)
+   */
+  frameSizeFromData: function(data, mask) {
+    var headerSize = 10; 
+    if (data.length < 0x7E) {
+      headerSize = 2;
+    } else if (data.length < 0xFFFF) {
+      headerSize = 4;
+    }
+    return headerSize + data.length + (mask ? 4 : 0);
+  },
+
+  frameOpCodes: {
+    CONT:     0x00,
+    TEXT:     0x01,
+    BIN:      0x02
+  },
+
+  mask: {
+    TO_SERVER: 0x80,
+    TO_CLIENT: 0x00
+  },
+
+  fin: {
+    CONT: 0x00,
+    FIN: 0x80
+  }
+};
+
+
+// createWebServer constructor and options
+/////////////////////////////////////////////////////////////////////
+
+/**
+ * @class
+ * @name ThriftWebServerOptions
+ * @property {string} staticFilePath - Path to serve static files from, if 
+ *      absent or "" static file service is disabled
+ * @property {TLSOptions} tlsOptions - Node.js TLS options 
+ *      (see: nodejs.org/api/tls.html), if not present or null regular http
+ *      is used, at least a key and a cert must be defined to use SSL/TLS
+ * @property {object} services - An object hash mapping service URIs to 
+ *      ThriftServiceOptions objects
+ * @see {@link ThriftServiceOptions}
+ */
+
+/**
+ * @class
+ * @name ThriftServiceOptions
+ * @property {object} transport - The layered transport to use (defaults 
+ *                                to none).
+ * @property {object} protocol - The Thrift Protocol to use (defaults to 
+ *                               TBinaryProtocol).
+ * @property {object} cls - The Thrift Service class generated by the IDL 
+ *                          Compiler for the service.
+ * @property {object} handler - The handler methods for the Thrift Service.
+ */
+
+/** 
+ * Creates a Thrift server which can serve static files and/or one or
+ * more Thrift Services. 
+ * @param {ThriftWebServerOptions} options - The server configuration.
+ * @returns {object} - The Thrift server.
+ */
+exports.createWebServer = function(options) {
+  var baseDir = options.staticFilePath;
+  var contentTypesByExtension = {
+    '.txt': 'text/plain',
+    '.html': 'text/html',
+    '.css': 'text/css',
+    '.xml': 'application/xml',
+    '.json': 'application/json',
+    '.js': 'application/javascript',
+    '.jpg': 'image/jpeg',
+    '.jpeg': 'image/jpeg',
+    '.gif': 'image/gif',
+    '.png': 'image/png',
+    '.svg': 'image/svg+xml'
+  };
+
+  //Setup all of the services
+  var services = options.services;
+  for (svc in services) {
+    var svcObj = services[svc];
+    var processor = svcObj.cls.Processor || svcObj.cls;
+    svcObj.processor = new processor(svcObj.handler);
+    svcObj.transport = svcObj.transport ? svcObj.transport : TBufferedTransport;
+    svcObj.protocol = svcObj.protocol ? svcObj.protocol : TBinaryProtocol;
+  }
+
+  //Handle POST methods (TXHRTransport)
+  function processPost(request, response) {
+    var uri = url.parse(request.url).pathname;
+    var svc = services[uri];
+    if (!svc) {
+      //TODO: add support for non Thrift posts
+      response.writeHead(500);
+      response.end();
+      return;
+    }
+
+    request.on('data', svc.transport.receiver(function(transportWithData) {
+      var input = new svc.protocol(transportWithData);
+      var output = new svc.protocol(new svc.transport(undefined, function(buf) {
+        try {
+          response.writeHead(200);
+          response.end(buf);
+        } catch (err) {
+          response.writeHead(500);
+          response.end();
+        }
+      }));
+
+      try {
+        svc.processor.process(input, output);
+        transportWithData.commitPosition();
+      }
+      catch (err) {
+        if (err instanceof TTransport.InputBufferUnderrunError) {
+          transportWithData.rollbackPosition();
+        }
+        else {
+          response.writeHead(500);
+          response.end();
+        }
+      }
+    }));
+  }
+
+  //Handle GET methods (Static Page Server)
+  function processGet(request, response) {
+    //Undefined or empty base directory means do not serve static files
+    if (!baseDir || "" == baseDir) {
+      response.writeHead(404);
+      response.end();
+      return;      
+    }
+    //Locate the file requested
+    var uri = url.parse(request.url).pathname;
+    var filename = path.join(baseDir, uri);
+    fs.exists(filename, function(exists) {
+      if(!exists) {
+        response.writeHead(404);
+        response.end();
+        return;
+      }
+     
+      if (fs.statSync(filename).isDirectory()) {
+        filename += '/index.html';
+      }
+     
+      fs.readFile(filename, "binary", function(err, file) {
+        if (err) {
+          response.writeHead(500);
+          response.end(err + "\n");
+          return;
+        }
+        var headers = {};
+        var contentType = contentTypesByExtension[path.extname(filename)];
+        if (contentType) {
+          headers["Content-Type"] = contentType;
+        }
+        response.writeHead(200, headers);
+        response.write(file, "binary");
+        response.end();
+      });
+    });
+  }
+
+  //Handle WebSocket calls (TWebSocketTransport)
+  function processWS(data, socket) {
+    var svc = services[Object.keys(services)[0]];
+    //TODO: add multiservice support (maybe multiplexing is the answer for both XHR and WS?)
+
+    svc.transport.receiver(function(transportWithData) {
+      var input = new svc.protocol(transportWithData);
+      var output = new svc.protocol(new svc.transport(undefined, function(buf) {
+        try {
+          var frame = wsFrame.encode(buf);
+          socket.write(frame);
+        } catch (err) {
+          //TODO: Add better error processing
+        }
+      }));
+
+      try {
+        svc.processor.process(input, output);
+        transportWithData.commitPosition();
+      }
+      catch (err) {
+        if (err instanceof TTransport.InputBufferUnderrunError) {
+          transportWithData.rollbackPosition();
+        }
+        else {
+          //TODO: Add better error processing
+        }
+      }
+    })(data);
+  }
+
+  //Create the server (HTTP or HTTPS)
+  var server = null;
+  if (options.tlsOptions) {
+    server = https.createServer(options.tlsOptions);
+  } else {
+    server = http.createServer();
+  }
+
+  //Wire up listeners for request(GET[files]), request(POST[XHR]), upgrade(WebSocket)
+  server.on('request', function(request, response) {
+    if (request.method === 'POST') {
+      processPost(request, response);
+    } else if (request.method === 'GET') {
+      processGet(request, response);
+    } else {
+      response.writeHead(500);
+      response.end();
+    }
+  }).on('upgrade', function(request, socket, head) {
+    var hash = crypto.createHash("sha1")
+    hash.update(request.headers['sec-websocket-key'] + "258EAFA5-E914-47DA-95CA-C5AB0DC85B11");
+    socket.write("HTTP/1.1 101 Switching Protocols\r\n" +
+                   "Upgrade: websocket\r\n" +
+                   "Connection: Upgrade\r\n" +
+                   "Sec-WebSocket-Accept: " + hash.digest("base64") + "\r\n" +
+                   "\r\n");  
+    socket.on('data', function(frame) {
+      do {
+        var result = wsFrame.decode(frame);
+        processWS(result.data, socket);
+        frame = result.nextFrame;
+      } while (frame);
+    });
+  });
+
+  //Return the server
+  return server;
+};
+
+
+
+
+
+
