<?php
/**
 * TokensApi
 * PHP version 7.4
 *
 * @category Class
 * @package  HubSpot\Client\Crm\Timeline
 * @author   OpenAPI Generator team
 * @link     https://openapi-generator.tech
 */

/**
 * Timeline events
 *
 * This feature allows an app to create and configure custom events that can show up in the timelines of certain CRM objects like contacts, companies, tickets, or deals. You'll find multiple use cases for this API in the sections below.
 *
 * The version of the OpenAPI document: v3
 * Generated by: https://openapi-generator.tech
 * OpenAPI Generator version: 6.0.1-SNAPSHOT
 */

/**
 * NOTE: This class is auto generated by OpenAPI Generator (https://openapi-generator.tech).
 * https://openapi-generator.tech
 * Do not edit the class manually.
 */

namespace HubSpot\Client\Crm\Timeline\Api;

use GuzzleHttp\Client;
use GuzzleHttp\ClientInterface;
use GuzzleHttp\Exception\ConnectException;
use GuzzleHttp\Exception\RequestException;
use GuzzleHttp\Psr7\MultipartStream;
use GuzzleHttp\Psr7\Request;
use GuzzleHttp\RequestOptions;
use HubSpot\Client\Crm\Timeline\ApiException;
use HubSpot\Client\Crm\Timeline\Configuration;
use HubSpot\Client\Crm\Timeline\HeaderSelector;
use HubSpot\Client\Crm\Timeline\ObjectSerializer;

/**
 * TokensApi Class Doc Comment
 *
 * @category Class
 * @package  HubSpot\Client\Crm\Timeline
 * @author   OpenAPI Generator team
 * @link     https://openapi-generator.tech
 */
class TokensApi
{
    /**
     * @var ClientInterface
     */
    protected $client;

    /**
     * @var Configuration
     */
    protected $config;

    /**
     * @var HeaderSelector
     */
    protected $headerSelector;

    /**
     * @var int Host index
     */
    protected $hostIndex;

    /**
     * @param ClientInterface $client
     * @param Configuration   $config
     * @param HeaderSelector  $selector
     * @param int             $hostIndex (Optional) host index to select the list of hosts if defined in the OpenAPI spec
     */
    public function __construct(
        ClientInterface $client = null,
        Configuration $config = null,
        HeaderSelector $selector = null,
        $hostIndex = 0
    ) {
        $this->client = $client ?: new Client();
        $this->config = $config ?: new Configuration();
        $this->headerSelector = $selector ?: new HeaderSelector();
        $this->hostIndex = $hostIndex;
    }

    /**
     * Set the host index
     *
     * @param int $hostIndex Host index (required)
     */
    public function setHostIndex($hostIndex): void
    {
        $this->hostIndex = $hostIndex;
    }

    /**
     * Get the host index
     *
     * @return int Host index
     */
    public function getHostIndex()
    {
        return $this->hostIndex;
    }

    /**
     * @return Configuration
     */
    public function getConfig()
    {
        return $this->config;
    }

    /**
     * Operation archive
     *
     * Removes a token from the event template
     *
     * @param  string $event_template_id The event template ID. (required)
     * @param  string $token_name The token name. (required)
     * @param  int $app_id The ID of the target app. (required)
     *
     * @throws \HubSpot\Client\Crm\Timeline\ApiException on non-2xx response
     * @throws \InvalidArgumentException
     * @return void
     */
    public function archive($event_template_id, $token_name, $app_id)
    {
        $this->archiveWithHttpInfo($event_template_id, $token_name, $app_id);
    }

