Jezda.Common.Integrations.GitHub
3.1.1
dotnet add package Jezda.Common.Integrations.GitHub --version 3.1.1
NuGet\Install-Package Jezda.Common.Integrations.GitHub -Version 3.1.1
<PackageReference Include="Jezda.Common.Integrations.GitHub" Version="3.1.1" />
<PackageVersion Include="Jezda.Common.Integrations.GitHub" Version="3.1.1" />
<PackageReference Include="Jezda.Common.Integrations.GitHub" />
paket add Jezda.Common.Integrations.GitHub --version 3.1.1
#r "nuget: Jezda.Common.Integrations.GitHub, 3.1.1"
#:package Jezda.Common.Integrations.GitHub@3.1.1
#addin nuget:?package=Jezda.Common.Integrations.GitHub&version=3.1.1
#tool nuget:?package=Jezda.Common.Integrations.GitHub&version=3.1.1
Jezda.Common.Integrations.GitHub
A strongly-typed .NET client for GitHub REST API, built on top of Jezda.Common.Integrations.
Simplifies access to GitHub repositories and issues.
✨ Features
- Repositories: List repositories for the authenticated user.
- Issues: List issues for a specific repository.
- Authentication: Supports PAT (Personal Access Token) or OAuth tokens via Bearer auth.
- Dependency Injection: Ready-to-use
IServiceCollectionextension.
📦 Installation
Add the project reference or NuGet package:
dotnet add package Jezda.Common.Integrations.GitHub
⚙️ Configuration
Add the following section to your appsettings.json:
{
"Integrations": {
"GitHub": {
"BaseUrl": "https://api.github.com/",
"AccessToken": "your-github-pat",
"UserAgent": "Jezda-Integration-App"
}
}
}
Note: GitHub API requires a valid
User-Agentheader.
🚀 Usage
1. Register Services
In your Program.cs:
using Jezda.Common.Integrations.GitHub.Extensions;
builder.Services.AddGitHubIntegration(builder.Configuration);
2. Inject and Use
Inject IGitHubClient into your service:
public class GitHubService
{
private readonly IGitHubClient _gitHubClient;
public GitHubService(IGitHubClient gitHubClient)
{
_gitHubClient = gitHubClient;
}
public async Task PrintIssuesAsync()
{
// 1. Get my repos
var repos = await _gitHubClient.GetRepositoriesAsync();
foreach(var repo in repos)
{
Console.WriteLine($"Repo: {repo.Name} ({repo.HtmlUrl})");
// 2. Get issues for this repo
var issues = await _gitHubClient.GetIssuesAsync(repo.Owner.Login, repo.Name);
foreach(var issue in issues)
{
Console.WriteLine($" - [{issue.State}] {issue.Title}");
}
}
}
}
Connection validation
ValidateConnectionAsync returns a rejection, InvalidToken, for 401, which is what GitHub answers a bad token with. Every
other failure propagates, including every 403, which can be a lockout after failed logins or an address
block, so none of them is shown to the user as a bad token. A rate limit propagates as 429, see below.
A token with a character outside printable ASCII, such as a pasted smart quote or line break, returns
NotSendable, without a request: it cannot go in a header, and the failure would otherwise read as an outage.
The other calls throw ArgumentException for such a token, also without a request, so it is not
retried and does not count towards the circuit breaker.
IExternalTaskProvider keeps one circuit breaker per token: every caller is on api.github.com, so
one caller whose searches keep timing out does not cut off the others. The breaker key holds a hash
of the token, never the token.
Rate limits
Every GitHubTaskProvider method reports a rate limit as IntegrationRateLimitException, an
HttpRequestException with status 429, even where GitHub answered 403, so it does not read as a rejected
token. Its RetryAt is when GitHub accepts requests again, taken from retry-after, or from
x-ratelimit-reset when no requests remain; it is null when GitHub said neither, and GitHub then asks for
at least a minute.
AddIntegrationResilience retries a 429 only when retry-after asks for at most 5 s. A longer pause, or a
429 without retry-after, reaches the caller at once, instead of a timeout after waiting it out.
Search failures
SearchTasksAsync looks up each repository in its result, at most five at once:
- A rate limit on the search or a lookup fails the search, as described above.
- A lookup answering 404, 451 or any other 403 drops only that repository's issues and logs a warning. If every repository is refused, the result is empty.
- Any other failure, such as 401 or 5xx, fails the search with its status.
| Product | Versions Compatible and additional computed target framework versions. |
|---|---|
| .NET | net10.0 is compatible. net10.0-android was computed. net10.0-browser was computed. net10.0-ios was computed. net10.0-maccatalyst was computed. net10.0-macos was computed. net10.0-tvos was computed. net10.0-windows was computed. |
-
net10.0
- Jezda.Common.Integrations (>= 3.1.1)
- Microsoft.Extensions.DependencyInjection.Abstractions (>= 10.0.14)
- Microsoft.Extensions.Logging.Abstractions (>= 10.0.14)
- Microsoft.Extensions.Options.ConfigurationExtensions (>= 10.0.14)
NuGet packages
This package is not used by any NuGet packages.
GitHub repositories
This package is not used by any popular GitHub repositories.