Package org.apache.olingo.odata2.core.batch

Source Code of org.apache.olingo.odata2.core.batch.BatchRequestParser

/*******************************************************************************
* Licensed to the Apache Software Foundation (ASF) under one
* or more contributor license agreements. See the NOTICE file
* distributed with this work for additional information
* regarding copyright ownership. The ASF licenses this file
* to you under the Apache License, Version 2.0 (the
* "License"); you may not use this file except in compliance
* with the License. You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing,
* software distributed under the License is distributed on an
* "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
* KIND, either express or implied. See the License for the
* specific language governing permissions and limitations
* under the License.
******************************************************************************/
package org.apache.olingo.odata2.core.batch;

import java.io.ByteArrayInputStream;
import java.io.IOException;
import java.io.InputStream;
import java.net.URI;
import java.net.URISyntaxException;
import java.util.ArrayList;
import java.util.Collections;
import java.util.HashMap;
import java.util.HashSet;
import java.util.LinkedList;
import java.util.List;
import java.util.Locale;
import java.util.Map;
import java.util.Scanner;
import java.util.Set;
import java.util.regex.MatchResult;
import java.util.regex.Pattern;

import org.apache.olingo.odata2.api.batch.BatchException;
import org.apache.olingo.odata2.api.batch.BatchRequestPart;
import org.apache.olingo.odata2.api.commons.HttpContentType;
import org.apache.olingo.odata2.api.commons.HttpHeaders;
import org.apache.olingo.odata2.api.commons.ODataHttpMethod;
import org.apache.olingo.odata2.api.ep.EntityProviderBatchProperties;
import org.apache.olingo.odata2.api.processor.ODataRequest;
import org.apache.olingo.odata2.api.processor.ODataRequest.ODataRequestBuilder;
import org.apache.olingo.odata2.api.uri.PathInfo;
import org.apache.olingo.odata2.api.uri.PathSegment;
import org.apache.olingo.odata2.core.ODataPathSegmentImpl;
import org.apache.olingo.odata2.core.PathInfoImpl;
import org.apache.olingo.odata2.core.commons.Decoder;
import org.apache.olingo.odata2.core.exception.ODataRuntimeException;

/**
*/
public class BatchRequestParser {
  private static final String LF = "\n";
  private static final String REG_EX_OPTIONAL_WHITESPACE = "\\s?";
  private static final String REG_EX_ZERO_OR_MORE_WHITESPACES = "\\s*";
  private static final String ANY_CHARACTERS = ".*";

  private static final Pattern REG_EX_BLANK_LINE = Pattern.compile("(|" + REG_EX_ZERO_OR_MORE_WHITESPACES + ")");
  private static final Pattern REG_EX_HEADER = Pattern.compile("([a-zA-Z\\-]+):" + REG_EX_OPTIONAL_WHITESPACE + "(.*)"
      + REG_EX_ZERO_OR_MORE_WHITESPACES);
  private static final Pattern REG_EX_VERSION = Pattern.compile("(?:HTTP/[0-9]\\.[0-9])");
  private static final Pattern REG_EX_ANY_BOUNDARY_STRING = Pattern.compile("--" + ANY_CHARACTERS
      + REG_EX_ZERO_OR_MORE_WHITESPACES);
  private static final Pattern REG_EX_REQUEST_LINE = Pattern.compile("(GET|POST|PUT|DELETE|MERGE|PATCH)\\s(.*)\\s?"
      + REG_EX_VERSION + REG_EX_ZERO_OR_MORE_WHITESPACES);
  private static final Pattern REG_EX_BOUNDARY_PARAMETER = Pattern.compile(REG_EX_OPTIONAL_WHITESPACE
      + "boundary=(\".*\"|.*)" + REG_EX_ZERO_OR_MORE_WHITESPACES);
  private static final Pattern REG_EX_CONTENT_TYPE = Pattern.compile(REG_EX_OPTIONAL_WHITESPACE
      + HttpContentType.MULTIPART_MIXED);
  private static final Pattern REG_EX_QUERY_PARAMETER = Pattern.compile("((?:\\$|)[^=]+)=([^=]+)");

