UNPKG

ri-backoffice

Version:

Administration panel for route-injector package

1,500 lines (1,315 loc) 142 kB
(function (angular) { 'use strict'; //Generic function makeArray(arr) { if(!arr){ return []; } return angular.isArray(arr) ? arr : [arr]; } //Angular function provideRootElement(modules, element) { element = angular.element(element); modules.unshift(['$provide', function ($provide) { $provide.value('$rootElement', element); }]); } function createInjector(injectorModules, element) { var modules = ['ng'].concat(makeArray(injectorModules)); if (element) { provideRootElement(modules, element); } return angular.injector(modules); } function bootstrapApplication(angularApp) { angular.element(document).ready(function () { angular.bootstrap(document, [angularApp]); }); } angular.lazy = function (app, modules) { var injector = createInjector(modules), $q = injector.get('$q'), promises = [], errorCallback = angular.noop, loadingCallback = angular.noop, doneCallback = angular.noop; return { resolve: function (promise) { promise = $q.when(injector.instantiate(promise)); promises.push(promise); return this; }, bootstrap: function () { loadingCallback(); return $q.all(promises) .then(function () { bootstrapApplication(app); }, errorCallback) .finally(doneCallback); }, loading: function(callback){ loadingCallback = callback; return this; }, done: function(callback){ doneCallback = callback; return this; }, error: function(callback){ errorCallback = callback; return this; } }; }; })(angular); (function () { 'use strict'; var app = angular .module( 'injectorApp', [ 'ngRoute', 'ngBiscuit', 'schemaForm', 'datePicker', 'ui.select', 'ui.ace', 'ui.codemirror', 'ui.bootstrap', 'ngFileUpload', 'ngDroplet', 'punchCard', 'nvd3ChartDirectives', 'flash', 'ngDialog', 'angular-loading-bar', 'pascalprecht.translate', 'ngCookies', 'nemLogging', 'ui-leaflet', 'angular-toArrayFilter', ], ['$rootScopeProvider', function ($rootScopeProvider) { $rootScopeProvider.digestTtl(15); }] ) .run(['$rootScope', 'configs', function ($rootScope, configs) { $rootScope.configs = configs; }]); angular .lazy('injectorApp') .resolve([ '$http', function ($http) { return $http.get('/configs').then(function (resp) { console.log("confs: ", resp); app.constant('configs', resp.data); }); }, ]) .resolve([ '$http', '$q', function ($http, $q) { var deferred = $q.defer(); $http.get('/admin/extensions').then(function (resp) { app.constant('extensions', resp.data); var extensions = resp.data; var assets = $('asset-loader'); var scripts = []; for (var i = 0; i < assets.length; i++) { var cache = []; var asset = assets[i]; var src = asset.attributes.src.nodeValue; var type = asset.attributes.type.nodeValue; if (src === 'files') { if (extensions.files[type] && extensions.files[type].length) { cache = cache.concat(extensions.files[type]); } } else if (src === 'pages') { for (var j in extensions.pages) { var p = extensions.pages[j]; if (p.backoffice) { if (p[type] && p[type].length) { cache = cache.concat(p[type]); } } } } if (type === 'css') { asset.appendChild(createCSSNodes(cache)); } else if (type === 'js') { if (cache && cache.length) { scripts = scripts.concat(cache); } } } //$.getMultiScripts(scripts).done(function () { // deferred.resolve(); //}); getScripts(scripts, function () { deferred.resolve(); }); }); return deferred.promise; }, ]) .bootstrap(); function createCSSNodes(obj) { var div = document.createElement('div'); for (var i in obj) { var link = document.createElement('link'); link.href = obj[i]; link.rel = 'stylesheet'; div.appendChild(link); } return div; } function getScripts(scripts, callback) { if (!scripts || !scripts.length) { return callback(); } var progress = 0; var internalCallback = function () { if (++progress == scripts.length) { $.ajaxSetup({ async: true }); callback(); } }; $.ajaxSetup({ async: false }); scripts.forEach(function (script) { $.getScript(script, internalCallback); }); } $.getMultiScripts = function (arr, path) { var _arr = $.map(arr, function (scr) { return $.getScript((path || '') + scr); }); _arr.push( $.Deferred(function (deferred) { $(deferred.resolve); }) ); return $.when.apply($, _arr); }; })(); (function () { 'use strict'; angular .module('injectorApp') .config(['$routeProvider', 'configs', 'extensions', 'customMenuProvider', function ($routeProvider, configs, extensions, customMenuProvider) { var authCheck = function ( $q, $rootScope, $location, $http, loginProvider, configs ) { var defer = $q.defer(); if (configs.auth) { loginProvider.getUser(function (user) { if (!user) { $location.path('/login'); } else { $http.defaults.headers.common.Authorization = 'BEARER ' + user.token; $rootScope.login = undefined; } defer.resolve(); }); } else { $rootScope.allowedUser = true; defer.resolve(); } return defer.promise; }; authCheck.$inject = ['$q', '$rootScope', '$location', '$http', 'loginProvider', 'configs']; var homePage = 'html/models.html'; if (configs.backoffice.home) { homePage = configs.backoffice.home; } $routeProvider .when('/', { templateUrl: homePage, controller: 'MainController', resolve: { app: authCheck, }, }) .when('/model/:schema', { templateUrl: 'html/model.html', controller: 'ModelController', resolve: { app: authCheck, }, }) .when('/model/:schema/new', { templateUrl: 'html/create-and-update.html', controller: 'CreateController', resolve: { app: authCheck, }, reloadOnSearch: false, }) .when('/model/:schema/update/:id', { templateUrl: 'html/create-and-update.html', controller: 'UpdateController', resolve: { app: authCheck, }, reloadOnSearch: false, }) .when('/model/:schema/update/:id/:shard', { templateUrl: 'html/create-and-update.html', controller: 'UpdateController', resolve: { app: authCheck, }, reloadOnSearch: false, }) .when('/model/:schema/graphs', { templateUrl: 'html/graphs.html', controller: 'GraphsController', resolve: { app: authCheck, }, }) .when('/login', { // login / password templateUrl: 'html/login.html', controller: 'LoginController', resolve: { app: ['$q', '$rootScope', '$location', 'loginProvider', function ($q, $rootScope, $location, loginProvider) { var defer = $q.defer(); loginProvider.getUser(function (user) { if (user) { $location.path('/'); } else { $rootScope.login = true; } defer.resolve(); }); return defer.promise; }], }, }) .when('/logout', { resolve: { app: ['$q', '$rootScope', '$location', 'loginProvider', function ($q, $rootScope, $location, loginProvider) { var defer = $q.defer(); loginProvider.logout(); $location.path('/'); defer.resolve(); return defer.promise; }], }, }) .when('/settings', { templateUrl: 'html/settings.html', controller: 'SettingsController', }); if (configs.images && configs.images.gallery) { $routeProvider.when('/gallery', { templateUrl: 'html/gallery.html', resolve: { app: authCheck, }, }); } if (extensions && extensions.pages) { var menu = []; for (var i in extensions.pages) { var page = extensions.pages[i]; //Add the route for the custom page. modelName controls the sharding selector if given if (page.backoffice) { $routeProvider.when('/' + page.url, { templateUrl: page.template, controller: page.controller, resolve: { app: authCheck, }, modelName: page.modelName, }); } //TO-DO: 20-04-2021 -> hide custom pages from menu (user.role) if (page.menu) { menu.push(page.menu); } } customMenuProvider.setCustomMenu(menu); } $routeProvider.otherwise({ redirectTo: '/' }); }]); })(); (function () { 'use strict'; angular.module('injectorApp') .config(['$translateProvider', '$translatePartialLoaderProvider', 'configs', function ($translateProvider, $translatePartialLoaderProvider, configs) { var i18n = configs.backoffice.i18n; $translatePartialLoaderProvider.addPart('login'); $translatePartialLoaderProvider.addPart('model'); $translatePartialLoaderProvider.addPart('models'); $translatePartialLoaderProvider.addPart('navbar'); $translatePartialLoaderProvider.addPart('search'); $translatePartialLoaderProvider.addPart('create_update'); //$translatePartialLoaderProvider.addPart('flash'); $translatePartialLoaderProvider.addPart('version_dialog'); if (i18n && i18n.length) { for (var i = 0; i < i18n.length; i++) { $translatePartialLoaderProvider.addPart(i18n[i]); } } $translateProvider.useLoader('$translatePartialLoader', { urlTemplate: 'i18n/{part}/{lang}.json' }); $translateProvider.registerAvailableLanguageKeys(['en', 'es']); var def = "en"; $translateProvider.fallbackLanguage('en'); $translateProvider.useLocalStorage(); if (configs.backoffice.uniqueLanguage) { def = configs.backoffice.uniqueLanguage; $translateProvider.use(def); } $translateProvider.preferredLanguage(def); }]); }()); (function () { 'use strict'; angular.module('injectorApp').provider('customMenu', function () { var menuElements; this.setCustomMenu = function (value) { menuElements = value; }; this.$get = ['loginProvider', function (loginProvider) { return { getSections: function (cb) { loginProvider.getUser(function (user) { var filtered = []; if (user) { filtered = menuElements.filter(function (elem) { if (elem.roles && Array.isArray(elem.roles)) return elem.roles.includes(user.role); else return elem; }); } else { filtered = menuElements.filter(function (elem) { return !!elem.roles; }); } return cb(filtered); }); }, }; }]; }); })(); (function () { 'use strict'; angular.module('injectorApp').provider('loginProvider', function () { this.$get = ['$http', '$location', 'cookieStore', '$rootScope', function ($http, $location, cookieStore, $rootScope) { var factory = {}; $http.defaults.headers.common['Client-Type'] = 'backoffice'; $http.defaults.headers.common.profile = 'back'; factory.login = function (userModel, cb) { $http .post('/auth/login', userModel) .success(function (res) { var user = {}; //user.name = userModel.login; user.login = userModel.login; user.role = res.role; user.token = res.token; var cookieOptions = { path: '/', end: Infinity }; cookieStore.put('user', JSON.stringify(user), cookieOptions); $http.defaults.headers.common.Authorization = 'BEARER ' + res.token; $rootScope.$broadcast('login', user); $rootScope.allowedUser = true; cb(user); }) .error(function (err) { var cookieOptions = { path: '/' }; cookieStore.remove('user', cookieOptions); $rootScope.$broadcast('logout', undefined); $rootScope.allowedUser = false; cb(false); }); }; factory.getUser = function (cb) { var user = JSON.parse(cookieStore.get('user')); if ( user && !$rootScope.allowedUser && user.login && (user.password || user.token) ) { factory.login(user, function (logged) { if (logged) { angular.extend(user, logged); cb(logged); } else { cb(undefined); } }); } else { if (!user) { $rootScope.allowedUser = false; } else { //$rootScope.$broadcast('login', user); } cb(user); } }; factory.logout = function () { var cookieOptions = { path: '/' }; cookieStore.remove('user', cookieOptions); $location.path('/login'); $rootScope.$broadcast('logout', undefined); }; return factory; }]; }); })(); (function () { 'use strict'; angular.module('injectorApp').provider('models', function () { var overrides = {}; var service = {}; this.override = function (_method, _function) { overrides[_method] = _function; }; this.getService = function () { return service; }; this.$get = ['$rootScope', '$http', '$httpParamSerializer', 'Upload', 'configs', 'common', function ( $rootScope, $http, $httpParamSerializer, Upload, configs, common ) { var modelsConfig = {}; var singlesCache = {}; var shards = {}; var prefix = ''; $rootScope.$on('logout', function () { service.invalidate(); }); $rootScope.$on('invalidate', function () { console.log('invalidate models provider'); service.invalidate(); }); service.invalidate = function () { shards = {}; singlesCache = {}; modelsConfig = {}; }; service.getHttp = function () { return $http; }; service.getUpload = function () { return Upload; }; service.setShard = function (key, value, model) { var shard = {}; shard.key = key; shard.value = value; shard.model = model; shards[model] = shard; }; service.getShard = function (model) { return shards[model]; }; service.removeShard = function (model) { delete shards[model]; }; service.getModels = function (cb) { prefix = configs.app.prefix; //AVOID CACHE (FOR CHANGING MODELS WHEN LOGIN LOGOUT :) $http.get('/schemas').then(function (schemas) { var models = schemas.data; cb(models); }); }; service.getModel = function (modelName, cb) { if (!modelsConfig[modelName] && cb) { $http.get('/schema/' + modelName).then(function (schema) { $http .get('/schema/' + modelName + '/formconfig') .then(function (config) { modelsConfig[modelName] = {}; modelsConfig[modelName].schema = schema.data; modelsConfig[modelName].config = config.data; cb(modelsConfig[modelName]); }); }); } else if (!modelsConfig[modelName] && !cb) { var schema = JSON.parse( $.ajax({ type: 'GET', url: '/schema/' + modelName, async: false, }).responseText ); var config = JSON.parse( $.ajax({ type: 'GET', url: '/schema/' + modelName + '/formconfig', async: false, }).responseText ); modelsConfig[modelName] = {}; modelsConfig[modelName].schema = schema; modelsConfig[modelName].config = config; return modelsConfig[modelName]; } else { if (cb) { cb(modelsConfig[modelName]); } else { return modelsConfig[modelName]; } } }; service.getModelElements = function (modelName, skip, limit, cb) { service.getModel(modelName, function (data) { var plural = data.config.plural || data.config.path + 's' || modelName + 's'; var body = { skip: skip, limit: limit, }; if (service.getShard(modelName)) { body[service.getShard(modelName).key] = service.getShard( modelName ).value; } $http.post(prefix + '/' + plural, body).success(function (elements) { cb(elements.result, elements.status.count); }); }); }; service.getModelSchema = function (modelName, cb) { service.getModel(modelName, function (data) { return cb(data.schema); }); }; service.getModelConfig = function (modelName, cb) { service.getModel(modelName, function (data) { return cb(data.config); }); }; service.postDocument = function (modelName, model, cb) { service.getModel(modelName, function (data) { var path = data.config.path || modelName; $http .post(prefix + '/' + path, JSON.stringify(model)) .then(function (response) { return cb(response); }); }); }; service.getUrl = function (modelName, cb) { throw new Error('Not implemented'); }; service.getDocument = function (modelName, id, shard, cb) { if (!cb) { cb = shard; shard = undefined; } if (!modelName) { return cb(); } if (!id) { return cb(); } service.getModel(modelName, function (data) { var path = data.config.path || modelName; var qParams = { params: { type: 'back', }, }; service.getModelConfig(modelName, function (cfg) { if (shard && cfg.shard && cfg.shard.shardKey) { qParams.params[cfg.shard.shardKey] = shard; } else if (service.getShard(modelName)) { qParams.params[ service.getShard(modelName).key ] = service.getShard(modelName).value; } $http .get(prefix + '/' + path + '/' + id, qParams) .success(function (document) { return cb(document, null); }) .error(function (data) { return cb(null, data); }); }); }); }; service.putDocument = function (modelName, id, model, cb) { service.getModel(modelName, function (data) { var path = data.config.path || modelName; $http .put(prefix + '/' + path + '/' + id, JSON.stringify(model)) .then(function (document) { return cb(document); }); }); }; service.removeDocument = function (modelName, id, shard, cb) { if (!cb) { cb = shard; shard = undefined; } service.getModel(modelName, function (data) { var cfg = data.config; var path = cfg.path || modelName; var opts = { params: {} }; if (shard && cfg.shard && cfg.shard.shardKey) { opts.params[cfg.shard.shardKey] = shard; } else if (service.getShard(modelName)) { opts.params[service.getShard(modelName).key] = service.getShard( modelName ).value; } $http.delete(prefix + '/' + path + '/' + id, opts).then(cb); }); }; service.removeDocumentByMongoId = function (modelName, id, shard, cb) { if (!cb) { cb = shard; shard = undefined; } service.getModel(modelName, function (data) { var cfg = data.config; var path = data.config.path || modelName; var opts = { params: { type: 'raw', }, }; if (shard && cfg.shard && cfg.shard.shardKey) { opts.params[cfg.shard.shardKey] = shard; } else if (service.getShard(modelName)) { opts.params[service.getShard(modelName).key] = service.getShard( modelName ).value; } $http.delete(prefix + '/' + path + '/' + id, opts).then(cb); }); }; service.uploadToGallery = function (file, cb) { var path = service.getGalleryPath(); Upload.upload({ url: path, file: file, fileFormDataName: ['file[]'], }) .progress(function (evt) { console.log( 'percent: ' + parseInt((100.0 * evt.loaded) / evt.total) ); }) .success(function (data, status, headers, config) { cb(data); }); }; service.uploadImage = function ( modelName, id, fieldName, index, image, cb ) { service.getModel(modelName, function (data) { var path = data.config.path || modelName; Upload.upload({ url: prefix + '/' + path + '/' + id + '/' + fieldName, //upload.php script, node.js route, or servlet url data: { index: index }, file: image, fileFormDataName: ['image'], }) .progress(function (evt) { console.log( 'percent: ' + parseInt((100.0 * evt.loaded) / evt.total) ); }) .success(function (data, status, headers, config) { cb(data); }); }); }; service.uploadFile = function ( modelName, id, fieldName, index, file, cb ) { service.getModel(modelName, function (data) { var path = data.config.path || modelName; Upload.upload({ url: prefix + '/' + path + '/' + id + '/' + fieldName, //upload.php script, node.js route, or servlet url data: { index: index }, file: file, fileFormDataName: ['file'], }) .progress(function (evt) { console.log( 'percent: ' + parseInt((100.0 * evt.loaded) / evt.total) ); }) .success(function (data, status, headers, config) { cb(data); }); }); }; service.deleteImage = function (modelName, id, index, image, cb) { service.getModel(modelName, function (data) { var path = data.config.path || modelName; $http .delete(prefix + '/' + path + '/' + id + '/image/' + image) .then(cb); }); }; service.deleteFile = function (modelName, id, index, file, cb) { service.getModel(modelName, function (data) { var path = data.config.path || modelName; $http .delete(prefix + '/' + path + '/' + id + '/file/' + file) .then(cb); }); }; service.getImageUrl = function (modelName, id, imageName, cb) { service.getModel(modelName, function (data) { var path = data.config.path || modelName; var url = prefix + '/' + path + '/image/' + imageName + common.getRandomQuery(); cb(url); }); }; service.getFileUrl = function (modelName, id, fileName, cb) { service.getModel(modelName, function (data) { var path = data.config.path || modelName; var url = prefix + '/' + path + '/file/' + fileName + common.getRandomQuery(); cb(url); }); }; service.getSingleModel = function (modelName, cb) { if (singlesCache[modelName]) { cb(singlesCache[modelName]); } else { service.search(modelName, { skip: 0, limit: 1 }, function ( elements, count ) { if (count > 0) { //We only cach if we found THE single document singlesCache[modelName] = elements[0]; cb(elements[0]); } else { //Do nothing from now cb(null); } }); } }; service.search = function (modelName, query, shard, cb) { if (!cb) { cb = shard; shard = undefined; } service.getModelConfig(modelName, function (config) { var path = config.plural || modelName; if (shard && config.shard && config.shard.shardKey) { query[config.shard.shardKey] = shard; } else if (service.getShard(modelName)) { query[service.getShard(modelName).key] = service.getShard( modelName ).value; } $http .post(prefix + '/' + path, JSON.stringify(query)) .success(function (documents) { if (documents.status.search_count !== undefined) { cb(documents.result, documents.status.search_count); } else { cb(documents.result, documents.status.count); } }); }); }; service.export = function (modelName, format, searchQuery, cb) { service.getModelConfig(modelName, function (config) { var query = {}; var path = config.plural || modelName; if (service.getShard(modelName)) { query[service.getShard(modelName).key] = service.getShard( modelName ).value; } query.format = format; query.by = config.id; query.query = searchQuery || {}; service.postAsForm(prefix + '/' + path + '/export', query); cb(); }); }; service.import = function (modelName, format, file, query, cb) { service.getModelConfig(modelName, function (config) { var path = config.plural || modelName; if (service.getShard(modelName)) { query[service.getShard(modelName).key] = service.getShard( modelName ).value; } query.format = format; service.postAsForm( prefix + '/' + path + '/import', query, 'POST', file ); cb(); }); }; service.postAsForm = function (path, params, method, file) { method = method || 'post'; // Set method to post by default if not specified. console.log('POST AS FORM', path, params, method, file); var info = common.parsePathParams(path); info.vars.token = $http.defaults.headers.common.Authorization.replace( 'BEARER ', '' ); // The rest of this code assumes you are not using a library. // It can be made less wordy if you use one. var form = document.createElement('form'); form.setAttribute('method', method); form.setAttribute( 'action', info.path + '?' + $httpParamSerializer(info.vars) ); // Open result into a new tab/window: form.setAttribute('target', '_blank'); for (var key in params) { if (params.hasOwnProperty(key)) { var hiddenField = document.createElement('input'); hiddenField.setAttribute('type', 'hidden'); hiddenField.setAttribute('name', key); if (typeof params[key] == 'object') { hiddenField.setAttribute('value', JSON.stringify(params[key])); } else { hiddenField.setAttribute('value', params[key]); } form.appendChild(hiddenField); } } document.body.appendChild(form); form.submit(); document.body.removeChild(form); }; service.getGraph = function (modelName, graphID, cb) { service.getModelConfig(modelName, function (config) { var path = config.path || modelName; $http .post(prefix + '/' + path + '/graphs/' + encodeURI(graphID)) .success(function (data) { cb(data); }); }); }; service.galleryGetByPath = function (path, cb) { if (!service.isGalleryEnabled()) return; $http.get(service.getGalleryPath() + path).success(function (data) { cb(data); }); }; service.galleryDelete = function (path, cb) { if (!service.isGalleryEnabled()) return; $http.delete(path).success(function (data) { cb(data); }); }; service.galleryDeleteByPath = function (path, cb) { if (!service.isGalleryEnabled()) return; $http.delete(service.getGalleryPath() + path).success(function (data) { cb(data); }); }; service.galleryPostByPath = function (path, cb) { Upload.upload({ url: service.getGalleryPath() + path, file: '', fileFormDataName: ['file[]'], }).success(function (data, status, headers, config) { cb(data); }); }; service.isGalleryEnabled = function (role) { if (role) { if (configs.images && configs.images.gallery && configs.images.gallery.menu && Array.isArray(configs.images.gallery.menu)) { return ( configs.images && configs.images.gallery && configs.images.gallery.endpoint && configs.images.gallery.menu.includes(role) ); } else { return ( configs.images && configs.images.gallery && configs.images.gallery.endpoint ); }; } else { return ( configs.images && configs.images.gallery && configs.images.gallery.endpoint && (!configs.images.gallery.menu || !configs.images.gallery.menu.length) ); } }; service.getGalleryPath = function () { var path = configs.images.gallery.endpoint; if (path[0] !== '/') path = '/' + path; if (path[path.length - 1] !== '/') path += '/'; return prefix + path; }; function fieldIsDenormalized(retElem, element) { var ret = null; // There is no denormalize field list if (!retElem || !retElem.denormalize) { return null; } // Look for the element as a string and return the position if found var i = retElem.denormalize.indexOf(element); if (i > -1) { return i; } // Look for the element as an object with target and source, return the position if found for (i = 0; i < retElem.denormalize.length; i++) { if ( typeof retElem.denormalize[i] === 'object' && retElem.denormalize[i].target == element ) { ret = i; } } return ret; } service.getFieldTitle = function (field, schema) { var i = field.indexOf('.'); if (i == -1) { var sch = service.getFieldFromSchema(field, schema); if (sch && sch.title) { return sch.title; } else { return common.prettifyTitle(field); } } else { var f = field.substring(0, i); var sch = service.getFieldFromSchema(f, schema); var part1; var part2; if (sch && sch.title) { part1 = sch.title; } else { part1 = common.prettifyTitle(field); } var sch = service.getFieldFromSchema(field, schema); if (sch && sch.title) { part2 = sch.title; } else { part2 = common.prettifyTitle(field.substring(i + 1)); } return part1 + ' > ' + part2; } }; /** * Obtains point separated field {{field}} from schema {{schema}} * @param field * @param schema * @returns {*} */ service.getFieldFromSchema = function (field, schema) { if (schema[field]) { return schema[field]; } else { var elements = field.split('.'); var retElem; for (var i in elements) { var denormalizedFieldPosition = fieldIsDenormalized( retElem, elements[i] ); if (retElem && retElem.properties) { retElem = retElem.properties[elements[i]]; } else if ( retElem && retElem.ref && denormalizedFieldPosition != null ) { var source; var target; var denormalizedField = retElem.denormalize[denormalizedFieldPosition]; if (typeof denormalizedField === 'string') { source = denormalizedField; target = denormalizedField; } else { source = denormalizedField.source; target = denormalizedField.target; } var refSchema = service.getModel(retElem.ref); retElem = angular.copy( service.getFieldFromSchema(source, refSchema.schema) ); if (retElem && retElem.title) { var index = field.lastIndexOf('.'); retElem.title = common.prettifyTitle( field.substring(0, index) + '.' + retElem.title ); } } else { retElem = schema[elements[i]]; } } return retElem; } }; angular.forEach(Object.keys(overrides), function (key) { service[key] = overrides[key]; }); return service; }]; }); })(); (function () { 'use strict'; angular.module('injectorApp') .factory('selectCacheService', function () { return { TIMEOUT_MS: 750, timers: {}, cache: {} }; }) .provider('selectCache', function () { this.$get = ['$rootScope', 'models', 'selectCacheService', function ($rootScope, models, selectCacheService) { var provider = {}; $rootScope.$on('$routeChangeStart', function (event, next, current) { if (next != current) { selectCacheService.cache = {}; angular.forEach(Object.keys(selectCacheService.timers), function (m) { clearTimeout(selectCacheService.timers[m]); delete selectCacheService.timers[m]; }); //console.log("[SelectCache] CACHE CLEARED"); } }); provider.search = function (modelName, b, shard, cb) { var body = JSON.stringify(b); var mainKey = shard ? modelName + "_" + shard : modelName; //console.log("[SelectCache] POST FROM SELECT", modelName, b); if (!selectCacheService.cache[mainKey]) { selectCacheService.cache[mainKey] = {}; } if (!selectCacheService.cache[mainKey].posts) { selectCacheService.cache[mainKey].posts = {}; } var cached = selectCacheService.cache[mainKey].posts[body]; if (!cached) {//A new query selectCacheService.cache[mainKey].posts[body] = {}; //CALLBACKS selectCacheService.cache[mainKey].posts[body].cbks = [cb]; //CALLBACKS //console.log("[SelectCache] >>>>>>>>>>>>>> HTTP POST", modelName, b); models.search(modelName, b, shard, function (response, count) { //console.log("[SelectCache] POST SELECT RESULT", modelName, b, { // count: count, // response: response //}); selectCacheService.cache[mainKey].posts[body].res = { response: response, count: count }; angular.forEach(selectCacheService.cache[mainKey].posts[body].cbks, function (cbk) { cbk(response, count); }); selectCacheService.cache[mainKey].posts[body].cbks = []; }); } else if (!cached.res && cached.cbks) {//Not finished query cached.cbks.push(cb); //console.log("[SelectCache] ADDED CB FOR POST", modelName, b); } else { //Finished query cached.cbks.push(cb); angular.forEach(cached.cbks, function (cbk) { //console.log("[SelectCache] CACHED POST", modelName, b, { // count: cached.res.count, // response: cached.res.response //}); cbk(cached.res.response, cached.res.count); }); cached.cbks = []; } }; provider.getDocument = function (modelName, id, shard, cb) { //console.log("[SelectCache] GET FROM SELECT", modelName, id); var mainKey = shard ? modelName + "_" + shard : modelName; if (!selectCacheService.cache[mainKey]) { selectCacheService.cache[mainKey] = {}; } if (!selectCacheService.cache[mainKey].gets) { selectCacheService.cache[mainKey].gets = {}; } if (id) { if (!selectCacheService.cache[mainKey].gets[id]) { selectCacheService.cache[mainKey].gets[id] = {}; } if (!selectCacheService.cache[mainKey].gets[id].cbks) { selectCacheService.cache[mainKey].gets[id].cbks = []; } if (selectCacheService.cache[mainKey].gets[id].result) { //console.log("[SelectCache] CACHED VALUE", modelName, id, selectCacheService.cache[modelName].gets[id].result); cb(selectCacheService.cache[mainKey].gets[id].result); } else if (selectCacheService.cache[mainKey].gets[id].cbks.indexOf(cb) == -1) { selectCacheService.cache[mainKey].gets[id].cbks.push(cb); //console.log("[SelectCache] ADDED CB FOR GET", modelName, id); if (selectCacheService.timers[mainKey]) { clearTimeout(selectCacheService.timers[mainKey]); } //TODO: Possible bug, ASYNC MODELNAME && SHARD !!!!! selectCacheService.timers[mainKey] = setTimeout(function(){ httpCall(modelName, shard); }, selectCacheService.TIMEOUT_MS); } } else{ //WE HAVE TO RELEASE THE GETDOCUMENT CALLBACK!!! cb(); } }; function httpCall(model, shard) { models.getModelConfig(model, function (cfg) { var mainKey = shard ? model + "_" + shard : model; var q = {}; if (shard && cfg.shard && cfg.shard.shardKey) { q[cfg.shard.shardKey] = shard; } var keys = Object.keys(selectCacheService.cache[mainKey].gets); if (keys.length == 1) { q[cfg.id] = keys[0]; } else { q.$or = []; angular.forEach(keys, function (id) { if (!selectCacheService.cache[mainKey].gets[id].result) { var singleQ = {}; singleQ[cfg.id] = id; q.$or.push(singleQ); } }); } //console.log("[SelectCache] >>>>>>>>>>>>>> HTTP GETS", model, q); models.search(model, {query: q}, function (result, count) { //console.log("[SelectCache] GET SELECT RESULT", model, q, result); angular.forEach(result, function (doc) { var id = doc[cfg.id]; if (!selectCacheService.cache[mainKey].gets[id]) selectCacheService.cache[mainKey].gets[id] = {}; selectCacheService.cache[mainKey].gets[id].result = doc; }); angular.forEach(Object.keys(selectCacheService.cache[mainKey].gets), function (idKey) { var getObj = selectCacheService.cache[mainKey].gets[idKey]; if (getObj.cbks) { angular.forEach(getObj.cbks, function (cb) { cb(getObj.result); }); delete getObj.cbks; } }); }); }); } return provider; }]; }); }()); (function () { 'use strict'; angular.module('injectorApp') .factory('httpResponseInterceptor', ['$q', '$location', '$routeParams', 'flash', '$injector', 'configs', function ($q, $location, $routeParams, flash, $injector, configs) { return { response: function (response) { //console.log(response); if (response.headers("routeinjector") && (response.headers("routeinjector") !== configs.backoffice.version)) { var ngDialog = $injector.get("ngDialog"); if (ngDialog.getOpenDialogs().length === 0) { ngDialog.open({ template: "dialogVersionMismatch", className: 'ngdialog-theme-default ngdialog-theme-custom' }); } } if (response.status === 401) { console.log("Response 401"); } else if (response.status === 201) { if (configs.images && configs.images.gallery && configs.images.gallery.endpoint && response.config.url.indexOf(configs.images.gallery.endpoint) == 0) { return response || $q.when(response); } flash.success("Done", "Document saved successfully"); } return response || $q.when(response); }, responseError: function (rejection) { var models = $injector.get("models"); var modelName = $routeParams.schema; var modelId = $routeParams.id; var errorInReferencedProperty; var prefix = configs.app.prefix; if (modelName) { models.getModelConfig(modelName, function (model) { var path = "/" + model.path + "/" + modelId; if (prefix) { path = "/" + path; } errorInReferencedProperty = path !== rejection.config.url; handleError(errorInReferencedProperty); }); } else { handleError(true); } function handleError(ignoreError) { function redirectError() { if ($location.url() != "/login" && $location.url() != "/logout" && $location.url() != "/") { if ($routeParams.schema) { $location.path('/model/' + $routeParams.schema); } else { $location.path('/'); } } } if (rejection.status === 401) { console.log("Response Error 401", rejection); redirectError(); if ($location.url() != "/login") { flash.error("Unauthorized", JSON.stringify(rejection.data)); } } else if (rejection.status === 500) { flash.error("Internal server error", JSON.stringify(rejection.data)); } else if (rejection.status === 400) { //Client error flash.error("Bad Request", JSON.stringify(rejection.data)); } else if (rejection.status === 404 && !ignoreError) { redirectError(); flash.error("Not Found", JSON.stringify(rejection.data)); } else if (rejection.status === 404 && ignoreError) { flas