Browse Source

Rework lib/io.js and all I/O related classes using async/await pattern

Rework I/O classes requestInput function to return a promise instead of receiving a callback as a parameter
Lucas de Souza 4 years ago
parent
commit
7b9a1c5dba
7 changed files with 90 additions and 79 deletions
  1. 9 6
      js/io/domConsole.js
  2. 6 3
      js/io/domInput.js
  3. 1 1
      js/io/input.js
  4. 42 46
      js/processor/lib/io.js
  5. 10 7
      js/util/inputTest.js
  6. 12 9
      js/util/input_assessment.js
  7. 10 7
      js/util/testConsole.js

+ 9 - 6
js/io/domConsole.js

@@ -315,12 +315,15 @@ export class DOMConsole {
     this.cursorInterval = null;
   }
 
-  requestInput (callback, anyKey = false) {
-    this.inputListeners.push(callback);
-    this.anyKey = anyKey;
-    if(this.idleInterval == null)
-      this.scheduleNotify();
-    this.showInput();
+  requestInput (anyKey = false) {
+    const promise = new Promise( (resolve, _) => {
+      this.inputListeners.push(resolve);
+      this.anyKey = anyKey;
+      if(this.idleInterval == null)
+        this.scheduleNotify();
+      this.showInput();
+    });
+    return promise;
   }
 
   sendOutput (text) {

+ 6 - 3
js/io/domInput.js

@@ -27,9 +27,12 @@ export class DOMInput extends Input{
     }
   }
 
-  requestInput (callback) {
-    this.listeners.push(callback);
-    this.el.focus();
+  requestInput () {
+    const promise = new Promise( (resolve, _) => {
+      this.listeners.push(resolve);
+      this.el.focus();
+    });
+    return promise;
   }
 
   notifyInput (text) {

+ 1 - 1
js/io/input.js

@@ -1,6 +1,6 @@
 export class Input {
 
-  requestInput (callback) {
+  requestInput () {
     throw new Error("Must be implemented");
   }
 

+ 42 - 46
js/processor/lib/io.js

@@ -6,11 +6,11 @@ import { ProcessorErrorFactory } from "./../error/processorErrorFactory";
 import { StoreValue } from '../store/value/store_value';
 
 export function createOutputFun () {
-  const writeFunction = function (store, _) {
+  const writeFunction = async function (store, _) {
     const val = store.applyStore('p1');
     this.output.sendOutput(convertToString(val.get(), val.type));
     store.mode = Modes.RETURN;
-    return Promise.resolve(store);
+    return store;
   }
   const block = new Commands.CommandBlock([], [new Commands.SysCall(writeFunction)]);
   const func = new Commands.Function('$write', Types.VOID,
@@ -20,51 +20,47 @@ export function createOutputFun () {
 }
 
 export function createInputFun () {
-  const readFunction = function (store, _) {
-    const request = new Promise((resolve, _) => {
-      this.input.requestInput(resolve);
-    });
-    return request.then(text => {
-      const typeToConvert = store.applyStore('p1').type;
-      let type = null
-      let result = null;
-      try {
-        if (typeToConvert.isCompatible(Types.INTEGER)) {
-          result = toInt(text.trim()).trunc();
-          type = Types.INTEGER;
-        } else if (typeToConvert.isCompatible(Types.REAL)) {
-          result = toReal(text.trim())
-          type = Types.REAL;
-        } else if (typeToConvert.isCompatible(Types.BOOLEAN)) {
-          result = toBool(text.trim())
-          type = Types.BOOLEAN;
-        } else if (typeToConvert.isCompatible(Types.STRING)) {
-          result = toString(text)
-          type  = Types.STRING;
-        } else {
-          return Promise.reject(new Error("!!!!Critical error: Unknown type in readFunction!!!!"));
-        }
-      } catch (_) {
-        if(this.mode == Modes.ABORT) {
-          store.mode = Modes.RETURN;
-          return Promise.resolve(store);
-        }
-        const stringInfo = typeToConvert.stringInfo()[0]
-        const realObject = store.getStoreObject("p1");
-        if (realObject.getReferenceDimension() > 0) {
-          const arrayInfo = realObject.type.stringInfo()[0];
-          const dim = realObject.getReferenceDimension();
-          const error = ProcessorErrorFactory.invalid_read_type_array(text, stringInfo.type, stringInfo.dim, realObject.getRefObj(), arrayInfo.type, dim, this.function_call_stack.pop());
-          return Promise.reject(error);
-        }
-        const error = ProcessorErrorFactory.invalid_read_type(text, stringInfo.type, stringInfo.dim, realObject.getRefObj(), this.function_call_stack.pop());
-        return Promise.reject(error);
+  const readFunction = async function (store, _) {
+    const text = await this.input.requestInput();
+    const typeToConvert = store.applyStore('p1').type;
+    let type = null
+    let result = null;
+    try {
+      if (typeToConvert.isCompatible(Types.INTEGER)) {
+        result = toInt(text.trim()).trunc();
+        type = Types.INTEGER;
+      } else if (typeToConvert.isCompatible(Types.REAL)) {
+        result = toReal(text.trim())
+        type = Types.REAL;
+      } else if (typeToConvert.isCompatible(Types.BOOLEAN)) {
+        result = toBool(text.trim())
+        type = Types.BOOLEAN;
+      } else if (typeToConvert.isCompatible(Types.STRING)) {
+        result = toString(text)
+        type  = Types.STRING;
+      } else {
+        throw new Error("!!!!Critical error: Unknown type in readFunction!!!!");
       }
-      const stoValue = new StoreValue(type, result);
-      store.updateStore('p1', stoValue);
-      store.mode = Modes.RETURN;
-      return Promise.resolve(store);
-    });
+    } catch (_) {
+      if(this.mode == Modes.ABORT) {
+        store.mode = Modes.RETURN;
+        return store;
+      }
+      const stringInfo = typeToConvert.stringInfo()[0]
+      const realObject = store.getStoreObject("p1");
+      if (realObject.getReferenceDimension() > 0) {
+        const arrayInfo = realObject.type.stringInfo()[0];
+        const dim = realObject.getReferenceDimension();
+        throw ProcessorErrorFactory.invalid_read_type_array(text, stringInfo.type, stringInfo.dim,
+          realObject.getRefObj(), arrayInfo.type, dim, this.function_call_stack.pop());
+      }
+      throw ProcessorErrorFactory.invalid_read_type(text, stringInfo.type, stringInfo.dim,
+        realObject.getRefObj(), this.function_call_stack.pop());
+    }
+    const stoValue = new StoreValue(type, result);
+    store.updateStore('p1', stoValue);
+    store.mode = Modes.RETURN;
+    return store;
   }
   const block = new Commands.CommandBlock([],  [new Commands.SysCall(readFunction)]);
   const func = new Commands.Function('$read', Types.VOID,

+ 10 - 7
js/util/inputTest.js

@@ -9,12 +9,15 @@ export class InputTest extends Input {
     this.inputList = inputList;
   }
 
-  requestInput (callback) {
-    if(this.index < this.inputList.length) {      
-      callback(this.inputList[this.index]);
-      this.index++;
-    } else {
-      throw new Error(LocalizedStrings.getError("exceeded_input_request"));
-    }
+  requestInput () {
+    const promise = new Promise( (resolve, reject) => {
+      if(this.index < this.inputList.length) {      
+        resolve(this.inputList[this.index]);
+        this.index++;
+      } else {
+        reject(new Error(LocalizedStrings.getError("exceeded_input_request")));
+      }
+    });
+    return promise
   }
 }

+ 12 - 9
js/util/input_assessment.js

@@ -11,15 +11,18 @@ export class InputAssessment extends Input {
     });
   }
 
-  requestInput (callback) {
-    if(this.index < this.input_list.length) {
-      const input = this.input_list[this.index];
-      input.read = true;
-      this.index += 1;
-      callback(input.value);
-    } else {
-      throw new Error(LocalizedStrings.getError("exceeded_input_request"));
-    }
+  requestInput () {
+    const promise = new Promise( (resolve, reject) => {
+      if(this.index < this.input_list.length) {
+        const input = this.input_list[this.index];
+        input.read = true;
+        this.index += 1;
+        resolve(input.value);
+      } else {
+        reject(new Error(LocalizedStrings.getError("exceeded_input_request")));
+      }
+    });
+    return promise
   }
 
   isInputAvailable () {

+ 10 - 7
js/util/testConsole.js

@@ -40,13 +40,16 @@ export class TestConsole {
     }
   }
 
-  requestInput (callback) {
-    if(this.index < this.inputList.length) {      
-      callback(this.inputList[this.index]);
-      this.index++;
-    } else {
-      throw new Error(LocalizedStrings.getError("exceeded_input_request"));
-    }
+  requestInput () {
+    const promise = new Promise( (resolve, reject) => {
+      if(this.index < this.inputList.length) {      
+        resolve(this.inputList[this.index]);
+        this.index++;
+      } else {
+        reject(new Error(LocalizedStrings.getError("exceeded_input_request")));
+      }
+    });
+    return promise
   }
 
   sendOutput (text) {