  private static final String REG_EX_BOUNDARY =
      "([a-zA-Z0-9_\\-\\.'\\+]{1,70})|\"([a-zA-Z0-9_\\-\\.'\\+\\s\\" +
          "(\\),/:=\\?]{1,69}[a-zA-Z0-9_\\-\\.'\\+\\(\\),/:=\\?])\""; // See RFC 2046

  private String baseUri;
  private PathInfo batchRequestPathInfo;
  private String contentTypeMime;
  private String boundary;
  private String currentMimeHeaderContentId;
  private int currentLineNumber = 0;
  private final static Set<String> HTTP_CHANGESET_METHODS;
  private final static Set<String> HTTP_BATCH_METHODS;

  static {
    HashSet<String> httpChangesetMethods = new HashSet<String>();
    httpChangesetMethods.add("POST");
    httpChangesetMethods.add("PUT");
    httpChangesetMethods.add("DELETE");
    httpChangesetMethods.add("MERGE");
    httpChangesetMethods.add("PATCH");
    HTTP_CHANGESET_METHODS = Collections.unmodifiableSet(httpChangesetMethods);

    HashSet<String> httpBatchMethods = new HashSet<String>();
    httpBatchMethods.add("GET");
    HTTP_BATCH_METHODS = Collections.unmodifiableSet(httpBatchMethods);
  }

  public BatchRequestParser(final String contentType, final EntityProviderBatchProperties properties) {
    contentTypeMime = contentType;
    batchRequestPathInfo = properties.getPathInfo();
  }

  public List<BatchRequestPart> parse(final InputStream in) throws BatchException {
    Scanner scanner = new Scanner(in, BatchHelper.DEFAULT_ENCODING);
    scanner.useDelimiter(LF);
    baseUri = getBaseUri();
    List<BatchRequestPart> requestList;
    try {
      requestList = parseBatchRequest(scanner);
    } finally {// NOPMD (suppress DoNotThrowExceptionInFinally)
      scanner.close();
      try {
        in.close();
      } catch (IOException e) {
        throw new ODataRuntimeException(e);
      }
    }
    return requestList;
  }

  private List<BatchRequestPart> parseBatchRequest(final Scanner scanner) throws BatchException {
    List<BatchRequestPart> requests = new LinkedList<BatchRequestPart>();
    if (contentTypeMime != null) {
      boundary = getBoundary(contentTypeMime);
      parsePreamble(scanner);
      final String closeDelimiter = "--" + boundary + "--" + REG_EX_ZERO_OR_MORE_WHITESPACES;
      while (scanner.hasNext() && !scanner.hasNext(closeDelimiter)) {
        requests.add(parseMultipart(scanner, boundary, false));
        parseOptionalLine(scanner);
      }
      if (scanner.hasNext(closeDelimiter)) {
        scanner.next(closeDelimiter);
        currentLineNumber++;
      } else {
        throw new BatchException(BatchException.MISSING_CLOSE_DELIMITER.addContent(currentLineNumber));
      }
    } else {
      throw new BatchException(BatchException.MISSING_CONTENT_TYPE);
    }
    return requests;
  }

  // The method parses additional information prior to the first boundary delimiter line
  private void parsePreamble(final Scanner scanner) {
    while (scanner.hasNext() && !scanner.hasNext(REG_EX_ANY_BOUNDARY_STRING)) {
      scanner.next();
      currentLineNumber++;
    }
  }

