コード例 #1
0
        private void ValidateAccessTokenInput(TraktDevice device, string clientId, string clientSecret)
        {
            if (device == null)
            {
                throw new ArgumentNullException(nameof(device), "device must not be null");
            }

            if (device.IsExpiredUnused)
            {
                throw new ArgumentException("device code expired unused", nameof(device));
            }

            if (!device.IsValid)
            {
                throw new ArgumentException("device not valid", nameof(device));
            }

            if (device.DeviceCode.ContainsSpace())
            {
                throw new ArgumentException("device code not valid", nameof(device.DeviceCode));
            }

            if (string.IsNullOrEmpty(clientId) || clientId.ContainsSpace())
            {
                throw new ArgumentException("client id not valid", nameof(clientId));
            }

            if (string.IsNullOrEmpty(clientSecret) || clientSecret.ContainsSpace())
            {
                throw new ArgumentException("client secret not valid", nameof(clientSecret));
            }
        }
コード例 #2
0
        /// <summary>
        /// Polls for a new access token. Assigns the returned <see cref="TraktAuthorization" /> instance to <see cref="TraktAuthentication.Authorization" />, if successful.
        /// <para>
        /// See <a href="http://docs.trakt.apiary.io/#reference/authentication-devices/get-token/poll-for-the-access_token">"Trakt API Doc - Devices: Get Token"</a> for more information.
        /// </para>
        /// <para>
        /// See also <seealso cref="PollForAuthorizationAsync()" />,
        /// <seealso cref="PollForAuthorizationAsync(TraktDevice)" /> and
        /// <seealso cref="PollForAuthorizationAsync(TraktDevice, string)" />.
        /// See also <seealso cref="TraktAuthentication.Authorization" />.
        /// </para>
        /// </summary>
        /// <param name="device">The <see cref="TraktDevice" />, which will be used for the request. See also <seealso cref="TraktAuthentication.Device "/>.</param>
        /// <param name="clientId">The Trakt Client ID, which will be used for the request. See also <seealso cref="TraktAuthentication.ClientId" />.</param>
        /// <param name="clientSecret">The Trakt Client Secret, which will be used for the request. See also <seealso cref="TraktAuthentication.ClientSecret" />.</param>
        /// <returns>A new <see cref="TraktAuthorization" /> instance, which contains a new access and refresh token.</returns>
        /// <exception cref="TraktAuthenticationDeviceException">
        /// Thrown, if the given device has an invalid device code.
        /// Thrown, if the user code of the given device was already approved by the user.
        /// Thrown, if the given device code is already expired unused.
        /// Thrown, if the user explicitly denied the user code of the given device.
        /// </exception>
        /// <exception cref="TraktException">Thrown, if the request fails.</exception>
        /// <exception cref="ArgumentException">
        /// Thrown, if the given device is null, or already expired unused or invalid or its user code contains spaces.
        /// Thrown, if the given client id is null, empty or contains spaces.
        /// Thrown, if the given client secret is null, empty or contains spaces.
        /// </exception>
        public async Task <TraktAuthorization> PollForAuthorizationAsync(TraktDevice device, string clientId, string clientSecret)
        {
            ValidateAccessTokenInput(device, clientId, clientSecret);

            var postContent = $"{{ \"code\": \"{device.DeviceCode}\", \"client_id\": \"{clientId}\", \"client_secret\": \"{clientSecret}\" }}";

            var httpClient = TraktConfiguration.HTTP_CLIENT ?? new HttpClient();

            SetDefaultRequestHeaders(httpClient);

            var tokenUrl = $"{Client.Configuration.BaseUrl}{TraktConstants.OAuthDeviceTokenUri}";

            HttpStatusCode responseCode        = default(HttpStatusCode);
            string         responseContent     = string.Empty;
            string         reasonPhrase        = string.Empty;
            int            totalExpiredSeconds = 0;

            while (totalExpiredSeconds < device.ExpiresInSeconds)
            {
                var content  = new StringContent(postContent, Encoding.UTF8, "application/json");
                var response = await httpClient.PostAsync(tokenUrl, content).ConfigureAwait(false);

                responseCode    = response.StatusCode;
                reasonPhrase    = response.ReasonPhrase;
                responseContent = response.Content != null ? await response.Content.ReadAsStringAsync() : string.Empty;

                if (responseCode == HttpStatusCode.OK) // Success
                {
                    var token = default(TraktAuthorization);

                    if (!string.IsNullOrEmpty(responseContent))
                    {
                        token = Json.Deserialize <TraktAuthorization>(responseContent);
                    }

                    Client.Authentication.Authorization = token;
                    return(token);
                }
                else if (responseCode == HttpStatusCode.BadRequest) // Pending
                {
                    await Task.Delay(device.IntervalInSeconds * 1000);

                    totalExpiredSeconds += device.IntervalInSeconds;
                    continue;
                }

                switch (responseCode)
                {
                case HttpStatusCode.NotFound:
                    throw new TraktAuthenticationDeviceException("Not Found - invalid device_code")
                          {
                              StatusCode         = responseCode,
                              RequestUrl         = tokenUrl,
                              RequestBody        = postContent,
                              ServerReasonPhrase = reasonPhrase
                          };

                case HttpStatusCode.Conflict:       // Already Used
                    throw new TraktAuthenticationDeviceException("Already Used - user already approved this code")
                          {
                              StatusCode         = responseCode,
                              RequestUrl         = tokenUrl,
                              RequestBody        = postContent,
                              ServerReasonPhrase = reasonPhrase
                          };

                case HttpStatusCode.Gone:           // Expired
                    throw new TraktAuthenticationDeviceException("Expired - the tokens have expired, restart the process")
                          {
                              StatusCode         = responseCode,
                              RequestUrl         = tokenUrl,
                              RequestBody        = postContent,
                              ServerReasonPhrase = reasonPhrase
                          };

                case (HttpStatusCode)418:           // Denied
                    throw new TraktAuthenticationDeviceException("Denied - user explicitly denied this code")
                          {
                              StatusCode         = (HttpStatusCode)418,
                              RequestUrl         = tokenUrl,
                              RequestBody        = postContent,
                              ServerReasonPhrase = reasonPhrase
                          };

                case (HttpStatusCode)429:           // Slow Down
                    throw new TraktAuthenticationDeviceException("Slow Down - your app is polling too quickly")
                          {
                              StatusCode         = (HttpStatusCode)429,
                              RequestUrl         = tokenUrl,
                              RequestBody        = postContent,
                              ServerReasonPhrase = reasonPhrase
                          };
                }

                await ErrorHandlingAsync(response, tokenUrl, postContent, true);

                break;
            }

            throw new TraktAuthenticationDeviceException("unknown exception")
                  {
                      ServerReasonPhrase = reasonPhrase
                  };
        }
