@Test
    public void testMultiTypeService() {
        final String serviceName = "tinker.multi-type";

        final TriFunction<ServiceCallContext, TraverserSet<Object>, Map, Iterator<Integer>> barrier =
                (ctx, traverserSet, map) -> IteratorUtils.of(traverserSet.size());

        final TriFunction<ServiceCallContext, Traverser.Admin<Object>,Map,Iterator<Object>> streaming =
                (ctx, traverser, map) -> IteratorUtils.of(1);

        final BiFunction<ServiceCallContext, Map, Iterator<Integer>> start =
                (ctx, map) -> IteratorUtils.of(0);

        final TinkerServiceRegistry.LambdaServiceFactory factory = graph.getServiceRegistry().registerLambdaService(serviceName);
        factory.addStartLambda(start);
        factory.addStreamingLambda(streaming);
        factory.addBarrierLambda(barrier);

        checkResult("{\"name\":\"tinker.multi-type\",\"type:[requirements]:\":{\"Start\":[],\"Streaming\":[],\"Barrier\":[]},\"params\":{}}",
                g.call("--list").with("service", serviceName).with("verbose"));

        // start
        checkResult(0, g.call(serviceName));
        // streaming
        checkResults(Arrays.asList(1, 1, 1, 1, 1, 1), g.V().call(serviceName, asMap(LambdaServiceFactory.Options.TYPE, Type.Streaming)));
        // all at once
        checkResults(Arrays.asList(6), g.V().call(serviceName, asMap(LambdaServiceFactory.Options.TYPE, Type.Barrier)));
        // chunk size 2
        checkResults(Arrays.asList(2, 2, 2), g.V().call(serviceName, asMap(LambdaServiceFactory.Options.TYPE, Type.Barrier, LambdaServiceFactory.Options.CHUNK_SIZE, 2)));
        // chunk size 4
        checkResults(Arrays.asList(4, 2), g.V().call(serviceName, asMap(LambdaServiceFactory.Options.TYPE, Type.Barrier, LambdaServiceFactory.Options.CHUNK_SIZE, 4)));
    }
Services may need to specify traverser requirements.
tinkergraph-gremlin/src/test/java/org/apache/tinkerpop/gremlin/tinkergraph/structure/TinkerGraphServiceTest.java