Source: js/secure_window_factory.js

  1. /* -*- Mode: js; tab-width: 2; indent-tabs-mode: nil; c-basic-offset: 2 -*- /
  2. /* vim: set shiftwidth=2 tabstop=2 autoindent cindent expandtab: */
  3. 'use strict';
  4. (function(exports) {
  5. /**
  6. * To delegate the ownership of apps out of other components,
  7. * so we can keep our components clean, and only hold minimal
  8. * parts they should know. The user should only need to know
  9. * how to create a SecureWindow app via the `create` method in
  10. * this factory.
  11. *
  12. * @constructor SecureWindowFactory
  13. */
  14. var SecureWindowFactory = function() {
  15. this.initEvents();
  16. };
  17. SecureWindowFactory.prototype = {
  18. /**
  19. * @memberof SecureWindowFactory#
  20. * @prop {object} apps - would hold spawned apps and release them
  21. * while they got terminated.
  22. */
  23. states: {
  24. apps: {}
  25. },
  26. /**
  27. * @memberof SecureWindowFactory#
  28. */
  29. configs: {
  30. listens: ['secure-launchapp',
  31. 'secure-appterminated',
  32. 'secure-modeon',
  33. 'secure-modeoff']
  34. }
  35. };
  36. /**
  37. * Hook listeners of events this factory interested in.
  38. *
  39. * @private
  40. * @this {SecureWindowFactory}
  41. * @memberof SecureWindowFactory
  42. */
  43. SecureWindowFactory.prototype.initEvents =
  44. function swf_initEvents() {
  45. this.configs.listens.forEach((function _initEvent(type) {
  46. self.addEventListener(type, this);
  47. }).bind(this));
  48. };
  49. /**
  50. * Remove listeners of events this factory interested in.
  51. *
  52. * @private
  53. * @this {SecureWindowFactory}
  54. * @memberof SecureWindowFactory
  55. */
  56. SecureWindowFactory.prototype.suspendEvents =
  57. function swf_suspendEvents() {
  58. this.configs.listens.forEach((function _unbind(ename) {
  59. self.removeEventListener(ename, this);
  60. }).bind(this));
  61. };
  62. /**
  63. * Remove event listeners except the resuming (`secure-modeon`)
  64. * event.
  65. *
  66. * @private
  67. * @this {SecureWindowFactory}
  68. * @memberof SecureWindowFactory
  69. */
  70. SecureWindowFactory.prototype.suspend =
  71. function swf_suspend() {
  72. this.suspendEvents();
  73. self.addEventListener('secure-modeon', this);
  74. for (var origin in this.states.apps) {
  75. this.unregisterApp(this.states.apps[origin]);
  76. }
  77. };
  78. /**
  79. * Hook event listeners back and don't care the resuming
  80. * (`secure-modeon`) event anymore.
  81. *
  82. * @private
  83. * @this {SecureWindowFactory}
  84. * @memberof SecureWindowFactory
  85. */
  86. SecureWindowFactory.prototype.resume =
  87. function swf_resume() {
  88. this.initEvents();
  89. // To prevent duplicated init.
  90. self.removeEventListener('secure-modeon', this);
  91. };
  92. /**
  93. * @listens secure-launchapp - launch app by URL and manifest URL.
  94. * @listens secure-modeon - the system would be in the secure mode by locking
  95. * or other reasons.
  96. * @listens secure-modeoff - the system now is not in the secure mode anymore.
  97. * @listens secure-appterminated - when a secure app got really closed, it
  98. * would fire this event.
  99. * @memberof SecureWindowFactory
  100. */
  101. SecureWindowFactory.prototype.handleEvent =
  102. function(evt) {
  103. switch (evt.type)
  104. {
  105. case 'secure-launchapp':
  106. var {appURL, appManifestURL} = evt.detail;
  107. this.create(appURL, appManifestURL);
  108. break;
  109. case 'secure-appterminated':
  110. var app = evt.detail;
  111. this.unregisterApp(app);
  112. break;
  113. case 'secure-modeoff':
  114. this.suspend();
  115. break;
  116. case 'secure-modeon':
  117. this.resume();
  118. break;
  119. }
  120. };
  121. /**
  122. * Create a SecureWindow app.
  123. *
  124. * @param {URL} url - the app's URL
  125. * @param {URL} manifestURL - the URL of the app's manifest
  126. * @this {SecureWindowFactory}
  127. * @memberof SecureWindowFactory
  128. */
  129. SecureWindowFactory.prototype.create =
  130. function(url, manifestURL) {
  131. var config = new self.BrowserConfigHelper({
  132. url: url,
  133. manifestURL: manifestURL
  134. });
  135. for (var instanceID in this.states.apps) {
  136. var secureWindow = this.states.apps[instanceID];
  137. if (config.manifestURL === secureWindow.manifestURL) {
  138. secureWindow.cancelSoftKill();
  139. secureWindow.open();
  140. return; // Already created.
  141. }
  142. }
  143. var app = new self.SecureWindow(config);
  144. app.open();
  145. this.registerApp(app);
  146. };
  147. /**
  148. * @private
  149. * @this {SecureWindowFactory}
  150. * @memberof SecureWindowFactory
  151. */
  152. SecureWindowFactory.prototype.registerApp =
  153. function(app) {
  154. this.states.apps[app.instanceID] = app;
  155. };
  156. /**
  157. * @private
  158. * @this {SecureWindowFactory}
  159. * @memberof SecureWindowFactory
  160. */
  161. SecureWindowFactory.prototype.unregisterApp =
  162. function(app) {
  163. delete this.states.apps[app.instanceID];
  164. };
  165. /** @exports SecureWindowFactory */
  166. exports.SecureWindowFactory = SecureWindowFactory;
  167. })(self);