2
0
mirror of https://github.com/esiur/esiur-js.git synced 2025-05-06 04:22:58 +00:00
This commit is contained in:
Ahmed Zamil 2022-03-13 11:28:38 +03:00
parent 7b1b844753
commit 15eb1453e7
55 changed files with 24308 additions and 4587 deletions

View File

@ -1,18 +1,6 @@
# Esiur.JS
Esiur Library for Javascript
# Usage
# Demo
npm run demo
import io;
import sys;
import json;
res = json.load(sys.stdin)
temp = res['main']['temp']
hum = res['main']['humidity']
vis = res['visibility']
wind = res['wind']['speed']
desc = res['weather'][0]['description']
sys.stdout.buffer.write(f'مرحبا بكم في أعمال, درجة الحرارة {temp} مئوية, الرطوبة {hum}%, مدى الرؤية {vis} متر, سرعة الرياح {wind} كيلومتر في الساعة, {desc}'.encode('utf8'))

File diff suppressed because it is too large Load Diff

File diff suppressed because it is too large Load Diff

View File

@ -6,10 +6,10 @@ import DistributedServer from "../../src/Net/IIP/DistributedServer.js";
import IMembership from "../../src/Security/Membership/IMembership.js";
import WSocket from "../../src/Net/Sockets/WSocket.js";
import MemoryStore from "../../src/Stores/MemoryStore.js";
import DC from "../../src/Data/DataConverter.js";
import DC from "../../src/Data/DC.js";
import IResource from "../../src/Resource/IResource.js";
import Structure from "../../src/Data/Structure.js";
import DataType from "../../src/Data/DataType.js";
import TransmissionType, { TransmissionTypeIdentifier } from "../../src/Data/TransmissionType.js";
import TypedMap from "../../src/Data/TypedMap.js";
const require = createRequire(import.meta.url);
@ -36,15 +36,15 @@ class MyChat extends IResource {
static get template() {
return {
namespace: "Chat",
properties: [["title", DataType.String], ["messages", DataType.StructureArray], ["users", DataType.StringArray]],
events: [["message", DataType.Structure], ["voice", 0, {listenable: true }], ["login"], ["logout"]],
functions: [[ "send", {msg: DataType.String} ]]
properties: [["title", String], ["messages", Array], ["users", Array]],
events: [["message", Map], ["voice", 0, {listenable: true }], ["login"], ["logout"]],
functions: [[ "send", [["msg", String, {optional: true}] ]]]
};
}
constructor() {
super();
this.messages = [new Structure({usr: "Admin", msg: "Welcome to Esiur", date: new Date()})];
this.messages = [new TypedMap({usr: "Admin", msg: "Welcome to Esiur", date: new Date()})];
this.title = "Chat Room";
}
@ -54,7 +54,7 @@ class MyChat extends IResource {
send(msg, sender)
{
let s = new Structure({ msg, usr: sender.session.remoteAuthentication.username, date: new Date()});
let s = new TypedMap({ msg, usr: sender.session.remoteAuthentication.username, date: new Date()});
this.messages.push(s);
this._emit("message", s);
}
@ -64,6 +64,10 @@ class MyChat extends IResource {
}
}
let x = TransmissionType.compose(TransmissionTypeIdentifier.List, new DC([1,2,3,4,5,6]));
let tt = TransmissionType.parse(x, 0, x.length);
let sys = await Warehouse.new(MemoryStore, "sys");
let ms = await Warehouse.new(MyMembership, "ms");
let chat = await Warehouse.new(MyChat, "chat", sys);

View File

@ -34,7 +34,7 @@
{
let el = document.createElement("div");
let list = document.getElementById("list");
el.innerHTML = `<span>${message.usr}</span><span>${message.msg}</span><span>${message.date.toLocaleTimeString()}</span>`;
el.innerHTML = `<span>${message.get("usr")}</span><span>${message.get("msg")}</span><span>${message.get("date").toLocaleTimeString()}</span>`;
list.append(el);
list.scrollTop = list.scrollHeight;
}

43
demo/dotnet/service.js Normal file
View File

@ -0,0 +1,43 @@
import Warehouse from "../../src/Resource/Warehouse.js";
import { createRequire } from 'module'
const require = createRequire(import.meta.url);
const WebSocket = require('ws');
var remote = await Warehouse.get('iip://localhost/mem/service');
// remote?.instance?.template.properties.forEach((element) => {
// console.log(element.name);
// console.log(remote[element.name]);
// });
await remote?.Void();
await remote?.Connection('ss', 33);
await remote?.ConnectionOptional('Test 2', 88);
var rt = await remote?.Optional('Optional', 311);
console.log(rt);
var t2 = await remote?.GetTuple2(1, 'A');
console.log(t2);
var t3 = await remote?.GetTuple3(1, 'A', 1.3);
console.log(t3);
var t4 = await remote?.GetTuple4(1, 'A', 1.3, true);
console.log(t4);
remote?.on('StringEvent', (args) => console.log(`StringEvent ${args}`));
remote?.on('ArrayEvent', (args) => console.log(`ArrayEvent ${args}`));
await remote?.InvokeEvents('Hello');
// var mcr = MyChildRecord()
// ..ChildName = "I'm Child"
// ..Name = 'Dad'
// ..Score = 332
// ..Id = 44;
// var rec = await remote?.SendRecord(mcr);
// print(rec);

View File

@ -6,7 +6,7 @@ import DistributedServer from "../../src/Net/IIP/DistributedServer.js";
import IMembership from "../../src/Security/Membership/IMembership.js";
import WSocket from "../../src/Net/Sockets/WSocket.js";
import MemoryStore from "../../src/Stores/MemoryStore.js";
import DC from "../../src/Data/DataConverter.js";
import DC from "../../src/Data/DC.js";
import IResource from "../../src/Resource/IResource.js";
import Structure from "../../src/Data/Structure.js";
import MongoDBStore from "../../src/Stores/MongoDBStore.js";

5149
package-lock.json generated

File diff suppressed because it is too large Load Diff

View File

@ -1,6 +1,6 @@
{
"name": "esiur",
"version": "1.8.2",
"version": "2.0.0",
"description": "Distributed Object Framework",
"main": "esiur.js",
"type": "module",
@ -9,7 +9,6 @@
"babel": "./node_modules/.bin/babel src -d build",
"build": "browserify src/esiur.js -t babelify --outfile build/esiur.js",
"prepublish": "browserify src/esiur.js -t babelify --outfile build/esiur.js"
},
"repository": {
"type": "git",

View File

@ -71,7 +71,6 @@ export default class AsyncQueue extends AsyncReply
remove(reply)
{
console.log("REMOVE QUEUE");
this.list.splice(this.list.indexOf(reply), 1);
this.processQueue();
}

View File

@ -153,7 +153,7 @@ export default class AsyncReply extends Promise
this.chunkCallbacks = [];
this.exception = new AsyncException();// null;
var self = this;
//var self = this;
if (result !== undefined && !(result instanceof Function)) {
this.result = result;

View File

@ -26,8 +26,7 @@
"use strict";
import DataType from './DataType.js';
import DC from './DataConverter.js';
import DC from './DC.js';
export default class BinaryList
{
@ -35,216 +34,198 @@ export default class BinaryList
constructor()
{
this.list = [];
//this.data = [];
}
addRange(bl)
{
for(var i = 0; i < bl.list.length; i++)
this.list.push(bl.list[i]);
addDateTime(value, endian) {
this.addDC(DC.dateTimeToBytes(value, endian));
return this;
}
add(typedValue, position)
{
if (position !== undefined)
this.list.splice(position, 0, typedValue);
else
this.list.push(typedValue);
insertDateTime(position, value, endian) {
this.insertDC(position, DC.dateTimeToBytes(value, endian));
return this;
}
addDateTimeArray(value, endian) {
this.addDC(DC.dateTimeArrayToBytes(value, endian));
return this;
}
insertDateTimeArray(position, value, endian) {
this.insertDC(position, DC.dateTimeArrayToBytes(value, endian));
return this;
}
addGuid(value) {
this.addDC(DC.guidToBytes(value));
return this;
}
insertGuid(position, value) {
this.insertDC(position, DC.guidToBytes(value));
return this;
}
addUint8Array(value) {
this.addDC(value);
return this;
}
addDC(value) {
this.list.push(...value);
return this;
}
insertUint8Array(position, value) {
this.insertDC(position, value);
return this;
}
addString(value) {
this.addDC(DC.stringToBytes(value));
return this;
}
insertString(position, value) {
this.insertDC(position, DC.stringToBytes(value));
return this;
}
insertUint8(position, value) {
this.list.splice(position, 0, value);
return this;
}
addUint8(value) {
this.list.push(value);
return this;
}
addInt8(value) {
this.list.push(value);
return this;
}
insertInt8(position, value) {
this.list.splice(position, 0, value);
return this;
}
addChar(value) {
this.addDC(DC.charToBytes(value));
return this;
}
insertChar(position, value) {
this.insertDC(position, DC.charToBytes(value));
return this;
}
addBoolean(value) {
this.addDC(DC.boolToBytes(value));
return this;
}
insertBoolean(position, value) {
this.insertDC(position, DC.boolToBytes(value));
return this;
}
addUint16(value, endian) {
this.addDC(DC.uint16ToBytes(value, endian));
return this;
}
insertUint16(position, value, endian) {
this.insertDC(position, DC.uint16ToBytes(value, endian));
return this;
}
addInt16(value, endian) {
this.addDC(DC.int16ToBytes(value, endian));
return this;
}
insertInt16(position, value, endian) {
this.insertDC(position, DC.int16ToBytes(value, endian));
return this;
}
addUint32(value, endian) {
this.addDC(DC.uint32ToBytes(value, endian));
return this;
}
insertUint32(position, value, endian ) {
this.insertDC(position, DC.uint32ToBytes(value, endian));
return this;
}
addInt32(value, endian) {
this.addDC(DC.int32ToBytes(value, endian));
return this;
}
insertInt32(position, value, endian) {
this.insertDC(position, DC.int32ToBytes(value, endian));
return this;
}
addUint64(value, endian) {
this.addDC(DC.uint64ToBytes(value, endian));
return this;
}
insertUint64( position, value, endian) {
this.insertDC(position, DC.uint64ToBytes(value, endian));
return this;
}
addInt64(value, endian) {
this.addDC(DC.int64ToBytes(value, endian));
return this;
}
insertInt64(position, value, endian) {
this.insertDC(position, DC.int64ToBytes(value, endian));
return this;
}
addFloat32(value, endian) {
this.addDC(DC.float32ToBytes(value, endian));
return this;
}
insertFloat32(position, value, endian ) {
this.insertDC(position, DC.float32ToBytes(value, endian));
return this;
}
addFloat64(value, endian) {
this.addDC(DC.float64ToBytes(value, endian));
return this;
}
insertFloat64(position, value, endian) {
this.insertDC(position, DC.float64ToBytes(value, endian));
return this;
}
get length()
{
return this.toArray().length;
return this.list.length;
}
toArray()
{
var ars = [];
// calculate length
for(var i = 0; i < this.list.length; i++)
{
switch (this.list[i].type)
{
case DataType.Bool:
ars.push(DC.boolToBytes(this.list[i].value));
break;
case DataType.UInt8:
ars.push(DC.uint8ToBytes(this.list[i].value));
break;
case DataType.Int8:
ars.push(DC.int8ToBytes(this.list[i].value));
break;
case DataType.Char:
ars.push(DC.charToBytes(this.list[i].value));
break;
case DataType.UInt16:
ars.push(DC.uint16ToBytes(this.list[i].value));
break;
case DataType.Int16:
ars.push(DC.int16ToBytes(this.list[i].value));
break;
case DataType.UInt32:
ars.push(DC.uint32ToBytes(this.list[i].value));
break;
case DataType.Int32:
ars.push(DC.int32ToBytes(this.list[i].value));
break;
case DataType.UInt64:
ars.push(DC.uint64ToBytes(this.list[i].value));
break;
case DataType.Int64:
ars.push(DC.int64ToBytes(this.list[i].value));
break;
case DataType.Float32:
ars.push(DC.float32ToBytes(this.list[i].value));
break;
case DataType.Float64:
ars.push(DC.float64ToBytes(this.list[i].value));
break;
case DataType.String:
ars.push(DC.stringToBytes(this.list[i].value));
break;
case DataType.DateTime:
ars.push(DC.dateTimeToBytes(this.list[i].value));
break;
case DataType.UInt8Array:
ars.push(this.list[i].value);
break;
case DataType.UInt16Array:
ars.push(DC.uint16ArrayToBytes(this.list[i].value));
break;
case DataType.UInt32Array:
ars.push(DC.uint32ArrayToBytes(this.list[i].value));
break;
case DataType.Int16Array:
ars.push(DC.int16ArrayToBytes(this.list[i].value));
break;
case DataType.Int32Array:
ars.push(DC.int32ArrayToBytes(this.list[i].value));
break;
case DataType.Float32Array:
ars.push(DC.float32ArrayToBytes(this.list[i].value));
break;
case DataType.Float64Array:
ars.push(DC.float64ArrayToBytes(this.list[i].value));
break;
//case DataType.Resource:
// ars.push(DC.uint32ToBytes(this.list[i].value.instance.id));
// break;
//case DataType.DistributedResource:
// ars.push(DC.int8ToBytes(this.list[i].value));
// break;
}
}
var length = 0;
ars.forEach(function(a){
length += a.length ;//?? a.byteLength;
});
var rt = new Uint8Array(length);
var offset = 0;
for(var i = 0; i < ars.length; i++) {
rt.set(ars[i], offset);
offset+=ars[i].length;// ?? ars[i].byteLength;
}
return rt;
return new Uint8Array(this.list);
}
toDC()
{
return new DC(this.toArray());
return new DC(this.list);
}
addDateTime(value, position)
{
return this.add({type: DataType.DateTime, value: value}, position);
}
addUint8Array(value, position)
{
return this.add({type: DataType.UInt8Array, value: value}, position);
}
addHex(value, position)
{
return this.addUint8Array(DC.hexToBytes(value), position);
}
addString(value, position)
{
return this.add({type: DataType.String, value: value}, position);
}
addUint8(value, position)
{
return this.add({type: DataType.UInt8, value: value}, position);
}
addInt8(value, position)
{
return this.add({type: DataType.Int8, value: value}, position);
}
addChar(value, position)
{
return this.add({type: DataType.Char, value: value}, position);
}
addUint16(value, position)
{
return this.add({type: DataType.UInt16, value: value}, position);
}
addInt16(value, position)
{
return this.add({type: DataType.Int16, value: value}, position);
}
addUint32(value, position)
{
return this.add({type: DataType.UInt32, value: value}, position);
}
addInt32(value, position)
{
return this.add({type: DataType.Int32, value: value}, position);
}
addUint64(value, position)
{
return this.add({type: DataType.UInt64, value: value}, position);
}
addInt64(value, position)
{
return this.add({type: DataType.Int64, value: value}, position);
}
addFloat32(value, position)
{
return this.add({type: DataType.Float32, value: value}, position);
}
addFloat64(value, position)
{
return this.add({type: DataType.Float64, value: value}, position);
}
}

File diff suppressed because it is too large Load Diff

View File

@ -32,6 +32,11 @@ import Guid from './Guid.js';
export const UNIX_EPOCH = 621355968000000000;
export const TWO_PWR_32 = (1 << 16) * (1 << 16);
export const Endian = {
Big: 0,
Little: 1
}
export default class DC extends Uint8Array
{
constructor(bufferOrSize) {
@ -63,6 +68,10 @@ export default class DC extends Uint8Array
return rt;
}
static fromList(list){
return new DC(list);
}
static hexToBytes(value)
{
// convert hex to Uint8Array
@ -79,73 +88,73 @@ export default class DC extends Uint8Array
return rt;
}
static charToBytes(value)
static charToBytes(value, endian)
{
var rt = new DC(2);
rt.setChar(0, value);
rt.setChar(0, value, endian);
return rt;
}
static int16ToBytes(value)
static int16ToBytes(value, endian)
{
var rt = new DC(2);
rt.setInt16(0, value);
rt.setInt16(0, value, endian);
return rt;
}
static uint16ToBytes(value)
static uint16ToBytes(value, endian)
{
var rt = new DC(2);
rt.setUint16(0, value);
rt.setUint16(0, value, endian);
return rt;
}
static int32ToBytes(value)
static int32ToBytes(value, endian)
{
var rt = new DC(4);
rt.setInt32(0, value);
rt.setInt32(0, value, endian);
return rt;
}
static uint32ToBytes(value)
static uint32ToBytes(value, endian)
{
var rt = new DC(4);
rt.setUint32(0, value);
rt.setUint32(0, value, endian);
return rt;
}
static float32ToBytes(value)
static float32ToBytes(value, endian)
{
var rt = new DC(4);
rt.setFloat32(0, value);
rt.setFloat32(0, value, endian);
return rt;
}
static int64ToBytes(value)
static int64ToBytes(value, endian)
{
var rt = new DC(8);
rt.setInt64(0, value);
rt.setInt64(0, value, endian);
return rt;
}
static uint64ToBytes(value)
static uint64ToBytes(value, endian)
{
var rt = new DC(8);
rt.setUint64(0, value);
rt.setUint64(0, value, endian);
return rt;
}
static float64ToBytes(value)
static float64ToBytes(value, endian)
{
var rt = new DC(8);
rt.setFloat64(0, value);
rt.setFloat64(0, value, endian);
return rt;
}
static dateTimeToBytes(value)
static dateTimeToBytes(value, endian)
{
var rt = new DC(8);
rt.setDateTime(0, value);
rt.setDateTime(0, value, endian);
return rt;
}
@ -172,68 +181,68 @@ export default class DC extends Uint8Array
return list.toArray();
}
static uint16ArrayToBytes(values)
static uint16ArrayToBytes(values, endian)
{
var rt = new DC(values.length * 2);
for(var i = 0; i < values.length; i++)
rt.setUint16(i * 2, values[i]);
rt.setUint16(i * 2, values[i], endian);
return rt;
}
static int16ArrayToBytes(values)
static int16ArrayToBytes(values, endian)
{
var rt = new DC(values.length * 2);
for(var i = 0; i < values.length; i++)
rt.setInt16(i * 2, values[i]);
rt.setInt16(i * 2, values[i], endian);
return rt;
}
static uint32ArrayToBytes(values)
static uint32ArrayToBytes(values, endian)
{
var rt = new DC(values.length * 4);
for(var i = 0; i < values.length; i++)
rt.setUint32(i * 4, values[i]);
rt.setUint32(i * 4, values[i], endian);
return rt;
}
static int32ArrayToBytes(values)
static int32ArrayToBytes(values, endian)
{
var rt = new DC(values.length * 4);
for(var i = 0; i < values.length; i++)
rt.setInt32(i * 4, values[i]);
rt.setInt32(i * 4, values[i], endian);
return rt;
}
static int64ArrayToBytes(values)
static int64ArrayToBytes(values, endian)
{
var rt = new DC(values.length * 8);
for(var i = 0; i < values.length; i++)
rt.setInt64(i * 8, values[i]);
rt.setInt64(i * 8, values[i], endian);
return rt;
}
static uint64ArrayToBytes(values)
static uint64ArrayToBytes(values, endian)
{
var rt = new DC(values.length * 8);
for(var i = 0; i < values.length; i++)
rt.setUint64(i * 8, values[i]);
rt.setUint64(i * 8, values[i], endian);
return rt;
}
static float32ArrayToBytes(values)
static float32ArrayToBytes(values, endian)
{
var rt = new DC(values.length * 4);
for(var i = 0; i < values.length; i++)
rt.setFloat32(i * 4, values[i]);
rt.setFloat32(i * 4, values[i], endian);
return rt;
}
static float64ArrayToBytes(values)
static float64ArrayToBytes(values, endian)
{
var rt = new DC(values.length * 8);
for(var i = 0; i < values.length; i++)
rt.setFloat64(i * 8, values[i]);
rt.setFloat64(i * 8, values[i], endian);
return rt;
}
@ -280,39 +289,34 @@ export default class DC extends Uint8Array
return this[offset];// this.dv.getUint8(offset);
}
getInt16(offset)
getInt16(offset, endian)
{
return this.dv.getInt16(offset);
return this.dv.getInt16(offset, endian != Endian.Big);
}
getUint16(offset)
getUint16(offset, endian)
{
return this.dv.getUint16(offset);
return this.dv.getUint16(offset, endian != Endian.Big);
}
getInt32(offset)
getInt32(offset, endian)
{
return this.dv.getInt32(offset);
return this.dv.getInt32(offset, endian != Endian.Big);
}
getInt32Little(offset)
getUint32(offset, endian)
{
return this.dv.getInt32(offset, true);
return this.dv.getUint32(offset, endian != Endian.Big);
}
getUint32(offset)
getFloat32(offset, endian)
{
return this.dv.getUint32(offset);
return this.dv.getFloat32(offset, endian != Endian.Big);
}
getFloat32(offset)
getFloat64(offset, endian)
{
return this.dv.getFloat32(offset);
}
getFloat64(offset)
{
return this.dv.getFloat64(offset);
return this.dv.getFloat64(offset, endian != Endian.Big);
}
setInt8(offset, value)
@ -325,34 +329,34 @@ export default class DC extends Uint8Array
return this.dv.setUint8(offset, value);
}
setInt16(offset, value)
setInt16(offset, value, endian)
{
return this.dv.setInt16(offset, value);
return this.dv.setInt16(offset, value, endian != Endian.Big);
}
setUint16(offset, value)
setUint16(offset, value, endian)
{
return this.dv.setUint16(offset, value);
return this.dv.setUint16(offset, value, endian != Endian.Big);
}
setInt32(offset, value)
setInt32(offset, value, endian)
{
return this.dv.setInt32(offset, value);
return this.dv.setInt32(offset, value, endian != Endian.Big);
}
setUint32(offset, value)
setUint32(offset, value, endian)
{
return this.dv.setUint32(offset, value);
return this.dv.setUint32(offset, value, endian != Endian.Big);
}
setFloat32(offset, value)
setFloat32(offset, value, endian)
{
return this.dv.setFloat32(offset, value);
return this.dv.setFloat32(offset, value, endian != Endian.Big);
}
setFloat64(offset, value)
setFloat64(offset, value, endian)
{
return this.dv.setFloat64(offset, value);
return this.dv.setFloat64(offset, value, endian != Endian.Big);
}
getInt8Array(offset, length)
@ -365,12 +369,12 @@ export default class DC extends Uint8Array
return new Uint8Array(this.buffer, offset, length);
}
copy(offset, length, elementSize, func, dstType)
copy(offset, length, elementSize, func, dstType, endian)
{
let rt = new dstType(length / elementSize);
let d = 0, end = offset + length;
for (let i = offset; i < end; i += elementSize)
rt[d++] = func.call(this, i);
rt[d++] = func.call(this, i, endian);
return rt;
}
@ -384,55 +388,47 @@ export default class DC extends Uint8Array
}
getInt16Array(offset, length)
getInt16Array(offset, length, endian)
{
return this.copy(offset, length, 2, this.getInt16, Int16Array);
return this.copy(offset, length, 2, this.getInt16, Int16Array, endian);
//return new Int16Array(this.clip(offset, length).buffer);
}
getUint16Array(offset, length)
getUint16Array(offset, length, endian)
{
return this.copy(offset, length, 2, this.getUint16, Uint16Array);
//return new Uint16Array(this.clip(offset, length).buffer);
return this.copy(offset, length, 2, this.getUint16, Uint16Array, endian);
}
getInt32Array(offset, length)
getInt32Array(offset, length, endian)
{
return this.copy(offset, length, 4, this.getInt32, Int32Array);
//return new Int32Array(this.clip(offset, length).buffer);
return this.copy(offset, length, 4, this.getInt32, Int32Array, endian);
}
getUint32Array(offset, length)
getUint32Array(offset, length, endian)
{
return this.copy(offset, length, 4, this.getUint32, Uint32Array);
//return new Uint32Array(this.clip(offset, length).buffer);
return this.copy(offset, length, 4, this.getUint32, Uint32Array, endian);
}
getFloat32Array(offset, length)
getFloat32Array(offset, length, endian)
{
return this.copy(offset, length, 4, this.getFloat32, Float32Array);
//return new Float32Array(this.clip(offset, length).buffer);
return this.copy(offset, length, 4, this.getFloat32, Float32Array, endian);
}
getFloat64Array(offset, length)
getFloat64Array(offset, length, endian)
{
return this.copy(offset, length, 8, this.getFloat64, Float64Array);
// return new Float64Array(this.clip(offset, length).buffer);
return this.copy(offset, length, 8, this.getFloat64, Float64Array, endian);
}
getInt64Array(offset, length)
getInt64Array(offset, length, endian)
{
return this.copy(offset, length, 8, this.getInt64, Float64Array);//BigInt64Array);
//return new Int64Array(this.clip(offset, length).buffer);
return this.copy(offset, length, 8, this.getInt64, Float64Array, endian);
}
getUint64Array(offset, length)
getUint64Array(offset, length, endian)
{
return this.copy(offset, length, 8, this.getUint64, Float64Array);//BigUint64Array);
//return new Uint64Array(this.clip(offset, length).buffer);
return this.copy(offset, length, 8, this.getUint64, Float64Array, endian);
}
getBoolean(offset)
@ -453,21 +449,21 @@ export default class DC extends Uint8Array
return rt;
}
getChar(offset)
getChar(offset, endian)
{
return String.fromCharCode(this.getUint16(offset));
return String.fromCharCode(this.getUint16(offset, endian));
}
setChar(offset, value)
setChar(offset, value, endian)
{
this.setUint16(offset, value.charCodeAt(0));
this.setUint16(offset, value.charCodeAt(0), endian);
}
getCharArray(offset, length)
getCharArray(offset, length, endian)
{
var rt = [];
for(var i = 0; i < length; i+=2)
rt.push(this.getChar(offset+i));
rt.push(this.getChar(offset+i, endian));
return rt;
}
@ -495,14 +491,14 @@ export default class DC extends Uint8Array
}
}
getStringArray(offset, length)
getStringArray(offset, length, endian)
{
var rt = [];
var i = 0;
while (i < length)
{
var cl = this.getUint32(offset + i);
var cl = this.getUint32(offset + i, endian);
i += 4;
rt.push(this.getString(offset + i, cl));
i += cl;
@ -512,55 +508,160 @@ export default class DC extends Uint8Array
}
// @TODO: Test numbers with bit 7 of h = 1
getInt64(offset)
getInt64(offset, endian)
{
var h = this.getInt32(offset);
var l = this.getInt32(offset + 4);
if (endian == Endian.Big) {
let bi = BigInt(0);
return h * TWO_PWR_32 + ((l >= 0) ? l : TWO_PWR_32 + l);
bi |= BigInt(this[offset++]) << 56n;
bi |= BigInt(this[offset++]) << 48n;
bi |= BigInt(this[offset++]) << 40n;
bi |= BigInt(this[offset++]) << 32n;
bi |= BigInt(this[offset++]) << 24n;
bi |= BigInt(this[offset++]) << 16n;
bi |= BigInt(this[offset++]) << 8n;
bi |= BigInt(this[offset++]);
return parseInt(bi);
} else {
let bi = BigInt(0);
bi |= BigInt(this[offset++]);
bi |= BigInt(this[offset++]) << 8n;
bi |= BigInt(this[offset++]) << 16n;
bi |= BigInt(this[offset++]) << 24n;
bi |= BigInt(this[offset++]) << 32n;
bi |= BigInt(this[offset++]) << 40n;
bi |= BigInt(this[offset++]) << 48n;
bi |= BigInt(this[offset++]) << 56n;
return parseInt(bi);
}
getUint64(offset)
{
var h = this.getUint32(offset);
var l = this.getUint32(offset + 4);
return h * TWO_PWR_32 + ((l >= 0) ? l : TWO_PWR_32 + l);
// var h = this.getInt32(offset);
// var l = this.getInt32(offset + 4);
// return h * TWO_PWR_32 + ((l >= 0) ? l : TWO_PWR_32 + l);
}
setInt64(offset, value)
getUint64(offset, endian)
{
var l = (value % TWO_PWR_32) | 0;
var h = (value / TWO_PWR_32) | 0;
this.setInt32(offset, h);
this.setInt32(offset + 4, l);
if (endian == Endian.Big) {
let bi = BigInt(0);
bi |= BigInt(this[offset++]) << 56n;
bi |= BigInt(this[offset++]) << 48n;
bi |= BigInt(this[offset++]) << 40n;
bi |= BigInt(this[offset++]) << 32n;
bi |= BigInt(this[offset++]) << 24n;
bi |= BigInt(this[offset++]) << 16n;
bi |= BigInt(this[offset++]) << 8n;
bi |= BigInt(this[offset++]);
return parseInt(bi);
} else {
let bi = BigInt(0);
bi |= BigInt(this[offset++]);
bi |= BigInt(this[offset++]) << 8n;
bi |= BigInt(this[offset++]) << 16n;
bi |= BigInt(this[offset++]) << 24n;
bi |= BigInt(this[offset++]) << 32n;
bi |= BigInt(this[offset++]) << 40n;
bi |= BigInt(this[offset++]) << 48n;
bi |= BigInt(this[offset++]) << 56n;
return parseInt(bi);
}
setUint64(offset, value)
{
var l = (value % TWO_PWR_32) | 0;
var h = (value / TWO_PWR_32) | 0;
this.setInt32(offset, h);
this.setInt32(offset + 4, l);
//var h = this.getUint32(offset);
//var l = this.getUint32(offset + 4);
//return h * TWO_PWR_32 + ((l >= 0) ? l : TWO_PWR_32 + l);
}
setDateTime(offset, value)
setInt64(offset, value, endian)
{
var bi = BigInt(value);
var byte = BigInt(0xFF);
if (endian == Endian.Big) {
this[offset++] = parseInt((bi >> 56n) & byte);
this[offset++] = parseInt((bi >> 48n) & byte);
this[offset++] = parseInt((bi >> 40n) & byte);
this[offset++] = parseInt((bi >> 32n) & byte);
this[offset++] = parseInt((bi >> 24n) & byte);
this[offset++] = parseInt((bi >> 16n) & byte);
this[offset++] = parseInt((bi >> 8n) & byte);
this[offset++] = parseInt(bi & byte);
} else {
this[offset++] = parseInt(bi & byte);
this[offset++] = parseInt((bi >> 8n) & byte);
this[offset++] = parseInt((bi >> 16n) & byte);
this[offset++] = parseInt((bi >> 24n) & byte);
this[offset++] = parseInt((bi >> 32n) & byte);
this[offset++] = parseInt((bi >> 40n) & byte);
this[offset++] = parseInt((bi >> 48n) & byte);
this[offset++] = parseInt((bi >> 56n) & byte);
}
//var l = (value % TWO_PWR_32) | 0;
//var h = (value / TWO_PWR_32) | 0;
//this.setInt32(offset, h);
//this.setInt32(offset + 4, l);
}
setUint64(offset, value, endian)
{
var bi = BigInt(value);
var byte = BigInt(0xFF);
if (endian == Endian.Big) {
this[offset++] = parseInt((bi >> 56n) & byte);
this[offset++] = parseInt((bi >> 48n) & byte);
this[offset++] = parseInt((bi >> 40n) & byte);
this[offset++] = parseInt((bi >> 32n) & byte);
this[offset++] = parseInt((bi >> 24n) & byte);
this[offset++] = parseInt((bi >> 16n) & byte);
this[offset++] = parseInt((bi >> 8n) & byte);
this[offset++] = parseInt(bi & byte);
} else {
this[offset++] = parseInt(bi & byte);
this[offset++] = parseInt((bi >> 8n) & byte);
this[offset++] = parseInt((bi >> 16n) & byte);
this[offset++] = parseInt((bi >> 24n) & byte);
this[offset++] = parseInt((bi >> 32n) & byte);
this[offset++] = parseInt((bi >> 40n) & byte);
this[offset++] = parseInt((bi >> 48n) & byte);
this[offset++] = parseInt((bi >> 56n) & byte);
}
// var l = (value % TWO_PWR_32) | 0;
// var h = (value / TWO_PWR_32) | 0;
// this.setInt32(offset, h);
// this.setInt32(offset + 4, l);
}
setDateTime(offset, value, endian)
{
// Unix Epoch
var ticks = 621355968000000000 + (value.getTime() * 10000);
this.setUint64(offset, ticks);
this.setUint64(offset, ticks, endian);
}
getDateTime(offset)
getDateTime(offset, endian)
{
var ticks = this.getUint64(offset);
var ticks = this.getUint64(offset, endian);
return new Date(Math.round((ticks-UNIX_EPOCH)/10000));
}
getDateTimeArray(offset)
getDateTimeArray(offset, endian)
{
var rt = [];
for(var i = 0; i < length; i+=8)
rt.push(this.getDateTime(offset+i));
rt.push(this.getDateTime(offset+i, endian));
return rt;
}

View File

@ -0,0 +1,510 @@
import IEnum from './IEnum.js';
import Tuple from './Tuple.js';
import TemplateType from '../Resource/Template/TemplateType.js';
import Warehouse from '../Resource/Warehouse.js';
import AsyncBag from '../Core/AsyncBag.js';
import AsyncReply from '../Core/AsyncReply.js';
import DC from './DC.js';
import DistributedConnection from '../Net/IIP/DistributedConnection.js';
import NotModified from './NotModified.js';
import RepresentationType from './RepresentationType.js';
import Codec from './Codec.js';
import TypedMap from './TypedMap.js';
import PropertyValueArray from './PropertyValueArray.js';
import PropertyValue from './PropertyValue.js';
import Record from './Record.js';
export class PropertyValueParserResults {
//final int size;
///final AsyncReply<PropertyValue> reply;
constructor(size, reply){
this.size = size;
this.reply = reply;
}
}
export default class DataDeserializer {
static nullParser(data, offset, length, connection) {
return new AsyncReply(null);
}
static booleanTrueParser(
data, offset, length, connection) {
return new AsyncReply(true);
}
static booleanFalseParser(
data, offset, length, connection) {
return new AsyncReply(false);
}
static notModifiedParser(
data, offset, length, connection) {
return new AsyncReply(NotModified());
}
static byteParser(
data, offset, length, connection) {
return new AsyncReply(data[offset]);
}
static sByteParser(
data, offset, length, connection) {
return new AsyncReply(
data[offset] > 127 ? data[offset] - 256 : data[offset]);
}
static char16Parser(
data, offset, length, connection) {
return new AsyncReply(data.getChar(offset));
}
static char8Parser(
data, offset, length, connection) {
return new AsyncReply(String.fromCharCode(data[offset]));
}
static int16Parser(
data, offset, length, connection) {
return new AsyncReply(data.getInt16(offset));
}
static uInt16Parser(
data, offset, length, connection) {
return new AsyncReply(data.getUint16(offset));
}
static int32Parser(
data, offset, length, connection) {
return new AsyncReply(data.getInt32(offset));
}
static uInt32Parser(
data, offset, length, connection) {
return new AsyncReply(data.getUint32(offset));
}
static float32Parser(
data, offset, length, connection) {
return new AsyncReply(data.getFloat32(offset));
}
static float64Parser(
data, offset, length, connection) {
return new AsyncReply(data.getFloat64(offset));
}
static float128Parser(
data, offset, length, connection) {
// @TODO
return new AsyncReply(data.getFloat64(offset));
}
static int128Parser(
data, offset, length, connection) {
// @TODO
return new AsyncReply(data.getInt64(offset));
}
static uInt128Parser(
data, offset, length, connection) {
return new AsyncReply(data.getUint64(offset));
}
static int64Parser(
data, offset, length, connection) {
return new AsyncReply(data.getInt64(offset));
}
static uInt64Parser(
data, offset, length, connection) {
return new AsyncReply(data.getUint64(offset));
}
static dateTimeParser(
data, offset, length, connection) {
return new AsyncReply(data.getDateTime(offset));
}
static resourceParser(
data, offset, length, connection) {
if (connection != null) {
var id = data.getUint32(offset);
return connection.fetch(id);
}
throw Error("Can't parse resource with no connection");
}
static localResourceParser(
data, offset, length, connection) {
var id = data.getUint32(offset);
return Warehouse.getById(id);
}
static rawDataParser(
data, offset, length, connection) {
return new AsyncReply(data.clip(offset, length));
}
static stringParser(
data, offset, length, connection) {
return new AsyncReply(data.getString(offset, length));
}
static recordParser(
data, offset, length, connection) {
var reply = new AsyncReply();
var classId = data.getGuid(offset);
offset += 16;
length -= 16;
var template = Warehouse.getTemplateByClassId(classId, TemplateType.Record);
if (template != null) {
listParser(data, offset, length, connection).then((ar) => {
let record;
if (template.definedType != null) {
record = Warehouse.createInstance(template.definedType);
} else {
record = Record();
}
var kv = new Map();
for (var i = 0; i < template.properties.length; i++)
kv[template.properties[i].name] = ar[i];
record.deserialize(kv);
reply.trigger(record);
});
} else {
if (connection == null)
throw Error("Can't parse record with no connection");
connection.getTemplate(classId).then((tmp) => {
if (tmp == null)
reply.triggerError(new Error("Couldn't fetch record template."));
DataDeserializer.listParser(data, offset, length, connection).then((ar) => {
var record = new Record();
//var kv = new Map();
for (var i = 0; i < tmp.properties.length; i++)
record[tmp.properties[i].name] = ar[i];
//record.deserialize(kv);
reply.trigger(record);
});
}).error((x) => reply.triggerError(x));
}
return reply;
}
static constantParser(
data, offset, length, connection) {
throw Error("NotImplementedException");
}
static enumParser(data, offset, length, connection) {
var classId = data.getGuid(offset);
offset += 16;
var index = data[offset++];
var template = Warehouse.getTemplateByClassId(classId, TemplateType.Enum);
if (template != null) {
if (template.definedType != null) {
var enumVal = Warehouse.createInstance(template.definedType);
enumVal.index = index;
enumVal.name = template.constants[index].name;
enumVal.value = template.constants[index].value;
return new AsyncReply.ready(enumVal);
} else {
return AsyncReply.ready(IEnum(index, template.constants[index].value,
template.constants[index].name));
}
} else {
var reply = new AsyncReply();
if (connection == null)
throw Error("Can't parse enum with no connection");
connection.getTemplate(classId).then((tmp) => {
if (tmp != null) {
if (tmp.definedType != null) {
var enumVal = Warehouse.createInstance(tmp.definedType);
enumVal.index = index;
enumVal.name = tmp.constants[index].name;
enumVal.value = tmp.constants[index].value;
reply.trigger(enumVal);
} else {
reply.trigger(new IEnum(
index, tmp.constants[index].value, tmp.constants[index].name));
}
} else
reply.triggerError(new Error("Template not found for enum"));
}).error((x) => reply.triggerError(x));
return reply;
}
}
static recordListParser(
data, offset, length, connection) {
var rt = new AsyncBag();
while (length > 0) {
var parsed = Codec.parse(data, offset, connection);
rt.add(parsed.reply);
if (parsed.size > 0) {
offset += parsed.size;
length -= parsed.size;
} else
throw new Error("Error while parsing structured data");
}
rt.seal();
return rt;
}
static resourceListParser(
data, offset, length, connection) {
var rt = new AsyncBag();
while (length > 0) {
var parsed = Codec.parse(data, offset, connection);
rt.add(parsed.reply);
if (parsed.size > 0) {
offset += parsed.size;
length -= parsed.size;
} else
throw new Error("Error while parsing structured data");
}
rt.seal();
return rt;
}
static listParser(
data, offset, length, connection) {
var rt = new AsyncBag();
while (length > 0) {
var parsed = Codec.parse(data, offset, connection);
rt.add(parsed.reply);
if (parsed.size > 0) {
offset += parsed.size;
length -= parsed.size;
} else
throw new Error("Error while parsing structured data");
}
rt.seal();
return rt;
}
static typedMapParser(
data, offset, length, connection) {
// get key type
var keyRep = RepresentationType.parse(data, offset);
offset += keyRep.size;
length -= keyRep.size;
var valueRep = RepresentationType.parse(data, offset);
offset += valueRep.size;
length -= valueRep.size;
var map = new TypedMap();
var rt = new AsyncReply();
var results = new AsyncBag();
while (length > 0) {
var parsed = Codec.parse(data, offset, connection);
results.add(parsed.reply);
if (parsed.size > 0) {
offset += parsed.size;
length -= parsed.size;
} else
throw new Error("Error while parsing structured data");
}
results.seal();
results.then((ar) => {
for (var i = 0; i < ar.length; i += 2)
map.set(ar[i], ar[i + 1]);
rt.trigger(map);
});
return rt;
}
static tupleParser(
data, offset, length, connection) {
var results = new AsyncBag();
var rt = new AsyncReply();
var tupleSize = data[offset++];
length--;
var types = [];
for (var i = 0; i < tupleSize; i++) {
var rep = RepresentationType.parse(data, offset);
if (rep.type != null)
types.push(rep.type.getRuntimeType() ?? Object);
offset += rep.size;
length -= rep.size;
}
while (length > 0) {
var parsed = Codec.parse(data, offset, connection);
results.add(parsed.reply);
if (parsed.size > 0) {
offset += parsed.size;
length -= parsed.size;
} else
throw new Error("Error while parsing structured data");
}
results.seal();
results.then((ar) => {
rt.trigger(new (Tuple.of(...types))(...ar));
});
return rt;
}
static typedListParser(
data, offset, length, connection) {
var rt = new AsyncBag();
// get the type
var rep = RepresentationType.parse(data, offset);
offset += rep.size;
length -= rep.size;
var runtimeType = rep.type.getRuntimeType();
rt.arrayType = runtimeType;
while (length > 0) {
var parsed = Codec.parse(data, offset, connection);
rt.add(parsed.reply);
if (parsed.size > 0) {
offset += parsed.size;
length -= parsed.size;
} else
throw new Error("Error while parsing structured data");
}
rt.seal();
return rt;
}
static PropertyValueArrayParser(
data,
offset,
length,
connection) //, bool ageIncluded = true)
{
var rt = new AsyncBag();
DataDeserializer.listParser(data, offset, length, connection).then((x) => {
var pvs = new PropertyValueArray();
for (var i = 0; i < x.length; i += 3)
pvs.push(new PropertyValue(x[2], x[0], x[1]));
rt.trigger(pvs);
});
return rt;
}
static propertyValueParser(data, offset,
connection) //, bool ageIncluded = true)
{
let reply = new AsyncReply();
let age = data.getUint64(offset);
offset += 8;
let date = data.getDateTime(offset);
offset += 8;
let parsed = Codec.parse(data, offset, connection);
parsed.reply.then((value) => {
reply.trigger(new PropertyValue(value, age, date));
});
return new PropertyValueParserResults(16 + parsed.size, reply);
}
static
historyParser(data, offset, length, resource,
connection) {
throw new Error("Not implemented");
// @TODO
// var list = new KeyList<PropertyTemplate, List<PropertyValue>>();
// var reply = new AsyncReply<KeyList<PropertyTemplate, List<PropertyValue[]>>>();
// var bagOfBags = new AsyncBag<PropertyValue[]>();
// var ends = offset + length;
// while (offset < ends)
// {
// var index = data[offset++];
// var pt = resource.Instance.Template.GetPropertyTemplateByIndex(index);
// list.Add(pt, null);
// var cs = data.GetUInt32(offset);
// offset += 4;
// var (len, pv) = PropertyValueParser(data, offset, connection);
// bagOfBags.Add(pv);// ParsePropertyValueArray(data, offset, cs, connection));
// offset += len;
// }
// bagOfBags.Seal();
// bagOfBags.Then(x =>
// {
// for (var i = 0; i < list.Count; i++)
// list[list.Keys.ElementAt(i)] = x[i];
// reply.Trigger(list);
// });
// return reply;
}
}

418
src/Data/DataSerializer.js Normal file
View File

@ -0,0 +1,418 @@
import BinaryList from './BinaryList.js';
import Codec from './Codec.js';
//import IRecord from './IRecord.js';
//import DistributedResource from '../Net/IIP/DistributedResource.js';
//import IResource from '../Resource/IResource.js';
import Warehouse from '../Resource/Warehouse.js';
//import PropertyTemplate from '../Resource/Template/PropertyTemplate.js';
//import PropertyValue from './PropertyValue.js';
import { TransmissionTypeIdentifier} from './TransmissionType.js';
//import DistributedConnection from '../Net/IIP/DistributedConnection.js';
import DC, { BL } from './DC.js';
import RepresentationType from './RepresentationType.js';
import Tuple from './Tuple.js';
export class DataSerializerComposeResults {
// int identifier;
//DC data;
constructor(identifier, data){
this.identifier = identifier;
this.data = data;
}
}
export default class DataSerializer {
//public delegate byte[] Serializer(object value);
static historyComposer(history, connection, prependLength = false) {
throw new Error("Not implemented");
}
static int32Composer(
value, connection) {
var rt = new DC(4);
rt.setInt32(0, value);
return new DataSerializerComposeResults(TransmissionTypeIdentifier.Int32, rt);
}
static uInt32Composer(
value, connection) {
var rt = new DC(4);
rt.setUint32(0, value);
return new DataSerializerComposeResults(TransmissionTypeIdentifier.UInt32, rt);
}
static int16Composer(
value, connection) {
var rt = new DC(2);
rt.setInt16(0, value);
return new DataSerializerComposeResults(TransmissionTypeIdentifier.Int16, rt);
}
static uInt16Composer(
value, connection) {
var rt = new DC(2);
rt.setUint16(0, value);
return new DataSerializerComposeResults(TransmissionTypeIdentifier.UInt16, rt);
}
static float32Composer(
value, connection) {
var rt = new DC(4);
rt.setFloat32(0, value);
return new DataSerializerComposeResults(TransmissionTypeIdentifier.Float32, rt);
}
static float64Composer(value, connection) {
var rt = new DC(8);
rt.setFloat64(0, value);
return new DataSerializerComposeResults(TransmissionTypeIdentifier.Float64, rt);
}
static int64Composer(
value, connection) {
var rt = new DC(8);
rt.setInt64(0, value);
return new DataSerializerComposeResults(TransmissionTypeIdentifier.Int64, rt);
}
static numberComposer(value, connection) {
var rt = new DC(8);
if (Number.isInteger(value)){
rt.setInt64(0, value);
return new DataSerializerComposeResults(TransmissionTypeIdentifier.Int64, rt);
}
else {
rt.setFloat64(0, value);
return new DataSerializerComposeResults(TransmissionTypeIdentifier.Float64, rt);
}
}
static uInt64Composer(
value, connection) {
var rt = new DC(8);
rt.setUint64(0, value);
return new DataSerializerComposeResults(TransmissionTypeIdentifier.UInt64, rt);
}
static dateTimeComposer(
value, connection) {
var rt = new DC(8);
rt.setDateTime(0, value);
return new DataSerializerComposeResults(
TransmissionTypeIdentifier.DateTime, rt);
}
static float128Composer(
value, connection) {
//@TODO: implement decimal
var rt = new DC(16);
rt.setFloat64(0, value);
return new DataSerializerComposeResults(TransmissionTypeIdentifier.Float64, rt);
}
static stringComposer(
value, connection) {
return new DataSerializerComposeResults(
TransmissionTypeIdentifier.String, DC.stringToBytes(value));
}
static enumComposer(
value, connection) {
if (value == null)
return new DataSerializerComposeResults(
TransmissionTypeIdentifier.Null, new DC(0));
var template = Warehouse.getTemplateByType(value.runtimeType);
if (template == null)
return new DataSerializerComposeResults(
TransmissionTypeIdentifier.Null, new DC(0));
var cts = template.constants.where((x) => x.value == value);
if (cts.isEmpty)
return new DataSerializerComposeResults(
TransmissionTypeIdentifier.Null, new DC(0));
var rt = BinaryList();
rt.addGuid(template.classId);
rt.addUint8(cts.first.index);
return new DataSerializerComposeResults(
TransmissionTypeIdentifier.Enum, rt.toDC());
}
static uInt8Composer(
value, connection) {
var rt = new DC(1);
rt[0] = value;
return new DataSerializerComposeResults(TransmissionTypeIdentifier.UInt8, rt);
}
static int8Composer(
value, connection) {
var rt = new DC(1);
rt[0] = value;
return new DataSerializerComposeResults(TransmissionTypeIdentifier.Int8, rt);
}
static char8Composer(
value, connection) {
var rt = new DC(1);
rt[0] = value;
return new DataSerializerComposeResults(TransmissionTypeIdentifier.Char8, rt);
}
static char16Composer(
value, connection) {
var rt = new DC(2);
rt.setUint16(0, value);
return new DataSerializerComposeResults(TransmissionTypeIdentifier.Char16, rt);
}
static boolComposer(
value, connection) {
return new DataSerializerComposeResults(
value
? TransmissionTypeIdentifier.True
: TransmissionTypeIdentifier.False,
new DC(0));
}
static notModifiedComposer(
value, connection) {
return new DataSerializerComposeResults(
TransmissionTypeIdentifier.NotModified, new DC(0));
}
static rawDataComposer(
value, connection) {
return new DataSerializerComposeResults(
TransmissionTypeIdentifier.RawData, value);
}
static listComposer(
value, connection) {
if (value == null)
return new DataSerializerComposeResults(
TransmissionTypeIdentifier.Null, new DC(0));
else
return new DataSerializerComposeResults(TransmissionTypeIdentifier.List,
DataSerializer.arrayComposer(value , connection));
//var rt = new List<byte>();
//var list = (IEnumerable)value;// ((List<object>)value);
//foreach (var o in list)
// rt.AddRange(Codec.Compose(o, connection));
//return (TransmissionTypeIdentifier.List, rt.ToArray());
}
static typedListComposer(
value, type, connection) {
if (value == null)
return new DataSerializerComposeResults(
TransmissionTypeIdentifier.Null, new DC(0));
var composed = DataSerializer.arrayComposer(value, connection);
var header =
(RepresentationType.fromType(type) ?? RepresentationType.Dynamic)
.compose();
var rt = new BinaryList()
.addDC(header)
.addDC(composed);
return new DataSerializerComposeResults(
TransmissionTypeIdentifier.TypedList, rt.toDC());
}
static propertyValueArrayComposer(
value, connection) {
if (value == null)
return new DataSerializerComposeResults(
TransmissionTypeIdentifier.Null, new DC(0));
var rt = BL();
for (var i = 0; i < value.length; i ++){
rt.addDC(Codec.compose(value[i].age, connection));
rt.addDC(Codec.compose(value[i].date, connection));
rt.addDC(Codec.compose(value[i].value, connection));
}
return new DataSerializerComposeResults(
TransmissionTypeIdentifier.List, rt.toDC());
}
static typedMapComposer(
value, keyType, valueType, connection) {
if (value == null)
return new DataSerializerComposeResults(
TransmissionTypeIdentifier.Null, new DC(0));
var kt =
(RepresentationType.fromType(keyType) ?? RepresentationType.Dynamic)
.compose();
var vt =
(RepresentationType.fromType(valueType) ?? RepresentationType.Dynamic)
.compose();
var rt = new BinaryList();
rt.addDC(kt);
rt.addDC(vt);
//@TODO
for(let [k, v] of value)
{
rt.addDC(Codec.compose(k, connection));
rt.addDC(Codec.compose(v, connection));
}
return new DataSerializerComposeResults(
TransmissionTypeIdentifier.TypedMap, rt.toDC());
}
static arrayComposer(value, connection) {
var rt = new BinaryList();
for (var i of value)
rt.addDC(Codec.compose(i, connection));
return rt.toDC();
}
static resourceListComposer(
value, connection) {
if (value == null)
return new DataSerializerComposeResults(
TransmissionTypeIdentifier.Null, new DC(0));
return new DataSerializerComposeResults(TransmissionTypeIdentifier.ResourceList,
DataSerializer.arrayComposer(value, connection));
}
static recordListComposer(
value, connection) {
if (value == null)
return new DataSerializerComposeResults(
TransmissionTypeIdentifier.Null, new DC(0));
return new DataSerializerComposeResults(TransmissionTypeIdentifier.RecordList,
DataSerializer.arrayComposer(value, connection));
}
static resourceComposer(
value, connection) {
var resource = value;
var rt = new DC(4);
if (Codec.isLocalResource(resource, connection)) {
rt.setUint32(0, resource.id ?? 0);
return new DataSerializerComposeResults(
TransmissionTypeIdentifier.ResourceLocal, rt);
} else {
// @TODO: connection.cache.Add(value as IResource, DateTime.UtcNow);
rt.setUint32(0, resource.instance?.id ?? 0);
return new DataSerializerComposeResults(
TransmissionTypeIdentifier.Resource, rt);
}
}
static mapComposer(
value, connection) {
if (value == null)
return new DataSerializerComposeResults(
TransmissionTypeIdentifier.Null, new DC(0));
var rt = BinaryList();
for (var el in value) {
rt.addDC(Codec.compose(el.key, connection));
rt.addDC(Codec.compose(el.value, connection));
}
return new DataSerializerComposeResults(
TransmissionTypeIdentifier.Map, rt.toDC());
}
static recordComposer(
value, connection) {
var rt = BinaryList();
var template = Warehouse.getTemplateByType(value.runtimeType);
if (template == null)
return new DataSerializerComposeResults(
TransmissionTypeIdentifier.Null, new DC(0));
rt.addDC(DC.guidToBytes(template.classId));
var recordData = value.serialize();
for (var pt in template.properties) {
var propValue = recordData[pt.name];
rt.addDC(Codec.compose(propValue, connection));
}
return new DataSerializerComposeResults(
TransmissionTypeIdentifier.Record, rt.toDC());
}
// TODO:
// static DataSerializerComposeResults historyComposer(KeyList<PropertyTemplate, PropertyValue[]> history,
// DistributedConnection connection, bool prependLength = false)
// {
// //@TODO:Test
// var rt = new BinaryList();
// for (var i = 0; i < history.Count; i++)
// rt.AddUInt8(history.Keys.ElementAt(i).Index)
// .AddUInt8Array(Codec.Compose(history.Values.ElementAt(i), connection));
// if (prependLength)
// rt.InsertInt32(0, rt.Length);
// return rt.ToArray();
// }
static tupleComposer(value, connection) {
if (value == null)
return new DataSerializerComposeResults(TransmissionTypeIdentifier.Null, new DC(0));
var rt = BL();
var fields = Tuple.getTypes(value);
var types = fields.map(x => RepresentationType.fromType(x).compose());
rt.Add(value.length);
for (var t of types)
rt.addUint8Array(t);
var composed = DataSerializer.arrayComposer(value, connection);
if (composed == null)
return new DataSerializerComposeResults(TransmissionTypeIdentifier.Null, new DC(0));
else
{
rt.addUint8Array(composed);
return new DataSerializerComposeResults(TransmissionTypeIdentifier.Tuple, rt.toArray());
}
}
}

28
src/Data/ExtendedTypes.js Normal file
View File

@ -0,0 +1,28 @@
class Num extends Number {
toString() { return super.toString()}
constructor(value) {
super(value);
}
}
export class Int128 extends Num {}
export class Int64 extends Num { }
export class Int32 extends Num { }
export class Int16 extends Num { }
export class Int8 extends Num { }
export class UInt128 extends Num {}
export class UInt64 extends Num { }
export class UInt32 extends Num { }
export class UInt16 extends Num { }
export class UInt8 extends Num { }
export class Float32 extends Num{}
export class Float64 extends Num{}
export class Float128 extends Num{}
export class Char16 extends String {}
export class Char8 extends String {}

View File

@ -24,8 +24,8 @@
* Created by Ahmed Zamil on 02/09/2017.
*/
"use strict";
import DC from './DC.js';
export default class Guid
{
constructor(dc)
@ -38,6 +38,14 @@ export default class Guid
return this.value.getHex(0, 16);
}
static fromString(data) {
this.value = DC.fromHex(data, '');
}
toString() {
return this.vlue.toHex('');
}
// [Symbol.toPrimitive](hint){
// console.log(hint);
// }

18
src/Data/IEnum.js Normal file
View File

@ -0,0 +1,18 @@
//import TemplateDescriber from '../Resource/Template/TemplateDescriber.js';
export default class IEnum {
IEnum(index, value, name){
this.index = index;
this.value = value;
this.name = name;
}
get template () {
//return new TemplateDescriber("IEnum");
}
toString() {
return `${this.name}<${this.value}>`;
}
}

View File

@ -1,3 +1,6 @@
export default class IRecord {
toString() {
//return serialize().toString();
}
}

7
src/Data/ParseResult.js Normal file
View File

@ -0,0 +1,7 @@
export default class ParseResult {
constructor (size, value){
this.size = size;
this.value = value;
}
}

View File

@ -0,0 +1,3 @@
export default class PropertyValueArray extends Array {
}

40
src/Data/RecordArray.js Normal file
View File

@ -0,0 +1,40 @@
/*
* Copyright (c) 2017-2022 Ahmed Kh. Zamil
*
* Permission is hereby granted, free of charge, to any person obtaining a copy
* of this software and associated documentation files (the "Software"), to deal
* in the Software without restriction, including without limitation the rights
* to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
* copies of the Software, and to permit persons to whom the Software is
* furnished to do so, subject to the following conditions:
*
* The above copyright notice and this permission notice shall be included in all
* copies or substantial portions of the Software.
*
* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
* IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
* FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
* AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
* LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
* OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
* SOFTWARE.
*/
/**
* Created by Ahmed Zamil on 26/08/2017.
*/
"use strict";
import IRecord from "./IRecord.js";
export default class RecordArray extends Array
{
push(value)
{
if (value instanceof IRecord)
super.push(value);
else
return;
}
}

View File

@ -0,0 +1,197 @@
import TemplateType from '../Resource/Template/TemplateType.js';
import IRecord from './IRecord.js';
import IResource from '../Resource/IResource.js';
import BinaryList from './BinaryList.js';
import DC from './DC.js';
import Warehouse from '../Resource/Warehouse.js';
import {Int8, Int16, Int32, Int64, Int128, UInt8, UInt16, UInt32, UInt64, UInt128, Char8, Char16, Float32, Float64, Float128} from './ExtendedTypes.js';
export const RepresentationTypeIdentifier = {
Void: 0x0,
Dynamic : 0x1,
Bool : 0x2,
UInt8 : 0x3,
Int8 : 0x4,
Char : 0x5,
Int16 : 0x6,
UInt16 : 0x7,
Int32 : 0x8,
UInt32 : 0x9,
Float32 : 0xA,
Int64 : 0xB,
UInt64 : 0xC,
Float64 : 0xD,
DateTime : 0xE,
Int128 : 0xF,
UInt128 : 0x10,
Decimal : 0x11,
String : 0x12,
RawData : 0x13,
Resource : 0x14,
Record : 0x15,
List : 0x16,
Map : 0x17,
Enum : 0x18,
TypedResource : 0x45, // Followed by UUID
TypedRecord : 0x46, // Followed by UUID
TypedList : 0x48, // Followed by element type
Tuple2 : 0x50, // Followed by element type
TypedMap : 0x51, // Followed by key type and value type
Tuple3 : 0x58,
Tuple4 : 0x60,
Tuple5 : 0x68,
Tuple6 : 0x70,
Tuple7 : 0x78
}
let RuntimeTypes = {};
RuntimeTypes[RepresentationTypeIdentifier.Void] = [Object, Object];
RuntimeTypes[RepresentationTypeIdentifier.Bool] = [Boolean, Object];
RuntimeTypes[RepresentationTypeIdentifier.Char] = [Char8, Object];
RuntimeTypes[RepresentationTypeIdentifier.Char16] = [Char16, Object];
RuntimeTypes[RepresentationTypeIdentifier.UInt8] = [UInt8, UInt8];
RuntimeTypes[RepresentationTypeIdentifier.Int8] = [Int8, Object];
RuntimeTypes[RepresentationTypeIdentifier.Int16] = [Int16, Object];
RuntimeTypes[RepresentationTypeIdentifier.UInt16] = [UInt16, Object];
RuntimeTypes[RepresentationTypeIdentifier.Int32] = [Int32, Object];
RuntimeTypes[RepresentationTypeIdentifier.UInt32] = [UInt32, Object];
RuntimeTypes[RepresentationTypeIdentifier.Int64] = [Int64, Object];
RuntimeTypes[RepresentationTypeIdentifier.UInt64] = [UInt64, Object];
RuntimeTypes[RepresentationTypeIdentifier.Int128] = [Int128, Object];
RuntimeTypes[RepresentationTypeIdentifier.UInt128] = [UInt128, Object];
RuntimeTypes[RepresentationTypeIdentifier.Float32] = [Float32, Object];
RuntimeTypes[RepresentationTypeIdentifier.Float64] = [Float64, Object];
RuntimeTypes[RepresentationTypeIdentifier.Decimal] = [Float128, Object];
RuntimeTypes[RepresentationTypeIdentifier.String] = [String, Object];
RuntimeTypes[RepresentationTypeIdentifier.DateTime] = [Date, Object];
RuntimeTypes[RepresentationTypeIdentifier.Resource] = [IResource, IResource];
RuntimeTypes[RepresentationTypeIdentifier.Record] = [IRecord, IRecord];
export class RepresentationTypeParseResults {
//RepresentationType type;
//int size;
constructor(size, type){
this.size= size;
this.type = type;
}
}
export default class RepresentationType {
// static getTypeFromName(name) {
// const types = {
// "int": int,
// "bool": bool,
// "double": double,
// "String": String,
// "IResource": IResource,
// "IRecord": IRecord,
// "IEnum": IEnum,
// "DC": DC,
// };
// if (types[name] != null) {
// return types[name];
// } else
// return Object().runtimeType;
// }
toNullable() {
return new RepresentationType(this.identifier, true, this.guid, this.subTypes);
}
static get Void () { return new RepresentationType(RepresentationTypeIdentifier.Void, true, null, null);}
static get Dynamic() { return new RepresentationType(RepresentationTypeIdentifier.Dynamic, true, null, null);}
static fromType(type) {
return Warehouse.typesFactory[type]?.representationType;
}
getRuntimeType() {
if (RuntimeTypes[this.identifier])
return this.nullable
? RuntimeTypes[this.identifier][1]
: RuntimeTypes[this.identifier][0];
if (this.identifier == RepresentationTypeIdentifier.TypedRecord)
return Warehouse.getTemplateByClassId(this.guid, TemplateType.Record)
?.definedType;
else if (this.identifier == RepresentationTypeIdentifier.TypedResource)
return Warehouse.getTemplateByClassId(this.guid, TemplateType.Unspecified)
?.definedType;
else if (this.identifier == RepresentationTypeIdentifier.Enum)
return Warehouse.getTemplateByClassId(this.guid, TemplateType.Enum)
?.definedType;
return null;
}
constructor(identifier, nullable, guid, subTypes) {
this.identifier = identifier;
this.nullable = nullable;
this.guid = guid;
this.subTypes = subTypes;
}
compose() {
var rt = new BinaryList();
if (this.nullable)
rt.addUint8(0x80 | this.identifier);
else
rt.addUint8(this.identifier);
if (this.guid != null) rt.addDC(DC.guidToBytes(this.guid));
if (this.subTypes != null)
for (var i = 0; i < this.subTypes.length; i++)
rt.addDC(this.subTypes[i].compose());
return rt.toDC();
}
//public override string ToString() => Identifier.ToString() + (Nullable ? "?" : "")
// + TypeTemplate != null ? "<" + TypeTemplate.ClassName + ">" : "";
static parse(data, offset) {
let oOffset = offset;
let header = data[offset++];
let nullable = (header & 0x80) > 0;
let identifier = (header & 0x7F);
if ((header & 0x40) > 0) {
let hasGUID = (header & 0x4) > 0;
let subsCount = (header >> 3) & 0x7;
let guid = null;
if (hasGUID) {
guid = data.getGuid(offset);
offset += 16;
}
let subs = [];
for (let i = 0; i < subsCount; i++) {
let parsed = RepresentationType.parse(data, offset);
subs.push(parsed.type);
offset += parsed.size;
}
return new RepresentationTypeParseResults(offset - oOffset,
new RepresentationType(identifier, nullable, guid, subs));
} else {
return new RepresentationTypeParseResults(
1, new RepresentationType(identifier, nullable, null, null));
}
}
}
export {RepresentationType};

View File

@ -26,6 +26,7 @@
"use strict";
import IResource from "../Resource/IResource.js";
export default class ResourceArray extends Array
{
push(value)

View File

@ -0,0 +1,196 @@
import DC from './DC.js';
export const TransmissionTypeIdentifier = {
Null : 0x0,
False : 0x1,
True : 0x2,
NotModified : 0x3,
UInt8 : 0x8,
Int8 : 0x9,
Char8 : 0xA,
Int16 : 0x10,
UInt16 : 0x11,
Char16 : 0x12,
Int32 : 0x18,
UInt32 : 0x19,
Float32 : 0x1A,
Resource : 0x1B,
ResourceLocal : 0x1C,
Int64 : 0x20,
UInt64 : 0x21,
Float64 : 0x22,
DateTime : 0x23,
Int128 : 0x28,
UInt128 : 0x29,
Float128 : 0x2A,
RawData : 0x40,
String : 0x41,
List : 0x42,
ResourceList : 0x43,
RecordList : 0x44,
Map : 0x45,
MapList : 0x46,
//Tuple = 0x47,
Record : 0x80,
TypedList : 0x81,
TypedMap : 0x82,
Tuple : 0x83,
Enum : 0x84,
Constant : 0x85
};
export let TransmissionTypeClass = {
Fixed : 0,
Dynamic : 1,
Typed : 2
}
export class TransmissionTypeParseResults {
constructor(size, type) {
this.size = size;
this.type = type;
}
}
export default class TransmissionType {
// final int identifier;
// final int index;
// final int classType;
// final int offset;
// final int contentLength;
// final int exponent;
static get Null() { return new
TransmissionType(TransmissionTypeIdentifier.Null, 0, 0, 0, 0);}
constructor(identifier, classType, index, offset, contentLength, exponent = 0){
this.identifier = identifier;
this.classType = classType;
this.index = index;
this.offset = offset;
this.contentLength = contentLength;
this.exponent = exponent;
}
static compose(identifier, data) {
if (data.length == 0) return DC.fromList([identifier]);
var cls = identifier >> 6;
if (cls == TransmissionTypeClass.Fixed) {
return DC.combine([identifier], 0, 1, data, 0, data.length);
} else {
var len = data.length;
if (len == 0) {
return DC.fromList([identifier]);
} else if (len <= 0xFF) {
let rt = new DC(2 + len);
rt[0] = identifier | 0x8;
rt[1] = len;
rt.set(data, 2);
return rt;
} else if (len <= 0xFFFF) {
let rt = new DC(3 + len);
rt[0] = identifier | 0x10;
rt[1] = (len >> 8) & 0xFF;
rt[2] = len & 0xFF;
rt.set(data, 3);
return rt;
} else if (len <= 0xFFFFFF) {
let rt = new DC(4 + len);
rt[0] = identifier | 0x18;
rt[1] = (len >> 16) & 0xFF;
rt[2] = (len >> 8) & 0xFF;
rt[3] = len & 0xFF;
rt.set(data, 4);
return rt;
} else if (len <= 0xFFFFFFFF) {
let rt = new DC(5 + len);
rt[0] = (identifier | 0x20);
rt[1] = ((len >> 24) & 0xFF);
rt[2] = ((len >> 16) & 0xFF);
rt[3] = ((len >> 8) & 0xFF);
rt[4] = (len & 0xFF);
rt.set(data, 5);
return rt;
} else if (len <= 0xFFFFFFFFFF) {
let rt = new DC(6 + len);
rt[0] = identifier | 0x28;
rt[1] = ((len >> 32) & 0xFF);
rt[2] = ((len >> 24) & 0xFF);
rt[3] = ((len >> 16) & 0xFF);
rt[4] = ((len >> 8) & 0xFF);
rt[5] = (len & 0xFF);
rt.set(data, 6);
return rt;
} else if (len <= 0xFFFFFFFFFFFF) {
let rt = new DC(7 + len);
rt[0] = identifier | 0x30;
rt[1] = (len >> 40) & 0xFF;
rt[2] = (len >> 32) & 0xFF;
rt[3] = (len >> 24) & 0xFF;
rt[4] = (len >> 16) & 0xFF;
rt[5] = (len >> 8) & 0xFF;
rt[6] = len & 0xFF;
rt.set(data, 7);
return rt;
} else //if (len <= 0xFF_FF_FF_FF_FF_FF_FF)
{
let rt = new DC(8 + len);
rt[0] = identifier | 0x38;
rt[1] = (len >> 48) & 0xFF;
rt[2] = (len >> 40) & 0xFF;
rt[3] = (len >> 32) & 0xFF;
rt[4] = (len >> 24) & 0xFF;
rt[5] = (len >> 16) & 0xFF;
rt[6] = (len >> 8) & 0xFF;
rt[7] = len & 0xFF;
data.set(data, 8);
return rt;
}
}
}
static parse(data, offset, ends) {
var h = data[offset++];
var cls = h >> 6;
if (cls == TransmissionTypeClass.Fixed) {
var exp = (h & 0x38) >> 3;
if (exp == 0)
return new TransmissionTypeParseResults(
1, new TransmissionType(h, cls, h & 0x7, 0, exp));
let cl = (1 << (exp - 1));
if (ends - offset < cl)
return new TransmissionTypeParseResults(ends - offset - cl, null);
return new TransmissionTypeParseResults(
1 + cl, new TransmissionType(h, cls, h & 0x7, offset, cl, exp));
} else {
let cll = (h >> 3) & 0x7;
if (ends - offset < cll)
return new TransmissionTypeParseResults(ends - offset - cll, null);
let cl = 0;
for (var i = 0; i < cll; i++) cl = cl << 8 | data[offset++];
return new TransmissionTypeParseResults(
1 + cl + cll, new TransmissionType((h & 0xC7), cls, h & 0x7, offset, cl));
}
}
}
export {TransmissionType}

26
src/Data/Tuple.js Normal file
View File

@ -0,0 +1,26 @@
export default class Tuple extends Array {
static cache = {};
static getTypes(tuple){
return tuple.constructor.types;
}
static of(){
let types = [];
for(let i =0 ; i < arguments.length; i++){
types.push(arguments[i]);
}
if (Tuple.cache[types] != null)
return Tuple.cache[types];
let c = class extends Tuple{}
Object.defineProperty(c, "name", {value: types.map(x => x.name).join('') + "Tuple"});
Object.defineProperty(c, "types", {value: types});
Tuple.cache[types] = c;
return c;
}
}

36
src/Data/TypedList.js Normal file
View File

@ -0,0 +1,36 @@
import IResource from "../Resource/IResource.js";
import PropertyValue from "./PropertyValue.js";
import PropertyValueArray from "./PropertyValueArray.js";
import ResourceArray from "./ResourceArray.js";
export default class TypedList extends Array
{
// constructor(data)
// {
// if (data != undefined && data instanceof Array)
// for(var i = 0; i < data.length; i++)
// this.push(data[i]);
// }
static cache = { [IResource] : ResourceArray,
[PropertyValue] : PropertyValueArray
};
static getType(typedList){
return typedList.constructor.type;
}
static of(type){
if (TypedList.cache[type] != null)
return TypedList.cache[type];
let c = class extends TypedList{}
Object.defineProperty(c, "name", {value: type.name + "List"});
Object.defineProperty(c, "type", {value: type});
TypedList.cache[type] = c;
return c;
}
}

43
src/Data/TypedMap.js Normal file
View File

@ -0,0 +1,43 @@
export default class TypedMap extends Map {
constructor(data)
{
super();
if (data instanceof Object)
for(var i in data)
this.set(i, data[i]);
}
static getTypes(typedMap){
return [typedMap.constructor.keyType ?? Object, typedMap.constructor.valueType ?? Object];
}
static cache = {};
static of(keyType, valueType){
if (TypedMap.cache[[keyType, valueType]] != null)
return TypedMap.cache[[keyType, valueType]];
//if (TypedMap.cache[keyType] != null)
// if (TypedMap.cache[keyType][valueType] != null)
// return TypedMap.cache[keyType][valueType];
let c = class extends TypedMap{}
Object.defineProperty(c, "name", {value: keyType.name + valueType.name + "Map"});
Object.defineProperty(c, "keyType", {value: keyType});
Object.defineProperty(c, "valueType", {value: valueType});
//if (TypedMap.cache[keyType] == null)
// TypedMap.cache[keyType] = {[valueType]: c};
//else
// TypedMap.cache[keyType][valueType] = c;
TypedMap.cache[[keyType, valueType]] = c;
return c;
}
}

View File

@ -32,7 +32,7 @@ import Authentication from '../../Security/Authority/Authentication.js';
import AuthenticationType from "../../Security/Authority/AuthenticationType.js";
import SHA256 from '../../Security/Integrity/SHA256.js';
import { BL, DC } from '../../Data/DataConverter.js';
import { BL, DC } from '../../Data/DC.js';
import SendList from '../SendList.js';
import AsyncReply from '../../Core/AsyncReply.js';
@ -76,6 +76,11 @@ import SocketState from "../Sockets/SocketState.js";
import TemplateType from '../../Resource/Template/TemplateType.js';
import AsyncBag from '../../Core/AsyncBag.js';
import {TransmissionType, TransmissionTypeIdentifier} from '../../Data/TransmissionType.js';
import PropertyValue from '../../Data/PropertyValue.js';
import PropertyValueArray from '../../Data/PropertyValueArray.js';
export default class DistributedConnection extends IStore {
@ -151,6 +156,8 @@ export default class DistributedConnection extends IStore {
var rt = packet.parse(msg, offset, ends);
//console.log("Inc " , rt, offset, ends);
if (rt <= 0) {
data.holdFor(msg, offset, ends - offset, -rt);
return ends;
@ -168,10 +175,10 @@ export default class DistributedConnection extends IStore {
this.IIPEventResourceDestroyed(packet.resourceId);
break;
case IIPPacketEvent.PropertyUpdated:
this.IIPEventPropertyUpdated(packet.resourceId, packet.methodIndex, packet.content);
this.IIPEventPropertyUpdated(packet.resourceId, packet.methodIndex, packet.dataType, msg);
break;
case IIPPacketEvent.EventOccurred:
this.IIPEventEventOccurred(packet.resourceId, packet.methodIndex, packet.content);
this.IIPEventEventOccurred(packet.resourceId, packet.methodIndex, packet.dataType, msg);
break;
case IIPPacketEvent.ChildAdded:
@ -181,10 +188,11 @@ export default class DistributedConnection extends IStore {
this.IIPEventChildRemoved(packet.resourceId, packet.childId);
break;
case IIPPacketEvent.Renamed:
this.IIPEventRenamed(packet.resourceId, packet.content);
this.IIPEventRenamed(packet.resourceId, packet.resourceName);
break;
case IIPPacketEvent.AttributesUpdated:
this.IIPEventAttributesUpdated(packet.resourceId, packet.content);
//@TODO: fix this
//this.IIPEventAttributesUpdated(packet.resourceId, packet.content);
break;
}
@ -203,7 +211,8 @@ export default class DistributedConnection extends IStore {
this.IIPRequestDetachResource(packet.callbackId, packet.resourceId);
break;
case IIPPacketAction.CreateResource:
this.IIPRequestCreateResource(packet.callbackId, packet.storeId, packet.resourceId, packet.content);
// @TODO: implement this
// this.IIPRequestCreateResource(packet.callbackId, packet.storeId, packet.resourceId, packet.content);
break;
case IIPPacketAction.DeleteResource:
this.IIPRequestDeleteResource(packet.callbackId, packet.resourceId);
@ -215,7 +224,7 @@ export default class DistributedConnection extends IStore {
this.IIPRequestRemoveChild(packet.callbackId, packet.resourceId, packet.childId);
break;
case IIPPacketAction.RenameResource:
this.IIPRequestRenameResource(packet.callbackId, packet.resourceId, packet.content);
this.IIPRequestRenameResource(packet.callbackId, packet.resourceId, packet.resourceName);
break;
// Inquire
@ -246,12 +255,11 @@ export default class DistributedConnection extends IStore {
break;
// Invoke
case IIPPacketAction.InvokeFunctionArrayArguments:
this.IIPRequestInvokeFunctionArrayArguments(packet.callbackId, packet.resourceId, packet.methodIndex, packet.content);
break;
case IIPPacketAction.InvokeFunctionNamedArguments:
this.IIPRequestInvokeFunctionNamedArguments(packet.callbackId, packet.resourceId, packet.methodIndex, packet.content);
case IIPPacketAction.InvokeFunction:
this.IIPRequestInvokeFunction(packet.callbackId, packet.resourceId, packet.methodIndex, packet.dataType, msg);
break;
// case IIPPacketAction.GetProperty:
// this.IIPRequestGetProperty(packet.callbackId, packet.resourceId, packet.methodIndex);
// break;
@ -267,28 +275,28 @@ export default class DistributedConnection extends IStore {
break;
case IIPPacketAction.SetProperty:
this.IIPRequestSetProperty(packet.callbackId, packet.resourceId, packet.methodIndex, packet.content);
this.IIPRequestSetProperty(packet.callbackId, packet.resourceId, packet.methodIndex, packet.dataType, msg);
break;
// Attribute
// Attribute @TODO: implement these
case IIPPacketAction.GetAllAttributes:
this.IIPRequestGetAttributes(packet.callbackId, packet.resourceId, packet.content, true);
// this.IIPRequestGetAttributes(packet.callbackId, packet.resourceId, packet.content, true);
break;
case IIPPacketAction.UpdateAllAttributes:
this.IIPRequestUpdateAttributes(packet.callbackId, packet.resourceId, packet.content, true);
// this.IIPRequestUpdateAttributes(packet.callbackId, packet.resourceId, packet.content, true);
break;
case IIPPacketAction.ClearAllAttributes:
this.IIPRequestClearAttributes(packet.callbackId, packet.resourceId, packet.content, true);
// this.IIPRequestClearAttributes(packet.callbackId, packet.resourceId, packet.content, true);
break;
case IIPPacketAction.GetAttributes:
this.IIPRequestGetAttributes(packet.callbackId, packet.resourceId, packet.content, false);
// this.IIPRequestGetAttributes(packet.callbackId, packet.resourceId, packet.content, false);
break;
case IIPPacketAction.UpdateAttributes:
this.IIPRequestUpdateAttributes(packet.callbackId, packet.resourceId, packet.content, false);
// this.IIPRequestUpdateAttributes(packet.callbackId, packet.resourceId, packet.content, false);
break;
case IIPPacketAction.ClearAttributes:
this.IIPRequestClearAttributes(packet.callbackId, packet.resourceId, packet.content, false);
// this.IIPRequestClearAttributes(packet.callbackId, packet.resourceId, packet.content, false);
break;
}
@ -296,10 +304,10 @@ export default class DistributedConnection extends IStore {
else if (packet.command == IIPPacketCommand.Reply) {
switch (packet.action) {
case IIPPacketAction.AttachResource:
this.IIPReply(packet.callbackId, packet.classId, packet.resourceAge, packet.resourceLink, packet.content);
this.IIPReply(packet.callbackId, packet.classId, packet.resourceAge, packet.resourceLink, packet.dataType, msg);
break;
case IIPPacketAction.ReattachResource:
this.IIPReply(packet.callbackId, packet.resourceAge, packet.content);
this.IIPReply(packet.callbackId, packet.resourceAge, packet.dataType, msg);
break;
case IIPPacketAction.DetachResource:
this.IIPReply(packet.callbackId);
@ -316,7 +324,16 @@ export default class DistributedConnection extends IStore {
case IIPPacketAction.TemplateFromClassName:
case IIPPacketAction.TemplateFromClassId:
case IIPPacketAction.TemplateFromResourceId:
this.IIPReply(packet.callbackId, TypeTemplate.parse(packet.content));
if (packet.dataType != null) {
var content = msg.clip(packet.dataType?.offset ?? 0,
packet.dataType?.contentLength ?? 0);
this.IIPReply(packet.callbackId, TypeTemplate.parse(content));
} else {
iipReportError(packet.callbackId, ErrorType.Management,
ExceptionCode.TemplateNotFound.index, "Template not found");
}
break;
case IIPPacketAction.QueryLink:
@ -324,12 +341,11 @@ export default class DistributedConnection extends IStore {
case IIPPacketAction.ResourceParents:
case IIPPacketAction.ResourceHistory:
case IIPPacketAction.LinkTemplates:
this.IIPReply(packet.callbackId, packet.content);
this.IIPReply(packet.callbackId, packet.dataType, msg);
break;
case IIPPacketAction.InvokeFunctionArrayArguments:
case IIPPacketAction.InvokeFunctionNamedArguments:
this.IIPReplyInvoke(packet.callbackId, packet.content);
case IIPPacketAction.InvokeFunction:
this.IIPReplyInvoke(packet.callbackId, packet.dataType, msg);
break;
// case IIPPacketAction.GetProperty:
@ -348,7 +364,7 @@ export default class DistributedConnection extends IStore {
// Attribute
case IIPPacketAction.GetAllAttributes:
case IIPPacketAction.GetAttributes:
this.IIPReply(packet.callbackId, packet.content);
this.IIPReply(packet.callbackId, packet.dataType, msg);
break;
case IIPPacketAction.UpdateAllAttributes:
@ -373,7 +389,7 @@ export default class DistributedConnection extends IStore {
this.IIPReportProgress(packet.callbackId, ProgressType.Execution, packet.progressValue, packet.progressMax);
break;
case IIPPacketReport.ChunkStream:
this.IIPReportChunk(packet.callbackId, packet.content);
this.IIPReportChunk(packet.callbackId, packet.dataType, msg);
break;
}
@ -1150,8 +1166,8 @@ export default class DistributedConnection extends IStore {
{
for (let resource of this.subscriptions.keys()) {
resource.instance.off("ResourceEventOccurred", this.#_instance_eventOccurred, this);
resource.instance.off("ResourceModified", this.#_instance_propertyModified, this);
resource.instance.off("EventOccurred", this.#_instance_eventOccurred, this);
resource.instance.off("PropertyModified", this.#_instance_propertyModified, this);
resource.instance.off("ResourceDestroyed", this.#_instance_resourceDestroyed, this);
}
@ -1279,33 +1295,14 @@ export default class DistributedConnection extends IStore {
}
}
sendInvokeByArrayArguments(instanceId, index, parameters) {
sendInvoke(instanceId, index, parameters) {
var reply = new AsyncReply();
var pb = Codec.composeVarArray(parameters, this, true);
var pb = Codec.compose(parameters, this);
let callbackId = ++this.callbackCounter;
this.sendParams()
.addUint8(0x40 | IIPPacketAction.InvokeFunctionArrayArguments)
.addUint32(callbackId)
.addUint32(instanceId)
.addUint8(index)
.addUint8Array(pb)
.done();
this.requests.set(callbackId, reply);
return reply;
}
sendInvokeByNamedArguments(instanceId, index, parameters) {
var reply = new AsyncReply();
var pb = Codec.composeStructure(parameters, this, true, true, true);
let callbackId = ++this.callbackCounter;
this.sendParams()
.addUint8(0x40 | IIPPacketAction.InvokeFunctionNamedArguments)
.addUint8(0x40 | IIPPacketAction.InvokeFunction)
.addUint32(callbackId)
.addUint32(instanceId)
.addUint8(index)
@ -1346,7 +1343,7 @@ export default class DistributedConnection extends IStore {
}
sendChunk(callbackId, chunk) {
var c = Codec.compose(chunk, this, true);
var c = Codec.compose(chunk, this);
this.sendParams()
.addUint8(0xC0 | IIPPacketReport.ChunkStream)
.addUint32(callbackId)
@ -1362,7 +1359,7 @@ export default class DistributedConnection extends IStore {
req.trigger(results);
}
IIPReplyInvoke(callbackId, result) {
IIPReplyInvoke(callbackId, dataType, data) {
var req = this.requests.item(callbackId);
@ -1370,7 +1367,7 @@ export default class DistributedConnection extends IStore {
this.requests.remove(callbackId);
Codec.parse(result, 0, {}, this).then(function (rt) {
Codec.parse(data, 0, this, dataType).reply.then(function (rt) {
req.trigger(rt);
});
}
@ -1391,10 +1388,10 @@ export default class DistributedConnection extends IStore {
req.triggerProgress(type, value, max);
}
IIPReportChunk(callbackId, data) {
IIPReportChunk(callbackId, dataType, data) {
var req = this.requests.item(callbackId);
if (req != null) {
Codec.parse(data, 0, {}, this).then(function (x) {
Codec.parse(data, 0, this, dataType).reply.then(function (x) {
req.triggerChunk(x);
});
}
@ -1412,7 +1409,7 @@ export default class DistributedConnection extends IStore {
}
}
IIPEventPropertyUpdated(resourceId, index, content) {
IIPEventPropertyUpdated(resourceId, index, dataType, data) {
let self = this;
@ -1427,7 +1424,7 @@ export default class DistributedConnection extends IStore {
let item = new AsyncReply();
self.queue.add(item);
Codec.parse(content, 0, {}, self).then(function (args) {
Codec.parse(data, 0, self, dataType).reply.then(function (args) {
item.trigger(new DistributedResourceQueueItem(r, DistributedResourceQueueItemType.Propery, args, index));
}).error(function (ex) {
self.queue.remove(item);
@ -1437,7 +1434,7 @@ export default class DistributedConnection extends IStore {
}
IIPEventEventOccurred(resourceId, index, content) {
IIPEventEventOccurred(resourceId, index, dataType, data) {
var self = this;
this.fetch(resourceId).then(function (r) {
@ -1451,7 +1448,7 @@ export default class DistributedConnection extends IStore {
self.queue.add(item);
// Codec.parseVarArray(content, 0, content.length, self).then(function (args) {
Codec.parse(content, 0, {}, self).then(function (args) {
Codec.parse(data, 0, self, dataType).reply.then(function (args) {
item.trigger(new DistributedResourceQueueItem(r, DistributedResourceQueueItemType.Event, args, index));
}).error(function (ex) {
@ -1483,7 +1480,7 @@ export default class DistributedConnection extends IStore {
IIPEventRenamed(resourceId, name) {
this.fetch(resourceId).then(function (resource) {
resource.instance.attributes.set("name", name.getString(0, name.length));
resource.instance.attributes.set("name", name);
});
}
@ -1568,7 +1565,7 @@ export default class DistributedConnection extends IStore {
.addUint64(r.instance.age)
.addUint16(link.length)
.addUint8Array(link)
.addUint8Array(Codec.composePropertyValueArray(r._serialize(), self, true))
.addUint8Array(Codec.compose(r._serialize(), self))
.done();
else
self.sendReply(IIPPacketAction.AttachResource, callback)
@ -1576,7 +1573,7 @@ export default class DistributedConnection extends IStore {
.addUint64(r.instance.age)
.addUint16(link.length)
.addUint8Array(link)
.addUint8Array(Codec.composePropertyValueArray(r.instance.serialize(), self, true))
.addUint8Array(Codec.compose(r.instance.serialize(), self))
.done();
@ -1591,8 +1588,8 @@ export default class DistributedConnection extends IStore {
_subscribe(resource)
{
resource.instance.on("ResourceEventOccurred", this.#_instance_eventOccurred, this);
resource.instance.on("ResourceModified", this.#_instance_propertyModified, this);
resource.instance.on("EventOccurred", this.#_instance_eventOccurred, this);
resource.instance.on("PropertyModified", this.#_instance_propertyModified, this);
resource.instance.on("ResourceDestroyed", this.#_instance_resourceDestroyed, this);
this.subscriptions.set(resource, []);
@ -1600,8 +1597,8 @@ export default class DistributedConnection extends IStore {
_unsubscribe(resource)
{
resource.instance.off("ResourceEventOccurred", this.#_instance_eventOccurred, this);
resource.instance.off("ResourceModified", this.#_instance_propertyModified, this);
resource.instance.off("EventOccurred", this.#_instance_eventOccurred, this);
resource.instance.off("PropertyModified", this.#_instance_propertyModified, this);
resource.instance.off("ResourceDestroyed", this.#_instance_resourceDestroyed, this);
this.subscriptions.delete(resource);
@ -1620,7 +1617,7 @@ export default class DistributedConnection extends IStore {
// reply ok
self.sendReply(IIPPacketAction.ReattachResource, callback)
.addUint64(r.instance.age)
.addUint8Array(Codec.composePropertyValueArray(r.instance.serialize(), self, true))
.addUint8Array(Codec.compose(r.instance.serialize(), self))
.done();
}
else {
@ -1694,14 +1691,14 @@ export default class DistributedConnection extends IStore {
return;
}
Codec.parseVarArray(content, offset, cl, self).then(function (parameters) {
DataDeserializer.listParser(content, offset, cl, self).then(function (parameters) {
offset += cl;
cl = content.getUint32(offset);
Codec.parseStructure(content, offset, cl, self).then(function (attributes) {
DataDeserializer.typedMapParser(content, offset, cl, self).then(function (attributes) {
offset += cl;
cl = content.length - offset;
Codec.parseStructure(content, offset, cl, self).then(function (values) {
DataDeserializer.typedMapParser(content, offset, cl, self).then(function (values) {
var resource = new (Function.prototype.bind.apply(type, values));
@ -1772,8 +1769,7 @@ export default class DistributedConnection extends IStore {
// send
this.sendReply(IIPPacketAction.LinkTemplates, callback)
.addInt32(msg.length)
.addUint8Array(msg.toArray())
.addDC(TransmissionType.compose(TransmissionTypeIdentifier.RawData, msg))
.done();
}
}
@ -1807,8 +1803,8 @@ export default class DistributedConnection extends IStore {
if (t != null)
self.sendReply(IIPPacketAction.TemplateFromClassId, callback)
.addUint32(t.content.length)
.addUint8Array(t.content)
.addDC(TransmissionType.compose(
TransmissionTypeIdentifier.RawData, t.content))
.done();
else {
// reply failed
@ -1823,8 +1819,8 @@ export default class DistributedConnection extends IStore {
Warehouse.getById(resourceId).then(function (r) {
if (r != null)
self.sendReply(IIPPacketAction.TemplateFromResourceId, callback)
.addUint32(r.instance.template.content.length)
.addUint8Array(r.instance.template.content)
.addDC(TransmissionType.compose(
TransmissionTypeIdentifier.RawData, r.instance.template.content))
.done();
else {
// reply failed
@ -1833,45 +1829,69 @@ export default class DistributedConnection extends IStore {
});
}
IIPRequestInvokeFunctionArrayArguments(callback, resourceId, index, content) {
IIPRequestInvokeFunction(callback, resourceId, index, dataType, data) {
var self = this;
let self = this;
Warehouse.getById(resourceId).then(function (r) {
if (r != null) {
Codec.parseVarArray(content, 0, content.length, self).then(function (args) {
var ft = r.instance.template.getFunctionTemplateByIndex(index);
if (ft != null) {
if (r == null) {
this.sendError(ErrorType.Management, callback, ExceptionCode.ResourceNotFound);
return;
}
let ft = r.instance.template.getFunctionTemplateByIndex(index);
if (ft == null)
{
// no function at this index
this.sendError(ErrorType.Management, callback, ExceptionCode.MethodNotFound);
return;
}
Codec.parse(data, 0, self, dataType).reply.then(function (args) {
if (r instanceof DistributedResource) {
var rt = r._invokeByArrayArguments(index, args);
var rt = r._invoke(index, args);
if (rt != null) {
rt.then(function (res) {
self.sendReply(IIPPacketAction.InvokeFunctionArrayArguments, callback)
self.sendReply(IIPPacketAction.InvokeFunction, callback)
.addUint8Array(Codec.compose(res, self))
.done();
});
}
else {
// function not found on a distributed object
this.sendError(ErrorType.Management, callback, ExceptionCode.MethodNotFound);
return;
}
}
else {
else
{
var fi = r[ft.name];
if (!(fi instanceof Function)) {
// ft found, fi not found, this should never happen
this.sendError(ErrorType.Management, callback, ExceptionCode.MethodNotFound);
return;
}
if (r.instance.applicable(self.session, ActionType.Execute, ft) == Ruling.Denied) {
self.sendError(ErrorType.Management, callback, ExceptionCode.InvokeDenied);
return;
}
if (fi instanceof Function) {
args.push(self);
let indexedArgs = [];
var rt;
for(let i = 0; i < ft.args.length; i++)
indexedArgs.push(args.get(i));
indexedArgs.push(self);
let rt;
try
{
rt = fi.apply(r, args);
rt = fi.apply(r, indexedArgs);
}
catch(ex)
{
@ -1884,13 +1904,13 @@ export default class DistributedConnection extends IStore {
for (let v of rt)
self.sendChunk(callback, v);
self.sendReply(IIPPacketAction.InvokeFunctionArrayArguments, callback)
self.sendReply(IIPPacketAction.InvokeFunction, callback)
.addUint8(DataType.Void)
.done();
}
else if (rt instanceof AsyncReply) {
rt.then(function (res) {
self.sendReply(IIPPacketAction.InvokeFunctionArrayArguments, callback)
self.sendReply(IIPPacketAction.InvokeFunction, callback)
.addUint8Array(Codec.compose(res, self))
.done();
}).error(ex => {
@ -1906,7 +1926,7 @@ export default class DistributedConnection extends IStore {
else if (rt instanceof Promise)
{
rt.then(function (res) {
self.sendReply(IIPPacketAction.InvokeFunctionArrayArguments, callback)
self.sendReply(IIPPacketAction.InvokeFunction, callback)
.addUint8Array(Codec.compose(res, self))
.done();
}).catch(ex => {
@ -1914,148 +1934,17 @@ export default class DistributedConnection extends IStore {
});
}
else {
self.sendReply(IIPPacketAction.InvokeFunctionArrayArguments, callback)
self.sendReply(IIPPacketAction.InvokeFunction, callback)
.addUint8Array(Codec.compose(rt, self))
.done();
}
}
else {
// ft found, fi not found, this should never happen
this.sendError(ErrorType.Management, callback, ExceptionCode.MethodNotFound);
}
}
}
else {
// no function at this index
this.sendError(ErrorType.Management, callback, ExceptionCode.MethodNotFound);
}
});
}
else {
// no resource with this id
this.sendError(ErrorType.Management, callback, ExceptionCode.ResourceNotFound);
}
});
}
IIPRequestInvokeFunctionNamedArguments(callback, resourceId, index, content) {
var self = this;
Warehouse.getById(resourceId).then(function (r) {
if (r != null) {
Codec.parseStructure(content, 0, content.length, self).then(function (namedArgs) {
var ft = r.instance.template.getFunctionTemplateByIndex(index);
if (ft != null) {
if (r instanceof DistributedResource) {
var rt = r._invokeByNamedArguments(index, namedArgs);
if (rt != null) {
rt.then(function (res) {
self.sendReply(IIPPacketAction.InvokeFunctionNamedArguments, callback)
.addUint8Array(Codec.compose(res, self))
.done();
});
}
else {
// function not found on a distributed object
}
}
else {
var fi = r[ft.name];
if (r.instance.applicable(self.session, ActionType.Execute, ft) == Ruling.Denied) {
self.sendError(ErrorType.Management, callback, ExceptionCode.InvokeDenied);
return;
}
if (fi instanceof Function) {
var pi = TypeTemplate.getFunctionParameters(fi);
var args = new Array(pi.length);
for (var i = 0; i < pi.length; i++) {
if (namedArgs[pi[i]] !== undefined)
args[i] = namedArgs[pi[i]];
}
// pass this to the last argument if it is undefined
if (args[args.length - 1] === undefined)
args[args.length - 1] = self;
var rt;
try
{
rt = fi.apply(r, args);
}
catch(ex)
{
self.sendError(ErrorType.Exception, callback, 0, ex.toString());
return;
}
// Is iterator ?
if (rt != null && rt[Symbol.iterator] instanceof Function) {
for (let v of rt)
self.sendChunk(callback, v);
self.sendReply(IIPPacketAction.InvokeFunctionNamedArguments, callback)
.addUint8(DataType.Void)
.done();
}
else if (rt instanceof AsyncReply) {
rt.then(function (res) {
self.sendReply(IIPPacketAction.InvokeFunctionNamedArguments, callback)
.addUint8Array(Codec.compose(res, self))
.done();
}).error(ex => {
self.sendError(ErrorType.Exception, callback, ex.code, ex.message);
}).progress((pt, pv, pm) =>
{
self.sendProgress(callback, pv, pm);
}).chunk(v =>
{
self.sendChunk(callback, v);
});
}
else if (rt instanceof Promise)
{
rt.then(function (res) {
self.sendReply(IIPPacketAction.InvokeFunctionNamedArguments, callback)
.addUint8Array(Codec.compose(res, self))
.done();
}).catch(ex => {
self.sendError(ErrorType.Exception, callback, 0, ex.toString());
});
}
else {
self.sendReply(IIPPacketAction.InvokeFunctionNamedArguments, callback)
.addUint8Array(Codec.compose(rt, self))
.done();
}
}
else {
// ft found, fi not found, this should never happen
this.sendError(ErrorType.Management, callback, ExceptionCode.MethodNotFound);
}
}
}
else {
// no function at this index
this.sendError(ErrorType.Management, callback, ExceptionCode.MethodNotFound);
}
});
}
else {
// no resource with this id
this.sendError(ErrorType.Management, callback, ExceptionCode.ResourceNotFound);
}
});
}
// IIPRequestGetProperty(callback, resourceId, index) {
// var self = this;
@ -2222,7 +2111,7 @@ export default class DistributedConnection extends IStore {
});
}
IIPRequestSetProperty(callback, resourceId, index, content) {
IIPRequestSetProperty(callback, resourceId, index, dataType, data) {
var self = this;
@ -2232,7 +2121,7 @@ export default class DistributedConnection extends IStore {
var pt = r.instance.template.getPropertyTemplateByIndex(index);
if (pt != null) {
Codec.parse(content, 0, {}, this).then(function (value) {
Codec.parse(data, 0, self, dataType).reply.then(function (value) {
if (r instanceof DistributedResource) {
// propagation
r._set(index, value).then(function (x) {
@ -2304,7 +2193,7 @@ export default class DistributedConnection extends IStore {
self.sendError(ErrorType.Management, callback, ExceptionCode.ResourceNotFound);
else
self.sendReply(IIPPacketAction.QueryLink, callback)
.addUint8Array(Codec.composeResourceArray(list, self, true))
.addUint8Array(Codec.compose(list, self))
.done();
}
};
@ -2354,10 +2243,16 @@ export default class DistributedConnection extends IStore {
.addUint16(sb.length)
.addUint8Array(sb)
.done()
.then(function (args) {
Codec.parseResourceArray(args[0], 0, args[0].length, self).then(function (resources) {
reply.trigger(resources);
});
.then(function (ar) {
let dataType = ar[0];
let data = ar[1];
Codec.parse(data, 0, self, dataType).reply.then((resources) => {
reply.trigger((resources))
}
).error((ex) => reply.triggerError(ex));
}).error(function (ex) {
reply.triggerError(ex);
});
@ -2459,10 +2354,12 @@ export default class DistributedConnection extends IStore {
var templates = [];
// parse templates
var data = rt[0];
let tt = rt[0];
let data = rt[1] ;
//var offset = 0;
for (var offset = 0; offset < data.length;)
{
for (var offset = tt.offset; offset < tt.contentLength;) {
var cs = data.getUint32(offset);
offset += 4;
templates.push(TypeTemplate.parse(data, offset, cs));
@ -2523,17 +2420,34 @@ export default class DistributedConnection extends IStore {
//let dr = resource || new DistributedResource(self, id, rt[1], rt[2]);
let transmissionType = rt[3] ;
let content = rt[4] ;
self.getTemplate(rt[0]).then(function (tmp) {
// ClassId, ResourceAge, ResourceLink, Content
if (resource == null)
{
let wp = Warehouse.put(id.toString(), dr, self, null, tmp).then(function(ok){
Codec.parsePropertyValueArray(rt[3], 0, rt[3].length, self).then(function (ar) {
dr._attach(ar);
Codec.parse(content, 0, self, transmissionType)
.reply
.then((ar) => {
var pvs = new PropertyValueArray();
for (var i = 0; i < ar.length; i += 3)
pvs.push(new PropertyValue(
ar[i + 2], ar[i], ar[i + 1]));
dr._attach(pvs);
self.resourceRequests.remove(id);
reply.trigger(dr);
});
})
.error((ex) => reply.triggerError(ex));
});
wp.error(function(ex){
@ -2542,13 +2456,24 @@ export default class DistributedConnection extends IStore {
}
else
{
Codec.parsePropertyValueArray(rt[3], 0, rt[3].length, self).then(function (ar) {
dr._attach(ar);
Codec.parse(content, 0, self, transmissionType)
.reply
.then((ar) => {
//print("attached");
if (results != null) {
var pvs = new PropertyValueArray();
for (var i = 0; i < ar.length; i += 3)
pvs.push(new PropertyValue(
ar[i + 2], ar[i], ar[i + 1]));
dr._attach(pvs);
}
self.resourceRequests.remove(id);
reply.trigger(dr);
}).error(function(ex){
reply.triggerError(ex);
});
}).error(function(ex) { reply.triggerError(ex)});
}
}).error(function(ex){
reply.triggerError(ex);
@ -2595,26 +2520,20 @@ export default class DistributedConnection extends IStore {
.done();
}
#_instance_propertyModified = function(resource, name, newValue) {
var pt = resource.instance.template.getPropertyTemplateByName(name);
if (pt == null)
return;
#_instance_propertyModified = function(info) {
this.sendEvent(IIPPacketEvent.PropertyUpdated)
.addUint32(resource.instance.id)
.addUint8(pt.index)
.addUint8Array(Codec.compose(newValue, this))
.addUint32(info.resource.instance?.id)
.addUint8(info.propertyTemplate.index)
.addUint8Array(Codec.compose(info.value, this))
.done();
}
#_instance_eventOccurred = function(resource, issuer, receivers, name, args) {
var et = resource.instance.template.getEventTemplateByName(name);
#_instance_eventOccurred = function(info) {
if (et == null)
return;
if (et.listenable)
if (info.eventTemplate.listenable)
{
// check the client requested listen
if (!this.subscriptions.has(resource))
@ -2624,19 +2543,20 @@ export default class DistributedConnection extends IStore {
return;
}
if (receivers instanceof Function)
if (!receivers(this.sessions))
if (info.receivers instanceof Function)
if (!info.receivers(this.sessions))
return;
if (resource.instance.applicable(this.session, ActionType.ReceiveEvent, et, issuer) == Ruling.Denied)
if (info.resource.instance.applicable(this.session,
ActionType.ReceiveEvent, info.eventTemplate, info.issuer) == Ruling.Denied)
return;
// compose the packet
this.sendEvent(IIPPacketEvent.EventOccurred)
.addUint32(resource.instance.id)
.addUint8(et.index)
.addUint8Array(Codec.compose(args, this, true))
.addUint32(info.resource.instance.id)
.addUint8(info.eventTemplate.index)
.addUint8Array(Codec.compose(info.value, this))
.done();
}
@ -2725,7 +2645,7 @@ export default class DistributedConnection extends IStore {
return;
}
resource.instance.name = name.getString(0, name.length);
resource.instance.name = name;
self.sendReply(IIPPacketAction.RenameResource, callback)
.done();
});
@ -2740,7 +2660,7 @@ export default class DistributedConnection extends IStore {
}
self.sendReply(IIPPacketAction.ResourceChildren, callback)
.addUint8Array(Codec.composeResourceArray(resource.instance.children.toArray(), this, true))
.addUint8Array(Codec.compose(resource.instance.children.toArray(), self))
.done();
});
@ -2756,7 +2676,7 @@ export default class DistributedConnection extends IStore {
}
self.sendReply(IIPPacketAction.ResourceParents, callback)
.addUint8Array(Codec.composeResourceArray(resource.instance.parents.toArray(), this, true))
.addUint8Array(Codec.compose(resource.instance.parents.toArray(), self))
.done();
});
}
@ -2801,7 +2721,7 @@ export default class DistributedConnection extends IStore {
return;
}
Codec.parseStructure(attributes, 0, attributes.length, this).then(function (attrs) {
DataDeserializer.typedListParser(attributes, 0, attributes.length, this).then(function (attrs) {
if (r.instance.setAttributes(attrs, clearAttributes))
self.sendReply(clearAttributes ? IIPPacketAction.ClearAllAttributes : IIPPacketAction.ClearAttributes,
callback)
@ -2826,11 +2746,16 @@ export default class DistributedConnection extends IStore {
this.sendRequest(IIPPacketAction.ResourceChildren)
.addUint32(resource._p.instanceId)
.done()
.then(function (d) {
.then(function (ar) {
Codec.parseResourceArray(d, 0, d.length, self).then(function (resources) {
let dataType = ar[0];
let data = ar[1];
Codec.parse(data, 0, self, dataType).reply.then((resources) => {
rt.trigger(resources);
}).error(function (ex) { rt.triggerError(ex); });
})
.error((ex) => rt.triggerError(ex));
});
return rt;
@ -2846,10 +2771,15 @@ export default class DistributedConnection extends IStore {
this.sendRequest(IIPPacketAction.ResourceParents)
.addUint32(resource._p.instanceId)
.done()
.then(function (d) {
Codec.parseResourceArray(d, 0, d.length, self).then(function (resources) {
.then(function (ar) {
let dataType = ar[0] ;
let data = ar[1];
Codec.parse(data, 0, self, dataType).reply.then((resources) => {
rt.trigger(resources);
}).error(function (ex) { rt.triggerError(ex); });
})
.error((ex) => rt.triggerError(ex));
});
return rt;
@ -2891,7 +2821,7 @@ export default class DistributedConnection extends IStore {
this.sendRequest(clearAttributes ? IIPPacketAction.UpdateAllAttributes : IIPPacketAction.UpdateAttributes)
.addUint32(resource._p.instanceId)
.addUint8Array(Codec.composeStructure(attributes, this, true, true, true))
.addUint8Array(Codec.compose(attributes, this))
.done()
.then(function () {
rt.trigger(true);
@ -2904,35 +2834,47 @@ export default class DistributedConnection extends IStore {
if (resource._p.connection != this)
return new AsyncReply(null);
var rt = new AsyncReply();
var self = this;
let rt = new AsyncReply();
let self = this;
if (attributes == null) {
this.sendRequest(IIPPacketAction.GetAllAttributes)
.addUint32(resource._p.instanceId)
.done()
.then(function (ar) {
Codec.parseStructure(ar[0], 0, ar[0].length, this).then(function (st) {
for (var a in st)
resource.instance.attributes.set(a, st[a]);
let dataType = ar[0];
let data = ar[1];
Codec.parse(data, 0, self, dataType).reply.then((st) => {
resource.instance?.setAttributes(st);
rt.trigger(st);
})
.error((ex) => rt.triggerError(ex));
}).error(function(ex) { rt.triggerError(ex); });
});
}
else {
var attrs = DC.stringArrayToBytes(attributes);
let attrs = DC.stringArrayToBytes(attributes);
this.sendRequest(IIPPacketAction.GetAttributes)
.addUint32(resource._p.instanceId)
.addUint32(attrs.length)
.addUint8Array(attrs)
.done()
.then(function (ar) {
Codec.parseStructure(ar[0], 0, ar[0].length, self).then(function (st) {
for (var a in st)
resource.instance.attributes.set(a, st[a]);
let dataType = ar[0] ;
let data = ar[1] ;
Codec.parse(data, 0, self, dataType).reply
.then((st) => {
resource.instance?.setAttributes(st);
rt.trigger(st);
}).error(function (ex) { rt.triggerError(ex); });
});
})
.error((ex) => rt.triggerError(ex));
}).error((ex) => rt.triggerError(ex));;
}
return rt;

View File

@ -29,12 +29,15 @@
import IResource from '../../Resource/IResource.js';
import AsyncReply from '../../Core/AsyncReply.js';
import Codec from '../../Data/Codec.js';
import Structure from '../../Data/Structure.js';
import IIPPacketAction from '../Packets//IIPPacketAction.js';
import EventTemplate from '../../Resource/Template/EventTemplate.js';
import AsyncException from '../../Core/AsyncException.js';
import ExceptionCode from '../../Core//ExceptionCode.js';
import ErrorType from '../../Core/ErrorType.js';
import {UInt8} from '../../Data/ExtendedTypes.js';
import TypedMap from '../../Data/TypedMap.js';
import PropertyValueArray from '../../Data/PropertyValueArray.js';
import PropertyValue from '../../Data/PropertyValue.js';
export default class DistributedResource extends IResource
{
@ -74,7 +77,7 @@ export default class DistributedResource extends IResource
_serialize()
{
var props = [];
var props = new PropertyValueArray();
for (var i = 0; i < this._p.properties.length; i++)
props.push(new PropertyValue(this._p.properties[i],
@ -112,25 +115,37 @@ export default class DistributedResource extends IResource
var self = this;
var makeFunc = function(index)
var makeFunc = function(ft)
{
var func = function () {
var argsMap = new (TypedMap.of(UInt8, Object));
if ( arguments.length == 1
&& arguments[0] instanceof Object
&& arguments[0].constructor.name == "Object")
{
var namedArgs = new Structure(arguments[0]);
return self._invokeByNamedArguments(index, namedArgs);
// named args
for (let i = 0; i < ft.args.length; i++){
let arg = ft.args[i];
if (arguments[arg.name] != undefined) {
argsMap.set(new UInt8(arg.index), arguments[arg.name]);
}
}
return self._invoke(ft.index, argsMap);
}
else
{
return self._invokeByArrayArguments(index, arguments);
for(let i = 0; (i < arguments.length) && (i < ft.args.length); i++)
argsMap.set(new UInt8(i), arguments[i]);
return self._invoke(ft.index, argsMap);
}
};
// get expansion
func.help = self.instance.template.functions[index].expansion;
func.help = self.instance.template.functions[ft.index].expansion;
return func;
};
@ -148,15 +163,15 @@ export default class DistributedResource extends IResource
};
};
for(var i = 0; i < this.instance.template.functions.length; i++)
for(let i = 0; i < this.instance.template.functions.length; i++)
{
var ft = this.instance.template.functions[i];
this[ft.name] = makeFunc(ft.index);
let ft = this.instance.template.functions[i];
this[ft.name] = makeFunc(ft);
}
for(var i = 0; i < this.instance.template.properties.length; i++)
for(let i = 0; i < this.instance.template.properties.length; i++)
{
var pt = this.instance.template.properties[i];
let pt = this.instance.template.properties[i];
Object.defineProperty(this, pt.name, {
get: makeGetter(pt.index),
@ -202,10 +217,10 @@ export default class DistributedResource extends IResource
//@TODO if array _emitArgs
//this._emitArgs(et.name, [args]);
this._emit(et.name, args);
this.instance._emitResourceEvent(null, null, et.name, args);
this.instance._emitResourceEvent(null, null, et, args);
}
_invokeByArrayArguments(index, args) {
_invoke(index, args) {
if (this.destroyed)
throw new Error("Trying to access destroyed object");
@ -215,20 +230,7 @@ export default class DistributedResource extends IResource
if (index >= this.instance.template.functions.length)
throw new Error("Function index is incorrect");
return this._p.connection.sendInvokeByArrayArguments(this._p.instanceId, index, args);
}
_invokeByNamedArguments(index, namedArgs) {
if (this.destroyed)
throw new Error("Trying to access destroyed object");
if (this._p.suspended)
throw new Error("Trying to access suspended object");
if (index >= this.instance.template.functions.length)
throw new Error("Function index is incorrect");
return this._p.connection.sendInvokeByNamedArguments(this._p.instanceId, index, namedArgs);
return this._p.connection.sendInvoke(this._p.instanceId, index, args);
}
_get(index)

View File

@ -24,9 +24,8 @@
* Created by Ahmed Zamil on 01/09/2017.
*/
"use strict";
import DC from '../Data/DataConverter.js';
import DC from '../Data/DC.js';
export default class NetworkBuffer {
constructor() {

View File

@ -1,5 +1,5 @@
/*
* Copyright (c) 2017 Ahmed Kh. Zamil
* Copyright (c) 2017-2022 Ahmed Kh. Zamil
*
* Permission is hereby granted, free of charge, to any person obtaining a copy
* of this software and associated documentation files (the "Software"), to deal
@ -31,6 +31,7 @@ import IIPPacketCommand from "./IIPPacketCommand.js";
import IIPPacketEvent from "./IIPPacketEvent.js";
import IIPPacketReport from "./IIPPacketReport.js";
import DataType from '../../Data/DataType.js';
import TransmissionType from '../../Data/TransmissionType.js';
export default class IIPPacket
{
@ -42,7 +43,7 @@ export default class IIPPacket
this.resourceId = 0;
this.newResourceId = 0;
this.resourceAge = 0;
this.content = [];
//this.content = [];
this.errorCode = 0;
this.errorMessage = "";
this.className = "";
@ -53,6 +54,8 @@ export default class IIPPacket
this.callbackId = 0;
this.dataLengthNeeded = 0;
this.originalOffset = 0;
this.resourceName = "";
this.dataType = null;
}
notEnough(offset, ends, needed)
@ -136,14 +139,13 @@ export default class IIPPacket
if (this.notEnough(offset, ends, 2))
return -this.dataLengthNeeded;
var cl = data.getUint16(offset);
let cl = data.getUint16(offset);
offset += 2;
if (this.notEnough(offset, ends, cl))
return -this.dataLengthNeeded;
this.content = data.clip(offset, cl);
this.resourceName = data.getString(offset, cl);
offset += cl;
}
else if (this.event == IIPPacketEvent.PropertyUpdated
@ -154,61 +156,28 @@ export default class IIPPacket
this.methodIndex = data[offset++];
var dt = data.getUint8(offset++);
var size = DataType.sizeOf(dt);
var parsed = TransmissionType.parse(data, offset, ends);
if (size < 0)
{
if (this.notEnough(offset, ends, 4))
return -this.dataLengthNeeded;
if (parsed.type == null) return -parsed.size;
var cl = data.getUint32(offset);
offset += 4;
this.dataType = parsed.type;
offset += parsed.size;
if (this.notEnough(offset, ends, cl))
return -this.dataLengthNeeded;
this.content = data.clip(offset - 5, cl + 5);
offset += cl;
}
else
{
if (this.notEnough(offset, ends, size))
return -this.dataLengthNeeded;
this.content = data.clip(offset - 1, size + 1);
offset += size;
}
}
// else if (this.event == IIPPacketEvent.EventOccurred)
// {
// if (this.notEnough(offset, ends, 5))
// return -this.dataLengthNeeded;
// this.methodIndex = data.getUint8(offset++);
// var cl = data.getUint32(offset);
// offset += 4;
// if (this.notEnough(offset, ends, cl))
// return -this.dataLengthNeeded;
// this.content = data.clip(offset, cl);
// offset += cl;
// }
// Attribute
else if (this.event == IIPPacketEvent.AttributesUpdated)
{
if (this.notEnough(offset, ends, 4))
return -this.dataLengthNeeded;
var cl = data.getUint32(offset);
let cl = data.getUint32(offset);
offset += 4;
if (this.notEnough(offset, ends, cl))
return -this.dataLengthNeeded;
this.content = data.clip(offset, cl);
//@TODO: fix this
//this.content = data.clip(offset, cl);
offset += cl;
}
@ -246,20 +215,21 @@ export default class IIPPacket
else if (this.action == IIPPacketAction.CreateResource)
{
if (this.notEnough(offset, ends, 12))
return -dataLengthNeeded;
return -this.dataLengthNeeded;
this.storeId = data.getUint32(offset);
offset += 4;
this.resourceId = data.getUint32(offset);
offset += 4;
var cl = data.getUint32(offset);
let cl = data.getUint32(offset);
offset += 4;
if (this.notEnough(offset, ends, cl))
return -dataLengthNeeded;
return -this.dataLengthNeeded;
this.content = data.clip(offset, cl);
//@TODO: fix this
//this.content = data.clip(offset, cl);
}
else if (this.action == IIPPacketAction.DeleteResource)
{
@ -291,13 +261,13 @@ export default class IIPPacket
this.resourceId = data.getUint32(offset);
offset += 4;
var cl = data.getUint16(offset);
let cl = data.getUint16(offset);
offset += 2;
if (this.notEnough(offset, ends, cl))
return -this.dataLengthNeeded;
this.content = data.clip(offset, cl);
this.resourceName = data.getString(offset, cl);
offset += cl;
}
@ -306,7 +276,7 @@ export default class IIPPacket
if (this.notEnough(offset, ends, 1))
return -this.dataLengthNeeded;
var cl = data.getUint8(offset++);
let cl = data.getUint8(offset++);
if (this.notEnough(offset, ends, cl))
return -this.dataLengthNeeded;
@ -337,7 +307,7 @@ export default class IIPPacket
if (this.notEnough(offset, ends, 2))
return -this.dataLengthNeeded;
var cl = data.getUint16(offset);
let cl = data.getUint16(offset);
offset += 2;
if (this.notEnough(offset, ends, cl))
@ -370,8 +340,7 @@ export default class IIPPacket
offset += 8;
}
else if ( this.action == IIPPacketAction.InvokeFunctionArrayArguments
|| this.action == IIPPacketAction.InvokeFunctionNamedArguments)
else if ( this.action == IIPPacketAction.InvokeFunction )
{
if (this.notEnough(offset, ends, 9))
@ -382,14 +351,13 @@ export default class IIPPacket
this.methodIndex = data.getUint8(offset++);
var cl = data.getUint32(offset);
offset += 4;
if (this.notEnough(offset, ends, cl))
return -this.dataLengthNeeded;
let parsed = TransmissionType.parse(data, offset, ends);
this.content = data.clip(offset, cl);
offset += cl;
if (parsed.type == null) return -parsed.size;
this.dataType = parsed.type;
offset += parsed.size;
}
else if (this.action == IIPPacketAction.Listen
@ -428,33 +396,13 @@ export default class IIPPacket
offset += 4;
this.methodIndex = data[offset++];
let parsed = TransmissionType.parse(data, offset, ends);
if (parsed.type == null) return -parsed.size;
var dt = data.getUint8(offset++);
var size = DataType.sizeOf(dt);
this.dataType = parsed.type;
offset += parsed.size;
if (size < 0)
{
if (this.notEnough(offset, ends, 4))
return -this.dataLengthNeeded;
var cl = data.getUint32(offset);
offset += 4;
if (this.notEnough(offset, ends, cl))
return -this.dataLengthNeeded;
this.content = data.clip(offset-5, cl + 5);
offset += cl;
}
else
{
if (this.notEnough(offset, ends, size))
return -this.dataLengthNeeded;
this.content = data.clip(offset-1, size + 1);
offset += size;
}
}
// Attribute
@ -468,13 +416,14 @@ export default class IIPPacket
this.resourceId = data.getUint32(offset);
offset += 4;
var cl = data.getUint32(offset);
let cl = data.getUint32(offset);
offset += 4;
if (this.notEnough(offset, ends, cl))
return -this.dataLengthNeeded;
this.content = data.clip(offset, cl);
// @TODO: fix this
//this.content = data.clip(offset, cl);
offset += cl;
}
@ -493,7 +442,7 @@ export default class IIPPacket
this.resourceAge = data.getUint64(offset);
offset += 8;
var cl = data.getUint16(offset);
let cl = data.getUint16(offset);
offset+=2;
if (this.notEnough(offset, ends, cl))
@ -502,17 +451,13 @@ export default class IIPPacket
this.resourceLink = data.getString(offset, cl);
offset += cl;
if (this.notEnough(offset, ends, 4))
return -this.dataLengthNeeded;
let parsed = TransmissionType.parse(data, offset, ends);
cl = data.getUint32(offset);
offset += 4;
if (parsed.type == null) return -parsed.size;
if (this.notEnough(offset, ends, cl))
return -this.dataLengthNeeded;
this.dataType = parsed.type;
offset += parsed.size;
this.content = data.clip(offset, cl);
offset += cl;
}
else if (this.action == IIPPacketAction.DetachResource)
{
@ -544,52 +489,30 @@ export default class IIPPacket
|| this.action == IIPPacketAction.GetAllAttributes
|| this.action == IIPPacketAction.GetAttributes)
{
if (this.notEnough(offset, ends, 4))
return -this.dataLengthNeeded;
var cl = data.getUint32(offset);
offset += 4;
if (this.notEnough(offset, ends, 1)) return -this.dataLengthNeeded;
if (this.notEnough(offset, ends, cl))
return -this.dataLengthNeeded;
let parsed = TransmissionType.parse(data, offset, ends);
if (parsed.type == null) return -parsed.size;
this.dataType = parsed.type;
offset += parsed.size;
this.content = data.clip(offset, cl);
offset += cl;
}
else if (this.action == IIPPacketAction.InvokeFunctionArrayArguments
|| this.action == IIPPacketAction.InvokeFunctionNamedArguments)
//|| this.action == IIPPacketAction.GetProperty
//|| this.action == IIPPacketAction.GetPropertyIfModified)
else if (this.action == IIPPacketAction.InvokeFunction)
{
if (this.notEnough(offset, ends, 1))
return -this.dataLengthNeeded;
var dt = data.getUint8(offset++);
var size = DataType.sizeOf(dt);
let parsed = TransmissionType.parse(data, offset, ends);
if (size < 0)
{
if (this.notEnough(offset, ends, 4))
return -this.dataLengthNeeded;
if (parsed.type == null) return -parsed.size;
var cl = data.getUint32(offset);
offset += 4;
this.dataType = parsed.type;
offset += parsed.size;
if (this.notEnough(offset, ends, cl))
return -this.dataLengthNeeded;
this.content = data.clip(offset - 5, cl + 5);
offset += cl;
}
else
{
if (this.notEnough(offset, ends, size))
return -this.dataLengthNeeded;
this.content = data.clip(offset - 1, size + 1);
offset += size;
}
}
else if (this.action == IIPPacketAction.SetProperty
|| this.action == IIPPacketAction.Listen
@ -619,7 +542,7 @@ export default class IIPPacket
if (this.notEnough(offset, ends, 2))
return -this.dataLengthNeeded;
var cl = data.getUint16(offset);
let cl = data.getUint16(offset);
offset += 2;
if (this.notEnough(offset, ends, cl))
@ -640,31 +563,16 @@ export default class IIPPacket
}
else if (this.report == IIPPacketReport.ChunkStream)
{
var dt = data.getUint8(offset++);
var size = DataType.sizeOf(dt);
if (size < 0)
{
if (this.notEnough(offset, ends, 4))
if (this.notEnough(offset, ends, 1))
return -this.dataLengthNeeded;
var cl = data.getUint32(offset);
offset += 4;
let parsed = TransmissionType.parse(data, offset, ends);
if (this.notEnough(offset, ends, cl))
return -this.dataLengthNeeded;
if (parsed.type == null) return -parsed.size;
this.content = data.clip(offset - 5, cl + 5);
offset += cl;
}
else
{
if (this.notEnough(offset, ends, size))
return -this.dataLengthNeeded;
this.dataType = parsed.type;
offset += parsed.size;
this.content = data.clip(offset - 1, size + 1);
offset += size;
}
}
}

View File

@ -21,8 +21,8 @@ export default // const IIPPacketAction =
LinkTemplates: 15,
// Request Invoke
InvokeFunctionArrayArguments: 16,
InvokeFunctionNamedArguments: 17,
InvokeFunction: 16,
Reserved: 17,
Listen: 18,
Unlisten: 19,
SetProperty: 20,

View File

@ -7,19 +7,15 @@ import NetworkBuffer from "../NetworkBuffer.js";
export default class WSocket extends ISocket
{
//SocketState State { get; }
//INetworkReceiver<ISocket> Receiver { get; set; }
constructor(websocket){
super();
this.receiveNetworkBuffer = new NetworkBuffer();
this.sendNetworkBuffer = new NetworkBuffer();
this.held = false;
if (websocket != null)// instanceof WebSocket)
if (websocket != null)
{
//websocket.onerror = () => {
// self.state = SocketState.Closed;
//};
websocket.onopen = () => {
self.state = SocketState.Established;
};
@ -47,6 +43,8 @@ export default class WSocket extends ISocket
sendAll(message)
{
// console.log("Out ", message.byteLength);
if (this.held)
this.sendNetworkBuffer.writeAll(message);
else
@ -68,17 +66,37 @@ export default class WSocket extends ISocket
this.ws.close();
}
static webSocket = null;
static async getWebScoket(){
if (WSocket.webSocket == null) {
if (typeof window === 'undefined') {
const wsModule = await import('ws');
WSocket.webSocket = wsModule.default;
}
else
{
WSocket.webSocket = WebSocket;
}
}
return WSocket.webSocket;
}
connect(hostname, port, secure = false) {
let self = this;
var rt = new AsyncReply();
this.state = SocketState.Connecting;
this.url = `ws${secure ? 's' : ''}://${hostname}:${port}`;
let ws = new WebSocket(this.url, "iip");
WSocket.getWebScoket().then(webSocket =>
{
let ws;
ws = new webSocket(this.url, "iip");
ws.binaryType = "arraybuffer";
ws.onopen = () => {
@ -91,7 +109,9 @@ export default class WSocket extends ISocket
rt.triggerError(ErrorType.Management, ExceptionCode.HostNotReachable);
};
this._assign(ws);
self._assign(ws);
});
return rt;// new AsyncReply(true);
}
@ -106,6 +126,7 @@ export default class WSocket extends ISocket
};
ws.onmessage = function(msg) {
//console.log("WREC ", msg.data.byteLength);
self.receiveNetworkBuffer.writeAll(msg.data);
self.receiver.networkReceive(this, self.receiveNetworkBuffer);
//self.lastAction = new Date();
@ -156,10 +177,3 @@ export default class WSocket extends ISocket
}
}
}
// if (this.holdSending) {
// //console.log("hold ", data.length);
// this.sendBuffer.writeAll(data);
// }
// else
// //console.log("Send", data.length);

View File

@ -28,10 +28,10 @@
export default class CustomResourceEvent
{
constructor(issuer, receivers, args)
constructor(issuer, receivers, value)
{
this.issuer = issuer;
this.receivers = receivers;
this.args = args;
this.value = value;
}
}

View File

@ -0,0 +1,20 @@
import Session from '../Security/Authority/Session.js';
import IResource from './IResource.js';
import EventTemplate from './Template/EventTemplate.js';
export default class EventOccurredInfo {
get name(){
return this.eventTemplate.name;
}
constructor(resource, eventTemplate, value, issuer,
receivers) {
this.resource =resource;
this.eventTemplate = eventTemplate;
this.value = value;
this.issuer = issuer;
this.receivers = receivers;
}
}

View File

@ -0,0 +1,34 @@
export default class FactoryEntry {
//Type get type => T;
//late Type nullableType;
//final Function instanceCreator;
//final Function arrayCreator = () => <T>[];
//final RepresentationType representationType;
isMapKeySubType(map) {
//return map is Map<T, dynamic>;
}
isMapValueSubType(map) {
//return map is Map<dynamic, T>;
}
isListSubType(list) {
//return list is List<T>;
}
constructor(type, representationType) {
this.type = type;
this.nullableType = this.getNullableType(type);
this.representationType = representationType;
}
getNullableType(type){
let c = class extends type {};
Object.defineProperty(c, "name", {value: "Nullable" + type.name});
Object.defineProperty(c, "nullable", {value: true});
return c;
}
}

View File

@ -53,6 +53,10 @@ export default class IResource extends IDestructible
super();
}
toString(){
return this?.instance?.template?.namespace ?? "IResource";
}
static get template()
{
return {

View File

@ -46,6 +46,11 @@ export default class IStore extends IResource {
}
modify(resource, propertyName, value, age, dateTime)
{
}
getRecord(resource, fromDate, toDate)
{

View File

@ -28,7 +28,6 @@
import IEventHandler from '../Core/IEventHandler.js';
import IPermissionsManager from '../Security/Permissions/IPermissionsManager.js';
import StructureArray from '../Data/StructureArray.js';
import AutoList from '../Data/AutoList.js';
import KeyList from '../Data/KeyList.js';
import Structure from '../Data/Structure.js';
@ -36,6 +35,11 @@ import PropertyValue from '../Data/PropertyValue.js';
import CustomResourceEvent from './CustomResourceEvent.js';
import Warehouse from './Warehouse.js';
import Ruling from '../Security/Permissions/Ruling.js';
import TypedMap from '../Data/TypedMap.js';
import TypedList from '../Data/TypedList.js';
import EventOccurredInfo from './EventOccurredInfo.js';
import PropertyModificationInfo from './PropertyModificationInfo.js';
import PropertyValueArray from '../Data/PropertyValueArray.js';
export default class Instance extends IEventHandler
{
@ -110,7 +114,7 @@ export default class Instance extends IEventHandler
serialize()
{
var props = [];
var props = new PropertyValueArray();
for (var i = 0; i < this.template.properties.length; i++)
props.push(new PropertyValue(this.resource[this.template.properties[i].name],
@ -122,7 +126,7 @@ export default class Instance extends IEventHandler
isStorable()
{
return resource instanceof Storable;
return false;
}
emitModification(pt, value)
@ -136,10 +140,17 @@ export default class Instance extends IEventHandler
if (pt.recordable)
this.store.record(this.resource, pt.name, value, this.ages[pt.index], now);
else
this.store.modify(this.resource, pt.name, value, this.ages[pt.index], now);
super._emit("ResourceModified", this.resource, pt.name, value);
//this.resource._emit("modified", pt.name, value);
this.resource._emit(":" + pt.name, value);
let pmInfo = new PropertyModificationInfo(this.resource, pt, value, this.instanceAge);
super._emit("PropertyModified", pmInfo);
this.resource._emit(`:${pt.name}`, value);
//this.resource.emitProperty(pmInfo);
//super._emit("ResourceModified", this.resource, pt.name, value);
//this.resource._emit(":" + pt.name, value);
}
modified(propertyName = null)
@ -155,9 +166,11 @@ export default class Instance extends IEventHandler
}
}
_emitResourceEvent(issuer, receivers, name, args)
_emitResourceEvent(issuer, receivers, eventTemplate, value)
{
super._emit("ResourceEventOccurred", this.resource, issuer, receivers, name, args);
super._emit("EventOccurred",
new EventOccurredInfo(this.resource, eventTemplate, value, issuer, receivers));
//super._emit("ResourceEventOccurred", this.resource, issuer, receivers, name, args);
}
getPropertyValue(name, resultObject)
@ -173,6 +186,9 @@ export default class Instance extends IEventHandler
}
get age() {
return this.instanceAge;
}
constructor(id, name, resource, store, customTemplate = null, age = 0)
{
@ -223,20 +239,20 @@ export default class Instance extends IEventHandler
}
// connect events
for (var i = 0; i < this.template.events.length; i++)
this.resource.on(this.template.events[i].name, this._makeHandler(this.template.events[i].name));
for (let i = 0; i < this.template.events.length; i++)
this.resource.on(this.template.events[i].name, this._makeHandler(this.template.events[i]));
}
_makeHandler(name)
_makeHandler(eventTemplate)
{
var self = this;
return function(args)
return function(argument)
{
if (args instanceof CustomResourceEvent)
self._emitResourceEvent(args.issuer, args.receivers, name, args.args);
if (argument instanceof CustomResourceEvent)
self._emitResourceEvent(argument.issuer, argument.receivers, eventTemplate, argument.value);
else
self._emitResourceEvent(null, null, name, args);
self._emitResourceEvent(null, null, eventTemplate, argument);
};
}
@ -294,14 +310,14 @@ export default class Instance extends IEventHandler
else if (attr == "managers")
{
var mngrs = new StructureArray();
var mngrs = new (TypedList.of(TypedMap.of(String, Object)));
for(var j = 0; j < this.managers.length; j++)
{
var manager = this.managers.item(j);
var sm = new Structure();
sm["type"] = manager.constructor.name;
sm["settings"] = manager.settings;
var sm = new (TypedMap.of(String, Object));
sm.set("type", manager.constructor.name);
sm.set("settings", manager.settings);
mngrs.push(sm);
}

View File

@ -0,0 +1,17 @@
import IResource from './IResource.js';
import PropertyTemplate from './Template/PropertyTemplate.js';
export default class PropertyModificationInfo {
get name(){
return this.propertyTemplate.name;
}
PropertyModificationInfo(
resource, propertyTemplate, value, age) {
this.resource = resource;
this.propertyTemplate = propertyTemplate;
this.value = value;
this.age = age;
}
}

View File

@ -1,32 +1,38 @@
import DC from "../../Data/DataConverter.js";
import BinaryList from "../../Data/BinaryList.js";
import TemplateDataType from "./TemplateDataType.js";
export default class ArgumentTemplate
{
static parse(data, offset)
{
import {DC, BL} from '../../Data/DC.js';
import RepresentationType from '../../Data/RepresentationType.js';
import ParseResult from "../../Data/ParseResult.js";
export default class ArgumentTemplate {
static parse(data, offset, index) {
var optional = (data[offset++] & 0x1) == 0x1;
var cs = data[offset++];
var name = data.getString(offset, cs);
offset += cs;
var {size, value} = TemplateDataType.parse(data, offset);
var tdr = RepresentationType.parse(data, offset);
return {size: cs + 1 + size, value: new ArgumentTemplate(name, value)};
return new ParseResult(
cs + 2 + tdr.size, new ArgumentTemplate(name, tdr.type, optional, index));
}
constructor(name, type){
constructor(name, type, optional, index){
this.name = name;
this.type = type;
this.optional = optional;
this.index = index;
}
compose()
{
compose() {
var name = DC.stringToBytes(this.name);
return new BinaryList()
return (BL()
.addUint8(this.optional ? 1 : 0)
.addUint8(name.length)
.addUint8Array(name)
.addUint8Array(this.type.compose())
.toArray();
.addDC(name)
.addDC(this.type.compose()))
.toDC();
}
}

View File

@ -0,0 +1,46 @@
import {DC, BL} from '../../Data/DC.js';
import MemberTemplate from './MemberTemplate.js';
import Codec from '../../Data/Codec.js';
export default class ConstantTemplate extends MemberTemplate {
//final dynamic value;
//final String? expansion;
//final RepresentationType valueType;
constructor(template, index, name,
inherited, valueType, value, expansion){
super(template, index, name, inherited) ;
this.valueType = valueType;
this.value = value;
this.expansion = expansion;
}
compose() {
var name = super.compose();
var hdr = this.inherited ? 0x80 : 0;
if (this.expansion != null) {
var exp = DC.stringToBytes(this.expansion);
hdr |= 0x70;
return (BL()
.addUint8(hdr)
.addUint8(name.length)
.addDC(name)
.addDC(this.valueType.compose())
.addDC(Codec.compose(this.value, null))
.addInt32(exp.length)
.addDC(exp))
.toDC();
} else {
hdr |= 0x60;
return (BL()
.addUint8(hdr)
.addUint8(name.length)
.addDC(name)
.addDC(this.valueType.compose())
.addDC(Codec.compose(this.value, null)))
.toDC();
}
}
}

View File

@ -26,39 +26,48 @@
"use strict";
import {DC, BL} from '../../Data/DataConverter.js';
import {DC, BL} from '../../Data/DC.js';
import MemberTemplate from './MemberTemplate.js';
import MemberType from './MemberType.js';
export default class EventTemplate extends MemberTemplate
{
constructor()
{
super();
this.type = MemberType.Event;
}
export default class EventTemplate extends MemberTemplate {
compose()
{
var rt = BL();
compose() {
let name = super.compose();
let hdr = this.inherited ? 0x80 : 0;
if (this.listenable) hdr |= 0x8;
var name = super.compose();
if (this.expansion != null) {
var exp = DC.stringToBytes(this.expansion);
return rt.addUint8(this.listenable ? 0x58 : 0x50)
let exp = DC.stringToBytes(this.expansion);
hdr |= 0x50;
return (BL()
.addUint8(hdr)
.addUint8(name.length)
.addUint8Array(name)
.addUint8Array(this.argumentType.compose())
.addUint32(exp.length)
.addUint8Array(exp)
.toArray();
}
else
return rt.addUint8(this.listenable ? 0x48 : 0x40)
.addDC(name)
.addDC(this.argumentType.compose())
.addInt32(exp.length)
.addDC(exp))
.toDC();
} else {
hdr |= 0x40;
return (BL()
.addUint8(hdr)
.addUint8(name.length)
.addUint8Array(name)
.addUint8Array(this.argumentType.compose())
.toArray();
.addDC(name)
.addDC(this.argumentType.compose()))
.toDC();
}
}
constructor(template, index, name, inherited, argumentType,
expansion = null, listenable = false)
{
super(template, index, name, inherited) ;
this.argumentType = argumentType;
this.expansion = expansion;
this.listenable = listenable;
}
}

View File

@ -1,5 +1,5 @@
/*
* Copyright (c) 2017 Ahmed Kh. Zamil
* Copyright (c) 2017-2022 Ahmed Kh. Zamil
*
* Permission is hereby granted, free of charge, to any person obtaining a copy
* of this software and associated documentation files (the "Software"), to deal
@ -26,38 +26,38 @@
"use strict";
import {DC, BL} from '../../Data/DataConverter.js';
import {DC, BL} from '../../Data/DC.js';
import MemberTemplate from './MemberTemplate.js';
import MemberType from './MemberType.js';
export default class FunctionTemplate extends MemberTemplate {
compose() {
var name = super.compose();
var bl = BL()
var bl = new BL()
.addUint8(name.length)
.addUint8Array(name)
.addUint8Array(this.returnType.compose())
.addUint8(this.arguments.length);
.addDC(name)
.addDC(this.returnType.compose())
.addUint8(this.args.length);
for (var i = 0; i < this.arguments.length; i++)
bl.addUint8Array(this.arguments[i].compose());
for (var i = 0; i < this.args.length; i++) bl.addDC(this.args[i].compose());
if (this.expansion != null)
{
if (this.expansion != null) {
var exp = DC.stringToBytes(this.expansion);
bl.addInt32(exp.length)
.addUint8Array(exp);
bl.insertUint8(0, 0x10);
}
else
bl.addUint8(0x0, 0);
bl
.addInt32(exp.length)
.addDC(exp);
bl.insertUint8(0, this.inherited ? 0x90 : 0x10);
} else
bl.insertUint8(0, this.inherited ? 0x80 : 0x0);
return bl.toArray();
return bl.toDC();
}
constructor() {
super();
this.type = MemberType.Function;
constructor(template, index, name, inherited, args, returnType, expansion = null){
super(template, index, name, inherited);
this.args = args;
this.returnType = returnType;
this.expansion = expansion;
}
}

View File

@ -26,9 +26,20 @@
"use strict";
import DC from '../../Data/DataConverter.js';
import DC from '../../Data/DC.js';
export default class MemberTemplate {
constructor(template, index, name, inherited) {
this.template = template;
this.index = index;
this.name = name;
this.inherited = inherited;
}
get fullname() {return this.template.className + "." + this.name;}
compose() {
return DC.stringToBytes(this.name);
}

View File

@ -1,5 +1,5 @@
/*
* Copyright (c) 2017 Ahmed Kh. Zamil
* Copyright (c) 2017-2022 Ahmed Kh. Zamil
*
* Permission is hereby granted, free of charge, to any person obtaining a copy
* of this software and associated documentation files (the "Software"), to deal
@ -24,74 +24,66 @@
* Created by Ahmed Zamil on 27/08/2017.
*/
"use strict";
import {DC, BL} from '../../Data/DataConverter.js';
import {DC, BL} from '../../Data/DC.js';
import MemberTemplate from './MemberTemplate.js';
import MemberType from './MemberType.js';
export const PropertyPermission = {
Read: 1,
Write: 2,
ReadWrite: 3
};
export default class PropertyTemplate extends MemberTemplate {
export default class PropertyTemplate extends MemberTemplate
{
constructor()
{
super();
this.type = MemberType.Property;
}
compose()
{
compose() {
var name = super.compose();
var rt = BL();
var pv = (this.permission << 1) | (this.recordable ? 1 : 0);
if (this.writeExpansion != null && this.readExpansion != null)
if (this.inherited) pv |= 0x80;
if (this.writeExpansion != null && this.readExpansion != null) {
let rexp = DC.stringToBytes(this.readExpansion);
let wexp = DC.stringToBytes(this.writeExpansion);
return (BL()
.addUint8(0x38 | pv)
.addUint8(name.length)
.addDC(name)
.addDC(this.valueType.compose())
.addInt32(wexp.length)
.addDC(wexp)
.addInt32(rexp.length)
.addDC(rexp))
.toDC();
} else if (this.writeExpansion != null) {
let wexp = DC.stringToBytes(this.writeExpansion);
return (BL()
.addUint8(0x30 | pv)
.addUint8(name.length)
.addDC(name)
.addDC(this.valueType.compose())
.addInt32(wexp.length)
.addDC(wexp))
.toDC();
} else if (this.readExpansion != null) {
let rexp = DC.stringToBytes(this.readExpansion);
return (BL()
.addUint8(0x28 | pv)
.addUint8(name.length)
.addDC(name)
.addDC(this.valueType.compose())
.addInt32(rexp.length)
.addDC(rexp))
.toDC();
} else
return (BL()
.addUint8(0x20 | pv)
.addUint8(name.length)
.addDC(name)
.addDC(this.valueType.compose()))
.toDC();
}
constructor(template, index, name,
inherited, valueType, readExpansion = null, writeExpansion = null, recordable = false)
{
var rexp = DC.stringToBytes(this.readExpansion);
var wexp = DC.stringToBytes(this.writeExpansion);
return rt.addUint8(0x38 | pv)
.addUint8(name.length)
.addUint8Array(name)
.addUint8Array(this.valueType.compose())
.addUint32(wexp.length)
.addUint8Array(wexp)
.addUint32(rexp.length)
.addUint8Array(rexp)
.toArray();
}
else if (this.writeExpansion != null)
{
var wexp = DC.stringToBytes(this.writeExpansion);
return rt.addUint8(0x30 | pv)
.addUint8(name.length)
.addUint8Array(name)
.addUint8Array(this.valueType.compose())
.addUint32(wexp.length)
.addUint8Array(wexp)
.toArray();
}
else if (this.readExpansion != null)
{
var rexp = DC.stringToBytes(this.readExpansion);
return rt.addUint8(0x28 | pv)
.addUint8(name.length)
.addUint8Array(name)
.addUint8Array(this.valueType.compose())
.addUint32(rexp.length)
.addUint8Array(rexp)
.toArray();
}
else
return rt.addUint8(0x20 | pv)
.addUint8(name.length)
.addUint8Array(name)
.addUint8Array(this.valueType.compose())
.toArray();
super(template, index, name, inherited);
this.valueType = valueType;
this.readExpansion = readExpansion;
this.writeExpansion = writeExpansion;
this.recordable = recordable;
}
}

View File

@ -22,7 +22,7 @@
"use strict";
import {DC, BL} from '../../Data/DataConverter.js';
import {DC, BL} from '../../Data/DC.js';
import DataType from "../../Data/DataType.js";
import Structure from '../../Data/Structure.js';
import IResource from '../IResource.js';

View File

@ -4,4 +4,5 @@ export default
Resource: 1,
Record: 2,
Wrapper: 3,
Enum: 4
}

View File

@ -26,15 +26,20 @@ import FunctionTemplate from './FunctionTemplate.js';
import PropertyTemplate from './PropertyTemplate.js';
import EventTemplate from './EventTemplate.js';
import SHA256 from '../../Security/Integrity/SHA256.js';
import {DC, BL} from '../../Data/DataConverter.js';
import {DC, BL} from '../../Data/DC.js';
import ArgumentTemplate from './ArgumentTemplate.js';
import TemplateDataType from "./TemplateDataType.js";
import IResource from '../IResource.js';
import IRecord from '../../Data/IRecord.js';
import TemplateType from './TemplateType.js'
import Warehouse from '../Warehouse.js';
import DistributedConnection from '../../Net/IIP/DistributedConnection.js';
import ConstantTemplate from './ConstantTemplate.js';
import IEnum from '../../Data/IEnum.js';
import DistributedResource from '../../Net/IIP/DistributedResource.js';
import RepresentationType from '../../Data/RepresentationType.js';
import Codec from '../../Data/Codec.js';
export default class TypeTemplate {
getEventTemplateByName(eventName) {
@ -79,6 +84,20 @@ export default class TypeTemplate {
return null;
}
getConstantTemplateByName(constantName) {
for (var i = 0; i < this.constants.length; i++)
if (this.constants[i].name == constantName)
return this.constants[i];
return null;
}
getConstantTemplateByIndex(index) {
for (var i = 0; i < this.constants.length; i++)
if (this.constants[i].index == index)
return this.constants[i];
return null;
}
/*
@ -217,16 +236,22 @@ export default class TypeTemplate {
this.events = [];
this.functions = [];
this.members = [];
this.constants = [];
if (type === undefined)
return;
if (type.prototype instanceof DistributedResource)
this.templateType = TemplateType.Wrapper;
if (type.prototype instanceof IRecord)
this.templateType = TemplateType.Record;
else if (type.prototype instanceof IResource)
this.templateType = TemplateType.Resource;
else if (type.prototype instanceof IEnum)
this.templateType = TemplateType.Enum;
else
throw new Error("Type is neither a resource nor a record.");
throw new Error("Type must implement IResource, IRecord, IEnum or a subtype of DistributedResource.");
this.definedType = type;
@ -244,35 +269,38 @@ export default class TypeTemplate {
//byte currentIndex = 0;
if (template.properties != null)
for (var i = 0; i < template.properties.length; i++) {
for (let i = 0; i < template.properties.length; i++) {
//[name, type, {read: comment, write: comment, recordable: }]
var pi = template.properties[i];
var pt = new PropertyTemplate();
pt.name = pi[0];
pt.index = i;
pt.valueType = TemplateDataType.fromType(pi[1]);
pt.readExpansion = pi[2]?.read;
pt.writeExpansion = pi[2]?.write;
pt.recordable = pi[2]?.recordable;
let pi = template.properties[i];
let pt = new PropertyTemplate(this, i, pi[0], false,
RepresentationType.fromType(pi[1]) ?? RepresentationType.Void,
pi[2]?.read, pi[2]?.write, pi[2]?.recordable);
pt.propertyInfo = pi;
this.properties.push(pt);
}
if (template.constants != null)
for (let i = 0; i < template.constants.length; i++) {
let ci = template.constants[i];
let ct = new ConstantTemplate(this, i, ci[0], false,
RepresentationType.fromType(ci[1]) ?? RepresentationType.Void,
ci.value, ci.help);
ct.propertyInfo = ci;
this.constants.push(ct);
}
if (this.templateType == TemplateType.Resource)
{
if (template.events != null)
{
for (let i = 0; i < template.events.length; i++) {
// [name, type, {listenable: true/false, help: ""}]
var ei = template.events[i];
var et = new EventTemplate();
et.name = ei[0];
et.index = i;
et.argumentType = TemplateDataType.fromType(ei[1]),
et.expansion = ei[2]?.help;
et.listenable = ei[2]?.listenable;
var et = new EventTemplate(this, i, ei[0], false,
RepresentationType.fromType(ei[1]) ?? RepresentationType.Void,
ei[2]?.help, ei[2]?.listenable)
et.eventInfo = ei;
this.events.push(et);
}
@ -284,16 +312,15 @@ export default class TypeTemplate {
var fi = template.functions[i];
// [name, {param1: type, param2: int}, returnType, "Description"]
var ft = new FunctionTemplate();
ft.name = fi[0];
ft.index = i;
ft.returnType = TemplateDataType.fromType(fi[2]);
ft.expansion = fi[3];
ft.arguments = [];
let args = [];
for(let ai = 0; ai < fi[1].length; ai++)
args.push(new ArgumentTemplate(fi[1][ai][0], RepresentationType.fromType(fi[1][ai][1])
?? RepresentationType.Dynamic, fi[1][ai][2]?.optional, ai));
for(var arg in fi[1])
ft.arguments.push(new ArgumentTemplate(arg, TemplateDataType.fromType(fi[1][arg])))
// [name, {param1: type, param2: int}, returnType, "Description"]
var ft = new FunctionTemplate(this, i, fi[0], false, args,
RepresentationType.fromType(fi[2]) ?? RepresentationType.Void,
fi[3]);
ft.methodInfo = fi;
@ -312,6 +339,9 @@ export default class TypeTemplate {
// append properties
for (let i = 0; i < this.properties.length; i++)
this.members.push(this.properties[i]);
// append constants
for (let i = 0; i < this.constants.length; i++)
this.members.push(this.constants[i]);
// bake it binarily
var b = BL();
@ -369,41 +399,52 @@ export default class TypeTemplate {
var od = new TypeTemplate();
od.content = data.clip(offset, contentLength);
od.templateType = data.getUint8(offset++);
let hasParent = (data.getUint8(offset) & 0x80) > 0;
od.templateType = data.getUint8(offset++) & 0xF;
od.classId = data.getGuid(offset);
offset += 16;
od.className = data.getString(offset + 1, data.getUint8(offset));
offset += data.getUint8(offset) + 1;
if (hasParent) {
od.parentId = data.getGuid(offset);
offset += 16;
}
od.version = data.getInt32(offset);
offset += 4;
var methodsCount = data.getUint16(offset);
let methodsCount = data.getUint16(offset);
offset += 2;
var functionIndex = 0;
var propertyIndex = 0;
var eventIndex = 0;
let functionIndex = 0;
let propertyIndex = 0;
let eventIndex = 0;
let constantIndex = 0;
for (var i = 0; i < methodsCount; i++) {
var type = data.getUint8(offset) >> 5;
for (let i = 0; i < methodsCount; i++) {
let inherited = (data.getUint8(offset) & 0x80) > 0;
let type = (data.getUint8(offset) >> 5) & 0x3;
if (type == 0) // function
{
let ft = new FunctionTemplate();
ft.index = functionIndex++;
let expansion = null;
let hasExpansion = ((data.getUint8(offset++) & 0x10) == 0x10);
let len = data.getUint8(offset++);
ft.name = data.getString(offset, len);
let name = data.getString(offset, len);
offset += len;
// return type
let {size, value: returnType} = TemplateDataType.parse(data, offset);
offset += size;
let dt = RepresentationType.parse(data, offset);
ft.returnType = returnType;
offset += dt.size;
//ft.returnType = returnType;
// arguments count
var argsCount = data.getUint8(offset++);
@ -411,47 +452,45 @@ export default class TypeTemplate {
for (var a = 0; a < argsCount; a++)
{
let {size: argSize, value: argType} = ArgumentTemplate.parse(data, offset);
let {size: argSize, value: argType} = ArgumentTemplate.parse(data, offset, a);
args.push(argType);
offset += argSize;
}
ft.arguments = args;
if (hasExpansion) // expansion ?
{
var cs = data.getUint32(offset);
offset += 4;
ft.expansion = data.getString(offset, cs);
expansion = data.getString(offset, cs);
offset += cs;
}
let ft = new FunctionTemplate(od, functionIndex++, name, inherited,
args, dt.type, expansion);
od.functions.push(ft);
}
else if (type == 1) // property
{
let pt = new PropertyTemplate();
pt.index = propertyIndex++;
let hasReadExpansion = ((data.getUint8(offset) & 0x8) == 0x8);
let hasWriteExpansion = ((data.getUint8(offset) & 0x10) == 0x10);
pt.recordable = ((data.getUint8(offset) & 1) == 1);
pt.permission = ((data.getUint8(offset++) >> 1) & 0x3);
let readExpansion, writeExpansion;
let recordable = ((data.getUint8(offset) & 1) == 1);
let permission = ((data.getUint8(offset++) >> 1) & 0x3);
let len = data.getUint8(offset++);
pt.name = data.getString(offset, len);
let name = data.getString(offset, len);
offset += len;
let {size, value: valueType} = TemplateDataType.parse(data, offset);
var dt = RepresentationType.parse(data, offset);
offset += size;
pt.valueType = valueType;
offset += dt.size;
if (hasReadExpansion) // expansion ?
{
let cs = data.getUint32(offset);
offset += 4;
pt.readExpansion = data.getString(offset, cs);
readExpansion = data.getString(offset, cs);
offset += cs;
}
@ -459,39 +498,70 @@ export default class TypeTemplate {
{
let cs = data.getUint32(offset);
offset += 4;
pt.writeExpansion = data.getString(offset, cs);
writeExpansion = data.getString(offset, cs);
offset += cs;
}
let pt = new PropertyTemplate(od, propertyIndex++, name, inherited, dt.type, readExpansion, writeExpansion, recordable);
od.properties.push(pt);
}
else if (type == 2) // Event
{
let et = new EventTemplate();
et.index = eventIndex++;
let hasExpansion = ((data.getUint8(offset) & 0x10) == 0x10);
et.listenable = ((data.getUint8(offset++) & 0x8) == 0x8);
let listenable = ((data.getUint8(offset++) & 0x8) == 0x8);
let len = data.getUint8(offset++);
et.name = data.getString(offset, len);
let name = data.getString(offset, len);
let expansion;
offset += len;
let {size, value: argType} = TemplateDataType.parse(data, offset);
let dt = RepresentationType.parse(data, offset);
offset += dt.size;
offset += size;
et.argumentType = argType;
if (hasExpansion) // expansion ?
{
let cs = data.getUint32(offset);
offset += 4;
et.expansion = data.getString(offset, cs);
expansion = data.getString(offset, cs);
offset += cs;
}
let et = new EventTemplate(od, eventIndex++, name, inherited, dt.type, expansion, listenable);
od.events.push(et);
}
else if (type == 3) // constant
{
let expansion = null;
let hasExpansion = ((data[offset++] & 0x10) == 0x10);
let name = data.getString(offset + 1, data[offset]);
offset += data[offset] + 1;
let dt = RepresentationType.parse(data, offset);
offset += dt.size;
let parsed = Codec.parse(data, offset, null);
offset += parsed.size;
if (hasExpansion) // expansion ?
{
let cs = data.getUint32(offset);
offset += 4;
expansion = data.getString(offset, cs);
offset += cs;
}
let ct = new ConstantTemplate(this, constantIndex++, name, inherited,
dt.type, parsed.reply.result, expansion);
od.constants.push(ct);
}
}
// append signals
@ -503,6 +573,9 @@ export default class TypeTemplate {
// append properties
for (let i = 0; i < od.properties.length; i++)
od.members.push(od.properties[i]);
// append constants
for (let i = 0; i < od.constants.length; i++)
od.members.push(od.constants[i]);
return od;

View File

@ -42,7 +42,12 @@ import AsyncBag from '../Core/AsyncBag.js';
import IRecord from '../Data/IRecord.js';
import TemplateType from './Template/TemplateType.js';
import DistributedResource from '../Net/IIP/DistributedResource.js';
import TypedList from '../Data/TypedList.js';
import { Int8, Int16, Int32, Int64, UInt8, UInt16, UInt32, UInt64, Float32, Float64 } from '../Data/ExtendedTypes.js';
import Record from '../Data/Record.js';
import TypedMap from '../Data/TypedMap.js';
import {RepresentationType, RepresentationTypeIdentifier} from '../Data/RepresentationType.js';
import FactoryEntry from './FactoryEntry.js'; './FactoryEntry.js';
export class WH extends IEventHandler
{
constructor()
@ -58,8 +63,12 @@ export class WH extends IEventHandler
this.templates.add(TemplateType.Resource, new KeyList());
this.templates.add(TemplateType.Record, new KeyList());
this.templates.add(TemplateType.Wrapper, new KeyList());
this.templates.add(TemplateType.Enum, new KeyList());
this.protocols = new KeyList();
this.typesFactory = this._getBuiltInTypes();
this._register("connected");
this._register("disconnected");
///this._urlRegex = /^(?:([\S]*):\/\/([^\/]*)\/?)/;
@ -529,6 +538,91 @@ export class WH extends IEventHandler
return rt;
}
/**
* @param {Function} instanceCreator - creator
* @param {RepresentationType} representationType - type
*/
_getTypeEntries(type, representationType) {
let listType = TypedList.of(type);
var entry = new FactoryEntry(type, representationType);
let nullableEntry = new FactoryEntry(entry.nullableType, representationType.toNullable());
let listEntry = new FactoryEntry(listType,
new RepresentationType(RepresentationTypeIdentifier.TypedList, false,
null, [representationType]));
let nullableList = new FactoryEntry(listEntry.nullableType,
new RepresentationType(RepresentationTypeIdentifier.TypedList, true, null,
[representationType]));
let nullableItemListType = TypedList.of(entry.nullableType);
let listNullableItemEntry = new FactoryEntry(nullableItemListType,
new RepresentationType(RepresentationTypeIdentifier.TypedList, false,
null, [representationType.toNullable()]));
let nullableListNullableItemEntry = new FactoryEntry(nullableItemListType,
new RepresentationType(RepresentationTypeIdentifier.TypedList, true, null,
[representationType.toNullable()]));
return [
entry, nullableEntry, listEntry, nullableList, listNullableItemEntry, nullableListNullableItemEntry
];
}
/**
* @param {Function} instanceCreator - creator
* @param {RepresentationType} representationType - type
*/
defineType(type, representationType) {
var entries = this._getTypeEntries(type, representationType);
for(var e of entries)
this.typesFactory[e.type] = e; //.push(e);
}
_getBuiltInTypes() {
let entries = [
...this._getTypeEntries(Int8, new RepresentationType(RepresentationTypeIdentifier.Int8, false)),
...this._getTypeEntries(UInt8, new RepresentationType(RepresentationTypeIdentifier.UInt8, false)),
...this._getTypeEntries(Int16, new RepresentationType(RepresentationTypeIdentifier.Int16, false)),
...this._getTypeEntries(UInt16, new RepresentationType(RepresentationTypeIdentifier.UInt16, false)),
...this._getTypeEntries(Int32, new RepresentationType(RepresentationTypeIdentifier.Int32, false)),
...this._getTypeEntries(UInt32, new RepresentationType(RepresentationTypeIdentifier.UInt32, false)),
...this._getTypeEntries(Int64, new RepresentationType(RepresentationTypeIdentifier.Int64, false)),
...this._getTypeEntries(UInt64, new RepresentationType(RepresentationTypeIdentifier.UInt64, false)),
...this._getTypeEntries(Float32, new RepresentationType(RepresentationTypeIdentifier.Float32, false)),
...this._getTypeEntries(Float64, new RepresentationType(RepresentationTypeIdentifier.Float64, false)),
...this._getTypeEntries(String, new RepresentationType(RepresentationTypeIdentifier.Int8, String)),
...this._getTypeEntries(Date, new RepresentationType(RepresentationTypeIdentifier.Int8, Date)),
...this._getTypeEntries(Record, new RepresentationType(RepresentationTypeIdentifier.Record, false)),
...this._getTypeEntries(IResource, new RepresentationType(RepresentationTypeIdentifier.Resource, false)),
...this._getTypeEntries(Array, new RepresentationType(RepresentationTypeIdentifier.List, false)),
...this._getTypeEntries(Map, new RepresentationType(RepresentationTypeIdentifier.Map, false)),
//...this._getTypeEntries(IResource, new RepresentationType(RepresentationTypeIdentifier.Resource, false)),
//...this._getTypeEntries(TypedMap, new RepresentationType(RepresentationTypeIdentifier.Resource, false)),
...this._getTypeEntries(TypedMap.of(String, Object), new RepresentationType(RepresentationTypeIdentifier.TypedMap, false, null, [
new RepresentationType(RepresentationTypeIdentifier.String, false),
RepresentationType.Dynamic])),
...this._getTypeEntries(TypedMap.of(UInt8, Object), new RepresentationType(RepresentationTypeIdentifier.TypedMap, false, null, [
new RepresentationType(RepresentationTypeIdentifier.UInt8, false),
RepresentationType.Dynamic])),
...this._getTypeEntries(TypedMap.of(Int32, Object), new RepresentationType(RepresentationTypeIdentifier.TypedMap, false, null, [
new RepresentationType(RepresentationTypeIdentifier.Int32, false),
RepresentationType.Dynamic])),
];
let rt = {};
for(let entry of entries)
rt[entry.type] = entry;
return rt;
}
}
let Warehouse = new WH();

View File

@ -26,7 +26,7 @@
* Ref: https://en.wikipedia.org/wiki/SHA-2
*/
import {DC, BL} from '../../Data/DataConverter.js';
import { DC, BL, Endian } from '../../Data/DC.js';
export default class SHA256
{
@ -82,7 +82,7 @@ export default class SHA256
var paddingBytes = new Uint8Array(paddingLength);
paddingBytes[0] = 0x80;
var data = new DC(BL().addUint8Array(msg).addUint8Array(paddingBytes).addUint64(L).toArray());
var data = BL().addUint8Array(msg).addUint8Array(paddingBytes).addUint64(L, Endian.Big).toDC();
@ -99,8 +99,8 @@ export default class SHA256
// copy chunk into first 16 words w[0..15] of the message schedule array
var w = new Uint32Array(64);
for(var i = 0; i < 16; i++)
w[i] = data.getInt32(chunk + (i * 4));
for(let i = 0; i < 16; i++)
w[i] = data.getUint32(chunk + (i * 4), Endian.Big);
//for(var i = 16; i < 64; i++)
// w[i] = 0;
@ -111,7 +111,7 @@ export default class SHA256
// s1 := (w[i-2] rightrotate 17) xor (w[i-2] rightrotate 19) xor (w[i-2] rightshift 10)
// w[i] := w[i-16] + s0 + w[i-7] + s1
for (var i = 16; i < 64; i++)
for (let i = 16; i < 64; i++)
{
var s0 = SHA256.RROT(w[i-15], 7) ^ SHA256.RROT(w[i-15], 18) ^ (w[i-15] >>> 3);
var s1 = SHA256.RROT(w[i-2], 17) ^ SHA256.RROT(w[i-2], 19) ^ (w[i-2] >>> 10);
@ -130,7 +130,7 @@ export default class SHA256
// Compression function main loop:
for (var i = 0; i < 64; i++)
for (let i = 0; i < 64; i++)
{
var S1 = SHA256.RROT(e, 6) ^ SHA256.RROT(e, 11) ^ SHA256.RROT(e, 25);
var ch = (e & f) ^ ((~e) & g);
@ -170,8 +170,8 @@ export default class SHA256
//digest := hash := h0 append h1 append h2 append h3 append h4 append h5 append h6 append h7
var results = BL();
for(var i = 0; i < 8; i++)
results.addUint32(hash[i]);
for(let i = 0; i < 8; i++)
results.addUint32(hash[i], Endian.Big);
return results.toDC();

View File

@ -25,7 +25,7 @@ import AutoList from './Data/AutoList.js';
import AutoMap from './Data/AutoMap.js';
import BinaryList from './Data/BinaryList.js';
import Codec from './Data/Codec.js';
import DataConverter from './Data/DataConverter.js';
import DC from './Data/DC.js';
import DataType from './Data/DataType.js';
import Guid from './Data/Guid.js';
import IRecord from './Data/IRecord.js';
@ -86,7 +86,7 @@ import Ruling from './Security/Permissions/Ruling.js';
let namespace = {
Core: { AsyncReply, AsyncException, AsyncQueue, ErrorType, ExceptionCode, IDestructible, IEventHandler, ProgressType},
Data: {AutoList, AutoMap, BinaryList, Codec, DataConverter, DataType, Guid, IRecord, KeyList, NotModified,
Data: {AutoList, AutoMap, BinaryList, Codec, DC, DataType, Guid, IRecord, KeyList, NotModified,
PropertyValue, Record, RecordComparisonResult, ResourceArray, ResourceArrayType, ResourceComparisonResult, Structure,
StructureArray, StructureComparisonResult },
Net: {INetworkReceiver, NetworkBuffer, NetworkConnections, NetworkServer, NetworkSession, SendList,