in src/table/batch/TableBatchSerialization.ts [37:134]
public deserializeBatchRequest(
batchRequestsString: string
): TableBatchOperation[] {
this.extractBatchBoundary(batchRequestsString);
this.extractChangeSetBoundary(batchRequestsString);
this.extractLineEndings(batchRequestsString);
// the line endings might be \r\n or \n
const HTTP_LINE_ENDING = this.lineEnding;
const subRequestPrefix = `--${this.changesetBoundary}${HTTP_LINE_ENDING}`;
const splitBody = batchRequestsString.split(subRequestPrefix);
// dropping first element as boundary if we have a batch with multiple requests
let subRequests: string[];
if (splitBody.length > 1) {
subRequests = splitBody.slice(1, splitBody.length);
} else {
subRequests = splitBody;
}
// This goes through each operation in the request and maps the content
// of the request by deserializing it into a BatchOperation Type
const batchOperations: TableBatchOperation[] = subRequests.map(
(subRequest) => {
let requestType: RegExpMatchArray | null = subRequest.match(
"(GET|PATCH|POST|PUT|MERGE|INSERT|DELETE)"
);
if (requestType === null || requestType.length < 2) {
throw new Error(
`Couldn't extract verb from sub-Request:\n ${subRequest}`
);
}
const fullRequestURI = subRequest.match(/((http+s?)(\S)+)/);
if (fullRequestURI === null || fullRequestURI.length < 3) {
throw new Error(
`Couldn't extract full request URL from sub-Request:\n ${subRequest}`
);
}
// extract the request path
const path = this.extractPath(fullRequestURI[1]);
if (path === null || path.length < 2) {
throw new Error(
`Couldn't extract path from URL in sub-Request:\n ${subRequest}`
);
}
const jsonOperationBody = subRequest.match(/{+.+}+/);
// Delete does not use a JSON body, but the COSMOS Table client also
// submits requests without a JSON body for merge
if (
subRequests.length > 1 &&
null !== requestType &&
requestType[0] !== "DELETE" &&
requestType[0] !== "MERGE" &&
(jsonOperationBody === null || jsonOperationBody.length < 1)
) {
throw new Error(
`Couldn't extract path from sub-Request:\n ${subRequest}`
);
}
let headers: string;
let jsonBody: string;
let subStringStart: number;
let subStringEnd: number;
// currently getting an invalid header in the first position
// during table entity test for insert & merge
subStringStart = subRequest.indexOf(fullRequestURI[1]);
subStringStart += fullRequestURI[1].length + 1; // for the space
if (jsonOperationBody != null) {
// we need the jsonBody and request path extracted to be able to extract headers.
subStringEnd = subRequest.indexOf(jsonOperationBody[0]);
jsonBody = jsonOperationBody[0];
} else {
// trim "\r\n\r\n" or "\n\n" from subRequest
subStringEnd = subRequest.length - HTTP_LINE_ENDING.length * 2;
jsonBody = "";
}
headers = subRequest.substring(subStringStart, subStringEnd);
const operation = new TableBatchOperation(headers);
if (null !== requestType) {
operation.httpMethod = requestType[0] as HttpMethod;
}
operation.path = path[1];
operation.uri = fullRequestURI[0];
operation.jsonRequestBody = jsonBody;
return operation;
}
);
return batchOperations;
}