103 lines
		
	
	
		
			2.8 KiB
		
	
	
	
		
			JavaScript
		
	
	
	
	
	
			
		
		
	
	
			103 lines
		
	
	
		
			2.8 KiB
		
	
	
	
		
			JavaScript
		
	
	
	
	
	
'use strict';
 | 
						|
 | 
						|
var urlUtils = require('./utils/url')
 | 
						|
  , eventUtils = require('./utils/event')
 | 
						|
  , JSON3 = require('json3')
 | 
						|
  , FacadeJS = require('./facade')
 | 
						|
  , InfoIframeReceiver = require('./info-iframe-receiver')
 | 
						|
  , iframeUtils = require('./utils/iframe')
 | 
						|
  , loc = require('./location')
 | 
						|
  ;
 | 
						|
 | 
						|
var debug = function() {};
 | 
						|
if (process.env.NODE_ENV !== 'production') {
 | 
						|
  debug = require('debug')('sockjs-client:iframe-bootstrap');
 | 
						|
}
 | 
						|
 | 
						|
module.exports = function(SockJS, availableTransports) {
 | 
						|
  var transportMap = {};
 | 
						|
  availableTransports.forEach(function(at) {
 | 
						|
    if (at.facadeTransport) {
 | 
						|
      transportMap[at.facadeTransport.transportName] = at.facadeTransport;
 | 
						|
    }
 | 
						|
  });
 | 
						|
 | 
						|
  // hard-coded for the info iframe
 | 
						|
  // TODO see if we can make this more dynamic
 | 
						|
  transportMap[InfoIframeReceiver.transportName] = InfoIframeReceiver;
 | 
						|
  var parentOrigin;
 | 
						|
 | 
						|
  /* eslint-disable camelcase */
 | 
						|
  SockJS.bootstrap_iframe = function() {
 | 
						|
    /* eslint-enable camelcase */
 | 
						|
    var facade;
 | 
						|
    iframeUtils.currentWindowId = loc.hash.slice(1);
 | 
						|
    var onMessage = function(e) {
 | 
						|
      if (e.source !== parent) {
 | 
						|
        return;
 | 
						|
      }
 | 
						|
      if (typeof parentOrigin === 'undefined') {
 | 
						|
        parentOrigin = e.origin;
 | 
						|
      }
 | 
						|
      if (e.origin !== parentOrigin) {
 | 
						|
        return;
 | 
						|
      }
 | 
						|
 | 
						|
      var iframeMessage;
 | 
						|
      try {
 | 
						|
        iframeMessage = JSON3.parse(e.data);
 | 
						|
      } catch (ignored) {
 | 
						|
        debug('bad json', e.data);
 | 
						|
        return;
 | 
						|
      }
 | 
						|
 | 
						|
      if (iframeMessage.windowId !== iframeUtils.currentWindowId) {
 | 
						|
        return;
 | 
						|
      }
 | 
						|
      switch (iframeMessage.type) {
 | 
						|
      case 's':
 | 
						|
        var p;
 | 
						|
        try {
 | 
						|
          p = JSON3.parse(iframeMessage.data);
 | 
						|
        } catch (ignored) {
 | 
						|
          debug('bad json', iframeMessage.data);
 | 
						|
          break;
 | 
						|
        }
 | 
						|
        var version = p[0];
 | 
						|
        var transport = p[1];
 | 
						|
        var transUrl = p[2];
 | 
						|
        var baseUrl = p[3];
 | 
						|
        debug(version, transport, transUrl, baseUrl);
 | 
						|
        // change this to semver logic
 | 
						|
        if (version !== SockJS.version) {
 | 
						|
          throw new Error('Incompatible SockJS! Main site uses:' +
 | 
						|
                    ' "' + version + '", the iframe:' +
 | 
						|
                    ' "' + SockJS.version + '".');
 | 
						|
        }
 | 
						|
 | 
						|
        if (!urlUtils.isOriginEqual(transUrl, loc.href) ||
 | 
						|
            !urlUtils.isOriginEqual(baseUrl, loc.href)) {
 | 
						|
          throw new Error('Can\'t connect to different domain from within an ' +
 | 
						|
                    'iframe. (' + loc.href + ', ' + transUrl + ', ' + baseUrl + ')');
 | 
						|
        }
 | 
						|
        facade = new FacadeJS(new transportMap[transport](transUrl, baseUrl));
 | 
						|
        break;
 | 
						|
      case 'm':
 | 
						|
        facade._send(iframeMessage.data);
 | 
						|
        break;
 | 
						|
      case 'c':
 | 
						|
        if (facade) {
 | 
						|
          facade._close();
 | 
						|
        }
 | 
						|
        facade = null;
 | 
						|
        break;
 | 
						|
      }
 | 
						|
    };
 | 
						|
 | 
						|
    eventUtils.attachEvent('message', onMessage);
 | 
						|
 | 
						|
    // Start
 | 
						|
    iframeUtils.postMessage('s');
 | 
						|
  };
 | 
						|
};
 |