  private BatchRequestPart parseMultipart(final Scanner scanner, final String boundary, final boolean isChangeSet)
      throws BatchException {

    if (scanner.hasNext("--" + boundary + REG_EX_ZERO_OR_MORE_WHITESPACES)) {
      scanner.next();
      currentLineNumber++;
      Map<String, String> mimeHeaders = parseHeaders(scanner);
      currentMimeHeaderContentId = mimeHeaders.get(BatchHelper.HTTP_CONTENT_ID.toLowerCase(Locale.ENGLISH));

      String contentType = mimeHeaders.get(HttpHeaders.CONTENT_TYPE.toLowerCase(Locale.ENGLISH));
      if (contentType == null) {
        throw new BatchException(BatchException.MISSING_CONTENT_TYPE);
      }
      if (isChangeSet) {
        return parseBatchRequestPartInChangeset(scanner, boundary, mimeHeaders, contentType);
      } else {
        return parseBatchRequestPart(scanner, boundary, mimeHeaders, contentType);
      }
    } else if (scanner.hasNext(boundary + REG_EX_ZERO_OR_MORE_WHITESPACES)) {
      currentLineNumber++;
      throw new BatchException(BatchException.INVALID_BOUNDARY_DELIMITER.addContent(currentLineNumber));
    } else if (scanner.hasNext(REG_EX_ANY_BOUNDARY_STRING)) {
      currentLineNumber++;
      throw new BatchException(BatchException.NO_MATCH_WITH_BOUNDARY_STRING.addContent(boundary).addContent(
          currentLineNumber));
    } else {
      currentLineNumber++;
      throw new BatchException(BatchException.MISSING_BOUNDARY_DELIMITER.addContent(currentLineNumber));
    }
  }

  private BatchRequestPart parseBatchRequestPart(final Scanner scanner, final String boundary,
      final Map<String, String> mimeHeaders,
      final String contentType) throws BatchException {
    if (HttpContentType.APPLICATION_HTTP.equalsIgnoreCase(contentType)) {
      validateEncoding(mimeHeaders.get(BatchHelper.HTTP_CONTENT_TRANSFER_ENCODING.toLowerCase(Locale.ENGLISH)));
      parseNewLine(scanner);// mandatory
      List<ODataRequest> requests = new ArrayList<ODataRequest>(1);
      requests.add(parseRequest(scanner, false, boundary));
      return new BatchRequestPartImpl(false, requests);
    } else if (contentType.matches(REG_EX_OPTIONAL_WHITESPACE + HttpContentType.MULTIPART_MIXED + ANY_CHARACTERS)) {
      String changeSetBoundary = getBoundary(contentType);
      if (boundary.equals(changeSetBoundary)) {
        throw new BatchException(BatchException.INVALID_CHANGESET_BOUNDARY.addContent(currentLineNumber));
      }
      List<ODataRequest> changeSetRequests = new LinkedList<ODataRequest>();
      parseNewLine(scanner);// mandatory
      Pattern changeSetCloseDelimiter =
          Pattern.compile("--" + changeSetBoundary + "--" + REG_EX_ZERO_OR_MORE_WHITESPACES);
      while (!scanner.hasNext(changeSetCloseDelimiter)) {
        BatchRequestPart part = parseMultipart(scanner, changeSetBoundary, true);
        changeSetRequests.addAll(part.getRequests());
      }
      scanner.next(changeSetCloseDelimiter);
      currentLineNumber++;
      return new BatchRequestPartImpl(true, changeSetRequests);
    } else {
      throw new BatchException(BatchException.INVALID_CONTENT_TYPE.addContent(HttpContentType.MULTIPART_MIXED
          + " or " + HttpContentType.APPLICATION_HTTP));
    }
  }

  private BatchRequestPart parseBatchRequestPartInChangeset(final Scanner scanner, final String boundary,
      final Map<String, String> mimeHeaders,
      final String contentType) throws BatchException {
    if (HttpContentType.APPLICATION_HTTP.equalsIgnoreCase(contentType)) {
      validateEncoding(mimeHeaders.get(BatchHelper.HTTP_CONTENT_TRANSFER_ENCODING.toLowerCase(Locale.ENGLISH)));
      parseNewLine(scanner);// mandatory
      List<ODataRequest> requests = new ArrayList<ODataRequest>(1);
      requests.add(parseRequest(scanner, true, boundary));
      return new BatchRequestPartImpl(false, requests);
    } else {
      throw new BatchException(BatchException.INVALID_CONTENT_TYPE.addContent(HttpContentType.APPLICATION_HTTP));
    }
  }

