io.instacount.client.InstacountClientTest.java Source code

Java tutorial

Introduction

Here is the source code for io.instacount.client.InstacountClientTest.java

Source

/**
 * Copyright (C) 2016 Instacount Inc. (developers@instacount.io)
 *
 * Licensed under the Apache License, Version 2.0 (the "License"); you may not use this file except in compliance with
 * the License. You may obtain a copy of the License at
 *
 * http://www.apache.org/licenses/LICENSE-2.0
 *
 * Unless required by applicable law or agreed to in writing, software distributed under the License is distributed on
 * an "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the License for the
 * specific language governing permissions and limitations under the License.
 */
package io.instacount.client;

import static org.hamcrest.CoreMatchers.*;
import static org.hamcrest.MatcherAssert.assertThat;
import static org.hamcrest.core.Is.is;
import static org.mockito.Mockito.mock;

import java.math.BigInteger;
import java.util.UUID;

import org.apache.commons.lang3.StringUtils;
import org.junit.BeforeClass;
import org.junit.Test;

import com.google.common.base.Optional;
import com.google.common.base.Preconditions;

import io.instacount.client.Constants.Links;
import io.instacount.client.InstacountClientParams.AbstractInstacountClientParams;
import io.instacount.client.exceptions.InstacountClientException;
import io.instacount.client.model.Errors;
import io.instacount.client.model.Errors.Error;
import io.instacount.client.model.InstacountResponse;
import io.instacount.client.model.shardedcounters.ShardedCounter;
import io.instacount.client.model.shardedcounters.ShardedCounter.CounterStatus;
import io.instacount.client.model.shardedcounters.ShardedCounterOperation;
import io.instacount.client.model.shardedcounters.ShardedCounterOperation.CounterOperationType;
import io.instacount.client.model.shardedcounters.inputs.CreateShardedCounterInput;
import io.instacount.client.model.shardedcounters.inputs.DecrementShardedCounterInput;
import io.instacount.client.model.shardedcounters.inputs.IncrementShardedCounterInput;
import io.instacount.client.model.shardedcounters.inputs.ShardedCounterStatusInput;
import io.instacount.client.model.shardedcounters.inputs.UpdateShardedCounterInput;
import io.instacount.client.model.shardedcounters.responses.CounterLocationInfo;
import io.instacount.client.model.shardedcounters.responses.CreateShardedCounterResponse;
import io.instacount.client.model.shardedcounters.responses.DecrementShardedCounterResponse;
import io.instacount.client.model.shardedcounters.responses.GetShardedCounterResponse;
import io.instacount.client.model.shardedcounters.responses.IncrementShardedCounterResponse;
import io.instacount.client.model.shardedcounters.responses.UpdateShardedCounterResponse;

/**
 * A test harness for testing the Instacount Client.
 */
public class InstacountClientTest {
    private static final boolean SYNC = false;
    private static final boolean ASYNC = true;

    private static Instacount client;

    @BeforeClass
    public static void before() {
        final AbstractInstacountClientParams params = new AbstractInstacountClientParams(false) {
            @Override
            public String getInstacountApplicationId() {
                return Preconditions.checkNotNull(System.getenv("INSTACOUNT_APPLICATION_ID"),
                        "System Env variable 'INSTACOUNT_APPLICATION_ID' not specified!");
            }

            @Override
            public String getInstacountReadOnlyApplicationKey() {
                return Preconditions.checkNotNull(System.getenv("INSTACOUNT_READ_ONLY_KEY"),
                        "System Env variable 'INSTACOUNT_READ_ONLY_KEY' not specified!");
            }

            @Override
            public String getInstacountReadWriteApplicationKey() {
                return Preconditions.checkNotNull(System.getenv("INSTACOUNT_READ_WRITE_KEY"),
                        "System Env variable 'INSTACOUNT_READ_WRITE_KEY' not specified!");
            }
        };

        final String accessToken = System.getenv("GOOGLE_ACCOUNTS_OAUTH_ACCESS_TOKEN");
        if (!StringUtils.isBlank(accessToken)) {
            final InstacountOAuth2BearerRequestInterceptor oauth2 = new InstacountOAuth2BearerRequestInterceptor.Impl(
                    accessToken);
            client = Instacount.Builder.build(params, oauth2);
        } else {
            client = Instacount.Builder.build(params);
        }
    }

