예제 #1
0
  private void parsePlugins(String context, QueryMetric queryMetric, JsonArray plugins)
      throws BeanValidationException, QueryException {
    for (int I = 0; I < plugins.size(); I++) {
      JsonObject pluginJson = plugins.get(I).getAsJsonObject();

      JsonElement name = pluginJson.get("name");
      if (name == null || name.getAsString().isEmpty())
        throw new BeanValidationException(
            new SimpleConstraintViolation("plugins[" + I + "]", "must have a name"), context);

      String pluginContext = context + ".plugins[" + I + "]";
      String pluginName = name.getAsString();
      QueryPlugin plugin = m_pluginFactory.createQueryPlugin(pluginName);

      if (plugin == null)
        throw new BeanValidationException(
            new SimpleConstraintViolation(pluginName, "invalid query plugin name"), pluginContext);

      deserializeProperties(pluginContext, pluginJson, pluginName, plugin);

      validateObject(plugin, pluginContext);

      queryMetric.addPlugin(plugin);
    }
  }
예제 #2
0
  private void parseGroupBy(String context, QueryMetric queryMetric, JsonArray groupBys)
      throws QueryException, BeanValidationException {
    for (int J = 0; J < groupBys.size(); J++) {
      String groupContext = "group_by[" + J + "]";
      JsonObject jsGroupBy = groupBys.get(J).getAsJsonObject();

      JsonElement nameElement = jsGroupBy.get("name");
      if (nameElement == null || nameElement.getAsString().isEmpty())
        throw new BeanValidationException(
            new SimpleConstraintViolation(groupContext, "must have a name"), context);

      String name = nameElement.getAsString();

      GroupBy groupBy = m_groupByFactory.createGroupBy(name);
      if (groupBy == null)
        throw new BeanValidationException(
            new SimpleConstraintViolation(groupContext + "." + name, "invalid group_by name"),
            context);

      deserializeProperties(context + "." + groupContext, jsGroupBy, name, groupBy);
      validateObject(groupBy, context + "." + groupContext);

      groupBy.setStartDate(queryMetric.getStartTime());

      queryMetric.addGroupBy(groupBy);
    }
  }
예제 #3
0
 public RollupTask parseRollupTask(String json) throws BeanValidationException, QueryException {
   JsonParser parser = new JsonParser();
   JsonObject taskObject = parser.parse(json).getAsJsonObject();
   RollupTask task = parseRollupTask(taskObject, "");
   task.addJson(taskObject.toString().replaceAll("\\n", ""));
   return task;
 }
예제 #4
0
  public List<RollupTask> parseRollupTasks(String json)
      throws BeanValidationException, QueryException {
    List<RollupTask> tasks = new ArrayList<RollupTask>();
    JsonParser parser = new JsonParser();
    JsonArray rollupTasks = parser.parse(json).getAsJsonArray();
    for (int i = 0; i < rollupTasks.size(); i++) {
      JsonObject taskObject = rollupTasks.get(i).getAsJsonObject();
      RollupTask task = parseRollupTask(taskObject, "tasks[" + i + "]");
      task.addJson(taskObject.toString().replaceAll("\\n", ""));
      tasks.add(task);
    }

    return tasks;
  }
예제 #5
0
  private void parseAggregators(
      String context, QueryMetric queryMetric, JsonArray aggregators, DateTimeZone timeZone)
      throws QueryException, BeanValidationException {
    for (int J = 0; J < aggregators.size(); J++) {
      JsonObject jsAggregator = aggregators.get(J).getAsJsonObject();

      JsonElement name = jsAggregator.get("name");
      if (name == null || name.getAsString().isEmpty())
        throw new BeanValidationException(
            new SimpleConstraintViolation("aggregators[" + J + "]", "must have a name"), context);

      String aggContext = context + ".aggregators[" + J + "]";
      String aggName = name.getAsString();
      Aggregator aggregator = m_aggregatorFactory.createAggregator(aggName);

      if (aggregator == null)
        throw new BeanValidationException(
            new SimpleConstraintViolation(aggName, "invalid aggregator name"), aggContext);

      // If it is a range aggregator we will default the start time to
      // the start of the query.
      if (aggregator instanceof RangeAggregator) {
        RangeAggregator ra = (RangeAggregator) aggregator;
        ra.setStartTime(queryMetric.getStartTime());
      }

      if (aggregator instanceof TimezoneAware) {
        TimezoneAware ta = (TimezoneAware) aggregator;
        ta.setTimeZone(timeZone);
      }

      if (aggregator instanceof GroupByAware) {
        GroupByAware groupByAware = (GroupByAware) aggregator;
        groupByAware.setGroupBys(queryMetric.getGroupBys());
      }

      deserializeProperties(aggContext, jsAggregator, aggName, aggregator);

      validateObject(aggregator, aggContext);

      queryMetric.addAggregator(aggregator);
    }
  }