    /**
     * Operation archiveWithHttpInfo
     *
     * Removes a token from the event template
     *
     * @param  string $event_template_id The event template ID. (required)
     * @param  string $token_name The token name. (required)
     * @param  int $app_id The ID of the target app. (required)
     *
     * @throws \HubSpot\Client\Crm\Timeline\ApiException on non-2xx response
     * @throws \InvalidArgumentException
     * @return array of null, HTTP status code, HTTP response headers (array of strings)
     */
    public function archiveWithHttpInfo($event_template_id, $token_name, $app_id)
    {
        $request = $this->archiveRequest($event_template_id, $token_name, $app_id);

        try {
            $options = $this->createHttpClientOption();
            try {
                $response = $this->client->send($request, $options);
            } catch (RequestException $e) {
                throw new ApiException(
                    "[{$e->getCode()}] {$e->getMessage()}",
                    (int) $e->getCode(),
                    $e->getResponse() ? $e->getResponse()->getHeaders() : null,
                    $e->getResponse() ? (string) $e->getResponse()->getBody() : null
                );
            } catch (ConnectException $e) {
                throw new ApiException(
                    "[{$e->getCode()}] {$e->getMessage()}",
                    (int) $e->getCode(),
                    null,
                    null
                );
            }

            $statusCode = $response->getStatusCode();

            if ($statusCode < 200 || $statusCode > 299) {
                throw new ApiException(
                    sprintf(
                        '[%d] Error connecting to the API (%s)',
                        $statusCode,
                        (string) $request->getUri()
                    ),
                    $statusCode,
                    $response->getHeaders(),
                    (string) $response->getBody()
                );
            }

            return [null, $statusCode, $response->getHeaders()];

        } catch (ApiException $e) {
            switch ($e->getCode()) {
                default:
                    $data = ObjectSerializer::deserialize(
                        $e->getResponseBody(),
                        '\HubSpot\Client\Crm\Timeline\Model\Error',
                        $e->getResponseHeaders()
                    );
                    $e->setResponseObject($data);
                    break;
            }
            throw $e;
        }
    }

    /**
     * Operation archiveAsync
     *
     * Removes a token from the event template
     *
     * @param  string $event_template_id The event template ID. (required)
     * @param  string $token_name The token name. (required)
     * @param  int $app_id The ID of the target app. (required)
     *
     * @throws \InvalidArgumentException
     * @return \GuzzleHttp\Promise\PromiseInterface
     */
    public function archiveAsync($event_template_id, $token_name, $app_id)
    {
        return $this->archiveAsyncWithHttpInfo($event_template_id, $token_name, $app_id)
            ->then(
                function ($response) {
                    return $response[0];
                }
            );
    }

    /**
     * Operation archiveAsyncWithHttpInfo
     *
     * Removes a token from the event template
     *
     * @param  string $event_template_id The event template ID. (required)
     * @param  string $token_name The token name. (required)
     * @param  int $app_id The ID of the target app. (required)
     *
     * @throws \InvalidArgumentException
     * @return \GuzzleHttp\Promise\PromiseInterface
     */
    public function archiveAsyncWithHttpInfo($event_template_id, $token_name, $app_id)
    {
        $returnType = '';
        $request = $this->archiveRequest($event_template_id, $token_name, $app_id);

        return $this->client
            ->sendAsync($request, $this->createHttpClientOption())
            ->then(
                function ($response) use ($returnType) {
                    return [null, $response->getStatusCode(), $response->getHeaders()];
                },
                function ($exception) {
                    $response = $exception->getResponse();
                    $statusCode = $response->getStatusCode();
                    throw new ApiException(
                        sprintf(
                            '[%d] Error connecting to the API (%s)',
                            $statusCode,
                            $exception->getRequest()->getUri()
                        ),
                        $statusCode,
                        $response->getHeaders(),
                        (string) $response->getBody()
                    );
                }
            );
    }