  private ODataRequest parseRequest(final Scanner scanner, final boolean isChangeSet, final String boundary)
      throws BatchException {
    if (scanner.hasNext(REG_EX_REQUEST_LINE)) {
      scanner.next(REG_EX_REQUEST_LINE);
      currentLineNumber++;
      final String method;
      final String uri;
      MatchResult result = scanner.match();
      if (result.groupCount() == 2) {
        method = result.group(1);
        uri = result.group(2).trim();
      } else {
        currentLineNumber++;
        throw new BatchException(BatchException.INVALID_REQUEST_LINE.addContent(scanner.next()).addContent(
            currentLineNumber));
      }
      PathInfo pathInfo = parseRequestUri(uri);
      Map<String, String> queryParameters = parseQueryParameters(uri);
      if (isChangeSet) {
        if (!HTTP_CHANGESET_METHODS.contains(method)) {
          throw new BatchException(BatchException.INVALID_CHANGESET_METHOD.addContent(currentLineNumber));
        }
      } else if (!HTTP_BATCH_METHODS.contains(method)) {
        throw new BatchException(BatchException.INVALID_QUERY_OPERATION_METHOD.addContent(currentLineNumber));
      }
      ODataHttpMethod httpMethod = ODataHttpMethod.valueOf(method);
      Map<String, List<String>> headers = parseRequestHeaders(scanner, boundary);
      if (currentMimeHeaderContentId != null) {
        List<String> headerList = new ArrayList<String>();
        headerList.add(currentMimeHeaderContentId);
        headers.put(BatchHelper.MIME_HEADER_CONTENT_ID.toLowerCase(Locale.ENGLISH), headerList);
      }

      String contentType = getContentTypeHeader(headers);
      List<String> acceptHeaders = getAcceptHeader(headers);
      List<Locale> acceptLanguages = getAcceptLanguageHeader(headers);
      InputStream body = new ByteArrayInputStream(new byte[0]);
      if (isChangeSet) {
        body = parseBody(scanner);
      }

      ODataRequestBuilder requestBuilder = ODataRequest.method(httpMethod)
          .queryParameters(queryParameters)
          .requestHeaders(headers)
          .pathInfo(pathInfo)
          .acceptableLanguages(acceptLanguages)
          .body(body)
          .acceptHeaders(acceptHeaders);

      if (contentType != null) {
        requestBuilder = requestBuilder.contentType(contentType);
      }
      return requestBuilder.build();
    } else {
      currentLineNumber++;
      throw new BatchException(BatchException.INVALID_REQUEST_LINE.addContent(scanner.next()).addContent(
          currentLineNumber));
    }

  }

  private Map<String, List<String>> parseRequestHeaders(final Scanner scanner, final String boundary)
      throws BatchException {
    Map<String, List<String>> headers = new HashMap<String, List<String>>();
    while (scanner.hasNext()
        && !scanner.hasNext(REG_EX_BLANK_LINE)
        && !scanner.hasNext("--" + boundary + REG_EX_ZERO_OR_MORE_WHITESPACES)) {
      if (scanner.hasNext(REG_EX_HEADER)) {
        scanner.next(REG_EX_HEADER);
        currentLineNumber++;
        MatchResult result = scanner.match();
        if (result.groupCount() == 2) {
          String headerName = result.group(1).trim().toLowerCase(Locale.ENGLISH);
          String headerValue = result.group(2).trim();
          if (HttpHeaders.ACCEPT.equalsIgnoreCase(headerName)) {
            List<String> acceptHeaders = parseAcceptHeaders(headerValue);
            headers.put(headerName, acceptHeaders);
          } else if (HttpHeaders.ACCEPT_LANGUAGE.equalsIgnoreCase(headerName)) {
            List<String> acceptLanguageHeaders = parseAcceptableLanguages(headerValue);
            headers.put(headerName, acceptLanguageHeaders);
          } else if (!BatchHelper.HTTP_CONTENT_ID.equalsIgnoreCase(headerName)) {
            if (headers.containsKey(headerName)) {
              headers.get(headerName).add(headerValue);
            } else {
              List<String> headerList = new ArrayList<String>();
              headerList.add(headerValue);
              headers.put(headerName, headerList);
            }
          } else {
            List<String> headerList = new ArrayList<String>();
            headerList.add(headerValue);
            headers.put(BatchHelper.REQUEST_HEADER_CONTENT_ID.toLowerCase(Locale.ENGLISH), headerList);
          }
        }
      } else {
        currentLineNumber++;
        throw new BatchException(BatchException.INVALID_HEADER.addContent(scanner.next())
            .addContent(currentLineNumber));
      }
    }
    return headers;
  }

