/** * @description Intel(r) AMT WSMAN Stack * @author Ylian Saint-Hilaire * @version v0.2.0 */ // Construct a MeshServer object var WsmanStackCreateService = function (host, port, user, pass, tls, extra) { var obj = {}; //obj.onDebugMessage = null; // Set to a function if you want to get debug messages. obj.NextMessageId = 1; // Next message number, used to label WSMAN calls. obj.Address = '/wsman'; obj.comm = CreateWsmanComm(host, port, user, pass, tls, extra); obj.PerformAjax = function (postdata, callback, tag, pri, namespaces) { if (namespaces == null) namespaces = ''; obj.comm.PerformAjax('
' + postdata, function (data, status, tag) { var wsresponse = obj.ParseWsman(data); if ((data != null) && (!wsresponse || wsresponse == null) && (status == 200)) { callback(obj, null, { Header: { HttpError: status } }, 601, tag); } else { if (status != 200) { if (wsresponse == null) { wsresponse = { Header: {} }; } wsresponse.Header.HttpError = status; try { wsresponse.Header.WsmanError = wsresponse.Body['Reason']['Text']['Value']; } catch (ex) { } } callback(obj, wsresponse.Header['ResourceURI'], wsresponse, status, tag); } }, tag, pri); } // Private method //obj.Debug = function (msg) { /*console.log(msg);*/ } // Cancel all pending queries with given status obj.CancelAllQueries = function (s) { obj.comm.CancelAllQueries(s); } // Get the last element of a URI string obj.GetNameFromUrl = function (resuri) { var x = resuri.lastIndexOf('/'); return (x == -1)?resuri:resuri.substring(x + 1); } // Perform a WSMAN Subscribe operation obj.ExecSubscribe = function (resuri, delivery, url, callback, tag, pri, selectors, opaque, user, pass) { var digest = '', digest2 = '', opaque = ''; if (user != null && pass != null) { digest = 'http://docs.oasis-open.org/wss/2004/01/oasis-200401-wss-username-token-profile-1.0#UsernameToken' + user + '' + pass + ''; digest2 = ''; } if (opaque != null) { opaque = '' + opaque + ''; } if (delivery == 'PushWithAck') { delivery = 'dmtf.org/wbem/wsman/1/wsman/PushWithAck'; } else if (delivery == 'Push') { delivery = 'xmlsoap.org/ws/2004/08/eventing/DeliveryModes/Push'; } var data = 'http://schemas.xmlsoap.org/ws/2004/08/eventing/Subscribe' + obj.Address + '' + resuri + '' + (obj.NextMessageId++) + 'http://schemas.xmlsoap.org/ws/2004/08/addressing/role/anonymous' + _PutObjToSelectorsXml(selectors) + digest + '
' + url + '' + opaque + '' + digest2 + ''; obj.PerformAjax(data + '
', callback, tag, pri, 'xmlns:e="http://schemas.xmlsoap.org/ws/2004/08/eventing" xmlns:m="http://x.com"'); } // Perform a WSMAN UnSubscribe operation obj.ExecUnSubscribe = function (resuri, callback, tag, pri, selectors) { var data = 'http://schemas.xmlsoap.org/ws/2004/08/eventing/Unsubscribe' + obj.Address + '' + resuri + '' + (obj.NextMessageId++) + 'http://schemas.xmlsoap.org/ws/2004/08/addressing/role/anonymous' + _PutObjToSelectorsXml(selectors) + ''; obj.PerformAjax(data + '', callback, tag, pri, 'xmlns:e="http://schemas.xmlsoap.org/ws/2004/08/eventing"'); } // Perform a WSMAN PUT operation obj.ExecPut = function (resuri, putobj, callback, tag, pri, selectors) { var data = 'http://schemas.xmlsoap.org/ws/2004/09/transfer/Put' + obj.Address + '' + resuri + '' + (obj.NextMessageId++) + 'http://schemas.xmlsoap.org/ws/2004/08/addressing/role/anonymousPT60.000S' + _PutObjToSelectorsXml(selectors) + '' + _PutObjToBodyXml(resuri, putobj); obj.PerformAjax(data + '', callback, tag, pri); } // Perform a WSMAN CREATE operation obj.ExecCreate = function (resuri, putobj, callback, tag, pri, selectors) { var objname = obj.GetNameFromUrl(resuri); var data = 'http://schemas.xmlsoap.org/ws/2004/09/transfer/Create' + obj.Address + '' + resuri + '' + (obj.NextMessageId++) + 'http://schemas.xmlsoap.org/ws/2004/08/addressing/role/anonymousPT60S' + _PutObjToSelectorsXml(selectors) + ''; for (var n in putobj) { data += '' + putobj[n] + '' } obj.PerformAjax(data + '', callback, tag, pri); } // Perform a WSMAN DELETE operation obj.ExecDelete = function (resuri, putobj, callback, tag, pri) { var data = 'http://schemas.xmlsoap.org/ws/2004/09/transfer/Delete' + obj.Address + '' + resuri + '' + (obj.NextMessageId++) + 'http://schemas.xmlsoap.org/ws/2004/08/addressing/role/anonymousPT60S' + _PutObjToSelectorsXml(putobj) + ''; obj.PerformAjax(data, callback, tag, pri); } // Perform a WSMAN GET operation obj.ExecGet = function (resuri, callback, tag, pri) { obj.PerformAjax('http://schemas.xmlsoap.org/ws/2004/09/transfer/Get' + obj.Address + '' + resuri + '' + (obj.NextMessageId++) + 'http://schemas.xmlsoap.org/ws/2004/08/addressing/role/anonymousPT60S', callback, tag, pri); } // Perform a WSMAN method call operation obj.ExecMethod = function (resuri, method, args, callback, tag, pri, selectors) { var argsxml = ''; for (var i in args) { if (args[i] != null) { if (Array.isArray(args[i])) { for (var x in args[i]) { argsxml += '' + args[i][x] + ''; } } else { argsxml += '' + args[i] + ''; } } } obj.ExecMethodXml(resuri, method, argsxml, callback, tag, pri, selectors); } // Perform a WSMAN method call operation. The arguments are already formatted in XML. obj.ExecMethodXml = function (resuri, method, argsxml, callback, tag, pri, selectors) { obj.PerformAjax(resuri + '/' + method + '' + obj.Address + '' + resuri + '' + (obj.NextMessageId++) + 'http://schemas.xmlsoap.org/ws/2004/08/addressing/role/anonymousPT60S' + _PutObjToSelectorsXml(selectors) + '' + argsxml + '', callback, tag, pri); } // Perform a WSMAN ENUM operation obj.ExecEnum = function (resuri, callback, tag, pri) { obj.PerformAjax('http://schemas.xmlsoap.org/ws/2004/09/enumeration/Enumerate' + obj.Address + '' + resuri + '' + (obj.NextMessageId++) + 'http://schemas.xmlsoap.org/ws/2004/08/addressing/role/anonymousPT60S', callback, tag, pri); //obj.PerformAjax('http://schemas.xmlsoap.org/ws/2004/09/enumeration/Enumerate' + obj.Address + '' + resuri + '' + (obj.NextMessageId++) + 'http://schemas.xmlsoap.org/ws/2004/08/addressing/role/anonymousPT99S51200', callback, tag, pri); } // Perform a WSMAN PULL operation obj.ExecPull = function (resuri, enumctx, callback, tag, pri) { obj.PerformAjax('http://schemas.xmlsoap.org/ws/2004/09/enumeration/Pull' + obj.Address + '' + resuri + '' + (obj.NextMessageId++) + 'http://schemas.xmlsoap.org/ws/2004/08/addressing/role/anonymousPT60S' + enumctx + '', callback, tag, pri); // --99999999-- //obj.PerformAjax('http://schemas.xmlsoap.org/ws/2004/09/enumeration/Pull' + obj.Address + '' + resuri + '' + (obj.NextMessageId++) + 'http://schemas.xmlsoap.org/ws/2004/08/addressing/role/anonymousPT99S51200' + enumctx + '99999999', callback, tag, pri); // --99999999-- } // Private method obj.ParseWsman = function (xml) { if (xml == null) return null; var r = { Header: {} }; try { if (!xml.childNodes) xml = _turnToXml(xml); var header = xml.getElementsByTagName('Header')[0], t; if (!header) header = xml.getElementsByTagName('a:Header')[0]; if (!header) return null; for (var i = 0; i < header.childNodes.length; i++) { var child = header.childNodes[i]; r.Header[child.localName] = child.textContent; } var body = xml.getElementsByTagName('Body')[0]; if (!body) body = xml.getElementsByTagName('a:Body')[0]; if (!body) return null; if (body.childNodes.length > 0) { t = body.childNodes[0].localName; var x = t.indexOf('_OUTPUT'); if ((x != -1) && (x == (t.length - 7))) { t = t.substring(0, t.length - 7); } r.Header['Method'] = t; try { r.Body = _ParseWsmanRec(body.childNodes[0]); } catch (ex) { console.log('_ParseWsmanRec failed', body, ex); return null; } } } catch (ex) { console.log('Unable to parse XML: ' + xml + ', ' + ex); return null; } return r; } // Private method function _ParseWsmanRec(node) { var data, r = {}; for (var i = 0; i < node.childNodes.length; i++) { var child = node.childNodes[i]; if ((child.childElementCount == null) || (child.childElementCount == 0)) { data = child.textContent; } else { data = _ParseWsmanRec(child); } if (data == 'true') data = true; // Convert 'true' into true if (data == 'false') data = false; // Convert 'false' into false if ((parseInt(data) + '') === data) data = parseInt(data); // Convert integers var childObj = data; if ((child.attributes != null) && (child.attributes.length > 0)) { childObj = { 'Value': data }; for(var j = 0; j < child.attributes.length; j++) { childObj['@' + child.attributes[j].name] = child.attributes[j].value; } } if (r[child.localName] instanceof Array) { r[child.localName].push(childObj); } else if (r[child.localName] == null) { r[child.localName] = childObj; } else { r[child.localName] = [r[child.localName], childObj]; } } return r; } function _PutObjToBodyXml(resuri, putObj) { if (!resuri || putObj == null) return ''; var objname = obj.GetNameFromUrl(resuri); var result = ''; for (var prop in putObj) { if (!putObj.hasOwnProperty(prop) || prop.indexOf('__') === 0 || prop.indexOf('@') === 0) continue; if (putObj[prop] == null || typeof putObj[prop] === 'function') continue; if (typeof putObj[prop] === 'object' && putObj[prop]['ReferenceParameters']) { result += '' + putObj[prop].Address + '' + putObj[prop]['ReferenceParameters']['ResourceURI'] + ''; var selectorArray = putObj[prop]['ReferenceParameters']['SelectorSet']['Selector']; if (Array.isArray(selectorArray)) { for (var i=0; i< selectorArray.length; i++) { result += '' + selectorArray[i]['Value'] + ''; } } else { result += '' + selectorArray['Value'] + ''; } result += ''; } else { if (Array.isArray(putObj[prop])) { for (var i = 0; i < putObj[prop].length; i++) { result += '' + putObj[prop][i].toString() + ''; } } else { result += '' + putObj[prop].toString() + ''; } } } result += ''; return result; } /* convert { @Name: 'InstanceID', @AttrName: 'Attribute Value'} into ' Name="InstanceID" AttrName="Attribute Value" ' */ function _ObjectToXmlAttributes(objWithAttributes) { if(!objWithAttributes) return ''; var result = ''; for (var propName in objWithAttributes) { if (!objWithAttributes.hasOwnProperty(propName) || propName.indexOf('@') !== 0) continue; result += ' ' + propName.substring(1) + '="' + objWithAttributes[propName] + '"'; } return result; } function _PutObjToSelectorsXml(selectorSet) { if (!selectorSet) return ''; if (typeof selectorSet == 'string') return selectorSet; if (selectorSet['InstanceID']) return '' + selectorSet['InstanceID'] + ''; var result = ''; for(var propName in selectorSet) { if (!selectorSet.hasOwnProperty(propName)) continue; result += ''; if (selectorSet[propName]['ReferenceParameters']) { result += ''; result += '' + selectorSet[propName]['Address'] + '' + selectorSet[propName]['ReferenceParameters']['ResourceURI'] + ''; var selectorArray = selectorSet[propName]['ReferenceParameters']['SelectorSet']['Selector']; if (Array.isArray(selectorArray)) { for (var i = 0; i < selectorArray.length; i++) { result += '' + selectorArray[i]['Value'] + ''; } } else { result += '' + selectorArray['Value'] + ''; } result += ''; } else { result += selectorSet[propName]; } result += ''; } result += ''; return result; } function _turnToXml(text) { // ###BEGIN###{!Mode-MeshCentral2} // NodeJS detection var isNode = new Function('try {return this===global;}catch(e){return false;}'); if (isNode()) { var XDOMParser = require('xmldom').DOMParser; return new XDOMParser().parseFromString(text, 'text/xml'); } // ###END###{!Mode-MeshCentral2} if (window.DOMParser) { return new DOMParser().parseFromString(text, 'text/xml'); } else { // Internet Explorer var xmlDoc = new ActiveXObject('Microsoft.XMLDOM'); xmlDoc.async = false; xmlDoc.loadXML(text); return xmlDoc; } } /* // This is a drop-in replacement to _turnToXml() that works without xml parser dependency. Object.defineProperty(Array.prototype, 'peek', { value: function () { return (this.length > 0 ? this[this.length - 1] : null); } }); function _treeBuilder() { this.tree = []; this.push = function (element) { this.tree.push(element); }; this.pop = function () { var element = this.tree.pop(); if (this.tree.length > 0) { var x = this.tree.peek(); x.childNodes.push(element); x.childElementCount = x.childNodes.length; } return (element); }; this.peek = function () { return (this.tree.peek()); } this.addNamespace = function (prefix, namespace) { this.tree.peek().nsTable[prefix] = namespace; if (this.tree.peek().attributes.length > 0) { for (var i = 0; i < this.tree.peek().attributes; ++i) { var a = this.tree.peek().attributes[i]; if (prefix == '*' && a.name == a.localName) { a.namespace = namespace; } else if (prefix != '*' && a.name != a.localName) { var pfx = a.name.split(':')[0]; if (pfx == prefix) { a.namespace = namespace; } } } } } this.getNamespace = function (prefix) { for (var i = this.tree.length - 1; i >= 0; --i) { if (this.tree[i].nsTable[prefix] != null) { return (this.tree[i].nsTable[prefix]); } } return null; } } function _turnToXml(text) { if (text == null) return null; return ({ childNodes: [_turnToXmlRec(text)], getElementsByTagName: _getElementsByTagName, getChildElementsByTagName: _getChildElementsByTagName, getElementsByTagNameNS: _getElementsByTagNameNS }); } function _getElementsByTagNameNS(ns, name) { var ret = []; _xmlTraverseAllRec(this.childNodes, function (node) { if (node.localName == name && (node.namespace == ns || ns == '*')) { ret.push(node); } }); return ret; } function _getElementsByTagName(name) { var ret = []; _xmlTraverseAllRec(this.childNodes, function (node) { if (node.localName == name) { ret.push(node); } }); return ret; } function _getChildElementsByTagName(name) { var ret = []; if (this.childNodes != null) { for (var node in this.childNodes) { if (this.childNodes[node].localName == name) { ret.push(this.childNodes[node]); } } } return (ret); } function _getChildElementsByTagNameNS(ns, name) { var ret = []; if (this.childNodes != null) { for (var node in this.childNodes) { if (this.childNodes[node].localName == name && (ns == '*' || this.childNodes[node].namespace == ns)) { ret.push(this.childNodes[node]); } } } return (ret); } function _xmlTraverseAllRec(nodes, func) { for (var i in nodes) { func(nodes[i]); if (nodes[i].childNodes) { _xmlTraverseAllRec(nodes[i].childNodes, func); } } } function _turnToXmlRec(text) { var elementStack = new _treeBuilder(), lastElement = null, x1 = text.split('<'), ret = [], element = null, currentElementName = null; for (var i in x1) { var x2 = x1[i].split('>'), x3 = x2[0].split(' '), elementName = x3[0]; if ((elementName.length > 0) && (elementName[0] != '?')) { if (elementName[0] != '/') { var attributes = [], localName, localname2 = elementName.split(' ')[0].split(':'), localName = (localname2.length > 1) ? localname2[1] : localname2[0]; Object.defineProperty(attributes, 'get', { value: function () { if (arguments.length == 1) { for (var a in this) { if (this[a].name == arguments[0]) { return (this[a]); } } } else if (arguments.length == 2) { for (var a in this) { if (this[a].name == arguments[1] && (arguments[0] == '*' || this[a].namespace == arguments[0])) { return (this[a]); } } } else { throw ('attributes.get(): Invalid number of parameters'); } } }); elementStack.push({ name: elementName, localName: localName, getChildElementsByTagName: _getChildElementsByTagName, getElementsByTagNameNS: _getElementsByTagNameNS, getChildElementsByTagNameNS: _getChildElementsByTagNameNS, attributes: attributes, childNodes: [], nsTable: {} }); // Parse Attributes if (x3.length > 0) { var skip = false; for (var j in x3) { if (x3[j] == '/') { // This is an empty Element elementStack.peek().namespace = elementStack.peek().name == elementStack.peek().localName ? elementStack.getNamespace('*') : elementStack.getNamespace(elementStack.peek().name.substring(0, elementStack.peek().name.indexOf(':'))); elementStack.peek().textContent = ''; lastElement = elementStack.pop(); skip = true; break; } var k = x3[j].indexOf('='); if (k > 0) { var attrName = x3[j].substring(0, k); var attrValue = x3[j].substring(k + 2, x3[j].length - 1); var attrNS = elementStack.getNamespace('*'); if (attrName == 'xmlns') { elementStack.addNamespace('*', attrValue); attrNS = attrValue; } else if (attrName.startsWith('xmlns:')) { elementStack.addNamespace(attrName.substring(6), attrValue); } else { var ax = attrName.split(':'); if (ax.length == 2) { attrName = ax[1]; attrNS = elementStack.getNamespace(ax[0]); } } var x = { name: attrName, value: attrValue } if (attrNS != null) x.namespace = attrNS; elementStack.peek().attributes.push(x); } } if (skip) { continue; } } elementStack.peek().namespace = elementStack.peek().name == elementStack.peek().localName ? elementStack.getNamespace('*') : elementStack.getNamespace(elementStack.peek().name.substring(0, elementStack.peek().name.indexOf(':'))); if (x2[1]) { elementStack.peek().textContent = x2[1]; } } else { lastElement = elementStack.pop(); } } } return lastElement; } */ return obj; }