    /**
     * Create request for operation 'archive'
     *
     * @param  string $event_template_id The event template ID. (required)
     * @param  string $token_name The token name. (required)
     * @param  int $app_id The ID of the target app. (required)
     *
     * @throws \InvalidArgumentException
     * @return \GuzzleHttp\Psr7\Request
     */
    public function archiveRequest($event_template_id, $token_name, $app_id)
    {
        // verify the required parameter 'event_template_id' is set
        if ($event_template_id === null || (is_array($event_template_id) && count($event_template_id) === 0)) {
            throw new \InvalidArgumentException(
                'Missing the required parameter $event_template_id when calling archive'
            );
        }
        // verify the required parameter 'token_name' is set
        if ($token_name === null || (is_array($token_name) && count($token_name) === 0)) {
            throw new \InvalidArgumentException(
                'Missing the required parameter $token_name when calling archive'
            );
        }
        // verify the required parameter 'app_id' is set
        if ($app_id === null || (is_array($app_id) && count($app_id) === 0)) {
            throw new \InvalidArgumentException(
                'Missing the required parameter $app_id when calling archive'
            );
        }

        $resourcePath = '/crm/v3/timeline/{appId}/event-templates/{eventTemplateId}/tokens/{tokenName}';
        $formParams = [];
        $queryParams = [];
        $headerParams = [];
        $httpBody = '';
        $multipart = false;



        // path params
        if ($event_template_id !== null) {
            $resourcePath = str_replace(
                '{' . 'eventTemplateId' . '}',
                ObjectSerializer::toPathValue($event_template_id),
                $resourcePath
            );
        }
        // path params
        if ($token_name !== null) {
            $resourcePath = str_replace(
                '{' . 'tokenName' . '}',
                ObjectSerializer::toPathValue($token_name),
                $resourcePath
            );
        }
        // path params
        if ($app_id !== null) {
            $resourcePath = str_replace(
                '{' . 'appId' . '}',
                ObjectSerializer::toPathValue($app_id),
                $resourcePath
            );
        }


        if ($multipart) {
            $headers = $this->headerSelector->selectHeadersForMultipart(
                ['*/*']
            );
        } else {
            $headers = $this->headerSelector->selectHeaders(
                ['*/*'],
                []
            );
        }

        // for model (json/xml)
        if (count($formParams) > 0) {
            if ($multipart) {
                $multipartContents = [];
                foreach ($formParams as $formParamName => $formParamValue) {
                    $formParamValueItems = is_array($formParamValue) ? $formParamValue : [$formParamValue];
                    foreach ($formParamValueItems as $formParamValueItem) {
                        $multipartContents[] = [
                            'name' => $formParamName,
                            'contents' => $formParamValueItem
                        ];
                    }
                }
                // for HTTP post (form)
                $httpBody = new MultipartStream($multipartContents);

            } elseif ($headers['Content-Type'] === 'application/json') {
                $httpBody = \GuzzleHttp\json_encode($formParams);

            } else {
                // for HTTP post (form)
                $httpBody = ObjectSerializer::buildQuery($formParams);
            }
        }

        // this endpoint requires API key authentication
        $apiKey = $this->config->getApiKeyWithPrefix('hapikey');
        if ($apiKey !== null) {
            $queryParams['hapikey'] = $apiKey;
        }

        $defaultHeaders = [];
        if ($this->config->getUserAgent()) {
            $defaultHeaders['User-Agent'] = $this->config->getUserAgent();
        }

        $headers = array_merge(
            $defaultHeaders,
            $headerParams,
            $headers
        );

        $query = ObjectSerializer::buildQuery($queryParams);
        return new Request(
            'DELETE',
            $this->config->getHost() . $resourcePath . ($query ? "?{$query}" : ''),
            $headers,
            $httpBody
        );
    }

    /**
     * Operation create
     *
     * Adds a token to an existing event template
     *
     * @param  string $event_template_id The event template ID. (required)
     * @param  int $app_id The ID of the target app. (required)
     * @param  \HubSpot\Client\Crm\Timeline\Model\TimelineEventTemplateToken $timeline_event_template_token The new token definition. (required)
     *
     * @throws \HubSpot\Client\Crm\Timeline\ApiException on non-2xx response
     * @throws \InvalidArgumentException
     * @return \HubSpot\Client\Crm\Timeline\Model\TimelineEventTemplateToken|\HubSpot\Client\Crm\Timeline\Model\Error
     */
    public function create($event_template_id, $app_id, $timeline_event_template_token)
    {
        list($response) = $this->createWithHttpInfo($event_template_id, $app_id, $timeline_event_template_token);
        return $response;
    }

