@azure/ms-rest-js
Version:
Isomorphic client Runtime for Typescript/node.js/browser javascript client libraries generated using AutoRest
1,251 lines (1,242 loc) • 217 kB
JavaScript
/** @license ms-rest-js
* Copyright (c) Microsoft Corporation. All rights reserved.
* Licensed under the MIT License. See License.txt and ThirdPartyNotices.txt in the project root for license information.
*/
'use strict';
Object.defineProperty(exports, '__esModule', { value: true });
function _interopDefault (ex) { return (ex && (typeof ex === 'object') && 'default' in ex) ? ex['default'] : ex; }
var uuid = require('uuid');
var tslib = require('tslib');
var tough = require('tough-cookie');
var http = require('http');
var https = require('https');
var node_fetch = _interopDefault(require('node-fetch'));
var FormData = _interopDefault(require('form-data'));
var stream = require('stream');
var tunnel = require('tunnel');
var xml2js = require('xml2js');
var os = require('os');
// Copyright (c) Microsoft Corporation. All rights reserved.
// Licensed under the MIT License. See License.txt in the project root for license information.
/**
* A collection of HttpHeaders that can be sent with a HTTP request.
*/
function getHeaderKey(headerName) {
return headerName.toLowerCase();
}
function isHttpHeadersLike(object) {
if (!object || typeof object !== "object") {
return false;
}
if (typeof object.rawHeaders === "function" &&
typeof object.clone === "function" &&
typeof object.get === "function" &&
typeof object.set === "function" &&
typeof object.contains === "function" &&
typeof object.remove === "function" &&
typeof object.headersArray === "function" &&
typeof object.headerValues === "function" &&
typeof object.headerNames === "function" &&
typeof object.toJson === "function") {
return true;
}
return false;
}
/**
* A collection of HTTP header key/value pairs.
*/
var HttpHeaders = /** @class */ (function () {
function HttpHeaders(rawHeaders) {
this._headersMap = {};
if (rawHeaders) {
for (var headerName in rawHeaders) {
this.set(headerName, rawHeaders[headerName]);
}
}
}
/**
* Set a header in this collection with the provided name and value. The name is
* case-insensitive.
* @param headerName The name of the header to set. This value is case-insensitive.
* @param headerValue The value of the header to set.
*/
HttpHeaders.prototype.set = function (headerName, headerValue) {
this._headersMap[getHeaderKey(headerName)] = {
name: headerName,
value: headerValue.toString(),
};
};
/**
* Get the header value for the provided header name, or undefined if no header exists in this
* collection with the provided name.
* @param headerName The name of the header.
*/
HttpHeaders.prototype.get = function (headerName) {
var header = this._headersMap[getHeaderKey(headerName)];
return !header ? undefined : header.value;
};
/**
* Get whether or not this header collection contains a header entry for the provided header name.
*/
HttpHeaders.prototype.contains = function (headerName) {
return !!this._headersMap[getHeaderKey(headerName)];
};
/**
* Remove the header with the provided headerName. Return whether or not the header existed and
* was removed.
* @param headerName The name of the header to remove.
*/
HttpHeaders.prototype.remove = function (headerName) {
var result = this.contains(headerName);
delete this._headersMap[getHeaderKey(headerName)];
return result;
};
/**
* Get the headers that are contained this collection as an object.
*/
HttpHeaders.prototype.rawHeaders = function () {
var result = {};
for (var headerKey in this._headersMap) {
var header = this._headersMap[headerKey];
result[header.name.toLowerCase()] = header.value;
}
return result;
};
/**
* Get the headers that are contained in this collection as an array.
*/
HttpHeaders.prototype.headersArray = function () {
var headers = [];
for (var headerKey in this._headersMap) {
headers.push(this._headersMap[headerKey]);
}
return headers;
};
/**
* Get the header names that are contained in this collection.
*/
HttpHeaders.prototype.headerNames = function () {
var headerNames = [];
var headers = this.headersArray();
for (var i = 0; i < headers.length; ++i) {
headerNames.push(headers[i].name);
}
return headerNames;
};
/**
* Get the header names that are contained in this collection.
*/
HttpHeaders.prototype.headerValues = function () {
var headerValues = [];
var headers = this.headersArray();
for (var i = 0; i < headers.length; ++i) {
headerValues.push(headers[i].value);
}
return headerValues;
};
/**
* Get the JSON object representation of this HTTP header collection.
*/
HttpHeaders.prototype.toJson = function () {
return this.rawHeaders();
};
/**
* Get the string representation of this HTTP header collection.
*/
HttpHeaders.prototype.toString = function () {
return JSON.stringify(this.toJson());
};
/**
* Create a deep clone/copy of this HttpHeaders collection.
*/
HttpHeaders.prototype.clone = function () {
return new HttpHeaders(this.rawHeaders());
};
return HttpHeaders;
}());
// Copyright (c) Microsoft Corporation. All rights reserved.
// Licensed under the MIT License. See License.txt in the project root for license information.
/**
* Encodes a string in base64 format.
* @param value the string to encode
*/
function encodeString(value) {
return Buffer.from(value).toString("base64");
}
/**
* Encodes a byte array in base64 format.
* @param value the Uint8Aray to encode
*/
function encodeByteArray(value) {
// Buffer.from accepts <ArrayBuffer> | <SharedArrayBuffer>-- the TypeScript definition is off here
// https://nodejs.org/api/buffer.html#buffer_class_method_buffer_from_arraybuffer_byteoffset_length
var bufferValue = value instanceof Buffer ? value : Buffer.from(value.buffer);
return bufferValue.toString("base64");
}
/**
* Decodes a base64 string into a byte array.
* @param value the base64 string to decode
*/
function decodeString(value) {
return Buffer.from(value, "base64");
}
// Copyright (c) Microsoft Corporation. All rights reserved.
// Licensed under the MIT License. See License.txt in the project root for license information.
var Constants = {
/**
* The ms-rest version
* @const
* @type {string}
*/
msRestVersion: "2.6.4",
/**
* Specifies HTTP.
*
* @const
* @type {string}
*/
HTTP: "http:",
/**
* Specifies HTTPS.
*
* @const
* @type {string}
*/
HTTPS: "https:",
/**
* Specifies HTTP Proxy.
*
* @const
* @type {string}
*/
HTTP_PROXY: "HTTP_PROXY",
/**
* Specifies HTTPS Proxy.
*
* @const
* @type {string}
*/
HTTPS_PROXY: "HTTPS_PROXY",
/**
* Specifies NO Proxy.
*/
NO_PROXY: "NO_PROXY",
/**
* Specifies ALL Proxy.
*/
ALL_PROXY: "ALL_PROXY",
HttpConstants: {
/**
* Http Verbs
*
* @const
* @enum {string}
*/
HttpVerbs: {
PUT: "PUT",
GET: "GET",
DELETE: "DELETE",
POST: "POST",
MERGE: "MERGE",
HEAD: "HEAD",
PATCH: "PATCH",
},
StatusCodes: {
TooManyRequests: 429,
},
},
/**
* Defines constants for use with HTTP headers.
*/
HeaderConstants: {
/**
* The Authorization header.
*
* @const
* @type {string}
*/
AUTHORIZATION: "authorization",
AUTHORIZATION_SCHEME: "Bearer",
/**
* The Retry-After response-header field can be used with a 503 (Service
* Unavailable) or 349 (Too Many Requests) responses to indicate how long
* the service is expected to be unavailable to the requesting client.
*
* @const
* @type {string}
*/
RETRY_AFTER: "Retry-After",
/**
* The UserAgent header.
*
* @const
* @type {string}
*/
USER_AGENT: "User-Agent",
},
};
// Copyright (c) Microsoft Corporation. All rights reserved.
/**
* A constant that indicates whether the environment is node.js or browser based.
*/
var isNode = typeof process !== "undefined" &&
!!process.version &&
!!process.versions &&
!!process.versions.node;
/**
* Encodes an URI.
*
* @param {string} uri The URI to be encoded.
* @return {string} The encoded URI.
*/
function encodeUri(uri) {
return encodeURIComponent(uri)
.replace(/!/g, "%21")
.replace(/"/g, "%27")
.replace(/\(/g, "%28")
.replace(/\)/g, "%29")
.replace(/\*/g, "%2A");
}
/**
* Returns a stripped version of the Http Response which only contains body,
* headers and the status.
*
* @param {HttpOperationResponse} response The Http Response
*
* @return {object} The stripped version of Http Response.
*/
function stripResponse(response) {
var strippedResponse = {};
strippedResponse.body = response.bodyAsText;
strippedResponse.headers = response.headers;
strippedResponse.status = response.status;
return strippedResponse;
}
/**
* Returns a stripped version of the Http Request that does not contain the
* Authorization header.
*
* @param {WebResource} request The Http Request object
*
* @return {WebResource} The stripped version of Http Request.
*/
function stripRequest(request) {
var strippedRequest = request.clone();
if (strippedRequest.headers) {
strippedRequest.headers.remove("authorization");
}
return strippedRequest;
}
/**
* Validates the given uuid as a string
*
* @param {string} uuid The uuid as a string that needs to be validated
*
* @return {boolean} True if the uuid is valid; false otherwise.
*/
function isValidUuid(uuid) {
var validUuidRegex = new RegExp("^[0-9a-fA-F]{8}-[0-9a-fA-F]{4}-[0-9a-fA-F]{4}-[0-9a-fA-F]{4}-[0-9a-fA-F]{12}$", "ig");
return validUuidRegex.test(uuid);
}
/**
* Generated UUID
*
* @return {string} RFC4122 v4 UUID.
*/
function generateUuid() {
return uuid.v4();
}
/**
* Executes an array of promises sequentially. Inspiration of this method is here:
* https://pouchdb.com/2015/05/18/we-have-a-problem-with-promises.html. An awesome blog on promises!
*
* @param {Array} promiseFactories An array of promise factories(A function that return a promise)
*
* @param {any} [kickstart] Input to the first promise that is used to kickstart the promise chain.
* If not provided then the promise chain starts with undefined.
*
* @return A chain of resolved or rejected promises
*/
function executePromisesSequentially(promiseFactories, kickstart) {
var result = Promise.resolve(kickstart);
promiseFactories.forEach(function (promiseFactory) {
result = result.then(promiseFactory);
});
return result;
}
/**
* A wrapper for setTimeout that resolves a promise after t milliseconds.
* @param {number} t The number of milliseconds to be delayed.
* @param {T} value The value to be resolved with after a timeout of t milliseconds.
* @returns {Promise<T>} Resolved promise
*/
function delay(t, value) {
return new Promise(function (resolve) { return setTimeout(function () { return resolve(value); }, t); });
}
/**
* Converts a Promise to a callback.
* @param {Promise<any>} promise The Promise to be converted to a callback
* @returns {Function} A function that takes the callback (cb: Function): void
* @deprecated generated code should instead depend on responseToBody
*/
function promiseToCallback(promise) {
if (typeof promise.then !== "function") {
throw new Error("The provided input is not a Promise.");
}
return function (cb) {
promise.then(function (data) {
cb(undefined, data);
}, function (err) {
cb(err);
});
};
}
/**
* Converts a Promise to a service callback.
* @param {Promise<HttpOperationResponse>} promise - The Promise of HttpOperationResponse to be converted to a service callback
* @returns {Function} A function that takes the service callback (cb: ServiceCallback<T>): void
*/
function promiseToServiceCallback(promise) {
if (typeof promise.then !== "function") {
throw new Error("The provided input is not a Promise.");
}
return function (cb) {
promise.then(function (data) {
process.nextTick(cb, undefined, data.parsedBody, data.request, data);
}, function (err) {
process.nextTick(cb, err);
});
};
}
function prepareXMLRootList(obj, elementName) {
var _a;
if (!Array.isArray(obj)) {
obj = [obj];
}
return _a = {}, _a[elementName] = obj, _a;
}
/**
* Applies the properties on the prototype of sourceCtors to the prototype of targetCtor
* @param {object} targetCtor The target object on which the properties need to be applied.
* @param {Array<object>} sourceCtors An array of source objects from which the properties need to be taken.
*/
function applyMixins(targetCtor, sourceCtors) {
sourceCtors.forEach(function (sourceCtors) {
Object.getOwnPropertyNames(sourceCtors.prototype).forEach(function (name) {
targetCtor.prototype[name] = sourceCtors.prototype[name];
});
});
}
var validateISODuration = /^(-|\+)?P(?:([-+]?[0-9,.]*)Y)?(?:([-+]?[0-9,.]*)M)?(?:([-+]?[0-9,.]*)W)?(?:([-+]?[0-9,.]*)D)?(?:T(?:([-+]?[0-9,.]*)H)?(?:([-+]?[0-9,.]*)M)?(?:([-+]?[0-9,.]*)S)?)?$/;
/**
* Indicates whether the given string is in ISO 8601 format.
* @param {string} value The value to be validated for ISO 8601 duration format.
* @return {boolean} `true` if valid, `false` otherwise.
*/
function isDuration(value) {
return validateISODuration.test(value);
}
/**
* Replace all of the instances of searchValue in value with the provided replaceValue.
* @param {string | undefined} value The value to search and replace in.
* @param {string} searchValue The value to search for in the value argument.
* @param {string} replaceValue The value to replace searchValue with in the value argument.
* @returns {string | undefined} The value where each instance of searchValue was replaced with replacedValue.
*/
function replaceAll(value, searchValue, replaceValue) {
return !value || !searchValue ? value : value.split(searchValue).join(replaceValue || "");
}
/**
* Determines whether the given enity is a basic/primitive type
* (string, number, boolean, null, undefined).
* @param value Any entity
* @return boolean - true is it is primitive type, false otherwise.
*/
function isPrimitiveType(value) {
return (typeof value !== "object" && typeof value !== "function") || value === null;
}
// Copyright (c) Microsoft Corporation. All rights reserved.
var Serializer = /** @class */ (function () {
function Serializer(modelMappers, isXML) {
if (modelMappers === void 0) { modelMappers = {}; }
this.modelMappers = modelMappers;
this.isXML = isXML;
}
Serializer.prototype.validateConstraints = function (mapper, value, objectName) {
var failValidation = function (constraintName, constraintValue) {
throw new Error("\"" + objectName + "\" with value \"" + value + "\" should satisfy the constraint \"" + constraintName + "\": " + constraintValue + ".");
};
if (mapper.constraints && value != undefined) {
var _a = mapper.constraints, ExclusiveMaximum = _a.ExclusiveMaximum, ExclusiveMinimum = _a.ExclusiveMinimum, InclusiveMaximum = _a.InclusiveMaximum, InclusiveMinimum = _a.InclusiveMinimum, MaxItems = _a.MaxItems, MaxLength = _a.MaxLength, MinItems = _a.MinItems, MinLength = _a.MinLength, MultipleOf = _a.MultipleOf, Pattern = _a.Pattern, UniqueItems = _a.UniqueItems;
if (ExclusiveMaximum != undefined && value >= ExclusiveMaximum) {
failValidation("ExclusiveMaximum", ExclusiveMaximum);
}
if (ExclusiveMinimum != undefined && value <= ExclusiveMinimum) {
failValidation("ExclusiveMinimum", ExclusiveMinimum);
}
if (InclusiveMaximum != undefined && value > InclusiveMaximum) {
failValidation("InclusiveMaximum", InclusiveMaximum);
}
if (InclusiveMinimum != undefined && value < InclusiveMinimum) {
failValidation("InclusiveMinimum", InclusiveMinimum);
}
if (MaxItems != undefined && value.length > MaxItems) {
failValidation("MaxItems", MaxItems);
}
if (MaxLength != undefined && value.length > MaxLength) {
failValidation("MaxLength", MaxLength);
}
if (MinItems != undefined && value.length < MinItems) {
failValidation("MinItems", MinItems);
}
if (MinLength != undefined && value.length < MinLength) {
failValidation("MinLength", MinLength);
}
if (MultipleOf != undefined && value % MultipleOf !== 0) {
failValidation("MultipleOf", MultipleOf);
}
if (Pattern) {
var pattern = typeof Pattern === "string" ? new RegExp(Pattern) : Pattern;
if (typeof value !== "string" || value.match(pattern) === null) {
failValidation("Pattern", Pattern);
}
}
if (UniqueItems &&
value.some(function (item, i, ar) { return ar.indexOf(item) !== i; })) {
failValidation("UniqueItems", UniqueItems);
}
}
};
/**
* Serialize the given object based on its metadata defined in the mapper
*
* @param {Mapper} mapper The mapper which defines the metadata of the serializable object
*
* @param {object|string|Array|number|boolean|Date|stream} object A valid Javascript object to be serialized
*
* @param {string} objectName Name of the serialized object
*
* @returns {object|string|Array|number|boolean|Date|stream} A valid serialized Javascript object
*/
Serializer.prototype.serialize = function (mapper, object, objectName) {
var payload = {};
var mapperType = mapper.type.name;
if (!objectName) {
objectName = mapper.serializedName;
}
if (mapperType.match(/^Sequence$/gi) !== null) {
payload = [];
}
if (mapper.isConstant) {
object = mapper.defaultValue;
}
// This table of allowed values should help explain
// the mapper.required and mapper.nullable properties.
// X means "neither undefined or null are allowed".
// || required
// || true | false
// nullable || ==========================
// true || null | undefined/null
// false || X | undefined
// undefined || X | undefined/null
var required = mapper.required, nullable = mapper.nullable;
if (required && nullable && object === undefined) {
throw new Error(objectName + " cannot be undefined.");
}
if (required && !nullable && object == undefined) {
throw new Error(objectName + " cannot be null or undefined.");
}
if (!required && nullable === false && object === null) {
throw new Error(objectName + " cannot be null.");
}
if (object == undefined) {
payload = object;
}
else {
// Validate Constraints if any
this.validateConstraints(mapper, object, objectName);
if (mapperType.match(/^any$/gi) !== null) {
payload = object;
}
else if (mapperType.match(/^(Number|String|Boolean|Object|Stream|Uuid)$/gi) !== null) {
payload = serializeBasicTypes(mapperType, objectName, object);
}
else if (mapperType.match(/^Enum$/gi) !== null) {
var enumMapper = mapper;
payload = serializeEnumType(objectName, enumMapper.type.allowedValues, object);
}
else if (mapperType.match(/^(Date|DateTime|TimeSpan|DateTimeRfc1123|UnixTime)$/gi) !== null) {
payload = serializeDateTypes(mapperType, object, objectName);
}
else if (mapperType.match(/^ByteArray$/gi) !== null) {
payload = serializeByteArrayType(objectName, object);
}
else if (mapperType.match(/^Base64Url$/gi) !== null) {
payload = serializeBase64UrlType(objectName, object);
}
else if (mapperType.match(/^Sequence$/gi) !== null) {
payload = serializeSequenceType(this, mapper, object, objectName);
}
else if (mapperType.match(/^Dictionary$/gi) !== null) {
payload = serializeDictionaryType(this, mapper, object, objectName);
}
else if (mapperType.match(/^Composite$/gi) !== null) {
payload = serializeCompositeType(this, mapper, object, objectName);
}
}
return payload;
};
/**
* Deserialize the given object based on its metadata defined in the mapper
*
* @param {object} mapper The mapper which defines the metadata of the serializable object
*
* @param {object|string|Array|number|boolean|Date|stream} responseBody A valid Javascript entity to be deserialized
*
* @param {string} objectName Name of the deserialized object
*
* @returns {object|string|Array|number|boolean|Date|stream} A valid deserialized Javascript object
*/
Serializer.prototype.deserialize = function (mapper, responseBody, objectName) {
if (responseBody == undefined) {
if (this.isXML && mapper.type.name === "Sequence" && !mapper.xmlIsWrapped) {
// Edge case for empty XML non-wrapped lists. xml2js can't distinguish
// between the list being empty versus being missing,
// so let's do the more user-friendly thing and return an empty list.
responseBody = [];
}
// specifically check for undefined as default value can be a falsey value `0, "", false, null`
if (mapper.defaultValue !== undefined) {
responseBody = mapper.defaultValue;
}
return responseBody;
}
var payload;
var mapperType = mapper.type.name;
if (!objectName) {
objectName = mapper.serializedName;
}
if (mapperType.match(/^Composite$/gi) !== null) {
payload = deserializeCompositeType(this, mapper, responseBody, objectName);
}
else {
if (this.isXML) {
/**
* If the mapper specifies this as a non-composite type value but the responseBody contains
* both header ("$") and body ("_") properties, then just reduce the responseBody value to
* the body ("_") property.
*/
if (responseBody["$"] != undefined && responseBody["_"] != undefined) {
responseBody = responseBody["_"];
}
}
if (mapperType.match(/^Number$/gi) !== null) {
payload = parseFloat(responseBody);
if (isNaN(payload)) {
payload = responseBody;
}
}
else if (mapperType.match(/^Boolean$/gi) !== null) {
if (responseBody === "true") {
payload = true;
}
else if (responseBody === "false") {
payload = false;
}
else {
payload = responseBody;
}
}
else if (mapperType.match(/^(String|Enum|Object|Stream|Uuid|TimeSpan|any)$/gi) !== null) {
payload = responseBody;
}
else if (mapperType.match(/^(Date|DateTime|DateTimeRfc1123)$/gi) !== null) {
payload = new Date(responseBody);
}
else if (mapperType.match(/^UnixTime$/gi) !== null) {
payload = unixTimeToDate(responseBody);
}
else if (mapperType.match(/^ByteArray$/gi) !== null) {
payload = decodeString(responseBody);
}
else if (mapperType.match(/^Base64Url$/gi) !== null) {
payload = base64UrlToByteArray(responseBody);
}
else if (mapperType.match(/^Sequence$/gi) !== null) {
payload = deserializeSequenceType(this, mapper, responseBody, objectName);
}
else if (mapperType.match(/^Dictionary$/gi) !== null) {
payload = deserializeDictionaryType(this, mapper, responseBody, objectName);
}
}
if (mapper.isConstant) {
payload = mapper.defaultValue;
}
return payload;
};
return Serializer;
}());
function trimEnd(str, ch) {
var len = str.length;
while (len - 1 >= 0 && str[len - 1] === ch) {
--len;
}
return str.substr(0, len);
}
function bufferToBase64Url(buffer) {
if (!buffer) {
return undefined;
}
if (!(buffer instanceof Uint8Array)) {
throw new Error("Please provide an input of type Uint8Array for converting to Base64Url.");
}
// Uint8Array to Base64.
var str = encodeByteArray(buffer);
// Base64 to Base64Url.
return trimEnd(str, "=").replace(/\+/g, "-").replace(/\//g, "_");
}
function base64UrlToByteArray(str) {
if (!str) {
return undefined;
}
if (str && typeof str.valueOf() !== "string") {
throw new Error("Please provide an input of type string for converting to Uint8Array");
}
// Base64Url to Base64.
str = str.replace(/\-/g, "+").replace(/\_/g, "/");
// Base64 to Uint8Array.
return decodeString(str);
}
function splitSerializeName(prop) {
var classes = [];
var partialclass = "";
if (prop) {
var subwords = prop.split(".");
for (var _i = 0, subwords_1 = subwords; _i < subwords_1.length; _i++) {
var item = subwords_1[_i];
if (item.charAt(item.length - 1) === "\\") {
partialclass += item.substr(0, item.length - 1) + ".";
}
else {
partialclass += item;
classes.push(partialclass);
partialclass = "";
}
}
}
return classes;
}
function dateToUnixTime(d) {
if (!d) {
return undefined;
}
if (typeof d.valueOf() === "string") {
d = new Date(d);
}
return Math.floor(d.getTime() / 1000);
}
function unixTimeToDate(n) {
if (!n) {
return undefined;
}
return new Date(n * 1000);
}
function serializeBasicTypes(typeName, objectName, value) {
if (value !== null && value !== undefined) {
if (typeName.match(/^Number$/gi) !== null) {
if (typeof value !== "number") {
throw new Error(objectName + " with value " + value + " must be of type number.");
}
}
else if (typeName.match(/^String$/gi) !== null) {
if (typeof value.valueOf() !== "string") {
throw new Error(objectName + " with value \"" + value + "\" must be of type string.");
}
}
else if (typeName.match(/^Uuid$/gi) !== null) {
if (!(typeof value.valueOf() === "string" && isValidUuid(value))) {
throw new Error(objectName + " with value \"" + value + "\" must be of type string and a valid uuid.");
}
}
else if (typeName.match(/^Boolean$/gi) !== null) {
if (typeof value !== "boolean") {
throw new Error(objectName + " with value " + value + " must be of type boolean.");
}
}
else if (typeName.match(/^Stream$/gi) !== null) {
var objectType = typeof value;
if (objectType !== "string" &&
objectType !== "function" &&
!(value instanceof ArrayBuffer) &&
!ArrayBuffer.isView(value) &&
!(typeof Blob === "function" && value instanceof Blob)) {
throw new Error(objectName + " must be a string, Blob, ArrayBuffer, ArrayBufferView, or a function returning NodeJS.ReadableStream.");
}
}
}
return value;
}
function serializeEnumType(objectName, allowedValues, value) {
if (!allowedValues) {
throw new Error("Please provide a set of allowedValues to validate " + objectName + " as an Enum Type.");
}
var isPresent = allowedValues.some(function (item) {
if (typeof item.valueOf() === "string") {
return item.toLowerCase() === value.toLowerCase();
}
return item === value;
});
if (!isPresent) {
throw new Error(value + " is not a valid value for " + objectName + ". The valid values are: " + JSON.stringify(allowedValues) + ".");
}
return value;
}
function serializeByteArrayType(objectName, value) {
if (value != undefined) {
if (!(value instanceof Uint8Array)) {
throw new Error(objectName + " must be of type Uint8Array.");
}
value = encodeByteArray(value);
}
return value;
}
function serializeBase64UrlType(objectName, value) {
if (value != undefined) {
if (!(value instanceof Uint8Array)) {
throw new Error(objectName + " must be of type Uint8Array.");
}
value = bufferToBase64Url(value);
}
return value;
}
function serializeDateTypes(typeName, value, objectName) {
if (value != undefined) {
if (typeName.match(/^Date$/gi) !== null) {
if (!(value instanceof Date ||
(typeof value.valueOf() === "string" && !isNaN(Date.parse(value))))) {
throw new Error(objectName + " must be an instanceof Date or a string in ISO8601 format.");
}
value =
value instanceof Date
? value.toISOString().substring(0, 10)
: new Date(value).toISOString().substring(0, 10);
}
else if (typeName.match(/^DateTime$/gi) !== null) {
if (!(value instanceof Date ||
(typeof value.valueOf() === "string" && !isNaN(Date.parse(value))))) {
throw new Error(objectName + " must be an instanceof Date or a string in ISO8601 format.");
}
value = value instanceof Date ? value.toISOString() : new Date(value).toISOString();
}
else if (typeName.match(/^DateTimeRfc1123$/gi) !== null) {
if (!(value instanceof Date ||
(typeof value.valueOf() === "string" && !isNaN(Date.parse(value))))) {
throw new Error(objectName + " must be an instanceof Date or a string in RFC-1123 format.");
}
value = value instanceof Date ? value.toUTCString() : new Date(value).toUTCString();
}
else if (typeName.match(/^UnixTime$/gi) !== null) {
if (!(value instanceof Date ||
(typeof value.valueOf() === "string" && !isNaN(Date.parse(value))))) {
throw new Error(objectName + " must be an instanceof Date or a string in RFC-1123/ISO8601 format " +
"for it to be serialized in UnixTime/Epoch format.");
}
value = dateToUnixTime(value);
}
else if (typeName.match(/^TimeSpan$/gi) !== null) {
if (!isDuration(value)) {
throw new Error(objectName + " must be a string in ISO 8601 format. Instead was \"" + value + "\".");
}
value = value;
}
}
return value;
}
function serializeSequenceType(serializer, mapper, object, objectName) {
if (!Array.isArray(object)) {
throw new Error(objectName + " must be of type Array.");
}
var elementType = mapper.type.element;
if (!elementType || typeof elementType !== "object") {
throw new Error("element\" metadata for an Array must be defined in the " +
("mapper and it must of type \"object\" in " + objectName + "."));
}
var tempArray = [];
for (var i = 0; i < object.length; i++) {
tempArray[i] = serializer.serialize(elementType, object[i], objectName);
}
return tempArray;
}
function serializeDictionaryType(serializer, mapper, object, objectName) {
if (typeof object !== "object") {
throw new Error(objectName + " must be of type object.");
}
var valueType = mapper.type.value;
if (!valueType || typeof valueType !== "object") {
throw new Error("\"value\" metadata for a Dictionary must be defined in the " +
("mapper and it must of type \"object\" in " + objectName + "."));
}
var tempDictionary = {};
for (var _i = 0, _a = Object.keys(object); _i < _a.length; _i++) {
var key = _a[_i];
tempDictionary[key] = serializer.serialize(valueType, object[key], objectName + "." + key);
}
return tempDictionary;
}
/**
* Resolves a composite mapper's modelProperties.
* @param serializer the serializer containing the entire set of mappers
* @param mapper the composite mapper to resolve
*/
function resolveModelProperties(serializer, mapper, objectName) {
var modelProps = mapper.type.modelProperties;
if (!modelProps) {
var className = mapper.type.className;
if (!className) {
throw new Error("Class name for model \"" + objectName + "\" is not provided in the mapper \"" + JSON.stringify(mapper, undefined, 2) + "\".");
}
var modelMapper = serializer.modelMappers[className];
if (!modelMapper) {
throw new Error("mapper() cannot be null or undefined for model \"" + className + "\".");
}
modelProps = modelMapper.type.modelProperties;
if (!modelProps) {
throw new Error("modelProperties cannot be null or undefined in the " +
("mapper \"" + JSON.stringify(modelMapper) + "\" of type \"" + className + "\" for object \"" + objectName + "\"."));
}
}
return modelProps;
}
function serializeCompositeType(serializer, mapper, object, objectName) {
var _a;
if (getPolymorphicDiscriminatorRecursively(serializer, mapper)) {
mapper = getPolymorphicMapper(serializer, mapper, object, "clientName");
}
if (object != undefined) {
var payload = {};
var modelProps = resolveModelProperties(serializer, mapper, objectName);
for (var _i = 0, _b = Object.keys(modelProps); _i < _b.length; _i++) {
var key = _b[_i];
var propertyMapper = modelProps[key];
if (propertyMapper.readOnly) {
continue;
}
var propName = void 0;
var parentObject = payload;
if (serializer.isXML) {
if (propertyMapper.xmlIsWrapped) {
propName = propertyMapper.xmlName;
}
else {
propName = propertyMapper.xmlElementName || propertyMapper.xmlName;
}
}
else {
var paths = splitSerializeName(propertyMapper.serializedName);
propName = paths.pop();
for (var _c = 0, paths_1 = paths; _c < paths_1.length; _c++) {
var pathName = paths_1[_c];
var childObject = parentObject[pathName];
if (childObject == undefined && object[key] != undefined) {
parentObject[pathName] = {};
}
parentObject = parentObject[pathName];
}
}
if (parentObject != undefined) {
var propertyObjectName = propertyMapper.serializedName !== ""
? objectName + "." + propertyMapper.serializedName
: objectName;
var toSerialize = object[key];
var polymorphicDiscriminator = getPolymorphicDiscriminatorRecursively(serializer, mapper);
if (polymorphicDiscriminator &&
polymorphicDiscriminator.clientName === key &&
toSerialize == undefined) {
toSerialize = mapper.serializedName;
}
var serializedValue = serializer.serialize(propertyMapper, toSerialize, propertyObjectName);
if (serializedValue !== undefined && propName != undefined) {
if (propertyMapper.xmlIsAttribute) {
// $ is the key attributes are kept under in xml2js.
// This keeps things simple while preventing name collision
// with names in user documents.
parentObject.$ = parentObject.$ || {};
parentObject.$[propName] = serializedValue;
}
else if (propertyMapper.xmlIsWrapped) {
parentObject[propName] = (_a = {}, _a[propertyMapper.xmlElementName] = serializedValue, _a);
}
else {
parentObject[propName] = serializedValue;
}
}
}
}
var additionalPropertiesMapper = mapper.type.additionalProperties;
if (additionalPropertiesMapper) {
var propNames = Object.keys(modelProps);
var _loop_1 = function (clientPropName) {
var isAdditionalProperty = propNames.every(function (pn) { return pn !== clientPropName; });
if (isAdditionalProperty) {
payload[clientPropName] = serializer.serialize(additionalPropertiesMapper, object[clientPropName], objectName + '["' + clientPropName + '"]');
}
};
for (var clientPropName in object) {
_loop_1(clientPropName);
}
}
return payload;
}
return object;
}
function isSpecialXmlProperty(propertyName) {
return ["$", "_"].includes(propertyName);
}
function deserializeCompositeType(serializer, mapper, responseBody, objectName) {
if (getPolymorphicDiscriminatorRecursively(serializer, mapper)) {
mapper = getPolymorphicMapper(serializer, mapper, responseBody, "serializedName");
}
var modelProps = resolveModelProperties(serializer, mapper, objectName);
var instance = {};
var handledPropertyNames = [];
for (var _i = 0, _a = Object.keys(modelProps); _i < _a.length; _i++) {
var key = _a[_i];
var propertyMapper = modelProps[key];
var paths = splitSerializeName(modelProps[key].serializedName);
handledPropertyNames.push(paths[0]);
var serializedName = propertyMapper.serializedName, xmlName = propertyMapper.xmlName, xmlElementName = propertyMapper.xmlElementName;
var propertyObjectName = objectName;
if (serializedName !== "" && serializedName !== undefined) {
propertyObjectName = objectName + "." + serializedName;
}
var headerCollectionPrefix = propertyMapper.headerCollectionPrefix;
if (headerCollectionPrefix) {
var dictionary = {};
for (var _b = 0, _c = Object.keys(responseBody); _b < _c.length; _b++) {
var headerKey = _c[_b];
if (headerKey.startsWith(headerCollectionPrefix)) {
dictionary[headerKey.substring(headerCollectionPrefix.length)] = serializer.deserialize(propertyMapper.type.value, responseBody[headerKey], propertyObjectName);
}
handledPropertyNames.push(headerKey);
}
instance[key] = dictionary;
}
else if (serializer.isXML) {
if (propertyMapper.xmlIsAttribute && responseBody.$) {
instance[key] = serializer.deserialize(propertyMapper, responseBody.$[xmlName], propertyObjectName);
}
else {
var propertyName = xmlElementName || xmlName || serializedName;
var unwrappedProperty = responseBody[propertyName];
if (propertyMapper.xmlIsWrapped) {
unwrappedProperty = responseBody[xmlName];
unwrappedProperty = unwrappedProperty && unwrappedProperty[xmlElementName];
var isEmptyWrappedList = unwrappedProperty === undefined;
if (isEmptyWrappedList) {
unwrappedProperty = [];
}
}
instance[key] = serializer.deserialize(propertyMapper, unwrappedProperty, propertyObjectName);
}
}
else {
// deserialize the property if it is present in the provided responseBody instance
var propertyInstance = void 0;
var res = responseBody;
// traversing the object step by step.
for (var _d = 0, paths_2 = paths; _d < paths_2.length; _d++) {
var item = paths_2[_d];
if (!res)
break;
res = res[item];
}
propertyInstance = res;
var polymorphicDiscriminator = mapper.type.polymorphicDiscriminator;
// checking that the model property name (key)(ex: "fishtype") and the
// clientName of the polymorphicDiscriminator {metadata} (ex: "fishtype")
// instead of the serializedName of the polymorphicDiscriminator (ex: "fish.type")
// is a better approach. The generator is not consistent with escaping '\.' in the
// serializedName of the property (ex: "fish\.type") that is marked as polymorphic discriminator
// and the serializedName of the metadata polymorphicDiscriminator (ex: "fish.type"). However,
// the clientName transformation of the polymorphicDiscriminator (ex: "fishtype") and
// the transformation of model property name (ex: "fishtype") is done consistently.
// Hence, it is a safer bet to rely on the clientName of the polymorphicDiscriminator.
if (polymorphicDiscriminator &&
key === polymorphicDiscriminator.clientName &&
propertyInstance == undefined) {
propertyInstance = mapper.serializedName;
}
var serializedValue = void 0;
// paging
if (Array.isArray(responseBody[key]) && modelProps[key].serializedName === "") {
propertyInstance = responseBody[key];
var arrayInstance = serializer.deserialize(propertyMapper, propertyInstance, propertyObjectName);
// Copy over any properties that have already been added into the instance, where they do
// not exist on the newly de-serialized array
for (var _e = 0, _f = Object.entries(instance); _e < _f.length; _e++) {
var _g = _f[_e], key_1 = _g[0], value = _g[1];
if (!arrayInstance.hasOwnProperty(key_1)) {
arrayInstance[key_1] = value;
}
}
instance = arrayInstance;
}
else if (propertyInstance !== undefined || propertyMapper.defaultValue !== undefined) {
serializedValue = serializer.deserialize(propertyMapper, propertyInstance, propertyObjectName);
instance[key] = serializedValue;
}
}
}
var additionalPropertiesMapper = mapper.type.additionalProperties;
if (additionalPropertiesMapper) {
var isAdditionalProperty = function (responsePropName) {
for (var clientPropName in modelProps) {
var paths = splitSerializeName(modelProps[clientPropName].serializedName);
if (paths[0] === responsePropName) {
return false;
}
}
return true;
};
for (var responsePropName in responseBody) {
if (isAdditionalProperty(responsePropName)) {
instance[responsePropName] = serializer.deserialize(additionalPropertiesMapper, responseBody[responsePropName], objectName + '["' + responsePropName + '"]');
}
}
}
else if (responseBody) {
for (var _h = 0, _j = Object.keys(responseBody); _h < _j.length; _h++) {
var key = _j[_h];
if (instance[key] === undefined &&
!handledPropertyNames.includes(key) &&
!isSpecialXmlProperty(key)) {
instance[key] = responseBody[key];
}
}
}
return instance;
}
function deserializeDictionaryType(serializer, mapper, responseBody, objectName) {
/*jshint validthis: true */
var value = mapper.type.value;
if (!value || typeof value !== "object") {
throw new Error("\"value\" metadata for a Dictionary must be defined in the " +
("mapper and it must of type \"object\" in " + objectName));
}
if (responseBody) {
var tempDictionary = {};
for (var _i = 0, _a = Object.keys(responseBody); _i < _a.length; _i++) {
var key = _a[_i];
tempDictionary[key] = serializer.deserialize(value, responseBody[key], objectName);
}
return tempDictionary;
}
return responseBody;
}
function deserializeSequenceType(serializer, mapper, responseBody, objectName) {
/*jshint validthis: true */
var element = mapper.type.element;
if (!element || typeof element !== "object") {
throw new Error("element\" metadata for an Array must be defined in the " +
("mapper and it must of type \"object\" in " + objectName));
}
if (responseBody) {
if (!Array.isArray(responseBody)) {
// xml2js will interpret a single element array as just the element, so force it to be an array
responseBody = [responseBody];
}
var tempArray = [];
for (var i = 0; i < responseBody.length; i++) {
tempArray[i] = serializer.deserialize(element, responseBody[i], objectName + "[" + i + "]");
}
return tempArray;
}
return responseBody;
}
function getPolymorphicMapper(serializer, mapper, object, polymorphicPropertyName) {
var polymorphicDiscriminator = getPolymorphicDiscriminatorRecursively(serializer, mapper);
if (polymorphicDiscriminator) {
var discriminatorName = polymorphicDiscriminator[polymorphicPropertyName];
if (discriminatorName != undefined) {
var discriminatorValue = object[discriminatorName];
if (discriminatorValue != undefined) {
var typeName = mapper.type.uberParent || mapper.type.className;
var indexDiscriminator = discriminatorValue === typeName
? discriminatorValue
: typeName + "." + discriminatorValue;
var polymorphicMapper = serializer.modelMappers.discriminators[indexDiscriminator];
if (polymorphicMapper) {
mapper = polymorphicMapper;
}
}
}
}
return mapper;
}
function getPolymorphicDiscriminatorRecursively(serializer, mapper) {
return (mapper.type.polymorphicDiscriminator ||
getPolymorphicDiscriminatorSafely(serializer, mapper.type.uberParent) ||
getPolymorphicDiscriminatorSafely(serializer, mapper.type.className));
}
function getPolymorphicDiscriminatorSafely(serializer, typeName) {
return (typeName &&
serializer.modelMappers[typeName] &&
serializer.modelMappers[typeName].type.polymorphicDiscriminator);
}
// TODO: why is this here?
function serializeObject(toSerialize) {
if (toSerialize == undefined)
return undefined;
if (toSerialize instanceof Uint8Array) {
toSerialize = encodeByteArray(toSerialize);
return toSerialize;
}
else if (toSerialize instanceof Date) {
return toSerialize.toISOString();
}
else if (Array.isArray(toSerialize)) {
var array = [];
for (var i = 0; i < toSerialize.length; i++) {
array.push(serializeObject(toSerialize[i]));
}
return array;
}
else if (typeof toSerialize === "object") {
var dictionary = {};
for (var property in toSerialize) {
dictionary[property] = serializeObject(toSerialize[property]);
}
return dictionary;
}
return toSerialize;
}
/**
* Utility function to create a K:V from a list of strings
*/
function strEnum(o) {
var result = {};
for (var _i = 0, o_1 = o; _i < o_1.length; _i++) {
var key = o_1[_i];
result[key] = key;
}
return result;
}
var MapperType = strEnum([
"Base64Url",
"Boolean",
"ByteArray",
"Composite",
"Date",
"DateTime",
"DateTimeRfc1123",
"Dictionary",
"Enum",
"Number",
"Object",
"Sequence",
"String",
"Stream",
"TimeSpan",
"UnixTime",
]);
// Copyright (c) Microsoft Corporation. All rights reserved