in lib/swaggerValidator/modelValidator.ts [311:442]
private validateRequest(operation: Operation, exampleContent: any, exampleFileUrl: string) {
const parameterizedHostDef = operation._path._spec["x-ms-parameterized-host"];
const useSchemePrefix = parameterizedHostDef
? parameterizedHostDef.useSchemePrefix === undefined
? true
: parameterizedHostDef.useSchemePrefix
: null;
const pathTemplate = operation._path._pathTemplate;
const parameters = operation.parameters;
const publicParameters = operation._path.parameters;
const mergedParameters = [...(parameters ?? []), ...(publicParameters ?? [])];
const pathParameters: { [key: string]: string } = {};
let bodyParameter: any = {};
const queryParameters: ParsedUrlQuery = {};
const formData: { [key: string]: string } = {};
const exampleRequestHeaders: { [propertyName: string]: string } = {};
if (mergedParameters === undefined) {
return;
}
for (const p of mergedParameters) {
const parameter = this.jsonLoader.resolveRefObj(p);
let parameterValue = exampleContent?.parameters[parameter.name];
if (!parameterValue) {
if (parameter.required) {
const meta = getOavErrorMeta(
ErrorCodeConstants.REQUIRED_PARAMETER_EXAMPLE_NOT_FOUND as any,
{ operationId: operation.operationId, name: parameter.name }
);
this.addErrorsFromErrorCode(
operation.operationId!,
exampleFileUrl,
meta,
operation,
undefined,
p
);
break;
}
continue;
}
const location = parameter.in;
if (location === "path") {
if (location === "path" && parameterValue && typeof parameterValue === "string") {
// "/{scope}/scopes/resourceGroups/{resourceGroupName}" In the aforementioned path
// template, we will search for the path parameter based on it's name
// for example: "scope". Find it's index in the string and move backwards by 2 positions.
// If the character at that position is a forward slash "/" and
// the value for the parameter starts with a forward slash "/" then we have found the case
// where there will be duplicate forward slashes in the url.
if (
pathTemplate.charAt(pathTemplate.indexOf(`${parameter.name}`) - 2) === "/" &&
parameterValue.startsWith("/")
) {
const meta = getOavErrorMeta(ErrorCodeConstants.DOUBLE_FORWARD_SLASHES_IN_URL as any, {
operationId: operation.operationId,
parameterName: parameter.name,
parameterValue,
pathTemplate,
});
this.addErrorsFromErrorCode(
operation.operationId!,
exampleFileUrl,
meta,
operation,
undefined,
p
);
break;
}
// replacing characters that may cause validator failed with empty string because this messes up Sways regex
// validation of path segment.
parameterValue = parameterValue.replace(/\//gi, "");
// replacing scheme that may cause validator failed when x-ms-parameterized-host enbaled & useSchemePrefix enabled
// because if useSchemePrefix enabled ,the parameter value in x-ms-parameterized-host should not has the scheme (http://|https://)
if (useSchemePrefix) {
parameterValue = (parameterValue as string).replace(/^https{0,1}:/gi, "");
}
}
// todo skip url encoding
pathParameters[parameter.name] = parameterValue;
} else if (location === "query") {
// validate the api version value
if (parameter.name === "api-version" && parameterValue !== this.swagger.info.version) {
const meta = getOavErrorMeta("INVALID_REQUEST_PARAMETER", {
parameterName: "api-version",
apiVersion: parameterValue,
});
this.addErrorsFromErrorCode(
operation.operationId!,
exampleFileUrl,
meta,
operation,
undefined,
exampleContent?.parameters,
`$parameters["api-version"]`
);
continue;
}
queryParameters[parameter.name] = parameterValue;
} else if (location === "body") {
if ((parameter as BodyParameter).schema?.format === "file") {
continue;
}
bodyParameter = parameterValue;
} else if (location === "header") {
exampleRequestHeaders[parameter.name] = parameterValue;
} else if (location === "formData") {
formData[parameter.name] = parameterValue;
}
} // end of mergedParameters for loop
transformMapValue(queryParameters, operation._queryTransform);
transformMapValue(pathParameters, operation._pathTransform);
const validate = operation._validate!;
const ctx = { isResponse: false };
const headers = transformLiveHeader(exampleRequestHeaders, operation);
const ajvValidatorErrors = validate(ctx, {
path: pathParameters,
body: transformBodyValue(bodyParameter, operation),
query: queryParameters,
headers,
formData,
});
this.schemaIssuesToModelValidationIssues(
operation.operationId!,
true,
ajvValidatorErrors,
exampleFileUrl,
exampleContent,
mergedParameters
);
}