    /**
     * Operation createWithHttpInfo
     *
     * Adds a token to an existing event template
     *
     * @param  string $event_template_id The event template ID. (required)
     * @param  int $app_id The ID of the target app. (required)
     * @param  \HubSpot\Client\Crm\Timeline\Model\TimelineEventTemplateToken $timeline_event_template_token The new token definition. (required)
     *
     * @throws \HubSpot\Client\Crm\Timeline\ApiException on non-2xx response
     * @throws \InvalidArgumentException
     * @return array of \HubSpot\Client\Crm\Timeline\Model\TimelineEventTemplateToken|\HubSpot\Client\Crm\Timeline\Model\Error, HTTP status code, HTTP response headers (array of strings)
     */
    public function createWithHttpInfo($event_template_id, $app_id, $timeline_event_template_token)
    {
        $request = $this->createRequest($event_template_id, $app_id, $timeline_event_template_token);

        try {
            $options = $this->createHttpClientOption();
            try {
                $response = $this->client->send($request, $options);
            } catch (RequestException $e) {
                throw new ApiException(
                    "[{$e->getCode()}] {$e->getMessage()}",
                    (int) $e->getCode(),
                    $e->getResponse() ? $e->getResponse()->getHeaders() : null,
                    $e->getResponse() ? (string) $e->getResponse()->getBody() : null
                );
            } catch (ConnectException $e) {
                throw new ApiException(
                    "[{$e->getCode()}] {$e->getMessage()}",
                    (int) $e->getCode(),
                    null,
                    null
                );
            }

            $statusCode = $response->getStatusCode();

            if ($statusCode < 200 || $statusCode > 299) {
                throw new ApiException(
                    sprintf(
                        '[%d] Error connecting to the API (%s)',
                        $statusCode,
                        (string) $request->getUri()
                    ),
                    $statusCode,
                    $response->getHeaders(),
                    (string) $response->getBody()
                );
            }

            switch($statusCode) {
                case 200:
                    if ('\HubSpot\Client\Crm\Timeline\Model\TimelineEventTemplateToken' === '\SplFileObject') {
                        $content = $response->getBody(); //stream goes to serializer
                    } else {
                        $content = (string) $response->getBody();
                        if ('\HubSpot\Client\Crm\Timeline\Model\TimelineEventTemplateToken' !== 'string') {
                            $content = json_decode($content);
                        }
                    }

                    return [
                        ObjectSerializer::deserialize($content, '\HubSpot\Client\Crm\Timeline\Model\TimelineEventTemplateToken', []),
                        $response->getStatusCode(),
                        $response->getHeaders()
                    ];
                default:
                    if ('\HubSpot\Client\Crm\Timeline\Model\Error' === '\SplFileObject') {
                        $content = $response->getBody(); //stream goes to serializer
                    } else {
                        $content = (string) $response->getBody();
                        if ('\HubSpot\Client\Crm\Timeline\Model\Error' !== 'string') {
                            $content = json_decode($content);
                        }
                    }

                    return [
                        ObjectSerializer::deserialize($content, '\HubSpot\Client\Crm\Timeline\Model\Error', []),
                        $response->getStatusCode(),
                        $response->getHeaders()
                    ];
            }

            $returnType = '\HubSpot\Client\Crm\Timeline\Model\TimelineEventTemplateToken';
            if ($returnType === '\SplFileObject') {
                $content = $response->getBody(); //stream goes to serializer
            } else {
                $content = (string) $response->getBody();
                if ($returnType !== 'string') {
                    $content = json_decode($content);
                }
            }

            return [
                ObjectSerializer::deserialize($content, $returnType, []),
                $response->getStatusCode(),
                $response->getHeaders()
            ];

        } catch (ApiException $e) {
            switch ($e->getCode()) {
                case 200:
                    $data = ObjectSerializer::deserialize(
                        $e->getResponseBody(),
                        '\HubSpot\Client\Crm\Timeline\Model\TimelineEventTemplateToken',
                        $e->getResponseHeaders()
                    );
                    $e->setResponseObject($data);
                    break;
                default:
                    $data = ObjectSerializer::deserialize(
                        $e->getResponseBody(),
                        '\HubSpot\Client\Crm\Timeline\Model\Error',
                        $e->getResponseHeaders()
                    );
                    $e->setResponseObject($data);
                    break;
            }
            throw $e;
        }
    }

    /**
     * Operation createAsync
     *
     * Adds a token to an existing event template
     *
     * @param  string $event_template_id The event template ID. (required)
     * @param  int $app_id The ID of the target app. (required)
     * @param  \HubSpot\Client\Crm\Timeline\Model\TimelineEventTemplateToken $timeline_event_template_token The new token definition. (required)
     *
     * @throws \InvalidArgumentException
     * @return \GuzzleHttp\Promise\PromiseInterface
     */
    public function createAsync($event_template_id, $app_id, $timeline_event_template_token)
    {
        return $this->createAsyncWithHttpInfo($event_template_id, $app_id, $timeline_event_template_token)
            ->then(
                function ($response) {
                    return $response[0];
                }
            );
    }

    /**
     * Operation createAsyncWithHttpInfo
     *
     * Adds a token to an existing event template
     *
     * @param  string $event_template_id The event template ID. (required)
     * @param  int $app_id The ID of the target app. (required)
     * @param  \HubSpot\Client\Crm\Timeline\Model\TimelineEventTemplateToken $timeline_event_template_token The new token definition. (required)
     *
     * @throws \InvalidArgumentException
     * @return \GuzzleHttp\Promise\PromiseInterface
     */
    public function createAsyncWithHttpInfo($event_template_id, $app_id, $timeline_event_template_token)
    {
        $returnType = '\HubSpot\Client\Crm\Timeline\Model\TimelineEventTemplateToken';
        $request = $this->createRequest($event_template_id, $app_id, $timeline_event_template_token);

        return $this->client
            ->sendAsync($request, $this->createHttpClientOption())
            ->then(
                function ($response) use ($returnType) {
                    if ($returnType === '\SplFileObject') {
                        $content = $response->getBody(); //stream goes to serializer
                    } else {
                        $content = (string) $response->getBody();
                        if ($returnType !== 'string') {
                            $content = json_decode($content);
                        }
                    }

                    return [
                        ObjectSerializer::deserialize($content, $returnType, []),
                        $response->getStatusCode(),
                        $response->getHeaders()
                    ];
                },
                function ($exception) {
                    $response = $exception->getResponse();
                    $statusCode = $response->getStatusCode();
                    throw new ApiException(
                        sprintf(
                            '[%d] Error connecting to the API (%s)',
                            $statusCode,
                            $exception->getRequest()->getUri()
                        ),
                        $statusCode,
                        $response->getHeaders(),
                        (string) $response->getBody()
                    );
                }
            );
    }