    /////////////////////////////
    // Sharded Counter Happy Path
    /////////////////////////////

    @Test
    public void testShardedCounterHappyPath() throws InstacountClientException {
        try {
            final String counterName = UUID.randomUUID().toString();
            {
                /////////
                // Create the Counter
                final CreateShardedCounterInput createCounterInput = new CreateShardedCounterInput(counterName);
                final CreateShardedCounterResponse createdCounterResponse = this.client
                        .createShardedCounter(createCounterInput);
                this.doBasicAssertions(createdCounterResponse, 201);
            }
            {
                /////////
                // Get the Counter
                final GetShardedCounterResponse createdShardedCounterResponse = this.client
                        .getShardedCounter(counterName);
                this.doBasicAssertions(createdShardedCounterResponse, 200);
                this.doShardedCounterAssertions(createdShardedCounterResponse.getShardedCounter(), counterName,
                        Optional.<String>absent(), 3, CounterStatus.AVAILABLE);
            }
            {
                ////////////
                // Increment the Counter by 1
                final IncrementShardedCounterResponse incrementShardedCounterResponse = client
                        .incrementShardedCounter(counterName);
                this.doBasicAssertions(incrementShardedCounterResponse, 201);
            }
            {
                ////////////
                // Increment the Counter by 10
                final IncrementShardedCounterResponse incrementShardedCounterResponse2 = client
                        .incrementShardedCounter(counterName,
                                new IncrementShardedCounterInput(BigInteger.TEN, false));
                this.doBasicAssertions(incrementShardedCounterResponse2, 201);
            }
            {
                ////////////
                // Decrement the Counter by 1
                final DecrementShardedCounterResponse decrementShardedCounterResponse = client
                        .decrementShardedCounter(counterName);
                this.doBasicAssertions(decrementShardedCounterResponse, 201);
            }
            {
                ////////////
                // Decrement the Counter by 10
                final DecrementShardedCounterResponse decrementShardedCounterResponse2 = client
                        .decrementShardedCounter(counterName,
                                new DecrementShardedCounterInput(BigInteger.TEN, false));
                this.doBasicAssertions(decrementShardedCounterResponse2, 201);
            }
            {
                ////////////
                // Get the Counter

                final GetShardedCounterResponse response = client.getShardedCounter(counterName);
                assertThat(response.getHttpResponseCode(), is(200));

                this.doShardedCounterAssertions(response.getShardedCounter(), counterName,
                        Optional.<String>absent(), 3, CounterStatus.AVAILABLE);

                assertThat(response.getShardedCounter().getCount(), is(BigInteger.ZERO));
            }
        } catch (InstacountClientException e) {
            assertThat(e.getErrors().getHttpResponseCode(), is(400));
            throw e;
        }
    }

    //////////////////////////
    // Test Create Counter
    //////////////////////////

    @Test(expected = NullPointerException.class)
    public void testCreateCounter_WithPayload_Null() throws InstacountClientException {
        this.client.createShardedCounter(null);
    }

    @Test
    public void testCreateCounter() throws InstacountClientException {
        final CreateShardedCounterResponse actualResponse = this.client.createShardedCounter();

        this.doBasicAssertions(actualResponse, 201);
        final CounterLocationInfo counterInfo = actualResponse.getOptCounterInfo().get();
        assertThat(counterInfo.getCounterName(), is(not(nullValue())));
        assertThat(counterInfo.getLocationUrl().startsWith(Links.API_URL), is(true));
    }

