From 2a1895a4930a3618d3ae231086c690fd7dd331c9 Mon Sep 17 00:00:00 2001 From: Mike Tolly Date: Thu, 25 Jun 2020 14:59:41 -0400 Subject: [PATCH 01/56] created the interface and models for the repository secrets client --- Octokit/Clients/IRepositorySecretsClient.cs | 78 +++++++++++++++++++ Octokit/Models/Response/RepositorySecret.cs | 21 +++++ .../Response/RepositorySecretsPublicKey.cs | 15 ++++ 3 files changed, 114 insertions(+) create mode 100644 Octokit/Clients/IRepositorySecretsClient.cs create mode 100644 Octokit/Models/Response/RepositorySecret.cs create mode 100644 Octokit/Models/Response/RepositorySecretsPublicKey.cs diff --git a/Octokit/Clients/IRepositorySecretsClient.cs b/Octokit/Clients/IRepositorySecretsClient.cs new file mode 100644 index 0000000000..d6819df61f --- /dev/null +++ b/Octokit/Clients/IRepositorySecretsClient.cs @@ -0,0 +1,78 @@ +using System.Collections.Generic; +using System.Threading.Tasks; + +namespace Octokit +{ + /// + /// A client for GitHub's Repository Secrets API. + /// + /// + /// See the Repository Secrets API documentation for more details. + /// + public interface IRepositorySecretsClient + { + /// + /// Get the public signing key to encrypt secrets for a repository. + /// + /// + /// See the API documentation for more information. + /// + /// The owner of the repository + /// The name of the repository + /// Thrown when a general API error occurs. + /// A instance for the repository public key. + Task GetPublicKey(string owner, string repoName); + + /// + /// List the secrets for a repository. + /// + /// + /// See the API documentation for more information. + /// + /// The owner of the repository + /// The name of the repository + /// Thrown when a general API error occurs. + /// A instance for the list of repository secrets. + Task> GetSecretsList(string owner, string repoName); + + /// + /// Get a secret from a repository. + /// + /// + /// See the API documentation for more information. + /// + /// The owner of the repository + /// The name of the repository + /// The name of the secret + /// Thrown when a general API error occurs. + /// A instance for the repository secret. + Task GetSecret(string owner, string repoName, string secretName); + + /// + /// Create or update a secret in a repository. + /// + /// + /// See the API documentation for more information. + /// + /// The owner of the repository + /// The name of the repository + /// The name of the secret + /// The value of the secret + /// Is the secret value already encrypted + /// Thrown when a general API error occurs. + /// A instance for the repository secret that was created or updated. + Task CreateOrUpdateSecret(string owner, string repoName, string secretName, string secretValue, bool valueEncrypted = false); + + /// + /// Delete a secret in a repository. + /// + /// + /// See the API documentation for more information. + /// + /// The owner of the repository + /// The name of the repository + /// The name of the secret + /// Thrown when a general API error occurs. + Task DeleteSecret(string owner, string repoName, string secretName); + } +} diff --git a/Octokit/Models/Response/RepositorySecret.cs b/Octokit/Models/Response/RepositorySecret.cs new file mode 100644 index 0000000000..48292c2c2f --- /dev/null +++ b/Octokit/Models/Response/RepositorySecret.cs @@ -0,0 +1,21 @@ +using Octokit.Internal; +using System; +using System.Collections.Generic; +using System.Text; + +namespace Octokit +{ + /// + /// Represents a repository secret. + /// Does not contain the secret value + /// + public class RepositorySecret + { + [Parameter(Key = "name")] + public string Name { get; set; } + [Parameter(Key = "created_at")] + public DateTime CreatedAt { get; set; } + [Parameter(Key = "updated_at")] + public DateTime UpdatedAt { get; set; } + } +} diff --git a/Octokit/Models/Response/RepositorySecretsPublicKey.cs b/Octokit/Models/Response/RepositorySecretsPublicKey.cs new file mode 100644 index 0000000000..5ab9ef1186 --- /dev/null +++ b/Octokit/Models/Response/RepositorySecretsPublicKey.cs @@ -0,0 +1,15 @@ +using System; +using System.Collections.Generic; +using System.Text; + +namespace Octokit +{ + /// + /// Represents the public key used to sign the secrets to post to GitHub + /// + public class RepositorySecretsPublicKey + { + public int KeyId { get; set; } + public string Key { get; set; } + } +} From 1bbf84678bc47781276571792381f99830c7f661 Mon Sep 17 00:00:00 2001 From: Mike Tolly Date: Thu, 25 Jun 2020 16:06:55 -0400 Subject: [PATCH 02/56] created a repository actions client to sit between repository and secrets for future extensibility --- Octokit/Clients/IRepositoryActionsClient.cs | 23 +++++++++++++++ Octokit/Clients/RepositoryActionsClient.cs | 32 +++++++++++++++++++++ 2 files changed, 55 insertions(+) create mode 100644 Octokit/Clients/IRepositoryActionsClient.cs create mode 100644 Octokit/Clients/RepositoryActionsClient.cs diff --git a/Octokit/Clients/IRepositoryActionsClient.cs b/Octokit/Clients/IRepositoryActionsClient.cs new file mode 100644 index 0000000000..363271389f --- /dev/null +++ b/Octokit/Clients/IRepositoryActionsClient.cs @@ -0,0 +1,23 @@ +using System; +using System.Collections.Generic; +using System.Text; + +namespace Octokit +{ + /// + /// A client for GitHub's Repository Actions API. + /// + /// + /// See the Repository Secrets API documentation for more details. + /// + public interface IRepositoryActionsClient + { + /// + /// Client for GitHub's Repository Secrets API + /// + /// + /// See the Deployments API documentation for more details + /// + IRepositorySecretsClient Secrets { get; set; } + } +} diff --git a/Octokit/Clients/RepositoryActionsClient.cs b/Octokit/Clients/RepositoryActionsClient.cs new file mode 100644 index 0000000000..22f9082e94 --- /dev/null +++ b/Octokit/Clients/RepositoryActionsClient.cs @@ -0,0 +1,32 @@ +using System; +using System.Collections.Generic; +using System.Text; + +namespace Octokit +{ + /// + /// A client for GitHub's Repository Actions API. + /// + /// + /// See the Repository Secrets API documentation for more details. + /// + public class RepositoryActionsClient : ApiClient, IRepositoryActionsClient + { + /// + /// Initializes a new GitHub Repository Branches API client. + /// + /// An API connection + public RepositoryActionsClient(IApiConnection apiConnection) : base(apiConnection) + { + Secrets = new RepositorySecretsClient(apiConnection); + } + + /// + /// Client for GitHub's Repository Secrets API + /// + /// + /// See the Deployments API documentation for more details + /// + public IRepositorySecretsClient Secrets { get; set; } + } +} From 67d5355e676b110e46353e1a6d4a9116bc25cc2b Mon Sep 17 00:00:00 2001 From: Mike Tolly Date: Thu, 25 Jun 2020 16:07:55 -0400 Subject: [PATCH 03/56] created the repository secret client and supporting objects to enable data transfer --- Octokit/Clients/IRepositorySecretsClient.cs | 8 +- Octokit/Clients/RepositorySecretsClient.cs | 138 ++++++++++++++++++ Octokit/Helpers/ApiUrls.cs | 34 +++++ .../Models/Request/UpsertRepositorySecret.cs | 24 +++ .../Response/RepositorySecretsPublicKey.cs | 5 +- 5 files changed, 202 insertions(+), 7 deletions(-) create mode 100644 Octokit/Clients/RepositorySecretsClient.cs create mode 100644 Octokit/Models/Request/UpsertRepositorySecret.cs diff --git a/Octokit/Clients/IRepositorySecretsClient.cs b/Octokit/Clients/IRepositorySecretsClient.cs index d6819df61f..84644b9354 100644 --- a/Octokit/Clients/IRepositorySecretsClient.cs +++ b/Octokit/Clients/IRepositorySecretsClient.cs @@ -33,7 +33,7 @@ public interface IRepositorySecretsClient /// The name of the repository /// Thrown when a general API error occurs. /// A instance for the list of repository secrets. - Task> GetSecretsList(string owner, string repoName); + Task> GetSecretsList(string owner, string repoName); /// /// Get a secret from a repository. @@ -57,11 +57,11 @@ public interface IRepositorySecretsClient /// The owner of the repository /// The name of the repository /// The name of the secret - /// The value of the secret - /// Is the secret value already encrypted + /// The value of the secret. See the API documentation for more information on how to encrypt the secret + /// The id of the encryption key used to encrypt the secret. Get key and id from and use the API documentation for more information on how to encrypt the secret /// Thrown when a general API error occurs. /// A instance for the repository secret that was created or updated. - Task CreateOrUpdateSecret(string owner, string repoName, string secretName, string secretValue, bool valueEncrypted = false); + Task CreateOrUpdateSecret(string owner, string repoName, string secretName, string encryptedSecretValue, string encryptionKeyId); /// /// Delete a secret in a repository. diff --git a/Octokit/Clients/RepositorySecretsClient.cs b/Octokit/Clients/RepositorySecretsClient.cs new file mode 100644 index 0000000000..dc553487e4 --- /dev/null +++ b/Octokit/Clients/RepositorySecretsClient.cs @@ -0,0 +1,138 @@ +using System; +using System.Collections.Generic; +using System.Text; +using System.Threading.Tasks; + +namespace Octokit +{ + public class RepositorySecretsClient : ApiClient, IRepositorySecretsClient + { + /// + /// Initializes a new GitHub Repository Branches API client. + /// + /// An API connection + public RepositorySecretsClient(IApiConnection apiConnection) : base(apiConnection) + { + } + + /// + /// Get the public signing key to encrypt secrets for a repository. + /// + /// + /// See the API documentation for more information. + /// + /// The owner of the repository + /// The name of the repository + /// Thrown when a general API error occurs. + /// A instance for the repository public key. + [ManualRoute("GET", "/repos/{owner}/{repo}/actions/secrets/public-key")] + public Task GetPublicKey(string owner, string repoName) + { + Ensure.ArgumentNotNullOrEmptyString(owner, nameof(owner)); + Ensure.ArgumentNotNullOrEmptyString(repoName, nameof(repoName)); + + var url = ApiUrls.RepositorySecretsPublicKey(owner, repoName); + + return ApiConnection.Get(url); + } + + /// + /// List the secrets for a repository. + /// + /// + /// See the API documentation for more information. + /// + /// The owner of the repository + /// The name of the repository + /// Thrown when a general API error occurs. + /// A instance for the list of repository secrets. + [ManualRoute("GET", "/repos/{owner}/{repo}/actions/secrets")] + public Task> GetSecretsList(string owner, string repoName) + { + Ensure.ArgumentNotNullOrEmptyString(owner, nameof(owner)); + Ensure.ArgumentNotNullOrEmptyString(repoName, nameof(repoName)); + + var url = ApiUrls.RepositorySecretsList(owner, repoName); + + return ApiConnection.GetAll(url); + } + + /// + /// Get a secret from a repository. + /// + /// + /// See the API documentation for more information. + /// + /// The owner of the repository + /// The name of the repository + /// The name of the secret + /// Thrown when a general API error occurs. + /// A instance for the repository secret. + [ManualRoute("GET", "/repos/{owner}/{repo}/actions/secrets/{secretName}")] + public Task GetSecret(string owner, string repoName, string secretName) + { + Ensure.ArgumentNotNullOrEmptyString(owner, nameof(owner)); + Ensure.ArgumentNotNullOrEmptyString(repoName, nameof(repoName)); + Ensure.ArgumentNotNullOrEmptyString(secretName, nameof(secretName)); + + var url = ApiUrls.RepositorySecrets(owner, repoName, secretName); + + return ApiConnection.Get(url); + } + + /// + /// Create or update a secret in a repository. + /// + /// + /// See the API documentation for more information. + /// + /// The owner of the repository + /// The name of the repository + /// The name of the secret + /// The value of the secret. See the API documentation for more information on how to encrypt the secret + /// /// The id of the encryption key used to encrypt the secret. Get key and id from and use the API documentation for more information on how to encrypt the secret + /// Thrown when a general API error occurs. + /// A instance for the repository secret that was created or updated. + [ManualRoute("PUT", "/repos/{owner}/{repo}/actions/secrets/{secretName}")] + public async Task CreateOrUpdateSecret(string owner, string repoName, string secretName, string encryptedSecretValue, string encryptionKeyId) + { + Ensure.ArgumentNotNullOrEmptyString(owner, nameof(owner)); + Ensure.ArgumentNotNullOrEmptyString(repoName, nameof(repoName)); + Ensure.ArgumentNotNullOrEmptyString(secretName, nameof(secretName)); + Ensure.ArgumentNotNullOrEmptyString(encryptedSecretValue, nameof(encryptedSecretValue)); + Ensure.ArgumentNotNullOrEmptyString(encryptionKeyId, nameof(encryptionKeyId)); + + var data = new UpsertRepositorySecret + { + EncryptedValue = encryptedSecretValue, + EncryptionKeyId = encryptionKeyId + }; + + var url = ApiUrls.RepositorySecrets(owner, repoName, secretName); + + return await ApiConnection.Put(url, data); + } + + /// + /// Delete a secret in a repository. + /// + /// + /// See the API documentation for more information. + /// + /// The owner of the repository + /// The name of the repository + /// The name of the secret + /// Thrown when a general API error occurs. + [ManualRoute("DELETE", "/repos/{owner}/{repo}/actions/secrets/{secretName}")] + public Task DeleteSecret(string owner, string repoName, string secretName) + { + Ensure.ArgumentNotNullOrEmptyString(owner, nameof(owner)); + Ensure.ArgumentNotNullOrEmptyString(repoName, nameof(repoName)); + Ensure.ArgumentNotNullOrEmptyString(secretName, nameof(secretName)); + + var url = ApiUrls.RepositorySecrets(owner, repoName, secretName); + + return ApiConnection.Delete(url); + } + } +} diff --git a/Octokit/Helpers/ApiUrls.cs b/Octokit/Helpers/ApiUrls.cs index be3a06c289..ef0cb3b687 100644 --- a/Octokit/Helpers/ApiUrls.cs +++ b/Octokit/Helpers/ApiUrls.cs @@ -4166,6 +4166,40 @@ public static Uri CheckSuitePreferences(string owner, string repo) return "repos/{0}/{1}/check-suites/preferences".FormatUri(owner, repo); } + /// + /// Returns the that handles the repository secrets for the repository + /// + /// The owner of the repo + /// The name of the repo + /// The name of the secret + /// The that handles the repository secrets for the repository + public static Uri RepositorySecrets(string owner, string repo, string secret) + { + return "repos/{0}/{1}/actions/secrets/{2}".FormatUri(owner, repo, secret); + } + + /// + /// Returns the that handles the repository secrets for the repository + /// + /// The owner of the repo + /// The name of the repo + /// The that handles the repository secrets for the repository + public static Uri RepositorySecretsList(string owner, string repo) + { + return "repos/{0}/{1}/actions/secrets".FormatUri(owner, repo); + } + + /// + /// Returns the that handles the repository secrets for the repository + /// + /// The owner of the repo + /// The name of the repo + /// The that handles the repository secrets for the repository + public static Uri RepositorySecretsPublicKey(string owner, string repo) + { + return "repos/{0}/{1}/actions/secrets/public-key".FormatUri(owner, repo); + } + /// /// Returns the that returns all emojis in /// response to a GET request. diff --git a/Octokit/Models/Request/UpsertRepositorySecret.cs b/Octokit/Models/Request/UpsertRepositorySecret.cs new file mode 100644 index 0000000000..d8e2be8407 --- /dev/null +++ b/Octokit/Models/Request/UpsertRepositorySecret.cs @@ -0,0 +1,24 @@ +using Octokit.Internal; +using System.Diagnostics; + +namespace Octokit +{ + /// + /// Used to create or update a repository secret + /// + [DebuggerDisplay("{DebuggerDisplay,nq}")] + public class UpsertRepositorySecret + { + /// + /// The encrypted value of the secret + /// + [Parameter(Value = "encrypted_value")] + public string EncryptedValue { get; set; } + + /// + /// The key_id used to encrypt the secret + /// + [Parameter(Value = "key_id")] + public string EncryptionKeyId { get; set; } + } +} diff --git a/Octokit/Models/Response/RepositorySecretsPublicKey.cs b/Octokit/Models/Response/RepositorySecretsPublicKey.cs index 5ab9ef1186..aa0e7ebdf3 100644 --- a/Octokit/Models/Response/RepositorySecretsPublicKey.cs +++ b/Octokit/Models/Response/RepositorySecretsPublicKey.cs @@ -1,12 +1,11 @@ -using System; -using System.Collections.Generic; -using System.Text; +using System.Diagnostics; namespace Octokit { /// /// Represents the public key used to sign the secrets to post to GitHub /// + [DebuggerDisplay("{DebuggerDisplay,nq}")] public class RepositorySecretsPublicKey { public int KeyId { get; set; } From cff4518ef9eee5add5cf95d8e24599788acc2184 Mon Sep 17 00:00:00 2001 From: Mike Tolly Date: Thu, 25 Jun 2020 19:12:55 -0400 Subject: [PATCH 04/56] created object for create or update secret body and made fixes to pass unit tests --- Octokit/Clients/IRepositorySecretsClient.cs | 24 +++++++--- Octokit/Clients/RepositorySecretsClient.cs | 46 +++++++++++++------ .../Models/Request/UpsertRepositorySecret.cs | 15 +++++- Octokit/Models/Response/RepositorySecret.cs | 43 +++++++++++++++-- .../Response/RepositorySecretsPublicKey.cs | 32 ++++++++++++- 5 files changed, 130 insertions(+), 30 deletions(-) diff --git a/Octokit/Clients/IRepositorySecretsClient.cs b/Octokit/Clients/IRepositorySecretsClient.cs index 84644b9354..6bf54a6086 100644 --- a/Octokit/Clients/IRepositorySecretsClient.cs +++ b/Octokit/Clients/IRepositorySecretsClient.cs @@ -33,7 +33,20 @@ public interface IRepositorySecretsClient /// The name of the repository /// Thrown when a general API error occurs. /// A instance for the list of repository secrets. - Task> GetSecretsList(string owner, string repoName); + Task> GetAll (string owner, string repoName); + + /// + /// List the secrets for a repository. + /// + /// + /// See the API documentation for more information. + /// + /// The owner of the repository + /// The name of the repository + /// Options for changing the API response + /// Thrown when a general API error occurs. + /// A instance for the list of repository secrets. + Task> GetAll(string owner, string repoName, ApiOptions options); /// /// Get a secret from a repository. @@ -46,7 +59,7 @@ public interface IRepositorySecretsClient /// The name of the secret /// Thrown when a general API error occurs. /// A instance for the repository secret. - Task GetSecret(string owner, string repoName, string secretName); + Task Get(string owner, string repoName, string secretName); /// /// Create or update a secret in a repository. @@ -57,11 +70,10 @@ public interface IRepositorySecretsClient /// The owner of the repository /// The name of the repository /// The name of the secret - /// The value of the secret. See the API documentation for more information on how to encrypt the secret - /// The id of the encryption key used to encrypt the secret. Get key and id from and use the API documentation for more information on how to encrypt the secret + /// The encrypted value and id of the encryption key /// Thrown when a general API error occurs. /// A instance for the repository secret that was created or updated. - Task CreateOrUpdateSecret(string owner, string repoName, string secretName, string encryptedSecretValue, string encryptionKeyId); + Task CreateOrUpdate(string owner, string repoName, string secretName, UpsertRepositorySecret upsertSecret); /// /// Delete a secret in a repository. @@ -73,6 +85,6 @@ public interface IRepositorySecretsClient /// The name of the repository /// The name of the secret /// Thrown when a general API error occurs. - Task DeleteSecret(string owner, string repoName, string secretName); + Task Delete(string owner, string repoName, string secretName); } } diff --git a/Octokit/Clients/RepositorySecretsClient.cs b/Octokit/Clients/RepositorySecretsClient.cs index dc553487e4..b54dbae72b 100644 --- a/Octokit/Clients/RepositorySecretsClient.cs +++ b/Octokit/Clients/RepositorySecretsClient.cs @@ -47,7 +47,7 @@ public Task GetPublicKey(string owner, string repoNa /// Thrown when a general API error occurs. /// A instance for the list of repository secrets. [ManualRoute("GET", "/repos/{owner}/{repo}/actions/secrets")] - public Task> GetSecretsList(string owner, string repoName) + public Task> GetAll(string owner, string repoName) { Ensure.ArgumentNotNullOrEmptyString(owner, nameof(owner)); Ensure.ArgumentNotNullOrEmptyString(repoName, nameof(repoName)); @@ -57,6 +57,28 @@ public Task> GetSecretsList(string owner, string return ApiConnection.GetAll(url); } + /// + /// List the secrets for a repository. + /// + /// + /// See the API documentation for more information. + /// + /// The owner of the repository + /// The name of the repository + /// Options for changing the API response + /// Thrown when a general API error occurs. + /// A instance for the list of repository secrets. + public Task> GetAll(string owner, string repoName, ApiOptions options) + { + Ensure.ArgumentNotNullOrEmptyString(owner, nameof(owner)); + Ensure.ArgumentNotNullOrEmptyString(repoName, nameof(repoName)); + Ensure.ArgumentNotNull(options, nameof(options)); + + var url = ApiUrls.RepositorySecretsList(owner, repoName); + + return ApiConnection.GetAll(url, options); + } + /// /// Get a secret from a repository. /// @@ -69,7 +91,7 @@ public Task> GetSecretsList(string owner, string /// Thrown when a general API error occurs. /// A instance for the repository secret. [ManualRoute("GET", "/repos/{owner}/{repo}/actions/secrets/{secretName}")] - public Task GetSecret(string owner, string repoName, string secretName) + public Task Get(string owner, string repoName, string secretName) { Ensure.ArgumentNotNullOrEmptyString(owner, nameof(owner)); Ensure.ArgumentNotNullOrEmptyString(repoName, nameof(repoName)); @@ -89,28 +111,22 @@ public Task GetSecret(string owner, string repoName, string se /// The owner of the repository /// The name of the repository /// The name of the secret - /// The value of the secret. See the API documentation for more information on how to encrypt the secret - /// /// The id of the encryption key used to encrypt the secret. Get key and id from and use the API documentation for more information on how to encrypt the secret + /// The encrypted value and id of the encryption key /// Thrown when a general API error occurs. /// A instance for the repository secret that was created or updated. [ManualRoute("PUT", "/repos/{owner}/{repo}/actions/secrets/{secretName}")] - public async Task CreateOrUpdateSecret(string owner, string repoName, string secretName, string encryptedSecretValue, string encryptionKeyId) + public async Task CreateOrUpdate(string owner, string repoName, string secretName, UpsertRepositorySecret upsertSecret) { Ensure.ArgumentNotNullOrEmptyString(owner, nameof(owner)); Ensure.ArgumentNotNullOrEmptyString(repoName, nameof(repoName)); Ensure.ArgumentNotNullOrEmptyString(secretName, nameof(secretName)); - Ensure.ArgumentNotNullOrEmptyString(encryptedSecretValue, nameof(encryptedSecretValue)); - Ensure.ArgumentNotNullOrEmptyString(encryptionKeyId, nameof(encryptionKeyId)); - - var data = new UpsertRepositorySecret - { - EncryptedValue = encryptedSecretValue, - EncryptionKeyId = encryptionKeyId - }; + Ensure.ArgumentNotNull(upsertSecret, nameof(upsertSecret)); + Ensure.ArgumentNotNullOrEmptyString(upsertSecret.EncryptedValue, nameof(upsertSecret.EncryptedValue)); + Ensure.ArgumentNotNullOrEmptyString(upsertSecret.EncryptionKeyId, nameof(upsertSecret.EncryptionKeyId)); var url = ApiUrls.RepositorySecrets(owner, repoName, secretName); - return await ApiConnection.Put(url, data); + return await ApiConnection.Put(url, upsertSecret); } /// @@ -124,7 +140,7 @@ public async Task CreateOrUpdateSecret(string owner, string re /// The name of the secret /// Thrown when a general API error occurs. [ManualRoute("DELETE", "/repos/{owner}/{repo}/actions/secrets/{secretName}")] - public Task DeleteSecret(string owner, string repoName, string secretName) + public Task Delete(string owner, string repoName, string secretName) { Ensure.ArgumentNotNullOrEmptyString(owner, nameof(owner)); Ensure.ArgumentNotNullOrEmptyString(repoName, nameof(repoName)); diff --git a/Octokit/Models/Request/UpsertRepositorySecret.cs b/Octokit/Models/Request/UpsertRepositorySecret.cs index d8e2be8407..1174395186 100644 --- a/Octokit/Models/Request/UpsertRepositorySecret.cs +++ b/Octokit/Models/Request/UpsertRepositorySecret.cs @@ -1,5 +1,6 @@ using Octokit.Internal; using System.Diagnostics; +using System.Globalization; namespace Octokit { @@ -10,15 +11,25 @@ namespace Octokit public class UpsertRepositorySecret { /// - /// The encrypted value of the secret + /// The encrypted value of the secret. /// + /// See the API documentation for more information on how to encrypt the secret [Parameter(Value = "encrypted_value")] public string EncryptedValue { get; set; } /// - /// The key_id used to encrypt the secret + /// The id of the encryption key used to encrypt the secret. /// + /// Get key and id from and use the API documentation for more information on how to encrypt the secret [Parameter(Value = "key_id")] public string EncryptionKeyId { get; set; } + + internal string DebuggerDisplay + { + get + { + return string.Format(CultureInfo.InvariantCulture, "KeyId: {0}", EncryptionKeyId); + } + } } } diff --git a/Octokit/Models/Response/RepositorySecret.cs b/Octokit/Models/Response/RepositorySecret.cs index 48292c2c2f..73deed285b 100644 --- a/Octokit/Models/Response/RepositorySecret.cs +++ b/Octokit/Models/Response/RepositorySecret.cs @@ -1,7 +1,7 @@ using Octokit.Internal; using System; -using System.Collections.Generic; -using System.Text; +using System.Diagnostics; +using System.Globalization; namespace Octokit { @@ -9,13 +9,46 @@ namespace Octokit /// Represents a repository secret. /// Does not contain the secret value /// + [DebuggerDisplay("{DebuggerDisplay,nq}")] public class RepositorySecret { + public RepositorySecret() + { + + } + + public RepositorySecret(string name, DateTime createdAt, DateTime updatedAt) + { + Name = name; + CreatedAt = createdAt; + UpdatedAt = updatedAt; + } + + /// + /// The name of the repository secret + /// [Parameter(Key = "name")] - public string Name { get; set; } + public string Name { get; protected set; } + + /// + /// The date and time that the secret was created + /// [Parameter(Key = "created_at")] - public DateTime CreatedAt { get; set; } + public DateTime CreatedAt { get; protected set; } + + /// + /// The date and time the secret was last updated + /// [Parameter(Key = "updated_at")] - public DateTime UpdatedAt { get; set; } + public DateTime UpdatedAt { get; protected set; } + + internal string DebuggerDisplay + { + get + { + return string.Format(CultureInfo.InvariantCulture, + "RepositorySecret: Name: {0}", Name); + } + } } } diff --git a/Octokit/Models/Response/RepositorySecretsPublicKey.cs b/Octokit/Models/Response/RepositorySecretsPublicKey.cs index aa0e7ebdf3..66d663ddef 100644 --- a/Octokit/Models/Response/RepositorySecretsPublicKey.cs +++ b/Octokit/Models/Response/RepositorySecretsPublicKey.cs @@ -1,4 +1,5 @@ using System.Diagnostics; +using System.Globalization; namespace Octokit { @@ -8,7 +9,34 @@ namespace Octokit [DebuggerDisplay("{DebuggerDisplay,nq}")] public class RepositorySecretsPublicKey { - public int KeyId { get; set; } - public string Key { get; set; } + public RepositorySecretsPublicKey() + { + + } + + public RepositorySecretsPublicKey(int keyId, string key) + { + KeyId = keyId; + Key = key; + } + + /// + /// The id of this repository public key. Needed to create or update a secret + /// + public int KeyId { get; protected set; } + + /// + /// The public key for this repository + /// + public string Key { get; protected set; } + + internal string DebuggerDisplay + { + get + { + return string.Format(CultureInfo.InvariantCulture, + "RepositorySecretPublicKey: Id: {0}", KeyId); + } + } } } From f69cce67ed44829b1a1962729ea2239f1981b01b Mon Sep 17 00:00:00 2001 From: Mike Tolly Date: Thu, 25 Jun 2020 19:13:14 -0400 Subject: [PATCH 05/56] created repository action unit tests --- .../Clients/RepositoryActionsClientTests.cs | 17 +++++++++++++++++ 1 file changed, 17 insertions(+) create mode 100644 Octokit.Tests/Clients/RepositoryActionsClientTests.cs diff --git a/Octokit.Tests/Clients/RepositoryActionsClientTests.cs b/Octokit.Tests/Clients/RepositoryActionsClientTests.cs new file mode 100644 index 0000000000..99928f232d --- /dev/null +++ b/Octokit.Tests/Clients/RepositoryActionsClientTests.cs @@ -0,0 +1,17 @@ +using System; +using Xunit; + +namespace Octokit.Tests.Clients +{ + public class RepositoryActionsClientTests + { + public class TheCtor + { + [Fact] + public void EnsuresNonNullArguments() + { + Assert.Throws(() => new AssigneesClient(null)); + } + } + } +} From d2a61b2b1afeb31fbd681f67911e9f183df512a6 Mon Sep 17 00:00:00 2001 From: Mike Tolly Date: Thu, 25 Jun 2020 19:38:04 -0400 Subject: [PATCH 06/56] created unit tests for RepositorySecretsClient --- .../Clients/RepositorySecretsClientTests.cs | 177 ++++++++++++++++++ 1 file changed, 177 insertions(+) create mode 100644 Octokit.Tests/Clients/RepositorySecretsClientTests.cs diff --git a/Octokit.Tests/Clients/RepositorySecretsClientTests.cs b/Octokit.Tests/Clients/RepositorySecretsClientTests.cs new file mode 100644 index 0000000000..ec4df9d2da --- /dev/null +++ b/Octokit.Tests/Clients/RepositorySecretsClientTests.cs @@ -0,0 +1,177 @@ +using NSubstitute; +using System; +using System.Threading.Tasks; +using Xunit; + +namespace Octokit.Tests.Clients +{ + public class RepositorySecretsClientTests + { + public class TheCtor + { + [Fact] + public void EnsuresNonNullArguments() + { + Assert.Throws(() => new AssigneesClient(null)); + } + } + + public class GetPublicKeyMethod + { + [Fact] + public async Task RequestsTheCorrectUrl() + { + var connection = Substitute.For(); + var client = new RepositorySecretsClient(connection); + + await client.GetPublicKey("owner", "repo"); + + connection.Received() + .Get(Arg.Is(u => u.ToString() == "repos/owner/repo/actions/secrets/public-key")); + } + + [Fact] + public async Task EnsuresNonNullArguments() + { + var client = new RepositorySecretsClient(Substitute.For()); + + await Assert.ThrowsAsync(() => client.GetPublicKey(null, "repo")); + await Assert.ThrowsAsync(() => client.GetPublicKey("owner", null)); + await Assert.ThrowsAsync(() => client.GetPublicKey("", "repo")); + await Assert.ThrowsAsync(() => client.GetPublicKey("owner", "")); + } + } + + public class GetAllMethod + { + [Fact] + public async Task RequestsTheCorrectUrl() + { + var connection = Substitute.For(); + var client = new RepositorySecretsClient(connection); + + await client.GetAll("owner", "repo"); + + connection.Received() + .GetAll(Arg.Is(u => u.ToString() == "repos/owner/repo/actions/secrets")); + } + + [Fact] + public async Task EnsuresNonNullArguments() + { + var client = new RepositorySecretsClient(Substitute.For()); + + await Assert.ThrowsAsync(() => client.GetAll(null, "repo")); + await Assert.ThrowsAsync(() => client.GetAll("owner", null)); + + await Assert.ThrowsAsync(() => client.GetAll("owner", null, ApiOptions.None)); + await Assert.ThrowsAsync(() => client.GetAll("owner", "repo", null)); + await Assert.ThrowsAsync(() => client.GetAll(null, "repo", ApiOptions.None)); + + await Assert.ThrowsAsync(() => client.GetAll("", "repo")); + await Assert.ThrowsAsync(() => client.GetAll("owner", "")); + + await Assert.ThrowsAsync(() => client.GetAll("owner", "repo", ApiOptions.None)); + } + } + + public class GetMethod + { + [Fact] + public async Task RequestsTheCorrectUrl() + { + var connection = Substitute.For(); + var client = new RepositorySecretsClient(connection); + + await client.Get("owner", "repo", "secret"); + + connection.Received() + .Get(Arg.Is(u => u.ToString() == "repos/owner/repo/actions/secrets/secret")); + } + + [Fact] + public async Task EnsuresNonNullArguments() + { + var client = new RepositorySecretsClient(Substitute.For()); + + await Assert.ThrowsAsync(() => client.Get(null, "repo", "secret")); + await Assert.ThrowsAsync(() => client.Get("owner", null, "secret")); + await Assert.ThrowsAsync(() => client.Get("owner", "repo", null)); + + await Assert.ThrowsAsync(() => client.Get("", "repo", "secret")); + await Assert.ThrowsAsync(() => client.Get("owner", "", "secret")); + await Assert.ThrowsAsync(() => client.Get("owner", "repo", "")); + } + } + + public class CreateOrUpdateMethod + { + [Fact] + public async Task PostsTheCorrectUrl() + { + var connection = Substitute.For(); + var client = new RepositorySecretsClient(connection); + var upsertSecret = new UpsertRepositorySecret + { + EncryptedValue = "encryptedValue", + EncryptionKeyId = "keyId" + }; + await client.CreateOrUpdate("owner", "repo", "secret", upsertSecret); + + connection.Received() + .Put(Arg.Is(u => u.ToString() == "repos/owner/repo/actions/secrets/secret"), upsertSecret); + } + + [Fact] + public async Task EnsuresNonNullArguments() + { + var client = new RepositorySecretsClient(Substitute.For()); + + var upsertSecret = new UpsertRepositorySecret + { + EncryptedValue = "encryptedValue", + EncryptionKeyId = "keyId" + }; + + await Assert.ThrowsAsync(() => client.CreateOrUpdate(null, "repo", "secret", upsertSecret)); + await Assert.ThrowsAsync(() => client.CreateOrUpdate("owner", null, "secret", upsertSecret)); + await Assert.ThrowsAsync(() => client.CreateOrUpdate("owner", "repo", null, upsertSecret)); + await Assert.ThrowsAsync(() => client.CreateOrUpdate("owner", "repo", "secret", null)); + await Assert.ThrowsAsync(() => client.CreateOrUpdate("owner", "repo", "secret", new UpsertRepositorySecret())); + + await Assert.ThrowsAsync(() => client.CreateOrUpdate("", "repo", "secret", upsertSecret)); + await Assert.ThrowsAsync(() => client.CreateOrUpdate("owner", "", "secret", upsertSecret)); + await Assert.ThrowsAsync(() => client.CreateOrUpdate("owner", "repo", "", upsertSecret)); + } + } + + public class DeleteMethod + { + [Fact] + public async Task DeletesTheCorrectUrl() + { + var connection = Substitute.For(); + var client = new RepositorySecretsClient(connection); + + await client.Delete("owner", "repo", "secret"); + + connection.Received() + .Delete(Arg.Is(u => u.ToString() == "repos/owner/repo/actions/secrets/secret")); + } + + [Fact] + public async Task EnsuresNonNullArguments() + { + var client = new RepositorySecretsClient(Substitute.For()); + + await Assert.ThrowsAsync(() => client.Delete(null, "repo", "secret")); + await Assert.ThrowsAsync(() => client.Delete("owner", null, "secret")); + await Assert.ThrowsAsync(() => client.Delete("owner", "repo", null)); + + await Assert.ThrowsAsync(() => client.Delete("", "repo", "secret")); + await Assert.ThrowsAsync(() => client.Delete("owner", "", "secret")); + await Assert.ThrowsAsync(() => client.Delete("owner", "repo", "")); + } + } + } +} From 84a8fb8e15668038fc45c181d6d2dd6d641f5e02 Mon Sep 17 00:00:00 2001 From: Mike Tolly Date: Thu, 25 Jun 2020 19:43:57 -0400 Subject: [PATCH 07/56] removed set from secrets interface --- Octokit/Clients/IRepositoryActionsClient.cs | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/Octokit/Clients/IRepositoryActionsClient.cs b/Octokit/Clients/IRepositoryActionsClient.cs index 363271389f..0cd39d7c14 100644 --- a/Octokit/Clients/IRepositoryActionsClient.cs +++ b/Octokit/Clients/IRepositoryActionsClient.cs @@ -18,6 +18,6 @@ public interface IRepositoryActionsClient /// /// See the Deployments API documentation for more details /// - IRepositorySecretsClient Secrets { get; set; } + IRepositorySecretsClient Secrets { get; } } } From 3778bd6c76fb6407665de55c690075a4cca2f177 Mon Sep 17 00:00:00 2001 From: Mike Tolly Date: Thu, 25 Jun 2020 20:26:12 -0400 Subject: [PATCH 08/56] fixed docs and added observable actions client --- .../IObservableRepositoryActionsClient.cs | 23 +++++++++++ .../ObservableRepositoryActionsClient.cs | 40 +++++++++++++++++++ Octokit/Clients/IRepositoryActionsClient.cs | 6 +-- Octokit/Clients/RepositoryActionsClient.cs | 8 ++-- 4 files changed, 70 insertions(+), 7 deletions(-) create mode 100644 Octokit.Reactive/Clients/IObservableRepositoryActionsClient.cs create mode 100644 Octokit.Reactive/Clients/ObservableRepositoryActionsClient.cs diff --git a/Octokit.Reactive/Clients/IObservableRepositoryActionsClient.cs b/Octokit.Reactive/Clients/IObservableRepositoryActionsClient.cs new file mode 100644 index 0000000000..6ab28ec7ad --- /dev/null +++ b/Octokit.Reactive/Clients/IObservableRepositoryActionsClient.cs @@ -0,0 +1,23 @@ +using System; +using System.Collections.Generic; +using System.Text; + +namespace Octokit.Reactive +{ + /// + /// A client for GitHub's Repository Actions API. + /// + /// + /// See the Repository Actions API documentation for more details. + /// + public interface IObservableRepositoryActionsClient + { + /// + /// Client for GitHub's Repository Actions API + /// + /// + /// See the Deployments API documentation for more details + /// + IObservableRepositorySecretsClient Secrets { get; } + } +} diff --git a/Octokit.Reactive/Clients/ObservableRepositoryActionsClient.cs b/Octokit.Reactive/Clients/ObservableRepositoryActionsClient.cs new file mode 100644 index 0000000000..5dade50e0a --- /dev/null +++ b/Octokit.Reactive/Clients/ObservableRepositoryActionsClient.cs @@ -0,0 +1,40 @@ +using System; +using System.Collections.Generic; +using System.Text; + +namespace Octokit.Reactive +{ + /// + /// A client for GitHub's Repository Actions API. + /// + /// + /// See the Repository Actions API documentation for more details. + /// + public class ObservableRepositoryActionsClient : IObservableRepositoryActionsClient + { + readonly IRepositoryActionsClient _client; + readonly IConnection _connection; + + /// + /// Initializes a new GitHub Repository Actions API client. + /// + /// An API connection + public ObservableRepositoryActionsClient(IGitHubClient client) + { + Ensure.ArgumentNotNull(client, nameof(client)); + + _client = client.Repository.Actions; + _connection = client.Connection; + + Secrets = new ObservableRepositorySecretsClient(client); + } + + /// + /// Client for GitHub's Repository Actions API + /// + /// + /// See the Deployments API documentation for more details + /// + public IObservableRepositorySecretsClient Secrets { get; private set; } + } +} diff --git a/Octokit/Clients/IRepositoryActionsClient.cs b/Octokit/Clients/IRepositoryActionsClient.cs index 0cd39d7c14..0c095d3d3f 100644 --- a/Octokit/Clients/IRepositoryActionsClient.cs +++ b/Octokit/Clients/IRepositoryActionsClient.cs @@ -8,15 +8,15 @@ namespace Octokit /// A client for GitHub's Repository Actions API. /// /// - /// See the Repository Secrets API documentation for more details. + /// See the Repository Actions API documentation for more details. /// public interface IRepositoryActionsClient { /// - /// Client for GitHub's Repository Secrets API + /// Client for GitHub's Repository Actions API /// /// - /// See the Deployments API documentation for more details + /// See the Deployments API documentation for more details /// IRepositorySecretsClient Secrets { get; } } diff --git a/Octokit/Clients/RepositoryActionsClient.cs b/Octokit/Clients/RepositoryActionsClient.cs index 22f9082e94..72dab366e2 100644 --- a/Octokit/Clients/RepositoryActionsClient.cs +++ b/Octokit/Clients/RepositoryActionsClient.cs @@ -8,12 +8,12 @@ namespace Octokit /// A client for GitHub's Repository Actions API. /// /// - /// See the Repository Secrets API documentation for more details. + /// See the Repository Actions API documentation for more details. /// public class RepositoryActionsClient : ApiClient, IRepositoryActionsClient { /// - /// Initializes a new GitHub Repository Branches API client. + /// Initializes a new GitHub Repository Actions API client. /// /// An API connection public RepositoryActionsClient(IApiConnection apiConnection) : base(apiConnection) @@ -22,10 +22,10 @@ public RepositoryActionsClient(IApiConnection apiConnection) : base(apiConnectio } /// - /// Client for GitHub's Repository Secrets API + /// Client for GitHub's Repository Actions API /// /// - /// See the Deployments API documentation for more details + /// See the Deployments API documentation for more details /// public IRepositorySecretsClient Secrets { get; set; } } From 717dd736d9c1cd85311eab0cf6591fc748b79a16 Mon Sep 17 00:00:00 2001 From: Mike Tolly Date: Thu, 25 Jun 2020 20:30:05 -0400 Subject: [PATCH 09/56] added Actions to repository client --- Octokit.Reactive/Clients/IObservableReactionsClient.cs | 8 ++++++++ Octokit.Reactive/Clients/ObservableRepositoriesClient.cs | 9 +++++++++ Octokit/Clients/IRepositoriesClient.cs | 8 ++++++++ Octokit/Clients/RepositoriesClient.cs | 9 +++++++++ 4 files changed, 34 insertions(+) diff --git a/Octokit.Reactive/Clients/IObservableReactionsClient.cs b/Octokit.Reactive/Clients/IObservableReactionsClient.cs index 2cedf69afd..ed4e46f038 100644 --- a/Octokit.Reactive/Clients/IObservableReactionsClient.cs +++ b/Octokit.Reactive/Clients/IObservableReactionsClient.cs @@ -5,6 +5,14 @@ namespace Octokit.Reactive { public interface IObservableReactionsClient { + /// + /// Access GitHub's Repository Actions API. + /// + /// + /// Refer to the API documentation for more information: https://developer.github.com/v3/actions/ + /// + IObservableRepositoryActionsClient Actions { get; } + /// /// Access GitHub's Reactions API for Commit Comments. /// diff --git a/Octokit.Reactive/Clients/ObservableRepositoriesClient.cs b/Octokit.Reactive/Clients/ObservableRepositoriesClient.cs index ddeb1338bc..01ac26f046 100644 --- a/Octokit.Reactive/Clients/ObservableRepositoriesClient.cs +++ b/Octokit.Reactive/Clients/ObservableRepositoriesClient.cs @@ -38,6 +38,7 @@ public ObservableRepositoriesClient(IGitHubClient client) Invitation = new ObservableRepositoryInvitationsClient(client); Traffic = new ObservableRepositoryTrafficClient(client); Project = new ObservableProjectsClient(client); + Actions = new ObservableRepositoryActionsClient(client); } /// @@ -742,6 +743,14 @@ public IObservable Compare(string owner, string name, string @bas return _client.Commit.Compare(owner, name, @base, head).ToObservable(); } + /// + /// A client for GitHub's Repository Actions API. + /// + /// + /// See the Actions API documentation for more details + /// + public IObservableRepositoryActionsClient Actions { get; private set; } + /// /// A client for GitHub's Repository Branches API. /// diff --git a/Octokit/Clients/IRepositoriesClient.cs b/Octokit/Clients/IRepositoriesClient.cs index ab9e31fb94..5d1b0abc80 100644 --- a/Octokit/Clients/IRepositoriesClient.cs +++ b/Octokit/Clients/IRepositoriesClient.cs @@ -21,6 +21,14 @@ public interface IRepositoriesClient /// IPullRequestsClient PullRequest { get; } + /// + /// Client for managing Actions in a repository. + /// + /// + /// See the Repository Actions API documentation for more information. + /// + IRepositoryActionsClient Actions { get; } + /// /// Client for managing branches in a repository. /// diff --git a/Octokit/Clients/RepositoriesClient.cs b/Octokit/Clients/RepositoriesClient.cs index d067ddcf43..f615862b3b 100644 --- a/Octokit/Clients/RepositoriesClient.cs +++ b/Octokit/Clients/RepositoriesClient.cs @@ -39,6 +39,7 @@ public RepositoriesClient(IApiConnection apiConnection) : base(apiConnection) Branch = new RepositoryBranchesClient(apiConnection); Traffic = new RepositoryTrafficClient(apiConnection); Project = new ProjectsClient(apiConnection); + Actions = new RepositoryActionsClient(apiConnection); } /// @@ -454,6 +455,14 @@ public Task> GetAllForOrg(string organization, ApiOpti return ApiConnection.GetAll(ApiUrls.OrganizationRepositories(organization), options); } + /// + /// Client for managing Actions in a repository. + /// + /// + /// See the Repository Actions API documentation for more information. + /// + public IRepositoryActionsClient Actions { get; private set; } + /// /// A client for GitHub's Repository Branches API. /// From d4cde855b2562f851a6c96b61ca6a7af01bd722e Mon Sep 17 00:00:00 2001 From: Mike Tolly Date: Thu, 25 Jun 2020 20:34:18 -0400 Subject: [PATCH 10/56] created IObservable repository secrets client --- .../IObservableRepositorySecretsClient.cs | 92 +++++++++++ .../ObservableRepositorySecretsClient.cs | 147 ++++++++++++++++++ 2 files changed, 239 insertions(+) create mode 100644 Octokit.Reactive/Clients/IObservableRepositorySecretsClient.cs create mode 100644 Octokit.Reactive/Clients/ObservableRepositorySecretsClient.cs diff --git a/Octokit.Reactive/Clients/IObservableRepositorySecretsClient.cs b/Octokit.Reactive/Clients/IObservableRepositorySecretsClient.cs new file mode 100644 index 0000000000..7207d73def --- /dev/null +++ b/Octokit.Reactive/Clients/IObservableRepositorySecretsClient.cs @@ -0,0 +1,92 @@ +using System; +using System.Collections.Generic; +using System.Reactive; +using System.Text; + +namespace Octokit.Reactive +{ + /// + /// A client for GitHub's Repository Secrets API. + /// + /// + /// See the Repository Secrets API documentation for more details. + /// + public interface IObservableRepositorySecretsClient + { + /// + /// Get the public signing key to encrypt secrets for a repository. + /// + /// + /// See the API documentation for more information. + /// + /// The owner of the repository + /// The name of the repository + /// Thrown when a general API error occurs. + /// A instance for the repository public key. + IObservable GetPublicKey(string owner, string repoName); + + /// + /// List the secrets for a repository. + /// + /// + /// See the API documentation for more information. + /// + /// The owner of the repository + /// The name of the repository + /// Thrown when a general API error occurs. + /// A instance for the list of repository secrets. + IObservable> GetAll(string owner, string repoName); + + /// + /// List the secrets for a repository. + /// + /// + /// See the API documentation for more information. + /// + /// The owner of the repository + /// The name of the repository + /// Options for changing the API response + /// Thrown when a general API error occurs. + /// A instance for the list of repository secrets. + IObservable> GetAll(string owner, string repoName, ApiOptions options); + + /// + /// Get a secret from a repository. + /// + /// + /// See the API documentation for more information. + /// + /// The owner of the repository + /// The name of the repository + /// The name of the secret + /// Thrown when a general API error occurs. + /// A instance for the repository secret. + IObservable Get(string owner, string repoName, string secretName); + + /// + /// Create or update a secret in a repository. + /// + /// + /// See the API documentation for more information. + /// + /// The owner of the repository + /// The name of the repository + /// The name of the secret + /// The encrypted value and id of the encryption key + /// Thrown when a general API error occurs. + /// A instance for the repository secret that was created or updated. + IObservable CreateOrUpdate(string owner, string repoName, string secretName, UpsertRepositorySecret upsertSecret); + + /// + /// Delete a secret in a repository. + /// + /// + /// See the API documentation for more information. + /// + /// The owner of the repository + /// The name of the repository + /// The name of the secret + /// Thrown when a general API error occurs. + IObservable Delete(string owner, string repoName, string secretName); + } +} diff --git a/Octokit.Reactive/Clients/ObservableRepositorySecretsClient.cs b/Octokit.Reactive/Clients/ObservableRepositorySecretsClient.cs new file mode 100644 index 0000000000..ce34eb1fd2 --- /dev/null +++ b/Octokit.Reactive/Clients/ObservableRepositorySecretsClient.cs @@ -0,0 +1,147 @@ +using System; +using System.Collections.Generic; +using System.Reactive; +using System.Reactive.Threading.Tasks; +using System.Text; + +namespace Octokit.Reactive +{ + /// + /// A client for GitHub's Repository Secrets API. + /// + /// + /// See the Repository Secrets API documentation for more details. + /// + public class ObservableRepositorySecretsClient : IObservableRepositorySecretsClient + { + readonly IRepositorySecretsClient _client; + readonly IConnection _connection; + + public ObservableRepositorySecretsClient(IGitHubClient client) + { + Ensure.ArgumentNotNull(client, nameof(client)); + + _client = client.Repository.Actions.Secrets; + _connection = client.Connection; + } + + /// + /// Get the public signing key to encrypt secrets for a repository. + /// + /// + /// See the API documentation for more information. + /// + /// The owner of the repository + /// The name of the repository + /// Thrown when a general API error occurs. + /// A instance for the repository public key. + public IObservable GetPublicKey(string owner, string repoName) + { + Ensure.ArgumentNotNullOrEmptyString(owner, nameof(owner)); + Ensure.ArgumentNotNullOrEmptyString(repoName, nameof(repoName)); + + return _client.GetPublicKey(owner, repoName).ToObservable(); + } + + /// + /// List the secrets for a repository. + /// + /// + /// See the API documentation for more information. + /// + /// The owner of the repository + /// The name of the repository + /// Thrown when a general API error occurs. + /// A instance for the list of repository secrets. + public IObservable> GetAll(string owner, string repoName) + { + Ensure.ArgumentNotNullOrEmptyString(owner, nameof(owner)); + Ensure.ArgumentNotNullOrEmptyString(repoName, nameof(repoName)); + + return _client.GetAll(owner, repoName).ToObservable(); + } + + /// + /// List the secrets for a repository. + /// + /// + /// See the API documentation for more information. + /// + /// The owner of the repository + /// The name of the repository + /// Options for changing the API response + /// Thrown when a general API error occurs. + /// A instance for the list of repository secrets. + public IObservable> GetAll(string owner, string repoName, ApiOptions options) + { + Ensure.ArgumentNotNullOrEmptyString(owner, nameof(owner)); + Ensure.ArgumentNotNullOrEmptyString(repoName, nameof(repoName)); + Ensure.ArgumentNotNull(options, nameof(options)); + + return _client.GetAll(owner, repoName, options).ToObservable(); + } + + /// + /// Get a secret from a repository. + /// + /// + /// See the API documentation for more information. + /// + /// The owner of the repository + /// The name of the repository + /// The name of the secret + /// Thrown when a general API error occurs. + /// A instance for the repository secret. + public IObservable Get(string owner, string repoName, string secretName) + { + Ensure.ArgumentNotNullOrEmptyString(owner, nameof(owner)); + Ensure.ArgumentNotNullOrEmptyString(repoName, nameof(repoName)); + Ensure.ArgumentNotNullOrEmptyString(secretName, nameof(secretName)); + + return _client.Get(owner, repoName, secretName).ToObservable(); + } + + /// + /// Create or update a secret in a repository. + /// + /// + /// See the API documentation for more information. + /// + /// The owner of the repository + /// The name of the repository + /// The name of the secret + /// The encrypted value and id of the encryption key + /// Thrown when a general API error occurs. + /// A instance for the repository secret that was created or updated. + public IObservable CreateOrUpdate(string owner, string repoName, string secretName, UpsertRepositorySecret upsertSecret) + { + Ensure.ArgumentNotNullOrEmptyString(owner, nameof(owner)); + Ensure.ArgumentNotNullOrEmptyString(repoName, nameof(repoName)); + Ensure.ArgumentNotNullOrEmptyString(secretName, nameof(secretName)); + Ensure.ArgumentNotNull(upsertSecret, nameof(upsertSecret)); + Ensure.ArgumentNotNullOrEmptyString(upsertSecret.EncryptedValue, nameof(upsertSecret.EncryptedValue)); + Ensure.ArgumentNotNullOrEmptyString(upsertSecret.EncryptionKeyId, nameof(upsertSecret.EncryptionKeyId)); + + return _client.CreateOrUpdate(owner, repoName, secretName, upsertSecret).ToObservable(); + } + + /// + /// Delete a secret in a repository. + /// + /// + /// See the API documentation for more information. + /// + /// The owner of the repository + /// The name of the repository + /// The name of the secret + /// Thrown when a general API error occurs. + public IObservable Delete(string owner, string repoName, string secretName) + { + Ensure.ArgumentNotNullOrEmptyString(owner, nameof(owner)); + Ensure.ArgumentNotNullOrEmptyString(repoName, nameof(repoName)); + Ensure.ArgumentNotNullOrEmptyString(secretName, nameof(secretName)); + + return _client.Delete(owner, repoName, secretName).ToObservable(); + } + } +} From 1665f26aff0bf3b6e1f237e44247c49a170be291 Mon Sep 17 00:00:00 2001 From: Mike Tolly Date: Fri, 26 Jun 2020 07:37:55 -0400 Subject: [PATCH 11/56] fixed property in wrong interface fixed wrong Ctor unit test --- Octokit.Reactive/Clients/IObservableReactionsClient.cs | 8 -------- Octokit.Reactive/Clients/IObservableRepositoriesClient.cs | 8 ++++++++ Octokit.Tests/Clients/RepositoryActionsClientTests.cs | 2 +- Octokit.Tests/Clients/RepositorySecretsClientTests.cs | 2 +- 4 files changed, 10 insertions(+), 10 deletions(-) diff --git a/Octokit.Reactive/Clients/IObservableReactionsClient.cs b/Octokit.Reactive/Clients/IObservableReactionsClient.cs index ed4e46f038..2cedf69afd 100644 --- a/Octokit.Reactive/Clients/IObservableReactionsClient.cs +++ b/Octokit.Reactive/Clients/IObservableReactionsClient.cs @@ -5,14 +5,6 @@ namespace Octokit.Reactive { public interface IObservableReactionsClient { - /// - /// Access GitHub's Repository Actions API. - /// - /// - /// Refer to the API documentation for more information: https://developer.github.com/v3/actions/ - /// - IObservableRepositoryActionsClient Actions { get; } - /// /// Access GitHub's Reactions API for Commit Comments. /// diff --git a/Octokit.Reactive/Clients/IObservableRepositoriesClient.cs b/Octokit.Reactive/Clients/IObservableRepositoriesClient.cs index 7d3218e884..f498586405 100644 --- a/Octokit.Reactive/Clients/IObservableRepositoriesClient.cs +++ b/Octokit.Reactive/Clients/IObservableRepositoriesClient.cs @@ -173,6 +173,14 @@ public interface IObservableRepositoriesClient /// A of . IObservable GetAllForOrg(string organization, ApiOptions options); + /// + /// Access GitHub's Repository Actions API. + /// + /// + /// Refer to the API documentation for more information: https://developer.github.com/v3/actions/ + /// + IObservableRepositoryActionsClient Actions { get; } + /// /// Client for managing branches in a repository. /// diff --git a/Octokit.Tests/Clients/RepositoryActionsClientTests.cs b/Octokit.Tests/Clients/RepositoryActionsClientTests.cs index 99928f232d..36f977d45d 100644 --- a/Octokit.Tests/Clients/RepositoryActionsClientTests.cs +++ b/Octokit.Tests/Clients/RepositoryActionsClientTests.cs @@ -10,7 +10,7 @@ public class TheCtor [Fact] public void EnsuresNonNullArguments() { - Assert.Throws(() => new AssigneesClient(null)); + Assert.Throws(() => new RepositoryActionsClient(null)); } } } diff --git a/Octokit.Tests/Clients/RepositorySecretsClientTests.cs b/Octokit.Tests/Clients/RepositorySecretsClientTests.cs index ec4df9d2da..a35efe10df 100644 --- a/Octokit.Tests/Clients/RepositorySecretsClientTests.cs +++ b/Octokit.Tests/Clients/RepositorySecretsClientTests.cs @@ -12,7 +12,7 @@ public class TheCtor [Fact] public void EnsuresNonNullArguments() { - Assert.Throws(() => new AssigneesClient(null)); + Assert.Throws(() => new RepositorySecretsClient(null)); } } From 6653736a207e40e604dae8832da53e0178075c9e Mon Sep 17 00:00:00 2001 From: Mike Tolly Date: Fri, 26 Jun 2020 14:56:30 -0400 Subject: [PATCH 12/56] created repository decrets reactive tests and clients --- .../IObservableRepositorySecretsClient.cs | 4 +- .../ObservableRepositoryActionsClient.cs | 4 - .../ObservableRepositorySecretsClient.cs | 11 +- .../ObservableRepositoryActionsClientTests.cs | 20 ++ .../ObservableRepositorySecretsClientTests.cs | 174 ++++++++++++++++++ 5 files changed, 202 insertions(+), 11 deletions(-) create mode 100644 Octokit.Tests/Reactive/ObservableRepositoryActionsClientTests.cs create mode 100644 Octokit.Tests/Reactive/ObservableRepositorySecretsClientTests.cs diff --git a/Octokit.Reactive/Clients/IObservableRepositorySecretsClient.cs b/Octokit.Reactive/Clients/IObservableRepositorySecretsClient.cs index 7207d73def..3543be0756 100644 --- a/Octokit.Reactive/Clients/IObservableRepositorySecretsClient.cs +++ b/Octokit.Reactive/Clients/IObservableRepositorySecretsClient.cs @@ -35,7 +35,7 @@ public interface IObservableRepositorySecretsClient /// The name of the repository /// Thrown when a general API error occurs. /// A instance for the list of repository secrets. - IObservable> GetAll(string owner, string repoName); + IObservable GetAll(string owner, string repoName); /// /// List the secrets for a repository. @@ -48,7 +48,7 @@ public interface IObservableRepositorySecretsClient /// Options for changing the API response /// Thrown when a general API error occurs. /// A instance for the list of repository secrets. - IObservable> GetAll(string owner, string repoName, ApiOptions options); + IObservable GetAll(string owner, string repoName, ApiOptions options); /// /// Get a secret from a repository. diff --git a/Octokit.Reactive/Clients/ObservableRepositoryActionsClient.cs b/Octokit.Reactive/Clients/ObservableRepositoryActionsClient.cs index 5dade50e0a..a387a44d8b 100644 --- a/Octokit.Reactive/Clients/ObservableRepositoryActionsClient.cs +++ b/Octokit.Reactive/Clients/ObservableRepositoryActionsClient.cs @@ -15,10 +15,6 @@ public class ObservableRepositoryActionsClient : IObservableRepositoryActionsCli readonly IRepositoryActionsClient _client; readonly IConnection _connection; - /// - /// Initializes a new GitHub Repository Actions API client. - /// - /// An API connection public ObservableRepositoryActionsClient(IGitHubClient client) { Ensure.ArgumentNotNull(client, nameof(client)); diff --git a/Octokit.Reactive/Clients/ObservableRepositorySecretsClient.cs b/Octokit.Reactive/Clients/ObservableRepositorySecretsClient.cs index ce34eb1fd2..c8e01f1da8 100644 --- a/Octokit.Reactive/Clients/ObservableRepositorySecretsClient.cs +++ b/Octokit.Reactive/Clients/ObservableRepositorySecretsClient.cs @@ -1,4 +1,5 @@ -using System; +using Octokit.Reactive.Internal; +using System; using System.Collections.Generic; using System.Reactive; using System.Reactive.Threading.Tasks; @@ -53,12 +54,12 @@ public IObservable GetPublicKey(string owner, string /// The name of the repository /// Thrown when a general API error occurs. /// A instance for the list of repository secrets. - public IObservable> GetAll(string owner, string repoName) + public IObservable GetAll(string owner, string repoName) { Ensure.ArgumentNotNullOrEmptyString(owner, nameof(owner)); Ensure.ArgumentNotNullOrEmptyString(repoName, nameof(repoName)); - return _client.GetAll(owner, repoName).ToObservable(); + return _connection.GetAndFlattenAllPages(ApiUrls.RepositorySecretsList(owner, repoName)); } /// @@ -72,13 +73,13 @@ public IObservable> GetAll(string owner, string /// Options for changing the API response /// Thrown when a general API error occurs. /// A instance for the list of repository secrets. - public IObservable> GetAll(string owner, string repoName, ApiOptions options) + public IObservable GetAll(string owner, string repoName, ApiOptions options) { Ensure.ArgumentNotNullOrEmptyString(owner, nameof(owner)); Ensure.ArgumentNotNullOrEmptyString(repoName, nameof(repoName)); Ensure.ArgumentNotNull(options, nameof(options)); - return _client.GetAll(owner, repoName, options).ToObservable(); + return _connection.GetAndFlattenAllPages(ApiUrls.RepositorySecretsList(owner, repoName), options); } /// diff --git a/Octokit.Tests/Reactive/ObservableRepositoryActionsClientTests.cs b/Octokit.Tests/Reactive/ObservableRepositoryActionsClientTests.cs new file mode 100644 index 0000000000..22b79b8fbc --- /dev/null +++ b/Octokit.Tests/Reactive/ObservableRepositoryActionsClientTests.cs @@ -0,0 +1,20 @@ +using Octokit.Reactive; +using System; +using System.Collections.Generic; +using System.Text; +using Xunit; + +namespace Octokit.Tests.Reactive +{ + public class ObservableRepositoryActionsClientTests + { + public class TheCtor + { + [Fact] + public void EnsuresNonNullArguments() + { + Assert.Throws(() => new ObservableRepositoryActionsClient(null)); + } + } + } +} diff --git a/Octokit.Tests/Reactive/ObservableRepositorySecretsClientTests.cs b/Octokit.Tests/Reactive/ObservableRepositorySecretsClientTests.cs new file mode 100644 index 0000000000..30cfb08734 --- /dev/null +++ b/Octokit.Tests/Reactive/ObservableRepositorySecretsClientTests.cs @@ -0,0 +1,174 @@ +using NSubstitute; +using Octokit.Reactive; +using System; +using System.Reactive.Linq; +using System.Reactive.Threading.Tasks; +using System.Threading.Tasks; +using Xunit; + +namespace Octokit.Tests.Reactive +{ + public class ObservableRepositorySecretsClientTests + { + public class TheCtor + { + [Fact] + public void EnsuresNonNullArguments() + { + Assert.Throws(() => new ObservableRepositorySecretsClient(null)); + } + } + + public class GetPublicKeyMethod + { + [Fact] + public async Task RequestsTheCorrectUrl() + { + var gitHubClient = Substitute.For(); + var client = new ObservableRepositorySecretsClient(gitHubClient); + + await client.GetPublicKey("owner", "repo"); + + gitHubClient.Received().Repository.Actions.Secrets.GetPublicKey("owner", "repo"); + } + + [Fact] + public async Task EnsuresNonNullArguments() + { + var client = new ObservableRepositorySecretsClient(Substitute.For()); + + await Assert.ThrowsAsync(() => client.GetPublicKey(null, "repo").ToTask()); + await Assert.ThrowsAsync(() => client.GetPublicKey("owner", null).ToTask()); + await Assert.ThrowsAsync(() => client.GetPublicKey("", "repo").ToTask()); + await Assert.ThrowsAsync(() => client.GetPublicKey("owner", "").ToTask()); + } + } + + public class GetAllMethod + { + [Fact] + public async Task RequestsTheCorrectUrl() + { + var gitHubClient = Substitute.For(); + var client = new ObservableRepositorySecretsClient(gitHubClient); + + await client.GetAll("owner", "repo"); + + gitHubClient.Received().Repository.Actions.Secrets.GetAll("owner", "repo"); + } + + [Fact] + public async Task EnsuresNonNullArguments() + { + var client = new ObservableRepositorySecretsClient(Substitute.For()); + + await Assert.ThrowsAsync(() => client.GetAll(null, "repo").ToTask()); + await Assert.ThrowsAsync(() => client.GetAll("owner", null).ToTask()); + + await Assert.ThrowsAsync(() => client.GetAll("owner", null, ApiOptions.None).ToTask()); + await Assert.ThrowsAsync(() => client.GetAll("owner", "repo", null).ToTask()); + await Assert.ThrowsAsync(() => client.GetAll(null, "repo", ApiOptions.None).ToTask()); + + await Assert.ThrowsAsync(() => client.GetAll("", "repo").ToTask()); + await Assert.ThrowsAsync(() => client.GetAll("owner", "").ToTask()); + } + } + + public class GetMethod + { + [Fact] + public async Task RequestsTheCorrectUrl() + { + var gitHubClient = Substitute.For(); + var client = new ObservableRepositorySecretsClient(gitHubClient); + + await client.Get("owner", "repo","secret"); + + gitHubClient.Received().Repository.Actions.Secrets.Get("owner", "repo", "secret"); + } + + [Fact] + public async Task EnsuresNonNullArguments() + { + var client = new ObservableRepositorySecretsClient(Substitute.For()); + + await Assert.ThrowsAsync(() => client.Get(null, "repo", "secret").ToTask()); + await Assert.ThrowsAsync(() => client.Get("owner", null, "secret").ToTask()); + await Assert.ThrowsAsync(() => client.Get("owner", "repo", null).ToTask()); + + await Assert.ThrowsAsync(() => client.Get("", "repo", "secret").ToTask()); + await Assert.ThrowsAsync(() => client.Get("owner", "", "secret").ToTask()); + await Assert.ThrowsAsync(() => client.Get("owner", "repo", "").ToTask()); + } + } + + public class CreateOrUpdateMethod + { + [Fact] + public async Task PostsTheCorrectUrl() + { + var gitHubClient = Substitute.For(); + var client = new ObservableRepositorySecretsClient(gitHubClient); + var upsert = new UpsertRepositorySecret + { + EncryptedValue = "encryptedValue", + EncryptionKeyId = "keyId" + }; + + await client.CreateOrUpdate("owner", "repo", "secret", upsert); + + gitHubClient.Received().Repository.Actions.Secrets.CreateOrUpdate("owner", "repo", "secret", upsert); + } + + [Fact] + public async Task EnsuresNonNullArguments() + { + var client = new ObservableRepositorySecretsClient(Substitute.For()); + + var upsertSecret = new UpsertRepositorySecret + { + EncryptedValue = "encryptedValue", + EncryptionKeyId = "keyId" + }; + + await Assert.ThrowsAsync(() => client.CreateOrUpdate(null, "repo", "secret", upsertSecret).ToTask()); + await Assert.ThrowsAsync(() => client.CreateOrUpdate("owner", null, "secret", upsertSecret).ToTask()); + await Assert.ThrowsAsync(() => client.CreateOrUpdate("owner", "repo", null, upsertSecret).ToTask()); + await Assert.ThrowsAsync(() => client.CreateOrUpdate("owner", "repo", "secret", null).ToTask()); + await Assert.ThrowsAsync(() => client.CreateOrUpdate("owner", "repo", "secret", new UpsertRepositorySecret()).ToTask()); + + await Assert.ThrowsAsync(() => client.CreateOrUpdate("", "repo", "secret", upsertSecret).ToTask()); + await Assert.ThrowsAsync(() => client.CreateOrUpdate("owner", "", "secret", upsertSecret).ToTask()); + await Assert.ThrowsAsync(() => client.CreateOrUpdate("owner", "repo", "", upsertSecret).ToTask()); + } + } + + public class DeleteMethod + { + [Fact] + public async Task DeletesTheCorrectUrl() + { + var gitHubClient = Substitute.For(); + var client = new ObservableRepositorySecretsClient(gitHubClient); + + await client.Delete("owner", "repo", "secret"); + + gitHubClient.Received().Repository.Actions.Secrets.Delete("owner", "repo", "secret"); + } + + [Fact] + public async Task EnsuresNonNullArguments() + { + var client = new ObservableRepositorySecretsClient(Substitute.For()); + + await Assert.ThrowsAsync(() => client.Delete(null, "repo", "secret").ToTask()); + await Assert.ThrowsAsync(() => client.Delete("owner", null, "secret").ToTask()); + await Assert.ThrowsAsync(() => client.Delete("owner", "repo", null).ToTask()); + + await Assert.ThrowsAsync(() => client.Delete("", "repo", "secret").ToTask()); + await Assert.ThrowsAsync(() => client.Delete("owner", "", "secret").ToTask()); + await Assert.ThrowsAsync(() => client.Delete("owner", "repo", "").ToTask()); + } + } + } +} From 93e660884f95738af0ac52560e91e0a5acd4d6aa Mon Sep 17 00:00:00 2001 From: Mike Tolly Date: Fri, 26 Jun 2020 14:57:23 -0400 Subject: [PATCH 13/56] created organization actions and scerets classes and made them available through the oprganizations client --- Octokit/Clients/IOrganizationActionsClient.cs | 23 +++++++++++++ Octokit/Clients/IOrganizationSecretsClient.cs | 16 ++++++++++ Octokit/Clients/IOrganizationsClient.cs | 5 +++ Octokit/Clients/OrganizationActionsClient.cs | 32 +++++++++++++++++++ Octokit/Clients/OrganizationSecretsClient.cs | 13 ++++++++ Octokit/Clients/OrganizationsClient.cs | 6 ++++ 6 files changed, 95 insertions(+) create mode 100644 Octokit/Clients/IOrganizationActionsClient.cs create mode 100644 Octokit/Clients/IOrganizationSecretsClient.cs create mode 100644 Octokit/Clients/OrganizationActionsClient.cs create mode 100644 Octokit/Clients/OrganizationSecretsClient.cs diff --git a/Octokit/Clients/IOrganizationActionsClient.cs b/Octokit/Clients/IOrganizationActionsClient.cs new file mode 100644 index 0000000000..36c45acb5e --- /dev/null +++ b/Octokit/Clients/IOrganizationActionsClient.cs @@ -0,0 +1,23 @@ +using System; +using System.Collections.Generic; +using System.Text; + +namespace Octokit +{ + /// + /// A client for GitHub's Org Actions API. + /// + /// + /// See the Actions API documentation for more information. + /// + public interface IOrganizationActionsClient + { + /// + /// Returns a client to manage organization secrets. + /// + /// + /// See the Secrets API documentation for more information. + /// + IOrganizationSecretsClient Secrets { get; } + } +} diff --git a/Octokit/Clients/IOrganizationSecretsClient.cs b/Octokit/Clients/IOrganizationSecretsClient.cs new file mode 100644 index 0000000000..0763a7d9a9 --- /dev/null +++ b/Octokit/Clients/IOrganizationSecretsClient.cs @@ -0,0 +1,16 @@ +using System; +using System.Collections.Generic; +using System.Text; + +namespace Octokit +{ + /// + /// A client for GitHub's Organization Secrets API. + /// + /// + /// See the Organization Secrets API documentation for more details. + /// + public interface IOrganizationSecretsClient + { + } +} diff --git a/Octokit/Clients/IOrganizationsClient.cs b/Octokit/Clients/IOrganizationsClient.cs index faaf082f3d..f2b6c11e69 100644 --- a/Octokit/Clients/IOrganizationsClient.cs +++ b/Octokit/Clients/IOrganizationsClient.cs @@ -35,6 +35,11 @@ public interface IOrganizationsClient /// IOrganizationOutsideCollaboratorsClient OutsideCollaborator { get; } + /// + /// Returns a client to manage organization actions. + /// + IOrganizationActionsClient Actions { get; } + /// /// Returns the specified . /// diff --git a/Octokit/Clients/OrganizationActionsClient.cs b/Octokit/Clients/OrganizationActionsClient.cs new file mode 100644 index 0000000000..7e8b514956 --- /dev/null +++ b/Octokit/Clients/OrganizationActionsClient.cs @@ -0,0 +1,32 @@ +using System; +using System.Collections.Generic; +using System.Text; + +namespace Octokit +{ + /// + /// A client for GitHub's Org Actions API. + /// + /// + /// See the Actions API documentation for more information. + /// + public class OrganizationActionsClient : ApiClient, IOrganizationActionsClient + { + /// + /// Initializes a new GitHub Orgs Actions API client. + /// + /// An API connection + public OrganizationActionsClient(IApiConnection apiConnection) : base(apiConnection) + { + Secrets = new OrganizationSecretsClient(apiConnection); + } + + /// + /// Returns a client to manage organization secrets. + /// + /// + /// See the Secrets API documentation for more information. + /// + public IOrganizationSecretsClient Secrets { get; private set; } + } +} diff --git a/Octokit/Clients/OrganizationSecretsClient.cs b/Octokit/Clients/OrganizationSecretsClient.cs new file mode 100644 index 0000000000..1cb5a1260b --- /dev/null +++ b/Octokit/Clients/OrganizationSecretsClient.cs @@ -0,0 +1,13 @@ +using System; +using System.Collections.Generic; +using System.Text; + +namespace Octokit +{ + public class OrganizationSecretsClient : ApiClient, IOrganizationSecretsClient + { + public OrganizationSecretsClient(IApiConnection apiConnection) : base(apiConnection) + { + } + } +} diff --git a/Octokit/Clients/OrganizationsClient.cs b/Octokit/Clients/OrganizationsClient.cs index 5d13ca1895..5e0bddefcd 100644 --- a/Octokit/Clients/OrganizationsClient.cs +++ b/Octokit/Clients/OrganizationsClient.cs @@ -22,6 +22,7 @@ public OrganizationsClient(IApiConnection apiConnection) : base(apiConnection) Team = new TeamsClient(apiConnection); Hook = new OrganizationHooksClient(apiConnection); OutsideCollaborator = new OrganizationOutsideCollaboratorsClient(apiConnection); + Actions = new OrganizationActionsClient(apiConnection); } /// @@ -34,6 +35,11 @@ public OrganizationsClient(IApiConnection apiConnection) : base(apiConnection) /// public ITeamsClient Team { get; private set; } + /// + /// Returns a client to manage organization actions. + /// + public IOrganizationActionsClient Actions { get; private set; } + /// /// Returns a client to manage outside collaborators of an organization. /// From 1747a2d8c0cc2fb55fd6c4c48ad2d1c3b6600524 Mon Sep 17 00:00:00 2001 From: Mike Tolly Date: Sat, 27 Jun 2020 15:31:08 -0400 Subject: [PATCH 14/56] fixed intellisense text --- Octokit/Clients/IRepositorySecretsClient.cs | 41 ++++++---------- Octokit/Clients/RepositorySecretsClient.cs | 54 ++++++--------------- 2 files changed, 30 insertions(+), 65 deletions(-) diff --git a/Octokit/Clients/IRepositorySecretsClient.cs b/Octokit/Clients/IRepositorySecretsClient.cs index 6bf54a6086..50213bec2a 100644 --- a/Octokit/Clients/IRepositorySecretsClient.cs +++ b/Octokit/Clients/IRepositorySecretsClient.cs @@ -17,11 +17,11 @@ public interface IRepositorySecretsClient /// /// See the API documentation for more information. /// - /// The owner of the repository - /// The name of the repository + /// The owner of the repository + /// The name of the repository /// Thrown when a general API error occurs. - /// A instance for the repository public key. - Task GetPublicKey(string owner, string repoName); + /// A instance for the repository public key. + Task GetPublicKey(string owner, string repoName); /// /// List the secrets for a repository. @@ -29,24 +29,11 @@ public interface IRepositorySecretsClient /// /// See the API documentation for more information. /// - /// The owner of the repository - /// The name of the repository + /// The owner of the repository + /// The name of the repository /// Thrown when a general API error occurs. - /// A instance for the list of repository secrets. - Task> GetAll (string owner, string repoName); - - /// - /// List the secrets for a repository. - /// - /// - /// See the API documentation for more information. - /// - /// The owner of the repository - /// The name of the repository - /// Options for changing the API response - /// Thrown when a general API error occurs. - /// A instance for the list of repository secrets. - Task> GetAll(string owner, string repoName, ApiOptions options); + /// A instance for the list of repository secrets. + Task GetAll (string owner, string repoName); /// /// Get a secret from a repository. @@ -54,8 +41,8 @@ public interface IRepositorySecretsClient /// /// See the API documentation for more information. /// - /// The owner of the repository - /// The name of the repository + /// The owner of the repository + /// The name of the repository /// The name of the secret /// Thrown when a general API error occurs. /// A instance for the repository secret. @@ -67,8 +54,8 @@ public interface IRepositorySecretsClient /// /// See the API documentation for more information. /// - /// The owner of the repository - /// The name of the repository + /// The owner of the repository + /// The name of the repository /// The name of the secret /// The encrypted value and id of the encryption key /// Thrown when a general API error occurs. @@ -81,8 +68,8 @@ public interface IRepositorySecretsClient /// /// See the API documentation for more information. /// - /// The owner of the repository - /// The name of the repository + /// The owner of the repository + /// The name of the repository /// The name of the secret /// Thrown when a general API error occurs. Task Delete(string owner, string repoName, string secretName); diff --git a/Octokit/Clients/RepositorySecretsClient.cs b/Octokit/Clients/RepositorySecretsClient.cs index b54dbae72b..95c521e04d 100644 --- a/Octokit/Clients/RepositorySecretsClient.cs +++ b/Octokit/Clients/RepositorySecretsClient.cs @@ -21,19 +21,19 @@ public RepositorySecretsClient(IApiConnection apiConnection) : base(apiConnectio /// /// See the API documentation for more information. /// - /// The owner of the repository - /// The name of the repository + /// The owner of the repository + /// The name of the repository /// Thrown when a general API error occurs. - /// A instance for the repository public key. + /// A instance for the repository public key. [ManualRoute("GET", "/repos/{owner}/{repo}/actions/secrets/public-key")] - public Task GetPublicKey(string owner, string repoName) + public Task GetPublicKey(string owner, string repoName) { Ensure.ArgumentNotNullOrEmptyString(owner, nameof(owner)); Ensure.ArgumentNotNullOrEmptyString(repoName, nameof(repoName)); var url = ApiUrls.RepositorySecretsPublicKey(owner, repoName); - return ApiConnection.Get(url); + return ApiConnection.Get(url); } /// @@ -42,41 +42,19 @@ public Task GetPublicKey(string owner, string repoNa /// /// See the API documentation for more information. /// - /// The owner of the repository - /// The name of the repository + /// The owner of the repository + /// The name of the repository /// Thrown when a general API error occurs. - /// A instance for the list of repository secrets. + /// A instance for the list of repository secrets. [ManualRoute("GET", "/repos/{owner}/{repo}/actions/secrets")] - public Task> GetAll(string owner, string repoName) + public Task GetAll(string owner, string repoName) { Ensure.ArgumentNotNullOrEmptyString(owner, nameof(owner)); Ensure.ArgumentNotNullOrEmptyString(repoName, nameof(repoName)); var url = ApiUrls.RepositorySecretsList(owner, repoName); - return ApiConnection.GetAll(url); - } - - /// - /// List the secrets for a repository. - /// - /// - /// See the API documentation for more information. - /// - /// The owner of the repository - /// The name of the repository - /// Options for changing the API response - /// Thrown when a general API error occurs. - /// A instance for the list of repository secrets. - public Task> GetAll(string owner, string repoName, ApiOptions options) - { - Ensure.ArgumentNotNullOrEmptyString(owner, nameof(owner)); - Ensure.ArgumentNotNullOrEmptyString(repoName, nameof(repoName)); - Ensure.ArgumentNotNull(options, nameof(options)); - - var url = ApiUrls.RepositorySecretsList(owner, repoName); - - return ApiConnection.GetAll(url, options); + return ApiConnection.Get(url); } /// @@ -85,8 +63,8 @@ public Task> GetAll(string owner, string repoNam /// /// See the API documentation for more information. /// - /// The owner of the repository - /// The name of the repository + /// The owner of the repository + /// The name of the repository /// The name of the secret /// Thrown when a general API error occurs. /// A instance for the repository secret. @@ -108,8 +86,8 @@ public Task Get(string owner, string repoName, string secretNa /// /// See the API documentation for more information. /// - /// The owner of the repository - /// The name of the repository + /// The owner of the repository + /// The name of the repository /// The name of the secret /// The encrypted value and id of the encryption key /// Thrown when a general API error occurs. @@ -135,8 +113,8 @@ public async Task CreateOrUpdate(string owner, string repoName /// /// See the API documentation for more information. /// - /// The owner of the repository - /// The name of the repository + /// The owner of the repository + /// The name of the repository /// The name of the secret /// Thrown when a general API error occurs. [ManualRoute("DELETE", "/repos/{owner}/{repo}/actions/secrets/{secretName}")] From 3ff14a2a1d672f3a1bf38f4c11fcef34c098d33e Mon Sep 17 00:00:00 2001 From: Mike Tolly Date: Sat, 27 Jun 2020 15:32:07 -0400 Subject: [PATCH 15/56] removed uneeded getall call after return type change --- .../IObservableRepositorySecretsClient.cs | 19 ++----------- .../ObservableRepositorySecretsClient.cs | 28 +++---------------- .../Clients/RepositorySecretsClientTests.cs | 8 +----- .../ObservableRepositorySecretsClientTests.cs | 4 --- 4 files changed, 8 insertions(+), 51 deletions(-) diff --git a/Octokit.Reactive/Clients/IObservableRepositorySecretsClient.cs b/Octokit.Reactive/Clients/IObservableRepositorySecretsClient.cs index 3543be0756..a073b7b0a9 100644 --- a/Octokit.Reactive/Clients/IObservableRepositorySecretsClient.cs +++ b/Octokit.Reactive/Clients/IObservableRepositorySecretsClient.cs @@ -22,8 +22,8 @@ public interface IObservableRepositorySecretsClient /// The owner of the repository /// The name of the repository /// Thrown when a general API error occurs. - /// A instance for the repository public key. - IObservable GetPublicKey(string owner, string repoName); + /// A instance for the repository public key. + IObservable GetPublicKey(string owner, string repoName); /// /// List the secrets for a repository. @@ -35,20 +35,7 @@ public interface IObservableRepositorySecretsClient /// The name of the repository /// Thrown when a general API error occurs. /// A instance for the list of repository secrets. - IObservable GetAll(string owner, string repoName); - - /// - /// List the secrets for a repository. - /// - /// - /// See the API documentation for more information. - /// - /// The owner of the repository - /// The name of the repository - /// Options for changing the API response - /// Thrown when a general API error occurs. - /// A instance for the list of repository secrets. - IObservable GetAll(string owner, string repoName, ApiOptions options); + IObservable GetAll(string owner, string repoName); /// /// Get a secret from a repository. diff --git a/Octokit.Reactive/Clients/ObservableRepositorySecretsClient.cs b/Octokit.Reactive/Clients/ObservableRepositorySecretsClient.cs index c8e01f1da8..ef1b99f961 100644 --- a/Octokit.Reactive/Clients/ObservableRepositorySecretsClient.cs +++ b/Octokit.Reactive/Clients/ObservableRepositorySecretsClient.cs @@ -35,8 +35,8 @@ public ObservableRepositorySecretsClient(IGitHubClient client) /// The owner of the repository /// The name of the repository /// Thrown when a general API error occurs. - /// A instance for the repository public key. - public IObservable GetPublicKey(string owner, string repoName) + /// A instance for the repository public key. + public IObservable GetPublicKey(string owner, string repoName) { Ensure.ArgumentNotNullOrEmptyString(owner, nameof(owner)); Ensure.ArgumentNotNullOrEmptyString(repoName, nameof(repoName)); @@ -54,32 +54,12 @@ public IObservable GetPublicKey(string owner, string /// The name of the repository /// Thrown when a general API error occurs. /// A instance for the list of repository secrets. - public IObservable GetAll(string owner, string repoName) + public IObservable GetAll(string owner, string repoName) { Ensure.ArgumentNotNullOrEmptyString(owner, nameof(owner)); Ensure.ArgumentNotNullOrEmptyString(repoName, nameof(repoName)); - return _connection.GetAndFlattenAllPages(ApiUrls.RepositorySecretsList(owner, repoName)); - } - - /// - /// List the secrets for a repository. - /// - /// - /// See the API documentation for more information. - /// - /// The owner of the repository - /// The name of the repository - /// Options for changing the API response - /// Thrown when a general API error occurs. - /// A instance for the list of repository secrets. - public IObservable GetAll(string owner, string repoName, ApiOptions options) - { - Ensure.ArgumentNotNullOrEmptyString(owner, nameof(owner)); - Ensure.ArgumentNotNullOrEmptyString(repoName, nameof(repoName)); - Ensure.ArgumentNotNull(options, nameof(options)); - - return _connection.GetAndFlattenAllPages(ApiUrls.RepositorySecretsList(owner, repoName), options); + return _client.GetAll(owner, repoName).ToObservable(); } /// diff --git a/Octokit.Tests/Clients/RepositorySecretsClientTests.cs b/Octokit.Tests/Clients/RepositorySecretsClientTests.cs index a35efe10df..b448cb31f8 100644 --- a/Octokit.Tests/Clients/RepositorySecretsClientTests.cs +++ b/Octokit.Tests/Clients/RepositorySecretsClientTests.cs @@ -27,7 +27,7 @@ public async Task RequestsTheCorrectUrl() await client.GetPublicKey("owner", "repo"); connection.Received() - .Get(Arg.Is(u => u.ToString() == "repos/owner/repo/actions/secrets/public-key")); + .Get(Arg.Is(u => u.ToString() == "repos/owner/repo/actions/secrets/public-key")); } [Fact] @@ -64,14 +64,8 @@ public async Task EnsuresNonNullArguments() await Assert.ThrowsAsync(() => client.GetAll(null, "repo")); await Assert.ThrowsAsync(() => client.GetAll("owner", null)); - await Assert.ThrowsAsync(() => client.GetAll("owner", null, ApiOptions.None)); - await Assert.ThrowsAsync(() => client.GetAll("owner", "repo", null)); - await Assert.ThrowsAsync(() => client.GetAll(null, "repo", ApiOptions.None)); - await Assert.ThrowsAsync(() => client.GetAll("", "repo")); await Assert.ThrowsAsync(() => client.GetAll("owner", "")); - - await Assert.ThrowsAsync(() => client.GetAll("owner", "repo", ApiOptions.None)); } } diff --git a/Octokit.Tests/Reactive/ObservableRepositorySecretsClientTests.cs b/Octokit.Tests/Reactive/ObservableRepositorySecretsClientTests.cs index 30cfb08734..ba64d4384c 100644 --- a/Octokit.Tests/Reactive/ObservableRepositorySecretsClientTests.cs +++ b/Octokit.Tests/Reactive/ObservableRepositorySecretsClientTests.cs @@ -65,10 +65,6 @@ public async Task EnsuresNonNullArguments() await Assert.ThrowsAsync(() => client.GetAll(null, "repo").ToTask()); await Assert.ThrowsAsync(() => client.GetAll("owner", null).ToTask()); - await Assert.ThrowsAsync(() => client.GetAll("owner", null, ApiOptions.None).ToTask()); - await Assert.ThrowsAsync(() => client.GetAll("owner", "repo", null).ToTask()); - await Assert.ThrowsAsync(() => client.GetAll(null, "repo", ApiOptions.None).ToTask()); - await Assert.ThrowsAsync(() => client.GetAll("", "repo").ToTask()); await Assert.ThrowsAsync(() => client.GetAll("owner", "").ToTask()); } From 4b43db6ef36c22c790c684a2062a3bdc4fd29cc4 Mon Sep 17 00:00:00 2001 From: Mike Tolly Date: Tue, 30 Jun 2020 11:43:02 -0400 Subject: [PATCH 16/56] created organization secret client and classes to support it --- Octokit/Clients/IOrganizationSecretsClient.cs | 108 ++++++++++- Octokit/Clients/OrganizationSecretsClient.cs | 177 +++++++++++++++++- Octokit/Clients/RepositorySecretsClient.cs | 8 +- Octokit/Helpers/ApiUrls.cs | 62 +++++- .../Request/SelectedRepositoryCollection.cs | 32 ++++ .../Request/UpsertOrganizationSecret.cs | 38 ++++ Octokit/Models/Response/OrganizationSecret.cs | 39 ++++ .../OrganizationSecretRepositoryCollection.cs | 40 ++++ .../Response/OrganizationSecretsCollection.cs | 38 ++++ .../Response/RepositorySecretsCollection.cs | 38 ++++ ...ecretsPublicKey.cs => SecretsPublicKey.cs} | 6 +- 11 files changed, 573 insertions(+), 13 deletions(-) create mode 100644 Octokit/Models/Request/SelectedRepositoryCollection.cs create mode 100644 Octokit/Models/Request/UpsertOrganizationSecret.cs create mode 100644 Octokit/Models/Response/OrganizationSecret.cs create mode 100644 Octokit/Models/Response/OrganizationSecretRepositoryCollection.cs create mode 100644 Octokit/Models/Response/OrganizationSecretsCollection.cs create mode 100644 Octokit/Models/Response/RepositorySecretsCollection.cs rename Octokit/Models/Response/{RepositorySecretsPublicKey.cs => SecretsPublicKey.cs} (85%) diff --git a/Octokit/Clients/IOrganizationSecretsClient.cs b/Octokit/Clients/IOrganizationSecretsClient.cs index 0763a7d9a9..4145892ccc 100644 --- a/Octokit/Clients/IOrganizationSecretsClient.cs +++ b/Octokit/Clients/IOrganizationSecretsClient.cs @@ -1,6 +1,4 @@ -using System; -using System.Collections.Generic; -using System.Text; +using System.Threading.Tasks; namespace Octokit { @@ -12,5 +10,109 @@ namespace Octokit /// public interface IOrganizationSecretsClient { + /// + /// Get the public signing key to encrypt secrets for an organization. + /// + /// + /// See the API documentation for more information. + /// + /// The name of the organization + /// Thrown when a general API error occurs. + /// A instance for the organization public key. + Task GetPublicKey(string org); + + /// + /// List the secrets for an organization. + /// + /// + /// See the API documentation for more information. + /// + /// The name of the organization + /// Thrown when a general API error occurs. + /// A instance for the list of organization secrets. + Task GetAll(string org); + + /// + /// Get a secret from an organization. + /// + /// + /// See the API documentation for more information. + /// + /// The name of the organization + /// The name of the secret + /// Thrown when a general API error occurs. + /// A instance for the organization secret. + Task Get(string org, string secretName); + + /// + /// Create or update a secret in an organization. + /// + /// + /// See the API documentation for more information. + /// + /// The name of the organization + /// The name of the secret + /// The encrypted value, id of the encryption key, and visibility info to upsert + /// Thrown when a general API error occurs. + /// A instance for the organization secret that was created or updated. + Task CreateOrUpdate(string org, string secretName, UpsertOrganizationSecret upsertSecret); + + /// + /// Delete a secret in an organization. + /// + /// + /// See the API documentation for more information. + /// + /// The name of the organization + /// The name of the secret + /// Thrown when a general API error occurs. + Task Delete(string org, string secretName); + + /// + /// Get the list of selected sites that have access to a secret. + /// + /// + /// See the API documentation for more information. + /// + /// The name of the organization + /// The name of the secret + /// Thrown when a general API error occurs. + Task GetSelectedRepositoriesForSecret(string org, string secretName); + + /// + /// Set the list of selected sites that have access to a secret. + /// + /// + /// See the API documentation for more information. + /// + /// The name of the organization + /// The name of the secret + /// The list of repositories that should have access to view and use the secret + /// Thrown when a general API error occurs. + Task SetSelectedRepositoriesForSecret(string org, string secretName, SelectedRepositoryCollection repositories); + + /// + /// Add a selected site to the visibility list of a secret. + /// + /// + /// See the API documentation for more information. + /// + /// The name of the organization + /// The name of the secret + /// The id of the repo to add to the visibility list of the secret + /// Thrown when a general API error occurs. + Task AddRepoToOrganiztionSecret(string org, string secretName, long repoId); + + /// + /// ARemoved a selected site from the visibility list of a secret. + /// + /// + /// See the API documentation for more information. + /// + /// The name of the organization + /// The name of the secret + /// The id of the repo to add to the visibility list of the secret + /// Thrown when a general API error occurs. + Task RemoveRepoFromOrganizationSecret(string org, string secretName, long repoId); } } diff --git a/Octokit/Clients/OrganizationSecretsClient.cs b/Octokit/Clients/OrganizationSecretsClient.cs index 1cb5a1260b..beafafc5e8 100644 --- a/Octokit/Clients/OrganizationSecretsClient.cs +++ b/Octokit/Clients/OrganizationSecretsClient.cs @@ -1,13 +1,188 @@ using System; using System.Collections.Generic; using System.Text; +using System.Threading.Tasks; namespace Octokit { + /// + /// A client for GitHub's Organization Secrets API. + /// + /// + /// See the Organization Secrets API documentation for more details. + /// public class OrganizationSecretsClient : ApiClient, IOrganizationSecretsClient { - public OrganizationSecretsClient(IApiConnection apiConnection) : base(apiConnection) + public OrganizationSecretsClient(IApiConnection apiConnection) : base(apiConnection) { } + + /// + /// Get the public signing key to encrypt secrets for an organization. + /// + /// + /// See the API documentation for more information. + /// + /// The name of the organization + /// Thrown when a general API error occurs. + /// A instance for the organization public key. + [ManualRoute("GET", "/orgs/{org}/actions/secrets/public-key")] + public Task GetPublicKey(string org) + { + Ensure.ArgumentNotNullOrEmptyString(org, nameof(org)); + + return ApiConnection.Get(ApiUrls.OrganizationRepositorySecretPublicKey(org)); + } + + /// + /// List the secrets for an organization. + /// + /// + /// See the API documentation for more information. + /// + /// The name of the organization + /// Thrown when a general API error occurs. + /// A instance for the list of organization secrets. + [ManualRoute("GET", "/orgs/{org}/actions/secrets")] + public Task GetAll(string org) + { + Ensure.ArgumentNotNullOrEmptyString(org, nameof(org)); + + return ApiConnection.Get(ApiUrls.OrganizationRepositorySecrets(org)); + } + + /// + /// Get a secret from an organization. + /// + /// + /// See the API documentation for more information. + /// + /// The name of the organization + /// The name of the secret + /// Thrown when a general API error occurs. + /// A instance for the organization secret. + [ManualRoute("GET", "/orgs/{org}/actions/secrets/{secretName}")] + public Task Get(string org, string secretName) + { + Ensure.ArgumentNotNullOrEmptyString(org, nameof(org)); + Ensure.ArgumentNotNullOrEmptyString(secretName, nameof(secretName)); + + return ApiConnection.Get(ApiUrls.OrganizationRepositorySecret(org, secretName)); + } + + /// + /// Create or update a secret in an organization. + /// + /// + /// See the API documentation for more information. + /// + /// The name of the organization + /// The name of the secret + /// The encrypted value, id of the encryption key, and visibility info to upsert + /// Thrown when a general API error occurs. + /// A instance for the organization secret that was created or updated. + [ManualRoute("PUT", "/orgs/{org}/actions/secrets/{secretName}")] + public Task CreateOrUpdate(string org, string secretName, UpsertOrganizationSecret upsertSecret) + { + Ensure.ArgumentNotNullOrEmptyString(org, nameof(org)); + Ensure.ArgumentNotNullOrEmptyString(secretName, nameof(secretName)); + Ensure.ArgumentNotNull(upsertSecret, nameof(upsertSecret)); + + return ApiConnection.Put(ApiUrls.OrganizationRepositorySecret(org, secretName), upsertSecret); + } + + /// + /// Delete a secret in an organization. + /// + /// + /// See the API documentation for more information. + /// + /// The name of the organization + /// The name of the secret + /// Thrown when a general API error occurs. + [ManualRoute("DELETE", "/orgs/{org}/actions/secrets/{secretName}")] + public Task Delete(string org, string secretName) { + Ensure.ArgumentNotNullOrEmptyString(org, nameof(org)); + Ensure.ArgumentNotNullOrEmptyString(secretName, nameof(secretName)); + + return ApiConnection.Delete(ApiUrls.OrganizationRepositorySecret(org, secretName)); + } + + /// + /// Get the list of selected sites that have access to a secret. + /// + /// + /// See the API documentation for more information. + /// + /// The name of the organization + /// The name of the secret + /// Thrown when a general API error occurs. + [ManualRoute("GET", "/orgs/{org}/actions/secrets/{secretName}/repositories")] + public Task GetSelectedRepositoriesForSecret(string org, string secretName) + { + Ensure.ArgumentNotNullOrEmptyString(org, nameof(org)); + Ensure.ArgumentNotNullOrEmptyString(secretName, nameof(secretName)); + + return ApiConnection.Get(ApiUrls.OrganizationRepositorySecretRepositories(org, secretName)); + } + + /// + /// Set the list of selected sites that have access to a secret. + /// + /// + /// See the API documentation for more information. + /// + /// The name of the organization + /// The name of the secret + /// The list of repositories that should have access to view and use the secret + /// Thrown when a general API error occurs. + [ManualRoute("PUT", "/orgs/{org}/actions/secrets/{secretName}/repositories")] + public Task SetSelectedRepositoriesForSecret(string org, string secretName, SelectedRepositoryCollection repositories) + { + Ensure.ArgumentNotNullOrEmptyString(org, nameof(org)); + Ensure.ArgumentNotNullOrEmptyString(secretName, nameof(secretName)); + Ensure.ArgumentNotNull(repositories, nameof(repositories)); + + return ApiConnection.Put(ApiUrls.OrganizationRepositorySecretRepositories(org, secretName)); + } + + /// + /// Add a selected site to the visibility list of a secret. + /// + /// + /// See the API documentation for more information. + /// + /// The name of the organization + /// The name of the secret + /// The id of the repo to add to the visibility list of the secret + /// Thrown when a general API error occurs. + [ManualRoute("PUT", "/orgs/{org}/actions/secrets/{secretName}/{repoId}")] + public Task AddRepoToOrganiztionSecret(string org, string secretName, long repoId) + { + Ensure.ArgumentNotNullOrEmptyString(org, nameof(org)); + Ensure.ArgumentNotNullOrEmptyString(secretName, nameof(secretName)); + Ensure.ArgumentNotNull(repoId, nameof(repoId)); + + return ApiConnection.Put(ApiUrls.OrganizationRepositorySecretRepository(org, secretName, repoId)); + } + + /// + /// ARemoved a selected site from the visibility list of a secret. + /// + /// + /// See the API documentation for more information. + /// + /// The name of the organization + /// The name of the secret + /// The id of the repo to add to the visibility list of the secret + /// Thrown when a general API error occurs. + [ManualRoute("DELETE", "/orgs/{org}/actions/secrets/{secretName}/{repoId}")] + public Task RemoveRepoFromOrganizationSecret(string org, string secretName, long repoId) + { + Ensure.ArgumentNotNullOrEmptyString(org, nameof(org)); + Ensure.ArgumentNotNullOrEmptyString(secretName, nameof(secretName)); + Ensure.ArgumentNotNull(repoId, nameof(repoId)); + + return ApiConnection.Delete(ApiUrls.OrganizationRepositorySecretRepository(org, secretName, repoId)); } } } diff --git a/Octokit/Clients/RepositorySecretsClient.cs b/Octokit/Clients/RepositorySecretsClient.cs index 95c521e04d..9ef1827d19 100644 --- a/Octokit/Clients/RepositorySecretsClient.cs +++ b/Octokit/Clients/RepositorySecretsClient.cs @@ -52,7 +52,7 @@ public Task GetAll(string owner, string repoName) Ensure.ArgumentNotNullOrEmptyString(owner, nameof(owner)); Ensure.ArgumentNotNullOrEmptyString(repoName, nameof(repoName)); - var url = ApiUrls.RepositorySecretsList(owner, repoName); + var url = ApiUrls.RepositorySecrets(owner, repoName); return ApiConnection.Get(url); } @@ -75,7 +75,7 @@ public Task Get(string owner, string repoName, string secretNa Ensure.ArgumentNotNullOrEmptyString(repoName, nameof(repoName)); Ensure.ArgumentNotNullOrEmptyString(secretName, nameof(secretName)); - var url = ApiUrls.RepositorySecrets(owner, repoName, secretName); + var url = ApiUrls.RepositorySecret(owner, repoName, secretName); return ApiConnection.Get(url); } @@ -102,7 +102,7 @@ public async Task CreateOrUpdate(string owner, string repoName Ensure.ArgumentNotNullOrEmptyString(upsertSecret.EncryptedValue, nameof(upsertSecret.EncryptedValue)); Ensure.ArgumentNotNullOrEmptyString(upsertSecret.EncryptionKeyId, nameof(upsertSecret.EncryptionKeyId)); - var url = ApiUrls.RepositorySecrets(owner, repoName, secretName); + var url = ApiUrls.RepositorySecret(owner, repoName, secretName); return await ApiConnection.Put(url, upsertSecret); } @@ -124,7 +124,7 @@ public Task Delete(string owner, string repoName, string secretName) Ensure.ArgumentNotNullOrEmptyString(repoName, nameof(repoName)); Ensure.ArgumentNotNullOrEmptyString(secretName, nameof(secretName)); - var url = ApiUrls.RepositorySecrets(owner, repoName, secretName); + var url = ApiUrls.RepositorySecret(owner, repoName, secretName); return ApiConnection.Delete(url); } diff --git a/Octokit/Helpers/ApiUrls.cs b/Octokit/Helpers/ApiUrls.cs index ef0cb3b687..554caaf336 100644 --- a/Octokit/Helpers/ApiUrls.cs +++ b/Octokit/Helpers/ApiUrls.cs @@ -69,6 +69,64 @@ public static Uri OrganizationRepositories(string organization) return "orgs/{0}/repos".FormatUri(organization); } + /// + /// Returns the that returns all of the secrets for the specified organization in + /// response to a GET request. + /// + /// The name of the organization + /// + public static Uri OrganizationRepositorySecrets(string organization) + { + return "orgs/{0}/actions/secrets".FormatUri(organization); + } + + /// + /// Returns the that returns a secret for the specified organization in + /// response to a GET request. A POST to this URL creates a new secret for the organization. + /// + /// The name of the organization + /// The name of the secret + /// + public static Uri OrganizationRepositorySecret(string organization, string secret) + { + return "orgs/{0}/actions/secrets/{1}".FormatUri(organization,secret); + } + + /// + /// Returns the that returns the public key for signing secrets for the specified organization in + /// response to a GET request. + /// + /// The name of the organization + /// The name of the secret + /// + public static Uri OrganizationRepositorySecretPublicKey(string organization) + { + return "orgs/{0}/actions/secrets/public-key".FormatUri(organization); + } + + /// + /// Returns the that returns a list of repositories for a secret for the specified organization in + /// response to a GET request. A POST to this URL sets the full repository list for a secret in the organization. + /// + /// The name of the organization + /// The name of the secret + /// + public static Uri OrganizationRepositorySecretRepositories(string organization, string secret) + { + return "orgs/{0}/actions/secrets/{1}/repositories".FormatUri(organization, secret); + } + + /// + /// Returns the that adds (PUT) or removes (DELETE) a repository from the visibility list of a secret. + /// + /// The name of the organization + /// The name of the secret + /// + public static Uri OrganizationRepositorySecretRepository(string organization, string secret, long repoId) + { + return "orgs/{0}/actions/secrets/{1}/repositories/{2}".FormatUri(organization, secret, repoId.ToString()); + } + /// /// Returns the that returns all of the organizations for the currently logged in user. /// @@ -4173,7 +4231,7 @@ public static Uri CheckSuitePreferences(string owner, string repo) /// The name of the repo /// The name of the secret /// The that handles the repository secrets for the repository - public static Uri RepositorySecrets(string owner, string repo, string secret) + public static Uri RepositorySecret(string owner, string repo, string secret) { return "repos/{0}/{1}/actions/secrets/{2}".FormatUri(owner, repo, secret); } @@ -4184,7 +4242,7 @@ public static Uri RepositorySecrets(string owner, string repo, string secret) /// The owner of the repo /// The name of the repo /// The that handles the repository secrets for the repository - public static Uri RepositorySecretsList(string owner, string repo) + public static Uri RepositorySecrets(string owner, string repo) { return "repos/{0}/{1}/actions/secrets".FormatUri(owner, repo); } diff --git a/Octokit/Models/Request/SelectedRepositoryCollection.cs b/Octokit/Models/Request/SelectedRepositoryCollection.cs new file mode 100644 index 0000000000..bf11200a5c --- /dev/null +++ b/Octokit/Models/Request/SelectedRepositoryCollection.cs @@ -0,0 +1,32 @@ +using Octokit.Internal; +using System.Collections.Generic; +using System.Diagnostics; +using System.Globalization; +using System.Linq; + +namespace Octokit +{ + /// + /// Represents request to set the repositories with visibility to the secrets in an organization. + /// + [DebuggerDisplay("{DebuggerDisplay,nq}")] + public class SelectedRepositoryCollection + { + public SelectedRepositoryCollection() + { + } + + public SelectedRepositoryCollection(IEnumerable selectedRepositoryIds) + { + SelectedRepositoryIds = selectedRepositoryIds; + } + + /// + /// List of repository Ids that should have visibility to the repository + /// + [Parameter(Key = "selected_repository_ids")] + public IEnumerable SelectedRepositoryIds { get; set; } + + internal string DebuggerDisplay => string.Format(CultureInfo.CurrentCulture, "SelectedRepositoryCollection: Count: {0}", SelectedRepositoryIds.Count()); + } +} diff --git a/Octokit/Models/Request/UpsertOrganizationSecret.cs b/Octokit/Models/Request/UpsertOrganizationSecret.cs new file mode 100644 index 0000000000..cc25167833 --- /dev/null +++ b/Octokit/Models/Request/UpsertOrganizationSecret.cs @@ -0,0 +1,38 @@ +using Octokit.Internal; +using System.Collections.Generic; +using System.Diagnostics; +using System.Globalization; + +namespace Octokit +{ + /// + /// Represents request to change the value of a secret for an organization. + /// + [DebuggerDisplay("{DebuggerDisplay,nq}")] + public class UpsertOrganizationSecret : UpsertRepositorySecret + { + public UpsertOrganizationSecret() { } + + public UpsertOrganizationSecret(string encryptedValue, string encryptionKeyId, string visibility, IEnumerable selectedRepositoriesIds) + { + EncryptedValue = encryptedValue; + EncryptionKeyId = encryptionKeyId; + Visibility = visibility; + SelectedRepositoriesIds = selectedRepositoriesIds; + } + + /// + /// The visibility level of the secret + /// + [Parameter(Key = "visibility")] + public string Visibility { get; set; } + + /// + /// The list of ids for the repositories with selected visibility to the secret + /// + [Parameter(Key = "selected_repository_ids")] + public IEnumerable SelectedRepositoriesIds { get; set; } + + internal new string DebuggerDisplay => string.Format(CultureInfo.CurrentCulture, "UpsertOrganizationSecret: Key ID: {0}", EncryptionKeyId); + } +} diff --git a/Octokit/Models/Response/OrganizationSecret.cs b/Octokit/Models/Response/OrganizationSecret.cs new file mode 100644 index 0000000000..958c72eefd --- /dev/null +++ b/Octokit/Models/Response/OrganizationSecret.cs @@ -0,0 +1,39 @@ +using Octokit.Internal; +using System; +using System.Collections.Generic; +using System.Diagnostics; +using System.Globalization; +using System.Text; + +namespace Octokit +{ + /// + /// Represents an organization secret. + /// Does not contain the secret value + /// + [DebuggerDisplay("{DebuggerDisplay,nq}")] + public class OrganizationSecret : RepositorySecret + { + public OrganizationSecret() { } + + public OrganizationSecret(string name, DateTime createdAt, DateTime updatedAt, string visibility, string selectedRepositoriesUrl) + { + Name = name; + CreatedAt = createdAt; + UpdatedAt = updatedAt; + Visibility = visibility; + SelectedRepositoriesUrl = selectedRepositoriesUrl; + } + + /// + /// The visibility level of the secret within the organization + /// + public string Visibility { get; } + + /// + /// The URL to retrieve the list of selected repositories + /// + [Parameter(Key = "selected_repositories_url")] + public string SelectedRepositoriesUrl { get; } + } +} diff --git a/Octokit/Models/Response/OrganizationSecretRepositoryCollection.cs b/Octokit/Models/Response/OrganizationSecretRepositoryCollection.cs new file mode 100644 index 0000000000..ff1e48b452 --- /dev/null +++ b/Octokit/Models/Response/OrganizationSecretRepositoryCollection.cs @@ -0,0 +1,40 @@ +using Octokit.Internal; +using System; +using System.Collections.Generic; +using System.Diagnostics; +using System.Globalization; +using System.Text; + +namespace Octokit +{ + /// + /// Represents response of the repositories for a secret in an organization. + /// + [DebuggerDisplay("{DebuggerDisplay,nq}")] + public class OrganizationSecretRepositoryCollection + { + public OrganizationSecretRepositoryCollection() + { + } + + public OrganizationSecretRepositoryCollection(int count, IReadOnlyList repositories) + { + Count = count; + Repositories = repositories; + } + + /// + /// The total count of repositories with visibility to the secret in the organization + /// + [Parameter(Key = "total_count")] + public int Count { get; } + + /// + /// The list of repositories with visibility to the secret in the organization + /// + [Parameter(Key = "repositories")] + public IReadOnlyList Repositories { get; } + + internal string DebuggerDisplay => string.Format(CultureInfo.CurrentCulture, "OrganizationSecretRepositoryCollection: Count: {0}", Count); + } +} diff --git a/Octokit/Models/Response/OrganizationSecretsCollection.cs b/Octokit/Models/Response/OrganizationSecretsCollection.cs new file mode 100644 index 0000000000..cd8e207bc5 --- /dev/null +++ b/Octokit/Models/Response/OrganizationSecretsCollection.cs @@ -0,0 +1,38 @@ +using Octokit.Internal; +using System.Collections.Generic; +using System.Diagnostics; +using System.Globalization; + +namespace Octokit +{ + /// + /// Represents response of secrets for an organization. + /// + [DebuggerDisplay("{DebuggerDisplay,nq}")] + public class OrganizationSecretsCollection + { + public OrganizationSecretsCollection() + { + } + + public OrganizationSecretsCollection(int count, IReadOnlyList secrets) + { + Count = count; + Secrets = secrets; + } + + /// + /// The total count of secrets for the organization + /// + [Parameter(Key = "total_count")] + public int Count { get; } + + /// + /// The list of secrets for the organization + /// + [Parameter(Key = "secrets")] + public IReadOnlyList Secrets { get; } + + internal string DebuggerDisplay => string.Format(CultureInfo.CurrentCulture, "OrganizationSecretCollection: Count: {0}", Count); + } +} diff --git a/Octokit/Models/Response/RepositorySecretsCollection.cs b/Octokit/Models/Response/RepositorySecretsCollection.cs new file mode 100644 index 0000000000..d2b31286ae --- /dev/null +++ b/Octokit/Models/Response/RepositorySecretsCollection.cs @@ -0,0 +1,38 @@ +using Octokit.Internal; +using System.Collections.Generic; +using System.Diagnostics; +using System.Globalization; + +namespace Octokit +{ + /// + /// Represents response of secrets for a repository. + /// + [DebuggerDisplay("{DebuggerDisplay,nq}")] + public class RepositorySecretsCollection + { + public RepositorySecretsCollection() + { + } + + public RepositorySecretsCollection(int count, IReadOnlyList secrets) + { + Count = count; + Secrets = secrets; + } + + /// + /// The total count of secrets for the repository + /// + [Parameter(Key = "total_count")] + public int Count { get; } + + /// + /// The list of secrets for the repository + /// + [Parameter(Key = "secrets")] + public IReadOnlyList Secrets { get; } + + internal string DebuggerDisplay => string.Format(CultureInfo.CurrentCulture, "RepositorySecretsCollection: Count: {0}", Count); + } +} diff --git a/Octokit/Models/Response/RepositorySecretsPublicKey.cs b/Octokit/Models/Response/SecretsPublicKey.cs similarity index 85% rename from Octokit/Models/Response/RepositorySecretsPublicKey.cs rename to Octokit/Models/Response/SecretsPublicKey.cs index 66d663ddef..2be67c130e 100644 --- a/Octokit/Models/Response/RepositorySecretsPublicKey.cs +++ b/Octokit/Models/Response/SecretsPublicKey.cs @@ -7,14 +7,14 @@ namespace Octokit /// Represents the public key used to sign the secrets to post to GitHub /// [DebuggerDisplay("{DebuggerDisplay,nq}")] - public class RepositorySecretsPublicKey + public class SecretsPublicKey { - public RepositorySecretsPublicKey() + public SecretsPublicKey() { } - public RepositorySecretsPublicKey(int keyId, string key) + public SecretsPublicKey(int keyId, string key) { KeyId = keyId; Key = key; From 788cf252d80903625c7d407a00e93c1749585ecb Mon Sep 17 00:00:00 2001 From: Mike Tolly Date: Tue, 30 Jun 2020 12:45:09 -0400 Subject: [PATCH 17/56] created the observable org secrets client and fixed a typo in a method name --- .../IObservableOrganizationActionsClient.cs | 23 +++ .../IObservableOrganizationSecretsClient.cs | 119 +++++++++++ .../Clients/IObservableOrganizationsClient.cs | 5 + .../ObservableOrganizationActionsClient.cs | 40 ++++ .../ObservableOrganizationSecretsClient.cs | 191 ++++++++++++++++++ .../Clients/ObservableOrganizationsClient.cs | 7 + Octokit/Clients/IOrganizationSecretsClient.cs | 2 +- Octokit/Clients/OrganizationSecretsClient.cs | 2 +- 8 files changed, 387 insertions(+), 2 deletions(-) create mode 100644 Octokit.Reactive/Clients/IObservableOrganizationActionsClient.cs create mode 100644 Octokit.Reactive/Clients/IObservableOrganizationSecretsClient.cs create mode 100644 Octokit.Reactive/Clients/ObservableOrganizationActionsClient.cs create mode 100644 Octokit.Reactive/Clients/ObservableOrganizationSecretsClient.cs diff --git a/Octokit.Reactive/Clients/IObservableOrganizationActionsClient.cs b/Octokit.Reactive/Clients/IObservableOrganizationActionsClient.cs new file mode 100644 index 0000000000..d4a8c63426 --- /dev/null +++ b/Octokit.Reactive/Clients/IObservableOrganizationActionsClient.cs @@ -0,0 +1,23 @@ +using System; +using System.Collections.Generic; +using System.Text; + +namespace Octokit.Reactive +{ + /// + /// A client for GitHub's Org Actions API. + /// + /// + /// See the Actions API documentation for more information. + /// + public interface IObservableOrganizationActionsClient + { + /// + /// Returns a client to manage organization secrets. + /// + /// + /// See the Secrets API documentation for more information. + /// + IObservableOrganizationSecretsClient Secrets { get; } + } +} diff --git a/Octokit.Reactive/Clients/IObservableOrganizationSecretsClient.cs b/Octokit.Reactive/Clients/IObservableOrganizationSecretsClient.cs new file mode 100644 index 0000000000..dbd1f70448 --- /dev/null +++ b/Octokit.Reactive/Clients/IObservableOrganizationSecretsClient.cs @@ -0,0 +1,119 @@ +using System; +using System.Reactive; + +namespace Octokit.Reactive +{ + /// + /// A client for GitHub's Organization Secrets API. + /// + /// + /// See the Organization Secrets API documentation for more details. + /// + public interface IObservableOrganizationSecretsClient + { + /// + /// Get the public signing key to encrypt secrets for an organization. + /// + /// + /// See the API documentation for more information. + /// + /// The name of the organization + /// Thrown when a general API error occurs. + /// A instance for the organization public key. + IObservable GetPublicKey(string org); + + /// + /// List the secrets for an organization. + /// + /// + /// See the API documentation for more information. + /// + /// The name of the organization + /// Thrown when a general API error occurs. + /// A instance for the list of organization secrets. + IObservable GetAll(string org); + + /// + /// Get a secret from an organization. + /// + /// + /// See the API documentation for more information. + /// + /// The name of the organization + /// The name of the secret + /// Thrown when a general API error occurs. + /// A instance for the organization secret. + IObservable Get(string org, string secretName); + + /// + /// Create or update a secret in an organization. + /// + /// + /// See the API documentation for more information. + /// + /// The name of the organization + /// The name of the secret + /// The encrypted value, id of the encryption key, and visibility info to upsert + /// Thrown when a general API error occurs. + /// A instance for the organization secret that was created or updated. + IObservable CreateOrUpdate(string org, string secretName, UpsertOrganizationSecret upsertSecret); + + /// + /// Delete a secret in an organization. + /// + /// + /// See the API documentation for more information. + /// + /// The name of the organization + /// The name of the secret + /// Thrown when a general API error occurs. + IObservable Delete(string org, string secretName); + + /// + /// Get the list of selected sites that have access to a secret. + /// + /// + /// See the API documentation for more information. + /// + /// The name of the organization + /// The name of the secret + /// Thrown when a general API error occurs. + IObservable GetSelectedRepositoriesForSecret(string org, string secretName); + + /// + /// Set the list of selected sites that have access to a secret. + /// + /// + /// See the API documentation for more information. + /// + /// The name of the organization + /// The name of the secret + /// The list of repositories that should have access to view and use the secret + /// Thrown when a general API error occurs. + IObservable SetSelectedRepositoriesForSecret(string org, string secretName, SelectedRepositoryCollection repositories); + + /// + /// Add a selected site to the visibility list of a secret. + /// + /// + /// See the API documentation for more information. + /// + /// The name of the organization + /// The name of the secret + /// The id of the repo to add to the visibility list of the secret + /// Thrown when a general API error occurs. + IObservable AddRepoToOrganizationSecret(string org, string secretName, long repoId); + + /// + /// ARemoved a selected site from the visibility list of a secret. + /// + /// + /// See the API documentation for more information. + /// + /// The name of the organization + /// The name of the secret + /// The id of the repo to add to the visibility list of the secret + /// Thrown when a general API error occurs. + IObservable RemoveRepoFromOrganizationSecret(string org, string secretName, long repoId); + } +} diff --git a/Octokit.Reactive/Clients/IObservableOrganizationsClient.cs b/Octokit.Reactive/Clients/IObservableOrganizationsClient.cs index 793b17846e..3f7b16a262 100644 --- a/Octokit.Reactive/Clients/IObservableOrganizationsClient.cs +++ b/Octokit.Reactive/Clients/IObservableOrganizationsClient.cs @@ -26,6 +26,11 @@ public interface IObservableOrganizationsClient /// IObservableOrganizationOutsideCollaboratorsClient OutsideCollaborator { get; } + /// + /// Returns a client to manage organization actions. + /// + IObservableOrganizationActionsClient Actions { get; } + /// /// Returns the specified organization. /// diff --git a/Octokit.Reactive/Clients/ObservableOrganizationActionsClient.cs b/Octokit.Reactive/Clients/ObservableOrganizationActionsClient.cs new file mode 100644 index 0000000000..e17c84c53a --- /dev/null +++ b/Octokit.Reactive/Clients/ObservableOrganizationActionsClient.cs @@ -0,0 +1,40 @@ +using System; +using System.Collections.Generic; +using System.Text; + +namespace Octokit.Reactive +{ + /// + /// A client for GitHub's Org Actions API. + /// + /// + /// See the Actions API documentation for more information. + /// + public class ObservableOrganizationActionsClient : IObservableOrganizationActionsClient + { + readonly IOrganizationActionsClient _client; + readonly IConnection _connection; + + /// + /// Initializes a new Organization API client. + /// + /// An used to make the requests + public ObservableOrganizationActionsClient(IGitHubClient client) + { + Ensure.ArgumentNotNull(client, nameof(client)); + + Secrets = new ObservableOrganizationSecretsClient(client); + + _client = client.Organization.Actions; + _connection = client.Connection; + } + + /// + /// Returns a client to manage organization secrets. + /// + /// + /// See the Secrets API documentation for more information. + /// + public IObservableOrganizationSecretsClient Secrets { get; private set; } + } +} diff --git a/Octokit.Reactive/Clients/ObservableOrganizationSecretsClient.cs b/Octokit.Reactive/Clients/ObservableOrganizationSecretsClient.cs new file mode 100644 index 0000000000..fb7478732e --- /dev/null +++ b/Octokit.Reactive/Clients/ObservableOrganizationSecretsClient.cs @@ -0,0 +1,191 @@ +using System; +using System.Reactive; +using System.Reactive.Threading.Tasks; + +namespace Octokit.Reactive +{ + /// + /// A client for GitHub's Organization Secrets API. + /// + /// + /// See the Organization Secrets API documentation for more details. + /// + public class ObservableOrganizationSecretsClient: IObservableOrganizationSecretsClient + { + readonly IOrganizationSecretsClient _client; + readonly IConnection _connection; + + /// + /// Initializes a new Organization API client. + /// + /// An used to make the requests + public ObservableOrganizationSecretsClient(IGitHubClient client) + { + Ensure.ArgumentNotNull(client, nameof(client)); + + _client = client.Organization.Actions.Secrets; + _connection = client.Connection; + } + + /// + /// Get the public signing key to encrypt secrets for an organization. + /// + /// + /// See the API documentation for more information. + /// + /// The name of the organization + /// Thrown when a general API error occurs. + /// A instance for the organization public key. + public IObservable GetPublicKey(string org) + { + Ensure.ArgumentNotNullOrEmptyString(org, nameof(org)); + + return _client.GetPublicKey(org).ToObservable(); + } + + /// + /// List the secrets for an organization. + /// + /// + /// See the API documentation for more information. + /// + /// The name of the organization + /// Thrown when a general API error occurs. + /// A instance for the list of organization secrets. + public IObservable GetAll(string org) + { + Ensure.ArgumentNotNullOrEmptyString(org, nameof(org)); + + return _client.GetAll(org).ToObservable(); + } + + /// + /// Get a secret from an organization. + /// + /// + /// See the API documentation for more information. + /// + /// The name of the organization + /// The name of the secret + /// Thrown when a general API error occurs. + /// A instance for the organization secret. + public IObservable Get(string org, string secretName) + { + Ensure.ArgumentNotNullOrEmptyString(org, nameof(org)); + Ensure.ArgumentNotNullOrEmptyString(secretName, nameof(secretName)); + + return _client.Get(org, secretName).ToObservable(); + } + + /// + /// Create or update a secret in an organization. + /// + /// + /// See the API documentation for more information. + /// + /// The name of the organization + /// The name of the secret + /// The encrypted value, id of the encryption key, and visibility info to upsert + /// Thrown when a general API error occurs. + /// A instance for the organization secret that was created or updated. + public IObservable CreateOrUpdate(string org, string secretName, UpsertOrganizationSecret upsertSecret) + { + Ensure.ArgumentNotNullOrEmptyString(org, nameof(org)); + Ensure.ArgumentNotNullOrEmptyString(secretName, nameof(secretName)); + Ensure.ArgumentNotNull(upsertSecret, nameof(upsertSecret)); + + return _client.CreateOrUpdate(org, secretName, upsertSecret).ToObservable(); + } + + /// + /// Delete a secret in an organization. + /// + /// + /// See the API documentation for more information. + /// + /// The name of the organization + /// The name of the secret + /// Thrown when a general API error occurs. + public IObservable Delete(string org, string secretName) + { + Ensure.ArgumentNotNullOrEmptyString(org, nameof(org)); + Ensure.ArgumentNotNullOrEmptyString(secretName, nameof(secretName)); + + return _client.Delete(org, secretName).ToObservable(); + } + + /// + /// Get the list of selected sites that have access to a secret. + /// + /// + /// See the API documentation for more information. + /// + /// The name of the organization + /// The name of the secret + /// Thrown when a general API error occurs. + public IObservable GetSelectedRepositoriesForSecret(string org, string secretName) + { + Ensure.ArgumentNotNullOrEmptyString(org, nameof(org)); + Ensure.ArgumentNotNullOrEmptyString(secretName, nameof(secretName)); + + return _client.GetSelectedRepositoriesForSecret(org, secretName).ToObservable(); + } + + /// + /// Set the list of selected sites that have access to a secret. + /// + /// + /// See the API documentation for more information. + /// + /// The name of the organization + /// The name of the secret + /// The list of repositories that should have access to view and use the secret + /// Thrown when a general API error occurs. + public IObservable SetSelectedRepositoriesForSecret(string org, string secretName, SelectedRepositoryCollection repositories) + { + Ensure.ArgumentNotNullOrEmptyString(org, nameof(org)); + Ensure.ArgumentNotNullOrEmptyString(secretName, nameof(secretName)); + Ensure.ArgumentNotNull(repositories, nameof(repositories)); + + return _client.SetSelectedRepositoriesForSecret(org, secretName, repositories).ToObservable(); + } + + /// + /// Add a selected site to the visibility list of a secret. + /// + /// + /// See the API documentation for more information. + /// + /// The name of the organization + /// The name of the secret + /// The id of the repo to add to the visibility list of the secret + /// Thrown when a general API error occurs. + public IObservable AddRepoToOrganizationSecret(string org, string secretName, long repoId) + { + Ensure.ArgumentNotNullOrEmptyString(org, nameof(org)); + Ensure.ArgumentNotNullOrEmptyString(secretName, nameof(secretName)); + Ensure.ArgumentNotNull(repoId, nameof(repoId)); + + return _client.AddRepoToOrganizationSecret(org, secretName, repoId).ToObservable(); + } + + /// + /// ARemoved a selected site from the visibility list of a secret. + /// + /// + /// See the API documentation for more information. + /// + /// The name of the organization + /// The name of the secret + /// The id of the repo to add to the visibility list of the secret + /// Thrown when a general API error occurs. + public IObservable RemoveRepoFromOrganizationSecret(string org, string secretName, long repoId) + { + Ensure.ArgumentNotNullOrEmptyString(org, nameof(org)); + Ensure.ArgumentNotNullOrEmptyString(secretName, nameof(secretName)); + Ensure.ArgumentNotNull(repoId, nameof(repoId)); + + return _client.RemoveRepoFromOrganizationSecret(org, secretName, repoId).ToObservable(); + } + } +} diff --git a/Octokit.Reactive/Clients/ObservableOrganizationsClient.cs b/Octokit.Reactive/Clients/ObservableOrganizationsClient.cs index ec816645e8..0a6e1a3eaa 100644 --- a/Octokit.Reactive/Clients/ObservableOrganizationsClient.cs +++ b/Octokit.Reactive/Clients/ObservableOrganizationsClient.cs @@ -1,4 +1,5 @@ using System; +using System.Reactive.Linq; using System.Reactive.Threading.Tasks; using Octokit.Reactive.Internal; @@ -21,6 +22,7 @@ public ObservableOrganizationsClient(IGitHubClient client) Team = new ObservableTeamsClient(client); Hook = new ObservableOrganizationHooksClient(client); OutsideCollaborator = new ObservableOrganizationOutsideCollaboratorsClient(client); + Actions = new ObservableOrganizationActionsClient(client); _client = client.Organization; _connection = client.Connection; @@ -47,6 +49,11 @@ public ObservableOrganizationsClient(IGitHubClient client) /// public IObservableOrganizationOutsideCollaboratorsClient OutsideCollaborator { get; private set; } + /// + /// Returns a client to manage organization actions. + /// + public IObservableOrganizationActionsClient Actions { get; private set; } + /// /// Returns the specified organization. /// diff --git a/Octokit/Clients/IOrganizationSecretsClient.cs b/Octokit/Clients/IOrganizationSecretsClient.cs index 4145892ccc..082d61a306 100644 --- a/Octokit/Clients/IOrganizationSecretsClient.cs +++ b/Octokit/Clients/IOrganizationSecretsClient.cs @@ -101,7 +101,7 @@ public interface IOrganizationSecretsClient /// The name of the secret /// The id of the repo to add to the visibility list of the secret /// Thrown when a general API error occurs. - Task AddRepoToOrganiztionSecret(string org, string secretName, long repoId); + Task AddRepoToOrganizationSecret(string org, string secretName, long repoId); /// /// ARemoved a selected site from the visibility list of a secret. diff --git a/Octokit/Clients/OrganizationSecretsClient.cs b/Octokit/Clients/OrganizationSecretsClient.cs index beafafc5e8..ccfba2a956 100644 --- a/Octokit/Clients/OrganizationSecretsClient.cs +++ b/Octokit/Clients/OrganizationSecretsClient.cs @@ -156,7 +156,7 @@ public Task SetSelectedRepositoriesForSecret(string org, string secretName, Sele /// The id of the repo to add to the visibility list of the secret /// Thrown when a general API error occurs. [ManualRoute("PUT", "/orgs/{org}/actions/secrets/{secretName}/{repoId}")] - public Task AddRepoToOrganiztionSecret(string org, string secretName, long repoId) + public Task AddRepoToOrganizationSecret(string org, string secretName, long repoId) { Ensure.ArgumentNotNullOrEmptyString(org, nameof(org)); Ensure.ArgumentNotNullOrEmptyString(secretName, nameof(secretName)); From b1b0f2bc8c5aab38e719951e07731326b1e2389a Mon Sep 17 00:00:00 2001 From: Mike Tolly Date: Tue, 30 Jun 2020 13:11:07 -0400 Subject: [PATCH 18/56] added more ensure checks --- Octokit/Clients/OrganizationSecretsClient.cs | 5 ++++- 1 file changed, 4 insertions(+), 1 deletion(-) diff --git a/Octokit/Clients/OrganizationSecretsClient.cs b/Octokit/Clients/OrganizationSecretsClient.cs index ccfba2a956..9942f7bfa9 100644 --- a/Octokit/Clients/OrganizationSecretsClient.cs +++ b/Octokit/Clients/OrganizationSecretsClient.cs @@ -83,8 +83,11 @@ public Task Get(string org, string secretName) public Task CreateOrUpdate(string org, string secretName, UpsertOrganizationSecret upsertSecret) { Ensure.ArgumentNotNullOrEmptyString(org, nameof(org)); - Ensure.ArgumentNotNullOrEmptyString(secretName, nameof(secretName)); + Ensure.ArgumentNotNullOrEmptyString(secretName, nameof(secretName)); Ensure.ArgumentNotNull(upsertSecret, nameof(upsertSecret)); + Ensure.ArgumentNotNullOrEmptyString(upsertSecret.EncryptionKeyId, nameof(upsertSecret.EncryptionKeyId)); + Ensure.ArgumentNotNullOrEmptyString(upsertSecret.EncryptedValue, nameof(upsertSecret.EncryptedValue)); + Ensure.ArgumentNotNullOrEmptyString(upsertSecret.Visibility, nameof(upsertSecret.Visibility)); return ApiConnection.Put(ApiUrls.OrganizationRepositorySecret(org, secretName), upsertSecret); } From 900ede11cd3027cf9e5a995034ba3727de8177e6 Mon Sep 17 00:00:00 2001 From: Mike Tolly Date: Tue, 30 Jun 2020 13:11:42 -0400 Subject: [PATCH 19/56] removed unused xml doc setting --- Octokit/Helpers/ApiUrls.cs | 1 - 1 file changed, 1 deletion(-) diff --git a/Octokit/Helpers/ApiUrls.cs b/Octokit/Helpers/ApiUrls.cs index 554caaf336..844e757c73 100644 --- a/Octokit/Helpers/ApiUrls.cs +++ b/Octokit/Helpers/ApiUrls.cs @@ -97,7 +97,6 @@ public static Uri OrganizationRepositorySecret(string organization, string secre /// response to a GET request. /// /// The name of the organization - /// The name of the secret /// public static Uri OrganizationRepositorySecretPublicKey(string organization) { From c0bce5e37076199d00562a28729f482dc2f4da0f Mon Sep 17 00:00:00 2001 From: Mike Tolly Date: Tue, 30 Jun 2020 14:31:30 -0400 Subject: [PATCH 20/56] created the unit tests for the organization secrets client fixed broken unit test for repository secrets client --- .../ObservableOrganizationSecretsClient.cs | 2 +- .../Clients/OrganizationActionsClientTests.cs | 17 ++ .../Clients/OrganizationSecretsClientTests.cs | 286 ++++++++++++++++++ .../Clients/RepositorySecretsClientTests.cs | 2 +- Octokit/Clients/OrganizationSecretsClient.cs | 3 +- 5 files changed, 307 insertions(+), 3 deletions(-) create mode 100644 Octokit.Tests/Clients/OrganizationActionsClientTests.cs create mode 100644 Octokit.Tests/Clients/OrganizationSecretsClientTests.cs diff --git a/Octokit.Reactive/Clients/ObservableOrganizationSecretsClient.cs b/Octokit.Reactive/Clients/ObservableOrganizationSecretsClient.cs index fb7478732e..92c5a6a947 100644 --- a/Octokit.Reactive/Clients/ObservableOrganizationSecretsClient.cs +++ b/Octokit.Reactive/Clients/ObservableOrganizationSecretsClient.cs @@ -10,7 +10,7 @@ namespace Octokit.Reactive /// /// See the Organization Secrets API documentation for more details. /// - public class ObservableOrganizationSecretsClient: IObservableOrganizationSecretsClient + public class ObservableOrganizationSecretsClient : IObservableOrganizationSecretsClient { readonly IOrganizationSecretsClient _client; readonly IConnection _connection; diff --git a/Octokit.Tests/Clients/OrganizationActionsClientTests.cs b/Octokit.Tests/Clients/OrganizationActionsClientTests.cs new file mode 100644 index 0000000000..8ac1ef66a5 --- /dev/null +++ b/Octokit.Tests/Clients/OrganizationActionsClientTests.cs @@ -0,0 +1,17 @@ +using System; +using Xunit; + +namespace Octokit.Tests.Clients +{ + public class OrganizationActionsClientTests + { + public class TheCtor + { + [Fact] + public void EnsuresNonNullArguments() + { + Assert.Throws(() => new OrganizationActionsClient(null)); + } + } + } +} \ No newline at end of file diff --git a/Octokit.Tests/Clients/OrganizationSecretsClientTests.cs b/Octokit.Tests/Clients/OrganizationSecretsClientTests.cs new file mode 100644 index 0000000000..cf5af3c852 --- /dev/null +++ b/Octokit.Tests/Clients/OrganizationSecretsClientTests.cs @@ -0,0 +1,286 @@ +using NSubstitute; +using System; +using System.Collections.Generic; +using System.Linq; +using System.Text; +using System.Threading.Tasks; +using Xunit; + +namespace Octokit.Tests.Clients +{ + public class OrganizationSecretsClientTests + { + public class TheCtor + { + [Fact] + public void EnsuresNonNullArguments() + { + Assert.Throws(() => new OrganizationSecretsClient(null)); + } + } + + public class GetPublicKeyMethod + { + [Fact] + public async Task RequestsTheCorrectUrl() + { + var connection = Substitute.For(); + var client = new OrganizationSecretsClient(connection); + + await client.GetPublicKey("org"); + + connection.Received() + .Get(Arg.Is(u => u.ToString() == "orgs/org/actions/secrets/public-key")); + } + + [Fact] + public async Task EnsuresNonNullArguments() + { + var client = new OrganizationSecretsClient(Substitute.For()); + + await Assert.ThrowsAsync(() => client.GetPublicKey(null)); + await Assert.ThrowsAsync(() => client.GetPublicKey("")); + } + } + + public class GetAllMethod + { + [Fact] + public async Task RequestsTheCorrectUrl() + { + var connection = Substitute.For(); + var client = new OrganizationSecretsClient(connection); + + await client.GetAll("org"); + + connection.Received() + .Get(Arg.Is(u => u.ToString() == "orgs/org/actions/secrets")); + } + + [Fact] + public async Task EnsuresNonNullArguments() + { + var client = new OrganizationSecretsClient(Substitute.For()); + + await Assert.ThrowsAsync(() => client.GetAll(null)); + await Assert.ThrowsAsync(() => client.GetAll("")); + } + } + + public class GetMethod + { + [Fact] + public async Task RequestsTheCorrectUrl() + { + var connection = Substitute.For(); + var client = new OrganizationSecretsClient(connection); + + await client.Get("org", "secret"); + + connection.Received() + .Get(Arg.Is(u => u.ToString() == "orgs/org/actions/secrets/secret")); + } + + [Fact] + public async Task EnsuresNonNullArguments() + { + var client = new OrganizationSecretsClient(Substitute.For()); + + await Assert.ThrowsAsync(() => client.Get(null, "secret")); + await Assert.ThrowsAsync(() => client.Get("org", null)); + + await Assert.ThrowsAsync(() => client.Get("", "secret")); + await Assert.ThrowsAsync(() => client.Get("org", "")); + } + } + + public class CreateOrUpdateMethod + { + [Fact] + public async Task PostsTheCorrectUrl() + { + var connection = Substitute.For(); + var client = new OrganizationSecretsClient(connection); + var upsertSecret = new UpsertOrganizationSecret + { + EncryptedValue = "encryptedValue", + EncryptionKeyId = "keyId", + Visibility = "private" + }; + await client.CreateOrUpdate("org", "secret", upsertSecret); + + connection.Received() + .Put(Arg.Is(u => u.ToString() == "orgs/org/actions/secrets/secret"), upsertSecret); + } + + [Fact] + public async Task EnsuresNonNullArguments() + { + var client = new OrganizationSecretsClient(Substitute.For()); + + var upsertSecret = new UpsertOrganizationSecret + { + EncryptedValue = "encryptedValue", + EncryptionKeyId = "keyId" + }; + + await Assert.ThrowsAsync(() => client.CreateOrUpdate(null, "secret", upsertSecret)); + await Assert.ThrowsAsync(() => client.CreateOrUpdate("owner", null, upsertSecret)); + await Assert.ThrowsAsync(() => client.CreateOrUpdate("owner", "secret", null)); + await Assert.ThrowsAsync(() => client.CreateOrUpdate("owner", "secret", new UpsertOrganizationSecret())); + + await Assert.ThrowsAsync(() => client.CreateOrUpdate("", "secret", upsertSecret)); + await Assert.ThrowsAsync(() => client.CreateOrUpdate("owner", "", upsertSecret)); + } + } + + public class DeleteMethod + { + [Fact] + public async Task DeletesTheCorrectUrl() + { + var connection = Substitute.For(); + var client = new OrganizationSecretsClient(connection); + + await client.Delete("org", "secret"); + + connection.Received() + .Delete(Arg.Is(u => u.ToString() == "orgs/org/actions/secrets/secret")); + } + + [Fact] + public async Task EnsuresNonNullArguments() + { + var client = new OrganizationSecretsClient(Substitute.For()); + + await Assert.ThrowsAsync(() => client.Delete(null, "secret")); + await Assert.ThrowsAsync(() => client.Delete("owner", null)); + + await Assert.ThrowsAsync(() => client.Delete("", "secret")); + await Assert.ThrowsAsync(() => client.Delete("owner", "")); + } + } + + public class GetSelectedRepositoriesForSecretMethod + { + [Fact] + public async Task RequestsTheCorrectUrl() + { + var connection = Substitute.For(); + var client = new OrganizationSecretsClient(connection); + + await client.GetSelectedRepositoriesForSecret("org", "secret"); + + connection.Received() + .Get(Arg.Is(u => u.ToString() == "orgs/org/actions/secrets/secret/repositories")); + } + + [Fact] + public async Task EnsuresNonNullArguments() + { + var client = new OrganizationSecretsClient(Substitute.For()); + + await Assert.ThrowsAsync(() => client.GetSelectedRepositoriesForSecret(null, "secret")); + await Assert.ThrowsAsync(() => client.GetSelectedRepositoriesForSecret("org", null)); + await Assert.ThrowsAsync(() => client.GetSelectedRepositoriesForSecret("", "secret")); + await Assert.ThrowsAsync(() => client.GetSelectedRepositoriesForSecret("org", "")); + } + } + + public class SetSelectedRepositoriesForSecretMethod + { + [Fact] + public async Task RequestsTheCorrectUrl() + { + var connection = Substitute.For(); + var client = new OrganizationSecretsClient(connection); + + var repoIds = new List + { + 1, + 2, + 3 + }; + var repos = new SelectedRepositoryCollection(repoIds); + + await client.SetSelectedRepositoriesForSecret("org", "secret", repos); + + connection.Received() + .Put(Arg.Is(u => u.ToString() == "orgs/org/actions/secrets/secret/repositories")); + } + + [Fact] + public async Task EnsuresNonNullArguments() + { + var client = new OrganizationSecretsClient(Substitute.For()); + + var repoIds = new List + { + 1, + 2, + 3 + }; + var repos = new SelectedRepositoryCollection(repoIds); + + await Assert.ThrowsAsync(() => client.SetSelectedRepositoriesForSecret(null, "secret", repos)); + await Assert.ThrowsAsync(() => client.SetSelectedRepositoriesForSecret("org", null, repos)); + await Assert.ThrowsAsync(() => client.SetSelectedRepositoriesForSecret("org", "secret", null)); + await Assert.ThrowsAsync(() => client.SetSelectedRepositoriesForSecret("org", "secret", new SelectedRepositoryCollection())); + await Assert.ThrowsAsync(() => client.SetSelectedRepositoriesForSecret("", "secret", repos)); + await Assert.ThrowsAsync(() => client.SetSelectedRepositoriesForSecret("org", "", repos)); + } + } + + public class AddRepoToOrganizationSecretMethod + { + [Fact] + public async Task RequestsTheCorrectUrl() + { + var connection = Substitute.For(); + var client = new OrganizationSecretsClient(connection); + + await client.AddRepoToOrganizationSecret("org", "secret", 1); + + connection.Received() + .Put(Arg.Is(u => u.ToString() == "orgs/org/actions/secrets/secret/repositories/1")); + } + + [Fact] + public async Task EnsuresNonNullArguments() + { + var client = new OrganizationSecretsClient(Substitute.For()); + + await Assert.ThrowsAsync(() => client.AddRepoToOrganizationSecret(null, "secret", 1)); + await Assert.ThrowsAsync(() => client.AddRepoToOrganizationSecret("org", null, 1)); + await Assert.ThrowsAsync(() => client.AddRepoToOrganizationSecret("", "secret", 1)); + await Assert.ThrowsAsync(() => client.AddRepoToOrganizationSecret("org", "", 1)); + } + } + + public class RemoveRepoFromOrganizationSecretMethod + { + [Fact] + public async Task RequestsTheCorrectUrl() + { + var connection = Substitute.For(); + var client = new OrganizationSecretsClient(connection); + + await client.RemoveRepoFromOrganizationSecret("org", "secret", 1); + + connection.Received() + .Delete(Arg.Is(u => u.ToString() == "orgs/org/actions/secrets/secret/repositories/1")); + } + + [Fact] + public async Task EnsuresNonNullArguments() + { + var client = new OrganizationSecretsClient(Substitute.For()); + + await Assert.ThrowsAsync(() => client.RemoveRepoFromOrganizationSecret(null, "secret", 1)); + await Assert.ThrowsAsync(() => client.RemoveRepoFromOrganizationSecret("org", null, 1)); + await Assert.ThrowsAsync(() => client.RemoveRepoFromOrganizationSecret("", "secret", 1)); + await Assert.ThrowsAsync(() => client.RemoveRepoFromOrganizationSecret("org", "", 1)); + } + } + } +} diff --git a/Octokit.Tests/Clients/RepositorySecretsClientTests.cs b/Octokit.Tests/Clients/RepositorySecretsClientTests.cs index b448cb31f8..80c7c8097a 100644 --- a/Octokit.Tests/Clients/RepositorySecretsClientTests.cs +++ b/Octokit.Tests/Clients/RepositorySecretsClientTests.cs @@ -53,7 +53,7 @@ public async Task RequestsTheCorrectUrl() await client.GetAll("owner", "repo"); connection.Received() - .GetAll(Arg.Is(u => u.ToString() == "repos/owner/repo/actions/secrets")); + .Get(Arg.Is(u => u.ToString() == "repos/owner/repo/actions/secrets")); } [Fact] diff --git a/Octokit/Clients/OrganizationSecretsClient.cs b/Octokit/Clients/OrganizationSecretsClient.cs index 9942f7bfa9..bf13baa089 100644 --- a/Octokit/Clients/OrganizationSecretsClient.cs +++ b/Octokit/Clients/OrganizationSecretsClient.cs @@ -83,7 +83,7 @@ public Task Get(string org, string secretName) public Task CreateOrUpdate(string org, string secretName, UpsertOrganizationSecret upsertSecret) { Ensure.ArgumentNotNullOrEmptyString(org, nameof(org)); - Ensure.ArgumentNotNullOrEmptyString(secretName, nameof(secretName)); + Ensure.ArgumentNotNullOrEmptyString(secretName, nameof(secretName)); Ensure.ArgumentNotNull(upsertSecret, nameof(upsertSecret)); Ensure.ArgumentNotNullOrEmptyString(upsertSecret.EncryptionKeyId, nameof(upsertSecret.EncryptionKeyId)); Ensure.ArgumentNotNullOrEmptyString(upsertSecret.EncryptedValue, nameof(upsertSecret.EncryptedValue)); @@ -144,6 +144,7 @@ public Task SetSelectedRepositoriesForSecret(string org, string secretName, Sele Ensure.ArgumentNotNullOrEmptyString(org, nameof(org)); Ensure.ArgumentNotNullOrEmptyString(secretName, nameof(secretName)); Ensure.ArgumentNotNull(repositories, nameof(repositories)); + Ensure.ArgumentNotNull(repositories.SelectedRepositoryIds, nameof(repositories.SelectedRepositoryIds)); return ApiConnection.Put(ApiUrls.OrganizationRepositorySecretRepositories(org, secretName)); } From 6938225c92b9e2d8f2676c105aaceca3d94f84e6 Mon Sep 17 00:00:00 2001 From: Mike Tolly Date: Wed, 1 Jul 2020 11:31:12 -0400 Subject: [PATCH 21/56] created observable organization actions and secrets client unit tests --- .../ObservableOrganizationSecretsClient.cs | 2 + ...bservableOrganizationActionsClientTests.cs | 20 ++ ...bservableOrganizationSecretsClientTests.cs | 282 ++++++++++++++++++ 3 files changed, 304 insertions(+) create mode 100644 Octokit.Tests/Reactive/ObservableOrganizationActionsClientTests.cs create mode 100644 Octokit.Tests/Reactive/ObservableOrganizationSecretsClientTests.cs diff --git a/Octokit.Reactive/Clients/ObservableOrganizationSecretsClient.cs b/Octokit.Reactive/Clients/ObservableOrganizationSecretsClient.cs index 92c5a6a947..3f74fbe933 100644 --- a/Octokit.Reactive/Clients/ObservableOrganizationSecretsClient.cs +++ b/Octokit.Reactive/Clients/ObservableOrganizationSecretsClient.cs @@ -93,6 +93,8 @@ public IObservable CreateOrUpdate(string org, string secretN Ensure.ArgumentNotNullOrEmptyString(org, nameof(org)); Ensure.ArgumentNotNullOrEmptyString(secretName, nameof(secretName)); Ensure.ArgumentNotNull(upsertSecret, nameof(upsertSecret)); + Ensure.ArgumentNotNull(upsertSecret.EncryptedValue, nameof(upsertSecret.EncryptedValue)); + Ensure.ArgumentNotNull(upsertSecret.EncryptionKeyId, nameof(upsertSecret.EncryptionKeyId)); return _client.CreateOrUpdate(org, secretName, upsertSecret).ToObservable(); } diff --git a/Octokit.Tests/Reactive/ObservableOrganizationActionsClientTests.cs b/Octokit.Tests/Reactive/ObservableOrganizationActionsClientTests.cs new file mode 100644 index 0000000000..1476c76b4f --- /dev/null +++ b/Octokit.Tests/Reactive/ObservableOrganizationActionsClientTests.cs @@ -0,0 +1,20 @@ +using Octokit.Reactive; +using System; +using System.Collections.Generic; +using System.Text; +using Xunit; + +namespace Octokit.Tests.Reactive +{ + public class ObservableOrganizationActionsClientTests + { + public class TheCtor + { + [Fact] + public void EnsuresNonNullArguments() + { + Assert.Throws(() => new ObservableOrganizationActionsClient(null)); + } + } + } +} diff --git a/Octokit.Tests/Reactive/ObservableOrganizationSecretsClientTests.cs b/Octokit.Tests/Reactive/ObservableOrganizationSecretsClientTests.cs new file mode 100644 index 0000000000..92fabd061e --- /dev/null +++ b/Octokit.Tests/Reactive/ObservableOrganizationSecretsClientTests.cs @@ -0,0 +1,282 @@ +using NSubstitute; +using Octokit.Reactive; +using System; +using System.Collections.Generic; +using System.Reactive.Linq; +using System.Reactive.Threading.Tasks; +using System.Threading.Tasks; +using Xunit; + +namespace Octokit.Tests.Reactive +{ + public class ObservableOrganizationSecretsClientTests + { + public class TheCtor + { + [Fact] + public void EnsuresNonNullArguments() + { + Assert.Throws(() => new ObservableOrganizationSecretsClient(null)); + } + } + + public class GetPublicKeyMethod + { + [Fact] + public async Task RequestsTheCorrectUrl() + { + var gitHubClient = Substitute.For(); + var client = new ObservableOrganizationSecretsClient(gitHubClient); + + await client.GetPublicKey("org"); + + gitHubClient.Received().Organization.Actions.Secrets.GetPublicKey("org"); + } + + [Fact] + public async Task EnsuresNonNullArguments() + { + var client = new ObservableOrganizationSecretsClient(Substitute.For()); + + await Assert.ThrowsAsync(() => client.GetPublicKey(null).ToTask()); + await Assert.ThrowsAsync(() => client.GetPublicKey("").ToTask()); + } + } + + public class GetAllMethod + { + [Fact] + public async Task RequestsTheCorrectUrl() + { + var gitHubClient = Substitute.For(); + var client = new ObservableOrganizationSecretsClient(gitHubClient); + + await client.GetAll("org"); + + gitHubClient.Received().Organization.Actions.Secrets.GetAll("org"); + } + + [Fact] + public async Task EnsuresNonNullArguments() + { + var client = new ObservableOrganizationSecretsClient(Substitute.For()); + + await Assert.ThrowsAsync(() => client.GetAll(null).ToTask()); + await Assert.ThrowsAsync(() => client.GetAll("").ToTask()); + } + } + + public class GetMethod + { + [Fact] + public async Task RequestsTheCorrectUrl() + { + var gitHubClient = Substitute.For(); + var client = new ObservableOrganizationSecretsClient(gitHubClient); + + await client.Get("org", "secret"); + + gitHubClient.Received().Organization.Actions.Secrets.Get("org", "secret"); + } + + [Fact] + public async Task EnsuresNonNullArguments() + { + var client = new ObservableOrganizationSecretsClient(Substitute.For()); + + await Assert.ThrowsAsync(() => client.Get(null, "secret").ToTask()); + await Assert.ThrowsAsync(() => client.Get("org", null).ToTask()); + + await Assert.ThrowsAsync(() => client.Get("", "secret").ToTask()); + await Assert.ThrowsAsync(() => client.Get("org", "").ToTask()); + } + } + + public class CreateOrUpdateMethod + { + [Fact] + public async Task PostsTheCorrectUrl() + { + var gitHubClient = Substitute.For(); + var client = new ObservableOrganizationSecretsClient(gitHubClient); + var upsertSecret = new UpsertOrganizationSecret + { + EncryptedValue = "encryptedValue", + EncryptionKeyId = "keyId", + Visibility = "private" + }; + + await client.CreateOrUpdate("org", "secret", upsertSecret); + + gitHubClient.Received().Organization.Actions.Secrets.CreateOrUpdate("org", "secret", upsertSecret); + } + + [Fact] + public async Task EnsuresNonNullArguments() + { + var client = new ObservableOrganizationSecretsClient(Substitute.For()); + + var upsertSecret = new UpsertOrganizationSecret + { + EncryptedValue = "encryptedValue", + EncryptionKeyId = "keyId" + }; + + await Assert.ThrowsAsync(() => client.CreateOrUpdate(null, "secret", upsertSecret).ToTask()); + await Assert.ThrowsAsync(() => client.CreateOrUpdate("owner", null, upsertSecret).ToTask()); + await Assert.ThrowsAsync(() => client.CreateOrUpdate("owner", "secret", null).ToTask()); + await Assert.ThrowsAsync(() => client.CreateOrUpdate("owner", "secret", new UpsertOrganizationSecret()).ToTask()); + + await Assert.ThrowsAsync(() => client.CreateOrUpdate("", "secret", upsertSecret).ToTask()); + await Assert.ThrowsAsync(() => client.CreateOrUpdate("owner", "", upsertSecret).ToTask()); + } + } + + public class DeleteMethod + { + [Fact] + public async Task DeletesTheCorrectUrl() + { + var gitHubClient = Substitute.For(); + var client = new ObservableOrganizationSecretsClient(gitHubClient); + + await client.Delete("org", "secret"); + + gitHubClient.Received().Organization.Actions.Secrets.Delete("org", "secret"); + } + + [Fact] + public async Task EnsuresNonNullArguments() + { + var client = new ObservableOrganizationSecretsClient(Substitute.For()); + + await Assert.ThrowsAsync(() => client.Delete(null, "secret").ToTask()); + await Assert.ThrowsAsync(() => client.Delete("owner", null).ToTask()); + + await Assert.ThrowsAsync(() => client.Delete("", "secret").ToTask()); + await Assert.ThrowsAsync(() => client.Delete("owner", "").ToTask()); + } + } + + public class GetSelectedRepositoriesForSecretMethod + { + [Fact] + public async Task RequestsTheCorrectUrl() + { + var gitHubClient = Substitute.For(); + var client = new ObservableOrganizationSecretsClient(gitHubClient); + + await client.GetSelectedRepositoriesForSecret("org", "secret"); + + gitHubClient.Received().Organization.Actions.Secrets.GetSelectedRepositoriesForSecret("org", "secret"); + } + + [Fact] + public async Task EnsuresNonNullArguments() + { + var client = new ObservableOrganizationSecretsClient(Substitute.For()); + + await Assert.ThrowsAsync(() => client.GetSelectedRepositoriesForSecret(null, "secret").ToTask()); + await Assert.ThrowsAsync(() => client.GetSelectedRepositoriesForSecret("org", null).ToTask()); + await Assert.ThrowsAsync(() => client.GetSelectedRepositoriesForSecret("", "secret").ToTask()); + await Assert.ThrowsAsync(() => client.GetSelectedRepositoriesForSecret("org", "").ToTask()); + } + } + + public class SetSelectedRepositoriesForSecretMethod + { + [Fact] + public async Task RequestsTheCorrectUrl() + { + var connection = Substitute.For(); + var client = new OrganizationSecretsClient(connection); + + var repoIds = new List + { + 1, + 2, + 3 + }; + var repos = new SelectedRepositoryCollection(repoIds); + + await client.SetSelectedRepositoriesForSecret("org", "secret", repos); + + connection.Received() + .Put(Arg.Is(u => u.ToString() == "orgs/org/actions/secrets/secret/repositories")); + } + + [Fact] + public async Task EnsuresNonNullArguments() + { + var client = new OrganizationSecretsClient(Substitute.For()); + + var repoIds = new List + { + 1, + 2, + 3 + }; + var repos = new SelectedRepositoryCollection(repoIds); + + await Assert.ThrowsAsync(() => client.SetSelectedRepositoriesForSecret(null, "secret", repos)); + await Assert.ThrowsAsync(() => client.SetSelectedRepositoriesForSecret("org", null, repos)); + await Assert.ThrowsAsync(() => client.SetSelectedRepositoriesForSecret("org", "secret", null)); + await Assert.ThrowsAsync(() => client.SetSelectedRepositoriesForSecret("org", "secret", new SelectedRepositoryCollection())); + await Assert.ThrowsAsync(() => client.SetSelectedRepositoriesForSecret("", "secret", repos)); + await Assert.ThrowsAsync(() => client.SetSelectedRepositoriesForSecret("org", "", repos)); + } + } + + public class AddRepoToOrganizationSecretMethod + { + [Fact] + public async Task RequestsTheCorrectUrl() + { + var connection = Substitute.For(); + var client = new OrganizationSecretsClient(connection); + + await client.AddRepoToOrganizationSecret("org", "secret", 1); + + connection.Received() + .Put(Arg.Is(u => u.ToString() == "orgs/org/actions/secrets/secret/repositories/1")); + } + + [Fact] + public async Task EnsuresNonNullArguments() + { + var client = new OrganizationSecretsClient(Substitute.For()); + + await Assert.ThrowsAsync(() => client.AddRepoToOrganizationSecret(null, "secret", 1)); + await Assert.ThrowsAsync(() => client.AddRepoToOrganizationSecret("org", null, 1)); + await Assert.ThrowsAsync(() => client.AddRepoToOrganizationSecret("", "secret", 1)); + await Assert.ThrowsAsync(() => client.AddRepoToOrganizationSecret("org", "", 1)); + } + } + + public class RemoveRepoFromOrganizationSecretMethod + { + [Fact] + public async Task RequestsTheCorrectUrl() + { + var connection = Substitute.For(); + var client = new OrganizationSecretsClient(connection); + + await client.RemoveRepoFromOrganizationSecret("org", "secret", 1); + + connection.Received() + .Delete(Arg.Is(u => u.ToString() == "orgs/org/actions/secrets/secret/repositories/1")); + } + + [Fact] + public async Task EnsuresNonNullArguments() + { + var client = new OrganizationSecretsClient(Substitute.For()); + + await Assert.ThrowsAsync(() => client.RemoveRepoFromOrganizationSecret(null, "secret", 1)); + await Assert.ThrowsAsync(() => client.RemoveRepoFromOrganizationSecret("org", null, 1)); + await Assert.ThrowsAsync(() => client.RemoveRepoFromOrganizationSecret("", "secret", 1)); + await Assert.ThrowsAsync(() => client.RemoveRepoFromOrganizationSecret("org", "", 1)); + } + } + } +} From 90e180e2ee4c0c35c52959ea6f7f2fb96d0cd516 Mon Sep 17 00:00:00 2001 From: Mike Tolly Date: Wed, 1 Jul 2020 12:39:14 -0400 Subject: [PATCH 22/56] added sodium.core to the integration tests to test secret creation --- Octokit.Tests.Integration/Octokit.Tests.Integration.csproj | 5 ++++- 1 file changed, 4 insertions(+), 1 deletion(-) diff --git a/Octokit.Tests.Integration/Octokit.Tests.Integration.csproj b/Octokit.Tests.Integration/Octokit.Tests.Integration.csproj index d41b06d2ca..501d77020d 100644 --- a/Octokit.Tests.Integration/Octokit.Tests.Integration.csproj +++ b/Octokit.Tests.Integration/Octokit.Tests.Integration.csproj @@ -48,10 +48,13 @@ + + 1.2.3 + - + From 1f7a1f9111a15a91ab01274ec2876aee684f8714 Mon Sep 17 00:00:00 2001 From: Mike Tolly Date: Thu, 2 Jul 2020 10:47:34 -0400 Subject: [PATCH 23/56] fixed keyid type --- Octokit/Models/Response/SecretsPublicKey.cs | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/Octokit/Models/Response/SecretsPublicKey.cs b/Octokit/Models/Response/SecretsPublicKey.cs index 2be67c130e..aedd40a9d8 100644 --- a/Octokit/Models/Response/SecretsPublicKey.cs +++ b/Octokit/Models/Response/SecretsPublicKey.cs @@ -14,7 +14,7 @@ public SecretsPublicKey() } - public SecretsPublicKey(int keyId, string key) + public SecretsPublicKey(string keyId, string key) { KeyId = keyId; Key = key; @@ -23,7 +23,7 @@ public SecretsPublicKey(int keyId, string key) /// /// The id of this repository public key. Needed to create or update a secret /// - public int KeyId { get; protected set; } + public string KeyId { get; protected set; } /// /// The public key for this repository From bf504bbe56441230c2275ec303b72d840e8d6ae0 Mon Sep 17 00:00:00 2001 From: Mike Tolly Date: Mon, 6 Jul 2020 11:31:47 -0400 Subject: [PATCH 24/56] added actions client integration test classes (empty since the class currently doesn't have any native methods) --- .../Clients/OrganizationActionsClientTests.cs | 10 ++++++++++ .../Clients/RepositoryActionsClientTests.cs | 10 ++++++++++ .../ObservableOrganizationActionsClientTests.cs | 10 ++++++++++ .../Reactive/ObservableRepositoryActionsClientTests.cs | 10 ++++++++++ 4 files changed, 40 insertions(+) create mode 100644 Octokit.Tests.Integration/Clients/OrganizationActionsClientTests.cs create mode 100644 Octokit.Tests.Integration/Clients/RepositoryActionsClientTests.cs create mode 100644 Octokit.Tests.Integration/Reactive/ObservableOrganizationActionsClientTests.cs create mode 100644 Octokit.Tests.Integration/Reactive/ObservableRepositoryActionsClientTests.cs diff --git a/Octokit.Tests.Integration/Clients/OrganizationActionsClientTests.cs b/Octokit.Tests.Integration/Clients/OrganizationActionsClientTests.cs new file mode 100644 index 0000000000..20548d7b1f --- /dev/null +++ b/Octokit.Tests.Integration/Clients/OrganizationActionsClientTests.cs @@ -0,0 +1,10 @@ +using System; +using System.Collections.Generic; +using System.Text; + +namespace Octokit.Tests.Integration.Clients +{ + public class OrganizationActionsClientTests + { + } +} diff --git a/Octokit.Tests.Integration/Clients/RepositoryActionsClientTests.cs b/Octokit.Tests.Integration/Clients/RepositoryActionsClientTests.cs new file mode 100644 index 0000000000..95f60732d1 --- /dev/null +++ b/Octokit.Tests.Integration/Clients/RepositoryActionsClientTests.cs @@ -0,0 +1,10 @@ +using System; +using System.Collections.Generic; +using System.Text; + +namespace Octokit.Tests.Integration.Clients +{ + public class RepositoryActionsClientTests + { + } +} diff --git a/Octokit.Tests.Integration/Reactive/ObservableOrganizationActionsClientTests.cs b/Octokit.Tests.Integration/Reactive/ObservableOrganizationActionsClientTests.cs new file mode 100644 index 0000000000..e05a22c110 --- /dev/null +++ b/Octokit.Tests.Integration/Reactive/ObservableOrganizationActionsClientTests.cs @@ -0,0 +1,10 @@ +using System; +using System.Collections.Generic; +using System.Text; + +namespace Octokit.Tests.Integration.Reactive +{ + public class ObservableOrganizationActionsClientTests + { + } +} diff --git a/Octokit.Tests.Integration/Reactive/ObservableRepositoryActionsClientTests.cs b/Octokit.Tests.Integration/Reactive/ObservableRepositoryActionsClientTests.cs new file mode 100644 index 0000000000..3e2ca85d2e --- /dev/null +++ b/Octokit.Tests.Integration/Reactive/ObservableRepositoryActionsClientTests.cs @@ -0,0 +1,10 @@ +using System; +using System.Collections.Generic; +using System.Text; + +namespace Octokit.Tests.Integration.Reactive +{ + public class ObservableRepositoryActionsClientTests + { + } +} From 026fb7ce79a66b7ac9e5b61b9370e091e34d7969 Mon Sep 17 00:00:00 2001 From: Mike Tolly Date: Mon, 6 Jul 2020 13:45:13 -0400 Subject: [PATCH 25/56] fixed deserialization issue --- Octokit/Models/Response/OrganizationSecret.cs | 4 ++-- .../Response/OrganizationSecretRepositoryCollection.cs | 4 ++-- .../Models/Response/OrganizationSecretsCollection.cs | 4 ++-- Octokit/Models/Response/RepositorySecret.cs | 9 +++------ Octokit/Models/Response/RepositorySecretsCollection.cs | 10 ++++------ 5 files changed, 13 insertions(+), 18 deletions(-) diff --git a/Octokit/Models/Response/OrganizationSecret.cs b/Octokit/Models/Response/OrganizationSecret.cs index 958c72eefd..caf1133596 100644 --- a/Octokit/Models/Response/OrganizationSecret.cs +++ b/Octokit/Models/Response/OrganizationSecret.cs @@ -28,12 +28,12 @@ public OrganizationSecret(string name, DateTime createdAt, DateTime updatedAt, s /// /// The visibility level of the secret within the organization /// - public string Visibility { get; } + public string Visibility { get; protected set; } /// /// The URL to retrieve the list of selected repositories /// [Parameter(Key = "selected_repositories_url")] - public string SelectedRepositoriesUrl { get; } + public string SelectedRepositoriesUrl { get; protected set; } } } diff --git a/Octokit/Models/Response/OrganizationSecretRepositoryCollection.cs b/Octokit/Models/Response/OrganizationSecretRepositoryCollection.cs index ff1e48b452..4f600d053f 100644 --- a/Octokit/Models/Response/OrganizationSecretRepositoryCollection.cs +++ b/Octokit/Models/Response/OrganizationSecretRepositoryCollection.cs @@ -27,13 +27,13 @@ public OrganizationSecretRepositoryCollection(int count, IReadOnlyList [Parameter(Key = "total_count")] - public int Count { get; } + public int Count { get; protected set; } /// /// The list of repositories with visibility to the secret in the organization /// [Parameter(Key = "repositories")] - public IReadOnlyList Repositories { get; } + public IReadOnlyList Repositories { get; protected set; } internal string DebuggerDisplay => string.Format(CultureInfo.CurrentCulture, "OrganizationSecretRepositoryCollection: Count: {0}", Count); } diff --git a/Octokit/Models/Response/OrganizationSecretsCollection.cs b/Octokit/Models/Response/OrganizationSecretsCollection.cs index cd8e207bc5..0bcce45656 100644 --- a/Octokit/Models/Response/OrganizationSecretsCollection.cs +++ b/Octokit/Models/Response/OrganizationSecretsCollection.cs @@ -25,13 +25,13 @@ public OrganizationSecretsCollection(int count, IReadOnlyList [Parameter(Key = "total_count")] - public int Count { get; } + public int Count { get; protected set; } /// /// The list of secrets for the organization /// [Parameter(Key = "secrets")] - public IReadOnlyList Secrets { get; } + public IReadOnlyList Secrets { get; protected set; } internal string DebuggerDisplay => string.Format(CultureInfo.CurrentCulture, "OrganizationSecretCollection: Count: {0}", Count); } diff --git a/Octokit/Models/Response/RepositorySecret.cs b/Octokit/Models/Response/RepositorySecret.cs index 73deed285b..a0a8a639c5 100644 --- a/Octokit/Models/Response/RepositorySecret.cs +++ b/Octokit/Models/Response/RepositorySecret.cs @@ -17,7 +17,7 @@ public RepositorySecret() } - public RepositorySecret(string name, DateTime createdAt, DateTime updatedAt) + public RepositorySecret(string name, DateTimeOffset createdAt, DateTimeOffset? updatedAt) { Name = name; CreatedAt = createdAt; @@ -27,20 +27,17 @@ public RepositorySecret(string name, DateTime createdAt, DateTime updatedAt) /// /// The name of the repository secret /// - [Parameter(Key = "name")] public string Name { get; protected set; } /// /// The date and time that the secret was created /// - [Parameter(Key = "created_at")] - public DateTime CreatedAt { get; protected set; } + public DateTimeOffset CreatedAt { get; protected set; } /// /// The date and time the secret was last updated /// - [Parameter(Key = "updated_at")] - public DateTime UpdatedAt { get; protected set; } + public DateTimeOffset? UpdatedAt { get; protected set; } internal string DebuggerDisplay { diff --git a/Octokit/Models/Response/RepositorySecretsCollection.cs b/Octokit/Models/Response/RepositorySecretsCollection.cs index d2b31286ae..72186e64f6 100644 --- a/Octokit/Models/Response/RepositorySecretsCollection.cs +++ b/Octokit/Models/Response/RepositorySecretsCollection.cs @@ -17,22 +17,20 @@ public RepositorySecretsCollection() public RepositorySecretsCollection(int count, IReadOnlyList secrets) { - Count = count; + TotalCount = count; Secrets = secrets; } /// /// The total count of secrets for the repository /// - [Parameter(Key = "total_count")] - public int Count { get; } + public int TotalCount { get; protected set; } /// /// The list of secrets for the repository /// - [Parameter(Key = "secrets")] - public IReadOnlyList Secrets { get; } + public IReadOnlyList Secrets { get; protected set; } - internal string DebuggerDisplay => string.Format(CultureInfo.CurrentCulture, "RepositorySecretsCollection: Count: {0}", Count); + internal string DebuggerDisplay => string.Format(CultureInfo.CurrentCulture, "RepositorySecretsCollection: Count: {0}", TotalCount); } } From 8fa2ec9e709ff2f34604a05ff8fb99487e671040 Mon Sep 17 00:00:00 2001 From: Mike Tolly Date: Mon, 6 Jul 2020 16:44:31 -0400 Subject: [PATCH 26/56] changed property name for deserialization issues --- .../Clients/ObservableOrganizationSecretsClient.cs | 2 +- .../Clients/ObservableRepositorySecretsClient.cs | 2 +- Octokit.Tests/Clients/OrganizationSecretsClientTests.cs | 4 ++-- Octokit.Tests/Clients/RepositorySecretsClientTests.cs | 4 ++-- .../Reactive/ObservableOrganizationSecretsClientTests.cs | 4 ++-- .../Reactive/ObservableRepositorySecretsClientTests.cs | 4 ++-- Octokit/Clients/OrganizationSecretsClient.cs | 7 ++++--- Octokit/Clients/RepositorySecretsClient.cs | 6 ++++-- Octokit/Models/Request/UpsertOrganizationSecret.cs | 4 ++-- Octokit/Models/Request/UpsertRepositorySecret.cs | 4 ++-- 10 files changed, 22 insertions(+), 19 deletions(-) diff --git a/Octokit.Reactive/Clients/ObservableOrganizationSecretsClient.cs b/Octokit.Reactive/Clients/ObservableOrganizationSecretsClient.cs index 3f74fbe933..2ff755bb6f 100644 --- a/Octokit.Reactive/Clients/ObservableOrganizationSecretsClient.cs +++ b/Octokit.Reactive/Clients/ObservableOrganizationSecretsClient.cs @@ -94,7 +94,7 @@ public IObservable CreateOrUpdate(string org, string secretN Ensure.ArgumentNotNullOrEmptyString(secretName, nameof(secretName)); Ensure.ArgumentNotNull(upsertSecret, nameof(upsertSecret)); Ensure.ArgumentNotNull(upsertSecret.EncryptedValue, nameof(upsertSecret.EncryptedValue)); - Ensure.ArgumentNotNull(upsertSecret.EncryptionKeyId, nameof(upsertSecret.EncryptionKeyId)); + Ensure.ArgumentNotNull(upsertSecret.KeyId, nameof(upsertSecret.KeyId)); return _client.CreateOrUpdate(org, secretName, upsertSecret).ToObservable(); } diff --git a/Octokit.Reactive/Clients/ObservableRepositorySecretsClient.cs b/Octokit.Reactive/Clients/ObservableRepositorySecretsClient.cs index ef1b99f961..f5f0be65d3 100644 --- a/Octokit.Reactive/Clients/ObservableRepositorySecretsClient.cs +++ b/Octokit.Reactive/Clients/ObservableRepositorySecretsClient.cs @@ -101,7 +101,7 @@ public IObservable CreateOrUpdate(string owner, string repoNam Ensure.ArgumentNotNullOrEmptyString(secretName, nameof(secretName)); Ensure.ArgumentNotNull(upsertSecret, nameof(upsertSecret)); Ensure.ArgumentNotNullOrEmptyString(upsertSecret.EncryptedValue, nameof(upsertSecret.EncryptedValue)); - Ensure.ArgumentNotNullOrEmptyString(upsertSecret.EncryptionKeyId, nameof(upsertSecret.EncryptionKeyId)); + Ensure.ArgumentNotNullOrEmptyString(upsertSecret.KeyId, nameof(upsertSecret.KeyId)); return _client.CreateOrUpdate(owner, repoName, secretName, upsertSecret).ToObservable(); } diff --git a/Octokit.Tests/Clients/OrganizationSecretsClientTests.cs b/Octokit.Tests/Clients/OrganizationSecretsClientTests.cs index cf5af3c852..8f9ac2ef20 100644 --- a/Octokit.Tests/Clients/OrganizationSecretsClientTests.cs +++ b/Octokit.Tests/Clients/OrganizationSecretsClientTests.cs @@ -104,7 +104,7 @@ public async Task PostsTheCorrectUrl() var upsertSecret = new UpsertOrganizationSecret { EncryptedValue = "encryptedValue", - EncryptionKeyId = "keyId", + KeyId = "keyId", Visibility = "private" }; await client.CreateOrUpdate("org", "secret", upsertSecret); @@ -121,7 +121,7 @@ public async Task EnsuresNonNullArguments() var upsertSecret = new UpsertOrganizationSecret { EncryptedValue = "encryptedValue", - EncryptionKeyId = "keyId" + KeyId = "keyId" }; await Assert.ThrowsAsync(() => client.CreateOrUpdate(null, "secret", upsertSecret)); diff --git a/Octokit.Tests/Clients/RepositorySecretsClientTests.cs b/Octokit.Tests/Clients/RepositorySecretsClientTests.cs index 80c7c8097a..4e8accaed9 100644 --- a/Octokit.Tests/Clients/RepositorySecretsClientTests.cs +++ b/Octokit.Tests/Clients/RepositorySecretsClientTests.cs @@ -108,7 +108,7 @@ public async Task PostsTheCorrectUrl() var upsertSecret = new UpsertRepositorySecret { EncryptedValue = "encryptedValue", - EncryptionKeyId = "keyId" + KeyId = "keyId" }; await client.CreateOrUpdate("owner", "repo", "secret", upsertSecret); @@ -124,7 +124,7 @@ public async Task EnsuresNonNullArguments() var upsertSecret = new UpsertRepositorySecret { EncryptedValue = "encryptedValue", - EncryptionKeyId = "keyId" + KeyId = "keyId" }; await Assert.ThrowsAsync(() => client.CreateOrUpdate(null, "repo", "secret", upsertSecret)); diff --git a/Octokit.Tests/Reactive/ObservableOrganizationSecretsClientTests.cs b/Octokit.Tests/Reactive/ObservableOrganizationSecretsClientTests.cs index 92fabd061e..db90cced63 100644 --- a/Octokit.Tests/Reactive/ObservableOrganizationSecretsClientTests.cs +++ b/Octokit.Tests/Reactive/ObservableOrganizationSecretsClientTests.cs @@ -102,7 +102,7 @@ public async Task PostsTheCorrectUrl() var upsertSecret = new UpsertOrganizationSecret { EncryptedValue = "encryptedValue", - EncryptionKeyId = "keyId", + KeyId = "keyId", Visibility = "private" }; @@ -119,7 +119,7 @@ public async Task EnsuresNonNullArguments() var upsertSecret = new UpsertOrganizationSecret { EncryptedValue = "encryptedValue", - EncryptionKeyId = "keyId" + KeyId = "keyId" }; await Assert.ThrowsAsync(() => client.CreateOrUpdate(null, "secret", upsertSecret).ToTask()); diff --git a/Octokit.Tests/Reactive/ObservableRepositorySecretsClientTests.cs b/Octokit.Tests/Reactive/ObservableRepositorySecretsClientTests.cs index ba64d4384c..92a57e1c2b 100644 --- a/Octokit.Tests/Reactive/ObservableRepositorySecretsClientTests.cs +++ b/Octokit.Tests/Reactive/ObservableRepositorySecretsClientTests.cs @@ -108,7 +108,7 @@ public async Task PostsTheCorrectUrl() var upsert = new UpsertRepositorySecret { EncryptedValue = "encryptedValue", - EncryptionKeyId = "keyId" + KeyId = "keyId" }; await client.CreateOrUpdate("owner", "repo", "secret", upsert); @@ -124,7 +124,7 @@ public async Task EnsuresNonNullArguments() var upsertSecret = new UpsertRepositorySecret { EncryptedValue = "encryptedValue", - EncryptionKeyId = "keyId" + KeyId = "keyId" }; await Assert.ThrowsAsync(() => client.CreateOrUpdate(null, "repo", "secret", upsertSecret).ToTask()); diff --git a/Octokit/Clients/OrganizationSecretsClient.cs b/Octokit/Clients/OrganizationSecretsClient.cs index bf13baa089..e5922d637b 100644 --- a/Octokit/Clients/OrganizationSecretsClient.cs +++ b/Octokit/Clients/OrganizationSecretsClient.cs @@ -80,16 +80,17 @@ public Task Get(string org, string secretName) /// Thrown when a general API error occurs. /// A instance for the organization secret that was created or updated. [ManualRoute("PUT", "/orgs/{org}/actions/secrets/{secretName}")] - public Task CreateOrUpdate(string org, string secretName, UpsertOrganizationSecret upsertSecret) + public async Task CreateOrUpdate(string org, string secretName, UpsertOrganizationSecret upsertSecret) { Ensure.ArgumentNotNullOrEmptyString(org, nameof(org)); Ensure.ArgumentNotNullOrEmptyString(secretName, nameof(secretName)); Ensure.ArgumentNotNull(upsertSecret, nameof(upsertSecret)); - Ensure.ArgumentNotNullOrEmptyString(upsertSecret.EncryptionKeyId, nameof(upsertSecret.EncryptionKeyId)); + Ensure.ArgumentNotNullOrEmptyString(upsertSecret.KeyId, nameof(upsertSecret.KeyId)); Ensure.ArgumentNotNullOrEmptyString(upsertSecret.EncryptedValue, nameof(upsertSecret.EncryptedValue)); Ensure.ArgumentNotNullOrEmptyString(upsertSecret.Visibility, nameof(upsertSecret.Visibility)); - return ApiConnection.Put(ApiUrls.OrganizationRepositorySecret(org, secretName), upsertSecret); + await ApiConnection.Put(ApiUrls.OrganizationRepositorySecret(org, secretName), upsertSecret); + return await ApiConnection.Get(ApiUrls.OrganizationRepositorySecret(org, secretName)); } /// diff --git a/Octokit/Clients/RepositorySecretsClient.cs b/Octokit/Clients/RepositorySecretsClient.cs index 9ef1827d19..aa87e7b98f 100644 --- a/Octokit/Clients/RepositorySecretsClient.cs +++ b/Octokit/Clients/RepositorySecretsClient.cs @@ -100,11 +100,13 @@ public async Task CreateOrUpdate(string owner, string repoName Ensure.ArgumentNotNullOrEmptyString(secretName, nameof(secretName)); Ensure.ArgumentNotNull(upsertSecret, nameof(upsertSecret)); Ensure.ArgumentNotNullOrEmptyString(upsertSecret.EncryptedValue, nameof(upsertSecret.EncryptedValue)); - Ensure.ArgumentNotNullOrEmptyString(upsertSecret.EncryptionKeyId, nameof(upsertSecret.EncryptionKeyId)); + Ensure.ArgumentNotNullOrEmptyString(upsertSecret.KeyId, nameof(upsertSecret.KeyId)); var url = ApiUrls.RepositorySecret(owner, repoName, secretName); - return await ApiConnection.Put(url, upsertSecret); + await ApiConnection.Put(url, upsertSecret); + + return await Get(owner, repoName, secretName); } /// diff --git a/Octokit/Models/Request/UpsertOrganizationSecret.cs b/Octokit/Models/Request/UpsertOrganizationSecret.cs index cc25167833..bd8f78fa32 100644 --- a/Octokit/Models/Request/UpsertOrganizationSecret.cs +++ b/Octokit/Models/Request/UpsertOrganizationSecret.cs @@ -16,7 +16,7 @@ public UpsertOrganizationSecret() { } public UpsertOrganizationSecret(string encryptedValue, string encryptionKeyId, string visibility, IEnumerable selectedRepositoriesIds) { EncryptedValue = encryptedValue; - EncryptionKeyId = encryptionKeyId; + KeyId = encryptionKeyId; Visibility = visibility; SelectedRepositoriesIds = selectedRepositoriesIds; } @@ -33,6 +33,6 @@ public UpsertOrganizationSecret(string encryptedValue, string encryptionKeyId, s [Parameter(Key = "selected_repository_ids")] public IEnumerable SelectedRepositoriesIds { get; set; } - internal new string DebuggerDisplay => string.Format(CultureInfo.CurrentCulture, "UpsertOrganizationSecret: Key ID: {0}", EncryptionKeyId); + internal new string DebuggerDisplay => string.Format(CultureInfo.CurrentCulture, "UpsertOrganizationSecret: Key ID: {0}", KeyId); } } diff --git a/Octokit/Models/Request/UpsertRepositorySecret.cs b/Octokit/Models/Request/UpsertRepositorySecret.cs index 1174395186..8fe5ee3657 100644 --- a/Octokit/Models/Request/UpsertRepositorySecret.cs +++ b/Octokit/Models/Request/UpsertRepositorySecret.cs @@ -22,13 +22,13 @@ public class UpsertRepositorySecret /// /// Get key and id from and use the API documentation for more information on how to encrypt the secret [Parameter(Value = "key_id")] - public string EncryptionKeyId { get; set; } + public string KeyId { get; set; } internal string DebuggerDisplay { get { - return string.Format(CultureInfo.InvariantCulture, "KeyId: {0}", EncryptionKeyId); + return string.Format(CultureInfo.InvariantCulture, "KeyId: {0}", KeyId); } } } From 48358c5dae184241c7b579c8416ca93457dd17c2 Mon Sep 17 00:00:00 2001 From: Mike Tolly Date: Mon, 6 Jul 2020 17:25:55 -0400 Subject: [PATCH 27/56] added doc for repoid on orginzation secrets url generator --- Octokit/Helpers/ApiUrls.cs | 1 + 1 file changed, 1 insertion(+) diff --git a/Octokit/Helpers/ApiUrls.cs b/Octokit/Helpers/ApiUrls.cs index 844e757c73..6bbd5476ca 100644 --- a/Octokit/Helpers/ApiUrls.cs +++ b/Octokit/Helpers/ApiUrls.cs @@ -120,6 +120,7 @@ public static Uri OrganizationRepositorySecretRepositories(string organization, /// /// The name of the organization /// The name of the secret + /// The id of the repo to target /// public static Uri OrganizationRepositorySecretRepository(string organization, string secret, long repoId) { From 045fe8c096bc02d853f48a935f7a24a396f88776 Mon Sep 17 00:00:00 2001 From: Mike Tolly Date: Mon, 6 Jul 2020 17:57:14 -0400 Subject: [PATCH 28/56] created integration tests for repository and organization secrets --- .../Clients/OrganizationSecretsClientTests.cs | 259 ++++++++++++++++++ .../Clients/RespositorySecretsClientTests.cs | 128 +++++++++ .../Octokit.Tests.Integration.csproj | 2 +- Octokit/Clients/OrganizationSecretsClient.cs | 6 +- 4 files changed, 391 insertions(+), 4 deletions(-) create mode 100644 Octokit.Tests.Integration/Clients/OrganizationSecretsClientTests.cs create mode 100644 Octokit.Tests.Integration/Clients/RespositorySecretsClientTests.cs diff --git a/Octokit.Tests.Integration/Clients/OrganizationSecretsClientTests.cs b/Octokit.Tests.Integration/Clients/OrganizationSecretsClientTests.cs new file mode 100644 index 0000000000..2048efc81e --- /dev/null +++ b/Octokit.Tests.Integration/Clients/OrganizationSecretsClientTests.cs @@ -0,0 +1,259 @@ +using System; +using System.Collections.Generic; +using System.Text; +using System.Threading.Tasks; +using Xunit; +using System.Linq; + +#if SODIUM_CORE_AVAILABLE +using Sodium; +#endif + +namespace Octokit.Tests.Integration.Clients +{ + public class OrganizationSecretsClientTests + { + /// + /// Fill these in for tests to work + /// + internal const string ORG = "mptolly-test-org"; + + public class GetPublicKeyMethod + { + [OrganizationTest] + public async Task GetPublicKey() + { + var github = Helper.GetAuthenticatedClient(); + + var key = await github.Organization.Actions.Secrets.GetPublicKey(ORG); + + Assert.True(!string.IsNullOrWhiteSpace(key.KeyId)); + } + } + + public class GetAllMethod + { + [OrganizationTest] + public async Task GetSecrets() + { + var github = Helper.GetAuthenticatedClient(); + + var secrets = await github.Organization.Actions.Secrets.GetAll(ORG); + + Assert.NotEmpty(secrets.Secrets); + } + } + + /// + /// Please create a secret in your specific repo called TEST + /// + public class GetMethod + { + [OrganizationTest] + public async Task GetSecret() + { + var github = Helper.GetAuthenticatedClient(); + + var secret = await github.Organization.Actions.Secrets.Get(ORG, "TEST"); + + Assert.NotNull(secret); + Assert.True(secret.Name == "TEST"); + } + } + + public class CreateOrUpdateMethod + { +#if SODIUM_CORE_AVAILABLE + [OrganizationTest] + public async Task UpsertSecret() + { + var github = Helper.GetAuthenticatedClient(); + var now = DateTime.Now; + + var publicKey = await github.Organization.Actions.Secrets.GetPublicKey(ORG); + var upsertValue = GetSecretForCreate("value", publicKey); + + var secret = await github.Organization.Actions.Secrets.CreateOrUpdate(ORG, "UPSERT_TEST", upsertValue); + + Assert.NotNull(secret); + Assert.True(secret.UpdatedAt > now); + } +#endif + } + + public class DeleteMethod + { +#if SODIUM_CORE_AVAILABLE + [OrganizationTest] + public async Task DeleteSecret() + { + var github = Helper.GetAuthenticatedClient(); + + var secretName = "DELETE_TEST"; + + var publicKey = await github.Organization.Actions.Secrets.GetPublicKey(ORG); + var upsertValue = GetSecretForCreate("value", publicKey); + + await github.Organization.Actions.Secrets.CreateOrUpdate(ORG, secretName, upsertValue); + await github.Organization.Actions.Secrets.Delete(ORG, secretName); + + } +#endif + } + + public class GetSelectedRepositoriesForSecretMethod + { +#if SODIUM_CORE_AVAILABLE + [OrganizationTest] + public async Task GetSelectedRepositoriesForSecret() + { + var github = Helper.GetAuthenticatedClient(); + + var secretName = "LIST_SELECTED_REPO_TEST"; + + var repo = await CreateRepoIfNotExists(github, "list-secrets-selected-repo-test"); + + var key = await github.Organization.Actions.Secrets.GetPublicKey(ORG); + var upsertSecret = GetSecretForCreate("secret", key, new Repository[] { repo }); + var secret = await github.Organization.Actions.Secrets.CreateOrUpdate(ORG, secretName, upsertSecret); + + var visibilityRepos = await github.Organization.Actions.Secrets.GetSelectedRepositoriesForSecret(ORG, secretName); + + Assert.NotEmpty(visibilityRepos.Repositories); + } +#endif + } + + public class SetSelectedRepositoriesForSecretMethod + { +#if SODIUM_CORE_AVAILABLE + [OrganizationTest] + public async Task SetSelectedRepositoriesForSecret() + { + var github = Helper.GetAuthenticatedClient(); + + var secretName = "SET_SELECTED_REPO_TEST"; + + var repo1 = await CreateRepoIfNotExists(github, "set-secrets-selected-repo-test-1"); + var repo2 = await CreateRepoIfNotExists(github, "set-secrets-selected-repo-test-2"); + + var key = await github.Organization.Actions.Secrets.GetPublicKey(ORG); + var upsertSecret = GetSecretForCreate("secret", key, new Repository[] { repo1 }); + await github.Organization.Actions.Secrets.CreateOrUpdate(ORG, secretName, upsertSecret); + + await github.Organization.Actions.Secrets.SetSelectedRepositoriesForSecret(ORG, secretName, new SelectedRepositoryCollection(new long[] { repo1.Id, repo2.Id })); + + var visibilityRepos = await github.Organization.Actions.Secrets.GetSelectedRepositoriesForSecret(ORG, secretName); + + Assert.NotEmpty(visibilityRepos.Repositories); + Assert.Equal(2, visibilityRepos.Count); + } +#endif + } + + public class AddRepoToOrganizationSecretMethod + { +#if SODIUM_CORE_AVAILABLE + [OrganizationTest] + public async Task AddSelectedRepositoriesForSecret() + { + var github = Helper.GetAuthenticatedClient(); + + var secretName = "ADD_SELECTED_REPO_TEST"; + + var repo1 = await CreateRepoIfNotExists(github, "set-secrets-selected-repo-test-1"); + var repo2 = await CreateRepoIfNotExists(github, "set-secrets-selected-repo-test-2"); + + var key = await github.Organization.Actions.Secrets.GetPublicKey(ORG); + var upsertSecret = GetSecretForCreate("secret", key, new Repository[] { repo1 }); + await github.Organization.Actions.Secrets.CreateOrUpdate(ORG, secretName, upsertSecret); + + await github.Organization.Actions.Secrets.AddRepoToOrganizationSecret(ORG, secretName, repo2.Id); + + var visibilityRepos = await github.Organization.Actions.Secrets.GetSelectedRepositoriesForSecret(ORG, secretName); + + Assert.NotEmpty(visibilityRepos.Repositories); + Assert.Equal(2, visibilityRepos.Count); + } +#endif + } + + public class RemoveRepoFromOrganizationSecretMethod + { +#if SODIUM_CORE_AVAILABLE + [OrganizationTest] + public async Task RemoveSelectedRepositoriesForSecret() + { + var github = Helper.GetAuthenticatedClient(); + + var secretName = "REMOVE_SELECTED_REPO_TEST"; + + var repo1 = await CreateRepoIfNotExists(github, "set-secrets-selected-repo-test-1"); + var repo2 = await CreateRepoIfNotExists(github, "set-secrets-selected-repo-test-2"); + + var key = await github.Organization.Actions.Secrets.GetPublicKey(ORG); + var upsertSecret = GetSecretForCreate("secret", key, new Repository[] { repo1, repo2 }); + await github.Organization.Actions.Secrets.CreateOrUpdate(ORG, secretName, upsertSecret); + + await github.Organization.Actions.Secrets.RemoveRepoFromOrganizationSecret(ORG, secretName, repo2.Id); + + var visibilityRepos = await github.Organization.Actions.Secrets.GetSelectedRepositoriesForSecret(ORG, secretName); + + Assert.NotEmpty(visibilityRepos.Repositories); + Assert.Equal(1, visibilityRepos.Count); + } +#endif + } + +#if SODIUM_CORE_AVAILABLE + private static UpsertOrganizationSecret GetSecretForCreate(string secretValue, SecretsPublicKey key) + { + var secretBytes = Encoding.UTF8.GetBytes(secretValue); + var publicKey = Convert.FromBase64String(key.Key); + var sealedPublicKeyBox = SealedPublicKeyBox.Create(secretBytes, publicKey); + + var upsertValue = new UpsertOrganizationSecret + { + EncryptedValue = Convert.ToBase64String(sealedPublicKeyBox), + KeyId = key.KeyId, + Visibility = "all" + + }; + + return upsertValue; + } + + private static UpsertOrganizationSecret GetSecretForCreate(string secretValue, SecretsPublicKey key, Repository[] repos) + { + var secretBytes = Encoding.UTF8.GetBytes(secretValue); + var publicKey = Convert.FromBase64String(key.Key); + var sealedPublicKeyBox = SealedPublicKeyBox.Create(secretBytes, publicKey); + + var upsertValue = new UpsertOrganizationSecret + { + EncryptedValue = Convert.ToBase64String(sealedPublicKeyBox), + KeyId = key.KeyId, + Visibility = "selected", + SelectedRepositoriesIds = repos.Select(r => r.Id) + + }; + + return upsertValue; + } +#endif + + private static async Task CreateRepoIfNotExists(IGitHubClient github, string name) + { + try + { + var existingRepo = await github.Repository.Get(ORG, name); + return existingRepo; + } + catch + { + var newRepo = await github.Repository.Create(ORG, new NewRepository(name)); + return newRepo; + } + } + } +} diff --git a/Octokit.Tests.Integration/Clients/RespositorySecretsClientTests.cs b/Octokit.Tests.Integration/Clients/RespositorySecretsClientTests.cs new file mode 100644 index 0000000000..cd82c53c54 --- /dev/null +++ b/Octokit.Tests.Integration/Clients/RespositorySecretsClientTests.cs @@ -0,0 +1,128 @@ +using System; +using System.Collections.Generic; +using System.Runtime.Versioning; +using System.Text; +using System.Threading.Tasks; +using Octokit; +using Octokit.Tests.Integration; +using Octokit.Tests.Integration.Helpers; +using Xunit; + +#if SODIUM_CORE_AVAILABLE +using Sodium; +#endif + +namespace Octokit.Tests.Integration.Clients +{ + /// + /// Access to view and update secrets is required for the following tests + /// + public class RespositorySecretsClientTests + { + /// + /// Fill these in for tests to work + /// + internal const string OWNER = "mptolly-test"; + internal const string REPO = "oktokit.net"; + + public class GetPublicKeyMethod + { + [IntegrationTest] + public async Task GetPublicKey() + { + var github = Helper.GetAuthenticatedClient(); + + var key = await github.Repository.Actions.Secrets.GetPublicKey(OWNER, REPO); + + Assert.True(!string.IsNullOrWhiteSpace(key.KeyId)); + } + } + + public class GetAllMethod + { + [IntegrationTest] + public async Task GetSecrets() + { + var github = Helper.GetAuthenticatedClient(); + + var secrets = await github.Repository.Actions.Secrets.GetAll(OWNER, REPO); + + Assert.NotEmpty(secrets.Secrets); + } + } + + /// + /// Please create a secret in your specific repo called TEST + /// + public class GetMethod + { + [IntegrationTest] + public async Task GetSecret() + { + var github = Helper.GetAuthenticatedClient(); + + var secret = await github.Repository.Actions.Secrets.Get(OWNER, REPO, "TEST"); + + Assert.NotNull(secret); + Assert.True(secret.Name == "TEST"); + } + } + + public class CreateOrUpdateMethod + { +#if SODIUM_CORE_AVAILABLE + [IntegrationTest] + public async Task UpsertSecret() + { + var github = Helper.GetAuthenticatedClient(); + var now = DateTime.Now; + + var publicKey = await github.Repository.Actions.Secrets.GetPublicKey(OWNER, REPO); + var upsertValue = GetSecretForCreate("value", publicKey); + + var secret = await github.Repository.Actions.Secrets.CreateOrUpdate(OWNER, REPO, "UPSERT_TEST", upsertValue); + + Assert.NotNull(secret); + Assert.True(secret.UpdatedAt > now); + } +#endif + } + + public class DeleteMethod + { +#if SODIUM_CORE_AVAILABLE + [IntegrationTest] + public async Task DeleteSecret() + { + var github = Helper.GetAuthenticatedClient(); + + var secretName = "DELETE_TEST"; + + var publicKey = await github.Repository.Actions.Secrets.GetPublicKey(OWNER, REPO); + var upsertValue = GetSecretForCreate("value", publicKey); + + await github.Repository.Actions.Secrets.CreateOrUpdate(OWNER, REPO, secretName, upsertValue); + await github.Repository.Actions.Secrets.Delete(OWNER, REPO, secretName); + + } +#endif + } +#if SODIUM_CORE_AVAILABLE + private static UpsertRepositorySecret GetSecretForCreate(string secretValue, SecretsPublicKey key) + { + var secretBytes = Encoding.UTF8.GetBytes(secretValue); + var publicKey = Convert.FromBase64String(key.Key); + var sealedPublicKeyBox = SealedPublicKeyBox.Create(secretBytes, publicKey); + + var upsertValue = new UpsertRepositorySecret + { + EncryptedValue = Convert.ToBase64String(sealedPublicKeyBox), + KeyId = key.KeyId + + }; + + return upsertValue; + } +#endif + } +} diff --git a/Octokit.Tests.Integration/Octokit.Tests.Integration.csproj b/Octokit.Tests.Integration/Octokit.Tests.Integration.csproj index 501d77020d..faead6a4f1 100644 --- a/Octokit.Tests.Integration/Octokit.Tests.Integration.csproj +++ b/Octokit.Tests.Integration/Octokit.Tests.Integration.csproj @@ -20,7 +20,7 @@ - $(DefineConstants);GITHUBJWT_HELPER_AVAILABLE + $(DefineConstants);GITHUBJWT_HELPER_AVAILABLE;SODIUM_CORE_AVAILABLE diff --git a/Octokit/Clients/OrganizationSecretsClient.cs b/Octokit/Clients/OrganizationSecretsClient.cs index e5922d637b..a0b10da84e 100644 --- a/Octokit/Clients/OrganizationSecretsClient.cs +++ b/Octokit/Clients/OrganizationSecretsClient.cs @@ -147,7 +147,7 @@ public Task SetSelectedRepositoriesForSecret(string org, string secretName, Sele Ensure.ArgumentNotNull(repositories, nameof(repositories)); Ensure.ArgumentNotNull(repositories.SelectedRepositoryIds, nameof(repositories.SelectedRepositoryIds)); - return ApiConnection.Put(ApiUrls.OrganizationRepositorySecretRepositories(org, secretName)); + return ApiConnection.Put(ApiUrls.OrganizationRepositorySecretRepositories(org, secretName), repositories); } /// @@ -160,7 +160,7 @@ public Task SetSelectedRepositoriesForSecret(string org, string secretName, Sele /// The name of the secret /// The id of the repo to add to the visibility list of the secret /// Thrown when a general API error occurs. - [ManualRoute("PUT", "/orgs/{org}/actions/secrets/{secretName}/{repoId}")] + [ManualRoute("PUT", "/orgs/{org}/actions/secrets/{secretName}/repositories/{repoId}")] public Task AddRepoToOrganizationSecret(string org, string secretName, long repoId) { Ensure.ArgumentNotNullOrEmptyString(org, nameof(org)); @@ -180,7 +180,7 @@ public Task AddRepoToOrganizationSecret(string org, string secretName, long repo /// The name of the secret /// The id of the repo to add to the visibility list of the secret /// Thrown when a general API error occurs. - [ManualRoute("DELETE", "/orgs/{org}/actions/secrets/{secretName}/{repoId}")] + [ManualRoute("DELETE", "/orgs/{org}/actions/secrets/{secretName}/repositories/{repoId}")] public Task RemoveRepoFromOrganizationSecret(string org, string secretName, long repoId) { Ensure.ArgumentNotNullOrEmptyString(org, nameof(org)); From a25278df918331e523c5d7d6c680b5d4bceb27d5 Mon Sep 17 00:00:00 2001 From: Mike Tolly Date: Mon, 6 Jul 2020 18:10:15 -0400 Subject: [PATCH 29/56] changed how return occurs for setting list of repos for secret --- Octokit/Clients/OrganizationSecretsClient.cs | 5 +++-- 1 file changed, 3 insertions(+), 2 deletions(-) diff --git a/Octokit/Clients/OrganizationSecretsClient.cs b/Octokit/Clients/OrganizationSecretsClient.cs index a0b10da84e..2ccb91e802 100644 --- a/Octokit/Clients/OrganizationSecretsClient.cs +++ b/Octokit/Clients/OrganizationSecretsClient.cs @@ -140,14 +140,15 @@ public Task GetSelectedRepositoriesForSe /// The list of repositories that should have access to view and use the secret /// Thrown when a general API error occurs. [ManualRoute("PUT", "/orgs/{org}/actions/secrets/{secretName}/repositories")] - public Task SetSelectedRepositoriesForSecret(string org, string secretName, SelectedRepositoryCollection repositories) + public async Task SetSelectedRepositoriesForSecret(string org, string secretName, SelectedRepositoryCollection repositories) { Ensure.ArgumentNotNullOrEmptyString(org, nameof(org)); Ensure.ArgumentNotNullOrEmptyString(secretName, nameof(secretName)); Ensure.ArgumentNotNull(repositories, nameof(repositories)); Ensure.ArgumentNotNull(repositories.SelectedRepositoryIds, nameof(repositories.SelectedRepositoryIds)); - return ApiConnection.Put(ApiUrls.OrganizationRepositorySecretRepositories(org, secretName), repositories); + await ApiConnection.Put(ApiUrls.OrganizationRepositorySecretRepositories(org, secretName), repositories); + return; } /// From 28be0339b0dfadb861b77fed2f4d68871750f72b Mon Sep 17 00:00:00 2001 From: Mike Tolly Date: Mon, 6 Jul 2020 18:28:36 -0400 Subject: [PATCH 30/56] fixed some names and removed reset org name --- .../Clients/OrganizationSecretsClientTests.cs | 10 +++++----- 1 file changed, 5 insertions(+), 5 deletions(-) diff --git a/Octokit.Tests.Integration/Clients/OrganizationSecretsClientTests.cs b/Octokit.Tests.Integration/Clients/OrganizationSecretsClientTests.cs index 2048efc81e..7d570694ac 100644 --- a/Octokit.Tests.Integration/Clients/OrganizationSecretsClientTests.cs +++ b/Octokit.Tests.Integration/Clients/OrganizationSecretsClientTests.cs @@ -16,7 +16,7 @@ public class OrganizationSecretsClientTests /// /// Fill these in for tests to work /// - internal const string ORG = "mptolly-test-org"; + internal const string ORG = ""; public class GetPublicKeyMethod { @@ -161,8 +161,8 @@ public async Task AddSelectedRepositoriesForSecret() var secretName = "ADD_SELECTED_REPO_TEST"; - var repo1 = await CreateRepoIfNotExists(github, "set-secrets-selected-repo-test-1"); - var repo2 = await CreateRepoIfNotExists(github, "set-secrets-selected-repo-test-2"); + var repo1 = await CreateRepoIfNotExists(github, "add-secrets-selected-repo-test-1"); + var repo2 = await CreateRepoIfNotExists(github, "add-secrets-selected-repo-test-2"); var key = await github.Organization.Actions.Secrets.GetPublicKey(ORG); var upsertSecret = GetSecretForCreate("secret", key, new Repository[] { repo1 }); @@ -188,8 +188,8 @@ public async Task RemoveSelectedRepositoriesForSecret() var secretName = "REMOVE_SELECTED_REPO_TEST"; - var repo1 = await CreateRepoIfNotExists(github, "set-secrets-selected-repo-test-1"); - var repo2 = await CreateRepoIfNotExists(github, "set-secrets-selected-repo-test-2"); + var repo1 = await CreateRepoIfNotExists(github, "remove-secrets-selected-repo-test-1"); + var repo2 = await CreateRepoIfNotExists(github, "remove-secrets-selected-repo-test-2"); var key = await github.Organization.Actions.Secrets.GetPublicKey(ORG); var upsertSecret = GetSecretForCreate("secret", key, new Repository[] { repo1, repo2 }); From 1c7fbe51c968866ace17213360dfd017e1e9b7a4 Mon Sep 17 00:00:00 2001 From: Mike Tolly Date: Tue, 7 Jul 2020 10:05:07 -0400 Subject: [PATCH 31/56] created integration tests for observable org secrets client --- ...bservableOrganizationSecretsClientTests.cs | 302 ++++++++++++++++++ 1 file changed, 302 insertions(+) create mode 100644 Octokit.Tests.Integration/Reactive/ObservableOrganizationSecretsClientTests.cs diff --git a/Octokit.Tests.Integration/Reactive/ObservableOrganizationSecretsClientTests.cs b/Octokit.Tests.Integration/Reactive/ObservableOrganizationSecretsClientTests.cs new file mode 100644 index 0000000000..698ab997b6 --- /dev/null +++ b/Octokit.Tests.Integration/Reactive/ObservableOrganizationSecretsClientTests.cs @@ -0,0 +1,302 @@ +using System; +using System.Collections.Generic; +using System.Reactive.Linq; +using System.Text; +using System.Threading.Tasks; +using Octokit.Reactive; +using Xunit; +using System.Linq; + +#if SODIUM_CORE_AVAILABLE +using Sodium; +#endif + +namespace Octokit.Tests.Integration.Reactive +{ + public class ObservableOrganizationSecretsClientTests + { + /// + /// Fill these in for tests to work + /// + internal const string ORG = "mptolly-test-org"; + + public class GetPublicKeyMethod + { + [OrganizationTest] + public async Task GetPublicKey() + { + var github = Helper.GetAuthenticatedClient(); + var clients = new ObservableOrganizationSecretsClient(github); + + var keyObservable = clients.GetPublicKey(ORG); + var key = await keyObservable; + + Assert.True(!string.IsNullOrWhiteSpace(key.KeyId)); + } + } + + public class GetAllMethod + { + [OrganizationTest] + public async Task GetSecrets() + { + var github = Helper.GetAuthenticatedClient(); + var clients = new ObservableOrganizationSecretsClient(github); + + var secretsObservable = clients.GetAll(ORG); + var secrets = await secretsObservable; + + Assert.NotEmpty(secrets.Secrets); + } + } + + /// + /// Please create a secret in your specific repo called TEST + /// + public class GetMethod + { + [OrganizationTest] + public async Task GetSecret() + { + var github = Helper.GetAuthenticatedClient(); + var clients = new ObservableOrganizationSecretsClient(github); + + var secretObservable = clients.Get(ORG, "TEST"); + var secret = await secretObservable; + + Assert.NotNull(secret); + Assert.True(secret.Name == "TEST"); + } + } + + public class CreateOrUpdateMethod + { +#if SODIUM_CORE_AVAILABLE + [OrganizationTest] + public async Task UpsertSecret() + { + var github = Helper.GetAuthenticatedClient(); + var clients = new ObservableOrganizationSecretsClient(github); + var now = DateTime.Now; + + var keyObservable = clients.GetPublicKey(ORG); + var key = await keyObservable; + + var upsertValue = GetSecretForCreate("value", key); + + var secretObservable = clients.CreateOrUpdate(ORG, "REACTIVE_UPSERT_TEST", upsertValue); + var secret = await secretObservable; + + Assert.NotNull(secret); + Assert.True(secret.UpdatedAt > now); + } +#endif + } + + public class DeleteMethod + { +#if SODIUM_CORE_AVAILABLE + [OrganizationTest] + public async Task DeleteSecret() + { + var github = Helper.GetAuthenticatedClient(); + var clients = new ObservableOrganizationSecretsClient(github); + + var secretName = "REACTIVE_DELETE_TEST"; + + var keyObservable = clients.GetPublicKey(ORG); + var key = await keyObservable; + var upsertValue = GetSecretForCreate("value", key); + + var createSecretObservable = clients.CreateOrUpdate(ORG, secretName, upsertValue); + await createSecretObservable; + + var deleteSecretObservable = clients.Delete(ORG, secretName); + await deleteSecretObservable; + } +#endif + } + + public class GetSelectedRepositoriesForSecretMethod + { +#if SODIUM_CORE_AVAILABLE + [OrganizationTest] + public async Task GetSelectedRepositoriesForSecret() + { + var github = Helper.GetAuthenticatedClient(); + var clients = new ObservableOrganizationSecretsClient(github); + var repoClients = new ObservableRepositoriesClient(github); + + var secretName = "REACTIVE_LIST_SELECTED_REPO_TEST"; + + var repo = await CreateRepoIfNotExists(repoClients, "reactive-list-secrets-selected-repo-test"); + + var keyObservable = clients.GetPublicKey(ORG); + var key = await keyObservable; + var upsertSecret = GetSecretForCreate("value", key, new Repository[] { repo }); + + var secretObservable = clients.CreateOrUpdate(ORG, secretName, upsertSecret); + await secretObservable; + + var visibilityReposObservable = clients.GetSelectedRepositoriesForSecret(ORG, secretName); + var visibilityRepos = await visibilityReposObservable; + + Assert.NotEmpty(visibilityRepos.Repositories); + } +#endif + } + + public class SetSelectedRepositoriesForSecretMethod + { +#if SODIUM_CORE_AVAILABLE + [OrganizationTest] + public async Task SetSelectedRepositoriesForSecret() + { + var github = Helper.GetAuthenticatedClient(); + var clients = new ObservableOrganizationSecretsClient(github); + var repoClients = new ObservableRepositoriesClient(github); + + var secretName = "REACTIVE_SET_SELECTED_REPO_TEST"; + + var repo1 = await CreateRepoIfNotExists(repoClients, "reactive-set-secrets-selected-repo-test-1"); + var repo2 = await CreateRepoIfNotExists(repoClients, "reactive-set-secrets-selected-repo-test-2"); + + var keyObservable = clients.GetPublicKey(ORG); + var key = await keyObservable; + var upsertSecret = GetSecretForCreate("value", key, new Repository[] { repo1 }); + + var secretObservable = clients.CreateOrUpdate(ORG, secretName, upsertSecret); + await secretObservable; + + var setRepoListObservable = clients.SetSelectedRepositoriesForSecret(ORG, secretName, new SelectedRepositoryCollection(new long[] { repo1.Id, repo2.Id })); + await setRepoListObservable; + + var visibilityReposObservable = clients.GetSelectedRepositoriesForSecret(ORG, secretName); + var visibilityRepos = await visibilityReposObservable; + + Assert.NotEmpty(visibilityRepos.Repositories); + Assert.Equal(2, visibilityRepos.Count); + } +#endif + } + + public class AddRepoToOrganizationSecretMethod + { +#if SODIUM_CORE_AVAILABLE + [OrganizationTest] + public async Task AddSelectedRepositoriesForSecret() + { + var github = Helper.GetAuthenticatedClient(); + var clients = new ObservableOrganizationSecretsClient(github); + var repoClients = new ObservableRepositoriesClient(github); + + var secretName = "REACTIVE_ADD_SELECTED_REPO_TEST"; + + var repo1 = await CreateRepoIfNotExists(repoClients, "reactive-add-secrets-selected-repo-test-1"); + var repo2 = await CreateRepoIfNotExists(repoClients, "reactive-add-secrets-selected-repo-test-2"); + + var keyObservable = clients.GetPublicKey(ORG); + var key = await keyObservable; + var upsertSecret = GetSecretForCreate("value", key, new Repository[] { repo1 }); + + var secretObservable = clients.CreateOrUpdate(ORG, secretName, upsertSecret); + await secretObservable; + + var addRepoListObservable = clients.AddRepoToOrganizationSecret(ORG, secretName, repo2.Id); + await addRepoListObservable; + + var visibilityReposObservable = clients.GetSelectedRepositoriesForSecret(ORG, secretName); + var visibilityRepos = await visibilityReposObservable; + + Assert.NotEmpty(visibilityRepos.Repositories); + Assert.Equal(2, visibilityRepos.Count); + } +#endif + } + + public class RemoveRepoFromOrganizationSecretMethod + { +#if SODIUM_CORE_AVAILABLE + [OrganizationTest] + public async Task RemoveSelectedRepositoriesForSecret() + { + var github = Helper.GetAuthenticatedClient(); + var clients = new ObservableOrganizationSecretsClient(github); + var repoClients = new ObservableRepositoriesClient(github); + + var secretName = "REACTIVE_REMOVE_SELECTED_REPO_TEST"; + + var repo1 = await CreateRepoIfNotExists(repoClients, "reactive-remove-secrets-selected-repo-test-1"); + var repo2 = await CreateRepoIfNotExists(repoClients, "reactive-remove-secrets-selected-repo-test-2"); + + var keyObservable = clients.GetPublicKey(ORG); + var key = await keyObservable; + var upsertSecret = GetSecretForCreate("secret", key, new Repository[] { repo1, repo2 }); + + var secretObservable = clients.CreateOrUpdate(ORG, secretName, upsertSecret); + await secretObservable; + + var removeRepoListObservable = clients.RemoveRepoFromOrganizationSecret(ORG, secretName, repo2.Id); + await removeRepoListObservable; + + var visibilityReposObservable = clients.GetSelectedRepositoriesForSecret(ORG, secretName); + var visibilityRepos = await visibilityReposObservable; + + Assert.NotEmpty(visibilityRepos.Repositories); + Assert.Equal(1, visibilityRepos.Count); + } +#endif + } + +#if SODIUM_CORE_AVAILABLE + private static UpsertOrganizationSecret GetSecretForCreate(string secretValue, SecretsPublicKey key) + { + var secretBytes = Encoding.UTF8.GetBytes(secretValue); + var publicKey = Convert.FromBase64String(key.Key); + var sealedPublicKeyBox = SealedPublicKeyBox.Create(secretBytes, publicKey); + + var upsertValue = new UpsertOrganizationSecret + { + EncryptedValue = Convert.ToBase64String(sealedPublicKeyBox), + KeyId = key.KeyId, + Visibility = "all" + + }; + + return upsertValue; + } + + private static UpsertOrganizationSecret GetSecretForCreate(string secretValue, SecretsPublicKey key, Repository[] repos) + { + var secretBytes = Encoding.UTF8.GetBytes(secretValue); + var publicKey = Convert.FromBase64String(key.Key); + var sealedPublicKeyBox = SealedPublicKeyBox.Create(secretBytes, publicKey); + + var upsertValue = new UpsertOrganizationSecret + { + EncryptedValue = Convert.ToBase64String(sealedPublicKeyBox), + KeyId = key.KeyId, + Visibility = "selected", + SelectedRepositoriesIds = repos.Select(r => r.Id) + + }; + + return upsertValue; + } +#endif + + private static async Task CreateRepoIfNotExists(ObservableRepositoriesClient client, string name) + { + try + { + var existingRepo = client.Get(ORG, name); + return await existingRepo; + } + catch + { + var newRepo = client.Create(ORG, new NewRepository(name)); + return await newRepo; + } + } + } +} From 635ccc69aef626a5cf586f7f0cc32943a0545932 Mon Sep 17 00:00:00 2001 From: Mike Tolly Date: Tue, 7 Jul 2020 10:08:55 -0400 Subject: [PATCH 32/56] removed default org value --- .../Reactive/ObservableOrganizationSecretsClientTests.cs | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/Octokit.Tests.Integration/Reactive/ObservableOrganizationSecretsClientTests.cs b/Octokit.Tests.Integration/Reactive/ObservableOrganizationSecretsClientTests.cs index 698ab997b6..7d2423cb28 100644 --- a/Octokit.Tests.Integration/Reactive/ObservableOrganizationSecretsClientTests.cs +++ b/Octokit.Tests.Integration/Reactive/ObservableOrganizationSecretsClientTests.cs @@ -18,7 +18,7 @@ public class ObservableOrganizationSecretsClientTests /// /// Fill these in for tests to work /// - internal const string ORG = "mptolly-test-org"; + internal const string ORG = ""; public class GetPublicKeyMethod { From 054cc2c966061e5806bc7f96a1e1a108cbe649e8 Mon Sep 17 00:00:00 2001 From: Mike Tolly Date: Tue, 7 Jul 2020 10:21:28 -0400 Subject: [PATCH 33/56] created the integration tests for the observable repository secrets client --- .../ObservableRepositorySecretsClientTests.cs | 138 ++++++++++++++++++ 1 file changed, 138 insertions(+) create mode 100644 Octokit.Tests.Integration/Reactive/ObservableRepositorySecretsClientTests.cs diff --git a/Octokit.Tests.Integration/Reactive/ObservableRepositorySecretsClientTests.cs b/Octokit.Tests.Integration/Reactive/ObservableRepositorySecretsClientTests.cs new file mode 100644 index 0000000000..bb29cd6175 --- /dev/null +++ b/Octokit.Tests.Integration/Reactive/ObservableRepositorySecretsClientTests.cs @@ -0,0 +1,138 @@ +using System; +using System.Collections.Generic; +using System.Text; +using System.Threading.Tasks; +using Xunit; +using Octokit.Reactive; +using System.Reactive.Linq; + +#if SODIUM_CORE_AVAILABLE +using Sodium; +#endif + +namespace Octokit.Tests.Integration.Reactive.Clients +{ + public class ObservableRepositorySecretsClientTests + { + /// + /// Fill these in for tests to work + /// + internal const string OWNER = ""; + internal const string REPO = ""; + + public class GetPublicKeyMethod + { + [IntegrationTest] + public async Task GetPublicKey() + { + var github = Helper.GetAuthenticatedClient(); + var client = new ObservableRepositorySecretsClient(github); + + var keyObservable = client.GetPublicKey(OWNER, REPO); + var key = await keyObservable; + + Assert.True(!string.IsNullOrWhiteSpace(key.KeyId)); + } + } + + public class GetAllMethod + { + [IntegrationTest] + public async Task GetSecrets() + { + var github = Helper.GetAuthenticatedClient(); + var client = new ObservableRepositorySecretsClient(github); + + var secretsObservable = client.GetAll(OWNER, REPO); + var secrets = await secretsObservable; + + Assert.NotEmpty(secrets.Secrets); + } + } + + /// + /// Please create a secret in your specific repo called TEST + /// + public class GetMethod + { + [IntegrationTest] + public async Task GetSecret() + { + var github = Helper.GetAuthenticatedClient(); + var client = new ObservableRepositorySecretsClient(github); + var secretName = "TEST"; + + var secretsObservable = client.Get(OWNER, REPO, secretName); + var secret = await secretsObservable; + + Assert.NotNull(secret); + Assert.True(secret.Name == secretName); + } + } + + public class CreateOrUpdateMethod + { +#if SODIUM_CORE_AVAILABLE + [IntegrationTest] + public async Task UpsertSecret() + { + var github = Helper.GetAuthenticatedClient(); + var client = new ObservableRepositorySecretsClient(github); + var now = DateTime.Now; + + var keyObservable = client.GetPublicKey(OWNER, REPO); + var key = await keyObservable; + var upsertValue = GetSecretForCreate("value", key); + + var secretObservable = client.CreateOrUpdate(OWNER, REPO, "REACTIVE_UPSERT_TEST", upsertValue); + var secret = await secretObservable; + + Assert.NotNull(secret); + Assert.True(secret.UpdatedAt > now); + } +#endif + } + + public class DeleteMethod + { +#if SODIUM_CORE_AVAILABLE + [IntegrationTest] + public async Task DeleteSecret() + { + var github = Helper.GetAuthenticatedClient(); + var client = new ObservableRepositorySecretsClient(github); + + var secretName = "DELETE_TEST"; + + var keyObservable = client.GetPublicKey(OWNER, REPO); + var key = await keyObservable; + var upsertValue = GetSecretForCreate("value", key); + + var createObservable = client.CreateOrUpdate(OWNER, REPO, secretName, upsertValue); + await createObservable; + + var deleteObservable = client.Delete(OWNER, REPO, secretName); + await deleteObservable; + + } +#endif + } +#if SODIUM_CORE_AVAILABLE + private static UpsertRepositorySecret GetSecretForCreate(string secretValue, SecretsPublicKey key) + { + var secretBytes = Encoding.UTF8.GetBytes(secretValue); + var publicKey = Convert.FromBase64String(key.Key); + var sealedPublicKeyBox = SealedPublicKeyBox.Create(secretBytes, publicKey); + + var upsertValue = new UpsertRepositorySecret + { + EncryptedValue = Convert.ToBase64String(sealedPublicKeyBox), + KeyId = key.KeyId + + }; + + return upsertValue; + } +#endif + } +} From 8a74f2e7f142b83717800ace27747c6e507596bf Mon Sep 17 00:00:00 2001 From: Mike Tolly Date: Tue, 7 Jul 2020 10:30:37 -0400 Subject: [PATCH 34/56] removed default owner project value --- .../Clients/RespositorySecretsClientTests.cs | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/Octokit.Tests.Integration/Clients/RespositorySecretsClientTests.cs b/Octokit.Tests.Integration/Clients/RespositorySecretsClientTests.cs index cd82c53c54..1bf3e0767a 100644 --- a/Octokit.Tests.Integration/Clients/RespositorySecretsClientTests.cs +++ b/Octokit.Tests.Integration/Clients/RespositorySecretsClientTests.cs @@ -22,8 +22,8 @@ public class RespositorySecretsClientTests /// /// Fill these in for tests to work /// - internal const string OWNER = "mptolly-test"; - internal const string REPO = "oktokit.net"; + internal const string OWNER = ""; + internal const string REPO = ""; public class GetPublicKeyMethod { From 2927d80e9ff965187b9754aa4ceee607b539a5e5 Mon Sep 17 00:00:00 2001 From: Mike Tolly Date: Tue, 7 Jul 2020 10:55:38 -0400 Subject: [PATCH 35/56] fixed unit tests --- Octokit.Tests/Clients/OrganizationSecretsClientTests.cs | 2 +- .../Reactive/ObservableOrganizationSecretsClientTests.cs | 2 +- Octokit/Models/Response/RepositorySecretsCollection.cs | 4 ++-- 3 files changed, 4 insertions(+), 4 deletions(-) diff --git a/Octokit.Tests/Clients/OrganizationSecretsClientTests.cs b/Octokit.Tests/Clients/OrganizationSecretsClientTests.cs index 8f9ac2ef20..da08c24e58 100644 --- a/Octokit.Tests/Clients/OrganizationSecretsClientTests.cs +++ b/Octokit.Tests/Clients/OrganizationSecretsClientTests.cs @@ -206,7 +206,7 @@ public async Task RequestsTheCorrectUrl() await client.SetSelectedRepositoriesForSecret("org", "secret", repos); connection.Received() - .Put(Arg.Is(u => u.ToString() == "orgs/org/actions/secrets/secret/repositories")); + .Put(Arg.Is(u => u.ToString() == "orgs/org/actions/secrets/secret/repositories"), repos); } [Fact] diff --git a/Octokit.Tests/Reactive/ObservableOrganizationSecretsClientTests.cs b/Octokit.Tests/Reactive/ObservableOrganizationSecretsClientTests.cs index db90cced63..7e36b26864 100644 --- a/Octokit.Tests/Reactive/ObservableOrganizationSecretsClientTests.cs +++ b/Octokit.Tests/Reactive/ObservableOrganizationSecretsClientTests.cs @@ -202,7 +202,7 @@ public async Task RequestsTheCorrectUrl() await client.SetSelectedRepositoriesForSecret("org", "secret", repos); connection.Received() - .Put(Arg.Is(u => u.ToString() == "orgs/org/actions/secrets/secret/repositories")); + .Put(Arg.Is(u => u.ToString() == "orgs/org/actions/secrets/secret/repositories"), repos); } [Fact] diff --git a/Octokit/Models/Response/RepositorySecretsCollection.cs b/Octokit/Models/Response/RepositorySecretsCollection.cs index 72186e64f6..6886ca1f87 100644 --- a/Octokit/Models/Response/RepositorySecretsCollection.cs +++ b/Octokit/Models/Response/RepositorySecretsCollection.cs @@ -15,9 +15,9 @@ public RepositorySecretsCollection() { } - public RepositorySecretsCollection(int count, IReadOnlyList secrets) + public RepositorySecretsCollection(int totalCount, IReadOnlyList secrets) { - TotalCount = count; + TotalCount = totalCount; Secrets = secrets; } From a186d31abc83eb13d030f261b3dd84af58d38d5a Mon Sep 17 00:00:00 2001 From: Thomas Hughes Date: Wed, 12 Aug 2020 10:09:56 -0500 Subject: [PATCH 36/56] Update links to new docs site --- .../Clients/IObservableOrganizationActionsClient.cs | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/Octokit.Reactive/Clients/IObservableOrganizationActionsClient.cs b/Octokit.Reactive/Clients/IObservableOrganizationActionsClient.cs index d4a8c63426..f3d00a623c 100644 --- a/Octokit.Reactive/Clients/IObservableOrganizationActionsClient.cs +++ b/Octokit.Reactive/Clients/IObservableOrganizationActionsClient.cs @@ -8,7 +8,7 @@ namespace Octokit.Reactive /// A client for GitHub's Org Actions API. /// /// - /// See the Actions API documentation for more information. + /// See the Actions API documentation for more information. /// public interface IObservableOrganizationActionsClient { @@ -16,7 +16,7 @@ public interface IObservableOrganizationActionsClient /// Returns a client to manage organization secrets. /// /// - /// See the Secrets API documentation for more information. + /// See the Secrets API documentation for more information. /// IObservableOrganizationSecretsClient Secrets { get; } } From 49d8626a47f05a8db75b407996f94a196b59853b Mon Sep 17 00:00:00 2001 From: Thomas Hughes Date: Wed, 12 Aug 2020 10:15:44 -0500 Subject: [PATCH 37/56] Update doc links to new docs site --- .../IObservableOrganizationSecretsClient.cs | 20 +++++++++---------- 1 file changed, 10 insertions(+), 10 deletions(-) diff --git a/Octokit.Reactive/Clients/IObservableOrganizationSecretsClient.cs b/Octokit.Reactive/Clients/IObservableOrganizationSecretsClient.cs index dbd1f70448..205dfeb229 100644 --- a/Octokit.Reactive/Clients/IObservableOrganizationSecretsClient.cs +++ b/Octokit.Reactive/Clients/IObservableOrganizationSecretsClient.cs @@ -7,7 +7,7 @@ namespace Octokit.Reactive /// A client for GitHub's Organization Secrets API. /// /// - /// See the Organization Secrets API documentation for more details. + /// See the Organization Secrets API documentation for more details. /// public interface IObservableOrganizationSecretsClient { @@ -15,7 +15,7 @@ public interface IObservableOrganizationSecretsClient /// Get the public signing key to encrypt secrets for an organization. /// /// - /// See the API documentation for more information. + /// See the API documentation for more information. /// /// The name of the organization /// Thrown when a general API error occurs. @@ -26,7 +26,7 @@ public interface IObservableOrganizationSecretsClient /// List the secrets for an organization. /// /// - /// See the API documentation for more information. + /// See the API documentation for more information. /// /// The name of the organization /// Thrown when a general API error occurs. @@ -37,7 +37,7 @@ public interface IObservableOrganizationSecretsClient /// Get a secret from an organization. /// /// - /// See the API documentation for more information. + /// See the API documentation for more information. /// /// The name of the organization /// The name of the secret @@ -49,7 +49,7 @@ public interface IObservableOrganizationSecretsClient /// Create or update a secret in an organization. /// /// - /// See the API documentation for more information. + /// See the API documentation for more information. /// /// The name of the organization /// The name of the secret @@ -62,7 +62,7 @@ public interface IObservableOrganizationSecretsClient /// Delete a secret in an organization. /// /// - /// See the API documentation for more information. + /// See the API documentation for more information. /// /// The name of the organization /// The name of the secret @@ -73,7 +73,7 @@ public interface IObservableOrganizationSecretsClient /// Get the list of selected sites that have access to a secret. /// /// - /// See the API documentation for more information. + /// See the API documentation for more information. /// /// The name of the organization /// The name of the secret @@ -84,7 +84,7 @@ public interface IObservableOrganizationSecretsClient /// Set the list of selected sites that have access to a secret. /// /// - /// See the API documentation for more information. + /// See the API documentation for more information. /// /// The name of the organization /// The name of the secret @@ -96,7 +96,7 @@ public interface IObservableOrganizationSecretsClient /// Add a selected site to the visibility list of a secret. /// /// - /// See the API documentation for more information. + /// See the API documentation for more information. /// /// The name of the organization /// The name of the secret @@ -108,7 +108,7 @@ public interface IObservableOrganizationSecretsClient /// ARemoved a selected site from the visibility list of a secret. /// /// - /// See the API documentation for more information. + /// See the API documentation for more information. /// /// The name of the organization /// The name of the secret From 398fb8f5a2cbe4562c7d542808b5a2be183e0853 Mon Sep 17 00:00:00 2001 From: Thomas Hughes Date: Wed, 12 Aug 2020 10:18:21 -0500 Subject: [PATCH 38/56] Update docs links to new docs site --- Octokit.Reactive/Clients/IObservableRepositoriesClient.cs | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/Octokit.Reactive/Clients/IObservableRepositoriesClient.cs b/Octokit.Reactive/Clients/IObservableRepositoriesClient.cs index f498586405..2fee574f04 100644 --- a/Octokit.Reactive/Clients/IObservableRepositoriesClient.cs +++ b/Octokit.Reactive/Clients/IObservableRepositoriesClient.cs @@ -177,7 +177,7 @@ public interface IObservableRepositoriesClient /// Access GitHub's Repository Actions API. /// /// - /// Refer to the API documentation for more information: https://developer.github.com/v3/actions/ + /// See the API documentation for more details. /// IObservableRepositoryActionsClient Actions { get; } From c88f02bc81978c4fb96a8b9a1e8398ca5fdb062e Mon Sep 17 00:00:00 2001 From: Thomas Hughes Date: Wed, 12 Aug 2020 10:19:46 -0500 Subject: [PATCH 39/56] Fix doc link to point to new docs site --- .../Clients/IObservableRepositoryActionsClient.cs | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/Octokit.Reactive/Clients/IObservableRepositoryActionsClient.cs b/Octokit.Reactive/Clients/IObservableRepositoryActionsClient.cs index 6ab28ec7ad..6f649e0ef4 100644 --- a/Octokit.Reactive/Clients/IObservableRepositoryActionsClient.cs +++ b/Octokit.Reactive/Clients/IObservableRepositoryActionsClient.cs @@ -8,7 +8,7 @@ namespace Octokit.Reactive /// A client for GitHub's Repository Actions API. /// /// - /// See the Repository Actions API documentation for more details. + /// See the Repository Actions API documentation for more details. /// public interface IObservableRepositoryActionsClient { @@ -16,7 +16,7 @@ public interface IObservableRepositoryActionsClient /// Client for GitHub's Repository Actions API /// /// - /// See the Deployments API documentation for more details + /// See the Deployments API documentation for more details /// IObservableRepositorySecretsClient Secrets { get; } } From f27d78c1b689ec7a9150db3c7faf91653d0112e5 Mon Sep 17 00:00:00 2001 From: Thomas Hughes Date: Wed, 12 Aug 2020 10:22:47 -0500 Subject: [PATCH 40/56] Update links to new docs site --- .../Clients/IObservableRepositorySecretsClient.cs | 10 +++++----- 1 file changed, 5 insertions(+), 5 deletions(-) diff --git a/Octokit.Reactive/Clients/IObservableRepositorySecretsClient.cs b/Octokit.Reactive/Clients/IObservableRepositorySecretsClient.cs index a073b7b0a9..0d346d0b31 100644 --- a/Octokit.Reactive/Clients/IObservableRepositorySecretsClient.cs +++ b/Octokit.Reactive/Clients/IObservableRepositorySecretsClient.cs @@ -17,7 +17,7 @@ public interface IObservableRepositorySecretsClient /// Get the public signing key to encrypt secrets for a repository. /// /// - /// See the API documentation for more information. + /// See the API documentation for more information. /// /// The owner of the repository /// The name of the repository @@ -29,7 +29,7 @@ public interface IObservableRepositorySecretsClient /// List the secrets for a repository. /// /// - /// See the API documentation for more information. + /// See the API documentation for more information. /// /// The owner of the repository /// The name of the repository @@ -41,7 +41,7 @@ public interface IObservableRepositorySecretsClient /// Get a secret from a repository. /// /// - /// See the API documentation for more information. + /// See the API documentation for more information. /// /// The owner of the repository /// The name of the repository @@ -54,7 +54,7 @@ public interface IObservableRepositorySecretsClient /// Create or update a secret in a repository. /// /// - /// See the API documentation for more information. + /// See the API documentation for more information. /// /// The owner of the repository /// The name of the repository @@ -68,7 +68,7 @@ public interface IObservableRepositorySecretsClient /// Delete a secret in a repository. /// /// - /// See the API documentation for more information. + /// See the API documentation for more information. /// /// The owner of the repository /// The name of the repository From 6c5e923aeb6b353a25ba309bf2a2268e8f6893f6 Mon Sep 17 00:00:00 2001 From: Thomas Hughes Date: Wed, 12 Aug 2020 10:24:23 -0500 Subject: [PATCH 41/56] Update doc links to new docs site --- .../Clients/ObservableOrganizationActionsClient.cs | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/Octokit.Reactive/Clients/ObservableOrganizationActionsClient.cs b/Octokit.Reactive/Clients/ObservableOrganizationActionsClient.cs index e17c84c53a..833a88514a 100644 --- a/Octokit.Reactive/Clients/ObservableOrganizationActionsClient.cs +++ b/Octokit.Reactive/Clients/ObservableOrganizationActionsClient.cs @@ -8,7 +8,7 @@ namespace Octokit.Reactive /// A client for GitHub's Org Actions API. /// /// - /// See the Actions API documentation for more information. + /// See the Actions API documentation for more information. /// public class ObservableOrganizationActionsClient : IObservableOrganizationActionsClient { @@ -33,7 +33,7 @@ public ObservableOrganizationActionsClient(IGitHubClient client) /// Returns a client to manage organization secrets. /// /// - /// See the Secrets API documentation for more information. + /// See the Secrets API documentation for more information. /// public IObservableOrganizationSecretsClient Secrets { get; private set; } } From 4c7a383a52dd6ad0da720b288d00b26d68e8eec8 Mon Sep 17 00:00:00 2001 From: Thomas Hughes Date: Wed, 12 Aug 2020 10:31:19 -0500 Subject: [PATCH 42/56] Update docs links --- .../ObservableOrganizationSecretsClient.cs | 20 +++++++++---------- 1 file changed, 10 insertions(+), 10 deletions(-) diff --git a/Octokit.Reactive/Clients/ObservableOrganizationSecretsClient.cs b/Octokit.Reactive/Clients/ObservableOrganizationSecretsClient.cs index 2ff755bb6f..d18febef65 100644 --- a/Octokit.Reactive/Clients/ObservableOrganizationSecretsClient.cs +++ b/Octokit.Reactive/Clients/ObservableOrganizationSecretsClient.cs @@ -8,7 +8,7 @@ namespace Octokit.Reactive /// A client for GitHub's Organization Secrets API. /// /// - /// See the Organization Secrets API documentation for more details. + /// See the Organization Secrets API documentation for more details. /// public class ObservableOrganizationSecretsClient : IObservableOrganizationSecretsClient { @@ -31,7 +31,7 @@ public ObservableOrganizationSecretsClient(IGitHubClient client) /// Get the public signing key to encrypt secrets for an organization. /// /// - /// See the API documentation for more information. + /// See the API documentation for more information. /// /// The name of the organization /// Thrown when a general API error occurs. @@ -47,7 +47,7 @@ public IObservable GetPublicKey(string org) /// List the secrets for an organization. /// /// - /// See the API documentation for more information. + /// See the API documentation for more information. /// /// The name of the organization /// Thrown when a general API error occurs. @@ -63,7 +63,7 @@ public IObservable GetAll(string org) /// Get a secret from an organization. /// /// - /// See the API documentation for more information. + /// See the API documentation for more information. /// /// The name of the organization /// The name of the secret @@ -81,7 +81,7 @@ public IObservable Get(string org, string secretName) /// Create or update a secret in an organization. /// /// - /// See the API documentation for more information. + /// See the API documentation for more information. /// /// The name of the organization /// The name of the secret @@ -103,7 +103,7 @@ public IObservable CreateOrUpdate(string org, string secretN /// Delete a secret in an organization. /// /// - /// See the API documentation for more information. + /// See the API documentation for more information. /// /// The name of the organization /// The name of the secret @@ -120,7 +120,7 @@ public IObservable Delete(string org, string secretName) /// Get the list of selected sites that have access to a secret. /// /// - /// See the API documentation for more information. + /// See the API documentation for more information. /// /// The name of the organization /// The name of the secret @@ -137,7 +137,7 @@ public IObservable GetSelectedRepositori /// Set the list of selected sites that have access to a secret. /// /// - /// See the API documentation for more information. + /// See the API documentation for more information. /// /// The name of the organization /// The name of the secret @@ -156,7 +156,7 @@ public IObservable SetSelectedRepositoriesForSecret(string org, string sec /// Add a selected site to the visibility list of a secret. /// /// - /// See the API documentation for more information. + /// See the API documentation for more information. /// /// The name of the organization /// The name of the secret @@ -175,7 +175,7 @@ public IObservable AddRepoToOrganizationSecret(string org, string secretNa /// ARemoved a selected site from the visibility list of a secret. /// /// - /// See the API documentation for more information. + /// See the API documentation for more information. /// /// The name of the organization /// The name of the secret From e7f04f84592b8a9991f649cb29b7d2b7224307c1 Mon Sep 17 00:00:00 2001 From: Thomas Hughes Date: Wed, 12 Aug 2020 10:33:26 -0500 Subject: [PATCH 43/56] Update docs --- Octokit.Reactive/Clients/ObservableRepositoriesClient.cs | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/Octokit.Reactive/Clients/ObservableRepositoriesClient.cs b/Octokit.Reactive/Clients/ObservableRepositoriesClient.cs index 01ac26f046..6927790d40 100644 --- a/Octokit.Reactive/Clients/ObservableRepositoriesClient.cs +++ b/Octokit.Reactive/Clients/ObservableRepositoriesClient.cs @@ -747,7 +747,7 @@ public IObservable Compare(string owner, string name, string @bas /// A client for GitHub's Repository Actions API. /// /// - /// See the Actions API documentation for more details + /// See the Actions API documentation for more details /// public IObservableRepositoryActionsClient Actions { get; private set; } From 67e4c6f242766011620a927e9cd84671cb07c22a Mon Sep 17 00:00:00 2001 From: Thomas Hughes Date: Wed, 12 Aug 2020 10:35:01 -0500 Subject: [PATCH 44/56] Update docs --- Octokit.Reactive/Clients/ObservableRepositoryActionsClient.cs | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/Octokit.Reactive/Clients/ObservableRepositoryActionsClient.cs b/Octokit.Reactive/Clients/ObservableRepositoryActionsClient.cs index a387a44d8b..631bbf4bf4 100644 --- a/Octokit.Reactive/Clients/ObservableRepositoryActionsClient.cs +++ b/Octokit.Reactive/Clients/ObservableRepositoryActionsClient.cs @@ -8,7 +8,7 @@ namespace Octokit.Reactive /// A client for GitHub's Repository Actions API. /// /// - /// See the Repository Actions API documentation for more details. + /// See the Repository Actions API documentation for more details. /// public class ObservableRepositoryActionsClient : IObservableRepositoryActionsClient { @@ -29,7 +29,7 @@ public ObservableRepositoryActionsClient(IGitHubClient client) /// Client for GitHub's Repository Actions API /// /// - /// See the Deployments API documentation for more details + /// See the Deployments API documentation for more details /// public IObservableRepositorySecretsClient Secrets { get; private set; } } From 4ca258f1ed3f55d7bf072e3b11a728468d6b5985 Mon Sep 17 00:00:00 2001 From: Thomas Hughes Date: Wed, 12 Aug 2020 10:38:21 -0500 Subject: [PATCH 45/56] Update doc links --- .../Clients/ObservableRepositorySecretsClient.cs | 12 ++++++------ 1 file changed, 6 insertions(+), 6 deletions(-) diff --git a/Octokit.Reactive/Clients/ObservableRepositorySecretsClient.cs b/Octokit.Reactive/Clients/ObservableRepositorySecretsClient.cs index f5f0be65d3..fa11987edf 100644 --- a/Octokit.Reactive/Clients/ObservableRepositorySecretsClient.cs +++ b/Octokit.Reactive/Clients/ObservableRepositorySecretsClient.cs @@ -11,7 +11,7 @@ namespace Octokit.Reactive /// A client for GitHub's Repository Secrets API. /// /// - /// See the Repository Secrets API documentation for more details. + /// See the Repository Secrets API documentation for more details. /// public class ObservableRepositorySecretsClient : IObservableRepositorySecretsClient { @@ -30,7 +30,7 @@ public ObservableRepositorySecretsClient(IGitHubClient client) /// Get the public signing key to encrypt secrets for a repository. /// /// - /// See the API documentation for more information. + /// See the API documentation for more information. /// /// The owner of the repository /// The name of the repository @@ -48,7 +48,7 @@ public IObservable GetPublicKey(string owner, string repoName) /// List the secrets for a repository. /// /// - /// See the API documentation for more information. + /// See the API documentation for more information. /// /// The owner of the repository /// The name of the repository @@ -66,7 +66,7 @@ public IObservable GetAll(string owner, string repo /// Get a secret from a repository. /// /// - /// See the API documentation for more information. + /// See the API documentation for more information. /// /// The owner of the repository /// The name of the repository @@ -86,7 +86,7 @@ public IObservable Get(string owner, string repoName, string s /// Create or update a secret in a repository. /// /// - /// See the API documentation for more information. + /// See the API documentation for more information. /// /// The owner of the repository /// The name of the repository @@ -110,7 +110,7 @@ public IObservable CreateOrUpdate(string owner, string repoNam /// Delete a secret in a repository. /// /// - /// See the API documentation for more information. + /// See the API documentation for more information. /// /// The owner of the repository /// The name of the repository From 92c0e903b72f1d36b86aa9e1a1c055ed8252b32f Mon Sep 17 00:00:00 2001 From: Thomas Hughes Date: Wed, 12 Aug 2020 10:40:14 -0500 Subject: [PATCH 46/56] Update docs --- Octokit/Clients/IOrganizationActionsClient.cs | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/Octokit/Clients/IOrganizationActionsClient.cs b/Octokit/Clients/IOrganizationActionsClient.cs index 36c45acb5e..38dd3cd032 100644 --- a/Octokit/Clients/IOrganizationActionsClient.cs +++ b/Octokit/Clients/IOrganizationActionsClient.cs @@ -8,7 +8,7 @@ namespace Octokit /// A client for GitHub's Org Actions API. /// /// - /// See the Actions API documentation for more information. + /// See the Actions API documentation for more information. /// public interface IOrganizationActionsClient { @@ -16,7 +16,7 @@ public interface IOrganizationActionsClient /// Returns a client to manage organization secrets. /// /// - /// See the Secrets API documentation for more information. + /// See the Secrets API documentation for more information. /// IOrganizationSecretsClient Secrets { get; } } From e36ffa060fad33e0f8b60149b3b22612afae88bb Mon Sep 17 00:00:00 2001 From: Thomas Hughes Date: Wed, 12 Aug 2020 10:43:35 -0500 Subject: [PATCH 47/56] Update doc links --- Octokit/Clients/IOrganizationSecretsClient.cs | 20 +++++++++---------- 1 file changed, 10 insertions(+), 10 deletions(-) diff --git a/Octokit/Clients/IOrganizationSecretsClient.cs b/Octokit/Clients/IOrganizationSecretsClient.cs index 082d61a306..7966ea9a63 100644 --- a/Octokit/Clients/IOrganizationSecretsClient.cs +++ b/Octokit/Clients/IOrganizationSecretsClient.cs @@ -6,7 +6,7 @@ namespace Octokit /// A client for GitHub's Organization Secrets API. /// /// - /// See the Organization Secrets API documentation for more details. + /// See the Organization Secrets API documentation for more details. /// public interface IOrganizationSecretsClient { @@ -14,7 +14,7 @@ public interface IOrganizationSecretsClient /// Get the public signing key to encrypt secrets for an organization. /// /// - /// See the API documentation for more information. + /// See the API documentation for more information. /// /// The name of the organization /// Thrown when a general API error occurs. @@ -25,7 +25,7 @@ public interface IOrganizationSecretsClient /// List the secrets for an organization. /// /// - /// See the API documentation for more information. + /// See the API documentation for more information. /// /// The name of the organization /// Thrown when a general API error occurs. @@ -36,7 +36,7 @@ public interface IOrganizationSecretsClient /// Get a secret from an organization. /// /// - /// See the API documentation for more information. + /// See the API documentation for more information. /// /// The name of the organization /// The name of the secret @@ -48,7 +48,7 @@ public interface IOrganizationSecretsClient /// Create or update a secret in an organization. /// /// - /// See the API documentation for more information. + /// See the API documentation for more information. /// /// The name of the organization /// The name of the secret @@ -61,7 +61,7 @@ public interface IOrganizationSecretsClient /// Delete a secret in an organization. /// /// - /// See the API documentation for more information. + /// See the API documentation for more information. /// /// The name of the organization /// The name of the secret @@ -72,7 +72,7 @@ public interface IOrganizationSecretsClient /// Get the list of selected sites that have access to a secret. /// /// - /// See the API documentation for more information. + /// See the API documentation for more information. /// /// The name of the organization /// The name of the secret @@ -83,7 +83,7 @@ public interface IOrganizationSecretsClient /// Set the list of selected sites that have access to a secret. /// /// - /// See the API documentation for more information. + /// See the API documentation for more information. /// /// The name of the organization /// The name of the secret @@ -95,7 +95,7 @@ public interface IOrganizationSecretsClient /// Add a selected site to the visibility list of a secret. /// /// - /// See the API documentation for more information. + /// See the API documentation for more information. /// /// The name of the organization /// The name of the secret @@ -107,7 +107,7 @@ public interface IOrganizationSecretsClient /// ARemoved a selected site from the visibility list of a secret. /// /// - /// See the API documentation for more information. + /// See the API documentation for more information. /// /// The name of the organization /// The name of the secret From 5fc0be6e75dd2f870963fb555da4940cbb1e7541 Mon Sep 17 00:00:00 2001 From: Thomas Hughes Date: Wed, 12 Aug 2020 11:20:28 -0500 Subject: [PATCH 48/56] Update doc links --- Octokit/Clients/IRepositoriesClient.cs | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) diff --git a/Octokit/Clients/IRepositoriesClient.cs b/Octokit/Clients/IRepositoriesClient.cs index 5d1b0abc80..f1a62e4bee 100644 --- a/Octokit/Clients/IRepositoriesClient.cs +++ b/Octokit/Clients/IRepositoriesClient.cs @@ -9,7 +9,7 @@ namespace Octokit /// A client for GitHub's Repositories API. /// /// - /// See the Repositories API documentation for more details. + /// See the Repositories API documentation for more details. /// public interface IRepositoriesClient { @@ -17,7 +17,7 @@ public interface IRepositoriesClient /// Client for managing pull requests. /// /// - /// See the Pull Requests API documentation for more details + /// See the Pull Requests API documentation for more details /// IPullRequestsClient PullRequest { get; } @@ -25,7 +25,7 @@ public interface IRepositoriesClient /// Client for managing Actions in a repository. /// /// - /// See the Repository Actions API documentation for more information. + /// See the Repository Actions API documentation for more information. /// IRepositoryActionsClient Actions { get; } From fcf32ebf03901bd51f393fc0130c7bd46afdde79 Mon Sep 17 00:00:00 2001 From: Thomas Hughes Date: Wed, 12 Aug 2020 11:21:46 -0500 Subject: [PATCH 49/56] Update doc links --- Octokit/Clients/IRepositoryActionsClient.cs | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/Octokit/Clients/IRepositoryActionsClient.cs b/Octokit/Clients/IRepositoryActionsClient.cs index 0c095d3d3f..af0aabe896 100644 --- a/Octokit/Clients/IRepositoryActionsClient.cs +++ b/Octokit/Clients/IRepositoryActionsClient.cs @@ -8,7 +8,7 @@ namespace Octokit /// A client for GitHub's Repository Actions API. /// /// - /// See the Repository Actions API documentation for more details. + /// See the Repository Actions API documentation for more details. /// public interface IRepositoryActionsClient { @@ -16,7 +16,7 @@ public interface IRepositoryActionsClient /// Client for GitHub's Repository Actions API /// /// - /// See the Deployments API documentation for more details + /// See the Deployments API documentation for more details /// IRepositorySecretsClient Secrets { get; } } From 7a88f334aa30cbf99c6c22c037efed19c9c420be Mon Sep 17 00:00:00 2001 From: Mike Tolly Date: Wed, 12 Aug 2020 12:41:09 -0400 Subject: [PATCH 50/56] updated documentation links in actions and secrets clients --- Octokit/Clients/OrganizationActionsClient.cs | 4 ++-- Octokit/Clients/OrganizationSecretsClient.cs | 20 ++++++++++---------- Octokit/Clients/RepositoryActionsClient.cs | 4 ++-- Octokit/Clients/RepositorySecretsClient.cs | 10 +++++----- 4 files changed, 19 insertions(+), 19 deletions(-) diff --git a/Octokit/Clients/OrganizationActionsClient.cs b/Octokit/Clients/OrganizationActionsClient.cs index 7e8b514956..639c728a9b 100644 --- a/Octokit/Clients/OrganizationActionsClient.cs +++ b/Octokit/Clients/OrganizationActionsClient.cs @@ -8,7 +8,7 @@ namespace Octokit /// A client for GitHub's Org Actions API. /// /// - /// See the Actions API documentation for more information. + /// See the Actions API documentation for more information. /// public class OrganizationActionsClient : ApiClient, IOrganizationActionsClient { @@ -25,7 +25,7 @@ public OrganizationActionsClient(IApiConnection apiConnection) : base(apiConnect /// Returns a client to manage organization secrets. /// /// - /// See the Secrets API documentation for more information. + /// See the Secrets API documentation for more information. /// public IOrganizationSecretsClient Secrets { get; private set; } } diff --git a/Octokit/Clients/OrganizationSecretsClient.cs b/Octokit/Clients/OrganizationSecretsClient.cs index 2ccb91e802..fb126eb915 100644 --- a/Octokit/Clients/OrganizationSecretsClient.cs +++ b/Octokit/Clients/OrganizationSecretsClient.cs @@ -9,7 +9,7 @@ namespace Octokit /// A client for GitHub's Organization Secrets API. /// /// - /// See the Organization Secrets API documentation for more details. + /// See the Organization Secrets API documentation for more details. /// public class OrganizationSecretsClient : ApiClient, IOrganizationSecretsClient { @@ -19,7 +19,7 @@ public OrganizationSecretsClient(IApiConnection apiConnection) : base(apiConnect /// Get the public signing key to encrypt secrets for an organization. /// /// - /// See the API documentation for more information. + /// See the API documentation for more information. /// /// The name of the organization /// Thrown when a general API error occurs. @@ -36,7 +36,7 @@ public Task GetPublicKey(string org) /// List the secrets for an organization. /// /// - /// See the API documentation for more information. + /// See the API documentation for more information. /// /// The name of the organization /// Thrown when a general API error occurs. @@ -53,7 +53,7 @@ public Task GetAll(string org) /// Get a secret from an organization. /// /// - /// See the API documentation for more information. + /// See the API documentation for more information. /// /// The name of the organization /// The name of the secret @@ -72,7 +72,7 @@ public Task Get(string org, string secretName) /// Create or update a secret in an organization. /// /// - /// See the API documentation for more information. + /// See the API documentation for more information. /// /// The name of the organization /// The name of the secret @@ -97,7 +97,7 @@ public async Task CreateOrUpdate(string org, string secretNa /// Delete a secret in an organization. /// /// - /// See the API documentation for more information. + /// See the API documentation for more information. /// /// The name of the organization /// The name of the secret @@ -115,7 +115,7 @@ public Task Delete(string org, string secretName) /// Get the list of selected sites that have access to a secret. /// /// - /// See the API documentation for more information. + /// See the API documentation for more information. /// /// The name of the organization /// The name of the secret @@ -133,7 +133,7 @@ public Task GetSelectedRepositoriesForSe /// Set the list of selected sites that have access to a secret. /// /// - /// See the API documentation for more information. + /// See the API documentation for more information. /// /// The name of the organization /// The name of the secret @@ -155,7 +155,7 @@ public async Task SetSelectedRepositoriesForSecret(string org, string secretName /// Add a selected site to the visibility list of a secret. /// /// - /// See the API documentation for more information. + /// See the API documentation for more information. /// /// The name of the organization /// The name of the secret @@ -175,7 +175,7 @@ public Task AddRepoToOrganizationSecret(string org, string secretName, long repo /// ARemoved a selected site from the visibility list of a secret. /// /// - /// See the API documentation for more information. + /// See the API documentation for more information. /// /// The name of the organization /// The name of the secret diff --git a/Octokit/Clients/RepositoryActionsClient.cs b/Octokit/Clients/RepositoryActionsClient.cs index 72dab366e2..9837448eba 100644 --- a/Octokit/Clients/RepositoryActionsClient.cs +++ b/Octokit/Clients/RepositoryActionsClient.cs @@ -8,7 +8,7 @@ namespace Octokit /// A client for GitHub's Repository Actions API. /// /// - /// See the Repository Actions API documentation for more details. + /// See the Repository Actions API documentation for more details. /// public class RepositoryActionsClient : ApiClient, IRepositoryActionsClient { @@ -25,7 +25,7 @@ public RepositoryActionsClient(IApiConnection apiConnection) : base(apiConnectio /// Client for GitHub's Repository Actions API /// /// - /// See the Deployments API documentation for more details + /// See the Deployments API documentation for more details /// public IRepositorySecretsClient Secrets { get; set; } } diff --git a/Octokit/Clients/RepositorySecretsClient.cs b/Octokit/Clients/RepositorySecretsClient.cs index aa87e7b98f..7810955bd1 100644 --- a/Octokit/Clients/RepositorySecretsClient.cs +++ b/Octokit/Clients/RepositorySecretsClient.cs @@ -19,7 +19,7 @@ public RepositorySecretsClient(IApiConnection apiConnection) : base(apiConnectio /// Get the public signing key to encrypt secrets for a repository. /// /// - /// See the API documentation for more information. + /// See the API documentation for more information. /// /// The owner of the repository /// The name of the repository @@ -40,7 +40,7 @@ public Task GetPublicKey(string owner, string repoName) /// List the secrets for a repository. /// /// - /// See the API documentation for more information. + /// See the API documentation for more information. /// /// The owner of the repository /// The name of the repository @@ -61,7 +61,7 @@ public Task GetAll(string owner, string repoName) /// Get a secret from a repository. /// /// - /// See the API documentation for more information. + /// See the API documentation for more information. /// /// The owner of the repository /// The name of the repository @@ -84,7 +84,7 @@ public Task Get(string owner, string repoName, string secretNa /// Create or update a secret in a repository. /// /// - /// See the API documentation for more information. + /// See the API documentation for more information. /// /// The owner of the repository /// The name of the repository @@ -113,7 +113,7 @@ public async Task CreateOrUpdate(string owner, string repoName /// Delete a secret in a repository. /// /// - /// See the API documentation for more information. + /// See the API documentation for more information. /// /// The owner of the repository /// The name of the repository From 3dc3b206902ce9c4bf992e4e292f8025e64f316b Mon Sep 17 00:00:00 2001 From: mptolly-takeda <61791994+mptolly-takeda@users.noreply.github.com> Date: Wed, 12 Aug 2020 15:43:05 -0700 Subject: [PATCH 51/56] Update Octokit/Models/Response/SecretsPublicKey.cs Removing line for consistency. Co-authored-by: Thomas Hughes --- Octokit/Models/Response/SecretsPublicKey.cs | 1 - 1 file changed, 1 deletion(-) diff --git a/Octokit/Models/Response/SecretsPublicKey.cs b/Octokit/Models/Response/SecretsPublicKey.cs index aedd40a9d8..361a68becc 100644 --- a/Octokit/Models/Response/SecretsPublicKey.cs +++ b/Octokit/Models/Response/SecretsPublicKey.cs @@ -11,7 +11,6 @@ public class SecretsPublicKey { public SecretsPublicKey() { - } public SecretsPublicKey(string keyId, string key) From 3797ee91ed25b082bc649ac926b078a9ad8dff6c Mon Sep 17 00:00:00 2001 From: mptolly-takeda <61791994+mptolly-takeda@users.noreply.github.com> Date: Wed, 12 Aug 2020 15:43:22 -0700 Subject: [PATCH 52/56] Update Octokit/Models/Response/RepositorySecret.cs Removing line for consistency. Co-authored-by: Thomas Hughes --- Octokit/Models/Response/RepositorySecret.cs | 1 - 1 file changed, 1 deletion(-) diff --git a/Octokit/Models/Response/RepositorySecret.cs b/Octokit/Models/Response/RepositorySecret.cs index a0a8a639c5..f2559a2311 100644 --- a/Octokit/Models/Response/RepositorySecret.cs +++ b/Octokit/Models/Response/RepositorySecret.cs @@ -14,7 +14,6 @@ public class RepositorySecret { public RepositorySecret() { - } public RepositorySecret(string name, DateTimeOffset createdAt, DateTimeOffset? updatedAt) From f02cfb03ee04fef39e849028c2a1b415c89577e0 Mon Sep 17 00:00:00 2001 From: Mike Tolly Date: Mon, 26 Oct 2020 09:38:22 -0400 Subject: [PATCH 53/56] set default owner and repo --- .../Clients/RespositorySecretsClientTests.cs | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/Octokit.Tests.Integration/Clients/RespositorySecretsClientTests.cs b/Octokit.Tests.Integration/Clients/RespositorySecretsClientTests.cs index 1bf3e0767a..e56c2d6cc2 100644 --- a/Octokit.Tests.Integration/Clients/RespositorySecretsClientTests.cs +++ b/Octokit.Tests.Integration/Clients/RespositorySecretsClientTests.cs @@ -22,8 +22,8 @@ public class RespositorySecretsClientTests /// /// Fill these in for tests to work /// - internal const string OWNER = ""; - internal const string REPO = ""; + internal const string OWNER = "octokit"; + internal const string REPO = "octokit.net"; public class GetPublicKeyMethod { From 060a4d0670dbb4c1bfe9d3afd992b644091ce3c7 Mon Sep 17 00:00:00 2001 From: Mike Tolly Date: Mon, 26 Oct 2020 09:38:54 -0400 Subject: [PATCH 54/56] switched to using the Helper.Organization from a ORG constant set at the top of the file --- .../Clients/OrganizationSecretsClientTests.cs | 54 +++++++++---------- 1 file changed, 25 insertions(+), 29 deletions(-) diff --git a/Octokit.Tests.Integration/Clients/OrganizationSecretsClientTests.cs b/Octokit.Tests.Integration/Clients/OrganizationSecretsClientTests.cs index 7d570694ac..ab93991787 100644 --- a/Octokit.Tests.Integration/Clients/OrganizationSecretsClientTests.cs +++ b/Octokit.Tests.Integration/Clients/OrganizationSecretsClientTests.cs @@ -13,10 +13,6 @@ namespace Octokit.Tests.Integration.Clients { public class OrganizationSecretsClientTests { - /// - /// Fill these in for tests to work - /// - internal const string ORG = ""; public class GetPublicKeyMethod { @@ -25,7 +21,7 @@ public async Task GetPublicKey() { var github = Helper.GetAuthenticatedClient(); - var key = await github.Organization.Actions.Secrets.GetPublicKey(ORG); + var key = await github.Organization.Actions.Secrets.GetPublicKey(Helper.Organization); Assert.True(!string.IsNullOrWhiteSpace(key.KeyId)); } @@ -38,7 +34,7 @@ public async Task GetSecrets() { var github = Helper.GetAuthenticatedClient(); - var secrets = await github.Organization.Actions.Secrets.GetAll(ORG); + var secrets = await github.Organization.Actions.Secrets.GetAll(Helper.Organization); Assert.NotEmpty(secrets.Secrets); } @@ -54,7 +50,7 @@ public async Task GetSecret() { var github = Helper.GetAuthenticatedClient(); - var secret = await github.Organization.Actions.Secrets.Get(ORG, "TEST"); + var secret = await github.Organization.Actions.Secrets.Get(Helper.Organization, "TEST"); Assert.NotNull(secret); Assert.True(secret.Name == "TEST"); @@ -70,10 +66,10 @@ public async Task UpsertSecret() var github = Helper.GetAuthenticatedClient(); var now = DateTime.Now; - var publicKey = await github.Organization.Actions.Secrets.GetPublicKey(ORG); + var publicKey = await github.Organization.Actions.Secrets.GetPublicKey(Helper.Organization); var upsertValue = GetSecretForCreate("value", publicKey); - var secret = await github.Organization.Actions.Secrets.CreateOrUpdate(ORG, "UPSERT_TEST", upsertValue); + var secret = await github.Organization.Actions.Secrets.CreateOrUpdate(Helper.Organization, "UPSERT_TEST", upsertValue); Assert.NotNull(secret); Assert.True(secret.UpdatedAt > now); @@ -91,11 +87,11 @@ public async Task DeleteSecret() var secretName = "DELETE_TEST"; - var publicKey = await github.Organization.Actions.Secrets.GetPublicKey(ORG); + var publicKey = await github.Organization.Actions.Secrets.GetPublicKey(Helper.Organization); var upsertValue = GetSecretForCreate("value", publicKey); - await github.Organization.Actions.Secrets.CreateOrUpdate(ORG, secretName, upsertValue); - await github.Organization.Actions.Secrets.Delete(ORG, secretName); + await github.Organization.Actions.Secrets.CreateOrUpdate(Helper.Organization, secretName, upsertValue); + await github.Organization.Actions.Secrets.Delete(Helper.Organization, secretName); } #endif @@ -113,11 +109,11 @@ public async Task GetSelectedRepositoriesForSecret() var repo = await CreateRepoIfNotExists(github, "list-secrets-selected-repo-test"); - var key = await github.Organization.Actions.Secrets.GetPublicKey(ORG); + var key = await github.Organization.Actions.Secrets.GetPublicKey(Helper.Organization); var upsertSecret = GetSecretForCreate("secret", key, new Repository[] { repo }); - var secret = await github.Organization.Actions.Secrets.CreateOrUpdate(ORG, secretName, upsertSecret); + var secret = await github.Organization.Actions.Secrets.CreateOrUpdate(Helper.Organization, secretName, upsertSecret); - var visibilityRepos = await github.Organization.Actions.Secrets.GetSelectedRepositoriesForSecret(ORG, secretName); + var visibilityRepos = await github.Organization.Actions.Secrets.GetSelectedRepositoriesForSecret(Helper.Organization, secretName); Assert.NotEmpty(visibilityRepos.Repositories); } @@ -137,13 +133,13 @@ public async Task SetSelectedRepositoriesForSecret() var repo1 = await CreateRepoIfNotExists(github, "set-secrets-selected-repo-test-1"); var repo2 = await CreateRepoIfNotExists(github, "set-secrets-selected-repo-test-2"); - var key = await github.Organization.Actions.Secrets.GetPublicKey(ORG); + var key = await github.Organization.Actions.Secrets.GetPublicKey(Helper.Organization); var upsertSecret = GetSecretForCreate("secret", key, new Repository[] { repo1 }); - await github.Organization.Actions.Secrets.CreateOrUpdate(ORG, secretName, upsertSecret); + await github.Organization.Actions.Secrets.CreateOrUpdate(Helper.Organization, secretName, upsertSecret); - await github.Organization.Actions.Secrets.SetSelectedRepositoriesForSecret(ORG, secretName, new SelectedRepositoryCollection(new long[] { repo1.Id, repo2.Id })); + await github.Organization.Actions.Secrets.SetSelectedRepositoriesForSecret(Helper.Organization, secretName, new SelectedRepositoryCollection(new long[] { repo1.Id, repo2.Id })); - var visibilityRepos = await github.Organization.Actions.Secrets.GetSelectedRepositoriesForSecret(ORG, secretName); + var visibilityRepos = await github.Organization.Actions.Secrets.GetSelectedRepositoriesForSecret(Helper.Organization, secretName); Assert.NotEmpty(visibilityRepos.Repositories); Assert.Equal(2, visibilityRepos.Count); @@ -164,13 +160,13 @@ public async Task AddSelectedRepositoriesForSecret() var repo1 = await CreateRepoIfNotExists(github, "add-secrets-selected-repo-test-1"); var repo2 = await CreateRepoIfNotExists(github, "add-secrets-selected-repo-test-2"); - var key = await github.Organization.Actions.Secrets.GetPublicKey(ORG); + var key = await github.Organization.Actions.Secrets.GetPublicKey(Helper.Organization); var upsertSecret = GetSecretForCreate("secret", key, new Repository[] { repo1 }); - await github.Organization.Actions.Secrets.CreateOrUpdate(ORG, secretName, upsertSecret); + await github.Organization.Actions.Secrets.CreateOrUpdate(Helper.Organization, secretName, upsertSecret); - await github.Organization.Actions.Secrets.AddRepoToOrganizationSecret(ORG, secretName, repo2.Id); + await github.Organization.Actions.Secrets.AddRepoToOrganizationSecret(Helper.Organization, secretName, repo2.Id); - var visibilityRepos = await github.Organization.Actions.Secrets.GetSelectedRepositoriesForSecret(ORG, secretName); + var visibilityRepos = await github.Organization.Actions.Secrets.GetSelectedRepositoriesForSecret(Helper.Organization, secretName); Assert.NotEmpty(visibilityRepos.Repositories); Assert.Equal(2, visibilityRepos.Count); @@ -191,13 +187,13 @@ public async Task RemoveSelectedRepositoriesForSecret() var repo1 = await CreateRepoIfNotExists(github, "remove-secrets-selected-repo-test-1"); var repo2 = await CreateRepoIfNotExists(github, "remove-secrets-selected-repo-test-2"); - var key = await github.Organization.Actions.Secrets.GetPublicKey(ORG); + var key = await github.Organization.Actions.Secrets.GetPublicKey(Helper.Organization); var upsertSecret = GetSecretForCreate("secret", key, new Repository[] { repo1, repo2 }); - await github.Organization.Actions.Secrets.CreateOrUpdate(ORG, secretName, upsertSecret); + await github.Organization.Actions.Secrets.CreateOrUpdate(Helper.Organization, secretName, upsertSecret); - await github.Organization.Actions.Secrets.RemoveRepoFromOrganizationSecret(ORG, secretName, repo2.Id); + await github.Organization.Actions.Secrets.RemoveRepoFromOrganizationSecret(Helper.Organization, secretName, repo2.Id); - var visibilityRepos = await github.Organization.Actions.Secrets.GetSelectedRepositoriesForSecret(ORG, secretName); + var visibilityRepos = await github.Organization.Actions.Secrets.GetSelectedRepositoriesForSecret(Helper.Organization, secretName); Assert.NotEmpty(visibilityRepos.Repositories); Assert.Equal(1, visibilityRepos.Count); @@ -246,12 +242,12 @@ private static async Task CreateRepoIfNotExists(IGitHubClient github { try { - var existingRepo = await github.Repository.Get(ORG, name); + var existingRepo = await github.Repository.Get(Helper.Organization, name); return existingRepo; } catch { - var newRepo = await github.Repository.Create(ORG, new NewRepository(name)); + var newRepo = await github.Repository.Create(Helper.Organization, new NewRepository(name)); return newRepo; } } From 163e538b4795620e845fa95414e0e2e23d5bbafc Mon Sep 17 00:00:00 2001 From: Mike Tolly Date: Tue, 27 Oct 2020 09:31:20 -0400 Subject: [PATCH 55/56] swapped out variable at top of file for the Helper.Organization property --- ...bservableOrganizationSecretsClientTests.cs | 55 +++++++++---------- 1 file changed, 25 insertions(+), 30 deletions(-) diff --git a/Octokit.Tests.Integration/Reactive/ObservableOrganizationSecretsClientTests.cs b/Octokit.Tests.Integration/Reactive/ObservableOrganizationSecretsClientTests.cs index 7d2423cb28..915f384a8f 100644 --- a/Octokit.Tests.Integration/Reactive/ObservableOrganizationSecretsClientTests.cs +++ b/Octokit.Tests.Integration/Reactive/ObservableOrganizationSecretsClientTests.cs @@ -15,11 +15,6 @@ namespace Octokit.Tests.Integration.Reactive { public class ObservableOrganizationSecretsClientTests { - /// - /// Fill these in for tests to work - /// - internal const string ORG = ""; - public class GetPublicKeyMethod { [OrganizationTest] @@ -28,7 +23,7 @@ public async Task GetPublicKey() var github = Helper.GetAuthenticatedClient(); var clients = new ObservableOrganizationSecretsClient(github); - var keyObservable = clients.GetPublicKey(ORG); + var keyObservable = clients.GetPublicKey(Helper.Organization); var key = await keyObservable; Assert.True(!string.IsNullOrWhiteSpace(key.KeyId)); @@ -43,7 +38,7 @@ public async Task GetSecrets() var github = Helper.GetAuthenticatedClient(); var clients = new ObservableOrganizationSecretsClient(github); - var secretsObservable = clients.GetAll(ORG); + var secretsObservable = clients.GetAll(Helper.Organization); var secrets = await secretsObservable; Assert.NotEmpty(secrets.Secrets); @@ -61,7 +56,7 @@ public async Task GetSecret() var github = Helper.GetAuthenticatedClient(); var clients = new ObservableOrganizationSecretsClient(github); - var secretObservable = clients.Get(ORG, "TEST"); + var secretObservable = clients.Get(Helper.Organization, "TEST"); var secret = await secretObservable; Assert.NotNull(secret); @@ -79,12 +74,12 @@ public async Task UpsertSecret() var clients = new ObservableOrganizationSecretsClient(github); var now = DateTime.Now; - var keyObservable = clients.GetPublicKey(ORG); + var keyObservable = clients.GetPublicKey(Helper.Organization); var key = await keyObservable; var upsertValue = GetSecretForCreate("value", key); - var secretObservable = clients.CreateOrUpdate(ORG, "REACTIVE_UPSERT_TEST", upsertValue); + var secretObservable = clients.CreateOrUpdate(Helper.Organization, "REACTIVE_UPSERT_TEST", upsertValue); var secret = await secretObservable; Assert.NotNull(secret); @@ -104,14 +99,14 @@ public async Task DeleteSecret() var secretName = "REACTIVE_DELETE_TEST"; - var keyObservable = clients.GetPublicKey(ORG); + var keyObservable = clients.GetPublicKey(Helper.Organization); var key = await keyObservable; var upsertValue = GetSecretForCreate("value", key); - var createSecretObservable = clients.CreateOrUpdate(ORG, secretName, upsertValue); + var createSecretObservable = clients.CreateOrUpdate(Helper.Organization, secretName, upsertValue); await createSecretObservable; - var deleteSecretObservable = clients.Delete(ORG, secretName); + var deleteSecretObservable = clients.Delete(Helper.Organization, secretName); await deleteSecretObservable; } #endif @@ -131,14 +126,14 @@ public async Task GetSelectedRepositoriesForSecret() var repo = await CreateRepoIfNotExists(repoClients, "reactive-list-secrets-selected-repo-test"); - var keyObservable = clients.GetPublicKey(ORG); + var keyObservable = clients.GetPublicKey(Helper.Organization); var key = await keyObservable; var upsertSecret = GetSecretForCreate("value", key, new Repository[] { repo }); - var secretObservable = clients.CreateOrUpdate(ORG, secretName, upsertSecret); + var secretObservable = clients.CreateOrUpdate(Helper.Organization, secretName, upsertSecret); await secretObservable; - var visibilityReposObservable = clients.GetSelectedRepositoriesForSecret(ORG, secretName); + var visibilityReposObservable = clients.GetSelectedRepositoriesForSecret(Helper.Organization, secretName); var visibilityRepos = await visibilityReposObservable; Assert.NotEmpty(visibilityRepos.Repositories); @@ -161,17 +156,17 @@ public async Task SetSelectedRepositoriesForSecret() var repo1 = await CreateRepoIfNotExists(repoClients, "reactive-set-secrets-selected-repo-test-1"); var repo2 = await CreateRepoIfNotExists(repoClients, "reactive-set-secrets-selected-repo-test-2"); - var keyObservable = clients.GetPublicKey(ORG); + var keyObservable = clients.GetPublicKey(Helper.Organization); var key = await keyObservable; var upsertSecret = GetSecretForCreate("value", key, new Repository[] { repo1 }); - var secretObservable = clients.CreateOrUpdate(ORG, secretName, upsertSecret); + var secretObservable = clients.CreateOrUpdate(Helper.Organization, secretName, upsertSecret); await secretObservable; - var setRepoListObservable = clients.SetSelectedRepositoriesForSecret(ORG, secretName, new SelectedRepositoryCollection(new long[] { repo1.Id, repo2.Id })); + var setRepoListObservable = clients.SetSelectedRepositoriesForSecret(Helper.Organization, secretName, new SelectedRepositoryCollection(new long[] { repo1.Id, repo2.Id })); await setRepoListObservable; - var visibilityReposObservable = clients.GetSelectedRepositoriesForSecret(ORG, secretName); + var visibilityReposObservable = clients.GetSelectedRepositoriesForSecret(Helper.Organization, secretName); var visibilityRepos = await visibilityReposObservable; Assert.NotEmpty(visibilityRepos.Repositories); @@ -195,17 +190,17 @@ public async Task AddSelectedRepositoriesForSecret() var repo1 = await CreateRepoIfNotExists(repoClients, "reactive-add-secrets-selected-repo-test-1"); var repo2 = await CreateRepoIfNotExists(repoClients, "reactive-add-secrets-selected-repo-test-2"); - var keyObservable = clients.GetPublicKey(ORG); + var keyObservable = clients.GetPublicKey(Helper.Organization); var key = await keyObservable; var upsertSecret = GetSecretForCreate("value", key, new Repository[] { repo1 }); - var secretObservable = clients.CreateOrUpdate(ORG, secretName, upsertSecret); + var secretObservable = clients.CreateOrUpdate(Helper.Organization, secretName, upsertSecret); await secretObservable; - var addRepoListObservable = clients.AddRepoToOrganizationSecret(ORG, secretName, repo2.Id); + var addRepoListObservable = clients.AddRepoToOrganizationSecret(Helper.Organization, secretName, repo2.Id); await addRepoListObservable; - var visibilityReposObservable = clients.GetSelectedRepositoriesForSecret(ORG, secretName); + var visibilityReposObservable = clients.GetSelectedRepositoriesForSecret(Helper.Organization, secretName); var visibilityRepos = await visibilityReposObservable; Assert.NotEmpty(visibilityRepos.Repositories); @@ -229,17 +224,17 @@ public async Task RemoveSelectedRepositoriesForSecret() var repo1 = await CreateRepoIfNotExists(repoClients, "reactive-remove-secrets-selected-repo-test-1"); var repo2 = await CreateRepoIfNotExists(repoClients, "reactive-remove-secrets-selected-repo-test-2"); - var keyObservable = clients.GetPublicKey(ORG); + var keyObservable = clients.GetPublicKey(Helper.Organization); var key = await keyObservable; var upsertSecret = GetSecretForCreate("secret", key, new Repository[] { repo1, repo2 }); - var secretObservable = clients.CreateOrUpdate(ORG, secretName, upsertSecret); + var secretObservable = clients.CreateOrUpdate(Helper.Organization, secretName, upsertSecret); await secretObservable; - var removeRepoListObservable = clients.RemoveRepoFromOrganizationSecret(ORG, secretName, repo2.Id); + var removeRepoListObservable = clients.RemoveRepoFromOrganizationSecret(Helper.Organization, secretName, repo2.Id); await removeRepoListObservable; - var visibilityReposObservable = clients.GetSelectedRepositoriesForSecret(ORG, secretName); + var visibilityReposObservable = clients.GetSelectedRepositoriesForSecret(Helper.Organization, secretName); var visibilityRepos = await visibilityReposObservable; Assert.NotEmpty(visibilityRepos.Repositories); @@ -289,12 +284,12 @@ private static async Task CreateRepoIfNotExists(ObservableRepositori { try { - var existingRepo = client.Get(ORG, name); + var existingRepo = client.Get(Helper.Organization, name); return await existingRepo; } catch { - var newRepo = client.Create(ORG, new NewRepository(name)); + var newRepo = client.Create(Helper.Organization, new NewRepository(name)); return await newRepo; } } From b69eba1fa32a7a7a171e84eea4550114f745a96d Mon Sep 17 00:00:00 2001 From: Mike Tolly Date: Tue, 27 Oct 2020 09:37:53 -0400 Subject: [PATCH 56/56] switched to helper method to create new repositories --- ...bservableOrganizationSecretsClientTests.cs | 57 ++++++++----------- 1 file changed, 25 insertions(+), 32 deletions(-) diff --git a/Octokit.Tests.Integration/Reactive/ObservableOrganizationSecretsClientTests.cs b/Octokit.Tests.Integration/Reactive/ObservableOrganizationSecretsClientTests.cs index 915f384a8f..9cdf668ba8 100644 --- a/Octokit.Tests.Integration/Reactive/ObservableOrganizationSecretsClientTests.cs +++ b/Octokit.Tests.Integration/Reactive/ObservableOrganizationSecretsClientTests.cs @@ -6,6 +6,7 @@ using Octokit.Reactive; using Xunit; using System.Linq; +using Octokit.Tests.Integration.Helpers; #if SODIUM_CORE_AVAILABLE using Sodium; @@ -120,15 +121,15 @@ public async Task GetSelectedRepositoriesForSecret() { var github = Helper.GetAuthenticatedClient(); var clients = new ObservableOrganizationSecretsClient(github); - var repoClients = new ObservableRepositoriesClient(github); var secretName = "REACTIVE_LIST_SELECTED_REPO_TEST"; - var repo = await CreateRepoIfNotExists(repoClients, "reactive-list-secrets-selected-repo-test"); + var repoName = Helper.MakeNameWithTimestamp("reactive-add-secrets-selected-repo-test"); + var repo = await github.CreateRepositoryContext(new NewRepository(repoName)); var keyObservable = clients.GetPublicKey(Helper.Organization); var key = await keyObservable; - var upsertSecret = GetSecretForCreate("value", key, new Repository[] { repo }); + var upsertSecret = GetSecretForCreate("value", key, new Repository[] { repo.Repository }); var secretObservable = clients.CreateOrUpdate(Helper.Organization, secretName, upsertSecret); await secretObservable; @@ -149,21 +150,23 @@ public async Task SetSelectedRepositoriesForSecret() { var github = Helper.GetAuthenticatedClient(); var clients = new ObservableOrganizationSecretsClient(github); - var repoClients = new ObservableRepositoriesClient(github); var secretName = "REACTIVE_SET_SELECTED_REPO_TEST"; - var repo1 = await CreateRepoIfNotExists(repoClients, "reactive-set-secrets-selected-repo-test-1"); - var repo2 = await CreateRepoIfNotExists(repoClients, "reactive-set-secrets-selected-repo-test-2"); + var repo1Name = Helper.MakeNameWithTimestamp("reactive-add-secrets-selected-repo-test-1"); + var repo2Name = Helper.MakeNameWithTimestamp("reactive-add-secrets-selected-repo-test-2"); + + var repo1 = await github.CreateRepositoryContext(new NewRepository(repo1Name)); + var repo2 = await github.CreateRepositoryContext(new NewRepository(repo2Name)); var keyObservable = clients.GetPublicKey(Helper.Organization); var key = await keyObservable; - var upsertSecret = GetSecretForCreate("value", key, new Repository[] { repo1 }); + var upsertSecret = GetSecretForCreate("value", key, new Repository[] { repo1.Repository }); var secretObservable = clients.CreateOrUpdate(Helper.Organization, secretName, upsertSecret); await secretObservable; - var setRepoListObservable = clients.SetSelectedRepositoriesForSecret(Helper.Organization, secretName, new SelectedRepositoryCollection(new long[] { repo1.Id, repo2.Id })); + var setRepoListObservable = clients.SetSelectedRepositoriesForSecret(Helper.Organization, secretName, new SelectedRepositoryCollection(new long[] { repo1.RepositoryId, repo2.RepositoryId })); await setRepoListObservable; var visibilityReposObservable = clients.GetSelectedRepositoriesForSecret(Helper.Organization, secretName); @@ -183,21 +186,23 @@ public async Task AddSelectedRepositoriesForSecret() { var github = Helper.GetAuthenticatedClient(); var clients = new ObservableOrganizationSecretsClient(github); - var repoClients = new ObservableRepositoriesClient(github); var secretName = "REACTIVE_ADD_SELECTED_REPO_TEST"; - var repo1 = await CreateRepoIfNotExists(repoClients, "reactive-add-secrets-selected-repo-test-1"); - var repo2 = await CreateRepoIfNotExists(repoClients, "reactive-add-secrets-selected-repo-test-2"); + var repo1Name = Helper.MakeNameWithTimestamp("reactive-add-secrets-selected-repo-test-1"); + var repo2Name = Helper.MakeNameWithTimestamp("reactive-add-secrets-selected-repo-test-2"); + + var repo1 = await github.CreateRepositoryContext(new NewRepository(repo1Name)); + var repo2 = await github.CreateRepositoryContext(new NewRepository(repo2Name)); var keyObservable = clients.GetPublicKey(Helper.Organization); var key = await keyObservable; - var upsertSecret = GetSecretForCreate("value", key, new Repository[] { repo1 }); + var upsertSecret = GetSecretForCreate("value", key, new Repository[] { repo1.Repository }); var secretObservable = clients.CreateOrUpdate(Helper.Organization, secretName, upsertSecret); await secretObservable; - var addRepoListObservable = clients.AddRepoToOrganizationSecret(Helper.Organization, secretName, repo2.Id); + var addRepoListObservable = clients.AddRepoToOrganizationSecret(Helper.Organization, secretName, repo2.RepositoryId); await addRepoListObservable; var visibilityReposObservable = clients.GetSelectedRepositoriesForSecret(Helper.Organization, secretName); @@ -217,21 +222,23 @@ public async Task RemoveSelectedRepositoriesForSecret() { var github = Helper.GetAuthenticatedClient(); var clients = new ObservableOrganizationSecretsClient(github); - var repoClients = new ObservableRepositoriesClient(github); var secretName = "REACTIVE_REMOVE_SELECTED_REPO_TEST"; - var repo1 = await CreateRepoIfNotExists(repoClients, "reactive-remove-secrets-selected-repo-test-1"); - var repo2 = await CreateRepoIfNotExists(repoClients, "reactive-remove-secrets-selected-repo-test-2"); + var repo1Name = Helper.MakeNameWithTimestamp("reactive-add-secrets-selected-repo-test-1"); + var repo2Name = Helper.MakeNameWithTimestamp("reactive-add-secrets-selected-repo-test-2"); + + var repo1 = await github.CreateRepositoryContext(new NewRepository(repo1Name)); + var repo2 = await github.CreateRepositoryContext(new NewRepository(repo2Name)); var keyObservable = clients.GetPublicKey(Helper.Organization); var key = await keyObservable; - var upsertSecret = GetSecretForCreate("secret", key, new Repository[] { repo1, repo2 }); + var upsertSecret = GetSecretForCreate("secret", key, new Repository[] { repo1.Repository, repo2.Repository }); var secretObservable = clients.CreateOrUpdate(Helper.Organization, secretName, upsertSecret); await secretObservable; - var removeRepoListObservable = clients.RemoveRepoFromOrganizationSecret(Helper.Organization, secretName, repo2.Id); + var removeRepoListObservable = clients.RemoveRepoFromOrganizationSecret(Helper.Organization, secretName, repo2.RepositoryId); await removeRepoListObservable; var visibilityReposObservable = clients.GetSelectedRepositoriesForSecret(Helper.Organization, secretName); @@ -279,19 +286,5 @@ private static UpsertOrganizationSecret GetSecretForCreate(string secretValue, S return upsertValue; } #endif - - private static async Task CreateRepoIfNotExists(ObservableRepositoriesClient client, string name) - { - try - { - var existingRepo = client.Get(Helper.Organization, name); - return await existingRepo; - } - catch - { - var newRepo = client.Create(Helper.Organization, new NewRepository(name)); - return await newRepo; - } - } } }