    /**
     * Create request for operation 'create'
     *
     * @param  string $event_template_id The event template ID. (required)
     * @param  int $app_id The ID of the target app. (required)
     * @param  \HubSpot\Client\Crm\Timeline\Model\TimelineEventTemplateToken $timeline_event_template_token The new token definition. (required)
     *
     * @throws \InvalidArgumentException
     * @return \GuzzleHttp\Psr7\Request
     */
    public function createRequest($event_template_id, $app_id, $timeline_event_template_token)
    {
        // verify the required parameter 'event_template_id' is set
        if ($event_template_id === null || (is_array($event_template_id) && count($event_template_id) === 0)) {
            throw new \InvalidArgumentException(
                'Missing the required parameter $event_template_id when calling create'
            );
        }
        // verify the required parameter 'app_id' is set
        if ($app_id === null || (is_array($app_id) && count($app_id) === 0)) {
            throw new \InvalidArgumentException(
                'Missing the required parameter $app_id when calling create'
            );
        }
        // verify the required parameter 'timeline_event_template_token' is set
        if ($timeline_event_template_token === null || (is_array($timeline_event_template_token) && count($timeline_event_template_token) === 0)) {
            throw new \InvalidArgumentException(
                'Missing the required parameter $timeline_event_template_token when calling create'
            );
        }

        $resourcePath = '/crm/v3/timeline/{appId}/event-templates/{eventTemplateId}/tokens';
        $formParams = [];
        $queryParams = [];
        $headerParams = [];
        $httpBody = '';
        $multipart = false;



        // path params
        if ($event_template_id !== null) {
            $resourcePath = str_replace(
                '{' . 'eventTemplateId' . '}',
                ObjectSerializer::toPathValue($event_template_id),
                $resourcePath
            );
        }
        // path params
        if ($app_id !== null) {
            $resourcePath = str_replace(
                '{' . 'appId' . '}',
                ObjectSerializer::toPathValue($app_id),
                $resourcePath
            );
        }


        if ($multipart) {
            $headers = $this->headerSelector->selectHeadersForMultipart(
                ['application/json', '*/*']
            );
        } else {
            $headers = $this->headerSelector->selectHeaders(
                ['application/json', '*/*'],
                ['application/json']
            );
        }

        // for model (json/xml)
        if (isset($timeline_event_template_token)) {
            if ($headers['Content-Type'] === 'application/json') {
                $httpBody = \GuzzleHttp\json_encode(ObjectSerializer::sanitizeForSerialization($timeline_event_template_token));
            } else {
                $httpBody = $timeline_event_template_token;
            }
        } elseif (count($formParams) > 0) {
            if ($multipart) {
                $multipartContents = [];
                foreach ($formParams as $formParamName => $formParamValue) {
                    $formParamValueItems = is_array($formParamValue) ? $formParamValue : [$formParamValue];
                    foreach ($formParamValueItems as $formParamValueItem) {
                        $multipartContents[] = [
                            'name' => $formParamName,
                            'contents' => $formParamValueItem
                        ];
                    }
                }
                // for HTTP post (form)
                $httpBody = new MultipartStream($multipartContents);

            } elseif ($headers['Content-Type'] === 'application/json') {
                $httpBody = \GuzzleHttp\json_encode($formParams);

            } else {
                // for HTTP post (form)
                $httpBody = ObjectSerializer::buildQuery($formParams);
            }
        }

        // this endpoint requires API key authentication
        $apiKey = $this->config->getApiKeyWithPrefix('hapikey');
        if ($apiKey !== null) {
            $queryParams['hapikey'] = $apiKey;
        }

        $defaultHeaders = [];
        if ($this->config->getUserAgent()) {
            $defaultHeaders['User-Agent'] = $this->config->getUserAgent();
        }

        $headers = array_merge(
            $defaultHeaders,
            $headerParams,
            $headers
        );

        $query = ObjectSerializer::buildQuery($queryParams);
        return new Request(
            'POST',
            $this->config->getHost() . $resourcePath . ($query ? "?{$query}" : ''),
            $headers,
            $httpBody
        );
    }