  private PathInfo parseRequestUri(final String uri) throws BatchException {
    PathInfoImpl pathInfo = new PathInfoImpl();
    pathInfo.setServiceRoot(batchRequestPathInfo.getServiceRoot());
    pathInfo.setPrecedingPathSegment(batchRequestPathInfo.getPrecedingSegments());
    final String odataPathSegmentsAsString;
    final String queryParametersAsString;
    try {
      Scanner uriScanner = new Scanner(uri);
      uriScanner.useDelimiter(LF);
      URI uriObject = new URI(uri);
      if (uriObject.isAbsolute()) {
        Pattern regexRequestUri = Pattern.compile(baseUri + "/([^/][^?]*)(\\?.*)?");
        if (uriScanner.hasNext(regexRequestUri)) {
          uriScanner.next(regexRequestUri);
          MatchResult result = uriScanner.match();
          if (result.groupCount() == 2) {
            odataPathSegmentsAsString = result.group(1);
            queryParametersAsString = result.group(2) != null ? result.group(2) : "";
          } else {
            uriScanner.close();
            throw new BatchException(BatchException.INVALID_URI.addContent(currentLineNumber));
          }
        } else {
          uriScanner.close();
          throw new BatchException(BatchException.INVALID_URI.addContent(currentLineNumber));
        }
      } else {
        Pattern regexRequestUri = Pattern.compile("([^/][^?]*)(\\?.*)?");
        if (uriScanner.hasNext(regexRequestUri)) {
          uriScanner.next(regexRequestUri);
          MatchResult result = uriScanner.match();
          if (result.groupCount() == 2) {
            odataPathSegmentsAsString = result.group(1);
            queryParametersAsString = result.group(2) != null ? result.group(2) : "";
          } else {
            uriScanner.close();
            throw new BatchException(BatchException.INVALID_URI.addContent(currentLineNumber));
          }
        } else if (uriScanner.hasNext("/(.*)")) {
          uriScanner.close();
          throw new BatchException(BatchException.UNSUPPORTED_ABSOLUTE_PATH.addContent(currentLineNumber));
        } else {
          uriScanner.close();
          throw new BatchException(BatchException.INVALID_URI.addContent(currentLineNumber));
        }

      }
      uriScanner.close();
      pathInfo.setODataPathSegment(parseODataPathSegments(odataPathSegmentsAsString));
      if (!odataPathSegmentsAsString.startsWith("$")) {
        String requestUri = baseUri + "/" + odataPathSegmentsAsString + queryParametersAsString;
        pathInfo.setRequestUri(new URI(requestUri));
      }
      return pathInfo;
    } catch (URISyntaxException e) {
      throw new BatchException(BatchException.INVALID_URI.addContent(currentLineNumber), e);
    }

  }

  private Map<String, String> parseQueryParameters(final String uri) throws BatchException {
    Scanner uriScanner = new Scanner(uri);
    uriScanner.useDelimiter("\n");
    Map<String, String> queryParametersMap = new HashMap<String, String>();
    Pattern regex = Pattern.compile("(?:" + baseUri + "/)?" + "[^?]+" + "\\?(.*)");
    if (uriScanner.hasNext(regex)) {
      uriScanner.next(regex);
      MatchResult uriResult = uriScanner.match();
      if (uriResult.groupCount() == 1) {
        String queryParams = uriResult.group(1);
        Scanner queryParamsScanner = new Scanner(queryParams);
        queryParamsScanner.useDelimiter("&");
        while (queryParamsScanner.hasNext(REG_EX_QUERY_PARAMETER)) {
          queryParamsScanner.next(REG_EX_QUERY_PARAMETER);
          MatchResult result = queryParamsScanner.match();
          if (result.groupCount() == 2) {
            String systemQueryOption = result.group(1);
            String value = result.group(2);
            queryParametersMap.put(systemQueryOption, Decoder.decode(value));
          } else {
            queryParamsScanner.close();
            throw new BatchException(BatchException.INVALID_QUERY_PARAMETER);
          }
        }
        queryParamsScanner.close();

      } else {
        uriScanner.close();
        throw new BatchException(BatchException.INVALID_URI.addContent(currentLineNumber));
      }
    }
    uriScanner.close();
    return queryParametersMap;
  }

