1/**
2 * API utilities service
3 *
4 * @module app/common/services/api-utils
5 * @exports APIUtils
6 * @name APIUtils
7 * @version 0.0.1
8 */
9
10window.angular && (function (angular) {
11    'use strict';
12    angular
13        .module('app.common.services')
14        .factory('APIUtils', ['$http', 'Constants', '$q', 'dataService',function($http, Constants, $q, DataService){
15          var getScaledValue = function(value, scale){
16            scale = scale + "";
17            scale = parseInt(scale, 10);
18            var power = Math.abs(parseInt(scale,10));
19
20            if(scale > 0){
21              value = value * Math.pow(10, power);
22            }else if(scale < 0){
23              value = value / Math.pow(10, power);
24            }
25            return value;
26          };
27          var SERVICE = {
28              API_CREDENTIALS: Constants.API_CREDENTIALS,
29              API_RESPONSE: Constants.API_RESPONSE,
30              CHASSIS_POWER_STATE: Constants.CHASSIS_POWER_STATE,
31              HOST_STATE_TEXT: Constants.HOST_STATE,
32              HOST_STATE: Constants.HOST_STATE,
33              LED_STATE: Constants.LED_STATE,
34              LED_STATE_TEXT: Constants.LED_STATE_TEXT,
35              HOST_SESSION_STORAGE_KEY: Constants.API_CREDENTIALS.host_storage_key,
36              getChassisState: function(){
37                var deferred = $q.defer();
38                $http({
39                  method: 'GET',
40                  url: DataService.getHost() + "/xyz/openbmc_project/state/chassis0/attr/CurrentPowerState",
41                  headers: {
42                      'Accept': 'application/json',
43                      'Content-Type': 'application/json'
44                  },
45                  withCredentials: true
46                }).then(function(response){
47                      var json = JSON.stringify(response.data);
48                      var content = JSON.parse(json);
49                      deferred.resolve(content.data);
50                }, function(error){
51                  console.log(error);
52                  deferred.reject(error);
53                });
54                return deferred.promise;
55              },
56              getHostState: function(){
57                var deferred = $q.defer();
58                $http({
59                  method: 'GET',
60                  url: DataService.getHost() + "/xyz/openbmc_project/state/host0/attr/CurrentHostState",
61                  headers: {
62                      'Accept': 'application/json',
63                      'Content-Type': 'application/json'
64                  },
65                  withCredentials: true
66                }).then(function(response){
67                      var json = JSON.stringify(response.data);
68                      var content = JSON.parse(json);
69                      deferred.resolve(content.data);
70                }, function(error){
71                  console.log(error);
72                  deferred.reject(error);
73                });
74                return deferred.promise;
75              },
76              getNetworkInfo: function(){
77                var deferred = $q.defer();
78                $http({
79                  method: 'GET',
80                  url: DataService.getHost() + "/xyz/openbmc_project/network/enumerate",
81                  headers: {
82                      'Accept': 'application/json',
83                      'Content-Type': 'application/json'
84                  },
85                  withCredentials: true
86                }).then(function(response){
87                    var json = JSON.stringify(response.data);
88                    var content = JSON.parse(json);
89                    var hostname = "";
90                    var macAddress = "";
91
92                    function parseNetworkData(content){
93                      var data = {
94                        interface_ids: [],
95                        interfaces: {
96                        }
97                      };
98                      var interfaceId = '', keyParts = [], interfaceHash = '', interfaceType = '';
99                      for(var key in content.data){
100                        if(key.match(/network\/eth\d+$/ig)){
101                          interfaceId = key.split("/").pop();
102                          if(data.interface_ids.indexOf(interfaceId) == -1){
103                            data.interface_ids.push(interfaceId);
104                            data.interfaces[interfaceId] = {
105                              interfaceIname: '',
106                              domainName:'',
107                              MACAddress:'',
108                              Nameservers: [],
109                              DHCPEnabled: 0,
110                              ipv4:
111                                {
112                                 ids: [],
113                                 values: []
114                                },
115                              ipv6:
116                                {
117                                 ids: [],
118                                 values: []
119                                }
120                            };
121                            data.interfaces[interfaceId].MACAddress = content.data[key].MACAddress;
122                            data.interfaces[interfaceId].DomainName = content.data[key].DomainName.join(" ");
123                            data.interfaces[interfaceId].Nameservers = content.data[key].Nameservers;
124                            data.interfaces[interfaceId].DHCPEnabled = content.data[key].DHCPEnabled;
125                          }
126                        }else if(key.match(/network\/eth\d+\/ipv[4|6]\/[a-z0-9]+$/ig)){
127                          keyParts = key.split("/");
128                          interfaceHash = keyParts.pop();
129                          interfaceType = keyParts.pop();
130                          interfaceId = keyParts.pop();
131
132                          if(data.interfaces[interfaceId][interfaceType].ids.indexOf(interfaceHash) == -1){
133                            data.interfaces[interfaceId][interfaceType].ids.push(interfaceHash);
134                            data.interfaces[interfaceId][interfaceType].values.push(content.data[key]);
135                          }
136                        }
137                      }
138                      return data;
139                    }
140
141                    if(content.data.hasOwnProperty('/xyz/openbmc_project/network/config') &&
142                      content.data['/xyz/openbmc_project/network/config'].hasOwnProperty('HostName')
143                      ){
144                      hostname = content.data['/xyz/openbmc_project/network/config'].HostName;
145                    }
146
147                    if(content.data.hasOwnProperty('/xyz/openbmc_project/network/eth0') &&
148                      content.data['/xyz/openbmc_project/network/eth0'].hasOwnProperty('MACAddress')
149                      ){
150                      macAddress = content.data['/xyz/openbmc_project/network/eth0'].MACAddress;
151                    }
152
153                    deferred.resolve({
154                      data: content.data,
155                      hostname: hostname,
156                      mac_address: macAddress,
157                      formatted_data: parseNetworkData(content)
158                    });
159                }, function(error){
160                  console.log(error);
161                  deferred.reject(error);
162                });
163                return deferred.promise;
164              },
165              getLEDState: function(){
166                var deferred = $q.defer();
167                $http({
168                  method: 'GET',
169                  url: DataService.getHost() + "/xyz/openbmc_project/led/groups/enclosure_identify",
170                  headers: {
171                      'Accept': 'application/json',
172                      'Content-Type': 'application/json'
173                  },
174                  withCredentials: true
175                }).then(function(response){
176                    var json = JSON.stringify(response.data);
177                    var content = JSON.parse(json);
178                    deferred.resolve(content.data.Asserted);
179                }, function(error){
180                  console.log(error);
181                  deferred.reject(error);
182                });
183                return deferred.promise;
184              },
185              login: function(username, password, callback){
186                $http({
187                  method: 'POST',
188                  url: DataService.getHost() + "/login",
189                  headers: {
190                      'Accept': 'application/json',
191                      'Content-Type': 'application/json'
192                  },
193                  withCredentials: true,
194                  data: JSON.stringify({"data": [username, password]})
195                }).then(function(response){
196                  if(callback){
197                      callback(response.data);
198                  }
199                }, function(error){
200                  if(callback){
201                      if(error && error.status && error.status == 'error'){
202                        callback(error);
203                      }else{
204                        callback(error, true);
205                      }
206                  }
207                  console.log(error);
208                });
209              },
210              testPassword: function(username, password){
211                // Calls /login without the current session to verify the given password is correct
212                // ignore the interceptor logout on a bad password
213                DataService.ignoreHttpError = true;
214                return $http({
215                  method: 'POST',
216                  url: DataService.getHost() + "/login",
217                  headers: {
218                    'Accept': 'application/json',
219                    'Content-Type': 'application/json'
220                  },
221                  withCredentials: false,
222                  data: JSON.stringify({"data": [username, password]})
223                }).then(function(response){
224                  return response.data;
225                });
226              },
227              logout: function(callback){
228                $http({
229                  method: 'POST',
230                  url: DataService.getHost() + "/logout",
231                  headers: {
232                      'Accept': 'application/json',
233                      'Content-Type': 'application/json'
234                  },
235                  withCredentials: true,
236                  data: JSON.stringify({"data": []})
237                }).then(function(response){
238                  if(callback){
239                      callback(response.data);
240                  }
241                }, function(error){
242                  if(callback){
243                      callback(null, error);
244                  }
245                  console.log(error);
246                });
247              },
248              changePassword: function(user, newPassword){
249                var deferred = $q.defer();
250                $http({
251                  method: 'POST',
252                  url: DataService.getHost() + "/xyz/openbmc_project/user/" + user + "/action/SetPassword",
253                  headers: {
254                    'Accept': 'application/json',
255                    'Content-Type': 'application/json'
256                  },
257                  withCredentials: true,
258                  data: JSON.stringify({"data": [newPassword]}),
259                  responseType: 'arraybuffer'
260                }).then(function(response, status, headers){
261                  deferred.resolve({
262                    data: response,
263                    status: status,
264                    headers: headers
265                  });
266                }, function(error){
267                  console.log(error);
268                  deferred.reject(error);
269                });
270                return deferred.promise;
271              },
272              chassisPowerOn: function(callback){
273                $http({
274                  method: 'POST',
275                  url: DataService.getHost() + "/xyz/openbmc_project/state/host0",
276                  headers: {
277                      'Accept': 'application/json',
278                      'Content-Type': 'application/json'
279                  },
280                  withCredentials: true,
281                  data: JSON.stringify({"data": []})
282                }).then(function(response){
283                      var json = JSON.stringify(response.data);
284                      var content = JSON.parse(json);
285                      if(callback){
286                          return callback(content.data.CurrentPowerState);
287                      }
288                }, function(error){
289                  if(callback){
290                      callback(error);
291                  }else{
292                      console.log(error);
293                  }
294                });
295              },
296              chassisPowerOff: function(){
297                var deferred = $q.defer();
298                $http({
299                  method: 'PUT',
300                  url: DataService.getHost() + "/xyz/openbmc_project/state/chassis0/attr/RequestedPowerTransition",
301                  headers: {
302                      'Accept': 'application/json',
303                      'Content-Type': 'application/json'
304                  },
305                  withCredentials: true,
306                  data: JSON.stringify({"data": "xyz.openbmc_project.State.Chassis.Transition.Off"})
307                }).then(function(response){
308                      var json = JSON.stringify(response.data);
309                      var content = JSON.parse(json);
310                      deferred.resolve(content.status);
311                }, function(error){
312                  console.log(error);
313                  deferred.reject(error);
314                });
315                return deferred.promise;
316              },
317              setLEDState: function(state, callback){
318                $http({
319                  method: 'PUT',
320                  url: DataService.getHost() + "/xyz/openbmc_project/led/groups/enclosure_identify/attr/Asserted",
321                  headers: {
322                      'Accept': 'application/json',
323                      'Content-Type': 'application/json'
324                  },
325                  withCredentials: true,
326                  data: JSON.stringify({"data": state})
327                }).then(function(response){
328                      var json = JSON.stringify(response.data);
329                      var content = JSON.parse(json);
330                      if(callback){
331                          return callback(content.status);
332                      }
333                }, function(error){
334                  if(callback){
335                      callback(error);
336                  }else{
337                      console.log(error);
338                  }
339                });
340              },
341              bmcReboot: function(callback){
342                $http({
343                  method: 'PUT',
344                  url: DataService.getHost() + "/xyz/openbmc_project/state/bmc0/attr/RequestedBmcTransition",
345                  headers: {
346                      'Accept': 'application/json',
347                      'Content-Type': 'application/json'
348                  },
349                  withCredentials: true,
350                  data: JSON.stringify({"data": "xyz.openbmc_project.State.BMC.Transition.Reboot"})
351                }).then(function(response){
352                      var json = JSON.stringify(response.data);
353                      var content = JSON.parse(json);
354                      if(callback){
355                          return callback(content.status);
356                      }
357                }, function(error){
358                  if(callback){
359                      callback(error);
360                  }else{
361                      console.log(error);
362                  }
363                });
364              },
365              hostPowerOn: function(){
366                var deferred = $q.defer();
367                $http({
368                  method: 'PUT',
369                  url: DataService.getHost() + "/xyz/openbmc_project/state/host0/attr/RequestedHostTransition",
370                  headers: {
371                      'Accept': 'application/json',
372                      'Content-Type': 'application/json'
373                  },
374                  withCredentials: true,
375                  data: JSON.stringify({"data": "xyz.openbmc_project.State.Host.Transition.On"})
376                }).then(function(response){
377                      var json = JSON.stringify(response.data);
378                      var content = JSON.parse(json);
379                      deferred.resolve(content.status);
380                }, function(error){
381                  console.log(error);
382                  deferred.reject(error);
383                });
384                return deferred.promise;
385              },
386              hostPowerOff: function(){
387                var deferred = $q.defer();
388                $http({
389                  method: 'PUT',
390                  url: DataService.getHost() + "/xyz/openbmc_project/state/host0/attr/RequestedHostTransition",
391                  headers: {
392                      'Accept': 'application/json',
393                      'Content-Type': 'application/json'
394                  },
395                  withCredentials: true,
396                  data: JSON.stringify({"data": "xyz.openbmc_project.State.Host.Transition.Off"})
397                }).then(function(response){
398                      var json = JSON.stringify(response.data);
399                      var content = JSON.parse(json);
400                      deferred.resolve(content.status);
401                }, function(error){
402                  console.log(error);
403                  deferred.reject(error);
404                });
405                return deferred.promise;
406              },
407              hostReboot: function(){
408                var deferred = $q.defer();
409                $http({
410                  method: 'PUT',
411                  url: DataService.getHost() + "/xyz/openbmc_project/state/host0/attr/RequestedHostTransition",
412                  headers: {
413                      'Accept': 'application/json',
414                      'Content-Type': 'application/json'
415                  },
416                  withCredentials: true,
417                  data: JSON.stringify({"data": "xyz.openbmc_project.State.Host.Transition.Reboot"})
418                }).then(function(response){
419                      var json = JSON.stringify(response.data);
420                      var content = JSON.parse(json);
421                      deferred.resolve(content.status);
422                }, function(error){
423                  console.log(error);
424                  deferred.reject(error);
425                });
426
427                return deferred.promise;
428              },
429              hostShutdown: function(callback){
430                $http({
431                  method: 'POST',
432                  url: DataService.getHost() + "/xyz/openbmc_project/state/host0",
433                  headers: {
434                      'Accept': 'application/json',
435                      'Content-Type': 'application/json'
436                  },
437                  withCredentials: true,
438                  data: JSON.stringify({"data": []})
439                }).then(function(response){
440                      var json = JSON.stringify(response.data);
441                      var content = JSON.parse(json);
442                      if(callback){
443                          return callback(content);
444                      }
445                }, function(error){
446                  if(callback){
447                      callback(error);
448                  }else{
449                      console.log(error);
450                  }
451                });
452              },
453              getLogs: function(){
454                var deferred = $q.defer();
455                $http({
456                  method: 'GET',
457                  url: DataService.getHost() + "/xyz/openbmc_project/logging/enumerate",
458                  headers: {
459                      'Accept': 'application/json',
460                      'Content-Type': 'application/json'
461                  },
462                  withCredentials: true
463                }).then(function(response){
464                      var json = JSON.stringify(response.data);
465                      var content = JSON.parse(json);
466                      var dataClone = JSON.parse(JSON.stringify(content.data));
467                      var data = [];
468                      var severityCode = '';
469                      var priority = '';
470                      var health = '';
471                      var relatedItems = [];
472
473                      for(var key in content.data){
474                        if(content.data.hasOwnProperty(key) && content.data[key].hasOwnProperty('Id')){
475                          var severityFlags = {low: false, medium: false, high: false};
476                          var healthFlags = {critical: false, warning: false, good: false};
477                          severityCode = content.data[key].Severity.split(".").pop();
478                          priority = Constants.SEVERITY_TO_PRIORITY_MAP[severityCode];
479                          severityFlags[priority.toLowerCase()] = true;
480                          health = Constants.SEVERITY_TO_HEALTH_MAP[severityCode];
481                          healthFlags[health.toLowerCase()] = true;
482                          relatedItems = [];
483                          content.data[key].associations.forEach(function(item){
484                            relatedItems.push(item[2]);
485                          });
486
487                          data.push(Object.assign({
488                            path: key,
489                            copied: false,
490                            priority: priority,
491                            severity_code: severityCode,
492                            severity_flags: severityFlags,
493                            health_flags: healthFlags,
494                            additional_data: content.data[key].AdditionalData.join("\n"),
495                            type: content.data[key].Message,
496                            selected: false,
497                            search_text: ("#" + content.data[key].Id + " " + severityCode + " " + content.data[key].Severity + " " + content.data[key].AdditionalData.join(" ")).toLowerCase(),
498                            meta: false,
499                            confirm: false,
500                            related_items: relatedItems,
501                            data: {key: key, value: content.data[key]}
502                          }, content.data[key]));
503                        }
504                      }
505                      deferred.resolve({data: data, original: dataClone});
506                }, function(error){
507                  console.log(error);
508                  deferred.reject(error);
509                });
510
511                return deferred.promise;
512              },
513              getAllSensorStatus: function(callback){
514                $http({
515                  method: 'GET',
516                  url: DataService.getHost() + "/xyz/openbmc_project/sensors/enumerate",
517                  headers: {
518                      'Accept': 'application/json',
519                      'Content-Type': 'application/json'
520                  },
521                  withCredentials: true
522                }).then(function(response){
523                      var json = JSON.stringify(response.data);
524                      var content = JSON.parse(json);
525                      var dataClone = JSON.parse(JSON.stringify(content.data));
526                      var sensorData = [];
527                      var severity = {};
528                      var title = "";
529                      var tempKeyParts = [];
530                      var order = 0;
531                      var customOrder = 0;
532
533                      function getSensorStatus(reading){
534                        var severityFlags = {critical: false, warning: false, normal: false}, severityText = '', order = 0;
535
536                        if(reading.hasOwnProperty('CriticalLow') &&
537                          reading.Value < reading.CriticalLow
538                          ){
539                          severityFlags.critical = true;
540                          severityText = 'critical';
541                          order = 2;
542                        }else if(reading.hasOwnProperty('CriticalHigh') &&
543                          reading.Value > reading.CriticalHigh
544                          ){
545                          severityFlags.critical = true;
546                          severityText = 'critical';
547                          order = 2;
548                        }else if(reading.hasOwnProperty('CriticalLow') &&
549                          reading.hasOwnProperty('WarningLow') &&
550                          reading.Value >= reading.CriticalLow && reading.Value <= reading.WarningLow){
551                          severityFlags.warning = true;
552                          severityText = 'warning';
553                          order = 1;
554                        }else if(reading.hasOwnProperty('WarningHigh') &&
555                          reading.hasOwnProperty('CriticalHigh') &&
556                          reading.Value >= reading.WarningHigh && reading.Value <= reading.CriticalHigh){
557                          severityFlags.warning = true;
558                          severityText = 'warning';
559                          order = 1;
560                        }else{
561                          severityFlags.normal = true;
562                          severityText = 'normal';
563                        }
564                        return { flags: severityFlags, severityText: severityText, order: order};
565                      }
566
567                      for(var key in content.data){
568                        if(content.data.hasOwnProperty(key) && content.data[key].hasOwnProperty('Unit')){
569
570                          severity = getSensorStatus(content.data[key]);
571
572                          if(!content.data[key].hasOwnProperty('CriticalLow')){
573                            content.data[key].CriticalLow = "--";
574                            content.data[key].CriticalHigh = "--";
575                          }
576
577                          if(!content.data[key].hasOwnProperty('WarningLow')){
578                            content.data[key].WarningLow = "--";
579                            content.data[key].WarningHigh = "--";
580                          }
581
582                          tempKeyParts = key.split("/");
583                          title = tempKeyParts.pop();
584                          title = tempKeyParts.pop() + '_' + title;
585                          title = title.split("_").map(function(item){
586                             return item.toLowerCase().charAt(0).toUpperCase() + item.slice(1);
587                          }).reduce(function(prev, el){
588                            return prev + " " + el;
589                          });
590
591                          content.data[key].Value = getScaledValue(content.data[key].Value, content.data[key].Scale);
592                          content.data[key].CriticalLow = getScaledValue(content.data[key].CriticalLow, content.data[key].Scale);
593                          content.data[key].CriticalHigh = getScaledValue(content.data[key].CriticalHigh, content.data[key].Scale);
594                          content.data[key].WarningLow = getScaledValue(content.data[key].WarningLow, content.data[key].Scale);
595                          content.data[key].WarningHigh = getScaledValue(content.data[key].WarningHigh, content.data[key].Scale);
596                          if(Constants.SENSOR_SORT_ORDER.indexOf(content.data[key].Unit) > -1){
597                            customOrder = Constants.SENSOR_SORT_ORDER.indexOf(content.data[key].Unit);
598                          }else{
599                            customOrder = Constants.SENSOR_SORT_ORDER_DEFAULT;
600                          }
601
602                          sensorData.push(Object.assign({
603                            path: key,
604                            selected: false,
605                            confirm: false,
606                            copied: false,
607                            title: title,
608                            unit: Constants.SENSOR_UNIT_MAP[content.data[key].Unit],
609                            severity_flags: severity.flags,
610                            status: severity.severityText,
611                            order: severity.order,
612                            custom_order: customOrder,
613                            search_text: (title + " " + content.data[key].Value + " " +
614                               Constants.SENSOR_UNIT_MAP[content.data[key].Unit] + " " +
615                               severity.severityText + " " +
616                               content.data[key].CriticalLow + " " +
617                               content.data[key].CriticalHigh + " " +
618                               content.data[key].WarningLow + " " +
619                               content.data[key].WarningHigh + " "
620                               ).toLowerCase(),
621                            original_data: {key: key, value: content.data[key]}
622                          }, content.data[key]));
623                        }
624                      }
625
626                      callback(sensorData, dataClone);
627                }, function(error){
628                  console.log(error);
629                });
630              },
631              getActivation: function(imageId){
632                return $http({
633                  method: 'GET',
634                  url: DataService.getHost() + "/xyz/openbmc_project/software/" + imageId + "/attr/Activation",
635                  headers: {
636                    'Accept': 'application/json',
637                    'Content-Type': 'application/json'
638                  },
639                  withCredentials: true
640                }).then(function(response){
641                  return response.data;
642                });
643              },
644              getFirmwares: function(){
645                var deferred = $q.defer();
646                $http({
647                  method: 'GET',
648                  url: DataService.getHost() + "/xyz/openbmc_project/software/enumerate",
649                  headers: {
650                      'Accept': 'application/json',
651                      'Content-Type': 'application/json'
652                  },
653                  withCredentials: true
654                }).then(function(response){
655                      var json = JSON.stringify(response.data);
656                      var content = JSON.parse(json);
657                      var data = [];
658                      var activationStatus = "";
659                      var isExtended = false;
660                      var bmcActiveVersion = "";
661                      var hostActiveVersion = "";
662                      var imageType = "";
663                      var extendedVersions = [];
664                      var functionalImages = [];
665
666                      function getFormatedExtendedVersions(extendedVersion){
667                        var versions = [];
668                        extendedVersion = extendedVersion.split(",");
669
670                        extendedVersion.forEach(function(item){
671                          var parts = item.split("-");
672                          var numberIndex = 0;
673                          for(var i = 0; i < parts.length; i++){
674                            if(/[0-9]/.test(parts[i])){
675                              numberIndex = i;
676                              break;
677                            }
678                          }
679                          var titlePart = parts.splice(0, numberIndex);
680                          titlePart = titlePart.join("");
681                          titlePart = titlePart[0].toUpperCase() + titlePart.substr(1, titlePart.length);
682                          var versionPart = parts.join("-");
683                          versions.push({
684                            title: titlePart,
685                            version: versionPart
686                          });
687                        });
688
689                        return versions;
690                      }
691
692                      // Get the list of functional images so we can compare
693                      // later if an image is functional
694                      if (content.data[Constants.FIRMWARE.FUNCTIONAL_OBJPATH])
695                      {
696                        functionalImages = content.data[Constants.FIRMWARE.FUNCTIONAL_OBJPATH].endpoints;
697                      }
698                      for(var key in content.data){
699                        if(content.data.hasOwnProperty(key) && content.data[key].hasOwnProperty('Version')){
700                          // If the image is "Functional" use that for the
701                          // activation status, else use the value of "Activation"
702                          // github.com/openbmc/phosphor-dbus-interfaces/blob/master/xyz/openbmc_project/Software/Activation.interface.yaml
703                          activationStatus = content.data[key].Activation.split(".").pop();
704                          if (functionalImages.includes(key))
705                          {
706                            activationStatus = "Functional";
707                          }
708
709                          imageType = content.data[key].Purpose.split(".").pop();
710                          isExtended = content.data[key].hasOwnProperty('ExtendedVersion') && content.data[key].ExtendedVersion != "";
711                          if(isExtended){
712                            extendedVersions = getFormatedExtendedVersions(content.data[key].ExtendedVersion);
713                          }
714                          data.push(Object.assign({
715                            path: key,
716                            activationStatus: activationStatus,
717                            imageId: key.split("/").pop(),
718                            imageType: imageType,
719                            isExtended: isExtended,
720                            extended: {
721                              show: false,
722                              versions: extendedVersions
723                            },
724                            data: {key: key, value: content.data[key]}
725                          }, content.data[key]));
726
727                          if(activationStatus == 'Functional' && imageType == 'BMC'){
728                            bmcActiveVersion = content.data[key].Version;
729                          }
730
731                          if(activationStatus == 'Functional' && imageType == 'Host'){
732                            hostActiveVersion = content.data[key].Version;
733                          }
734                        }
735                      }
736
737                      deferred.resolve({
738                          data: data,
739                          bmcActiveVersion: bmcActiveVersion,
740                          hostActiveVersion: hostActiveVersion
741                      });
742                }, function(error){
743                  console.log(error);
744                  deferred.reject(error);
745                });
746
747                return deferred.promise;
748              },
749              changePriority: function(imageId, priority){
750                var deferred = $q.defer();
751                $http({
752                  method: 'PUT',
753                  url: DataService.getHost() + "/xyz/openbmc_project/software/" + imageId + "/attr/Priority",
754                  headers: {
755                      'Accept': 'application/json',
756                      'Content-Type': 'application/json'
757                  },
758                  withCredentials: true,
759                  data: JSON.stringify({"data": priority})
760                }).then(function(response){
761                      var json = JSON.stringify(response.data);
762                      var content = JSON.parse(json);
763                      deferred.resolve(content);
764                }, function(error){
765                  console.log(error);
766                  deferred.reject(error);
767                });
768
769                return deferred.promise;
770              },
771              deleteImage: function(imageId){
772                var deferred = $q.defer();
773                $http({
774                  method: 'POST',
775                  url: DataService.getHost() + "/xyz/openbmc_project/software/" + imageId + "/action/Delete",
776                  headers: {
777                      'Accept': 'application/json',
778                      'Content-Type': 'application/json'
779                  },
780                  withCredentials: true,
781                  data: JSON.stringify({"data": []})
782                }).then(function(response){
783                      var json = JSON.stringify(response.data);
784                      var content = JSON.parse(json);
785                      deferred.resolve(content);
786                }, function(error){
787                  console.log(error);
788                  deferred.reject(error);
789                });
790
791                return deferred.promise;
792              },
793              activateImage: function(imageId){
794                var deferred = $q.defer();
795                $http({
796                  method: 'PUT',
797                  url: DataService.getHost() + "/xyz/openbmc_project/software/" + imageId + "/attr/RequestedActivation",
798                  headers: {
799                      'Accept': 'application/json',
800                      'Content-Type': 'application/json'
801                  },
802                  withCredentials: true,
803                  data: JSON.stringify({"data": Constants.FIRMWARE.ACTIVATE_FIRMWARE})
804                }).then(function(response){
805                      var json = JSON.stringify(response.data);
806                      var content = JSON.parse(json);
807                      deferred.resolve(content);
808                }, function(error){
809                  console.log(error);
810                  deferred.reject(error);
811                });
812
813                return deferred.promise;
814              },
815              uploadImage: function(file){
816                return $http({
817                  method: 'POST',
818                  timeout: 5 * 60 * 1000,
819                  url: DataService.getHost() + "/upload/image",
820                  headers: {
821                    'Content-Type': 'application/octet-stream'
822                  },
823                  withCredentials: true,
824                  data: file
825                }).then(function(response){
826                  return response.data;
827                });
828              },
829              downloadImage: function(host, filename){
830                return $http({
831                  method: 'POST',
832                  url: DataService.getHost() + "/xyz/openbmc_project/software/action/DownloadViaTFTP",
833                  headers: {
834                    'Accept': 'application/json',
835                    'Content-Type': 'application/json'
836                  },
837                  withCredentials: true,
838                  data: JSON.stringify({"data": [filename, host]}),
839                  responseType: 'arraybuffer'
840                }).then(function(response){
841                  return response.data;
842                });
843              },
844              getBMCEthernetInfo: function(){
845                var deferred = $q.defer();
846                $http({
847                  method: 'GET',
848                  url: DataService.getHost() + "/xyz/openbmc_project/inventory/system/chassis/motherboard/boxelder/bmc/ethernet",
849                  headers: {
850                      'Accept': 'application/json',
851                      'Content-Type': 'application/json'
852                  },
853                  withCredentials: true
854                }).then(function(response){
855                    var json = JSON.stringify(response.data);
856                    var content = JSON.parse(json);
857                    deferred.resolve(content.data);
858                }, function(error){
859                  console.log(error);
860                  deferred.reject(error);
861                });
862
863                return deferred.promise;
864              },
865              getBMCInfo: function(callback){
866                var deferred = $q.defer();
867                $http({
868                  method: 'GET',
869                  url: DataService.getHost() + "/xyz/openbmc_project/inventory/system/chassis/motherboard/boxelder/bmc",
870                  headers: {
871                      'Accept': 'application/json',
872                      'Content-Type': 'application/json'
873                  },
874                  withCredentials: true
875                }).then(function(response){
876                    var json = JSON.stringify(response.data);
877                    var content = JSON.parse(json);
878                    deferred.resolve(content.data);
879                }, function(error){
880                  console.log(error);
881                  deferred.reject(error);
882                });
883                return deferred.promise;
884              },
885              getServerInfo: function(){
886                return $http({
887                  method: 'GET',
888                  url: DataService.getHost() + "/xyz/openbmc_project/inventory/system",
889                  headers: {
890                    'Accept': 'application/json',
891                    'Content-Type': 'application/json'
892                  },
893                  withCredentials: true
894                }).then(function(response){
895                  return response.data;
896                });
897              },
898              getHardwares: function(callback){
899                $http({
900                  method: 'GET',
901                  url: DataService.getHost() + "/xyz/openbmc_project/inventory/enumerate",
902                  headers: {
903                      'Accept': 'application/json',
904                      'Content-Type': 'application/json'
905                  },
906                  withCredentials: true
907                }).then(function(response){
908                      var json = JSON.stringify(response.data);
909                      var content = JSON.parse(json);
910                      var hardwareData = [];
911                      var keyIndexMap = {};
912                      var title = "";
913                      var data = [];
914                      var searchText = "";
915                      var componentIndex = -1;
916                      var tempParts = [];
917
918
919                      function isSubComponent(key){
920
921                        for(var i = 0; i < Constants.HARDWARE.parent_components.length; i++){
922                          if(key.split(Constants.HARDWARE.parent_components[i]).length == 2) return true;
923                        }
924
925                        return false;
926                      }
927
928                      function titlelize(title){
929                        title = title.replace(/([A-Z0-9]+)/g, " $1").replace(/^\s+/, "");
930                        for(var i = 0; i < Constants.HARDWARE.uppercase_titles.length; i++){
931                          if(title.toLowerCase().indexOf((Constants.HARDWARE.uppercase_titles[i] + " ")) > -1){
932                            return title.toUpperCase();
933                          }
934                        }
935
936                        return title;
937                      }
938
939                      function camelcaseToLabel(obj){
940                        var transformed = [], label = "", value = "";
941                        for(var key in obj){
942                          label = key.replace(/([A-Z0-9]+)/g, " $1").replace(/^\s+/, "");
943                          if(obj[key] !== ""){
944                            value = obj[key];
945                            if(value == 1 || value == 0){
946                              value = (value == 1) ? 'Yes' : 'No';
947                            }
948                            transformed.push({key:label, value: value});
949                          }
950                        }
951
952                        return transformed;
953                      }
954
955                      function getSearchText(data){
956                        var searchText = "";
957                        for(var i = 0; i < data.length; i++){
958                          searchText += " " + data[i].key + " " + data[i].value;
959                        }
960
961                        return searchText;
962                      }
963
964                      for(var key in content.data){
965                        if(content.data.hasOwnProperty(key) &&
966                           key.indexOf(Constants.HARDWARE.component_key_filter) == 0){
967
968                          data = camelcaseToLabel(content.data[key]);
969                          searchText = getSearchText(data);
970                          title = key.split("/").pop();
971
972                          title = titlelize(title);
973
974                          if(!isSubComponent(key)){
975                              hardwareData.push(Object.assign({
976                                path: key,
977                                title: title,
978                                selected: false,
979                                expanded: false,
980                                search_text: title.toLowerCase() + " " + searchText.toLowerCase(),
981                                sub_components: [],
982                                original_data: {key: key, value: content.data[key]}
983                              }, {items: data}));
984
985                              keyIndexMap[key] = hardwareData.length - 1;
986                          }else{
987                            var tempParts = key.split("/");
988                            tempParts.pop();
989                            tempParts = tempParts.join("/");
990                            componentIndex = keyIndexMap[tempParts];
991                            data = content.data[key];
992                            data.title = title;
993                            hardwareData[componentIndex].sub_components.push(data);
994                            hardwareData[componentIndex].search_text += " " + title.toLowerCase();
995
996                            // Sort the subcomponents alphanumeric so they are displayed on the
997                            // inventory page in order (e.g. core 0, core 1, core 2, ... core 12, core 13)
998                            hardwareData[componentIndex].sub_components.sort(function (a, b) {
999                                return a.title.localeCompare(b.title, 'en', { numeric: true });
1000                            });
1001                          }
1002                      }
1003                    }
1004
1005                    if(callback){
1006                       callback(hardwareData, content.data);
1007                    }else{
1008                       return { data: hardwareData, original_data: content.data};
1009                    }
1010                });
1011              },
1012              deleteLogs: function(logs) {
1013                  var defer = $q.defer();
1014                  var promises = [];
1015
1016                  function finished(){
1017                      defer.resolve();
1018                  }
1019
1020                  logs.forEach(function(item){
1021                    promises.push($http({
1022                                      method: 'POST',
1023                                      url: DataService.getHost() + "/xyz/openbmc_project/logging/entry/"+item.Id+"/action/Delete",
1024                                      headers: {
1025                                          'Accept': 'application/json',
1026                                          'Content-Type': 'application/json'
1027                                      },
1028                                      withCredentials: true,
1029                                      data: JSON.stringify({"data": []})
1030                                 }));
1031                  });
1032
1033                  $q.all(promises).then(finished);
1034
1035                  return defer.promise;
1036              },
1037              resolveLogs: function(logs) {
1038                  var defer = $q.defer();
1039                  var promises = [];
1040
1041                  function finished(){
1042                      defer.resolve();
1043                  }
1044
1045                  logs.forEach(function(item){
1046                    promises.push($http({
1047                                      method: 'PUT',
1048                                      url: DataService.getHost() + "/xyz/openbmc_project/logging/entry/"+item.Id+"/attr/Resolved",
1049                                      headers: {
1050                                          'Accept': 'application/json',
1051                                          'Content-Type': 'application/json'
1052                                      },
1053                                      withCredentials: true,
1054                                      data: JSON.stringify({"data": "1"})
1055                                 }));
1056                  });
1057
1058                  $q.all(promises).then(finished);
1059
1060                  return defer.promise;
1061              },
1062              getPowerConsumption: function(){
1063                return $http({
1064                  method: 'GET',
1065                  url: DataService.getHost() + "/xyz/openbmc_project/sensors/power/total_power",
1066                  headers: {
1067                      'Accept': 'application/json',
1068                      'Content-Type': 'application/json'
1069                  },
1070                  withCredentials: true
1071                }).then(function(response){
1072                    var json = JSON.stringify(response.data);
1073                    var content = JSON.parse(json);
1074
1075                    return getScaledValue(content.data.Value,
1076                                          content.data.Scale) + ' ' +
1077                      Constants.POWER_CONSUMPTION_TEXT[content.data.Unit];
1078                }, function(error){
1079                  if ('Not Found' == error.statusText) {
1080                    return Constants.POWER_CONSUMPTION_TEXT.notavailable;
1081                  } else {
1082                    console.log(error);
1083                  }
1084                });
1085              },
1086              getPowerCap: function(){
1087                return $http({
1088                  method: 'GET',
1089                  url: DataService.getHost() + "/xyz/openbmc_project/control/host0/power_cap",
1090                  headers: {
1091                      'Accept': 'application/json',
1092                      'Content-Type': 'application/json'
1093                  },
1094                  withCredentials: true
1095                }).then(function(response){
1096                    var json = JSON.stringify(response.data);
1097                    var content = JSON.parse(json);
1098
1099                    return (false == content.data.PowerCapEnable) ?
1100                        Constants.POWER_CAP_TEXT.disabled :
1101                        content.data.PowerCap + ' ' + Constants.POWER_CAP_TEXT.unit;
1102                }, function(error){
1103                  console.log(error);
1104                });
1105              },
1106          };
1107          return SERVICE;
1108        }]);
1109
1110        })(window.angular);
1111