    /**
     * Operation update
     *
     * Updates an existing token on an event template
     *
     * @param  string $event_template_id The event template ID. (required)
     * @param  string $token_name The token name. (required)
     * @param  int $app_id The ID of the target app. (required)
     * @param  \HubSpot\Client\Crm\Timeline\Model\TimelineEventTemplateTokenUpdateRequest $timeline_event_template_token_update_request The updated token definition. (required)
     *
     * @throws \HubSpot\Client\Crm\Timeline\ApiException on non-2xx response
     * @throws \InvalidArgumentException
     * @return \HubSpot\Client\Crm\Timeline\Model\TimelineEventTemplateToken|\HubSpot\Client\Crm\Timeline\Model\Error
     */
    public function update($event_template_id, $token_name, $app_id, $timeline_event_template_token_update_request)
    {
        list($response) = $this->updateWithHttpInfo($event_template_id, $token_name, $app_id, $timeline_event_template_token_update_request);
        return $response;
    }

    /**
     * Operation updateWithHttpInfo
     *
     * Updates an existing token on an event template
     *
     * @param  string $event_template_id The event template ID. (required)
     * @param  string $token_name The token name. (required)
     * @param  int $app_id The ID of the target app. (required)
     * @param  \HubSpot\Client\Crm\Timeline\Model\TimelineEventTemplateTokenUpdateRequest $timeline_event_template_token_update_request The updated token definition. (required)
     *
     * @throws \HubSpot\Client\Crm\Timeline\ApiException on non-2xx response
     * @throws \InvalidArgumentException
     * @return array of \HubSpot\Client\Crm\Timeline\Model\TimelineEventTemplateToken|\HubSpot\Client\Crm\Timeline\Model\Error, HTTP status code, HTTP response headers (array of strings)
     */
    public function updateWithHttpInfo($event_template_id, $token_name, $app_id, $timeline_event_template_token_update_request)
    {
        $request = $this->updateRequest($event_template_id, $token_name, $app_id, $timeline_event_template_token_update_request);

        try {
            $options = $this->createHttpClientOption();
            try {
                $response = $this->client->send($request, $options);
            } catch (RequestException $e) {
                throw new ApiException(
                    "[{$e->getCode()}] {$e->getMessage()}",
                    (int) $e->getCode(),
                    $e->getResponse() ? $e->getResponse()->getHeaders() : null,
                    $e->getResponse() ? (string) $e->getResponse()->getBody() : null
                );
            } catch (ConnectException $e) {
                throw new ApiException(
                    "[{$e->getCode()}] {$e->getMessage()}",
                    (int) $e->getCode(),
                    null,
                    null
                );
            }

            $statusCode = $response->getStatusCode();

            if ($statusCode < 200 || $statusCode > 299) {
                throw new ApiException(
                    sprintf(
                        '[%d] Error connecting to the API (%s)',
                        $statusCode,
                        (string) $request->getUri()
                    ),
                    $statusCode,
                    $response->getHeaders(),
                    (string) $response->getBody()
                );
            }

            switch($statusCode) {
                case 200:
                    if ('\HubSpot\Client\Crm\Timeline\Model\TimelineEventTemplateToken' === '\SplFileObject') {
                        $content = $response->getBody(); //stream goes to serializer
                    } else {
                        $content = (string) $response->getBody();
                        if ('\HubSpot\Client\Crm\Timeline\Model\TimelineEventTemplateToken' !== 'string') {
                            $content = json_decode($content);
                        }
                    }

                    return [
                        ObjectSerializer::deserialize($content, '\HubSpot\Client\Crm\Timeline\Model\TimelineEventTemplateToken', []),
                        $response->getStatusCode(),
                        $response->getHeaders()
                    ];
                default:
                    if ('\HubSpot\Client\Crm\Timeline\Model\Error' === '\SplFileObject') {
                        $content = $response->getBody(); //stream goes to serializer
                    } else {
                        $content = (string) $response->getBody();
                        if ('\HubSpot\Client\Crm\Timeline\Model\Error' !== 'string') {
                            $content = json_decode($content);
                        }
                    }

                    return [
                        ObjectSerializer::deserialize($content, '\HubSpot\Client\Crm\Timeline\Model\Error', []),
                        $response->getStatusCode(),
                        $response->getHeaders()
                    ];
            }

            $returnType = '\HubSpot\Client\Crm\Timeline\Model\TimelineEventTemplateToken';
            if ($returnType === '\SplFileObject') {
                $content = $response->getBody(); //stream goes to serializer
            } else {
                $content = (string) $response->getBody();
                if ($returnType !== 'string') {
                    $content = json_decode($content);
                }
            }

            return [
                ObjectSerializer::deserialize($content, $returnType, []),
                $response->getStatusCode(),
                $response->getHeaders()
            ];

        } catch (ApiException $e) {
            switch ($e->getCode()) {
                case 200:
                    $data = ObjectSerializer::deserialize(
                        $e->getResponseBody(),
                        '\HubSpot\Client\Crm\Timeline\Model\TimelineEventTemplateToken',
                        $e->getResponseHeaders()
                    );
                    $e->setResponseObject($data);
                    break;
                default:
                    $data = ObjectSerializer::deserialize(
                        $e->getResponseBody(),
                        '\HubSpot\Client\Crm\Timeline\Model\Error',
                        $e->getResponseHeaders()
                    );
                    $e->setResponseObject($data);
                    break;
            }
            throw $e;
        }
    }