    @Test
    public void testCreateCounter_WithPayload_WithName() throws InstacountClientException {
        final String counterName = UUID.randomUUID().toString();
        final CreateShardedCounterInput createCounterInput = new CreateShardedCounterInput(counterName);
        final CreateShardedCounterResponse actualResponse = this.client.createShardedCounter(createCounterInput);

        this.doBasicAssertions(actualResponse, 201);
        final CounterLocationInfo counterInfo = actualResponse.getOptCounterInfo().get();
        assertThat(counterInfo.getCounterName(), is(counterName));
        assertThat(counterInfo.getLocationUrl(), is(Links.API_URL + "/sharded_counters/" + counterName));

        this.doShardedCounterAssertions(client.getShardedCounter(counterName).getShardedCounter(), counterName,
                Optional.<String>absent(), 3, CounterStatus.AVAILABLE);
    }

    @Test
    public void testCreateCounter_WithPayload_WithNameAndDescription() throws InstacountClientException {
        final String counterName = UUID.randomUUID().toString();
        final String counterDescription = "Sample description from ClientTestHarness.java\"";
        final CreateShardedCounterInput createCounterInput = new CreateShardedCounterInput(counterName,
                counterDescription);
        final CreateShardedCounterResponse actualResponse = this.client.createShardedCounter(createCounterInput);

        this.doBasicAssertions(actualResponse, 201);
        final CounterLocationInfo counterInfo = actualResponse.getOptCounterInfo().get();
        assertThat(counterInfo.getCounterName(), is(counterName));
        assertThat(counterInfo.getLocationUrl(), is(Links.API_URL + "/sharded_counters/" + counterName));

        this.doShardedCounterAssertions(client.getShardedCounter(counterName).getShardedCounter(), counterName,
                Optional.of(counterDescription), 3, CounterStatus.AVAILABLE);
    }

    @Test
    public void testCreateCounter_WithPayload_WithExistingCounterName() throws InstacountClientException {
        final String counterName = UUID.randomUUID().toString();

        final CreateShardedCounterInput createCounterInput = new CreateShardedCounterInput(counterName);
        final CreateShardedCounterResponse actualResponse = this.client.createShardedCounter(createCounterInput);

        this.doBasicAssertions(actualResponse, 201);

        // Try again, expect an error!
        try {
            this.client.createShardedCounter(createCounterInput);
        } catch (InstacountClientException e) {
            assertThat(e.getErrors(), is(not(nullValue())));
            assertThat(e.getErrors().getHttpResponseCode(), is(409));
            assertThat(e.getErrors().getErrors(), is(not(nullValue())));
            assertThat(e.getErrors().getErrors().size(), is(1));
            final Error error = e.getErrors().getErrors().get(0);
            assertThat(error.getMessage(), is("This counter already exists!"));
            assertThat(error.getDeveloperMessage(),
                    is("A sharded counter with the specified name already exists!"));
            assertThat(error.getMoreInfo(), is("https://instacount.readme.io"));
        }
    }

    @Test
    public void testCreateCounter_WithFullPayload() throws InstacountClientException {
        final String counterName = UUID.randomUUID().toString();
        final String counterDescription = "Sample description from ClientTestHarness.java\"";

        final CreateShardedCounterInput createCounterInput = new CreateShardedCounterInput(counterName,
                Optional.of(counterDescription), 3, ShardedCounterStatusInput.READ_ONLY_COUNT);

        final CreateShardedCounterResponse actualResponse = this.client.createShardedCounter(createCounterInput);

        this.doBasicAssertions(actualResponse, 201);
        final CounterLocationInfo counterInfo = actualResponse.getOptCounterInfo().get();
        assertThat(counterInfo.getCounterName(), is(counterName));
        assertThat(counterInfo.getLocationUrl(), is(Links.API_URL + "/sharded_counters/" + counterName));

        final ShardedCounter createdShardedCounter = this.client.getShardedCounter(counterName).getShardedCounter();

        // FIXME ref #143
        this.doShardedCounterAssertions(createdShardedCounter, counterName, Optional.of(counterDescription), 3,
                CounterStatus.READ_ONLY_COUNT);
    }

