Java tutorial
/* * Copyright 2014 Amazon Technologies, Inc. * * Licensed 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://aws.amazon.com/apache2.0 * * This file 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 com.amediamanager.metrics; import java.util.Collection; import java.util.List; import java.util.Map; import org.slf4j.Logger; import org.slf4j.LoggerFactory; import org.springframework.scheduling.annotation.Scheduled; import com.amazonaws.handlers.AsyncHandler; import com.amazonaws.services.cloudwatch.AmazonCloudWatchAsync; import com.amazonaws.services.cloudwatch.model.MetricDatum; import com.amazonaws.services.cloudwatch.model.PutMetricDataRequest; import com.google.common.collect.LinkedListMultimap; import com.google.common.collect.Lists; import com.google.common.collect.Multimap; import com.google.common.collect.Multimaps; public class MetricBatcher { private static final Logger LOG = LoggerFactory.getLogger(MetricBatcher.class); private static final int BATCH_SIZE = 10; private final Multimap<String, MetricDatum> queuedDatums = Multimaps .synchronizedListMultimap(LinkedListMultimap.<String, MetricDatum>create()); protected final AmazonCloudWatchAsync cloudWatch; public MetricBatcher(AmazonCloudWatchAsync cloudWatch) { this.cloudWatch = cloudWatch; } public final void addDatum(String namespace, MetricDatum datum) { queuedDatums.put(namespace, datum); } public final void addDatums(String namespace, Collection<MetricDatum> datums) { queuedDatums.putAll(namespace, datums); } @Scheduled(fixedDelay = 60000) private void send() { LOG.info("Sending metric data."); synchronized (queuedDatums) { sendBatch(LinkedListMultimap.create(queuedDatums).asMap()); queuedDatums.clear(); } } protected void sendBatch(Map<String, Collection<MetricDatum>> datums) { for (final Map.Entry<String, Collection<MetricDatum>> e : datums.entrySet()) { for (final List<MetricDatum> batch : Lists.partition(Lists.newLinkedList(e.getValue()), BATCH_SIZE)) { cloudWatch.putMetricDataAsync( new PutMetricDataRequest().withNamespace(e.getKey()).withMetricData(batch), new AsyncHandler<PutMetricDataRequest, Void>() { @Override public void onError(Exception exception) { LOG.error("PutMetricData failed", exception); LOG.info("Requeueing metric data."); queuedDatums.putAll(e.getKey(), batch); } @Override public void onSuccess(PutMetricDataRequest request, Void result) { LOG.info("Successfully put " + request.getMetricData().size() + " datums for namespace " + request.getNamespace()); LOG.debug("Request", request); } }); } } } }