internal async static Task <T> makeRequest <T>(string endpoint, string method, object body = null) where T : DefaultObjectWrapper
        {
            var responseMessage = await CapsuleClient.makeApiCall(endpoint, body, method);

            T responseObject;

            if (responseMessage.StatusCode == System.Net.HttpStatusCode.OK ||
                responseMessage.StatusCode == System.Net.HttpStatusCode.Created ||
                responseMessage.StatusCode == System.Net.HttpStatusCode.NoContent)
            {
                var responseContent = await responseMessage.Content.ReadAsStringAsync();

                responseObject = JsonConvert.DeserializeObject <T>(responseContent);

                if (responseMessage.Headers.Any(p => p.Key == "Link"))
                {
                    responseObject.Pagination.Parse(responseMessage.Headers.FirstOrDefault(p => p.Key == "Link").Value);
                }
            }
            else if (responseMessage.StatusCode == System.Net.HttpStatusCode.NoContent)
            {
                return(default(T));
            }
            else
            {
                var responseContent = await responseMessage.Content.ReadAsStringAsync();

                throw new InvalidOperationException(responseContent);
            }

            return(responseObject);
        }
        internal async static Task <T> baseGetRequest <T>(string endpoint, DateTime?since, int page, int perPage, Embed[] embed) where T : DefaultObjectWrapper
        {
            var requestString = new StringBuilder($"{endpoint}?");

            if (page < 1)
            {
                page = 1;
            }

            requestString.Append($"page={page}&");

            if (perPage > 100)
            {
                perPage = 100;
            }

            requestString.Append($"perPage={perPage}&");

            if (since != null && since.HasValue)
            {
                requestString.Append($"since={since.Value.ToString("yyyy-MM-dd")}");
            }

            if (embed != null && embed.Length > 0)
            {
                requestString.Append($"embed={string.Join(",", embed)}");
            }

            return(await CapsuleClient.makeRequest <T>(requestString.ToString(), "GET"));
        }
        public async static Task <bool> RemoveAdditionalPartyAsync(long opportunityId, long partyId)
        {
            var endpoint = new StringBuilder($"{BASE_ENDPOINT}/{opportunityId}/parties/{partyId}");

            var apiResponse = await CapsuleClient.makeRequest(endpoint.ToString(), "DELETE");

            return(apiResponse);
        }
        public async static Task <OpportunityWrapper> ListByPartyAsync(long partyId, int page = 1, int perPage = 20, Embed[] embed = null)
        {
            var endpoint = $"{BASE_ENDPOINT}/{partyId}/opportunities";

            var opportunities = await CapsuleClient.baseGetRequest <OpportunityWrapper>(BASE_ENDPOINT, null, page, perPage, embed);

            return(opportunities);
        }
        public async static Task <OpportunityWrapper> SearchOpportunitiesAsync(string query, int page = 1, int perPage = 20)
        {
            var endpoint = $"{BASE_ENDPOINT}/search?q={query}&page={page}&perPage={perPage}";

            var foundOpportunities = await CapsuleClient.makeRequest <OpportunityWrapper>(endpoint, "GET");

            return(foundOpportunities);
        }
        public async static Task <Opportunity> CreateAsync(Opportunity opportunity)
        {
            var wrapperObject = OpportunityWrapper.Load(opportunity);

            var response = await CapsuleClient.makeRequest <OpportunityWrapper>(BASE_ENDPOINT,
                                                                                "POST",
                                                                                wrapperObject);

            return(response.Opportunity);
        }
        public async static Task <Party> UpdateAsync(long partyId, Party party)
        {
            var wrapperObject = PartyWrapper.Load(party);

            var response = await CapsuleClient.makeRequest <PartyWrapper>($"{BASE_ENDPOINT}/{partyId}",
                                                                          "PUT",
                                                                          wrapperObject);

            return(response.Party);
        }
        public async static Task <Party> CreateAsync(Party party)
        {
            var wrapperObject = PartyWrapper.Load(party);

            var response = await CapsuleClient.makeRequest <PartyWrapper>(BASE_ENDPOINT,
                                                                          "POST",
                                                                          wrapperObject);

            return(response.Party);
        }
        public async static Task <Opportunity> ShowAsync(long opportunityId, Embed[] embed = null)
        {
            var endpoint = new StringBuilder($"{BASE_ENDPOINT}/{opportunityId}");

            if (embed != null)
            {
                endpoint.Append($"?embed={String.Join(",", embed)}");
            }

            var apiResponse = await CapsuleClient.makeRequest <OpportunityWrapper>(endpoint.ToString(), "get");

            return(apiResponse.Opportunity);
        }
        public async static Task <CaseWrapper> ListAssociatedCasesAsync(long opportunityId, int page = 1, int perPage = 20, Embed[] embed = null)
        {
            var endpoint = new StringBuilder($"{BASE_ENDPOINT}/{opportunityId}/kases?page={page}&perPage={perPage}");

            if (embed != null)
            {
                endpoint.Append($"?embed={String.Join(",", embed)}");
            }

            var apiResponse = await CapsuleClient.makeRequest <CaseWrapper>(endpoint.ToString(), "GET"); //

            return(apiResponse);
        }
        public async static Task <PartyWrapper> ListAdditionalPartiesAsync(long caseId, int page = 1, int perPage = 20, Embed[] embed = null)
        {
            var endpoint = new StringBuilder($"{BASE_ENDPOINT}/{caseId}/parties?page={page}&perPage={perPage}");

            if (embed != null)
            {
                endpoint.Append($"&embed={String.Join(",", embed)}");
            }

            var parties = await CapsuleClient.makeRequest <PartyWrapper>(endpoint.ToString(), "get");

            return(parties);
        }
        public async static Task <Party> ShowAsync(long partyId, Embed[] embed = null)
        {
            var endpoint = new StringBuilder($"{BASE_ENDPOINT}/{partyId}");

            if (embed != null)
            {
                endpoint.Append($"?embed={String.Join(",", embed)}");
            }

            var party = await CapsuleClient.makeRequest <PartyWrapper>(endpoint.ToString(), "get");

            return(party.Party);
        }
        public async static Task <PartyWrapper> ListEmployeesAsync(long partyId, int page = 1, int perPage = 20, Embed[] embed = null)
        {
            var endpoint = new StringBuilder($"{BASE_ENDPOINT}/{partyId}/people?page={page}&perPage={perPage}");

            if (embed != null)
            {
                endpoint.Append($"?embed={String.Join(",", embed)}");
            }

            var employees = await CapsuleClient.makeRequest <PartyWrapper>(endpoint.ToString(), "GET");

            return(employees);
        }
        public async static Task <Opportunity> UpdateAsync(long opportunityId, Opportunity opportunity)
        {
            // Duration bases cannot be updated
            opportunity.DurationBasis = null;

            var wrapperObject = OpportunityWrapper.Load(opportunity);

            var response = await CapsuleClient.makeRequest <OpportunityWrapper>($"{BASE_ENDPOINT}/{opportunityId}",
                                                                                "PUT",
                                                                                wrapperObject);

            return(response.Opportunity);
        }
        internal async static Task <bool> makeRequest(string endpoint, string method, object body = null)
        {
            var responseMessage = await CapsuleClient.makeApiCall(endpoint : endpoint, method : method, body : body);

            if (responseMessage.StatusCode == System.Net.HttpStatusCode.OK ||
                responseMessage.StatusCode == System.Net.HttpStatusCode.Created ||
                responseMessage.StatusCode == System.Net.HttpStatusCode.NoContent)
            {
                return(true);
            }
            else
            {
                return(false);
            }
        }
        public async static Task <OpportunityWrapper> ShowMultipleAsync(long[] opportunityIds, Embed[] embed = null)
        {
            if (opportunityIds.Length > 10)
            {
                throw new ArgumentException("A max of 10 opportunity id's can be sent at any one time");
            }

            var endpoint = new StringBuilder($"{BASE_ENDPOINT}/{string.Join(",", opportunityIds)}");

            if (embed != null)
            {
                endpoint.Append($"?embed={String.Join(",", embed)}");
            }

            var opportunity = await CapsuleClient.makeRequest <OpportunityWrapper>(endpoint.ToString(), "get");

            return(opportunity);
        }
 static CaseResource()
 {
     CapsuleClient.IsInit();
 }
        public async static Task <OpportunityWrapper> ListAsync(DateTime?since = null, int page = 1, int perPage = 20, Embed[] embed = null)
        {
            var opportunities = await CapsuleClient.baseGetRequest <OpportunityWrapper>(BASE_ENDPOINT, since, page, perPage, embed);

            return(opportunities);
        }
        public async static Task <bool> DeleteAdditionalPartyAsync(long caseId, long partyId)
        {
            var endpoint = new StringBuilder($"{BASE_ENDPOINT}/{caseId}/parties/{partyId}");

            return(await CapsuleClient.makeRequest(endpoint.ToString(), "delete"));;
        }
        public async static Task <bool> DeleteAsync(long opportunityId)
        {
            var response = await CapsuleClient.makeRequest <OpportunityWrapper>($"{BASE_ENDPOINT}/{opportunityId}", "DELETE");

            return(true);
        }
 static OpportunityResource()
 {
     CapsuleClient.IsInit();
 }
        public async static Task <OpportunityWrapper> ListDeletedAsync(DateTime since)
        {
            var deletedOpportunities = await CapsuleClient.makeRequest <OpportunityWrapper>($"{BASE_ENDPOINT}/deleted?since={since.ToString("yyyy/MM/dd")}", "GET");

            return(deletedOpportunities);
        }
 static PartyResource()
 {
     CapsuleClient.IsInit();
 }