Example #1
0
  private PatternBinding getBinding(String nameOrUriPattern) {
    Collection<List<PatternBinding>> values = bindingsCache.values();
    Route route;
    for (List<PatternBinding> bindings : values) {
      for (PatternBinding binding : bindings) {
        route = binding.getRoute();
        if (nameOrUriPattern.equals(route.getName())
            || nameOrUriPattern.equals(route.getUriPattern())) {
          return binding;
        }
      }
    }

    return null;
  }
Example #2
0
  private void addPattern(
      String verb, String input, Middleware[] handler, List<PatternBinding> bindings) {
    // We need to search for any :<token name> tokens in the String and replace them with named
    // capture groups
    Matcher m = Pattern.compile(":([A-Za-z][A-Za-z0-9_]*)").matcher(input);
    StringBuffer sb = new StringBuffer();
    Set<String> groups = new HashSet<>();
    while (m.find()) {
      String group = m.group().substring(1);
      if (groups.contains(group)) {
        throw new IllegalArgumentException(
            "Cannot use identifier " + group + " more than once in pattern string");
      }
      m.appendReplacement(sb, "(?<$1>[^\\/]+)");
      groups.add(group);
    }
    m.appendTail(sb);
    // ignore tailing slash if not part of the input, not really REST but common on other frameworks
    if (sb.charAt(sb.length() - 1) != '/') {
      sb.append("\\/?$");
    }

    Pattern regex = Pattern.compile(sb.toString());
    boolean exists = false;
    // verify if the binding already exists, if yes add to it
    for (PatternBinding pb : bindings) {
      if (pb.isFor(input)) {
        exists = true;
        pb.addMiddleware(handler);
        break;
      }
    }

    if (!exists) {
      PatternBinding binding = new PatternBinding(hashCode(), verb, input, regex, groups, handler);
      bindings.add(binding);
    }

    // also pass the vertx object to the routes
    for (Middleware h : handler) {
      if (!h.isInitialized() && isInitialized()) {
        h.init(yoke, mount);
      }
    }
  }
Example #3
0
  private Map<String, String> getParameters(PatternBinding binding, String requestUri) {
    if (binding.getParameterNames().isEmpty()) {
      return Collections.EMPTY_MAP;
    }

    Map<String, String> parameters = new HashMap<>();
    List<String> parameterNames = binding.getParameterNames();
    Matcher matcher = binding.getPattern().matcher(requestUri);
    matcher.matches();
    int groupCount = matcher.groupCount();
    if (groupCount > 0) {
      for (int i = 0; i < parameterNames.size(); i++) {
        parameters.put(parameterNames.get(i), matcher.group(i + 1));
      }
    }

    return parameters;
  }
Example #4
0
  @Override
  public List<RouteMatch> findRoutes(String requestUri, String requestMethod) {
    log.trace("Finding route matches for {} '{}'", requestMethod, requestUri);

    List<RouteMatch> routeMatches = new ArrayList<>();

    List<PatternBinding> bindings = getBindings(requestMethod);
    for (Route route : routes) { // to preserve the routes order
      for (PatternBinding binding : bindings) {
        if (route.equals(binding.getRoute())
            && binding.getPattern().matcher(requestUri).matches()) {
          // TODO improve (it's possible to have the same uriPattern for many routes => same
          // parameters)
          routeMatches.add(new RouteMatch(route, getParameters(binding, requestUri)));
          break;
        }
      }
    }

    log.debug("Found {} route matches for {} '{}'", routeMatches.size(), requestMethod, requestUri);

    return routeMatches;
  }
Example #5
0
 public void visitPatternsSpec(PatternsSpec aPatternsSpec) {
   out.print("PatternsSpec(");
   ++indentLevel;
   out.println();
   printIndent();
   out.print("bindings=");
   if (aPatternsSpec.getBindings() != null) {
     out.println("[");
     ++indentLevel;
     for (PatternBinding e : aPatternsSpec.getBindings()) {
       printIndent();
       e.visit(this);
     }
     --indentLevel;
     printIndent();
     out.println("]");
   } else {
     out.println("null");
   }
   --indentLevel;
   printIndent();
   out.println(")");
 }
Example #6
0
  private void addRegEx(
      String verb, Pattern regex, Middleware handler[], List<PatternBinding> bindings) {
    boolean exists = false;
    // verify if the binding already exists, if yes add to it
    for (PatternBinding pb : bindings) {
      if (pb.isFor(regex)) {
        pb.addMiddleware(handler);
        exists = true;
        break;
      }
    }

    if (!exists) {
      PatternBinding binding = new PatternBinding(hashCode(), verb, null, regex, null, handler);
      bindings.add(binding);
    }

    // also pass the vertx object to the routes
    for (Middleware h : handler) {
      if (!h.isInitialized() && isInitialized()) {
        h.init(yoke, mount);
      }
    }
  }
Example #7
0
  private String uriFor(PatternBinding binding, Map<String, Object> parameters) {
    String uri = binding.getRoute().getUriPattern();

    List<String> parameterNames = binding.getParameterNames();
    if (!parameters.keySet().containsAll(parameterNames)) {
      log.error(
          "You must provide values for all path parameters. {} vs {}",
          parameterNames,
          parameters.keySet());
    }

    Map<String, Object> queryParameters = new HashMap<>(parameters.size());

    for (Entry<String, Object> parameterPair : parameters.entrySet()) {
      boolean foundAsPathParameter = false;

      StringBuffer sb = new StringBuffer();
      String buffer = String.format(VARIABLE_PART_PATTERN_WITH_PLACEHOLDER, parameterPair.getKey());

      Pattern pattern = Pattern.compile(buffer);
      Matcher matcher = pattern.matcher(uri);
      while (matcher.find()) {
        String pathValue = parameterPair.getValue().toString();
        matcher.appendReplacement(sb, pathValue);
        foundAsPathParameter = true;
      }

      matcher.appendTail(sb);
      uri = sb.toString();

      if (!foundAsPathParameter) {
        queryParameters.put(parameterPair.getKey(), parameterPair.getValue());
      }
    }

    // now prepare the query string for this url if we got some query params
    if (!queryParameters.isEmpty()) {
      // add remaining parameters as query parameters
      StringBuilder query = new StringBuilder();
      Iterator<Entry<String, Object>> iterator = queryParameters.entrySet().iterator();
      while (iterator.hasNext()) {
        Entry<String, Object> parameterEntry = iterator.next();
        String parameterName = parameterEntry.getKey();
        Object parameterValue = parameterEntry.getValue();
        String encodedParameterValue = null;
        try {
          encodedParameterValue = URLEncoder.encode(parameterValue.toString(), PippoConstants.UTF8);
        } catch (UnsupportedEncodingException e) {
          throw new PippoRuntimeException(
              "Cannot encode the parameter value '" + parameterValue.toString() + "'", e);
        }
        query.append(parameterName).append("=").append(encodedParameterValue);

        if (iterator.hasNext()) {
          query.append("&");
        }
      }

      uri += "?" + query;
    }

    return uri;
  }