@Builder private RestliServiceBasedLimiter(String resourceLimited, String serviceIdentifier, MetricContext metricContext, RequestSender requestSender) { Preconditions.checkNotNull(requestSender, "Request sender cannot be null."); this.bachedPermitsContainer = BatchedPermitsRequester.builder() .resourceId(resourceLimited).requestorIdentifier(serviceIdentifier).requestSender(requestSender).build(); this.metricContext = Optional.fromNullable(metricContext); if (this.metricContext.isPresent()) { this.permitsRequestedMeter = Optional.of(this.metricContext.get().meter(PERMITS_REQUESTED_METER_NAME)); this.permitsGrantedMeter = Optional.of(this.metricContext.get().meter(PERMITS_GRANTED_METER_NAME)); } else { this.permitsRequestedMeter = Optional.absent(); this.permitsGrantedMeter = Optional.absent(); } }
Queue<RequestAndCallback> queue = Queues.newArrayDeque(); BatchedPermitsRequester container = BatchedPermitsRequester.builder().resourceId("resource") .requestorIdentifier("requestor").requestSender(new TestRequestSender(queue, false)).build(); try (ParallelRequester requester = new ParallelRequester(container)) {
@Test public void testForwardingOfRequests() throws Exception { Queue<RequestAndCallback> queue = Queues.newArrayDeque(); BatchedPermitsRequester container = BatchedPermitsRequester.builder().resourceId("resource") .requestorIdentifier("requestor").requestSender(new TestRequestSender(queue, false)).build(); try (ParallelRequester requester = new ParallelRequester(container)) { Future<Boolean> future = requester.request(10); await(new QueueSize(queue, 1), 1000); Assert.assertEquals(queue.size(), 1); satisfyRequestBuilder().requestAndCallback(queue.poll()).satisfy(); future.get(1, TimeUnit.SECONDS); Assert.assertTrue(future.isDone()); Assert.assertTrue(future.get()); } }
@Test public void testRetriableFail() throws Exception { Queue<RequestAndCallback> queue = Queues.newArrayDeque(); BatchedPermitsRequester container = BatchedPermitsRequester.builder().resourceId("resource") .requestorIdentifier("requestor").requestSender(new TestRequestSender(queue, false)).build(); try (ParallelRequester requester = new ParallelRequester(container)) { Future<Boolean> future = requester.request(10); for (int i = 0; i < BatchedPermitsRequester.MAX_RETRIES; i++) { // container will fail 5 times await(new QueueSize(queue, 1), 1000); Assert.assertFalse(future.isDone()); failRequestBuilder().requestAndCallback(queue.poll()).fail(); } // should return a failure Assert.assertFalse(future.get()); // should not make any more request Assert.assertEquals(queue.size(), 0); } }
@Test public void testNonRetriableFail() throws Exception { Queue<RequestAndCallback> queue = Queues.newArrayDeque(); BatchedPermitsRequester container = BatchedPermitsRequester.builder().resourceId("resource") .requestorIdentifier("requestor").requestSender(new TestRequestSender(queue, false)).build(); try (ParallelRequester requester = new ParallelRequester(container)) { Future<Boolean> future = requester.request(10); // container should only try request once await(new QueueSize(queue, 1), 1000); Assert.assertFalse(future.isDone()); failRequestBuilder().requestAndCallback(queue.poll()).errorStatus(HttpStatus.S_422_UNPROCESSABLE_ENTITY).fail(); Assert.assertFalse(future.get()); Assert.assertEquals(queue.size(), 0); } }