/**
* @module 'brixy.mvc.Application'
*/
BX.module.define('brixy.mvc.Application', function() {
/**
* Application class.
* Configuration object may either be empty or may override any default application settings.
* - Dependency injection container = `config.container` or 'brixy.di.Container'
* - Collection of services `config.services` is registered in the DI container
* - Request router = `config.requestRouter` or 'brixy.mvc.Router'
* - Collection of routes `config.routes` is registered in the request router
* - Event router = `config.eventRouter` or 'brixy.mvc.Router'
* - Collection of events `config.events` is registered in the event router
*
* @class
* @alias module:'brixy.mvc.Application'~Application
* @param {Object} config - Configuration object.
*/
function Application(config) {
if (!config || typeof config !== 'object')
config = {};
// DI container
var container = config.container || 'brixy.di.Container';
switch (typeof container) {
case 'string':
container = new (BX.module(container).Me)();
break;
case 'function':
container = new container();
break;
}
if ('services' in config)
container.registerServices(config.services);
this._requestRouter = container.getInstance(config.requestRouter || 'brixy.mvc.Router');
this._eventRouter = config.eventRouter || 'brixy.mvc.Router'; // lazy creating
this._eventRouterCreated = false;
this._container = container;
if ('routes' in config)
this._requestRouter.setRoutes(config.routes);
if ('events' in config)
this.getEventRouter().setRoutes(config.events);
}
/**
* Returns a string representation of the object.
* @method
* @return {string}
*/
Application.prototype.toString = BX.toString;
/**
* Returns dependency injection container.
* @return {Object}
*/
Application.prototype.getContainer = function() {
return this._container;
};
/**
* Returns request router.
* @return {Object}
*/
Application.prototype.getRequestRouter = function() {
return this._requestRouter;
};
/**
* Returns event router.
* @return {Object}
*/
Application.prototype.getEventRouter = function() {
if (!this._eventRouterCreated) {
this._eventRouter = this.getContainer().getInstance(this._eventRouter);
this._eventRouterCreated = true;
}
return this._eventRouter;
};
/**
* Processes the request. Tries to convert any request to a request route.
* @param {string|Object} request - Request string or route object.
* @param {string|Object} [sender] - Controller that sent this request. (optional)
* @throws Exception
*/
Application.prototype.processRequest = function(request, sender) {
if (!request)
return;
try {
var next = request,
route,
router = this.getRequestRouter(),
c;
while (next) {
route = router.createRoute(next);
if (route.controller) {
c = (route.controller === 'this') ? sender : route.controller;
c = sender = this.getContainer().getInstance(c);
try {
next = c.run(route.action, route.data) || route.forward;
}
catch (ee) {
if (c && ('run' in c) && (typeof c.run === "function"))
throw ee;
else
throw Error('Controller\'s ' + c + '.run() method is not defined.');
}
}
else if (route.forward) {
next = router.createRoute(route.forward);
next.refine({action: route.action, data: route.data});
}
else
next = null;
}
}
catch (e) {
try {
next = next.toHumanString();
}
catch (ee) {
}
throw new BX.error('brixy.mvc.Application.processRequest()', Error('Processing of the request "' + next + '" failed.'), e);
}
};
/**
* Gets event route and forwards it to `processRequest()` method. Only event routes, that are registered in the event router, are allowed.
* `AppManager.processEvent()` uses this method as an entry point into the application.
* @param {string} event - Event name.
* @param {Object} [data] - Application can pass the data to the event handler. (optional)
* @throws Exception
*/
Application.prototype.processEvent = function(event, data) {
if (!event)
return;
try {
var route = this.getEventRouter().getRoute(event);
if (!route) // only saved routes are processed
return;
if (!data || typeof data !== 'object')
data = {};
data.event = event + '';
route.refine({data: data});
// forward request
this.processRequest(route);
}
catch (e) {
throw new BX.error('brixy.mvc.Application.processEvent()', Error('Processing of the event "' + event + '" failed.'), e);
}
};
/**
* Returns true if application can process the event. Only event routes, that are registered in the event router, are allowed.
* @param {string} event - Event name.
* @return {boolean}
*/
Application.prototype.listensEvent = function(event) {
try {
return this.getEventRouter().hasRoute(event);
}
catch (e) {
return false;
}
};
// publish
return {
/**
* Application class.
* @memberOf module:'brixy.mvc.Application'
* @type {module:'brixy.mvc.Application'~Application}
*/
Me: Application
};
});
►