    //////////////////////////
    // Test Get Counter
    //////////////////////////

    @Test(expected = NullPointerException.class)
    public void testGetCounter_NullCounterName() throws InstacountClientException {
        client.getShardedCounter(null);
    }

    @Test(expected = IllegalArgumentException.class)
    public void testGetCounter_EmptCounterName() throws InstacountClientException {
        client.getShardedCounter("");
    }

    @Test
    public void testGetCounter_NonExistentCounterName() throws InstacountClientException {
        try {
            final String counterName = UUID.randomUUID().toString();
            final CreateShardedCounterInput createCounterInput = new CreateShardedCounterInput(counterName);
            client.createShardedCounter(createCounterInput);
            client.getShardedCounter(counterName);
        } catch (InstacountClientException e) {
            this.doNotFoundAssertions(e.getErrors());
        }
    }

    @Test
    public void testGetCounter() throws InstacountClientException {
        final String counterName = UUID.randomUUID().toString();
        final CreateShardedCounterInput createCounterInput = new CreateShardedCounterInput(counterName);
        final CreateShardedCounterResponse createResponse = client.createShardedCounter(createCounterInput);

        final GetShardedCounterResponse shardedCounter = client
                .getShardedCounter(createResponse.getOptCounterInfo().get().getCounterName());

        this.doShardedCounterAssertions(shardedCounter.getShardedCounter(), counterName, Optional.<String>absent(),
                3, CounterStatus.AVAILABLE);
    }

    //////////////////////////
    // Test Update Counter
    //////////////////////////

    @Test(expected = NullPointerException.class)
    public void testUpdateCounter_NullCounterName() throws InstacountClientException {
        client.updateShardedCounter(null, mock(UpdateShardedCounterInput.class));
    }

    @Test(expected = IllegalArgumentException.class)
    public void testUpdateCounter_EmptyCounterName() throws InstacountClientException {
        client.updateShardedCounter("", mock(UpdateShardedCounterInput.class));
    }

    @Test(expected = NullPointerException.class)
    public void testUpdateCounter_NullCounterInput() throws InstacountClientException {
        final String counterName = UUID.randomUUID().toString();
        client.updateShardedCounter(counterName, null);
    }

    @Test
    public void testUpdateCounter_NonExistentCounterName() throws InstacountClientException {
        try {
            final UpdateShardedCounterInput updateCounterInput = new UpdateShardedCounterInput("foo");
            client.updateShardedCounter("foo", updateCounterInput);
        } catch (InstacountClientException e) {
            this.doNotFoundAssertions(e.getErrors());
        }
    }

    @Test
    public void testUpdateCounter() throws InstacountClientException {
        final String counterName = UUID.randomUUID().toString();

        // First,create the counter...
        final CreateShardedCounterInput createCounterInput = new CreateShardedCounterInput(counterName,
                Optional.<String>absent(), 1, ShardedCounterStatusInput.AVAILABLE);
        client.createShardedCounter(createCounterInput);

        // Next, update all values, and assert the differences...
        final UpdateShardedCounterInput updateCounterInput = new UpdateShardedCounterInput(counterName,
                Optional.of("New Description"), 3, ShardedCounterStatusInput.READ_ONLY_COUNT);
        final UpdateShardedCounterResponse updatedShardedCounterResponse = client.updateShardedCounter(counterName,
                updateCounterInput);

        assertThat(updatedShardedCounterResponse.getHttpResponseCode(), is(200));
        final ShardedCounter updatedShardedCounter = updatedShardedCounterResponse.getShardedCounter();
        assertThat(updatedShardedCounter.getName(), is(counterName));
        assertThat(updatedShardedCounter.getCounterStatus(), is(CounterStatus.READ_ONLY_COUNT));
        assertThat(updatedShardedCounter.getOptDescription().get(), is("New Description"));

        // FIXME Ref #152.
        assertThat(updatedShardedCounter.getNumShards(), is(3));
    }

