1/** 2 * API utilities service 3 * 4 * @module app/common/services/api-utils 5 * @exports APIUtils 6 * @name APIUtils 7 */ 8 9window.angular && (function(angular) { 10 'use strict'; 11 angular.module('app.common.services').factory('APIUtils', [ 12 '$http', 'Constants', '$q', 'dataService', 13 function($http, Constants, $q, DataService) { 14 var getScaledValue = function(value, scale) { 15 scale = scale + ''; 16 scale = parseInt(scale, 10); 17 var power = Math.abs(parseInt(scale, 10)); 18 19 if (scale > 0) { 20 value = value * Math.pow(10, power); 21 } else if (scale < 0) { 22 value = value / Math.pow(10, power); 23 } 24 return value; 25 }; 26 var SERVICE = { 27 API_CREDENTIALS: Constants.API_CREDENTIALS, 28 API_RESPONSE: Constants.API_RESPONSE, 29 CHASSIS_POWER_STATE: Constants.CHASSIS_POWER_STATE, 30 HOST_STATE_TEXT: Constants.HOST_STATE, 31 HOST_STATE: Constants.HOST_STATE, 32 LED_STATE: Constants.LED_STATE, 33 LED_STATE_TEXT: Constants.LED_STATE_TEXT, 34 HOST_SESSION_STORAGE_KEY: Constants.API_CREDENTIALS.host_storage_key, 35 getChassisState: function() { 36 var deferred = $q.defer(); 37 $http({ 38 method: 'GET', 39 url: DataService.getHost() + 40 '/xyz/openbmc_project/state/chassis0/attr/CurrentPowerState', 41 headers: { 42 'Accept': 'application/json', 43 'Content-Type': 'application/json' 44 }, 45 withCredentials: true 46 }) 47 .then( 48 function(response) { 49 var json = JSON.stringify(response.data); 50 var content = JSON.parse(json); 51 deferred.resolve(content.data); 52 }, 53 function(error) { 54 console.log(error); 55 deferred.reject(error); 56 }); 57 return deferred.promise; 58 }, 59 validIPV4IP: function(ip) { 60 // Checks for [0-255].[0-255].[0-255].[0-255] 61 return ip.match( 62 /\b(?:(?:25[0-5]|2[0-4][0-9]|[01]?[0-9][0-9]?)\.){3}(?:25[0-5]|2[0-4][0-9]|[01]?[0-9][0-9]?)\b/); 63 }, 64 getHostState: function() { 65 var deferred = $q.defer(); 66 $http({ 67 method: 'GET', 68 url: DataService.getHost() + 69 '/xyz/openbmc_project/state/host0/attr/CurrentHostState', 70 headers: { 71 'Accept': 'application/json', 72 'Content-Type': 'application/json' 73 }, 74 withCredentials: true 75 }) 76 .then( 77 function(response) { 78 var json = JSON.stringify(response.data); 79 var content = JSON.parse(json); 80 deferred.resolve(content.data); 81 }, 82 function(error) { 83 console.log(error); 84 deferred.reject(error); 85 }); 86 return deferred.promise; 87 }, 88 getNetworkInfo: function() { 89 var deferred = $q.defer(); 90 $http({ 91 method: 'GET', 92 url: DataService.getHost() + 93 '/xyz/openbmc_project/network/enumerate', 94 headers: { 95 'Accept': 'application/json', 96 'Content-Type': 'application/json' 97 }, 98 withCredentials: true 99 }) 100 .then( 101 function(response) { 102 var json = JSON.stringify(response.data); 103 var content = JSON.parse(json); 104 var hostname = ''; 105 var defaultgateway = ''; 106 var macAddress = ''; 107 108 function parseNetworkData(content) { 109 var data = { 110 interface_ids: [], 111 interfaces: {}, 112 ip_addresses: {ipv4: [], ipv6: []}, 113 }; 114 var interfaceId = '', keyParts = [], interfaceHash = '', 115 interfaceType = ''; 116 for (var key in content.data) { 117 if (key.match(/network\/eth\d+(_\d+)?$/ig)) { 118 interfaceId = key.split('/').pop(); 119 if (data.interface_ids.indexOf(interfaceId) == -1) { 120 data.interface_ids.push(interfaceId); 121 data.interfaces[interfaceId] = { 122 interfaceIname: '', 123 DomainName: '', 124 MACAddress: '', 125 Nameservers: [], 126 DHCPEnabled: 0, 127 ipv4: {ids: [], values: []}, 128 ipv6: {ids: [], values: []} 129 }; 130 data.interfaces[interfaceId].MACAddress = 131 content.data[key].MACAddress; 132 data.interfaces[interfaceId].DomainName = 133 content.data[key].DomainName.join(' '); 134 data.interfaces[interfaceId].Nameservers = 135 content.data[key].Nameservers; 136 data.interfaces[interfaceId].DHCPEnabled = 137 content.data[key].DHCPEnabled; 138 } 139 } else if ( 140 key.match( 141 /network\/eth\d+(_\d+)?\/ipv[4|6]\/[a-z0-9]+$/ig)) { 142 keyParts = key.split('/'); 143 interfaceHash = keyParts.pop(); 144 interfaceType = keyParts.pop(); 145 interfaceId = keyParts.pop(); 146 147 if (data.interfaces[interfaceId][interfaceType] 148 .ids.indexOf(interfaceHash) == -1) { 149 data.interfaces[interfaceId][interfaceType] 150 .ids.push(interfaceHash); 151 data.interfaces[interfaceId][interfaceType] 152 .values.push(content.data[key]); 153 data.ip_addresses[interfaceType].push( 154 content.data[key]['Address']); 155 } 156 } 157 } 158 return data; 159 } 160 161 if (content.data.hasOwnProperty( 162 '/xyz/openbmc_project/network/config')) { 163 if (content.data['/xyz/openbmc_project/network/config'] 164 .hasOwnProperty('HostName')) { 165 hostname = 166 content.data['/xyz/openbmc_project/network/config'] 167 .HostName; 168 } 169 if (content.data['/xyz/openbmc_project/network/config'] 170 .hasOwnProperty('DefaultGateway')) { 171 defaultgateway = 172 content.data['/xyz/openbmc_project/network/config'] 173 .DefaultGateway; 174 } 175 } 176 177 if (content.data.hasOwnProperty( 178 '/xyz/openbmc_project/network/eth0') && 179 content.data['/xyz/openbmc_project/network/eth0'] 180 .hasOwnProperty('MACAddress')) { 181 macAddress = 182 content.data['/xyz/openbmc_project/network/eth0'] 183 .MACAddress; 184 } 185 186 deferred.resolve({ 187 data: content.data, 188 hostname: hostname, 189 defaultgateway: defaultgateway, 190 mac_address: macAddress, 191 formatted_data: parseNetworkData(content) 192 }); 193 }, 194 function(error) { 195 console.log(error); 196 deferred.reject(error); 197 }); 198 return deferred.promise; 199 }, 200 setMACAddress: function(interface_name, mac_address) { 201 return $http({ 202 method: 'PUT', 203 url: DataService.getHost() + 204 '/xyz/openbmc_project/network/' + interface_name + 205 '/attr/MACAddress', 206 headers: { 207 'Accept': 'application/json', 208 'Content-Type': 'application/json' 209 }, 210 withCredentials: true, 211 data: JSON.stringify({'data': mac_address}) 212 }) 213 .then(function(response) { 214 return response.data; 215 }); 216 }, 217 setDefaultGateway: function(defaultGateway) { 218 return $http({ 219 method: 'PUT', 220 url: DataService.getHost() + 221 '/xyz/openbmc_project/network/config/attr/DefaultGateway', 222 headers: { 223 'Accept': 'application/json', 224 'Content-Type': 'application/json' 225 }, 226 withCredentials: true, 227 data: JSON.stringify({'data': defaultGateway}) 228 }) 229 .then(function(response) { 230 return response.data; 231 }); 232 }, 233 setDHCPEnabled: function(interfaceName, dhcpEnabled) { 234 return $http({ 235 method: 'PUT', 236 url: DataService.getHost() + 237 '/xyz/openbmc_project/network/' + interfaceName + 238 '/attr/DHCPEnabled', 239 headers: { 240 'Accept': 'application/json', 241 'Content-Type': 'application/json' 242 }, 243 withCredentials: true, 244 data: JSON.stringify({'data': dhcpEnabled}) 245 }) 246 .then(function(response) { 247 return response.data; 248 }); 249 }, 250 setNameservers: function(interfaceName, dnsServers) { 251 return $http({ 252 method: 'PUT', 253 url: DataService.getHost() + 254 '/xyz/openbmc_project/network/' + interfaceName + 255 '/attr/Nameservers', 256 headers: { 257 'Accept': 'application/json', 258 'Content-Type': 'application/json' 259 }, 260 withCredentials: true, 261 data: JSON.stringify({'data': dnsServers}) 262 }) 263 .then(function(response) { 264 return response.data; 265 }); 266 }, 267 deleteIPV4: function(interfaceName, networkID) { 268 return $http({ 269 method: 'POST', 270 url: DataService.getHost() + 271 '/xyz/openbmc_project/network/' + interfaceName + 272 '/ipv4/' + networkID + '/action/Delete', 273 headers: { 274 'Accept': 'application/json', 275 'Content-Type': 'application/json' 276 }, 277 withCredentials: true, 278 data: JSON.stringify({'data': []}) 279 }) 280 .then(function(response) { 281 return response.data; 282 }); 283 }, 284 addIPV4: function( 285 interfaceName, ipAddress, netmaskPrefixLength, gateway) { 286 return $http({ 287 method: 'POST', 288 url: DataService.getHost() + 289 '/xyz/openbmc_project/network/' + interfaceName + 290 '/action/IP', 291 headers: { 292 'Accept': 'application/json', 293 'Content-Type': 'application/json' 294 }, 295 withCredentials: true, 296 data: JSON.stringify({ 297 'data': [ 298 'xyz.openbmc_project.Network.IP.Protocol.IPv4', 299 ipAddress, +netmaskPrefixLength, gateway 300 ] 301 }) 302 }) 303 .then(function(response) { 304 return response.data; 305 }); 306 }, 307 getLEDState: function() { 308 var deferred = $q.defer(); 309 $http({ 310 method: 'GET', 311 url: DataService.getHost() + 312 '/xyz/openbmc_project/led/groups/enclosure_identify', 313 headers: { 314 'Accept': 'application/json', 315 'Content-Type': 'application/json' 316 }, 317 withCredentials: true 318 }) 319 .then( 320 function(response) { 321 var json = JSON.stringify(response.data); 322 var content = JSON.parse(json); 323 deferred.resolve(content.data.Asserted); 324 }, 325 function(error) { 326 console.log(error); 327 deferred.reject(error); 328 }); 329 return deferred.promise; 330 }, 331 login: function(username, password, callback) { 332 $http({ 333 method: 'POST', 334 url: DataService.getHost() + '/login', 335 headers: { 336 'Accept': 'application/json', 337 'Content-Type': 'application/json' 338 }, 339 withCredentials: true, 340 data: JSON.stringify({'data': [username, password]}) 341 }) 342 .then( 343 function(response) { 344 if (callback) { 345 callback(response.data); 346 } 347 }, 348 function(error) { 349 if (callback) { 350 if (error && error.status && error.status == 'error') { 351 callback(error); 352 } else { 353 callback(error, true); 354 } 355 } 356 console.log(error); 357 }); 358 }, 359 testPassword: function(username, password) { 360 // Calls /login without the current session to verify the given 361 // password is correct ignore the interceptor logout on a bad password 362 return $http({ 363 method: 'POST', 364 url: DataService.getHost() + '/login', 365 headers: { 366 'Accept': 'application/json', 367 'Content-Type': 'application/json' 368 }, 369 withCredentials: false, 370 data: JSON.stringify({'data': [username, password]}) 371 }) 372 .then(function(response) { 373 return response.data; 374 }); 375 }, 376 logout: function(callback) { 377 $http({ 378 method: 'POST', 379 url: DataService.getHost() + '/logout', 380 headers: { 381 'Accept': 'application/json', 382 'Content-Type': 'application/json' 383 }, 384 withCredentials: true, 385 data: JSON.stringify({'data': []}) 386 }) 387 .then( 388 function(response) { 389 if (callback) { 390 callback(response.data); 391 } 392 }, 393 function(error) { 394 if (callback) { 395 callback(null, error); 396 } 397 console.log(error); 398 }); 399 }, 400 changePassword: function(user, newPassword) { 401 var deferred = $q.defer(); 402 $http({ 403 method: 'POST', 404 url: DataService.getHost() + '/xyz/openbmc_project/user/' + user + 405 '/action/SetPassword', 406 headers: { 407 'Accept': 'application/json', 408 'Content-Type': 'application/json' 409 }, 410 withCredentials: true, 411 data: JSON.stringify({'data': [newPassword]}), 412 responseType: 'arraybuffer' 413 }) 414 .then( 415 function(response, status, headers) { 416 deferred.resolve( 417 {data: response, status: status, headers: headers}); 418 }, 419 function(error) { 420 console.log(error); 421 deferred.reject(error); 422 }); 423 return deferred.promise; 424 }, 425 chassisPowerOn: function(callback) { 426 $http({ 427 method: 'POST', 428 url: DataService.getHost() + '/xyz/openbmc_project/state/host0', 429 headers: { 430 'Accept': 'application/json', 431 'Content-Type': 'application/json' 432 }, 433 withCredentials: true, 434 data: JSON.stringify({'data': []}) 435 }) 436 .then( 437 function(response) { 438 var json = JSON.stringify(response.data); 439 var content = JSON.parse(json); 440 if (callback) { 441 return callback(content.data.CurrentPowerState); 442 } 443 }, 444 function(error) { 445 if (callback) { 446 callback(error); 447 } else { 448 console.log(error); 449 } 450 }); 451 }, 452 chassisPowerOff: function() { 453 var deferred = $q.defer(); 454 $http({ 455 method: 'PUT', 456 url: DataService.getHost() + 457 '/xyz/openbmc_project/state/chassis0/attr/RequestedPowerTransition', 458 headers: { 459 'Accept': 'application/json', 460 'Content-Type': 'application/json' 461 }, 462 withCredentials: true, 463 data: JSON.stringify( 464 {'data': 'xyz.openbmc_project.State.Chassis.Transition.Off'}) 465 }) 466 .then( 467 function(response) { 468 var json = JSON.stringify(response.data); 469 var content = JSON.parse(json); 470 deferred.resolve(content.status); 471 }, 472 function(error) { 473 console.log(error); 474 deferred.reject(error); 475 }); 476 return deferred.promise; 477 }, 478 setLEDState: function(state, callback) { 479 $http({ 480 method: 'PUT', 481 url: DataService.getHost() + 482 '/xyz/openbmc_project/led/groups/enclosure_identify/attr/Asserted', 483 headers: { 484 'Accept': 'application/json', 485 'Content-Type': 'application/json' 486 }, 487 withCredentials: true, 488 data: JSON.stringify({'data': state}) 489 }) 490 .then( 491 function(response) { 492 var json = JSON.stringify(response.data); 493 var content = JSON.parse(json); 494 if (callback) { 495 return callback(content.status); 496 } 497 }, 498 function(error) { 499 if (callback) { 500 callback(error); 501 } else { 502 console.log(error); 503 } 504 }); 505 }, 506 bmcReboot: function(callback) { 507 $http({ 508 method: 'PUT', 509 url: DataService.getHost() + 510 '/xyz/openbmc_project/state/bmc0/attr/RequestedBmcTransition', 511 headers: { 512 'Accept': 'application/json', 513 'Content-Type': 'application/json' 514 }, 515 withCredentials: true, 516 data: JSON.stringify( 517 {'data': 'xyz.openbmc_project.State.BMC.Transition.Reboot'}) 518 }) 519 .then( 520 function(response) { 521 var json = JSON.stringify(response.data); 522 var content = JSON.parse(json); 523 if (callback) { 524 return callback(content.status); 525 } 526 }, 527 function(error) { 528 if (callback) { 529 callback(error); 530 } else { 531 console.log(error); 532 } 533 }); 534 }, 535 getLastRebootTime: function() { 536 return $http({ 537 method: 'GET', 538 url: DataService.getHost() + 539 '/xyz/openbmc_project/state/bmc0/attr/LastRebootTime', 540 headers: { 541 'Accept': 'application/json', 542 'Content-Type': 'application/json' 543 }, 544 withCredentials: true 545 }) 546 .then(function(response) { 547 return response.data; 548 }); 549 }, 550 hostPowerOn: function() { 551 var deferred = $q.defer(); 552 $http({ 553 method: 'PUT', 554 url: DataService.getHost() + 555 '/xyz/openbmc_project/state/host0/attr/RequestedHostTransition', 556 headers: { 557 'Accept': 'application/json', 558 'Content-Type': 'application/json' 559 }, 560 withCredentials: true, 561 data: JSON.stringify( 562 {'data': 'xyz.openbmc_project.State.Host.Transition.On'}) 563 }) 564 .then( 565 function(response) { 566 var json = JSON.stringify(response.data); 567 var content = JSON.parse(json); 568 deferred.resolve(content.status); 569 }, 570 function(error) { 571 console.log(error); 572 deferred.reject(error); 573 }); 574 return deferred.promise; 575 }, 576 hostPowerOff: function() { 577 var deferred = $q.defer(); 578 $http({ 579 method: 'PUT', 580 url: DataService.getHost() + 581 '/xyz/openbmc_project/state/host0/attr/RequestedHostTransition', 582 headers: { 583 'Accept': 'application/json', 584 'Content-Type': 'application/json' 585 }, 586 withCredentials: true, 587 data: JSON.stringify( 588 {'data': 'xyz.openbmc_project.State.Host.Transition.Off'}) 589 }) 590 .then( 591 function(response) { 592 var json = JSON.stringify(response.data); 593 var content = JSON.parse(json); 594 deferred.resolve(content.status); 595 }, 596 function(error) { 597 console.log(error); 598 deferred.reject(error); 599 }); 600 return deferred.promise; 601 }, 602 hostReboot: function() { 603 var deferred = $q.defer(); 604 $http({ 605 method: 'PUT', 606 url: DataService.getHost() + 607 '/xyz/openbmc_project/state/host0/attr/RequestedHostTransition', 608 headers: { 609 'Accept': 'application/json', 610 'Content-Type': 'application/json' 611 }, 612 withCredentials: true, 613 data: JSON.stringify( 614 {'data': 'xyz.openbmc_project.State.Host.Transition.Reboot'}) 615 }) 616 .then( 617 function(response) { 618 var json = JSON.stringify(response.data); 619 var content = JSON.parse(json); 620 deferred.resolve(content.status); 621 }, 622 function(error) { 623 console.log(error); 624 deferred.reject(error); 625 }); 626 627 return deferred.promise; 628 }, 629 hostShutdown: function(callback) { 630 $http({ 631 method: 'POST', 632 url: DataService.getHost() + '/xyz/openbmc_project/state/host0', 633 headers: { 634 'Accept': 'application/json', 635 'Content-Type': 'application/json' 636 }, 637 withCredentials: true, 638 data: JSON.stringify({'data': []}) 639 }) 640 .then( 641 function(response) { 642 var json = JSON.stringify(response.data); 643 var content = JSON.parse(json); 644 if (callback) { 645 return callback(content); 646 } 647 }, 648 function(error) { 649 if (callback) { 650 callback(error); 651 } else { 652 console.log(error); 653 } 654 }); 655 }, 656 getLastPowerTime: function() { 657 return $http({ 658 method: 'GET', 659 url: DataService.getHost() + 660 '/xyz/openbmc_project/state/chassis0/attr/LastStateChangeTime', 661 headers: { 662 'Accept': 'application/json', 663 'Content-Type': 'application/json' 664 }, 665 withCredentials: true 666 }) 667 .then(function(response) { 668 return response.data; 669 }); 670 }, 671 getLogs: function() { 672 var deferred = $q.defer(); 673 $http({ 674 method: 'GET', 675 url: DataService.getHost() + 676 '/xyz/openbmc_project/logging/enumerate', 677 headers: { 678 'Accept': 'application/json', 679 'Content-Type': 'application/json' 680 }, 681 withCredentials: true 682 }) 683 .then( 684 function(response) { 685 var json = JSON.stringify(response.data); 686 var content = JSON.parse(json); 687 var dataClone = JSON.parse(JSON.stringify(content.data)); 688 var data = []; 689 var severityCode = ''; 690 var priority = ''; 691 var health = ''; 692 var relatedItems = []; 693 var eventID = 'None'; 694 var description = 'None'; 695 696 for (var key in content.data) { 697 if (content.data.hasOwnProperty(key) && 698 content.data[key].hasOwnProperty('Id')) { 699 var severityFlags = { 700 low: false, 701 medium: false, 702 high: false 703 }; 704 var healthFlags = { 705 critical: false, 706 warning: false, 707 good: false 708 }; 709 severityCode = 710 content.data[key].Severity.split('.').pop(); 711 priority = 712 Constants.SEVERITY_TO_PRIORITY_MAP[severityCode]; 713 severityFlags[priority.toLowerCase()] = true; 714 health = Constants.SEVERITY_TO_HEALTH_MAP[severityCode]; 715 healthFlags[health.toLowerCase()] = true; 716 relatedItems = []; 717 content.data[key].associations.forEach(function(item) { 718 relatedItems.push(item[2]); 719 }); 720 721 if (content.data[key].hasOwnProperty(['EventID'])) { 722 eventID = content.data[key].EventID; 723 } 724 725 if (content.data[key].hasOwnProperty(['Description'])) { 726 description = content.data[key].Description; 727 } 728 729 data.push(Object.assign( 730 { 731 path: key, 732 copied: false, 733 priority: priority, 734 severity_code: severityCode, 735 severity_flags: severityFlags, 736 health_flags: healthFlags, 737 additional_data: 738 content.data[key].AdditionalData.join('\n'), 739 type: content.data[key].Message, 740 selected: false, 741 search_text: 742 ('#' + content.data[key].Id + ' ' + 743 severityCode + ' ' + 744 content.data[key].Message + ' ' + 745 content.data[key].Severity + ' ' + 746 content.data[key].AdditionalData.join(' ')) 747 .toLowerCase(), 748 meta: false, 749 confirm: false, 750 related_items: relatedItems, 751 eventID: eventID, 752 description: description, 753 data: {key: key, value: content.data[key]} 754 }, 755 content.data[key])); 756 } 757 } 758 deferred.resolve({data: data, original: dataClone}); 759 }, 760 function(error) { 761 console.log(error); 762 deferred.reject(error); 763 }); 764 765 return deferred.promise; 766 }, 767 getAllSensorStatus: function(callback) { 768 $http({ 769 method: 'GET', 770 url: DataService.getHost() + 771 '/xyz/openbmc_project/sensors/enumerate', 772 headers: { 773 'Accept': 'application/json', 774 'Content-Type': 'application/json' 775 }, 776 withCredentials: true 777 }) 778 .then( 779 function(response) { 780 var json = JSON.stringify(response.data); 781 var content = JSON.parse(json); 782 var dataClone = JSON.parse(JSON.stringify(content.data)); 783 var sensorData = []; 784 var severity = {}; 785 var title = ''; 786 var tempKeyParts = []; 787 var order = 0; 788 var customOrder = 0; 789 790 function getSensorStatus(reading) { 791 var severityFlags = { 792 critical: false, 793 warning: false, 794 normal: false 795 }, 796 severityText = '', order = 0; 797 798 if (reading.hasOwnProperty('CriticalLow') && 799 reading.Value < reading.CriticalLow) { 800 severityFlags.critical = true; 801 severityText = 'critical'; 802 order = 2; 803 } else if ( 804 reading.hasOwnProperty('CriticalHigh') && 805 reading.Value > reading.CriticalHigh) { 806 severityFlags.critical = true; 807 severityText = 'critical'; 808 order = 2; 809 } else if ( 810 reading.hasOwnProperty('CriticalLow') && 811 reading.hasOwnProperty('WarningLow') && 812 reading.Value >= reading.CriticalLow && 813 reading.Value <= reading.WarningLow) { 814 severityFlags.warning = true; 815 severityText = 'warning'; 816 order = 1; 817 } else if ( 818 reading.hasOwnProperty('WarningHigh') && 819 reading.hasOwnProperty('CriticalHigh') && 820 reading.Value >= reading.WarningHigh && 821 reading.Value <= reading.CriticalHigh) { 822 severityFlags.warning = true; 823 severityText = 'warning'; 824 order = 1; 825 } else { 826 severityFlags.normal = true; 827 severityText = 'normal'; 828 } 829 return { 830 flags: severityFlags, 831 severityText: severityText, 832 order: order 833 }; 834 } 835 836 for (var key in content.data) { 837 if (content.data.hasOwnProperty(key) && 838 content.data[key].hasOwnProperty('Unit')) { 839 severity = getSensorStatus(content.data[key]); 840 841 if (!content.data[key].hasOwnProperty('CriticalLow')) { 842 content.data[key].CriticalLow = '--'; 843 content.data[key].CriticalHigh = '--'; 844 } 845 846 if (!content.data[key].hasOwnProperty('WarningLow')) { 847 content.data[key].WarningLow = '--'; 848 content.data[key].WarningHigh = '--'; 849 } 850 851 tempKeyParts = key.split('/'); 852 title = tempKeyParts.pop(); 853 title = tempKeyParts.pop() + '_' + title; 854 title = title.split('_') 855 .map(function(item) { 856 return item.toLowerCase() 857 .charAt(0) 858 .toUpperCase() + 859 item.slice(1); 860 }) 861 .reduce(function(prev, el) { 862 return prev + ' ' + el; 863 }); 864 865 content.data[key].Value = getScaledValue( 866 content.data[key].Value, content.data[key].Scale); 867 content.data[key].CriticalLow = getScaledValue( 868 content.data[key].CriticalLow, 869 content.data[key].Scale); 870 content.data[key].CriticalHigh = getScaledValue( 871 content.data[key].CriticalHigh, 872 content.data[key].Scale); 873 content.data[key].WarningLow = getScaledValue( 874 content.data[key].WarningLow, 875 content.data[key].Scale); 876 content.data[key].WarningHigh = getScaledValue( 877 content.data[key].WarningHigh, 878 content.data[key].Scale); 879 if (Constants.SENSOR_SORT_ORDER.indexOf( 880 content.data[key].Unit) > -1) { 881 customOrder = Constants.SENSOR_SORT_ORDER.indexOf( 882 content.data[key].Unit); 883 } else { 884 customOrder = Constants.SENSOR_SORT_ORDER_DEFAULT; 885 } 886 887 sensorData.push(Object.assign( 888 { 889 path: key, 890 selected: false, 891 confirm: false, 892 copied: false, 893 title: title, 894 unit: 895 Constants 896 .SENSOR_UNIT_MAP[content.data[key].Unit], 897 severity_flags: severity.flags, 898 status: severity.severityText, 899 order: severity.order, 900 custom_order: customOrder, 901 search_text: 902 (title + ' ' + content.data[key].Value + ' ' + 903 Constants.SENSOR_UNIT_MAP[content.data[key] 904 .Unit] + 905 ' ' + severity.severityText + ' ' + 906 content.data[key].CriticalLow + ' ' + 907 content.data[key].CriticalHigh + ' ' + 908 content.data[key].WarningLow + ' ' + 909 content.data[key].WarningHigh + ' ') 910 .toLowerCase(), 911 original_data: 912 {key: key, value: content.data[key]} 913 }, 914 content.data[key])); 915 } 916 } 917 918 callback(sensorData, dataClone); 919 }, 920 function(error) { 921 console.log(error); 922 }); 923 }, 924 getActivation: function(imageId) { 925 return $http({ 926 method: 'GET', 927 url: DataService.getHost() + 928 '/xyz/openbmc_project/software/' + imageId + 929 '/attr/Activation', 930 headers: { 931 'Accept': 'application/json', 932 'Content-Type': 'application/json' 933 }, 934 withCredentials: true 935 }) 936 .then(function(response) { 937 return response.data; 938 }); 939 }, 940 getFirmwares: function() { 941 var deferred = $q.defer(); 942 $http({ 943 method: 'GET', 944 url: DataService.getHost() + 945 '/xyz/openbmc_project/software/enumerate', 946 headers: { 947 'Accept': 'application/json', 948 'Content-Type': 'application/json' 949 }, 950 withCredentials: true 951 }) 952 .then( 953 function(response) { 954 var json = JSON.stringify(response.data); 955 var content = JSON.parse(json); 956 var data = []; 957 var isExtended = false; 958 var bmcActiveVersion = ''; 959 var hostActiveVersion = ''; 960 var imageType = ''; 961 var extendedVersions = []; 962 var functionalImages = []; 963 964 function getFormatedExtendedVersions(extendedVersion) { 965 var versions = []; 966 extendedVersion = extendedVersion.split(','); 967 968 extendedVersion.forEach(function(item) { 969 var parts = item.split('-'); 970 var numberIndex = 0; 971 for (var i = 0; i < parts.length; i++) { 972 if (/[0-9]/.test(parts[i])) { 973 numberIndex = i; 974 break; 975 } 976 } 977 var titlePart = parts.splice(0, numberIndex); 978 titlePart = titlePart.join(''); 979 titlePart = titlePart[0].toUpperCase() + 980 titlePart.substr(1, titlePart.length); 981 var versionPart = parts.join('-'); 982 versions.push({title: titlePart, version: versionPart}); 983 }); 984 985 return versions; 986 } 987 988 // Get the list of functional images so we can compare 989 // later if an image is functional 990 if (content.data[Constants.FIRMWARE.FUNCTIONAL_OBJPATH]) { 991 functionalImages = 992 content.data[Constants.FIRMWARE.FUNCTIONAL_OBJPATH] 993 .endpoints; 994 } 995 for (var key in content.data) { 996 if (content.data.hasOwnProperty(key) && 997 content.data[key].hasOwnProperty('Version')) { 998 var activationStatus = ''; 999 1000 // If the image is "Functional" use that for the 1001 // activation status, else use the value of "Activation" 1002 // github.com/openbmc/phosphor-dbus-interfaces/blob/master/xyz/openbmc_project/Software/Activation.interface.yaml 1003 if (content.data[key].Activation) { 1004 activationStatus = 1005 content.data[key].Activation.split('.').pop(); 1006 } 1007 1008 if (functionalImages.includes(key)) { 1009 activationStatus = 'Functional'; 1010 } 1011 1012 imageType = content.data[key].Purpose.split('.').pop(); 1013 isExtended = content.data[key].hasOwnProperty( 1014 'ExtendedVersion') && 1015 content.data[key].ExtendedVersion != ''; 1016 if (isExtended) { 1017 extendedVersions = getFormatedExtendedVersions( 1018 content.data[key].ExtendedVersion); 1019 } 1020 data.push(Object.assign( 1021 { 1022 path: key, 1023 activationStatus: activationStatus, 1024 imageId: key.split('/').pop(), 1025 imageType: imageType, 1026 isExtended: isExtended, 1027 extended: 1028 {show: false, versions: extendedVersions}, 1029 data: {key: key, value: content.data[key]} 1030 }, 1031 content.data[key])); 1032 1033 if (activationStatus == 'Functional' && 1034 imageType == 'BMC') { 1035 bmcActiveVersion = content.data[key].Version; 1036 } 1037 1038 if (activationStatus == 'Functional' && 1039 imageType == 'Host') { 1040 hostActiveVersion = content.data[key].Version; 1041 } 1042 } 1043 } 1044 1045 deferred.resolve({ 1046 data: data, 1047 bmcActiveVersion: bmcActiveVersion, 1048 hostActiveVersion: hostActiveVersion 1049 }); 1050 }, 1051 function(error) { 1052 console.log(error); 1053 deferred.reject(error); 1054 }); 1055 1056 return deferred.promise; 1057 }, 1058 changePriority: function(imageId, priority) { 1059 var deferred = $q.defer(); 1060 $http({ 1061 method: 'PUT', 1062 url: DataService.getHost() + '/xyz/openbmc_project/software/' + 1063 imageId + '/attr/Priority', 1064 headers: { 1065 'Accept': 'application/json', 1066 'Content-Type': 'application/json' 1067 }, 1068 withCredentials: true, 1069 data: JSON.stringify({'data': priority}) 1070 }) 1071 .then( 1072 function(response) { 1073 var json = JSON.stringify(response.data); 1074 var content = JSON.parse(json); 1075 deferred.resolve(content); 1076 }, 1077 function(error) { 1078 console.log(error); 1079 deferred.reject(error); 1080 }); 1081 1082 return deferred.promise; 1083 }, 1084 deleteImage: function(imageId) { 1085 var deferred = $q.defer(); 1086 $http({ 1087 method: 'POST', 1088 url: DataService.getHost() + '/xyz/openbmc_project/software/' + 1089 imageId + '/action/Delete', 1090 headers: { 1091 'Accept': 'application/json', 1092 'Content-Type': 'application/json' 1093 }, 1094 withCredentials: true, 1095 data: JSON.stringify({'data': []}) 1096 }) 1097 .then( 1098 function(response) { 1099 var json = JSON.stringify(response.data); 1100 var content = JSON.parse(json); 1101 deferred.resolve(content); 1102 }, 1103 function(error) { 1104 console.log(error); 1105 deferred.reject(error); 1106 }); 1107 1108 return deferred.promise; 1109 }, 1110 activateImage: function(imageId) { 1111 var deferred = $q.defer(); 1112 $http({ 1113 method: 'PUT', 1114 url: DataService.getHost() + '/xyz/openbmc_project/software/' + 1115 imageId + '/attr/RequestedActivation', 1116 headers: { 1117 'Accept': 'application/json', 1118 'Content-Type': 'application/json' 1119 }, 1120 withCredentials: true, 1121 data: 1122 JSON.stringify({'data': Constants.FIRMWARE.ACTIVATE_FIRMWARE}) 1123 }) 1124 .then( 1125 function(response) { 1126 var json = JSON.stringify(response.data); 1127 var content = JSON.parse(json); 1128 deferred.resolve(content); 1129 }, 1130 function(error) { 1131 console.log(error); 1132 deferred.reject(error); 1133 }); 1134 1135 return deferred.promise; 1136 }, 1137 uploadImage: function(file) { 1138 return $http({ 1139 method: 'POST', 1140 timeout: 5 * 60 * 1000, 1141 url: DataService.getHost() + '/upload/image', 1142 headers: {'Content-Type': 'application/octet-stream'}, 1143 withCredentials: true, 1144 data: file 1145 }) 1146 .then(function(response) { 1147 return response.data; 1148 }); 1149 }, 1150 downloadImage: function(host, filename) { 1151 return $http({ 1152 method: 'POST', 1153 url: DataService.getHost() + 1154 '/xyz/openbmc_project/software/action/DownloadViaTFTP', 1155 headers: { 1156 'Accept': 'application/json', 1157 'Content-Type': 'application/json' 1158 }, 1159 withCredentials: true, 1160 data: JSON.stringify({'data': [filename, host]}), 1161 responseType: 'arraybuffer' 1162 }) 1163 .then(function(response) { 1164 return response.data; 1165 }); 1166 }, 1167 getBMCEthernetInfo: function() { 1168 var deferred = $q.defer(); 1169 $http({ 1170 method: 'GET', 1171 url: DataService.getHost() + 1172 '/xyz/openbmc_project/inventory/system/chassis/motherboard/boxelder/bmc/ethernet', 1173 headers: { 1174 'Accept': 'application/json', 1175 'Content-Type': 'application/json' 1176 }, 1177 withCredentials: true 1178 }) 1179 .then( 1180 function(response) { 1181 var json = JSON.stringify(response.data); 1182 var content = JSON.parse(json); 1183 deferred.resolve(content.data); 1184 }, 1185 function(error) { 1186 console.log(error); 1187 deferred.reject(error); 1188 }); 1189 1190 return deferred.promise; 1191 }, 1192 getBMCInfo: function(callback) { 1193 var deferred = $q.defer(); 1194 $http({ 1195 method: 'GET', 1196 url: DataService.getHost() + 1197 '/xyz/openbmc_project/inventory/system/chassis/motherboard/boxelder/bmc', 1198 headers: { 1199 'Accept': 'application/json', 1200 'Content-Type': 'application/json' 1201 }, 1202 withCredentials: true 1203 }) 1204 .then( 1205 function(response) { 1206 var json = JSON.stringify(response.data); 1207 var content = JSON.parse(json); 1208 deferred.resolve(content.data); 1209 }, 1210 function(error) { 1211 console.log(error); 1212 deferred.reject(error); 1213 }); 1214 return deferred.promise; 1215 }, 1216 getServerInfo: function() { 1217 // TODO: openbmc/openbmc#3117 Need a way via REST to get 1218 // interfaces so we can get the system object(s) by the looking 1219 // for the system interface. 1220 return $http({ 1221 method: 'GET', 1222 url: DataService.getHost() + 1223 '/xyz/openbmc_project/inventory/system', 1224 headers: { 1225 'Accept': 'application/json', 1226 'Content-Type': 'application/json' 1227 }, 1228 withCredentials: true 1229 }) 1230 .then(function(response) { 1231 return response.data; 1232 }); 1233 }, 1234 getBMCTime: function() { 1235 return $http({ 1236 method: 'GET', 1237 url: DataService.getHost() + '/xyz/openbmc_project/time/bmc', 1238 headers: { 1239 'Accept': 'application/json', 1240 'Content-Type': 'application/json' 1241 }, 1242 withCredentials: true 1243 }) 1244 .then(function(response) { 1245 return response.data; 1246 }); 1247 }, 1248 getHardwares: function(callback) { 1249 $http({ 1250 method: 'GET', 1251 url: DataService.getHost() + 1252 '/xyz/openbmc_project/inventory/enumerate', 1253 headers: { 1254 'Accept': 'application/json', 1255 'Content-Type': 'application/json' 1256 }, 1257 withCredentials: true 1258 }).then(function(response) { 1259 var json = JSON.stringify(response.data); 1260 var content = JSON.parse(json); 1261 var hardwareData = []; 1262 var keyIndexMap = {}; 1263 var title = ''; 1264 var data = []; 1265 var searchText = ''; 1266 var componentIndex = -1; 1267 var tempParts = []; 1268 1269 function isSubComponent(key) { 1270 for (var i = 0; i < Constants.HARDWARE.parent_components.length; 1271 i++) { 1272 if (key.split(Constants.HARDWARE.parent_components[i]).length == 1273 2) 1274 return true; 1275 } 1276 1277 return false; 1278 } 1279 1280 function titlelize(title) { 1281 title = title.replace(/([A-Z0-9]+)/g, ' $1').replace(/^\s+/, ''); 1282 for (var i = 0; i < Constants.HARDWARE.uppercase_titles.length; 1283 i++) { 1284 if (title.toLowerCase().indexOf( 1285 (Constants.HARDWARE.uppercase_titles[i] + ' ')) > -1) { 1286 return title.toUpperCase(); 1287 } 1288 } 1289 1290 return title; 1291 } 1292 1293 function camelcaseToLabel(obj) { 1294 var transformed = [], label = '', value = ''; 1295 for (var key in obj) { 1296 label = key.replace(/([A-Z0-9]+)/g, ' $1').replace(/^\s+/, ''); 1297 if (obj[key] !== '') { 1298 value = obj[key]; 1299 if (value == 1 || value == 0) { 1300 value = (value == 1) ? 'Yes' : 'No'; 1301 } 1302 transformed.push({key: label, value: value}); 1303 } 1304 } 1305 1306 return transformed; 1307 } 1308 1309 function getSearchText(data) { 1310 var searchText = ''; 1311 for (var i = 0; i < data.length; i++) { 1312 searchText += ' ' + data[i].key + ' ' + data[i].value; 1313 } 1314 1315 return searchText; 1316 } 1317 1318 for (var key in content.data) { 1319 if (content.data.hasOwnProperty(key) && 1320 key.indexOf(Constants.HARDWARE.component_key_filter) == 0) { 1321 data = camelcaseToLabel(content.data[key]); 1322 searchText = getSearchText(data); 1323 title = key.split('/').pop(); 1324 1325 title = titlelize(title); 1326 1327 if (!isSubComponent(key)) { 1328 hardwareData.push(Object.assign( 1329 { 1330 path: key, 1331 title: title, 1332 selected: false, 1333 expanded: false, 1334 search_text: title.toLowerCase() + ' ' + 1335 searchText.toLowerCase(), 1336 sub_components: [], 1337 original_data: {key: key, value: content.data[key]} 1338 }, 1339 {items: data})); 1340 1341 keyIndexMap[key] = hardwareData.length - 1; 1342 } else { 1343 var tempParts = key.split('/'); 1344 tempParts.pop(); 1345 tempParts = tempParts.join('/'); 1346 componentIndex = keyIndexMap[tempParts]; 1347 data = content.data[key]; 1348 data.title = title; 1349 hardwareData[componentIndex].sub_components.push(data); 1350 hardwareData[componentIndex].search_text += 1351 ' ' + title.toLowerCase(); 1352 1353 // Sort the subcomponents alphanumeric so they are displayed 1354 // on the inventory page in order (e.g. core 0, core 1, core 1355 // 2, ... core 12, core 13) 1356 hardwareData[componentIndex].sub_components.sort(function( 1357 a, b) { 1358 return a.title.localeCompare( 1359 b.title, 'en', {numeric: true}); 1360 }); 1361 } 1362 } 1363 } 1364 1365 if (callback) { 1366 callback(hardwareData, content.data); 1367 } else { 1368 return {data: hardwareData, original_data: content.data}; 1369 } 1370 }); 1371 }, 1372 deleteLogs: function(logs) { 1373 var defer = $q.defer(); 1374 var promises = []; 1375 1376 function finished() { 1377 defer.resolve(); 1378 } 1379 1380 logs.forEach(function(item) { 1381 promises.push($http({ 1382 method: 'POST', 1383 url: DataService.getHost() + 1384 '/xyz/openbmc_project/logging/entry/' + item.Id + 1385 '/action/Delete', 1386 headers: { 1387 'Accept': 'application/json', 1388 'Content-Type': 'application/json' 1389 }, 1390 withCredentials: true, 1391 data: JSON.stringify({'data': []}) 1392 })); 1393 }); 1394 1395 $q.all(promises).then(finished); 1396 1397 return defer.promise; 1398 }, 1399 resolveLogs: function(logs) { 1400 var defer = $q.defer(); 1401 var promises = []; 1402 1403 function finished() { 1404 defer.resolve(); 1405 } 1406 1407 logs.forEach(function(item) { 1408 promises.push($http({ 1409 method: 'PUT', 1410 url: DataService.getHost() + 1411 '/xyz/openbmc_project/logging/entry/' + item.Id + 1412 '/attr/Resolved', 1413 headers: { 1414 'Accept': 'application/json', 1415 'Content-Type': 'application/json' 1416 }, 1417 withCredentials: true, 1418 data: JSON.stringify({'data': '1'}) 1419 })); 1420 }); 1421 1422 $q.all(promises).then(finished); 1423 1424 return defer.promise; 1425 }, 1426 getPowerConsumption: function() { 1427 return $http({ 1428 method: 'GET', 1429 url: DataService.getHost() + 1430 '/xyz/openbmc_project/sensors/power/total_power', 1431 headers: { 1432 'Accept': 'application/json', 1433 'Content-Type': 'application/json' 1434 }, 1435 withCredentials: true 1436 }) 1437 .then( 1438 function(response) { 1439 var json = JSON.stringify(response.data); 1440 var content = JSON.parse(json); 1441 1442 return getScaledValue( 1443 content.data.Value, content.data.Scale) + 1444 ' ' + 1445 Constants.POWER_CONSUMPTION_TEXT[content.data.Unit]; 1446 }, 1447 function(error) { 1448 if ('Not Found' == error.statusText) { 1449 return Constants.POWER_CONSUMPTION_TEXT.notavailable; 1450 } else { 1451 throw error; 1452 } 1453 }); 1454 }, 1455 getPowerCap: function() { 1456 return $http({ 1457 method: 'GET', 1458 url: DataService.getHost() + 1459 '/xyz/openbmc_project/control/host0/power_cap', 1460 headers: { 1461 'Accept': 'application/json', 1462 'Content-Type': 'application/json' 1463 }, 1464 withCredentials: true 1465 }) 1466 .then(function(response) { 1467 var json = JSON.stringify(response.data); 1468 var content = JSON.parse(json); 1469 1470 return (false == content.data.PowerCapEnable) ? 1471 Constants.POWER_CAP_TEXT.disabled : 1472 content.data.PowerCap + ' ' + Constants.POWER_CAP_TEXT.unit; 1473 }); 1474 }, 1475 setHostname: function(hostname) { 1476 return $http({ 1477 method: 'PUT', 1478 url: DataService.getHost() + 1479 '/xyz/openbmc_project/network/config/attr/HostName', 1480 headers: { 1481 'Accept': 'application/json', 1482 'Content-Type': 'application/json' 1483 }, 1484 withCredentials: true, 1485 data: JSON.stringify({'data': hostname}) 1486 }) 1487 .then(function(response) { 1488 return response.data; 1489 }); 1490 }, 1491 }; 1492 return SERVICE; 1493 } 1494 ]); 1495})(window.angular); 1496