    /**
     * Operation updateAsync
     *
     * Updates an existing token on an event template
     *
     * @param  string $event_template_id The event template ID. (required)
     * @param  string $token_name The token name. (required)
     * @param  int $app_id The ID of the target app. (required)
     * @param  \HubSpot\Client\Crm\Timeline\Model\TimelineEventTemplateTokenUpdateRequest $timeline_event_template_token_update_request The updated token definition. (required)
     *
     * @throws \InvalidArgumentException
     * @return \GuzzleHttp\Promise\PromiseInterface
     */
    public function updateAsync($event_template_id, $token_name, $app_id, $timeline_event_template_token_update_request)
    {
        return $this->updateAsyncWithHttpInfo($event_template_id, $token_name, $app_id, $timeline_event_template_token_update_request)
            ->then(
                function ($response) {
                    return $response[0];
                }
            );
    }

    /**
     * Operation updateAsyncWithHttpInfo
     *
     * Updates an existing token on an event template
     *
     * @param  string $event_template_id The event template ID. (required)
     * @param  string $token_name The token name. (required)
     * @param  int $app_id The ID of the target app. (required)
     * @param  \HubSpot\Client\Crm\Timeline\Model\TimelineEventTemplateTokenUpdateRequest $timeline_event_template_token_update_request The updated token definition. (required)
     *
     * @throws \InvalidArgumentException
     * @return \GuzzleHttp\Promise\PromiseInterface
     */
    public function updateAsyncWithHttpInfo($event_template_id, $token_name, $app_id, $timeline_event_template_token_update_request)
    {
        $returnType = '\HubSpot\Client\Crm\Timeline\Model\TimelineEventTemplateToken';
        $request = $this->updateRequest($event_template_id, $token_name, $app_id, $timeline_event_template_token_update_request);

        return $this->client
            ->sendAsync($request, $this->createHttpClientOption())
            ->then(
                function ($response) use ($returnType) {
                    if ($returnType === '\SplFileObject') {
                        $content = $response->getBody(); //stream goes to serializer
                    } else {
                        $content = (string) $response->getBody();
                        if ($returnType !== 'string') {
                            $content = json_decode($content);
                        }
                    }

                    return [
                        ObjectSerializer::deserialize($content, $returnType, []),
                        $response->getStatusCode(),
                        $response->getHeaders()
                    ];
                },
                function ($exception) {
                    $response = $exception->getResponse();
                    $statusCode = $response->getStatusCode();
                    throw new ApiException(
                        sprintf(
                            '[%d] Error connecting to the API (%s)',
                            $statusCode,
                            $exception->getRequest()->getUri()
                        ),
                        $statusCode,
                        $response->getHeaders(),
                        (string) $response->getBody()
                    );
                }
            );
    }