    //////////////////////////
    // Test Increment Counter
    //////////////////////////

    @Test(expected = NullPointerException.class)
    public void testIncrement_NullCounterName() throws InstacountClientException {
        client.incrementShardedCounter(null);
    }

    @Test(expected = IllegalArgumentException.class)
    public void testIncrement_EmptyCounterName() throws InstacountClientException {
        client.incrementShardedCounter("");
    }

    @Test(expected = NullPointerException.class)
    public void testIncrement_NullPayload() throws InstacountClientException {
        final String counterName = UUID.randomUUID().toString();
        client.incrementShardedCounter(counterName, null);
    }

    @Test
    public void testIncrement_NoPayload() throws InstacountClientException {
        final String counterName = UUID.randomUUID().toString();
        client.incrementShardedCounter(counterName);
        assertThat(client.getShardedCounter(counterName).getShardedCounter().getCount(),
                is(BigInteger.valueOf(1L)));
    }

    @Test
    public void testIncrement_Sync() throws InstacountClientException {
        final String counterName = UUID.randomUUID().toString();
        final IncrementShardedCounterResponse response = client.incrementShardedCounter(counterName,
                new IncrementShardedCounterInput(BigInteger.TEN, SYNC));
        assertThat(response.getOptCounterOperation().isPresent(), is(true));
        assertThat(response.getOptCounterOperation().get().getAmount(), is(BigInteger.TEN));
        assertThat(response.getOptCounterOperation().get().getCounterOperationType(),
                is(CounterOperationType.INCREMENT));
        assertThat(response.getOptCounterOperation().get().getShardIndex(), anyOf(is(0), is(1), is(2)));
        assertThat(response.getOptCounterOperation().get().getId(), is(not(nullValue())));

        // Get the counter and assert its value!
        assertThat(client.getShardedCounter(counterName).getShardedCounter().getCount(), is(BigInteger.TEN));
    }

    @Test
    public void testIncrement_Async() throws InstacountClientException {
        final String counterName = UUID.randomUUID().toString();
        final IncrementShardedCounterResponse response = client.incrementShardedCounter(counterName,
                new IncrementShardedCounterInput(BigInteger.TEN, ASYNC));

        assertThat(response.getHttpResponseCode(), is(202));
        assertThat(response.getOptCounterOperation().isPresent(), is(false));

        // Get the counter and assert its value!
        assertThat(client.getShardedCounter(counterName).getHttpResponseCode(), anyOf(is(200), is(404)));
    }

    //////////////////////////
    // Test Decrement Counter
    //////////////////////////

    @Test(expected = NullPointerException.class)
    public void testDecrement_NullCounterName() throws InstacountClientException {
        client.decrementShardedCounter(null);
    }

    @Test(expected = IllegalArgumentException.class)
    public void testDecrement_EmptyCounterName() throws InstacountClientException {
        client.decrementShardedCounter("");
    }

    @Test(expected = NullPointerException.class)
    public void testDecrement_NullPayload() throws InstacountClientException {
        final String counterName = UUID.randomUUID().toString();
        client.decrementShardedCounter(counterName, null);
    }

    @Test
    public void testDecrement_NoPayload() throws InstacountClientException {
        final String counterName = UUID.randomUUID().toString();
        client.decrementShardedCounter(counterName);
        assertThat(client.getShardedCounter(counterName).getShardedCounter().getCount(),
                is(BigInteger.valueOf(-1L)));
    }