예제 #6
0
  public RollupTask parseRollupTask(JsonObject rollupTask, String context)
      throws BeanValidationException, QueryException {
    RollupTask task = m_gson.fromJson(rollupTask.getAsJsonObject(), RollupTask.class);

    validateObject(task);

    JsonArray rollups = rollupTask.getAsJsonObject().getAsJsonArray("rollups");
    if (rollups != null) {
      for (int j = 0; j < rollups.size(); j++) {
        JsonObject rollupObject = rollups.get(j).getAsJsonObject();
        Rollup rollup = m_gson.fromJson(rollupObject, Rollup.class);

        context = context + "rollup[" + j + "]";
        validateObject(rollup, context);

        JsonObject queryObject = rollupObject.getAsJsonObject("query");
        List<QueryMetric> queries = parseQueryMetric(queryObject, context);

        for (int k = 0; k < queries.size(); k++) {
          QueryMetric query = queries.get(k);
          context += ".query[" + k + "]";
          validateHasRangeAggregator(query, context);

          // Add aggregators needed for rollups
          SaveAsAggregator saveAsAggregator =
              (SaveAsAggregator) m_aggregatorFactory.createAggregator("save_as");
          saveAsAggregator.setMetricName(rollup.getSaveAs());

          TrimAggregator trimAggregator =
              (TrimAggregator) m_aggregatorFactory.createAggregator("trim");
          trimAggregator.setTrim(TrimAggregator.Trim.LAST);

          query.addAggregator(saveAsAggregator);
          query.addAggregator(trimAggregator);
        }

        rollup.addQueries(queries);
        task.addRollup(rollup);
      }
    }

    return task;
  }
예제 #7
0
    @Override
    public Metric deserialize(
        JsonElement jsonElement, Type type, JsonDeserializationContext jsonDeserializationContext)
        throws JsonParseException {
      JsonObject jsonObject = jsonElement.getAsJsonObject();

      String name = null;
      if (jsonObject.get("name") != null) name = jsonObject.get("name").getAsString();

      boolean exclude_tags = false;
      if (jsonObject.get("exclude_tags") != null)
        exclude_tags = jsonObject.get("exclude_tags").getAsBoolean();

      TreeMultimap<String, String> tags = TreeMultimap.create();
      JsonElement jeTags = jsonObject.get("tags");
      if (jeTags != null) {
        JsonObject joTags = jeTags.getAsJsonObject();
        int count = 0;
        for (Map.Entry<String, JsonElement> tagEntry : joTags.entrySet()) {
          String context = "tags[" + count + "]";
          if (tagEntry.getKey().isEmpty())
            throw new ContextualJsonSyntaxException(context, "name must not be empty");

          if (tagEntry.getValue().isJsonArray()) {
            for (JsonElement element : tagEntry.getValue().getAsJsonArray()) {
              if (element.isJsonNull() || element.getAsString().isEmpty())
                throw new ContextualJsonSyntaxException(
                    context + "." + tagEntry.getKey(), "value must not be null or empty");
              tags.put(tagEntry.getKey(), element.getAsString());
            }
          } else {
            if (tagEntry.getValue().isJsonNull() || tagEntry.getValue().getAsString().isEmpty())
              throw new ContextualJsonSyntaxException(
                  context + "." + tagEntry.getKey(), "value must not be null or empty");
            tags.put(tagEntry.getKey(), tagEntry.getValue().getAsString());
          }
          count++;
        }
      }

      Metric ret = new Metric(name, exclude_tags, tags);

      JsonElement limit = jsonObject.get("limit");
      if (limit != null) ret.setLimit(limit.getAsInt());

      return (ret);
    }
