public bool RevokeAndCheckCanRetry() { lock (this.gitAuthorizationLock) { // Wipe the username and password so we can try recovering if applicable. this.cachedAuthString = null; if (!this.credentialHasBeenRevoked) { GitProcess.RevokeCredential(this.enlistment); this.credentialHasBeenRevoked = true; return(true); } else { this.authRetryBackoff = DateTime.MaxValue; return(false); } } }
private GitEndPointResponseData SendRequest( Uri requestUri, HttpMethod httpMethod, string requestContent, MediaTypeWithQualityHeaderValue acceptType = null) { string authString; if (!this.TryGetCredentials(out authString)) { string message = this.authRetryBackoff == DateTime.MinValue ? "Authorization failed." : "Authorization failed. No retries will be made until: " + this.authRetryBackoff; return(new GitEndPointResponseData( HttpStatusCode.Unauthorized, new HttpGitObjectsException(HttpStatusCode.Unauthorized, message), shouldRetry: false)); } HttpRequestMessage request = new HttpRequestMessage(httpMethod, requestUri); request.Headers.UserAgent.Add(this.userAgentHeader); request.Headers.Authorization = new AuthenticationHeaderValue("Basic", authString); if (acceptType != null) { request.Headers.Accept.Add(acceptType); } if (requestContent != null) { request.Content = new StringContent(requestContent, Encoding.UTF8, "application/json"); } try { HttpResponseMessage response = client.SendAsync(request, HttpCompletionOption.ResponseHeadersRead).Result; if (response.StatusCode == HttpStatusCode.OK) { string contentType = string.Empty; IEnumerable <string> values; if (response.Content.Headers.TryGetValues("Content-Type", out values)) { contentType = values.First(); } this.credentialHasBeenRevoked = false; Stream responseStream = response.Content.ReadAsStreamAsync().Result; return(new GitEndPointResponseData(response.StatusCode, contentType, responseStream)); } else { string errorMessage = response.Content.ReadAsStringAsync().Result; int statusInt = (int)response.StatusCode; if (string.IsNullOrWhiteSpace(errorMessage)) { if (response.StatusCode == HttpStatusCode.Unauthorized) { lock (this.gitAuthorizationLock) { // Wipe the username and password so we can try recovering if applicable. this.gitAuthorization = null; if (!this.credentialHasBeenRevoked) { GitProcess.RevokeCredential(this.enlistment); this.credentialHasBeenRevoked = true; return(new GitEndPointResponseData( response.StatusCode, new HttpGitObjectsException(response.StatusCode, "Server returned error code 401 (Unauthorized). Your PAT may be expired."), shouldRetry: true)); } else { this.authRetryBackoff = DateTime.MaxValue; return(new GitEndPointResponseData( response.StatusCode, new HttpGitObjectsException(response.StatusCode, "Server returned error code 401 (Unauthorized) after successfully renewing your PAT. You may not have access to this repo"), shouldRetry: false)); } } } else { errorMessage = string.Format("Server returned error code {0} ({1})", statusInt, response.StatusCode); } } return(new GitEndPointResponseData(response.StatusCode, new HttpGitObjectsException(response.StatusCode, errorMessage), ShouldRetry(response.StatusCode))); } } catch (TaskCanceledException) { string errorMessage = string.Format("Request to {0} timed out", requestUri); return(new GitEndPointResponseData(HttpStatusCode.RequestTimeout, new HttpGitObjectsException(HttpStatusCode.RequestTimeout, errorMessage), shouldRetry: true)); } catch (WebException ex) { return(new GitEndPointResponseData(HttpStatusCode.InternalServerError, ex, shouldRetry: true)); } }