    @Test
    public void testDecrement_Sync() throws InstacountClientException {
        final String counterName = UUID.randomUUID().toString();
        final DecrementShardedCounterResponse response = client.decrementShardedCounter(counterName,
                new DecrementShardedCounterInput(BigInteger.TEN, SYNC));
        assertThat(response.getOptCounterOperation().isPresent(), is(true));
        assertThat(response.getOptCounterOperation().get().getAmount(), is(BigInteger.TEN));
        assertThat(response.getOptCounterOperation().get().getCounterOperationType(),
                is(CounterOperationType.DECREMENT));
        assertThat(response.getOptCounterOperation().get().getShardIndex(), anyOf(is(0), is(1), is(2)));
        assertThat(response.getOptCounterOperation().get().getId(), is(not(nullValue())));

        // Get the counter and assert its value!
        assertThat(client.getShardedCounter(counterName).getShardedCounter().getCount(),
                is(BigInteger.valueOf(-10L)));
    }

    @Test
    public void testDecrement_Async() throws InstacountClientException {
        final String counterName = UUID.randomUUID().toString();
        final DecrementShardedCounterResponse response = client.decrementShardedCounter(counterName,
                new DecrementShardedCounterInput(BigInteger.TEN, ASYNC));

        assertThat(response.getHttpResponseCode(), is(202));
        assertThat(response.getOptCounterOperation().isPresent(), is(false));

        // Get the counter and assert its value!
        assertThat(client.getShardedCounter(counterName).getHttpResponseCode(), anyOf(is(200), is(404)));
    }

    //////////////////////////
    // Test Get CounterOperation
    //////////////////////////

    @Test(expected = NullPointerException.class)
    public void testGetCounterOperation_NullCounterName() throws InstacountClientException {
        client.getShardedCounterOperation(null, 0, UUID.randomUUID().toString());
    }

    @Test(expected = IllegalArgumentException.class)
    public void testGetCounterOperation_EmptyCounterName() throws InstacountClientException {
        client.getShardedCounterOperation("", 0, UUID.randomUUID().toString());
    }

    @Test(expected = NullPointerException.class)
    public void testGetCounterOperation_NullShardIndex() throws InstacountClientException {
        final String counterName = UUID.randomUUID().toString();
        client.getShardedCounterOperation(counterName, null, UUID.randomUUID().toString());
    }

    @Test(expected = NullPointerException.class)
    public void testGetCounterOperation_NullOperationId() throws InstacountClientException {
        final String counterName = UUID.randomUUID().toString();
        client.getShardedCounterOperation(counterName, 1, null);
    }

    @Test(expected = IllegalArgumentException.class)
    public void testGetCounterOperation_EmptyOperationId() throws InstacountClientException {
        final String counterName = UUID.randomUUID().toString();
        client.getShardedCounterOperation(counterName, 1, "");
    }

    @Test
    public void testGetCounterOperationIndex() throws InstacountClientException {
        // Create the ShardedCounter
        final CreateShardedCounterResponse result = client.createShardedCounter();
        final String counterName = result.getOptCounterInfo().get().getCounterName();

        // Increment the ShardedCounter
        final ShardedCounterOperation createdCounterOperation = client.incrementShardedCounter(counterName)
                .getOptCounterOperation().get();

        // Get the ShardedCounter from the API.
        final ShardedCounterOperation loadedCounterOperation = client.getShardedCounterOperation(counterName,
                createdCounterOperation.getShardIndex(), createdCounterOperation.getId()).getCounterOperation();

        // Assert that the ShardedCounterOperation returned from the create matches the value returned from the GET.
        this.doCounterOperationAssertions(createdCounterOperation, counterName, loadedCounterOperation.getId(),
                loadedCounterOperation.getShardIndex(), loadedCounterOperation.getCounterOperationType(),
                loadedCounterOperation.getAmount());
    }

    //////////////////
    // Private Helpers
    //////////////////

