Successfully reported this slideshow.
We use your LinkedIn profile and activity data to personalize ads and to show you more relevant ads. You can change your ad preferences anytime.

EWD 3 Training Course Part 19: The cache.node APIs

559 views

Published on

This presentation is Part 19 of the EWD 3 Training Course. It examines how to access a Global Storage database from JavaScript, by making use of the cache.node APIs

Published in: Software

EWD 3 Training Course Part 19: The cache.node APIs

  1. 1. Copyright © 2016 M/Gateway Developments Ltd EWD 3 Training Course Part 19 Accessing a Global Storage Database from JavaScript: the cache.node APIs Rob Tweed Director, M/Gateway Developments Ltd Twitter: @rtweed
  2. 2. Copyright © 2016 M/Gateway Developments Ltd cache.node • The cache.node interface module allows you to access a Caché database from JavaScript
  3. 3. Copyright © 2016 M/Gateway Developments Ltd NodeM • The NodeM module is an Open Source emulation of cache.node, allowing the GT.M database to be accessed identically from JavaScript – https://github.com/dlwicksell/nodem
  4. 4. Copyright © 2016 M/Gateway Developments Ltd ewd-redis-globals • The Redis-based ewd-redis-globals implementation of Global Storage includes an implementation of the cache.node APIs, allowing the database to be accessed identically from JavaScript – https://github.com/robtweed/ewd-redis-globals
  5. 5. Copyright © 2016 M/Gateway Developments Ltd cache.node, NodeM & ewd-redis-globals APIs When accessed in a QEWD application: this.db.{{someFunctioName}}()
  6. 6. Copyright © 2016 M/Gateway Developments Ltd Loading and Initialising the Interface Modules These steps are done for you automatically by QEWD Here’s how to do it manually, eg if you're creating a standalone test-harness…
  7. 7. Copyright © 2016 M/Gateway Developments Ltd cache.node APIs Loading cache.node: var interface = require('cache'); var db = new interface.Cache();
  8. 8. Copyright © 2016 M/Gateway Developments Ltd cache.node APIs Opening connection to Caché : db.open({ path: '/opt/cache/mgr', username: '_SYSTEM', password: 'SYS', namespace: 'USER', charset: 'UTF-8', lock: 0 });
  9. 9. Copyright © 2016 M/Gateway Developments Ltd cache.node APIs Closing connection to Caché: var ok = db.close();
  10. 10. Copyright © 2016 M/Gateway Developments Ltd NodeM (GT.M) APIs Loading NodeM: var interface = require('nodem'); var db = new interface.Gtm();
  11. 11. Copyright © 2016 M/Gateway Developments Ltd NodeM APIs Opening connection to GT.M: db.open();
  12. 12. Copyright © 2016 M/Gateway Developments Ltd NodeM APIs Opening connection to GT.M: db.open(); Thereafter, all APIs are identical to those used with cache.node
  13. 13. Copyright © 2016 M/Gateway Developments Ltd NodeM APIs Closing connection to GT.M: var ok = db.close(); ie: Identical to cache.node
  14. 14. Copyright © 2016 M/Gateway Developments Ltd ewd-redis-globals APIs Loading ewd-redis-globals: var interface = require('ewd-redis-globals'); var db = new interface();
  15. 15. Copyright © 2016 M/Gateway Developments Ltd Opening connection to Redis / ewd-redis-globals: db.open(); ewd-redis-globals APIs
  16. 16. Copyright © 2016 M/Gateway Developments Ltd Thereafter, all APIs are identical to those used with cache.node Opening connection to Redis / ewd-redis-globals: db.open(); ewd-redis-globals APIs
  17. 17. Copyright © 2016 M/Gateway Developments Ltd Closing connection to Redis / ewd-redis-globals: var ok = db.close(); ie: Identical to cache.node ewd-redis-globals APIs
  18. 18. Copyright © 2016 M/Gateway Developments Ltd Setting up a test harness • Ready to use example for Caché in QEWD: – C:qewdnode_modulesqewdexampletest.js – Needs editing to match your Caché (or other database) configuration • Use previous slides for GT.M and Redis
  19. 19. Copyright © 2016 M/Gateway Developments Ltd Edit test.js var interface = require('cache'); var db = new interface.Cache(); console.log('db: ' + JSON.stringify(db)); // Change these parameters to match your GlobalsDB or Cache system: var ok = db.open({ path: '/opt/cache/mgr', username: '_SYSTEM', password: 'SYS', namespace: 'USER' }); console.log('ok: ' + JSON.stringify(ok)); console.log(db.version()); var node = { global: 'rob', subscripts: [1], data: 'hello' }; db.set(node); var result = db.get(node); console.log(JSON.stringify(result)); db.close();
  20. 20. Copyright © 2016 M/Gateway Developments Ltd Edit test.js var interface = require('cache'); var db = new interface.Cache(); console.log('db: ' + JSON.stringify(db)); // Change these parameters to match your GlobalsDB or Cache system: var ok = db.open({ path: 'C:InterSystemsCache2015-2mgr', username: '_SYSTEM', password: 'SYS', namespace: 'USER' }); console.log('ok: ' + JSON.stringify(ok)); console.log(db.version()); var node = { global: 'rob', subscripts: [1], data: 'hello' }; db.set(node); var result = db.get(node); console.log(JSON.stringify(result)); db.close();
  21. 21. Copyright © 2016 M/Gateway Developments Ltd Save as C:qewdtest.js var interface = require('cache'); var db = new interface.Cache(); console.log('db: ' + JSON.stringify(db)); // Change these parameters to match your GlobalsDB or Cache system: var ok = db.open({ path: 'C:InterSystemsCache2015-2mgr', username: '_SYSTEM', password: 'SYS', namespace: 'USER' }); console.log('ok: ' + JSON.stringify(ok)); console.log(db.version()); var node = { global: 'rob', subscripts: [1], data: 'hello' }; db.set(node); var result = db.get(node); console.log(JSON.stringify(result)); db.close();
  22. 22. Copyright © 2016 M/Gateway Developments Ltd Run it cd qewd (or on Linux / Raspberry Pi: cd /qewd ) node test
  23. 23. Copyright © 2016 M/Gateway Developments Ltd Run it cd qewd node test db: {} ok: {"ok":1,"result":1,"cache_pid":2960} Node.js Adaptor for Cache: Version: 1.1.113 (CM); Cache Version: 2015.2 build 66 4 {"global":"rob","subscripts":[1],"data":"hello","ok":1,"defined":1}
  24. 24. Copyright © 2016 M/Gateway Developments Ltd One difference between test harness and QEWD • Test harness: invoke cache.node APIs using: – db.xxx() • In QEWD worker module, they are accessed using: – this.db.xxx()
  25. 25. Copyright © 2016 M/Gateway Developments Ltd One difference between test harness and QEWD • Test harness: invoke cache.node APIs using: – db.xxx() db.set(node); var result = db.get(node); console.log(JSON.stringify(result)); db.close();
  26. 26. Copyright © 2016 M/Gateway Developments Ltd One difference between test harness and QEWD • In QEWD worker module: – this.db.xxx() • Note: QEWD opens the database automatically when a worker is started, and closes it automatically when the worker is stopped this.db.set(node); var result = this.db.get(node); console.log(JSON.stringify(result));
  27. 27. Copyright © 2016 M/Gateway Developments Ltd The Basic Global Storage APIs
  28. 28. Copyright © 2016 M/Gateway Developments Ltd Global Storage handling APIs Accessing global nodes: - set - get - delete (kill)
  29. 29. Copyright © 2016 M/Gateway Developments Ltd Defining a Global Node: var node = { global: 'employee', subscripts: [123456, 'name'] }; Global Storage handling APIs
  30. 30. Copyright © 2016 M/Gateway Developments Ltd Defining a Global Node: var node = { global: 'employee', subscripts: [123456, 'name'] }; employee(123456,"name") Global Storage handling APIs
  31. 31. Copyright © 2016 M/Gateway Developments Ltd Accessing global nodes: - set node.data = 'Rob Tweed'; this.db.set(node); Global Storage handling APIs
  32. 32. Copyright © 2016 M/Gateway Developments Ltd Accessing global nodes: - get var value = this.db.get(node).data; Global Storage handling APIs
  33. 33. Copyright © 2016 M/Gateway Developments Ltd Accessing global nodes: - kill this.db.kill(node); Global Storage handling APIs
  34. 34. Copyright © 2016 M/Gateway Developments Ltd Traversing Global Subscripts
  35. 35. Copyright © 2016 M/Gateway Developments Ltd Traversing global nodes: - Iterate through subscripts Global Storage handling APIs
  36. 36. Copyright © 2016 M/Gateway Developments Ltd Traversing global nodes: - Iterate through subscripts at a particular hierarchy level myGlobal("a")=123 myGlobal("b","c1")="foo" myGlobal("b","c2")="foo2" myGlobal("d","e1","f1")="bar1" myGlobal("d","e1","f2")="bar2" myGlobal("d","e2","f1")="bar1" myGlobal("d","e2","f2")="bar2" myGlobal("d","e2","f3")="bar3" myGlobal "a" 123 "b" "c2" "foo2" "d" "c1" "foo" "e2" "e1" "f2" "bar2" "f1" "bar1" "f2" "bar2" "f1" "bar1" "f3" "bar3" "a", "b", "d" Global Storage handling APIs
  37. 37. Copyright © 2016 M/Gateway Developments Ltd Traversing global nodes: - Iterate through subscripts at a particular hierarchy level myGlobal("a")=123 myGlobal("b","c1")="foo" myGlobal("b","c2")="foo2" myGlobal("d","e1","f1")="bar1" myGlobal("d","e1","f2")="bar2" myGlobal("d","e2","f1")="bar1" myGlobal("d","e2","f2")="bar2" myGlobal("d","e2","f3")="bar3" myGlobal "a" 123 "b" "c2" "foo2" "d" "c1" "foo" "e2" "e1" "f2" "bar2" "f1" "bar1" "f2" "bar2" "f1" "bar1" "f3" "bar3" "e1", "e2" Global Storage handling APIs
  38. 38. Copyright © 2016 M/Gateway Developments Ltd Traversing global nodes: - Iterate through subscripts at a particular hierarchy level myGlobal("a")=123 myGlobal("b","c1")="foo" myGlobal("b","c2")="foo2" myGlobal("d","e1","f1")="bar1" myGlobal("d","e1","f2")="bar2" myGlobal("d","e2","f1")="bar1" myGlobal("d","e2","f2")="bar2" myGlobal("d","e2","f3")="bar3" myGlobal "a" 123 "b" "c2" "foo2" "d" "c1" "foo" "e2" "e1" "f2" "bar2" "f1" "bar1" "f2" "bar2" "f1" "bar1" "f3" "bar3" "f1", "f2", "f3" Global Storage handling APIs
  39. 39. Copyright © 2016 M/Gateway Developments Ltd myGlobal("d","e2","f1")="bar1" myGlobal("d","e2","f2")="bar2" myGlobal("d","e2","f3")="bar3" "f1", "f2", "f3" Global Storage handling APIs To achieve the following traversal:
  40. 40. Copyright © 2016 M/Gateway Developments Ltd Traversing Global Node: var node = { global: 'myGlobal', subscripts: ['d', 'e2', '' ] }; myGlobal("d","e2","f1")="bar1" myGlobal("d","e2","f2")="bar2" myGlobal("d","e2","f3")="bar3" "f1", "f2", "f3" Global Storage handling APIs
  41. 41. Copyright © 2016 M/Gateway Developments Ltd Traversing Global Node: var node = { global: 'myGlobal', subscripts: ['d', 'e2', '' ] }; myGlobal("d","e2","f1")="bar1" myGlobal("d","e2","f2")="bar2" myGlobal("d","e2","f3")="bar3" "f1", "f2", "f3" "seed" value to start iterator Empty string Global Storage handling APIs
  42. 42. Copyright © 2016 M/Gateway Developments Ltd Traversing Global Node: var node = { global: 'myGlobal', subscripts: ['d', 'e2', '' ] }; var subscript = this.db.order(node).result; // 'f1' myGlobal("d","e2","f1")="bar1" myGlobal("d","e2","f2")="bar2" myGlobal("d","e2","f3")="bar3" "f1", "f2", "f3" Global Storage handling APIs
  43. 43. Copyright © 2016 M/Gateway Developments Ltd Traversing Global Node: var node = { global: 'myGlobal', subscripts: ['d', 'e2', '' ] }; var subscript = this.db.order(node).result; // 'f1' subscript = this.db.order(node).result; // 'f2' myGlobal("d","e2","f1")="bar1" myGlobal("d","e2","f2")="bar2" myGlobal("d","e2","f3")="bar3" "f1", "f2", "f3" Global Storage handling APIs
  44. 44. Copyright © 2016 M/Gateway Developments Ltd Traversing Global Node: var node = { global: 'myGlobal', subscripts: ['d', 'e2', '' ] }; var subscript = this.db.order(node).result; // 'f1' subscript = this.db.order(node).result; // 'f2' subscript = this.db.order(node).result; // 'f3' myGlobal("d","e2","f1")="bar1" myGlobal("d","e2","f2")="bar2" myGlobal("d","e2","f3")="bar3" "f1", "f2", "f3" Global Storage handling APIs
  45. 45. Copyright © 2016 M/Gateway Developments Ltd Traversing Global Node: var node = { global: 'myGlobal', subscripts: ['d', 'e2', '' ] }; var subscript = this.db.order(node).result; // 'f1' subscript = this.db.order(node).result; // 'f2' subscript = this.db.order(node).result; // 'f3' subscript = this.db.order(node).result; // '' myGlobal("d","e2","f1")="bar1" myGlobal("d","e2","f2")="bar2" myGlobal("d","e2","f3")="bar3" "f1", "f2", "f3" Global Storage handling APIs
  46. 46. Copyright © 2016 M/Gateway Developments Ltd Traversing Global Node: var node = { global: 'myGlobal', subscripts: ['d', 'e2', 'f2' ] }; var subscript = this.db.order(node).result; // 'f3' myGlobal("d","e2","f1")="bar1" myGlobal("d","e2","f2")="bar2" myGlobal("d","e2","f3")="bar3" "f3" "seed" value to start iterator Start from f2 Global Storage handling APIs
  47. 47. Copyright © 2016 M/Gateway Developments Ltd Traversing Global Node: var subscript = this.db.order(node).result; // 'f3' node is now: { global: 'myGlobal', subscripts: ['d', 'e2', 'f3' ] }; myGlobal("d","e2","f1")="bar1" myGlobal("d","e2","f2")="bar2" myGlobal("d","e2","f3")="bar3" Global Storage handling APIs
  48. 48. Copyright © 2016 M/Gateway Developments Ltd Traversing Global Node: var node = { global: 'myGlobal', subscripts: ['d', 'e2', 'f2' ] }; var subscript = this.db.order(node).result; // 'f3' subscript = this.db.order(node).result; // '' myGlobal("d","e2","f1")="bar1" myGlobal("d","e2","f2")="bar2" myGlobal("d","e2","f3")="bar3" "" Global Storage handling APIs Empty string means no further subscripts, so traversal is complete
  49. 49. Copyright © 2016 M/Gateway Developments Ltd Traversing Global Node – generic loop: var node = { global: 'myGlobal', subscripts: ['d', 'e2', '' ] }; var subscript; do { subscript = this.db.order(node).result; if (subscript !== '') console.log(subscript); } while (subscript !== ''); myGlobal("d","e2","f1")="bar1" myGlobal("d","e2","f2")="bar2" myGlobal("d","e2","f3")="bar3" "f1", "f2", "f3" Global Storage handling APIs
  50. 50. Copyright © 2016 M/Gateway Developments Ltd The APIs are low-level • Deliberately designed to provide the basic means of access to Global Storage and nothing more • They assume you understand the mechanics of Global Storage • Too low-level for JavaScript development – Traversal, in particular, requires a lot of code • However, they can be abstracted to a more JavaScript-centric point of view – Which is the subject of the next part of this course

×