2 'app/yangui/yangui.services',
\r
3 'app/yangui/pluginHandler.services',
\r
6 'app/yangui/directives/abn_tree.directive',
\r
7 'app/yangui/directives/sticky.directive',
\r
8 'app/yangui/directives/read_file.directive',
\r
9 'app/yangui/directives/ui-codemirror.directive'
\r
12 'app/yangui/controllers/api/augmentation-modal.controller',
\r
13 'app/yangui/controllers/api/case.controller',
\r
14 'app/yangui/controllers/api/coll-box.controller',
\r
15 'app/yangui/controllers/api/container.controller',
\r
16 'app/yangui/controllers/api/filter.controller',
\r
17 'app/yangui/controllers/api/filter-type.controller',
\r
18 'app/yangui/controllers/api/filter-type-bit.controller',
\r
19 'app/yangui/controllers/api/filter-type-empty.controller',
\r
20 'app/yangui/controllers/api/filter-type-enum.controller',
\r
21 'app/yangui/controllers/parameters/history-param.controller',
\r
22 'app/yangui/controllers/api/choice.controller',
\r
23 'app/yangui/controllers/api/input.controller',
\r
24 'app/yangui/controllers/api/leaf.controller',
\r
25 'app/yangui/controllers/api/leaf-list.controller',
\r
26 'app/yangui/controllers/api/list.controller',
\r
27 'app/yangui/controllers/api/output.controller',
\r
28 'app/yangui/controllers/parameters/param-box.controller',
\r
29 'app/yangui/controllers/parameters/params-view.controller',
\r
30 'app/yangui/controllers/history/req-in-history.controller',
\r
31 'app/yangui/controllers/history/request-history.controller',
\r
32 'app/yangui/controllers/api/rpc.controller',
\r
33 'app/yangui/controllers/api/type.controller',
\r
34 'app/yangui/controllers/api/type-bit.controller',
\r
35 'app/yangui/controllers/api/type-empty.controller',
\r
36 'app/yangui/controllers/api/type-enum.controller'
\r
39 define(['app/yangui/yangui.module'].concat(services).concat(directives).concat(controllers), function(yangui) {
\r
42 yangui.register.controller('yanguiCtrl', ['$scope', '$timeout', '$rootScope', '$http', '$filter', 'YangUtilsRestangular', 'yangUtils', 'reqBuilder', 'custFunct',
\r
43 'pluginHandler', 'pathUtils', 'constants', 'nodeWrapper', 'mountPointsConnector', 'filterConstants','displayMountPoints','yinParser', 'designUtils', 'eventDispatcher', 'syncFact',
\r
44 'customFunctUnsetter', 'HistoryServices', 'dataBackuper', 'parsingJson',
\r
45 function ($scope, $timeout, $rootScope, $http, $filter, YangUtilsRestangular, yangUtils, reqBuilder, custFunctFact, pluginHandler, pathUtils, constants, nodeWrapper, mountPointsConnector,
\r
46 filterConstants, displayMountPoints, yinParser, designUtils, eventDispatcher, syncFact, customFunctUnsetter, HistoryServices, dataBackuper, parsingJson) {
\r
47 $rootScope['section_logo'] = 'assets/images/logo_yangui.gif';
\r
48 $scope.currentPath = 'src/app/yangui/views/';
\r
49 $scope.apiType = '';
\r
50 $scope.constants = constants;
\r
51 $scope.filterConstants = filterConstants;
\r
52 $scope.filterRootNode = null;
\r
53 $scope.previewValidity = true;
\r
54 $scope.previewDelay = 2000;
\r
55 $scope.selCustFunct = null;
\r
56 $scope.selCustFunctButts = [];
\r
57 $scope.mpSynchronizer = syncFact.generateObj();
\r
58 $scope.defaultTreeName = $filter('translate')('YANGUI_ROOT');
\r
59 $scope.treeName = $scope.defaultTreeName;
\r
73 $scope.showTabs = function(tabs, tabName){
\r
74 for(var prop in tabs){
\r
75 tabs[prop] = tabName === prop;
\r
78 designUtils.triggerWindowResize(100);
\r
81 var mountPrefix = constants.MPPREFIX;
\r
83 var statusChangeEvent = function(messages) {
\r
84 // var newMessage = $scope.status.rawMsg + '\r\n' + messages.join('\r\n');
\r
85 processingModulesCallback(messages[0]);
\r
88 var fillPathIdentifiersByKey = function(inputs) {
\r
89 var node = inputs[0],
\r
90 value = inputs[1] || '';
\r
92 if($scope.selSubApi && node.parent && $scope.selSubApi.node.id === node.parent.id) { //or $scope.node === node.parent?
\r
93 var identifiers = $scope.selSubApi.pathArray[$scope.selSubApi.pathArray.length - 1].identifiers;
\r
94 pathUtils.fillIdentifiers(identifiers, node.label, value);
\r
98 var fillPathIdentifiersByListData = function(inputs) {
\r
99 var node = inputs[0];
\r
101 if($scope.selSubApi && node && $scope.selSubApi.node.id === node.id) { //or $scope.node === node.parent?
\r
102 var identifiers = $scope.selSubApi.pathArray[$scope.selSubApi.pathArray.length - 1].identifiers,
\r
103 keys = node.refKey;
\r
105 keys.forEach(function(key) {
\r
106 pathUtils.fillIdentifiers(identifiers, key.label, key.value);
\r
111 $scope.parameterizeData = function(path) {
\r
112 var parameterList = null;
\r
114 $scope.$broadcast('GET_PARAMETER_LIST', function(parameters) {
\r
115 parameterList = parameters;
\r
118 return HistoryServices.parametrizeData(parameterList.list, path);
\r
121 eventDispatcher.registerHandler(constants.EV_SRC_MAIN, statusChangeEvent);
\r
122 eventDispatcher.registerHandler(constants.EV_FILL_PATH, fillPathIdentifiersByKey);
\r
123 eventDispatcher.registerHandler(constants.EV_LIST_CHANGED, fillPathIdentifiersByListData);
\r
125 var processingModulesCallback = function(e) {
\r
129 msg: 'PROCESSING_MODULES',
\r
134 $scope.processingModulesSuccessCallback = function(e) {
\r
137 msg: 'PROCESSING_MODULES_SUCCESS',
\r
142 $scope.processingModulesErrorCallback = function(e) {
\r
145 msg: 'PROCESSING_MODULES_ERROR',
\r
150 var requestWorkingCallback = function() {
\r
158 var requestSuccessCallback = function() {
\r
161 msg: 'SEND_SUCCESS'
\r
165 $scope.setStatusMessage = function(type, msg, e){
\r
173 var requestErrorCallback = function(e, resp) {
\r
174 var errorMessages = yangUtils.errorMessages,
\r
175 msg = errorMessages.method[resp.config.method] ? errorMessages.method[resp.config.method][resp.status] ? errorMessages.method[resp.config.method][resp.status] : 'SEND_ERROR' : 'SEND_ERROR';
\r
180 rawMsg: e.toString()
\r
184 var setCustFunct = function(apis) {
\r
185 pluginHandler.plugAll($scope.apis, $scope);
\r
188 $scope.removeMountPointPath = function(pathArray){
\r
189 var mpPathIndex = pathArray.length;
\r
191 pathArray.some(function(pathElem, index) {
\r
192 var isMPElem = pathElem.name === mountPrefix;
\r
194 mpPathIndex = index;
\r
200 var pathCopy = pathArray.slice(0, mpPathIndex);
\r
204 $scope.invalidatePreview = function() {
\r
205 $scope.previewValidity = false;
\r
208 $scope.validatePreview = function() {
\r
209 $scope.previewValidity = true;
\r
212 $scope.isPreviewValid = function() {
\r
213 return $scope.previewValidity;
\r
216 $scope.preview = function() {
\r
217 if($scope.isPreviewValid()) {
\r
218 $scope.invalidatePreview();
\r
220 $timeout(function () {
\r
221 $scope.buildPreview();
\r
222 $scope.validatePreview();
\r
223 }, $scope.previewDelay);
\r
227 $scope.buildPreview = function() {
\r
229 var reqString = $scope.selSubApi.buildApiRequestString(),
\r
233 $scope.node.buildRequest(reqBuilder, requestData, $scope.node.module);
\r
234 // update request data (remove envelope from POST request etc.)
\r
235 requestData = yangUtils.prepareRequestData(requestData, $scope.selectedOperation, reqString, $scope.selSubApi);
\r
237 var jsonRequestData = requestData ? JSON.stringify(requestData, null, 4) : '';
\r
239 $scope.previewValue = $scope.selApi.basePath + reqString;
\r
240 $scope.previewValue = $scope.previewValue + '\r\n' + jsonRequestData;
\r
242 $scope.previewValue = '';
\r
246 $scope.getNodeName = function(localeLabel, label) {
\r
247 var localeResult = $filter('translate')(localeLabel);
\r
248 return localeResult.indexOf(constants.LOCALE_PREFIX) === 0 ? label : localeResult;
\r
251 $scope.showCustFunctButton = function() {
\r
252 return $scope.selCustFunct === null;
\r
255 $scope.showCustFunctCancelButton = function() {
\r
256 return $scope.selCustFunct !== null;
\r
259 $scope.unsetCustomFunctionality = function() {
\r
260 if($scope.selCustFunct) {
\r
261 customFunctUnsetter.unset($scope.selCustFunct, $scope);
\r
263 $scope.selCustFunct = null;
\r
264 $scope.treeName = $scope.defaultTreeName;
\r
265 $scope.selCustFunctButts = [];
\r
268 var loadApis = function loadApis() {
\r
270 $scope.allNodes = [];
\r
271 $scope.treeApis = [];
\r
272 $scope.augmentations = {};
\r
274 processingModulesCallback();
\r
275 yangUtils.generateNodesToApis(function(apis, allNodes, augGroups) {
\r
276 $scope.apis = apis;
\r
277 $scope.allNodes = allNodes;
\r
278 $scope.augmentations = augGroups;
\r
279 console.info('got data', $scope.apis, $scope.allNodes, $scope.augmentations);
\r
280 $scope.treeApis = yangUtils.generateApiTreeData(apis);
\r
281 console.info('tree api', $scope.treeApis);
\r
282 $scope.processingModulesSuccessCallback();
\r
284 setCustFunct($scope.apis);
\r
285 $scope.$broadcast('LOAD_REQ_DATA');
\r
287 $scope.processingModulesErrorCallback(e);
\r
291 $scope.isMountPointSelected = function() {
\r
292 return $scope.selCustFunct.label === 'YANGUI_CUST_MOUNT_POINTS';
\r
295 $scope.dismissStatus = function() {
\r
296 $scope.status = {};
\r
299 $scope.setNode = function() {
\r
300 $scope.node = $scope.selSubApi.node;
\r
303 $scope.setApiNode = function(indexApi, indexSubApi) {
\r
304 $scope.selectedOperation = null;
\r
306 if(indexApi !== undefined && indexSubApi !== undefined ) {
\r
307 $scope.selApi = $scope.apis[indexApi];
\r
308 $scope.selSubApi = $scope.selApi.subApis[indexSubApi];
\r
310 $scope.apiType = $scope.selSubApi.pathArray[0].name === 'operational' ? 'operational/':'';
\r
311 $scope.node = $scope.selSubApi.node;
\r
312 $scope.filterRootNode = $scope.selSubApi.node;
\r
313 $scope.node.clear();
\r
315 if($scope.selSubApi && $scope.selSubApi.operations) {
\r
316 $scope.selectedOperation = $scope.selSubApi.operations[0];
\r
318 $scope.$broadcast('EV_REFRESH_LIST_INDEX');
\r
319 designUtils.triggerWindowResize(100);
\r
321 $scope.selApi = null;
\r
322 $scope.selSubApi = null;
\r
323 $scope.node = null;
\r
327 $scope.loadController = function() {
\r
329 $scope.devices = [];
\r
331 $scope.previewVisible = false;
\r
332 $scope.previewValue = '';
\r
333 $scope.popupData = { show: false};
\r
334 $scope.dataToFill = '';
\r
335 $scope.apiToFill = '';
\r
339 $rootScope.$on('$includeContentLoaded', function() {
\r
340 designUtils.setDraggablePopups();
\r
341 //designUtils.getHistoryPopUpWidth();
\r
345 $scope.executeOperation = function(operation, callback, reqPath) {
\r
346 var reqString = $scope.selSubApi.buildApiRequestString(),
\r
348 preparedRequestData = {},
\r
351 reqString = reqPath ? reqPath.slice($scope.selApi.basePath.length, reqPath.length) : reqString;
\r
352 var requestPath = $scope.selApi.basePath + reqString;
\r
354 $scope.node.buildRequest(reqBuilder, requestData, $scope.node.module);
\r
355 angular.copy(requestData, preparedRequestData);
\r
357 preparedRequestData = yangUtils.prepareRequestData(preparedRequestData, operation, reqString, $scope.selSubApi);
\r
359 operation = yangUtils.prepareOperation(operation);
\r
360 headers = yangUtils.prepareHeaders(preparedRequestData);
\r
362 requestWorkingCallback();
\r
364 YangUtilsRestangular.one('restconf').customOperation(operation.toLowerCase(), reqString, null, headers, preparedRequestData).then(
\r
366 if(operation === 'REMOVE'){
\r
367 $scope.node.clear();
\r
371 $scope.node.clear();
\r
372 var props = Object.getOwnPropertyNames(data);
\r
374 props.forEach(function(p) { //fill each property - needed for root mountpoint node, in other cases there should be only one property anyway
\r
375 $scope.node.fill(p, data[p]);
\r
377 $scope.node.expanded = true;
\r
380 requestSuccessCallback();
\r
381 //TODO after first GET we have set $scope.node with data so build from the top of this function return requestData
\r
382 if(operation === 'GET'){
\r
385 $scope.$broadcast('YUI_ADD_TO_HISTORY', 'success', data, preparedRequestData, operation, requestPath);
\r
387 if ( angular.isFunction(callback) ) {
\r
391 if($scope.previewVisible === true){
\r
395 }, function(resp) {
\r
398 if(resp.data && resp.data.errors && resp.data.errors.error && resp.data.errors.error.length) {
\r
399 errorMsg = ': ' + resp.data.errors.error.map(function(e) {
\r
400 return e['error-message'];
\r
404 requestErrorCallback(errorMsg, resp);
\r
406 //TODO after first GET we have set $scope.node with data so build from the top of this function return requestData
\r
407 if(operation === 'GET'){
\r
410 $scope.$broadcast('YUI_ADD_TO_HISTORY', 'error', resp.data, preparedRequestData, operation, requestPath);
\r
412 console.info('error sending request to',$scope.selSubApi.buildApiRequestString(),'reqString',reqString,'got',resp.status,'data',resp.data);
\r
417 $scope.executeCustFunctionality = function(custFunct) {
\r
418 custFunct.runCallback($scope);
\r
419 $scope.selCustFunct = custFunct;
\r
422 $scope.fillNodeData = function(pathElem, identifier) {
\r
423 if($scope.selSubApi && $scope.selSubApi.storage === 'config' &&
\r
424 $scope.selSubApi.pathArray.indexOf(pathElem) === ($scope.selSubApi.pathArray.length - 1)) {
\r
425 pathUtils.fillListNode($scope.node, identifier.label, identifier.value);
\r
429 $scope.showPreview = function() {
\r
430 $scope.previewVisible = true;
\r
431 $scope.buildPreview();
\r
434 $scope.hidePreview = function() {
\r
435 $scope.previewVisible = false;
\r
438 $scope.copyReqPathToClipboard = function(req){
\r
439 var reqPath = req ? req.api.parent.basePath : $scope.selApi.basePath;
\r
441 reqPath += req ? req.parametrizedPath ? $scope.parameterizeData(req.parametrizedPath) : req.api.buildApiRequestString() : $scope.selSubApi.buildApiRequestString();
\r
446 $scope.fallback = function(path) {
\r
447 window.prompt($filter('translate')('YANGUI_CLIPBOARD_ALERT_MSG'), path);
\r
450 $scope.buildRoot = function() {
\r
451 $scope.node.buildRequest(reqBuilder, {}, $scope.node.module);
\r
454 $scope.changePathInPreview = function() {
\r
458 $scope.fillApiAndData = function(req, dataForView, fromSetCustApi) {
\r
459 var path = req.parametrizedPath ? req.parametrizedPath : req.path,
\r
460 rdata = req.receivedData,
\r
461 sdata = dataForView ? parsingJson.parseJson(dataForView) : req.sentData;
\r
464 $scope.fillApi(path, fromSetCustApi);
\r
466 if($scope.node && (rdata || sdata)) {
\r
468 $scope.fillApiData(rdata);
\r
472 $scope.fillApiData(sdata);
\r
477 $scope.selectedOperation = req.method;
\r
480 $scope.fillStandardApi = function(searchPath, fillPath, fromSetCustApi) {
\r
481 fillPath = fillPath || searchPath;
\r
483 var moduleNew = pathUtils.getModuleNameFromPath(searchPath),
\r
484 moduleOld = $scope.selSubApi && $scope.selSubApi.pathArray.length > 1 ? $scope.selSubApi.pathArray[1].module : null;
\r
486 if((fromSetCustApi && searchPath.indexOf(mountPrefix) === -1 && $scope.selCustFunct && $scope.selCustFunct.label === 'YANGUI_CUST_MOUNT_POINTS') ||
\r
487 (fromSetCustApi && searchPath.indexOf(mountPrefix) !== -1 && $scope.selCustFunct && $scope.selCustFunct.label === 'YANGUI_CUST_MOUNT_POINTS' && moduleNew !== moduleOld)){
\r
488 $scope.unsetCustomFunctionality();
\r
491 var apiIndexes = fromSetCustApi ? pathUtils.searchNodeByPath(searchPath, $scope.treeApis, $scope.treeRows) : pathUtils.searchNodeByPath(mountPointsConnector.alterMpPath(searchPath), $scope.treeApis, $scope.treeRows);
\r
494 $scope.setApiNode(apiIndexes.indexApi, apiIndexes.indexSubApi);
\r
495 if($scope.selSubApi) {
\r
496 pathUtils.fillPath($scope.selSubApi.pathArray, fillPath);
\r
501 $scope.fillApi = function(path, fromSetCustApi) {
\r
502 var parameterizedPath = $scope.parameterizeData(path);
\r
503 fillPath = parameterizedPath;
\r
505 if(parameterizedPath.indexOf(mountPrefix) !== -1) {
\r
506 fillPath = parameterizedPath.replace('restconf/config','restconf/operational');
\r
509 $scope.fillStandardApi(fillPath, null, fromSetCustApi);
\r
511 if(path.indexOf(mountPrefix) !== -1 && $scope.selSubApi) {
\r
512 $scope.selSubApi.pathArray = $scope.removeMountPointPath($scope.selSubApi.pathArray);
\r
515 $scope.mpSynchronizer.waitFor(function () {
\r
516 $scope.fillMPApi(parameterizedPath);
\r
521 $scope.selectMP = function() {
\r
522 var mpCF = custFunctFact.getMPCustFunctionality($scope.selSubApi.custFunct);
\r
524 $scope.executeCustFunctionality(mpCF);
\r
526 console.warn('Mountpoint custom functionality for api', $scope.selSubApi.buildApiRequestString(), ' is not set');
\r
530 $scope.fillMPApi = function(path) {
\r
531 var mpPath = mountPointsConnector.alterMpPath(path),
\r
532 apiIndexes = pathUtils.searchNodeByPath(mpPath, $scope.treeApis, $scope.treeRows);
\r
534 $scope.setApiNode(apiIndexes.indexApi, apiIndexes.indexSubApi);
\r
535 if($scope.selSubApi) {
\r
536 pathUtils.fillPath($scope.selSubApi.pathArray, path);
\r
541 $scope.fillApiData = function(data){
\r
542 var parametrizedData = $scope.parameterizeData(data),
\r
545 obj = typeof parametrizedData === "object" ? parametrizedData : parsingJson.parseJson(parametrizedData);
\r
547 if (obj !== null && typeof obj === "object") {
\r
548 var p = Object.keys(obj)[0];
\r
549 $scope.node.fill(p, obj[p]);
\r
553 $scope.show_add_data_popup = function(){
\r
554 $scope.popupData.show = true;
\r
557 $scope.close_popup = function(popObj){
\r
558 popObj.show = false;
\r
561 $scope.tabs = function(event, index){
\r
562 var tabDom = $(event.target).closest('.tabs');
\r
564 tabDom.find(' > .tab-content').children('.tab-pane')
\r
565 .removeClass('active')
\r
566 .eq(index).addClass('active');
\r
568 tabDom.find('> .nav-tabs').children('li')
\r
569 .removeClass('btn-selected')
\r
570 .eq(index).addClass('btn-selected');
\r
573 $scope.initMp = function(mountPointStructure, mountPointTreeApis, mountPointApis, augmentations){
\r
574 dataBackuper.storeFromScope(['treeApis', 'treeRows', 'apis', 'node', 'selApi', 'selSubApi', 'augmentations'], $scope);
\r
575 $scope.filterRootNode = null;
\r
576 $scope.node = null;
\r
577 $scope.treeApis = mountPointTreeApis;
\r
578 $scope.apis = mountPointApis;
\r
579 $scope.processingModulesSuccessCallback();
\r
580 $scope.augmentations = augmentations;
\r
581 $scope.$broadcast('REFRESH_HISTORY_REQUEST_APIS');
\r
584 $scope.showModalRequestWin = function(){
\r
585 $scope.$broadcast('LOAD_REQ_DATA');
\r
588 $scope.$on('SET_SCOPE_TREE_ROWS', function(e, rows){
\r
589 $scope.treeRows = rows;
\r
593 loadApis: loadApis,
\r
594 processingModulesErrorCallback: $scope.processingModulesErrorCallback,
\r
595 requestErrorCallback: requestErrorCallback,
\r
596 requestSuccessCallback: requestSuccessCallback,
\r
597 requestWorkingCallback: requestWorkingCallback,
\r
598 processingModulesCallback: processingModulesCallback,
\r
599 processingModulesSuccessCallback: $scope.processingModulesSuccessCallback
\r
602 $scope.loadController();
\r
630 yangui.register.filter('onlyConfigStmts', function(nodeUtils){
\r
631 return function(nodes){
\r
634 nodes = nodes.filter(function(n){
\r
635 return nodeUtils.isOnlyOperationalNode(n);
\r