@Test
  public void roundTrip() throws JSONException {
    Response response = new Response();
    response.setStatus(ErrorCodes.SUCCESS);
    response.setValue(ImmutableMap.of("color", "red"));

    HttpResponse httpResponse = codec.encode(response);
    Response decoded = codec.decode(httpResponse);

    assertEquals(response.getStatus(), decoded.getStatus());
    assertEquals(response.getSessionId(), decoded.getSessionId());
    assertEquals(response.getValue(), decoded.getValue());
  }
  @Test
  public void decodeJsonResponseMissingContentType() throws JSONException {
    Response response = new Response();
    response.setStatus(ErrorCodes.ASYNC_SCRIPT_TIMEOUT);
    response.setValue(ImmutableMap.of("color", "red"));

    HttpResponse httpResponse = new HttpResponse();
    httpResponse.setStatus(HTTP_OK);
    httpResponse.setContent(new BeanToJsonConverter().convert(response).getBytes(UTF_8));

    Response decoded = codec.decode(httpResponse);
    assertEquals(response.getStatus(), decoded.getStatus());
    assertEquals(response.getSessionId(), decoded.getSessionId());
    assertEquals(response.getValue(), decoded.getValue());
  }
  @Test
  public void decodeNonJsonResponse_204() throws JSONException {
    HttpResponse response = new HttpResponse();
    response.setStatus(HTTP_NO_CONTENT);

    Response decoded = codec.decode(response);
    assertEquals(ErrorCodes.SUCCESS, decoded.getStatus());
    assertNull(decoded.getValue());
  }
  @Test
  public void decodeNonJsonResponse_200() throws JSONException {
    HttpResponse response = new HttpResponse();
    response.setStatus(HTTP_OK);
    response.setContent("foobar".getBytes(UTF_8));

    Response decoded = codec.decode(response);
    assertEquals(ErrorCodes.SUCCESS, decoded.getStatus());
    assertEquals("foobar", decoded.getValue());
  }
  @Test
  public void convertsResponses_failure() throws JSONException {
    Response response = new Response();
    response.setStatus(ErrorCodes.NO_SUCH_ELEMENT);
    response.setValue(ImmutableMap.of("color", "red"));

    HttpResponse converted = codec.encode(response);
    assertThat(converted.getStatus(), is(HTTP_INTERNAL_ERROR));
    assertThat(converted.getHeader(CONTENT_TYPE), is(JSON_UTF_8.toString()));

    Response rebuilt =
        new JsonToBeanConverter()
            .convert(Response.class, new String(converted.getContent(), UTF_8));

    assertEquals(response.getStatus(), rebuilt.getStatus());
    assertEquals(response.getState(), rebuilt.getState());
    assertEquals(response.getSessionId(), rebuilt.getSessionId());
    assertEquals(response.getValue(), rebuilt.getValue());
  }
  @Test
  public void decodeNonJsonResponse_5xx() throws JSONException {
    HttpResponse response = new HttpResponse();
    response.setStatus(HTTP_INTERNAL_ERROR);
    response.setContent("foobar".getBytes(UTF_8));

    Response decoded = codec.decode(response);
    assertEquals(ErrorCodes.UNHANDLED_ERROR, decoded.getStatus());
    assertEquals("foobar", decoded.getValue());
  }
  @Test
  public void decodeNonJsonResponse_4xx() throws JSONException {
    HttpResponse response = new HttpResponse();
    response.setStatus(HTTP_BAD_REQUEST);
    response.setContent("foobar".getBytes(UTF_8));

    Response decoded = codec.decode(response);
    assertEquals(ErrorCodes.UNKNOWN_COMMAND, decoded.getStatus());
    assertEquals("foobar", decoded.getValue());
  }