예제 #8
0
  private void deserializeProperties(
      String context, JsonObject jsonObject, String name, Object object)
      throws QueryException, BeanValidationException {
    Set<Map.Entry<String, JsonElement>> props = jsonObject.entrySet();
    for (Map.Entry<String, JsonElement> prop : props) {
      String property = prop.getKey();
      if (property.equals("name")) continue;

      PropertyDescriptor pd = null;
      try {
        pd = getPropertyDescriptor(object.getClass(), property);
      } catch (IntrospectionException e) {
        logger.error("Introspection error on " + object.getClass(), e);
      }

      if (pd == null) {
        String msg =
            "Property '"
                + property
                + "' was specified for object '"
                + name
                + "' but no matching setter was found on '"
                + object.getClass()
                + "'";

        throw new QueryException(msg);
      }

      Class propClass = pd.getPropertyType();

      Object propValue;
      try {
        propValue = m_gson.fromJson(prop.getValue(), propClass);
        validateObject(propValue, context + "." + property);
      } catch (ContextualJsonSyntaxException e) {
        throw new BeanValidationException(
            new SimpleConstraintViolation(e.getContext(), e.getMessage()), context);
      } catch (NumberFormatException e) {
        throw new BeanValidationException(
            new SimpleConstraintViolation(property, e.getMessage()), context);
      }

      Method method = pd.getWriteMethod();
      if (method == null) {
        String msg =
            "Property '"
                + property
                + "' was specified for object '"
                + name
                + "' but no matching setter was found on '"
                + object.getClass().getName()
                + "'";

        throw new QueryException(msg);
      }

      try {
        method.invoke(object, propValue);
      } catch (Exception e) {
        logger.error("Invocation error: ", e);
        String msg =
            "Call to "
                + object.getClass().getName()
                + ":"
                + method.getName()
                + " failed with message: "
                + e.getMessage();

        throw new QueryException(msg);
      }
    }
  }
예제 #9
0
  private List<QueryMetric> parseQueryMetric(JsonObject obj, String contextPrefix)
      throws QueryException, BeanValidationException {
    List<QueryMetric> ret = new ArrayList<QueryMetric>();

    Query query;
    try {
      query = m_gson.fromJson(obj, Query.class);
      validateObject(query);
    } catch (ContextualJsonSyntaxException e) {
      throw new BeanValidationException(
          new SimpleConstraintViolation(e.getContext(), e.getMessage()), "query");
    }

    JsonArray metricsArray = obj.getAsJsonArray("metrics");
    if (metricsArray == null) {
      throw new BeanValidationException(
          new SimpleConstraintViolation("metric[]", "must have a size of at least 1"),
          contextPrefix + "query");
    }

    for (int I = 0; I < metricsArray.size(); I++) {
      String context =
          (!contextPrefix.isEmpty() ? contextPrefix + "." : contextPrefix)
              + "query.metric["
              + I
              + "]";
      try {
        Metric metric = m_gson.fromJson(metricsArray.get(I), Metric.class);

        validateObject(metric, context);

        long startTime = getStartTime(query, context);
        QueryMetric queryMetric =
            new QueryMetric(startTime, query.getCacheTime(), metric.getName());
        queryMetric.setExcludeTags(metric.isExcludeTags());
        queryMetric.setLimit(metric.getLimit());

        long endTime = getEndTime(query);
        if (endTime > -1) queryMetric.setEndTime(endTime);

        if (queryMetric.getEndTime() < startTime)
          throw new BeanValidationException(
              new SimpleConstraintViolation("end_time", "must be greater than the start time"),
              context);

        queryMetric.setCacheString(query.getCacheString() + metric.getCacheString());

        JsonObject jsMetric = metricsArray.get(I).getAsJsonObject();

        JsonElement group_by = jsMetric.get("group_by");
        if (group_by != null) {
          JsonArray groupBys = group_by.getAsJsonArray();
          parseGroupBy(context, queryMetric, groupBys);
        }

        JsonElement aggregators = jsMetric.get("aggregators");
        if (aggregators != null) {
          JsonArray asJsonArray = aggregators.getAsJsonArray();
          if (asJsonArray.size() > 0)
            parseAggregators(context, queryMetric, asJsonArray, query.getTimeZone());
        }

        JsonElement plugins = jsMetric.get("plugins");
        if (plugins != null) {
          JsonArray pluginArray = plugins.getAsJsonArray();
          if (pluginArray.size() > 0) parsePlugins(context, queryMetric, pluginArray);
        }

        JsonElement order = jsMetric.get("order");
        if (order != null) queryMetric.setOrder(Order.fromString(order.getAsString(), context));

        queryMetric.setTags(metric.getTags());

        ret.add(queryMetric);
      } catch (ContextualJsonSyntaxException e) {
        throw new BeanValidationException(
            new SimpleConstraintViolation(e.getContext(), e.getMessage()), context);
      }
    }

    return (ret);
  }