  private List<PathSegment> parseODataPathSegments(final String odataPathSegmentsAsString) {
    Scanner pathSegmentScanner = new Scanner(odataPathSegmentsAsString);
    pathSegmentScanner.useDelimiter("/");
    List<PathSegment> odataPathSegments = new ArrayList<PathSegment>();
    while (pathSegmentScanner.hasNext()) {
      odataPathSegments.add(new ODataPathSegmentImpl(pathSegmentScanner.next(), null));
    }
    pathSegmentScanner.close();
    return odataPathSegments;
  }

  private List<String> parseAcceptHeaders(final String headerValue) throws BatchException {
    return AcceptParser.parseAcceptHeaders(headerValue);
  }

  private List<String> parseAcceptableLanguages(final String headerValue) throws BatchException {
    return AcceptParser.parseAcceptableLanguages(headerValue);
  }

  private InputStream parseBody(final Scanner scanner) {
    StringBuilder body = null;
    final InputStream requestBody;

    while (scanner.hasNext() && !scanner.hasNext(REG_EX_ANY_BOUNDARY_STRING)) {
      if (!scanner.hasNext(REG_EX_ZERO_OR_MORE_WHITESPACES)) {
        if (body == null) {
          body = new StringBuilder(scanner.next());
        } else {
          body.append(LF).append(scanner.next());
        }
      } else {
        scanner.next();
      }
      currentLineNumber++;
    }

    if (body != null) {
      requestBody = new ByteArrayInputStream(BatchHelper.getBytes(body.toString()));
    } else {
      requestBody = new ByteArrayInputStream(new byte[0]);
    }
    return requestBody;
  }

  private String getBoundary(final String contentType) throws BatchException {
    Scanner contentTypeScanner = new Scanner(contentType);
    contentTypeScanner.useDelimiter(";\\s?");
    if (contentTypeScanner.hasNext(REG_EX_CONTENT_TYPE)) {
      contentTypeScanner.next(REG_EX_CONTENT_TYPE);
    } else {
      contentTypeScanner.close();
      throw new BatchException(BatchException.INVALID_CONTENT_TYPE.addContent(HttpContentType.MULTIPART_MIXED));
    }
    if (contentTypeScanner.hasNext(REG_EX_BOUNDARY_PARAMETER)) {
      contentTypeScanner.next(REG_EX_BOUNDARY_PARAMETER);
      MatchResult result = contentTypeScanner.match();
      contentTypeScanner.close();
      if (result.groupCount() == 1 && result.group(1).trim().matches(REG_EX_BOUNDARY)) {
        return trimQuota(result.group(1).trim());
      } else {
        throw new BatchException(BatchException.INVALID_BOUNDARY);
      }
    } else {
      contentTypeScanner.close();
      throw new BatchException(BatchException.MISSING_PARAMETER_IN_CONTENT_TYPE);
    }
  }

  private void validateEncoding(final String encoding) throws BatchException {
    if (!BatchHelper.BINARY_ENCODING.equalsIgnoreCase(encoding)) {
      throw new BatchException(BatchException.INVALID_CONTENT_TRANSFER_ENCODING);
    }
  }

  private Map<String, String> parseHeaders(final Scanner scanner) throws BatchException {
    Map<String, String> headers = new HashMap<String, String>();
    while (scanner.hasNext() && !(scanner.hasNext(REG_EX_BLANK_LINE))) {
      if (scanner.hasNext(REG_EX_HEADER)) {
        scanner.next(REG_EX_HEADER);
        currentLineNumber++;
        MatchResult result = scanner.match();
        if (result.groupCount() == 2) {
          String headerName = result.group(1).trim().toLowerCase(Locale.ENGLISH);
          String headerValue = result.group(2).trim();
          headers.put(headerName, headerValue);
        }
      } else {
        throw new BatchException(BatchException.INVALID_HEADER.addContent(scanner.next()));
      }
    }
    return headers;
  }

