mirror of
https://github.com/zoriya/octokit.net.git
synced 2025-12-05 23:06:10 +00:00
Add repository topics support (#2246)
This commit is contained in:
@@ -1,6 +1,8 @@
|
|||||||
using System;
|
using System;
|
||||||
|
using System.Collections.Generic;
|
||||||
using System.Diagnostics.CodeAnalysis;
|
using System.Diagnostics.CodeAnalysis;
|
||||||
using System.Reactive;
|
using System.Reactive;
|
||||||
|
using System.Threading.Tasks;
|
||||||
|
|
||||||
namespace Octokit.Reactive
|
namespace Octokit.Reactive
|
||||||
{
|
{
|
||||||
@@ -556,5 +558,77 @@ namespace Octokit.Reactive
|
|||||||
/// Refer to the API documentation for more information: https://developer.github.com/v3/repos/projects/
|
/// Refer to the API documentation for more information: https://developer.github.com/v3/repos/projects/
|
||||||
/// </remarks>
|
/// </remarks>
|
||||||
IObservableProjectsClient Project { get; }
|
IObservableProjectsClient Project { get; }
|
||||||
|
|
||||||
|
/// <summary>
|
||||||
|
/// Gets all topics for the specified owner and repository name.
|
||||||
|
/// </summary>
|
||||||
|
/// <remarks>
|
||||||
|
/// See the <a href="https://docs.github.com/en/rest/reference/repos#get-all-repository-topics">API documentation</a> for more details
|
||||||
|
/// </remarks>
|
||||||
|
/// <param name="owner">The owner of the repository</param>
|
||||||
|
/// <param name="name">The name of the repository</param>
|
||||||
|
/// <param name="options">Options for changing the API response</param>
|
||||||
|
/// <returns>All topics associated with the repository.</returns>
|
||||||
|
IObservable<RepositoryTopics> GetAllTopics(string owner, string name, ApiOptions options);
|
||||||
|
|
||||||
|
/// <summary>
|
||||||
|
/// Gets all topics for the specified owner and repository name.
|
||||||
|
/// </summary>
|
||||||
|
/// <remarks>
|
||||||
|
/// See the <a href="https://docs.github.com/en/rest/reference/repos#get-all-repository-topics">API documentation</a> for more details
|
||||||
|
/// </remarks>
|
||||||
|
/// <param name="owner">The owner of the repository</param>
|
||||||
|
/// <param name="name">The name of the repository</param>
|
||||||
|
/// <returns>All topics associated with the repository.</returns>
|
||||||
|
IObservable<RepositoryTopics> GetAllTopics(string owner, string name);
|
||||||
|
|
||||||
|
/// <summary>
|
||||||
|
/// Gets all topics for the specified repository ID.
|
||||||
|
/// </summary>
|
||||||
|
/// <remarks>
|
||||||
|
/// See the <a href="https://docs.github.com/en/rest/reference/repos#get-all-repository-topics">API documentation</a> for more details
|
||||||
|
/// </remarks>
|
||||||
|
/// <param name="repositoryId">The ID of the repository</param>
|
||||||
|
/// <param name="options">Options for changing the API response</param>
|
||||||
|
/// <returns>All topics associated with the repository.</returns>
|
||||||
|
IObservable<RepositoryTopics> GetAllTopics(long repositoryId, ApiOptions options);
|
||||||
|
|
||||||
|
/// <summary>
|
||||||
|
/// Gets all topics for the specified repository ID.
|
||||||
|
/// </summary>
|
||||||
|
/// <remarks>
|
||||||
|
/// See the <a href="https://docs.github.com/en/rest/reference/repos#get-all-repository-topics">API documentation</a> for more details
|
||||||
|
/// </remarks>
|
||||||
|
/// <param name="repositoryId">The ID of the repository</param>
|
||||||
|
/// <returns>All topics associated with the repository.</returns>
|
||||||
|
IObservable<RepositoryTopics> GetAllTopics(long repositoryId);
|
||||||
|
|
||||||
|
/// <summary>
|
||||||
|
/// Replaces all topics for the specified repository.
|
||||||
|
/// </summary>
|
||||||
|
/// <remarks>
|
||||||
|
/// See the <a href="https://docs.github.com/en/rest/reference/repos#replace-all-repository-topics">API documentation</a> for more details
|
||||||
|
///
|
||||||
|
/// This is a replacement operation; it is not additive. To clear repository topics, for example, you could specify an empty list of topics here.
|
||||||
|
/// </remarks>
|
||||||
|
/// <param name="repositoryId">The ID of the repository</param>
|
||||||
|
/// <param name="topics">The list of topics to associate with the repository</param>
|
||||||
|
/// <returns>All topics now associated with the repository.</returns>
|
||||||
|
IObservable<RepositoryTopics> ReplaceAllTopics(long repositoryId, RepositoryTopics topics);
|
||||||
|
|
||||||
|
/// <summary>
|
||||||
|
/// Replaces all topics for the specified repository.
|
||||||
|
/// </summary>
|
||||||
|
/// <remarks>
|
||||||
|
/// See the <a href="https://docs.github.com/en/rest/reference/repos#replace-all-repository-topics">API documentation</a> for more details
|
||||||
|
///
|
||||||
|
/// This is a replacement operation; it is not additive. To clear repository topics, for example, you could specify an empty list of topics here.
|
||||||
|
/// </remarks>
|
||||||
|
/// <param name="owner">The owner of the repository</param>
|
||||||
|
/// <param name="name">The name of the repository</param>
|
||||||
|
/// <param name="topics">The list of topics to associate with the repository</param>
|
||||||
|
/// <returns>All topics now associated with the repository.</returns>
|
||||||
|
IObservable<RepositoryTopics> ReplaceAllTopics(string owner, string name, RepositoryTopics topics);
|
||||||
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -1,9 +1,11 @@
|
|||||||
using System;
|
using System;
|
||||||
using System.Collections.Generic;
|
using System.Collections.Generic;
|
||||||
using System.Diagnostics.CodeAnalysis;
|
using System.Diagnostics.CodeAnalysis;
|
||||||
|
using System.Linq;
|
||||||
using System.Reactive;
|
using System.Reactive;
|
||||||
using System.Reactive.Linq;
|
using System.Reactive.Linq;
|
||||||
using System.Reactive.Threading.Tasks;
|
using System.Reactive.Threading.Tasks;
|
||||||
|
using System.Threading.Tasks;
|
||||||
using Octokit.Reactive.Clients;
|
using Octokit.Reactive.Clients;
|
||||||
using Octokit.Reactive.Internal;
|
using Octokit.Reactive.Internal;
|
||||||
|
|
||||||
@@ -821,5 +823,94 @@ namespace Octokit.Reactive
|
|||||||
/// Refer to the API documentation for more information: https://developer.github.com/v3/repos/projects/
|
/// Refer to the API documentation for more information: https://developer.github.com/v3/repos/projects/
|
||||||
/// </remarks>
|
/// </remarks>
|
||||||
public IObservableProjectsClient Project { get; private set; }
|
public IObservableProjectsClient Project { get; private set; }
|
||||||
|
|
||||||
|
/// <summary>
|
||||||
|
/// Gets all topics for the specified owner and repository name.
|
||||||
|
/// </summary>
|
||||||
|
/// <remarks>
|
||||||
|
/// See the <a href="https://docs.github.com/en/rest/reference/repos#get-all-repository-topics">API documentation</a> for more details
|
||||||
|
/// </remarks>
|
||||||
|
/// <param name="owner">The owner of the repository</param>
|
||||||
|
/// <param name="name">The name of the repository</param>
|
||||||
|
/// <param name="options">Options for changing the API response</param>
|
||||||
|
/// <returns>All topics associated with the repository.</returns>
|
||||||
|
public IObservable<RepositoryTopics> GetAllTopics(string owner, string name, ApiOptions options)
|
||||||
|
{
|
||||||
|
return _client.GetAllTopics(owner, name, options).ToObservable();
|
||||||
|
}
|
||||||
|
|
||||||
|
/// <summary>
|
||||||
|
/// Gets all topics for the specified owner and repository name.
|
||||||
|
/// </summary>
|
||||||
|
/// <remarks>
|
||||||
|
/// See the <a href="https://docs.github.com/en/rest/reference/repos#get-all-repository-topics">API documentation</a> for more details
|
||||||
|
/// </remarks>
|
||||||
|
/// <param name="owner">The owner of the repository</param>
|
||||||
|
/// <param name="name">The name of the repository</param>
|
||||||
|
/// <returns>All topics associated with the repository.</returns>
|
||||||
|
public IObservable<RepositoryTopics> GetAllTopics(string owner, string name)
|
||||||
|
{
|
||||||
|
return GetAllTopics(owner, name, ApiOptions.None);
|
||||||
|
}
|
||||||
|
|
||||||
|
/// <summary>
|
||||||
|
/// Gets all topics for the specified repository ID.
|
||||||
|
/// </summary>
|
||||||
|
/// <remarks>
|
||||||
|
/// See the <a href="https://docs.github.com/en/rest/reference/repos#get-all-repository-topics">API documentation</a> for more details
|
||||||
|
/// </remarks>
|
||||||
|
/// <param name="repositoryId">The ID of the repository</param>
|
||||||
|
/// <param name="options">Options for changing the API response</param>
|
||||||
|
/// <returns>All topics associated with the repository.</returns>
|
||||||
|
public IObservable<RepositoryTopics> GetAllTopics(long repositoryId, ApiOptions options)
|
||||||
|
{
|
||||||
|
return _client.GetAllTopics(repositoryId, options).ToObservable();
|
||||||
|
}
|
||||||
|
|
||||||
|
/// <summary>
|
||||||
|
/// Gets all topics for the specified repository ID.
|
||||||
|
/// </summary>
|
||||||
|
/// <remarks>
|
||||||
|
/// See the <a href="https://docs.github.com/en/rest/reference/repos#get-all-repository-topics">API documentation</a> for more details
|
||||||
|
/// </remarks>
|
||||||
|
/// <param name="repositoryId">The ID of the repository</param>
|
||||||
|
/// <returns>All topics associated with the repository.</returns>
|
||||||
|
public IObservable<RepositoryTopics> GetAllTopics(long repositoryId)
|
||||||
|
{
|
||||||
|
return GetAllTopics(repositoryId, ApiOptions.None);
|
||||||
|
}
|
||||||
|
|
||||||
|
/// <summary>
|
||||||
|
/// Replaces all topics for the specified repository.
|
||||||
|
/// </summary>
|
||||||
|
/// <remarks>
|
||||||
|
/// See the <a href="https://docs.github.com/en/rest/reference/repos#replace-all-repository-topics">API documentation</a> for more details
|
||||||
|
///
|
||||||
|
/// This is a replacement operation; it is not additive. To clear repository topics, for example, you could specify an empty list of topics here.
|
||||||
|
/// </remarks>
|
||||||
|
/// <param name="repositoryId">The ID of the repository</param>
|
||||||
|
/// <param name="topics">The list of topics to associate with the repository</param>
|
||||||
|
/// <returns>All topics now associated with the repository.</returns>
|
||||||
|
public IObservable<RepositoryTopics> ReplaceAllTopics(long repositoryId, RepositoryTopics topics)
|
||||||
|
{
|
||||||
|
return _client.ReplaceAllTopics(repositoryId, topics).ToObservable();
|
||||||
|
}
|
||||||
|
|
||||||
|
/// <summary>
|
||||||
|
/// Replaces all topics for the specified repository.
|
||||||
|
/// </summary>
|
||||||
|
/// <remarks>
|
||||||
|
/// See the <a href="https://docs.github.com/en/rest/reference/repos#replace-all-repository-topics">API documentation</a> for more details
|
||||||
|
///
|
||||||
|
/// This is a replacement operation; it is not additive. To clear repository topics, for example, you could specify an empty list of topics here.
|
||||||
|
/// </remarks>
|
||||||
|
/// <param name="owner">The owner of the repository</param>
|
||||||
|
/// <param name="name">The name of the repository</param>
|
||||||
|
/// <param name="topics">The list of topics to associate with the repository</param>
|
||||||
|
/// <returns>All topics now associated with the repository.</returns>
|
||||||
|
public IObservable<RepositoryTopics> ReplaceAllTopics(string owner, string name, RepositoryTopics topics)
|
||||||
|
{
|
||||||
|
return _client.ReplaceAllTopics(owner, name, topics).ToObservable();
|
||||||
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -1452,6 +1452,104 @@ public class RepositoriesClientTests
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
public class TheReplaceAllTopicsMethod : IDisposable
|
||||||
|
{
|
||||||
|
readonly IGitHubClient _github = Helper.GetAuthenticatedClient();
|
||||||
|
private readonly RepositoryTopics _defaultTopics = new RepositoryTopics(new List<string> { "blog", "ruby", "jekyll" });
|
||||||
|
private readonly RepositoryContext _context;
|
||||||
|
private readonly string _theRepository;
|
||||||
|
private readonly string _theRepoOwner;
|
||||||
|
|
||||||
|
public TheReplaceAllTopicsMethod()
|
||||||
|
{
|
||||||
|
_theRepoOwner = Helper.Organization;
|
||||||
|
_theRepository = Helper.MakeNameWithTimestamp("topics");
|
||||||
|
_context = _github.CreateRepositoryContext(_theRepoOwner, new NewRepository(_theRepository)).Result;
|
||||||
|
var defaultTopicAssignmentResult = _github.Repository.ReplaceAllTopics(_context.RepositoryId, _defaultTopics).Result;
|
||||||
|
}
|
||||||
|
|
||||||
|
[IntegrationTest]
|
||||||
|
public async Task ClearsTopicsWithAnEmptyList()
|
||||||
|
{
|
||||||
|
var result = await _github.Repository.ReplaceAllTopics(_theRepoOwner, _theRepository, new RepositoryTopics());
|
||||||
|
Assert.Empty(result.Names);
|
||||||
|
|
||||||
|
var doubleCheck = await _github.Repository.GetAllTopics(_theRepoOwner, _theRepository);
|
||||||
|
Assert.Empty((doubleCheck.Names));
|
||||||
|
}
|
||||||
|
|
||||||
|
[IntegrationTest]
|
||||||
|
public async Task ClearsTopicsWithAnEmptyListWhenUsingRepoId()
|
||||||
|
{
|
||||||
|
var repo = await _github.Repository.Get(_theRepoOwner, _theRepository);
|
||||||
|
var result = await _github.Repository.ReplaceAllTopics(repo.Id, new RepositoryTopics());
|
||||||
|
Assert.Empty(result.Names);
|
||||||
|
|
||||||
|
var doubleCheck = await _github.Repository.GetAllTopics(_theRepoOwner, _theRepository);
|
||||||
|
Assert.Empty((doubleCheck.Names));
|
||||||
|
}
|
||||||
|
|
||||||
|
[IntegrationTest]
|
||||||
|
public async Task ReplacesTopicsWithAList()
|
||||||
|
{
|
||||||
|
var defaultTopicsList = new RepositoryTopics(_defaultTopics.Names);
|
||||||
|
var result = await _github.Repository.ReplaceAllTopics(_theRepoOwner, _theRepository, defaultTopicsList);
|
||||||
|
|
||||||
|
Assert.NotEmpty(result.Names);
|
||||||
|
Assert.Contains(result.Names, item => _defaultTopics.Names.Contains(item, StringComparer.InvariantCultureIgnoreCase));
|
||||||
|
|
||||||
|
var doubleCheck = await _github.Repository.GetAllTopics(_theRepoOwner, _theRepository);
|
||||||
|
Assert.Contains(doubleCheck.Names, item => _defaultTopics.Names.Contains(item, StringComparer.InvariantCultureIgnoreCase));
|
||||||
|
}
|
||||||
|
|
||||||
|
[IntegrationTest]
|
||||||
|
public async Task ReplacesTopicsWithAListWhenUsingRepoId()
|
||||||
|
{
|
||||||
|
var defaultTopicsList = new RepositoryTopics(_defaultTopics.Names);
|
||||||
|
var repo = await _github.Repository.Get(_theRepoOwner, _theRepository);
|
||||||
|
var result = await _github.Repository.ReplaceAllTopics(repo.Id, defaultTopicsList);
|
||||||
|
|
||||||
|
Assert.NotEmpty(result.Names);
|
||||||
|
Assert.Contains(result.Names, item => _defaultTopics.Names.Contains(item, StringComparer.InvariantCultureIgnoreCase));
|
||||||
|
|
||||||
|
var doubleCheck = await _github.Repository.GetAllTopics(_theRepoOwner, _theRepository);
|
||||||
|
Assert.Contains(doubleCheck.Names, item => _defaultTopics.Names.Contains(item, StringComparer.InvariantCultureIgnoreCase));
|
||||||
|
}
|
||||||
|
|
||||||
|
public void Dispose()
|
||||||
|
{
|
||||||
|
_context.Dispose();
|
||||||
|
}
|
||||||
|
}
|
||||||
|
public class TheGetAllTopicsMethod
|
||||||
|
{
|
||||||
|
private readonly string _repoOwner = "SeanKilleen";
|
||||||
|
private readonly string _repoName = "seankilleen.github.io";
|
||||||
|
|
||||||
|
[IntegrationTest]
|
||||||
|
public async Task GetsTopicsByOwnerAndName()
|
||||||
|
{
|
||||||
|
var github = Helper.GetAnonymousClient();
|
||||||
|
var result = await github.Repository.GetAllTopics(_repoOwner, _repoName);
|
||||||
|
|
||||||
|
Assert.Contains("blog", result.Names);
|
||||||
|
Assert.Contains("ruby", result.Names);
|
||||||
|
Assert.Contains("jekyll", result.Names);
|
||||||
|
}
|
||||||
|
|
||||||
|
[IntegrationTest]
|
||||||
|
public async Task GetsTopicsByRepoID()
|
||||||
|
{
|
||||||
|
var github = Helper.GetAnonymousClient();
|
||||||
|
var repo = await github.Repository.Get(_repoOwner, _repoName);
|
||||||
|
var result = await github.Repository.GetAllTopics(repo.Id);
|
||||||
|
|
||||||
|
Assert.Contains("blog", result.Names);
|
||||||
|
Assert.Contains("ruby", result.Names);
|
||||||
|
Assert.Contains("jekyll", result.Names);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
public class TheGetAllTagsMethod
|
public class TheGetAllTagsMethod
|
||||||
{
|
{
|
||||||
[IntegrationTest]
|
[IntegrationTest]
|
||||||
|
|||||||
@@ -24,6 +24,26 @@ public class SearchClientTests
|
|||||||
Assert.NotEmpty(repos.Items);
|
Assert.NotEmpty(repos.Items);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
[IntegrationTest]
|
||||||
|
public async Task SearchForSingleTopic()
|
||||||
|
{
|
||||||
|
var request = new SearchRepositoriesRequest { Topic = "csharp" };
|
||||||
|
|
||||||
|
var repos = await _gitHubClient.Search.SearchRepo(request);
|
||||||
|
|
||||||
|
Assert.NotEmpty(repos.Items);
|
||||||
|
}
|
||||||
|
|
||||||
|
[IntegrationTest]
|
||||||
|
public async Task SearchForMoreThan2Topics()
|
||||||
|
{
|
||||||
|
var request = new SearchRepositoriesRequest { Topics = Octokit.Range.GreaterThanOrEquals(2) };
|
||||||
|
|
||||||
|
var repos = await _gitHubClient.Search.SearchRepo(request);
|
||||||
|
|
||||||
|
Assert.NotEmpty(repos.Items);
|
||||||
|
}
|
||||||
|
|
||||||
[IntegrationTest]
|
[IntegrationTest]
|
||||||
public async Task SearchForCSharpRepositoriesUpdatedIn2020()
|
public async Task SearchForCSharpRepositoriesUpdatedIn2020()
|
||||||
{
|
{
|
||||||
|
|||||||
@@ -1251,5 +1251,116 @@ namespace Octokit.Tests.Clients
|
|||||||
.Get<string>(Arg.Is<Uri>(u => u.ToString() == "repos/owner/name/commits/reference"), null, "application/vnd.github.v3.sha");
|
.Get<string>(Arg.Is<Uri>(u => u.ToString() == "repos/owner/name/commits/reference"), null, "application/vnd.github.v3.sha");
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
public class TheGetAllTopicsMethod
|
||||||
|
{
|
||||||
|
readonly RepositoriesClient _client = new RepositoriesClient(Substitute.For<IApiConnection>());
|
||||||
|
|
||||||
|
[Fact]
|
||||||
|
public async Task EnsuresNonNullArguments()
|
||||||
|
{
|
||||||
|
await Assert.ThrowsAsync<ArgumentNullException>(() => _client.GetAllTopics(123, null));
|
||||||
|
await Assert.ThrowsAsync<ArgumentNullException>(() => _client.GetAllTopics("owner", "repo", null));
|
||||||
|
await Assert.ThrowsAsync<ArgumentNullException>(() => _client.GetAllTopics(null, "repo", ApiOptions.None));
|
||||||
|
await Assert.ThrowsAsync<ArgumentNullException>(() => _client.GetAllTopics("owner", null, ApiOptions.None));
|
||||||
|
}
|
||||||
|
|
||||||
|
[Fact]
|
||||||
|
public async Task EnsuresNonEmptyArguments()
|
||||||
|
{
|
||||||
|
await Assert.ThrowsAsync<ArgumentException>(() => _client.GetAllTopics(string.Empty, "repo", ApiOptions.None));
|
||||||
|
await Assert.ThrowsAsync<ArgumentException>(() => _client.GetAllTopics("owner", string.Empty, ApiOptions.None));
|
||||||
|
}
|
||||||
|
|
||||||
|
[Fact]
|
||||||
|
public void RequestsTheCorrectUrlForOwnerAndRepo()
|
||||||
|
{
|
||||||
|
var connection = Substitute.For<IApiConnection>();
|
||||||
|
var client = new RepositoriesClient(connection);
|
||||||
|
|
||||||
|
client.GetAllTopics("owner", "name");
|
||||||
|
|
||||||
|
connection.Received()
|
||||||
|
.Get<RepositoryTopics>(Arg.Is<Uri>(u => u.ToString() == "repos/owner/name/topics"), null, "application/vnd.github.mercy-preview+json");
|
||||||
|
}
|
||||||
|
|
||||||
|
[Fact]
|
||||||
|
public void RequestsTheCorrectUrlForRepoId()
|
||||||
|
{
|
||||||
|
var connection = Substitute.For<IApiConnection>();
|
||||||
|
var client = new RepositoriesClient(connection);
|
||||||
|
|
||||||
|
client.GetAllTopics(1234);
|
||||||
|
|
||||||
|
connection.Received()
|
||||||
|
.Get<RepositoryTopics>(Arg.Is<Uri>(u => u.ToString() == "repositories/1234/topics"), null, "application/vnd.github.mercy-preview+json");
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
public class TheReplaceAllTopicsMethod
|
||||||
|
{
|
||||||
|
private readonly RepositoryTopics _emptyTopics = new RepositoryTopics();
|
||||||
|
private readonly RepositoryTopics _listOfTopics = new RepositoryTopics(new List<string> { "one", "two", "three" });
|
||||||
|
private readonly IApiConnection _connection;
|
||||||
|
private readonly RepositoriesClient _client;
|
||||||
|
|
||||||
|
public TheReplaceAllTopicsMethod()
|
||||||
|
{
|
||||||
|
_connection = Substitute.For<IApiConnection>();
|
||||||
|
_client = new RepositoriesClient(_connection);
|
||||||
|
}
|
||||||
|
|
||||||
|
[Fact]
|
||||||
|
public async Task EnsuresNonNullArguments()
|
||||||
|
{
|
||||||
|
await Assert.ThrowsAsync<ArgumentNullException>(() => _client.ReplaceAllTopics("owner", "repo", null));
|
||||||
|
await Assert.ThrowsAsync<ArgumentNullException>(() => _client.ReplaceAllTopics(123, null));
|
||||||
|
await Assert.ThrowsAsync<ArgumentNullException>(() => _client.ReplaceAllTopics(null, "repo", _emptyTopics));
|
||||||
|
await Assert.ThrowsAsync<ArgumentNullException>(() => _client.ReplaceAllTopics("owner", null, _emptyTopics));
|
||||||
|
}
|
||||||
|
|
||||||
|
[Fact]
|
||||||
|
public async Task EnsuresNonEmptyArguments()
|
||||||
|
{
|
||||||
|
await Assert.ThrowsAsync<ArgumentException>(() => _client.ReplaceAllTopics(string.Empty, "repo", _emptyTopics));
|
||||||
|
await Assert.ThrowsAsync<ArgumentException>(() => _client.ReplaceAllTopics("owner", string.Empty, _emptyTopics));
|
||||||
|
}
|
||||||
|
|
||||||
|
[Fact]
|
||||||
|
public async Task RequestsTheCorrectUrlForOwnerAndRepoWithEmptyTopics()
|
||||||
|
{
|
||||||
|
await _client.ReplaceAllTopics("owner", "name", _emptyTopics);
|
||||||
|
|
||||||
|
_connection.Received()
|
||||||
|
.Put<RepositoryTopics>(Arg.Is<Uri>(u => u.ToString() == "repos/owner/name/topics"), _emptyTopics, null,"application/vnd.github.mercy-preview+json");
|
||||||
|
}
|
||||||
|
|
||||||
|
[Fact]
|
||||||
|
public async Task RequestsTheCorrectUrlForOwnerAndRepoWithListOfTopics()
|
||||||
|
{
|
||||||
|
await _client.ReplaceAllTopics("owner", "name", _listOfTopics);
|
||||||
|
|
||||||
|
_connection.Received()
|
||||||
|
.Put<RepositoryTopics>(Arg.Is<Uri>(u => u.ToString() == "repos/owner/name/topics"), _listOfTopics,null, "application/vnd.github.mercy-preview+json");
|
||||||
|
}
|
||||||
|
|
||||||
|
[Fact]
|
||||||
|
public async Task RequestsTheCorrectUrlForRepoIdWithEmptyTopics()
|
||||||
|
{
|
||||||
|
await _client.ReplaceAllTopics(1234, _emptyTopics);
|
||||||
|
|
||||||
|
_connection.Received()
|
||||||
|
.Put<RepositoryTopics>(Arg.Is<Uri>(u => u.ToString() == "repositories/1234/topics"), _emptyTopics, null, "application/vnd.github.mercy-preview+json");
|
||||||
|
}
|
||||||
|
|
||||||
|
[Fact]
|
||||||
|
public async Task RequestsTheCorrectUrlForRepoIdWithListOfTopics()
|
||||||
|
{
|
||||||
|
await _client.ReplaceAllTopics(1234,_listOfTopics);
|
||||||
|
|
||||||
|
_connection.Received()
|
||||||
|
.Put<RepositoryTopics>(Arg.Is<Uri>(u => u.ToString() == "repositories/1234/topics"), _listOfTopics,null, "application/vnd.github.mercy-preview+json");
|
||||||
|
}
|
||||||
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -702,6 +702,42 @@ namespace Octokit.Tests.Clients
|
|||||||
Arg.Is<Dictionary<string, string>>(d =>
|
Arg.Is<Dictionary<string, string>>(d =>
|
||||||
string.IsNullOrEmpty(d["q"])));
|
string.IsNullOrEmpty(d["q"])));
|
||||||
}
|
}
|
||||||
|
|
||||||
|
[Fact]
|
||||||
|
public async Task TestingTheTopicQualifier()
|
||||||
|
{
|
||||||
|
var request = new SearchRepositoriesRequest("github");
|
||||||
|
request.Topic = "TheTopic";
|
||||||
|
|
||||||
|
Assert.Contains("topic:thetopic", request.MergedQualifiers());
|
||||||
|
}
|
||||||
|
|
||||||
|
[Fact]
|
||||||
|
public void TestingTheTopicsQualifierWithGreaterThanOneTopic()
|
||||||
|
{
|
||||||
|
var request = new SearchRepositoriesRequest("github");
|
||||||
|
request.Topics = Range.GreaterThan(1);
|
||||||
|
|
||||||
|
Assert.Contains("topics:>1", request.MergedQualifiers());
|
||||||
|
}
|
||||||
|
|
||||||
|
[Fact]
|
||||||
|
public void TestingTheTopicsQualifierWithExactlyOneTopic()
|
||||||
|
{
|
||||||
|
var request = new SearchRepositoriesRequest("github");
|
||||||
|
request.Topics = new Range(1);
|
||||||
|
|
||||||
|
Assert.Contains("topics:1", request.MergedQualifiers());
|
||||||
|
}
|
||||||
|
|
||||||
|
[Fact]
|
||||||
|
public void TestingTheTopicsQualifierWithTwoOrLessTopics()
|
||||||
|
{
|
||||||
|
var request = new SearchRepositoriesRequest("github");
|
||||||
|
request.Topics = Range.LessThanOrEquals(2);
|
||||||
|
|
||||||
|
Assert.Contains("topics:<=2", request.MergedQualifiers());
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
public class TheSearchIssuesMethod
|
public class TheSearchIssuesMethod
|
||||||
|
|||||||
46
Octokit.Tests/Models/RepositoryTopicsTests.cs
Normal file
46
Octokit.Tests/Models/RepositoryTopicsTests.cs
Normal file
@@ -0,0 +1,46 @@
|
|||||||
|
using System.Collections.Generic;
|
||||||
|
using Xunit;
|
||||||
|
|
||||||
|
namespace Octokit.Tests.Models
|
||||||
|
{
|
||||||
|
public class RepositoryTopicsTests
|
||||||
|
{
|
||||||
|
public class Ctor
|
||||||
|
{
|
||||||
|
[Fact]
|
||||||
|
public void EmptyListWhenCtorEmpty()
|
||||||
|
{
|
||||||
|
var result = new RepositoryTopics();
|
||||||
|
Assert.NotNull(result.Names);
|
||||||
|
Assert.Empty(result.Names);
|
||||||
|
}
|
||||||
|
|
||||||
|
[Fact]
|
||||||
|
public void EmptyListWhenCtorListIsEmpty()
|
||||||
|
{
|
||||||
|
var result = new RepositoryTopics(new List<string>());
|
||||||
|
Assert.NotNull(result.Names);
|
||||||
|
Assert.Empty(result.Names);
|
||||||
|
}
|
||||||
|
|
||||||
|
[Fact]
|
||||||
|
public void EmptyListWhenCtorIsNull()
|
||||||
|
{
|
||||||
|
var result = new RepositoryTopics(null);
|
||||||
|
Assert.NotNull(result.Names);
|
||||||
|
Assert.Empty(result.Names);
|
||||||
|
}
|
||||||
|
|
||||||
|
[Fact]
|
||||||
|
public void SetsListWhenListProvided()
|
||||||
|
{
|
||||||
|
var theItems = new List<string> {"one", "two", "three"};
|
||||||
|
var result = new RepositoryTopics(theItems);
|
||||||
|
|
||||||
|
Assert.Contains("one", result.Names);
|
||||||
|
Assert.Contains("two", result.Names);
|
||||||
|
Assert.Contains("three", result.Names);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
@@ -269,6 +269,7 @@ II.2.12 <HandlesEvent />
|
|||||||
<s:Boolean x:Key="/Default/Environment/SettingsMigration/IsMigratorApplied/=JetBrains_002EReSharper_002EPsi_002ECSharp_002ECodeStyle_002ECSharpKeepExistingMigration/@EntryIndexedValue">True</s:Boolean>
|
<s:Boolean x:Key="/Default/Environment/SettingsMigration/IsMigratorApplied/=JetBrains_002EReSharper_002EPsi_002ECSharp_002ECodeStyle_002ECSharpKeepExistingMigration/@EntryIndexedValue">True</s:Boolean>
|
||||||
<s:Boolean x:Key="/Default/Environment/SettingsMigration/IsMigratorApplied/=JetBrains_002EReSharper_002EPsi_002ECSharp_002ECodeStyle_002ECSharpPlaceEmbeddedOnSameLineMigration/@EntryIndexedValue">True</s:Boolean>
|
<s:Boolean x:Key="/Default/Environment/SettingsMigration/IsMigratorApplied/=JetBrains_002EReSharper_002EPsi_002ECSharp_002ECodeStyle_002ECSharpPlaceEmbeddedOnSameLineMigration/@EntryIndexedValue">True</s:Boolean>
|
||||||
<s:Boolean x:Key="/Default/Environment/SettingsMigration/IsMigratorApplied/=JetBrains_002EReSharper_002EPsi_002ECSharp_002ECodeStyle_002ECSharpRenamePlacementToArrangementMigration/@EntryIndexedValue">True</s:Boolean>
|
<s:Boolean x:Key="/Default/Environment/SettingsMigration/IsMigratorApplied/=JetBrains_002EReSharper_002EPsi_002ECSharp_002ECodeStyle_002ECSharpRenamePlacementToArrangementMigration/@EntryIndexedValue">True</s:Boolean>
|
||||||
|
<s:Boolean x:Key="/Default/Environment/SettingsMigration/IsMigratorApplied/=JetBrains_002EReSharper_002EPsi_002ECSharp_002ECodeStyle_002ECSharpUseContinuousIndentInsideBracesMigration/@EntryIndexedValue">True</s:Boolean>
|
||||||
<s:Boolean x:Key="/Default/Environment/SettingsMigration/IsMigratorApplied/=JetBrains_002EReSharper_002EPsi_002ECSharp_002ECodeStyle_002ESettingsUpgrade_002EAddAccessorOwnerDeclarationBracesMigration/@EntryIndexedValue">True</s:Boolean>
|
<s:Boolean x:Key="/Default/Environment/SettingsMigration/IsMigratorApplied/=JetBrains_002EReSharper_002EPsi_002ECSharp_002ECodeStyle_002ESettingsUpgrade_002EAddAccessorOwnerDeclarationBracesMigration/@EntryIndexedValue">True</s:Boolean>
|
||||||
<s:Boolean x:Key="/Default/Environment/SettingsMigration/IsMigratorApplied/=JetBrains_002EReSharper_002EPsi_002ECSharp_002ECodeStyle_002ESettingsUpgrade_002ECSharpPlaceAttributeOnSameLineMigration/@EntryIndexedValue">True</s:Boolean>
|
<s:Boolean x:Key="/Default/Environment/SettingsMigration/IsMigratorApplied/=JetBrains_002EReSharper_002EPsi_002ECSharp_002ECodeStyle_002ESettingsUpgrade_002ECSharpPlaceAttributeOnSameLineMigration/@EntryIndexedValue">True</s:Boolean>
|
||||||
<s:Boolean x:Key="/Default/Environment/SettingsMigration/IsMigratorApplied/=JetBrains_002EReSharper_002EPsi_002ECSharp_002ECodeStyle_002ESettingsUpgrade_002EMigrateBlankLinesAroundFieldToBlankLinesAroundProperty/@EntryIndexedValue">True</s:Boolean>
|
<s:Boolean x:Key="/Default/Environment/SettingsMigration/IsMigratorApplied/=JetBrains_002EReSharper_002EPsi_002ECSharp_002ECodeStyle_002ESettingsUpgrade_002EMigrateBlankLinesAroundFieldToBlankLinesAroundProperty/@EntryIndexedValue">True</s:Boolean>
|
||||||
|
|||||||
@@ -621,5 +621,77 @@ namespace Octokit
|
|||||||
/// Refer to the API documentation for more information: https://developer.github.com/v3/repos/projects/
|
/// Refer to the API documentation for more information: https://developer.github.com/v3/repos/projects/
|
||||||
/// </remarks>
|
/// </remarks>
|
||||||
IProjectsClient Project { get; }
|
IProjectsClient Project { get; }
|
||||||
|
|
||||||
|
/// <summary>
|
||||||
|
/// Gets all topics for the specified owner and repository name.
|
||||||
|
/// </summary>
|
||||||
|
/// <remarks>
|
||||||
|
/// See the <a href="https://docs.github.com/en/rest/reference/repos#get-all-repository-topics">API documentation</a> for more details
|
||||||
|
/// </remarks>
|
||||||
|
/// <param name="owner">The owner of the repository</param>
|
||||||
|
/// <param name="name">The name of the repository</param>
|
||||||
|
/// <param name="options">Options for changing the API response</param>
|
||||||
|
/// <returns>All topics associated with the repository.</returns>
|
||||||
|
Task<RepositoryTopics> GetAllTopics(string owner, string name, ApiOptions options);
|
||||||
|
|
||||||
|
/// <summary>
|
||||||
|
/// Gets all topics for the specified owner and repository name.
|
||||||
|
/// </summary>
|
||||||
|
/// <remarks>
|
||||||
|
/// See the <a href="https://docs.github.com/en/rest/reference/repos#get-all-repository-topics">API documentation</a> for more details
|
||||||
|
/// </remarks>
|
||||||
|
/// <param name="owner">The owner of the repository</param>
|
||||||
|
/// <param name="name">The name of the repository</param>
|
||||||
|
/// <returns>All topics associated with the repository.</returns>
|
||||||
|
Task<RepositoryTopics> GetAllTopics(string owner, string name);
|
||||||
|
|
||||||
|
/// <summary>
|
||||||
|
/// Gets all topics for the specified repository ID.
|
||||||
|
/// </summary>
|
||||||
|
/// <remarks>
|
||||||
|
/// See the <a href="https://docs.github.com/en/rest/reference/repos#get-all-repository-topics">API documentation</a> for more details
|
||||||
|
/// </remarks>
|
||||||
|
/// <param name="repositoryId">The ID of the repository</param>
|
||||||
|
/// <param name="options">Options for changing the API response</param>
|
||||||
|
/// <returns>All topics associated with the repository.</returns>
|
||||||
|
Task<RepositoryTopics> GetAllTopics(long repositoryId, ApiOptions options);
|
||||||
|
|
||||||
|
/// <summary>
|
||||||
|
/// Gets all topics for the specified repository ID.
|
||||||
|
/// </summary>
|
||||||
|
/// <remarks>
|
||||||
|
/// See the <a href="https://docs.github.com/en/rest/reference/repos#get-all-repository-topics">API documentation</a> for more details
|
||||||
|
/// </remarks>
|
||||||
|
/// <param name="repositoryId">The ID of the repository</param>
|
||||||
|
/// <returns>All topics associated with the repository.</returns>
|
||||||
|
Task<RepositoryTopics> GetAllTopics(long repositoryId);
|
||||||
|
|
||||||
|
/// <summary>
|
||||||
|
/// Replaces all topics for the specified repository.
|
||||||
|
/// </summary>
|
||||||
|
/// <remarks>
|
||||||
|
/// See the <a href="https://docs.github.com/en/rest/reference/repos#replace-all-repository-topics">API documentation</a> for more details
|
||||||
|
///
|
||||||
|
/// This is a replacement operation; it is not additive. To clear repository topics, for example, you could specify an empty list of topics here.
|
||||||
|
/// </remarks>
|
||||||
|
/// <param name="repositoryId">The ID of the repository</param>
|
||||||
|
/// <param name="topics">The list of topics to associate with the repository</param>
|
||||||
|
/// <returns>All topics now associated with the repository.</returns>
|
||||||
|
Task<RepositoryTopics> ReplaceAllTopics(long repositoryId, RepositoryTopics topics);
|
||||||
|
|
||||||
|
/// <summary>
|
||||||
|
/// Replaces all topics for the specified repository.
|
||||||
|
/// </summary>
|
||||||
|
/// <remarks>
|
||||||
|
/// See the <a href="https://docs.github.com/en/rest/reference/repos#replace-all-repository-topics">API documentation</a> for more details
|
||||||
|
///
|
||||||
|
/// This is a replacement operation; it is not additive. To clear repository topics, for example, you could specify an empty list of topics here.
|
||||||
|
/// </remarks>
|
||||||
|
/// <param name="owner">The owner of the repository</param>
|
||||||
|
/// <param name="name">The name of the repository</param>
|
||||||
|
/// <param name="topics">The list of topics to associate with the repository</param>
|
||||||
|
/// <returns>All topics now associated with the repository.</returns>
|
||||||
|
Task<RepositoryTopics> ReplaceAllTopics(string owner, string name, RepositoryTopics topics);
|
||||||
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -179,6 +179,7 @@ namespace Octokit
|
|||||||
/// <param name="name">The name of the repository</param>
|
/// <param name="name">The name of the repository</param>
|
||||||
/// <param name="repositoryTransfer">Repository transfer information</param>
|
/// <param name="repositoryTransfer">Repository transfer information</param>
|
||||||
/// <returns>A <see cref="Repository"/></returns>
|
/// <returns>A <see cref="Repository"/></returns>
|
||||||
|
[Preview("mercy")]
|
||||||
[ManualRoute("POST", "/repos/{owner}/{repo}/transfer")]
|
[ManualRoute("POST", "/repos/{owner}/{repo}/transfer")]
|
||||||
public Task<Repository> Transfer(string owner, string name, RepositoryTransfer repositoryTransfer)
|
public Task<Repository> Transfer(string owner, string name, RepositoryTransfer repositoryTransfer)
|
||||||
{
|
{
|
||||||
@@ -198,6 +199,7 @@ namespace Octokit
|
|||||||
/// <param name="repositoryId">The id of the repository</param>
|
/// <param name="repositoryId">The id of the repository</param>
|
||||||
/// <param name="repositoryTransfer">Repository transfer information</param>
|
/// <param name="repositoryTransfer">Repository transfer information</param>
|
||||||
/// <returns>A <see cref="Repository"/></returns>
|
/// <returns>A <see cref="Repository"/></returns>
|
||||||
|
[Preview("mercy")]
|
||||||
[ManualRoute("POST", "/repositories/{id}/transfer")]
|
[ManualRoute("POST", "/repositories/{id}/transfer")]
|
||||||
public Task<Repository> Transfer(long repositoryId, RepositoryTransfer repositoryTransfer)
|
public Task<Repository> Transfer(long repositoryId, RepositoryTransfer repositoryTransfer)
|
||||||
{
|
{
|
||||||
@@ -231,6 +233,7 @@ namespace Octokit
|
|||||||
/// <param name="repositoryId">The Id of the repository</param>
|
/// <param name="repositoryId">The Id of the repository</param>
|
||||||
/// <param name="update">New values to update the repository with</param>
|
/// <param name="update">New values to update the repository with</param>
|
||||||
/// <returns>The updated <see cref="T:Octokit.Repository"/></returns>
|
/// <returns>The updated <see cref="T:Octokit.Repository"/></returns>
|
||||||
|
[Preview("mercy")]
|
||||||
[ManualRoute("PATCH", "/repositories/{id}")]
|
[ManualRoute("PATCH", "/repositories/{id}")]
|
||||||
public Task<Repository> Edit(long repositoryId, RepositoryUpdate update)
|
public Task<Repository> Edit(long repositoryId, RepositoryUpdate update)
|
||||||
{
|
{
|
||||||
@@ -268,6 +271,7 @@ namespace Octokit
|
|||||||
/// <param name="repositoryId">The Id of the repository</param>
|
/// <param name="repositoryId">The Id of the repository</param>
|
||||||
/// <exception cref="ApiException">Thrown when a general API error occurs.</exception>
|
/// <exception cref="ApiException">Thrown when a general API error occurs.</exception>
|
||||||
/// <returns>A <see cref="Repository"/></returns>
|
/// <returns>A <see cref="Repository"/></returns>
|
||||||
|
[Preview("mercy")]
|
||||||
[ManualRoute("GET", "/repositories/{id}")]
|
[ManualRoute("GET", "/repositories/{id}")]
|
||||||
public Task<Repository> Get(long repositoryId)
|
public Task<Repository> Get(long repositoryId)
|
||||||
{
|
{
|
||||||
@@ -727,6 +731,126 @@ namespace Octokit
|
|||||||
return ApiConnection.GetAll<RepositoryContributor>(ApiUrls.RepositoryContributors(repositoryId), parameters, options);
|
return ApiConnection.GetAll<RepositoryContributor>(ApiUrls.RepositoryContributors(repositoryId), parameters, options);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/// <summary>
|
||||||
|
/// Gets all topics for the specified repository ID.
|
||||||
|
/// </summary>
|
||||||
|
/// <remarks>
|
||||||
|
/// See the <a href="https://docs.github.com/en/rest/reference/repos#get-all-repository-topics">API documentation</a> for more details
|
||||||
|
/// </remarks>
|
||||||
|
/// <param name="repositoryId">The ID of the repository</param>
|
||||||
|
/// <param name="options">Options for changing the API response</param>
|
||||||
|
/// <returns>All topics associated with the repository.</returns>
|
||||||
|
[ManualRoute("GET", "/repositories/{id}/topics")]
|
||||||
|
public async Task<RepositoryTopics> GetAllTopics(long repositoryId, ApiOptions options)
|
||||||
|
{
|
||||||
|
Ensure.ArgumentNotNull(options, nameof(options));
|
||||||
|
var endpoint = ApiUrls.RepositoryTopics(repositoryId);
|
||||||
|
var data = await ApiConnection.Get<RepositoryTopics>(endpoint,null,AcceptHeaders.RepositoryTopicsPreview).ConfigureAwait(false);
|
||||||
|
|
||||||
|
return data ?? new RepositoryTopics();
|
||||||
|
}
|
||||||
|
|
||||||
|
/// <summary>
|
||||||
|
/// Gets all topics for the specified repository ID.
|
||||||
|
/// </summary>
|
||||||
|
/// <remarks>
|
||||||
|
/// See the <a href="https://docs.github.com/en/rest/reference/repos#get-all-repository-topics">API documentation</a> for more details
|
||||||
|
/// </remarks>
|
||||||
|
/// <param name="repositoryId">The ID of the repository</param>
|
||||||
|
/// <returns>All topics associated with the repository.</returns>
|
||||||
|
[ManualRoute("GET", "/repositories/{id}/topics")]
|
||||||
|
|
||||||
|
public Task<RepositoryTopics> GetAllTopics(long repositoryId)
|
||||||
|
{
|
||||||
|
return GetAllTopics(repositoryId, ApiOptions.None);
|
||||||
|
}
|
||||||
|
|
||||||
|
/// <summary>
|
||||||
|
/// Gets all topics for the specified owner and repository name.
|
||||||
|
/// </summary>
|
||||||
|
/// <remarks>
|
||||||
|
/// See the <a href="https://docs.github.com/en/rest/reference/repos#get-all-repository-topics">API documentation</a> for more details
|
||||||
|
/// </remarks>
|
||||||
|
/// <param name="owner">The owner of the repository</param>
|
||||||
|
/// <param name="name">The name of the repository</param>
|
||||||
|
/// <param name="options">Options for changing the API response</param>
|
||||||
|
/// <returns>All topics associated with the repository.</returns>
|
||||||
|
[ManualRoute("GET", "/repos/{owner}/{repo}/topics")]
|
||||||
|
public async Task<RepositoryTopics> GetAllTopics(string owner, string name, ApiOptions options)
|
||||||
|
{
|
||||||
|
Ensure.ArgumentNotNullOrEmptyString(owner, nameof(owner));
|
||||||
|
Ensure.ArgumentNotNullOrEmptyString(name, nameof(name));
|
||||||
|
Ensure.ArgumentNotNull(options, nameof(options));
|
||||||
|
|
||||||
|
var endpoint = ApiUrls.RepositoryTopics(owner, name);
|
||||||
|
var data = await ApiConnection.Get<RepositoryTopics>(endpoint, null, AcceptHeaders.RepositoryTopicsPreview).ConfigureAwait(false);
|
||||||
|
|
||||||
|
return data ?? new RepositoryTopics();
|
||||||
|
}
|
||||||
|
|
||||||
|
/// <summary>
|
||||||
|
/// Gets all topics for the specified owner and repository name.
|
||||||
|
/// </summary>
|
||||||
|
/// <remarks>
|
||||||
|
/// See the <a href="https://docs.github.com/en/rest/reference/repos#get-all-repository-topics">API documentation</a> for more details
|
||||||
|
/// </remarks>
|
||||||
|
/// <param name="owner">The owner of the repository</param>
|
||||||
|
/// <param name="name">The name of the repository</param>
|
||||||
|
/// <returns>All topics associated with the repository.</returns>
|
||||||
|
[ManualRoute("GET", "/repos/{owner}/{repo}/topics")]
|
||||||
|
|
||||||
|
public Task<RepositoryTopics> GetAllTopics(string owner, string name)
|
||||||
|
{
|
||||||
|
return GetAllTopics(owner, name, ApiOptions.None);
|
||||||
|
}
|
||||||
|
|
||||||
|
/// <summary>
|
||||||
|
/// Replaces all topics for the specified repository.
|
||||||
|
/// </summary>
|
||||||
|
/// <remarks>
|
||||||
|
/// See the <a href="https://docs.github.com/en/rest/reference/repos#replace-all-repository-topics">API documentation</a> for more details
|
||||||
|
///
|
||||||
|
/// This is a replacement operation; it is not additive. To clear repository topics, for example, you could specify an empty list of topics here.
|
||||||
|
/// </remarks>
|
||||||
|
/// <param name="owner">The owner of the repository</param>
|
||||||
|
/// <param name="name">The name of the repository</param>
|
||||||
|
/// <param name="topics">The list of topics to associate with the repository</param>
|
||||||
|
/// <returns>All topics now associated with the repository.</returns>
|
||||||
|
[ManualRoute("PUT", "/repos/{owner}/{repo}/topics")]
|
||||||
|
public async Task<RepositoryTopics> ReplaceAllTopics(string owner, string name, RepositoryTopics topics)
|
||||||
|
{
|
||||||
|
Ensure.ArgumentNotNullOrEmptyString(owner, nameof(owner));
|
||||||
|
Ensure.ArgumentNotNullOrEmptyString(name, nameof(name));
|
||||||
|
Ensure.ArgumentNotNull(topics, nameof(topics));
|
||||||
|
|
||||||
|
var endpoint = ApiUrls.RepositoryTopics(owner, name);
|
||||||
|
var data = await ApiConnection.Put<RepositoryTopics>(endpoint, topics,null, AcceptHeaders.RepositoryTopicsPreview).ConfigureAwait(false);
|
||||||
|
|
||||||
|
return data ?? new RepositoryTopics();
|
||||||
|
}
|
||||||
|
|
||||||
|
/// <summary>
|
||||||
|
/// Replaces all topics for the specified repository.
|
||||||
|
/// </summary>
|
||||||
|
/// <remarks>
|
||||||
|
/// See the <a href="https://docs.github.com/en/rest/reference/repos#replace-all-repository-topics">API documentation</a> for more details
|
||||||
|
///
|
||||||
|
/// This is a replacement operation; it is not additive. To clear repository topics, for example, you could specify an empty list of topics here.
|
||||||
|
/// </remarks>
|
||||||
|
/// <param name="repositoryId">The ID of the repository</param>
|
||||||
|
/// <param name="topics">The list of topics to associate with the repository</param>
|
||||||
|
/// <returns>All topics now associated with the repository.</returns>
|
||||||
|
[ManualRoute("PUT", "/repositories/{id}/topics")]
|
||||||
|
public async Task<RepositoryTopics> ReplaceAllTopics(long repositoryId, RepositoryTopics topics)
|
||||||
|
{
|
||||||
|
Ensure.ArgumentNotNull(topics, nameof(topics));
|
||||||
|
|
||||||
|
var endpoint = ApiUrls.RepositoryTopics(repositoryId);
|
||||||
|
var data = await ApiConnection.Put<RepositoryTopics>(endpoint, topics, null, AcceptHeaders.RepositoryTopicsPreview).ConfigureAwait(false);
|
||||||
|
|
||||||
|
return data ?? new RepositoryTopics();
|
||||||
|
}
|
||||||
|
|
||||||
/// <summary>
|
/// <summary>
|
||||||
/// Gets all languages for the specified repository.
|
/// Gets all languages for the specified repository.
|
||||||
/// </summary>
|
/// </summary>
|
||||||
|
|||||||
@@ -168,6 +168,7 @@ namespace Octokit
|
|||||||
/// <param name="owner">The owner of the repository</param>
|
/// <param name="owner">The owner of the repository</param>
|
||||||
/// <param name="name">The name of the repository</param>
|
/// <param name="name">The name of the repository</param>
|
||||||
/// <param name="fork">Used to fork a repository</param>
|
/// <param name="fork">Used to fork a repository</param>
|
||||||
|
[Preview("mercy")]
|
||||||
[ManualRoute("POST", "/repos/{owner}/{repo}/forks")]
|
[ManualRoute("POST", "/repos/{owner}/{repo}/forks")]
|
||||||
public Task<Repository> Create(string owner, string name, NewRepositoryFork fork)
|
public Task<Repository> Create(string owner, string name, NewRepositoryFork fork)
|
||||||
{
|
{
|
||||||
@@ -186,6 +187,7 @@ namespace Octokit
|
|||||||
/// </remarks>
|
/// </remarks>
|
||||||
/// <param name="repositoryId">The Id of the repository</param>
|
/// <param name="repositoryId">The Id of the repository</param>
|
||||||
/// <param name="fork">Used to fork a repository</param>
|
/// <param name="fork">Used to fork a repository</param>
|
||||||
|
[Preview("mercy")]
|
||||||
[ManualRoute("POST", "/repositories/{id}/forks")]
|
[ManualRoute("POST", "/repositories/{id}/forks")]
|
||||||
public Task<Repository> Create(long repositoryId, NewRepositoryFork fork)
|
public Task<Repository> Create(long repositoryId, NewRepositoryFork fork)
|
||||||
{
|
{
|
||||||
|
|||||||
@@ -50,6 +50,8 @@ namespace Octokit
|
|||||||
|
|
||||||
public const string OAuthApplicationsPreview = "application/vnd.github.doctor-strange-preview+json";
|
public const string OAuthApplicationsPreview = "application/vnd.github.doctor-strange-preview+json";
|
||||||
|
|
||||||
|
public const string RepositoryTopicsPreview = "application/vnd.github.mercy-preview+json";
|
||||||
|
|
||||||
public const string VisibilityPreview = "application/vnd.github.nebula-preview+json";
|
public const string VisibilityPreview = "application/vnd.github.nebula-preview+json";
|
||||||
|
|
||||||
/// <summary>
|
/// <summary>
|
||||||
|
|||||||
@@ -1902,6 +1902,27 @@ namespace Octokit
|
|||||||
return "repos/{0}/{1}/contributors".FormatUri(owner, name);
|
return "repos/{0}/{1}/contributors".FormatUri(owner, name);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/// <summary>
|
||||||
|
/// Returns the <see cref="Uri"/> for repository topics.
|
||||||
|
/// </summary>
|
||||||
|
/// <param name="owner">The owner of the repository</param>
|
||||||
|
/// <param name="name">The name of the repository</param>
|
||||||
|
/// <returns>the <see cref="Uri"/> for repository topics.</returns>
|
||||||
|
public static Uri RepositoryTopics(string owner, string name)
|
||||||
|
{
|
||||||
|
return "repos/{0}/{1}/topics".FormatUri(owner, name);
|
||||||
|
}
|
||||||
|
|
||||||
|
/// <summary>
|
||||||
|
/// Returns the <see cref="Uri"/> for repository topics.
|
||||||
|
/// </summary>
|
||||||
|
/// <param name="repositoryId">The ID of the repository</param>
|
||||||
|
/// <returns>the <see cref="Uri"/> for repository topics.</returns>
|
||||||
|
public static Uri RepositoryTopics(long repositoryId)
|
||||||
|
{
|
||||||
|
return "repositories/{0}/topics".FormatUri(repositoryId);
|
||||||
|
}
|
||||||
|
|
||||||
/// <summary>
|
/// <summary>
|
||||||
/// Returns the <see cref="Uri"/> for repository languages.
|
/// Returns the <see cref="Uri"/> for repository languages.
|
||||||
/// </summary>
|
/// </summary>
|
||||||
|
|||||||
@@ -123,6 +123,16 @@ namespace Octokit
|
|||||||
/// </summary>
|
/// </summary>
|
||||||
public bool? Archived { get; set; }
|
public bool? Archived { get; set; }
|
||||||
|
|
||||||
|
/// <summary>
|
||||||
|
/// Filters on whether repositories are tagged with the given topic.
|
||||||
|
/// </summary>
|
||||||
|
public string Topic { get; set; }
|
||||||
|
|
||||||
|
/// <summary>
|
||||||
|
/// Filters on the number of topics that a repository is associated with.
|
||||||
|
/// </summary>
|
||||||
|
public Range Topics { get; set; }
|
||||||
|
|
||||||
public override IReadOnlyList<string> MergedQualifiers()
|
public override IReadOnlyList<string> MergedQualifiers()
|
||||||
{
|
{
|
||||||
var parameters = new List<string>();
|
var parameters = new List<string>();
|
||||||
@@ -177,6 +187,15 @@ namespace Octokit
|
|||||||
parameters.Add(string.Format(CultureInfo.InvariantCulture, "archived:{0}", Archived.ToString().ToLower()));
|
parameters.Add(string.Format(CultureInfo.InvariantCulture, "archived:{0}", Archived.ToString().ToLower()));
|
||||||
}
|
}
|
||||||
|
|
||||||
|
if (Topic != null)
|
||||||
|
{
|
||||||
|
parameters.Add(string.Format(CultureInfo.InvariantCulture, "topic:{0}", Topic.ToLower()));
|
||||||
|
}
|
||||||
|
|
||||||
|
if (Topics != null)
|
||||||
|
{
|
||||||
|
parameters.Add(string.Format(CultureInfo.InvariantCulture, "topics:{0}", Topics.ToString().ToLower()));
|
||||||
|
}
|
||||||
if (License != null)
|
if (License != null)
|
||||||
{
|
{
|
||||||
parameters.Add(string.Format(CultureInfo.InvariantCulture, "license:{0}", License.ToParameter()));
|
parameters.Add(string.Format(CultureInfo.InvariantCulture, "license:{0}", License.ToParameter()));
|
||||||
|
|||||||
@@ -1,6 +1,9 @@
|
|||||||
using System;
|
using System;
|
||||||
|
using System.Collections.Generic;
|
||||||
|
using System.Collections.ObjectModel;
|
||||||
using System.Diagnostics;
|
using System.Diagnostics;
|
||||||
using System.Globalization;
|
using System.Globalization;
|
||||||
|
using System.Linq;
|
||||||
|
|
||||||
namespace Octokit
|
namespace Octokit
|
||||||
{
|
{
|
||||||
@@ -14,7 +17,7 @@ namespace Octokit
|
|||||||
Id = id;
|
Id = id;
|
||||||
}
|
}
|
||||||
|
|
||||||
public Repository(string url, string htmlUrl, string cloneUrl, string gitUrl, string sshUrl, string svnUrl, string mirrorUrl, long id, string nodeId, User owner, string name, string fullName, bool isTemplate, string description, string homepage, string language, bool @private, bool fork, int forksCount, int stargazersCount, string defaultBranch, int openIssuesCount, DateTimeOffset? pushedAt, DateTimeOffset createdAt, DateTimeOffset updatedAt, RepositoryPermissions permissions, Repository parent, Repository source, LicenseMetadata license, bool hasIssues, bool hasWiki, bool hasDownloads, bool hasPages, int subscribersCount, long size, bool? allowRebaseMerge, bool? allowSquashMerge, bool? allowMergeCommit, bool archived, int watchersCount, bool? deleteBranchOnMerge, RepositoryVisibility visibility)
|
public Repository(string url, string htmlUrl, string cloneUrl, string gitUrl, string sshUrl, string svnUrl, string mirrorUrl, long id, string nodeId, User owner, string name, string fullName, bool isTemplate, string description, string homepage, string language, bool @private, bool fork, int forksCount, int stargazersCount, string defaultBranch, int openIssuesCount, DateTimeOffset? pushedAt, DateTimeOffset createdAt, DateTimeOffset updatedAt, RepositoryPermissions permissions, Repository parent, Repository source, LicenseMetadata license, bool hasIssues, bool hasWiki, bool hasDownloads, bool hasPages, int subscribersCount, long size, bool? allowRebaseMerge, bool? allowSquashMerge, bool? allowMergeCommit, bool archived, int watchersCount, bool? deleteBranchOnMerge, RepositoryVisibility visibility, IEnumerable<string> topics)
|
||||||
{
|
{
|
||||||
Url = url;
|
Url = url;
|
||||||
HtmlUrl = htmlUrl;
|
HtmlUrl = htmlUrl;
|
||||||
@@ -56,6 +59,7 @@ namespace Octokit
|
|||||||
AllowMergeCommit = allowMergeCommit;
|
AllowMergeCommit = allowMergeCommit;
|
||||||
Archived = archived;
|
Archived = archived;
|
||||||
WatchersCount = watchersCount;
|
WatchersCount = watchersCount;
|
||||||
|
Topics = topics.ToList();
|
||||||
DeleteBranchOnMerge = deleteBranchOnMerge;
|
DeleteBranchOnMerge = deleteBranchOnMerge;
|
||||||
Visibility = visibility;
|
Visibility = visibility;
|
||||||
}
|
}
|
||||||
@@ -144,6 +148,8 @@ namespace Octokit
|
|||||||
|
|
||||||
public bool Archived { get; protected set; }
|
public bool Archived { get; protected set; }
|
||||||
|
|
||||||
|
public IReadOnlyList<string> Topics { get; protected set; }
|
||||||
|
|
||||||
public bool? DeleteBranchOnMerge { get; protected set; }
|
public bool? DeleteBranchOnMerge { get; protected set; }
|
||||||
|
|
||||||
public RepositoryVisibility? Visibility { get; protected set; }
|
public RepositoryVisibility? Visibility { get; protected set; }
|
||||||
|
|||||||
33
Octokit/Models/Response/RepositoryTopics.cs
Normal file
33
Octokit/Models/Response/RepositoryTopics.cs
Normal file
@@ -0,0 +1,33 @@
|
|||||||
|
using System.Collections.Generic;
|
||||||
|
using System.Collections.ObjectModel;
|
||||||
|
using System.Diagnostics;
|
||||||
|
using System.Diagnostics.CodeAnalysis;
|
||||||
|
using System.Globalization;
|
||||||
|
using System.Linq;
|
||||||
|
|
||||||
|
namespace Octokit
|
||||||
|
{
|
||||||
|
[DebuggerDisplay("{DebuggerDisplay,nq}")]
|
||||||
|
public class RepositoryTopics
|
||||||
|
{
|
||||||
|
public RepositoryTopics() { Names = new List<string>(); }
|
||||||
|
|
||||||
|
public RepositoryTopics(IEnumerable<string> names)
|
||||||
|
{
|
||||||
|
var initialItems = names?.ToList() ?? new List<string>();
|
||||||
|
Names = new ReadOnlyCollection<string>(initialItems);
|
||||||
|
}
|
||||||
|
|
||||||
|
public IReadOnlyList<string> Names { get; protected set; }
|
||||||
|
|
||||||
|
[SuppressMessage("Microsoft.Performance", "CA1811:AvoidUncalledPrivateCode")]
|
||||||
|
internal string DebuggerDisplay
|
||||||
|
{
|
||||||
|
get
|
||||||
|
{
|
||||||
|
return string.Format(CultureInfo.InvariantCulture,
|
||||||
|
"RepositoryTopics: Names: {0}", string.Join(", ", Names));
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
Reference in New Issue
Block a user