/** * Increment a counter metric when peeking at each tuple. * * @param <T> * TStream tuple type * @param stream to stream to instrument * @return a {@link TStream} containing the input tuples */ public static <T> TStream<T> counter(TStream<T> stream) { return stream.pipe(new CounterOp<T>()); }
/** * Add counter metrics to all the topology's streams. * <p> * {@link CounterOp} oplets are inserted between every two graph * vertices with the following exceptions: * <ul> * <li>Oplets are only inserted upstream from a FanOut oplet.</li> * <li>If a chain of Peek oplets exists between oplets A and B, a Metric * oplet is inserted after the last Peek, right upstream from oplet B.</li> * <li>If a chain a Peek oplets is followed by a FanOut, a metric oplet is * inserted between the last Peek and the FanOut oplet.</li> * <li>Oplets are not inserted immediately downstream from another * {@code CounterOp} oplet (but they are inserted upstream from one.)</li> * </ul> * The implementation is not idempotent: Calling the method twice * will insert a new set of metric oplets into the graph. * @param t * The topology * @see org.apache.edgent.graph.Graph#peekAll(org.apache.edgent.function.Supplier, org.apache.edgent.function.Predicate) Graph.peekAll() */ public static void counter(Topology t) { // peekAll() embodies the above exclusion semantics t.graph().peekAll( () -> new CounterOp<>(), v -> !(v.getInstance() instanceof CounterOp) ); } }
@Test public void metricNameCounter() throws Exception { Context<Object,Object> ctx = new Context<>(); ctx.addService(MetricRegistry.class, new MetricRegistry()); CounterOp<Object> op = new CounterOp<>(); op.initialize(ctx); assertNotNull(op.getMetricName()); op.close(); }
@Test public void metricNullNameCounter() throws Exception { Context<Object,Object> ctx = new Context<>(); CounterOp<Object> op = new CounterOp<>(); op.initialize(ctx); assertNull(op.getMetricName()); op.close(); }