  private void parseNewLine(final Scanner scanner) throws BatchException {
    if (scanner.hasNext() && scanner.hasNext(REG_EX_BLANK_LINE)) {
      scanner.next();
      currentLineNumber++;
    } else {
      currentLineNumber++;
      if (scanner.hasNext()) {
        throw new BatchException(BatchException.MISSING_BLANK_LINE.addContent(scanner.next()).addContent(
            currentLineNumber));
      } else {
        throw new BatchException(BatchException.TRUNCATED_BODY.addContent(currentLineNumber));

      }
    }
  }

  private void parseOptionalLine(final Scanner scanner) throws BatchException {
    while (scanner.hasNext() && scanner.hasNext(REG_EX_BLANK_LINE)) {
      scanner.next();
      currentLineNumber++;
    }
  }

  private String getBaseUri() throws BatchException {
    if (batchRequestPathInfo != null) {
      if (batchRequestPathInfo.getServiceRoot() != null) {
        String baseUri = batchRequestPathInfo.getServiceRoot().toASCIIString();
        if (baseUri.lastIndexOf('/') == baseUri.length() - 1) {
          baseUri = baseUri.substring(0, baseUri.length() - 1);
        }
        for (PathSegment precedingPS : batchRequestPathInfo.getPrecedingSegments()) {
          baseUri = baseUri + "/" + precedingPS.getPath();
        }
        return baseUri;
      }
    } else {
      throw new BatchException(BatchException.INVALID_PATHINFO);
    }
    return null;
  }

  private String trimQuota(String boundary) {
    if (boundary.matches("\".*\"")) {
      boundary = boundary.replace("\"", "");
    }
    boundary = boundary.replaceAll("\\)", "\\\\)");
    boundary = boundary.replaceAll("\\(", "\\\\(");
    boundary = boundary.replaceAll("\\?", "\\\\?");
    boundary = boundary.replaceAll("\\+", "\\\\+");
    return boundary;
  }

  private List<String> getAcceptHeader(final Map<String, List<String>> headers) {
    List<String> acceptHeaders = new ArrayList<String>();
    List<String> requestAcceptHeaderList = headers.get(HttpHeaders.ACCEPT.toLowerCase(Locale.ENGLISH));

    if (requestAcceptHeaderList != null) {
      acceptHeaders = requestAcceptHeaderList;
    }
    return acceptHeaders;
  }

  private List<Locale> getAcceptLanguageHeader(final Map<String, List<String>> headers) {
    List<String> requestAcceptLanguageList = headers.get(HttpHeaders.ACCEPT_LANGUAGE.toLowerCase(Locale.ENGLISH));
    List<Locale> acceptLanguages = new ArrayList<Locale>();
    if (requestAcceptLanguageList != null) {
      for (String acceptLanguage : requestAcceptLanguageList) {
        String[] part = acceptLanguage.split("-");
        String language = part[0];
        String country = "";
        if (part.length == 2) {
          country = part[part.length - 1];
        }
        Locale locale = new Locale(language, country);
        acceptLanguages.add(locale);
      }
    }
    return acceptLanguages;
  }

  private String getContentTypeHeader(final Map<String, List<String>> headers) {
    List<String> requestContentTypeList = headers.get(HttpHeaders.CONTENT_TYPE.toLowerCase(Locale.ENGLISH));
    String contentType = null;
    if (requestContentTypeList != null) {
      for (String requestContentType : requestContentTypeList) {
        contentType = contentType != null ? contentType + "," + requestContentType : requestContentType;
      }
    }
    return contentType;
  }
}
TOP

Related Classes of org.apache.olingo.odata2.core.batch.BatchRequestParser

TOP
Copyright © 2018 www.massapi.com. All rights reserved.
All source code are property of their respective owners. Java is a trademark of Sun Microsystems, Inc and owned by ORACLE Inc. Contact coftware#gmail.com.