    private void doShardedCounterAssertions(final ShardedCounter actualShardedCounter,
            final String expectedCounterName, final Optional<String> optExpectedDescription,
            final int expectedNumShards, final CounterStatus expectedCounterStatus) {
        assertThat(actualShardedCounter.getMeta().getSelfLink().getHrefUrl().toString(),
                is(Links.API_URL + "/sharded_counters/" + expectedCounterName));
        assertThat(actualShardedCounter.getMeta().getIncrementsLink().getHrefUrl().toString(),
                is(Links.API_URL + "/sharded_counters/" + expectedCounterName + "/increments"));
        assertThat(actualShardedCounter.getMeta().getDecrementsLink().getHrefUrl().toString(),
                is(Links.API_URL + "/sharded_counters/" + expectedCounterName + "/decrements"));

        assertThat(actualShardedCounter.getName(), is(expectedCounterName));

        if (optExpectedDescription.isPresent()) {
            assertThat(actualShardedCounter.getOptDescription().isPresent(), is(true));
            assertThat(actualShardedCounter.getOptDescription().get(), is(optExpectedDescription.get()));
        } else {
            assertThat(actualShardedCounter.getOptDescription().isPresent(), is(false));
        }

        assertThat(actualShardedCounter.getNumShards(), is(expectedNumShards));
        assertThat(actualShardedCounter.getCounterStatus(), is(expectedCounterStatus));
        // logger.info("Actual Creation: " + actualCounter.getCreatedDateTime());
        // logger.info("Expect Creation: " + expectedCounter.getCreatedDateTime());
        // assertThat(actualCounter.getCreatedDateTime().isAfter(expectedCounter.getCreatedDateTime()), is(true));
        assertThat(actualShardedCounter.getCreatedDateTime(), is(not(nullValue())));
    }

    private void doCounterOperationAssertions(final ShardedCounterOperation counterOperation,
            final String expectedCounterName, final String expectedOperationId, final int expectedShardIndex,
            final CounterOperationType expectedCounterOperationType, final BigInteger expectedAmount) {
        assertThat(counterOperation.getMeta().getSelfLink().getHrefUrl().toString(),
                is(Links.API_URL + "/sharded_counters/" + expectedCounterName + "/shards/" + expectedShardIndex
                        + "/operations/" + expectedOperationId));
        assertThat(counterOperation.getMeta().getCounterLink().getHrefUrl().toString(),
                is(Links.API_URL + "/sharded_counters/" + expectedCounterName));

        assertThat(counterOperation.getId(), is(expectedOperationId));
        assertThat(counterOperation.getShardIndex(), is(expectedShardIndex));
        assertThat(counterOperation.getCounterOperationType(), is(expectedCounterOperationType));
        assertThat(counterOperation.getAmount(), is(expectedAmount));
        assertThat(counterOperation.getCreatedDateTime(), is(not(nullValue())));
    }

    private void doBasicAssertions(final InstacountResponse instacountResponse,
            final int expectedHttpResponseCode) {
        assertThat(instacountResponse.getHttpResponseCode(), is(expectedHttpResponseCode));
        assertThat(instacountResponse.getQuota(), is(not(nullValue())));
        assertThat(instacountResponse.getQuota().getNumAccessRequestsLimit() > 0, is(true));
        assertThat(instacountResponse.getQuota().getNumMutationRequestsLimit() > 0, is(true));
        assertThat(instacountResponse.getQuota().getNumAccessRequestsRemaining() > 0, is(true));
        assertThat(instacountResponse.getQuota().getNumAccessRequestsRemaining() > 0, is(true));
        assertThat(instacountResponse.getResponse(), is(not(nullValue())));
    }

    private void doNotFoundAssertions(final Errors errors) {
        assertThat(errors, is(not(nullValue())));
        assertThat(errors.getHttpResponseCode(), is(404));
        assertThat(errors.getErrors(), is(not(nullValue())));
        assertThat(errors.getErrors().size(), is(1));
        final Error error = errors.getErrors().get(0);
        assertThat(error.getMessage(), is("What you requested does not exist."));
        assertThat(error.getDeveloperMessage(), is("The requested resource was not found!"));
        assertThat(error.getMoreInfo(), is("https://instacount.readme.io"));
    }
}