title: java.lang.OutOfMemoryError: Java heap space (JUnit test)
body: <p>I have a class,which i use input stream and then conver it to string.
  Also i have a Junit test,where i get the exception " java.lang.OutOfMemoryError: Java heap space",I know that the problem is that I have a memory leak in the test, but I don’t understand how to fix it.Maybe someone know how to do it?</p>
  
  <p>My class:</p>
  
  <pre><code>public class IntegrationMonitoringHttpInterceptor implements ClientHttpRequestInterceptor
  {
  
      private static final Logger LOG = LoggerFactory.getLogger(IntegrationMonitoringHttpInterceptor.class);
  
      @Resource
      private IntegrationMessageService integrationMessageService;
  
      @Override
      public ClientHttpResponse intercept(final HttpRequest request, final byte[] bytes, final ClientHttpRequestExecution clientHttpRequestExecution) throws IOException
      {
          final String requestMethod = request.getMethod().toString();
          final String requestURI = request.getURI().toString();
          final String requestHeaders = request.getHeaders().toString();
          final String requestBody = new String(bytes, StandardCharsets.UTF_8);
          final String requestMessageBody = requestMethod + "\n" + requestURI + "\n" + requestHeaders + "\n" + requestBody;
  
          final IntegrationMessageBatchModel batch = saveRequest(requestURI, requestMessageBody);
  
          try
          {
              final ClientHttpResponse response = clientHttpRequestExecution.execute(request, bytes);
  
              final String responseStatusCode = response.getStatusCode().toString();
              final String responseStatusText = response.getStatusText();
              final String responseHeaders = response.getHeaders().toString();
              final InputStream responseInputStream = response.getBody();
              final String responseBody = IOUtils.toString(responseInputStream, StandardCharsets.UTF_8.name()); //in the test, a memory leak occurs here
              IOUtils.closeQuietly(responseInputStream);
              responseInputStream.close();
              final String responseMessageBody = responseStatusCode + "\n" + responseStatusText + responseHeaders + "\n" + responseBody;
  
  
              saveResponse(responseMessageBody, batch, requestURI);
  
              return response;
          }
          catch (Exception exception)
          {
              integrationMessageService.createMessageInBatch(exception.getMessage(), batch);
              LOG.warn("Cannot execute request due to unexpected error", exception);
              throw exception;
          }
  
      }
  
      private IntegrationMessageBatchModel saveRequest(final String requestURI, final String requestMessageBody)
      {
          try
          {
              IntegrationMessageBatchModel integrationMessageBatchModel = integrationMessageService.createBatch(IntegrationExchangeType.HTTP, requestURI);
              integrationMessageService.createMessageInBatch(requestMessageBody, integrationMessageBatchModel);
  
              return integrationMessageBatchModel;
          }
          catch (Exception exception)
          {
              LOG.warn("Cannot save message due to unexpected error", exception);
              return null;
          }
      }
  
      private void saveResponse(final String response, final IntegrationMessageBatchModel batchModel, final String requestURI)
      {
          try
          {
              if (batchModel != null)
              {
                  integrationMessageService.createMessageInBatch(response, batchModel);
              }
              else
              {
                  IntegrationMessageBatchModel integrationMessageBatchModel = integrationMessageService.createBatch(IntegrationExchangeType.HTTP, requestURI);
                  integrationMessageService.createMessageInBatch(response, integrationMessageBatchModel);
              }
          }
          catch (Exception exception)
          {
              LOG.warn("Cannot save message due to unexpected error", exception);
          }
      }
  }
  </code></pre>
  
  <p>My JUnit test:</p>
  
  <pre><code>@RunWith(MockitoJUnitRunner.class)
  @UnitTest
  public class IntegrationMonitoringHttpInterceptorTest
  {
      @Rule
      public ExpectedException thrown = ExpectedException.none();
  
      @Mock
      private IntegrationMessageService integrationMessageService;
  
      @Mock
      private HttpRequest httpRequest;
  
      @Mock
      private ClientHttpRequestExecution clientHttpRequestExecution;
  
      @Mock
      private ClientHttpResponse clientHttpResponse;
  
  
      @InjectMocks
      private IntegrationMonitoringHttpInterceptor integrationMonitoringHttpInterceptor = new IntegrationMonitoringHttpInterceptor();
  
      @Test
      public void intercept() throws Exception
      {
  
          final String body = "http message";
          final URI uri = new URI("http://headers.jsontest.com/");
          final InputStream inputStream = new InputStream()
          {
              @Override
              public int read()
              {
                  return 0;
              }
          };
          when(httpRequest.getURI()).thenReturn(uri);
          when(httpRequest.getMethod()).thenReturn(HttpMethod.POST);
          when(httpRequest.getHeaders()).thenReturn(new HttpHeaders());
          when(clientHttpRequestExecution.execute(httpRequest, body.getBytes(StandardCharsets.UTF_8))).thenReturn(clientHttpResponse);
          when(clientHttpResponse.getStatusCode()).thenReturn(HttpStatus.OK);
          when(clientHttpResponse.getStatusText()).thenReturn("OK");
          when(clientHttpResponse.getHeaders()).thenReturn(new HttpHeaders());
          when(clientHttpResponse.getBody()).thenReturn(inputStream);
          when(integrationMessageService.createBatch(eq(IntegrationExchangeType.HTTP), eq(uri.toString())))
                  .thenReturn(new IntegrationMessageBatchModel());
          when(integrationMessageService.createMessageInBatch(eq(body), any(IntegrationMessageBatchModel.class)))
                  .thenReturn(new IntegrationMessageModel());
          when(integrationMessageService.createMessageInBatch(contains(body), any(IntegrationMessageBatchModel.class)))
                  .thenReturn(new IntegrationMessageModel());
  
          integrationMonitoringHttpInterceptor.intercept(httpRequest, body.getBytes(StandardCharsets.UTF_8), clientHttpRequestExecution);
  
          verify(clientHttpRequestExecution, times(1)).execute(httpRequest, body.getBytes(StandardCharsets.UTF_8));
          verify(integrationMessageService, times(1)).createBatch(eq(IntegrationExchangeType.HTTP), eq(uri.toString()));
          verify(integrationMessageService, times(2)).createMessageInBatch(anyString(), any(IntegrationMessageBatchModel.class));
      }
  </code></pre>
  
  <p>Stacktrace:</p>
  
  <pre><code>java.lang.OutOfMemoryError: Java heap space
      at java.util.Arrays.copyOf(Arrays.java:2367)
      at java.lang.AbstractStringBuilder.expandCapacity(AbstractStringBuilder.java:130)
      at java.lang.AbstractStringBuilder.ensureCapacityInternal(AbstractStringBuilder.java:114)
      at java.lang.AbstractStringBuilder.append(AbstractStringBuilder.java:535)
      at java.lang.StringBuilder.append(StringBuilder.java:204)
      at org.apache.commons.io.output.StringBuilderWriter.write(StringBuilderWriter.java:138)
      at org.apache.commons.io.IOUtils.copyLarge(IOUtils.java:2002)
      at org.apache.commons.io.IOUtils.copyLarge(IOUtils.java:1980)
      at org.apache.commons.io.IOUtils.copy(IOUtils.java:1957)
      at org.apache.commons.io.IOUtils.copy(IOUtils.java:1907)
      at org.apache.commons.io.IOUtils.toString(IOUtils.java:778)
      at org.apache.commons.io.IOUtils.toString(IOUtils.java:803)
      at core.interceptors.IntegrationMonitoringHttpInterceptor.intercept(IntegrationMonitoringHttpInterceptor.java:48)
      at core.interceptors.IntegrationMonitoringHttpInterceptorTest.intercept(IntegrationMonitoringHttpInterceptorTest.java:85)
      at sun.reflect.NativeMethodAccessorImpl.invoke0(Native Method)
      at sun.reflect.NativeMethodAccessorImpl.invoke(NativeMethodAccessorImpl.java:57)
      at sun.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:43)
      at java.lang.reflect.Method.invoke(Method.java:606)
      at org.junit.runners.model.FrameworkMethod$1.runReflectiveCall(FrameworkMethod.java:44)
      at org.junit.internal.runners.model.ReflectiveCallable.run(ReflectiveCallable.java:15)
      at org.junit.runners.model.FrameworkMethod.invokeExplosively(FrameworkMethod.java:41)
      at org.junit.internal.runners.statements.InvokeMethod.evaluate(InvokeMethod.java:20)
      at org.junit.rules.ExpectedException$ExpectedExceptionStatement.evaluate(ExpectedException.java:110)
      at org.junit.rules.RunRules.evaluate(RunRules.java:18)
      at org.junit.runners.ParentRunner.runLeaf(ParentRunner.java:263)
      at org.junit.runners.BlockJUnit4ClassRunner.runChild(BlockJUnit4ClassRunner.java:69)
      at org.junit.runners.BlockJUnit4ClassRunner.runChild(BlockJUnit4ClassRunner.java:48)
      at org.junit.runners.ParentRunner$3.run(ParentRunner.java:231)
      at org.junit.runners.ParentRunner$1.schedule(ParentRunner.java:60)
      at org.junit.runners.ParentRunner.runChildren(ParentRunner.java:229)
      at org.junit.runners.ParentRunner.access$000(ParentRunner.java:50)
      at org.junit.runners.ParentRunner$2.evaluate(ParentRunner.java:222)
  </code></pre>