wangzhibo
2026-05-09 53418655c061ac26f66058253f39200aced1ab1d
1
{"version":3,"file":"serializationPolicy.js","sourceRoot":"","sources":["../../src/serializationPolicy.ts"],"names":[],"mappings":"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","sourcesContent":["// Copyright (c) Microsoft Corporation.\n// Licensed under the MIT License.\n\nimport type {\n  DictionaryMapper,\n  OperationArguments,\n  OperationRequest,\n  OperationSpec,\n  RequiredSerializerOptions,\n  SerializerOptions,\n  XmlOptions,\n} from \"./interfaces.js\";\nimport { XML_ATTRKEY, XML_CHARKEY } from \"./interfaces.js\";\nimport type { PipelinePolicy, PipelineResponse, SendRequest } from \"@azure/core-rest-pipeline\";\nimport {\n  getOperationArgumentValueFromParameter,\n  getOperationRequestInfo,\n} from \"./operationHelpers.js\";\nimport { MapperTypeNames } from \"./serializer.js\";\nimport { getPathStringFromParameter } from \"./interfaceHelpers.js\";\n\n/**\n * The programmatic identifier of the serializationPolicy.\n */\nexport const serializationPolicyName = \"serializationPolicy\";\n\n/**\n * Options to configure API request serialization.\n */\nexport interface SerializationPolicyOptions {\n  /**\n   * A function that is able to write XML. Required for XML support.\n   */\n  stringifyXML?: (obj: any, opts?: XmlOptions) => string;\n\n  /**\n   * Configures behavior of xml parser and builder.\n   */\n  serializerOptions?: SerializerOptions;\n}\n\n/**\n * This policy handles assembling the request body and headers using\n * an OperationSpec and OperationArguments on the request.\n */\nexport function serializationPolicy(options: SerializationPolicyOptions = {}): PipelinePolicy {\n  const stringifyXML = options.stringifyXML;\n\n  return {\n    name: serializationPolicyName,\n    async sendRequest(request: OperationRequest, next: SendRequest): Promise<PipelineResponse> {\n      const operationInfo = getOperationRequestInfo(request);\n      const operationSpec = operationInfo?.operationSpec;\n      const operationArguments = operationInfo?.operationArguments;\n      if (operationSpec && operationArguments) {\n        serializeHeaders(request, operationArguments, operationSpec);\n        serializeRequestBody(request, operationArguments, operationSpec, stringifyXML);\n      }\n      return next(request);\n    },\n  };\n}\n\n/**\n * @internal\n */\nexport function serializeHeaders(\n  request: OperationRequest,\n  operationArguments: OperationArguments,\n  operationSpec: OperationSpec,\n): void {\n  if (operationSpec.headerParameters) {\n    for (const headerParameter of operationSpec.headerParameters) {\n      let headerValue = getOperationArgumentValueFromParameter(operationArguments, headerParameter);\n      if ((headerValue !== null && headerValue !== undefined) || headerParameter.mapper.required) {\n        headerValue = operationSpec.serializer.serialize(\n          headerParameter.mapper,\n          headerValue,\n          getPathStringFromParameter(headerParameter),\n        );\n        const headerCollectionPrefix = (headerParameter.mapper as DictionaryMapper)\n          .headerCollectionPrefix;\n        if (headerCollectionPrefix) {\n          for (const key of Object.keys(headerValue)) {\n            request.headers.set(headerCollectionPrefix + key, headerValue[key]);\n          }\n        } else {\n          request.headers.set(\n            headerParameter.mapper.serializedName || getPathStringFromParameter(headerParameter),\n            headerValue,\n          );\n        }\n      }\n    }\n  }\n  const customHeaders = operationArguments.options?.requestOptions?.customHeaders;\n  if (customHeaders) {\n    for (const customHeaderName of Object.keys(customHeaders)) {\n      request.headers.set(customHeaderName, customHeaders[customHeaderName]);\n    }\n  }\n}\n\n/**\n * @internal\n */\nexport function serializeRequestBody(\n  request: OperationRequest,\n  operationArguments: OperationArguments,\n  operationSpec: OperationSpec,\n  stringifyXML: (obj: any, opts?: XmlOptions) => string = function () {\n    throw new Error(\"XML serialization unsupported!\");\n  },\n): void {\n  const serializerOptions = operationArguments.options?.serializerOptions;\n  const updatedOptions: RequiredSerializerOptions = {\n    xml: {\n      rootName: serializerOptions?.xml.rootName ?? \"\",\n      includeRoot: serializerOptions?.xml.includeRoot ?? false,\n      xmlCharKey: serializerOptions?.xml.xmlCharKey ?? XML_CHARKEY,\n    },\n  };\n\n  const xmlCharKey = updatedOptions.xml.xmlCharKey;\n  if (operationSpec.requestBody && operationSpec.requestBody.mapper) {\n    request.body = getOperationArgumentValueFromParameter(\n      operationArguments,\n      operationSpec.requestBody,\n    );\n\n    const bodyMapper = operationSpec.requestBody.mapper;\n    const {\n      required,\n      serializedName,\n      xmlName,\n      xmlElementName,\n      xmlNamespace,\n      xmlNamespacePrefix,\n      nullable,\n    } = bodyMapper;\n    const typeName = bodyMapper.type.name;\n\n    try {\n      if (\n        (request.body !== undefined && request.body !== null) ||\n        (nullable && request.body === null) ||\n        required\n      ) {\n        const requestBodyParameterPathString: string = getPathStringFromParameter(\n          operationSpec.requestBody,\n        );\n        request.body = operationSpec.serializer.serialize(\n          bodyMapper,\n          request.body,\n          requestBodyParameterPathString,\n          updatedOptions,\n        );\n\n        const isStream = typeName === MapperTypeNames.Stream;\n\n        if (operationSpec.isXML) {\n          const xmlnsKey = xmlNamespacePrefix ? `xmlns:${xmlNamespacePrefix}` : \"xmlns\";\n          const value = getXmlValueWithNamespace(\n            xmlNamespace,\n            xmlnsKey,\n            typeName,\n            request.body,\n            updatedOptions,\n          );\n\n          if (typeName === MapperTypeNames.Sequence) {\n            request.body = stringifyXML(\n              prepareXMLRootList(\n                value,\n                xmlElementName || xmlName || serializedName!,\n                xmlnsKey,\n                xmlNamespace,\n              ),\n              { rootName: xmlName || serializedName, xmlCharKey },\n            );\n          } else if (!isStream) {\n            request.body = stringifyXML(value, {\n              rootName: xmlName || serializedName,\n              xmlCharKey,\n            });\n          }\n        } else if (\n          typeName === MapperTypeNames.String &&\n          (operationSpec.contentType?.match(\"text/plain\") || operationSpec.mediaType === \"text\")\n        ) {\n          // the String serializer has validated that request body is a string\n          // so just send the string.\n          return;\n        } else if (!isStream) {\n          request.body = JSON.stringify(request.body);\n        }\n      }\n    } catch (error: any) {\n      throw new Error(\n        `Error \"${error.message}\" occurred in serializing the payload - ${JSON.stringify(\n          serializedName,\n          undefined,\n          \"  \",\n        )}.`,\n      );\n    }\n  } else if (operationSpec.formDataParameters && operationSpec.formDataParameters.length > 0) {\n    request.formData = {};\n    for (const formDataParameter of operationSpec.formDataParameters) {\n      const formDataParameterValue = getOperationArgumentValueFromParameter(\n        operationArguments,\n        formDataParameter,\n      );\n      if (formDataParameterValue !== undefined && formDataParameterValue !== null) {\n        const formDataParameterPropertyName: string =\n          formDataParameter.mapper.serializedName || getPathStringFromParameter(formDataParameter);\n        request.formData[formDataParameterPropertyName] = operationSpec.serializer.serialize(\n          formDataParameter.mapper,\n          formDataParameterValue,\n          getPathStringFromParameter(formDataParameter),\n          updatedOptions,\n        );\n      }\n    }\n  }\n}\n\n/**\n * Adds an xml namespace to the xml serialized object if needed, otherwise it just returns the value itself\n */\nfunction getXmlValueWithNamespace(\n  xmlNamespace: string | undefined,\n  xmlnsKey: string,\n  typeName: string,\n  serializedValue: any,\n  options: RequiredSerializerOptions,\n): any {\n  // Composite and Sequence schemas already got their root namespace set during serialization\n  // We just need to add xmlns to the other schema types\n  if (xmlNamespace && ![\"Composite\", \"Sequence\", \"Dictionary\"].includes(typeName)) {\n    const result: any = {};\n    result[options.xml.xmlCharKey] = serializedValue;\n    result[XML_ATTRKEY] = { [xmlnsKey]: xmlNamespace };\n    return result;\n  }\n\n  return serializedValue;\n}\n\nfunction prepareXMLRootList(\n  obj: any,\n  elementName: string,\n  xmlNamespaceKey?: string,\n  xmlNamespace?: string,\n): { [key: string]: any[] } {\n  if (!Array.isArray(obj)) {\n    obj = [obj];\n  }\n  if (!xmlNamespaceKey || !xmlNamespace) {\n    return { [elementName]: obj };\n  }\n\n  const result = { [elementName]: obj };\n  result[XML_ATTRKEY] = { [xmlNamespaceKey]: xmlNamespace };\n  return result;\n}\n"]}