@gudhub/core 1.1.15 → 1.1.18

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
@@ -105,6 +105,16 @@ export class AppProcessor {
105
105
  }
106
106
 
107
107
  saveAppInStorage(app) {
108
+
109
+ app.items_object = {};
110
+
111
+ for(let item = 0; item < app.items_list.length; item++) {
112
+ app.items_object[app.items_list[item].item_id] = {};
113
+ for(let field = 0; field < app.items_list[item].fields.length; field++) {
114
+ app.items_object[app.items_list[item].item_id][app.items_list[item].fields[field].field_id] = app.items_list[item].fields[field];
115
+ }
116
+ }
117
+
108
118
  const storageApp = this.storage.getApp(app.app_id);
109
119
  if (storageApp) {
110
120
  app.from_apps_list = storageApp.from_apps_list;
@@ -122,6 +132,7 @@ export class AppProcessor {
122
132
  app.items_list = storageApp.items_list;
123
133
  app.file_list = storageApp.file_list;
124
134
  app.from_apps_list = storageApp.from_apps_list;
135
+ app.items_object =storageApp.items_object;
125
136
  this.storage.updateApp(app);
126
137
  //-- Sending updates for Views Updates
127
138
  this.pipeService.emit(
@@ -167,6 +178,15 @@ export class AppProcessor {
167
178
  try {
168
179
  const app = await this.getAppApi(app_id);
169
180
  if (app) {
181
+ app.items_object = {};
182
+
183
+ for(let item = 0; item < app.items_list.length; item++) {
184
+ app.items_object[app.items_list[item].item_id] = {};
185
+ for(let field = 0; field < app.items_list[item].fields.length; field++) {
186
+ app.items_object[app.items_list[item].item_id][app.items_list[item].fields[field].field_id] = app.items_list[item].fields[field];
187
+ }
188
+ }
189
+
170
190
  this.storage.updateApp(app);
171
191
  }
172
192
  } catch (err) {
@@ -254,7 +274,9 @@ export class AppProcessor {
254
274
  }
255
275
  }
256
276
 
257
- return trash ? app : {...app, items_list: app.items_list.filter(item => !item.trash)};
277
+ // This code for trash must be changed
278
+ // return trash ? app : {...app, items_list: app.items_list.filter(item => !item.trash)};
279
+ return app;
258
280
  }
259
281
 
260
282
  async updateApp(app) {
@@ -282,6 +304,7 @@ export class AppProcessor {
282
304
 
283
305
  async createNewApp(app) {
284
306
  const newApp = await this.createNewAppApi(app);
307
+ newApp.items_object = {};
285
308
  this.addNewAppToStorage(newApp);
286
309
  return newApp;
287
310
  }
@@ -4,14 +4,16 @@ export class Auth {
4
4
  this.storage = storage;
5
5
  }
6
6
 
7
- login({ username, password } = {}) {
8
- return this.req.simplePost({
7
+ async login({ username, password } = {}) {
8
+ let user = await this.req.simplePost({
9
9
  url: "/auth/login",
10
10
  form: {
11
11
  username,
12
12
  password,
13
13
  },
14
14
  });
15
+ this.storage.updateUser(user);
16
+ return user;
15
17
  }
16
18
 
17
19
  logout(token) {
@@ -77,11 +77,13 @@ export class FieldProcessor {
77
77
  item.fields.forEach((field) => {
78
78
  if (field.field_id == field_id) {
79
79
  field.field_value = field_value;
80
+ app.items_object[item.item_id][field.field_id] = field;
80
81
  }
81
82
  });
82
83
  }
83
84
  });
84
85
  this.storage.updateApp(app);
86
+ return field_value;
85
87
  }
86
88
 
87
89
  async getField(app_id, field_id) {
@@ -116,16 +118,10 @@ export class FieldProcessor {
116
118
  let fieldValue = null;
117
119
  const app = await this.appProcessor.getApp(app_id);
118
120
 
119
- if (app) {
120
- const fundedItem = app.items_list.find((item) => item.item_id == item_id);
121
- if (fundedItem) {
122
- const fundedField = fundedItem.fields.find(
123
- (field) => field.field_id == field_id
124
- );
125
- if (fundedField) {
126
- fieldValue = fundedField.field_value;
127
- }
128
- }
121
+ try {
122
+ fieldValue = app.items_object[item_id][field_id].field_value;
123
+ } catch(err) {
124
+
129
125
  }
130
126
 
131
127
  return fieldValue;
@@ -136,7 +132,7 @@ export class FieldProcessor {
136
132
  return;
137
133
  }
138
134
  await this.setFieldValueApi(app_id, item_id, field_id, field_value);
139
- this.updateFieldValue(app_id, item_id, field_id, field_value);
135
+ return this.updateFieldValue(app_id, item_id, field_id, field_value);
140
136
  }
141
137
 
142
138
  fieldListeners() {
@@ -10,7 +10,36 @@ describe("FIELD PROCESSOR", async function() {
10
10
  var fieldModel = await gudhub.getField(16259, 254055);
11
11
  fieldModel.data_type.should.equal('text');
12
12
  (typeof fieldModel).should.equal('object');
13
+ });
14
+
15
+ it('GET FIELD VALUE / should return a field value', async () => {
16
+ let value = await gudhub.getFieldValue(16259, 1064673, 254055);
17
+ value.should.equal('Hall up');
18
+ });
19
+
20
+ it('UPDATE FIELD AND GET NEW VALUE / should return new field value', async () => {
21
+ await gudhub.setFieldValue(16259, 1064673, 254055, 'Updated value');
22
+ let value = await gudhub.getFieldValue(16259, 1064673, 254055);
23
+ value.should.equal('Updated value');
13
24
  })
14
25
 
26
+ it('CREATE ITEM AND SET IT VALUE / should return new value of new item', async () => {
27
+ let items = await gudhub.addNewItems(16259, newItems);
28
+ let item_id = items[0].item_id;
29
+
30
+ await gudhub.setFieldValue(16259, item_id, 254056, 'Big Fish Tank');
31
+
32
+ let value = await gudhub.getFieldValue(16259, item_id, 254056);
33
+
34
+ value.should.equal('Big Fish Tank');
35
+ });
36
+
15
37
 
16
- });
38
+ });
39
+
40
+ const newItems = [
41
+ {
42
+ item_id: 0,
43
+ fields: []
44
+ },
45
+ ]
@@ -82,27 +82,47 @@ export default async function createAngularModuleInstance(gudhub, module_id, mod
82
82
 
83
83
  if (IS_WEB) {
84
84
 
85
- // Download module with $ocLazyLoad if module not in injector already.
85
+ if(window.angular) {
86
86
 
87
- if (!angularInjector.has(module_id)) {
88
- await angularInjector.get('$ocLazyLoad').load(module_url);
89
- }
87
+ // Download module with $ocLazyLoad if module not in injector already.
90
88
 
91
- angularModule = await angularInjector.get(module_id);
89
+ if (!angularInjector.has(module_id)) {
90
+ await angularInjector.get('$ocLazyLoad').load(module_url);
91
+ }
92
92
 
93
- // Then, dynamically import modules from url.
93
+ angularModule = await angularInjector.get(module_id);
94
94
 
95
- let module = await axios.get(module_url);
96
- module = module.data;
95
+ // Then, dynamically import modules from url.
97
96
 
98
- try {
99
- eval(module);
100
- } catch (error) {
101
- console.error(`ERROR WHILE EVAL() IN GHCONSTRUCTOR. MODULE ID: ${module_id}`);
102
- console.log(error);
103
- }
97
+ let module = await axios.get(module_url);
98
+ module = module.data;
104
99
 
105
- importedClass = factoryReturns[module_id];
100
+ try {
101
+ eval(module);
102
+ } catch (error) {
103
+ console.error(`ERROR WHILE EVAL() IN GHCONSTRUCTOR. MODULE ID: ${module_id}`);
104
+ console.log(error);
105
+ }
106
+
107
+ importedClass = factoryReturns[module_id];
108
+
109
+ } else {
110
+
111
+ let module = await axios.get(module_url);
112
+ module = module.data;
113
+
114
+ try {
115
+ eval(module);
116
+ } catch (err) {
117
+ console.log(`Error while importing module: ${module_id}`);
118
+ console.log(err);
119
+ }
120
+
121
+ // Modules always exports classes as default, so we create new class instance.
122
+
123
+ importedClass = factoryReturns[module_id];
124
+
125
+ }
106
126
 
107
127
  } else {
108
128
 
@@ -50,11 +50,16 @@ export class ItemProcessor {
50
50
  }
51
51
  }
52
52
 
53
- addItemsToStorage(app_id, items) {
54
- const app = this.storage.getApp(app_id);
53
+ async addItemsToStorage(app_id, items) {
54
+ // !!!!! Need to fix this
55
+ const app = await this.appProcessor.getApp(app_id);
55
56
  if (app) {
56
57
  items.forEach((item) => {
57
58
  app.items_list.push(item);
59
+ app.items_object[item.item_id] = {};
60
+ for(let field = 0; field < item.fields.length; field++) {
61
+ app.items_object[item.item_id][item.fields[field].field_id] = item.fields[field];
62
+ }
58
63
  this.pipeService.emit("gh_item_update", { app_id }, [item]);
59
64
  });
60
65
  this.pipeService.emit("gh_items_update", { app_id }, app.items_list);
@@ -63,10 +68,10 @@ export class ItemProcessor {
63
68
  return app;
64
69
  }
65
70
 
66
- updateItemsInStorage(app_id, items) {
71
+ async updateItemsInStorage(app_id, items) {
67
72
  this.pipeService.emit("gh_items_update", { app_id }, items);
68
73
  //-- getting app from storage
69
- const app = this.storage.getApp(app_id);
74
+ const app = await this.appProcessor.getApp(app_id);
70
75
  if (app && items) {
71
76
  items.forEach((item) => {
72
77
  const addressToEmit = { app_id };
@@ -88,6 +93,8 @@ export class ItemProcessor {
88
93
  //-- Checking if value of existing fields were updated, because we are not sending updates if value didn't changed
89
94
  if (fundedField.field_value != field.field_value) {
90
95
  fundedField.field_value = field.field_value;
96
+ app.items_object[fundedItem.item_id][fundedField.field_id] = fundedField;
97
+
91
98
  this.pipeService.emit(
92
99
  "gh_value_update",
93
100
  addressToEmit,
@@ -110,12 +117,16 @@ export class ItemProcessor {
110
117
  return items;
111
118
  }
112
119
 
113
- deleteItemsFromStorage(app_id, itemsForDelete = []) {
114
- const app = this.storage.getApp(app_id);
120
+ async deleteItemsFromStorage(app_id, itemsForDelete = []) {
121
+ const app = await this.appProcessor.getApp(app_id);
115
122
  if (app) {
116
- app.items_list = app.items_list.filter(
117
- (item) => !itemsForDelete.includes(item.item_id)
118
- );
123
+ app.items_list = app.items_list.filter(item => {
124
+ if(itemsForDelete.find(findedItem => item.item_id == findedItem.item_id)) {
125
+ delete app.items_object[item.item_id];
126
+ return false;
127
+ }
128
+ return true;
129
+ });
119
130
  this.pipeService.emit("gh_items_update", { app_id }, app.items_list);
120
131
  this.storage.updateApp(app);
121
132
  }
@@ -133,7 +144,7 @@ export class ItemProcessor {
133
144
  fields: filterFields(item.fields),
134
145
  }));
135
146
  const newItems = await this.addItemsApi(app_id, preparedItemsList);
136
- this.addItemsToStorage(app_id, newItems);
147
+ await this.addItemsToStorage(app_id, newItems);
137
148
  this.pipeService.emit("gh_items_add", { app_id }, newItems);
138
149
  return newItems;
139
150
  }
@@ -144,12 +155,12 @@ export class ItemProcessor {
144
155
  fields: filterFields(item.fields),
145
156
  }));
146
157
  const updatedItems = await this.updateItemsApi(app_id, preparedItemsList);
147
- return this.updateItemsInStorage(app_id, updatedItems);
158
+ return await this.updateItemsInStorage(app_id, updatedItems);
148
159
  }
149
160
 
150
161
  async deleteItems(app_id, itemsIds) {
151
- return this.deleteItemsApi(itemsIds).then(() =>
152
- this.deleteItemsFromStorage(app_id, itemsIds)
162
+ return this.deleteItemsApi(itemsIds).then(async (items) =>
163
+ await this.deleteItemsFromStorage(app_id, items)
153
164
  );
154
165
  }
155
166
 
@@ -0,0 +1,76 @@
1
+ import should from "should";
2
+ import { GudHub } from './../gudhub.js';
3
+
4
+ describe("ITEM PROCESSOR", async function () {
5
+ const auth_key = 'Z/lxMHLenEaQTvPjW5U6c3jBDwWFYZrh2F9Kxa3fbt8drvabS2u2lXQ2zI+SRmic';
6
+ const gudhub = new GudHub(auth_key);
7
+
8
+
9
+ it("GET ITEM / should return an item", async () => {
10
+ let item = await gudhub.getItem(16259, 1064673);
11
+ item.item_id.should.equal(1064673)
12
+ let itemType = typeof item;
13
+ itemType.should.equal('object');
14
+ });
15
+
16
+ it("ADD ITEM AND GET IT / should return new item twice", async () => {
17
+ let items = await gudhub.addNewItems(16259, newItems);
18
+
19
+ let isItemsArray = Array.isArray(items);
20
+
21
+ isItemsArray.should.equal(true);
22
+ items[0].fields[0].field_value.should.equal('Big Fish Tank');
23
+
24
+ let item = await gudhub.getItem(16259, items[0].item_id);
25
+
26
+ item.fields[0].field_value.should.equal('Big Fish Tank');
27
+ });
28
+
29
+ it("ADD NEW ITEM AND GET ITS VALUE / should return new item's value", async () => {
30
+ let items = await gudhub.addNewItems(16259, newItems);
31
+ let item_id = items[0].item_id;
32
+
33
+ let value = await gudhub.getFieldValue(16259, item_id, 254056);
34
+
35
+ value.should.equal('Big Fish Tank');
36
+ });
37
+
38
+ it("ADD NEW ITEM, UPDATE ITS VALUE AND GET IT / should return updated value of new item", async () => {
39
+ let items = await gudhub.addNewItems(16259, newItems);
40
+ let item_id = items[0].item_id;
41
+
42
+ await gudhub.setFieldValue(16259, item_id, 254056, 'Updated value');
43
+
44
+ let value = await gudhub.getFieldValue(16259, item_id, 254056);
45
+
46
+ value.should.equal('Updated value');
47
+ });
48
+
49
+ it("ADD NEW ITEM, THEN DELETE IT / should return null", async () => {
50
+ let items = await gudhub.addNewItems(16259, newItems);
51
+ let item_id = items[0].item_id;
52
+
53
+ await gudhub.deleteItems(16259, [item_id]);
54
+
55
+ let value = await gudhub.getFieldValue(16259, item_id, 254056);
56
+
57
+ let isValueNull = value === null ? true : false;
58
+
59
+ isValueNull.should.equal(true);
60
+ });
61
+
62
+ });
63
+
64
+ const newItems = [
65
+ {
66
+ item_id: 0,
67
+ fields: [
68
+ {
69
+ field_id: 254056,
70
+ element_id: 254056,
71
+ field_value: "Big Fish Tank",
72
+ data_id: 5994845
73
+ }
74
+ ]
75
+ },
76
+ ]
@@ -54,6 +54,7 @@ import { checkParams, createId } from "./utils.js";
54
54
  export class PipeService {
55
55
  constructor() {
56
56
  this.subscribers = {};
57
+ this.messageBox = {};
57
58
  }
58
59
 
59
60
  //============================== ON PIPE ====================================//
@@ -84,6 +85,9 @@ export class PipeService {
84
85
  }
85
86
 
86
87
  this.subscribers[typeWithId].add(fn);
88
+
89
+ //checking for messeges those were sent before subscription created
90
+ this.checkMessageBox(typeWithId);
87
91
  });
88
92
  }
89
93
  return this;
@@ -103,14 +107,26 @@ export class PipeService {
103
107
  | 'value' - Any (require). Emiter value to subscribers
104
108
  |-------------------------------------------------------------------------------*/
105
109
 
106
- emit(types, destination, address, params) {
110
+ emit(types, destination, value, params) {
107
111
  types.split(" ").forEach((type) => {
108
112
  const listenerName = type + ":" + createId(destination);
109
113
 
110
114
  if (this.subscribers[listenerName]) {
115
+
116
+ // if subscribers list is empty we put message to messageBox
117
+ if (this.subscribers[listenerName].size == 0){
118
+ this.messageBox[listenerName] = [types, destination, value, params];
119
+ return this;
120
+ }
121
+
122
+ // sending messege to subscribers
111
123
  this.subscribers[listenerName].forEach(function (fn) {
112
- fn(null, address, params);
124
+ fn(null, value, params);
113
125
  });
126
+
127
+ }else {
128
+ // if there no subscribers list we put message to messageBox
129
+ this.messageBox[listenerName] = [types, destination, value, params];
114
130
  }
115
131
  });
116
132
  return this;
@@ -158,10 +174,27 @@ export class PipeService {
158
174
 
159
175
  //if we are not passing a function then we remove a subscriber property
160
176
  if (this.subscribers[listenerName] && !func) {
161
- delete this.subscribers[listenerName]
177
+ delete this.subscribers[listenerName];
162
178
  }
163
179
  });
164
180
 
165
181
  return this;
166
182
  }
167
- }
183
+
184
+
185
+ //============================== MESSAGE BOX ====================================//
186
+ /*---------------------------------------------------------------------------------
187
+ | If emitting event started erlier then subscriber apears then we save it to the MessageBox
188
+ | After subscriber is created we update check MessageBox for encomming messendges
189
+ |
190
+ |---------------------------------------------------------------------------------*/
191
+
192
+ checkMessageBox(listenerName) {
193
+ if (this.messageBox[listenerName]) {
194
+ this.emit(...this.messageBox[listenerName]);
195
+
196
+ //we delete message after it was readed
197
+ delete this.messageBox[listenerName];
198
+ }
199
+ }
200
+ }
@@ -62,16 +62,16 @@ describe("PipeService", () => {
62
62
  });
63
63
 
64
64
 
65
- // it("Emitting event and then adding new subscriber", () => {
66
- // let incomeData = null;
65
+ it("Emitting event and then adding new subscriber", () => {
66
+ let incomeData = null;
67
67
 
68
- // gudhub
69
- // .emit("test", { app_id: 4, item_id: 3, field_id: 2 }, {"message" : "this is the data"})
70
- // .on("test", { app_id: 4, item_id: 3, field_id: 2 }, (event, data) => {
71
- // incomeData = data.message;
72
- // });
73
- // incomeData.should.equal("this is the data");
74
- // });
68
+ gudhub
69
+ .emit("test", { app_id: 4, item_id: 3, field_id: 2 }, {"message" : "this is the data"})
70
+ .on("test", { app_id: 4, item_id: 3, field_id: 2 }, (event, data) => {
71
+ incomeData = data.message;
72
+ });
73
+ incomeData.should.equal("this is the data");
74
+ });
75
75
 
76
76
 
77
77
  });
@@ -87,8 +87,9 @@ export default function generateModulesList(async_modules_path, file_server_url)
87
87
  },
88
88
  {
89
89
  name: "calendar",
90
- url: file_server_url + '/' + async_modules_path + "calendar_data.js",
91
- type: 'angular'
90
+ js: 'https://gudhub.com/modules/FullCalendar-Gh-Element/dist/main.js',
91
+ css: 'https://gudhub.com/modules/FullCalendar-Gh-Element/dist/style.css',
92
+ type: "class"
92
93
  },
93
94
  {
94
95
  name: "data_ref",
@@ -1,12 +1,13 @@
1
1
  import should from "should";
2
2
  import { GudHub } from "./../../gudhub.js";
3
3
  import { JSDOM } from 'jsdom';
4
+ import { file_server_url, async_modules_path, server_url } from './../../config.js';
4
5
 
5
6
  describe("JSON CONSTRUCTOR", function () {
6
7
  const gudhub = new GudHub('Z/lxMHLenEaQTvPjW5U6c3jBDwWFYZrh2F9Kxa3fbt8drvabS2u2lXQ2zI+SRmic', {
7
- server_url: 'https://gudhub.com/GudHub_Test',
8
- async_modules_path: 'build/async_modules_node/',
9
- file_server_url: 'http://localhost:8080'
8
+ server_url,
9
+ async_modules_path,
10
+ file_server_url,
10
11
  });
11
12
 
12
13
  const jsdom = new JSDOM('', {
@@ -19,6 +20,7 @@ describe("JSON CONSTRUCTOR", function () {
19
20
  gudhub.ghconstructor.initJsdomWindow(window);
20
21
 
21
22
  it("JSON FROM ONE APP : Here we construct simple json from one App", async function () {
23
+ this.timeout(4000);
22
24
  //-- checking if json was generated properly
23
25
  let json = await gudhub.jsonConstructor(fishtank_scheme);
24
26
  json.fishtank[0].should.have.property("name", "Big Fish Tank");
package/GUDHUB/config.js CHANGED
@@ -1,8 +1,10 @@
1
- //export const server_url = "https://gudhub.com/GudHub";
1
+ export const server_url = "https://gudhub.com/GudHub";
2
2
  //export const server_url = "https://gudhub.com/GudHub_Temp";
3
3
  //export const server_url = "https://integration.gudhub.com/GudHub_Test";
4
- export const server_url = "http://localhost:9000";
4
+ //export const server_url = "http://localhost:9000";
5
5
  export const wss_url = "wss://gudhub.com/GudHub/ws/app/";
6
+ export const async_modules_path = 'async_modules/';
7
+ export const file_server_url = 'http://localhost:9000';
6
8
 
7
9
  // FOR TESTS
8
10
  export const port = 9000;
package/GUDHUB/gudhub.js CHANGED
@@ -2,7 +2,7 @@ import { GudHubHttpsService } from "./gudhub-https-service.js";
2
2
  import { PipeService } from "./PipeService/PipeService.js";
3
3
  import { Storage } from "./Storage/Storage.js";
4
4
  import { WebSocketApi } from "./WebSocket/WebSocket.js";
5
- import { wss_url, server_url } from "./config.js";
5
+ import { wss_url, server_url, async_modules_path, file_server_url } from "./config.js";
6
6
  import { Utils } from "./Utils/Utils.js";
7
7
  import { Auth } from "./Auth/Auth.js";
8
8
  import { GHConstructor } from "./GHConstructor/ghconstructor.js";
@@ -25,8 +25,8 @@ export class GudHub {
25
25
  initWebsocket: false,
26
26
  activateSW: false,
27
27
  swLink: "",
28
- async_modules_path: '',
29
- file_server_url: ''
28
+ async_modules_path,
29
+ file_server_url
30
30
  }
31
31
  ) {
32
32
  this.ghconstructor = new GHConstructor(this);
@@ -4,6 +4,9 @@ import {GudHub} from './gudhub.js';
4
4
  import java_server from "../fake_server/fake_java_server.js";
5
5
  import {data} from '../fake_server/fake_server_data/fake_server_data.js';
6
6
  import {port,wss_url,server_url} from "./config.js";
7
+ import path from 'path';
8
+
9
+ const __dirname = path.resolve();
7
10
 
8
11
  //** TEST ACCOUNT CREDENTIONALS **/
9
12
  //fullname: "Vasya Pupkin"
@@ -16,6 +19,8 @@ const app = express();
16
19
  app.use(express.json());
17
20
  app.use(express.urlencoded());
18
21
 
22
+ app.use('/async_modules', express.static(__dirname + '/fake_server/fake_server_data/async_modules/'))
23
+
19
24
  app.listen(port, (err) => {
20
25
  if (err) console.log(err);
21
26
  console.log("Server run on port: ", port);