    /**
     * Create request for operation 'update'
     *
     * @param  string $event_template_id The event template ID. (required)
     * @param  string $token_name The token name. (required)
     * @param  int $app_id The ID of the target app. (required)
     * @param  \HubSpot\Client\Crm\Timeline\Model\TimelineEventTemplateTokenUpdateRequest $timeline_event_template_token_update_request The updated token definition. (required)
     *
     * @throws \InvalidArgumentException
     * @return \GuzzleHttp\Psr7\Request
     */
    public function updateRequest($event_template_id, $token_name, $app_id, $timeline_event_template_token_update_request)
    {
        // verify the required parameter 'event_template_id' is set
        if ($event_template_id === null || (is_array($event_template_id) && count($event_template_id) === 0)) {
            throw new \InvalidArgumentException(
                'Missing the required parameter $event_template_id when calling update'
            );
        }
        // verify the required parameter 'token_name' is set
        if ($token_name === null || (is_array($token_name) && count($token_name) === 0)) {
            throw new \InvalidArgumentException(
                'Missing the required parameter $token_name when calling update'
            );
        }
        // verify the required parameter 'app_id' is set
        if ($app_id === null || (is_array($app_id) && count($app_id) === 0)) {
            throw new \InvalidArgumentException(
                'Missing the required parameter $app_id when calling update'
            );
        }
        // verify the required parameter 'timeline_event_template_token_update_request' is set
        if ($timeline_event_template_token_update_request === null || (is_array($timeline_event_template_token_update_request) && count($timeline_event_template_token_update_request) === 0)) {
            throw new \InvalidArgumentException(
                'Missing the required parameter $timeline_event_template_token_update_request when calling update'
            );
        }

        $resourcePath = '/crm/v3/timeline/{appId}/event-templates/{eventTemplateId}/tokens/{tokenName}';
        $formParams = [];
        $queryParams = [];
        $headerParams = [];
        $httpBody = '';
        $multipart = false;



        // path params
        if ($event_template_id !== null) {
            $resourcePath = str_replace(
                '{' . 'eventTemplateId' . '}',
                ObjectSerializer::toPathValue($event_template_id),
                $resourcePath
            );
        }
        // path params
        if ($token_name !== null) {
            $resourcePath = str_replace(
                '{' . 'tokenName' . '}',
                ObjectSerializer::toPathValue($token_name),
                $resourcePath
            );
        }
        // path params
        if ($app_id !== null) {
            $resourcePath = str_replace(
                '{' . 'appId' . '}',
                ObjectSerializer::toPathValue($app_id),
                $resourcePath
            );
        }


        if ($multipart) {
            $headers = $this->headerSelector->selectHeadersForMultipart(
                ['application/json', '*/*']
            );
        } else {
            $headers = $this->headerSelector->selectHeaders(
                ['application/json', '*/*'],
                ['application/json']
            );
        }

        // for model (json/xml)
        if (isset($timeline_event_template_token_update_request)) {
            if ($headers['Content-Type'] === 'application/json') {
                $httpBody = \GuzzleHttp\json_encode(ObjectSerializer::sanitizeForSerialization($timeline_event_template_token_update_request));
            } else {
                $httpBody = $timeline_event_template_token_update_request;
            }
        } elseif (count($formParams) > 0) {
            if ($multipart) {
                $multipartContents = [];
                foreach ($formParams as $formParamName => $formParamValue) {
                    $formParamValueItems = is_array($formParamValue) ? $formParamValue : [$formParamValue];
                    foreach ($formParamValueItems as $formParamValueItem) {
                        $multipartContents[] = [
                            'name' => $formParamName,
                            'contents' => $formParamValueItem
                        ];
                    }
                }
                // for HTTP post (form)
                $httpBody = new MultipartStream($multipartContents);

            } elseif ($headers['Content-Type'] === 'application/json') {
                $httpBody = \GuzzleHttp\json_encode($formParams);

            } else {
                // for HTTP post (form)
                $httpBody = ObjectSerializer::buildQuery($formParams);
            }
        }

        // this endpoint requires API key authentication
        $apiKey = $this->config->getApiKeyWithPrefix('hapikey');
        if ($apiKey !== null) {
            $queryParams['hapikey'] = $apiKey;
        }

        $defaultHeaders = [];
        if ($this->config->getUserAgent()) {
            $defaultHeaders['User-Agent'] = $this->config->getUserAgent();
        }

        $headers = array_merge(
            $defaultHeaders,
            $headerParams,
            $headers
        );

        $query = ObjectSerializer::buildQuery($queryParams);
        return new Request(
            'PUT',
            $this->config->getHost() . $resourcePath . ($query ? "?{$query}" : ''),
            $headers,
            $httpBody
        );
    }

    /**
     * Create http client option
     *
     * @throws \RuntimeException on file opening failure
     * @return array of http client options
     */
    protected function createHttpClientOption()
    {
        $options = [];
        if ($this->config->getDebug()) {
            $options[RequestOptions::DEBUG] = fopen($this->config->getDebugFile(), 'a');
            if (!$options[RequestOptions::DEBUG]) {
                throw new \RuntimeException('Failed to open the debug file: ' . $this->config->getDebugFile());
            }
        }

        return $options;
    }
}