コード例 #3
0
 /// <summary>
 /// Polls for a new access token. Uses the current <see cref="TraktAuthentication.ClientSecret" /> for the request.
 /// Assigns the returned <see cref="TraktAuthorization" /> instance to <see cref="TraktAuthentication.Authorization" />, if successful.
 /// <para>
 /// See <a href="http://docs.trakt.apiary.io/#reference/authentication-devices/get-token/poll-for-the-access_token">"Trakt API Doc - Devices: Get Token"</a> for more information.
 /// </para>
 /// <para>
 /// See also <seealso cref="PollForAuthorizationAsync()" />,
 /// <seealso cref="PollForAuthorizationAsync(TraktDevice)" /> and
 /// <seealso cref="PollForAuthorizationAsync(TraktDevice, string, string)" />.
 /// See also <seealso cref="TraktAuthentication.Authorization" />.
 /// </para>
 /// </summary>
 /// <param name="device">The <see cref="TraktDevice" />, which will be used for the request. See also <seealso cref="TraktAuthentication.Device "/>.</param>
 /// <param name="clientId">The Trakt Client ID, which will be used for the request. See also <seealso cref="TraktAuthentication.ClientId" />.</param>
 /// <returns>A new <see cref="TraktAuthorization" /> instance, which contains a new access and refresh token.</returns>
 /// <exception cref="TraktAuthenticationDeviceException">
 /// Thrown, if the given device has an invalid device code.
 /// Thrown, if the user code of the given device was already approved by the user.
 /// Thrown, if the given device code is already expired unused.
 /// Thrown, if the user explicitly denied the user code of the given device.
 /// </exception>
 /// <exception cref="TraktException">Thrown, if the request fails.</exception>
 /// <exception cref="ArgumentException">
 /// Thrown, if the given device is null, or already expired unused or invalid or its user code contains spaces.
 /// Thrown, if the given client id is null, empty or contains spaces.
 /// Thrown, if the current client secret is null, empty or contains spaces.
 /// </exception>
 public async Task <TraktAuthorization> PollForAuthorizationAsync(TraktDevice device, string clientId)
 => await PollForAuthorizationAsync(device, clientId, Client.ClientSecret);