Forráskód Böngészése

Performance Improvements for uwebsocket.js (#8499)

* 1. Added Slow-JSON-Stringify based JSON serialization to improve the speed.

2. Used a different sort method which is sligthly faster and gives better performance for this usecase.

3. Updated to latest postgres module

* More Optimisation for fortunes
Avoiding the extra object instantiation multiple times.

* Added links for reference as requested by co contributor.

* Removed reference to just js
srisaiswaroop 1 éve
szülő
commit
d1b15ff3c7

+ 10 - 4
frameworks/JavaScript/uwebsockets.js/package-lock.json

@@ -9,19 +9,25 @@
       "version": "0.0.1",
       "license": "MIT",
       "dependencies": {
-        "postgres": "^3.3.5",
+        "postgres": "^3.4.0",
+        "slow-json-stringify": "^2.0.1",
         "uWebSockets.js": "uNetworking/uWebSockets.js#v20.32.0"
       }
     },
     "node_modules/postgres": {
-      "version": "3.3.5",
-      "resolved": "https://registry.npmjs.org/postgres/-/postgres-3.3.5.tgz",
-      "integrity": "sha512-+JD93VELV9gHkqpV5gdL5/70HdGtEw4/XE1S4BC8f1mcPmdib3K5XsKVbnR1XcAyC41zOnifJ+9YRKxdIsXiUw==",
+      "version": "3.4.0",
+      "resolved": "https://registry.npmjs.org/postgres/-/postgres-3.4.0.tgz",
+      "integrity": "sha512-d7UtSoCg4hUtzxM9aRi3J8BrM6t0h4bQmgAHG96cDCNpP9CnnWQRdRl7WWNvKs0oOaQU2InGoOi1jETmdZK02g==",
       "funding": {
         "type": "individual",
         "url": "https://github.com/sponsors/porsager"
       }
     },
+    "node_modules/slow-json-stringify": {
+      "version": "2.0.1",
+      "resolved": "https://registry.npmjs.org/slow-json-stringify/-/slow-json-stringify-2.0.1.tgz",
+      "integrity": "sha512-jqyzIqTaSkRGcWdWqjmOLKHZgOGUT71ZCTsvQu1xGu9Mqaod7O26y5FJJEmaUQhaTWh0bkXv2qqN0i+EQsD1jQ=="
+    },
     "node_modules/uWebSockets.js": {
       "version": "20.31.0",
       "resolved": "git+ssh://[email protected]/uNetworking/uWebSockets.js.git#809b99d2d7d12e2cbf89b7135041e9b41ff84084"

+ 3 - 2
frameworks/JavaScript/uwebsockets.js/package.json

@@ -1,7 +1,8 @@
 {
   "dependencies": {
-    "postgres": "^3.3.5",
-    "uWebSockets.js": "uNetworking/uWebSockets.js#v20.32.0"
+    "postgres": "^3.4.0",
+    "uWebSockets.js": "uNetworking/uWebSockets.js#v20.32.0",
+    "slow-json-stringify": "^2.0.1"
   },
   "license": "MIT",
   "main": "src/server.js",

+ 17 - 9
frameworks/JavaScript/uwebsockets.js/src/server.js

@@ -5,6 +5,9 @@ import {
   getQueriesCount,
   handleError,
   escape,
+  jsonSerializer,
+  worldObjectSerializer,
+  sortByMessage
 } from "./utils.js";
 
 let db;
@@ -22,7 +25,8 @@ webserver.get("/plaintext", (response) => {
 webserver.get("/json", (response) => {
   addBenchmarkHeaders(response);
   response.writeHeader("Content-Type", "application/json");
-  response.end(JSON.stringify({ message: "Hello, World!" }));
+  // response.end(JSON.stringify({ message: "Hello, World!" }));
+  response.end(jsonSerializer({ message: "Hello, World!" }));
 });
 
 if (db) {
@@ -32,7 +36,7 @@ if (db) {
     });
 
     try {
-      const rows = await db.find(generateRandomNumber());
+      const row = await db.find(generateRandomNumber());
 
       if (response.aborted) {
         return;
@@ -41,7 +45,8 @@ if (db) {
       response.cork(() => {
         addBenchmarkHeaders(response);
         response.writeHeader("Content-Type", "application/json");
-        response.end(JSON.stringify(rows));
+        // response.end(JSON.stringify(rows));
+        response.end(worldObjectSerializer(row));
       });
     } catch (error) {
       if (response.aborted) {
@@ -85,6 +90,8 @@ if (db) {
       handleError(error, response);
     }
   });
+  
+  const extra = { id: 0, message: "Additional fortune added at request time." };
 
   webserver.get("/fortunes", async (response) => {
     response.onAborted(() => {
@@ -92,18 +99,19 @@ if (db) {
     });
 
     try {
-      const rows = await db.fortunes();
+      const rows = [extra, ...await db.fortunes()];
 
       if (response.aborted) {
         return;
       }
 
-      rows.push({
-        id: 0,
-        message: "Additional fortune added at request time.",
-      });
+      // rows.push({
+      //   id: 0,
+      //   message: "Additional fortune added at request time.",
+      // });
 
-      rows.sort((a, b) => (a.message < b.message) ? -1 : 1);
+      // rows.sort((a, b) => (a.message < b.message) ? -1 : 1);
+      sortByMessage(rows)
 
       const n = rows.length
 

+ 28 - 1
frameworks/JavaScript/uwebsockets.js/src/utils.js

@@ -1,3 +1,5 @@
+import { sjs, attr } from 'slow-json-stringify'
+
 /**
  * Add Benchmark HTTP response headers.
  *
@@ -42,7 +44,7 @@ export function getQueriesCount(request) {
  *
  */
 export function generateRandomNumber() {
-  return Math.floor(Math.random() * 10000) + 1;
+  return Math.ceil(Math.random() * 10000);
 }
 
 /**
@@ -57,3 +59,28 @@ export function escape(text) {
   if (unsafeHTMLMatcher.test(text) === false) return text;
   return text.replace(unsafeHTMLMatcher, function (m) { return escapeHTMLRules[m] || m; });
 }
+
+/**
+ * Using Slow json stringify module to get faster results 
+ */
+export const jsonSerializer = sjs({ message: attr("string")}); 
+export const worldObjectSerializer = sjs({ id: attr('number'), randomnumber: attr('number') });
+// export const worldObjectsSerializer = sjs({ rows: attr("array", worldObjectSerializer) });
+
+/**
+ * Using Sort method which is performant for the test scenario
+ * @returns 
+ */
+export function sortByMessage (arr) {
+  const n = arr.length
+  for (let i = 1; i < n; i++) {
+    const c = arr[i]
+    let j = i - 1
+    while ((j > -1) && (c.message < arr[j].message)) {
+      arr[j + 1] = arr[j]
+      j--
+    }
+    arr[j + 1] = c
+  }
+  return arr
+}