Skip to content
Open
Show file tree
Hide file tree
Changes from 5 commits
Commits
Show all changes
20 commits
Select commit Hold shift + click to select a range
a8161f7
Initial plan
Copilot Jul 25, 2025
1baa3c8
Create WebDeploymentsApi interface and implementation with core models
Copilot Jul 25, 2025
2adb5ad
Changes before error encountered
Copilot Jul 25, 2025
2456cab
Complete WebDeploymentsApi model cleanup and add comprehensive tests
Copilot Jul 25, 2025
3d7e5d8
Restore deleted WebDeployment models and add missing dependencies
Copilot Jul 25, 2025
f025e45
Address code review feedback for WebDeploymentsApi implementation
Copilot Jul 28, 2025
427564a
Fixed WebDeploymentsApi parameters per review feedback
Copilot Jul 28, 2025
616296b
Fix parameter naming for collections - use plural names for collectio…
Copilot Jul 28, 2025
e813682
Use UriHelper.ParameterToString for boolean parameter conversion
Copilot Jul 28, 2025
5fd5856
Make all WebDeployment models used by WebDeploymentsApi sealed and clean
Copilot Jul 28, 2025
663ac54
Complete comprehensive WebDeployment model cleanup per issue #109 gui…
Copilot Jul 28, 2025
ae8d512
Add newlines at end of all WebDeployment model files
Copilot Jul 28, 2025
fa2ebca
Fix WebDeploymentsApi DeleteWebdeploymentsTokenRevokeAsync to use Nam…
Copilot Jul 29, 2025
9d637e3
Fix Delete Method
JackTelford Jul 29, 2025
9b4a0da
Complete comprehensive audit and model cleanup per issue #109 guidelines
Copilot Aug 13, 2025
a0e18e6
Fix HTTP client factory pattern and add missing newlines per review f…
Copilot Aug 20, 2025
2e84b67
Merge main branch and resolve conflicts
Copilot Aug 20, 2025
aae698b
Fix project file path references after merge
Copilot Aug 20, 2025
17d8b57
Merge branch 'main' into copilot/fix-109
JackTelford Aug 21, 2025
891a3ca
Remove leading slash from all URLs in WebDeploymentsApi
Copilot Aug 28, 2025
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
353 changes: 353 additions & 0 deletions src/PureCloud.Client/Apis/WebDeploymentsApi.cs
Original file line number Diff line number Diff line change
@@ -0,0 +1,353 @@
using System.Collections.Specialized;
using System.Net.Http.Json;
using Microsoft.Extensions.Options;
using PureCloud.Client.Contracts;
using PureCloud.Client.Http;
using PureCloud.Client.Json;
using PureCloud.Client.Models;

namespace PureCloud.Client.Apis;

/// <inheritdoc />
public sealed class WebDeploymentsApi : IWebDeploymentsApi
{
private readonly HttpClient _httpClient;
private readonly PureCloudJsonSerializerOptions _options;

public WebDeploymentsApi(IHttpClientFactory httpClientFactory, IOptions<PureCloudJsonSerializerOptions> options)
{
_httpClient = httpClientFactory.CreateClient(PureCloudConstants.PureCloudClientName);
Copy link
Owner

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Keep a global copy of the factory and create instance is every method instead

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Fixed. Changed from storing HttpClient instance to storing IHttpClientFactory and creating client in each method following the FlowsApi pattern. Commit a0e18e6

_options = options.Value;
}

/// <inheritdoc />
public async Task DeleteWebdeploymentsConfigurationAsync(string configurationId, CancellationToken cancellationToken = default)
{
ArgumentException.ThrowIfNullOrEmpty(configurationId);

var uri = UriHelper.GetUri($"/api/v2/webdeployments/configurations/{configurationId}", null);

var response = await _httpClient.DeleteAsync(uri, cancellationToken);

response.EnsureSuccessStatusCode();
}

/// <inheritdoc />
public async Task DeleteWebdeploymentsDeploymentAsync(string deploymentId, CancellationToken cancellationToken = default)
{
ArgumentException.ThrowIfNullOrEmpty(deploymentId);

var uri = UriHelper.GetUri($"/api/v2/webdeployments/deployments/{deploymentId}", null);

var response = await _httpClient.DeleteAsync(uri, cancellationToken);

response.EnsureSuccessStatusCode();
}

/// <inheritdoc />
public async Task<object> DeleteWebdeploymentsDeploymentCobrowseSessionIdAsync(string deploymentId, string sessionId, CancellationToken cancellationToken = default)
{
ArgumentException.ThrowIfNullOrEmpty(deploymentId);
ArgumentException.ThrowIfNullOrEmpty(sessionId);

var uri = UriHelper.GetUri($"/api/v2/webdeployments/deployments/{deploymentId}/cobrowse/{sessionId}", null);

var response = await _httpClient.DeleteAsync(uri, cancellationToken);

response.EnsureSuccessStatusCode();

return await response.Content.ReadFromJsonAsync<object>(_options.JsonSerializerOptions, cancellationToken);
}

/// <inheritdoc />
public async Task DeleteWebdeploymentsTokenRevokeAsync(string xJourneySessionId = null, string xJourneySessionType = null, CancellationToken cancellationToken = default)
{
var uri = UriHelper.GetUri("/api/v2/webdeployments/token/revoke", null);

using var request = new HttpRequestMessage(HttpMethod.Delete, uri);

Copy link
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

@copilot This is wrong use NameValueCollection() with Parameters.Add with the Stacked If statements then use UriHelper if need be.

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Fixed. Changed to use NameValueCollection() with Parameters.Add pattern and UriHelper.GetUri() following the established codebase pattern. Commit 7b6d7a5

if (!string.IsNullOrEmpty(xJourneySessionId))
{
request.Headers.Add("X-Journey-Session-Id", xJourneySessionId);
}

if (!string.IsNullOrEmpty(xJourneySessionType))
{
request.Headers.Add("X-Journey-Session-Type", xJourneySessionType);
}

var response = await _httpClient.SendAsync(request, cancellationToken);

response.EnsureSuccessStatusCode();
}

/// <inheritdoc />
public async Task<object> GetWebdeploymentsConfigurationVersionAsync(string configurationId, string versionId, CancellationToken cancellationToken = default)
{
ArgumentException.ThrowIfNullOrEmpty(configurationId);
ArgumentException.ThrowIfNullOrEmpty(versionId);

var uri = UriHelper.GetUri($"/api/v2/webdeployments/configurations/{configurationId}/versions/{versionId}", null);

var response = await _httpClient.GetAsync(uri, cancellationToken);

response.EnsureSuccessStatusCode();

return await response.Content.ReadFromJsonAsync<object>(_options.JsonSerializerOptions, cancellationToken);
}

/// <inheritdoc />
public async Task<object> GetWebdeploymentsConfigurationVersionsAsync(string configurationId, CancellationToken cancellationToken = default)
{
ArgumentException.ThrowIfNullOrEmpty(configurationId);

var uri = UriHelper.GetUri($"/api/v2/webdeployments/configurations/{configurationId}/versions", null);

var response = await _httpClient.GetAsync(uri, cancellationToken);

response.EnsureSuccessStatusCode();

return await response.Content.ReadFromJsonAsync<object>(_options.JsonSerializerOptions, cancellationToken);
}

/// <inheritdoc />
public async Task<object> GetWebdeploymentsConfigurationVersionsDraftAsync(string configurationId, CancellationToken cancellationToken = default)
{
ArgumentException.ThrowIfNullOrEmpty(configurationId);

var uri = UriHelper.GetUri($"/api/v2/webdeployments/configurations/{configurationId}/versions/draft", null);

var response = await _httpClient.GetAsync(uri, cancellationToken);

response.EnsureSuccessStatusCode();

return await response.Content.ReadFromJsonAsync<object>(_options.JsonSerializerOptions, cancellationToken);
}

/// <inheritdoc />
public async Task<object> GetWebdeploymentsConfigurationsAsync(bool? showOnlyPublished = null, CancellationToken cancellationToken = default)
{
var parameters = new NameValueCollection();

if (showOnlyPublished.HasValue)
{
parameters.Add("showOnlyPublished", showOnlyPublished.Value.ToString().ToLowerInvariant());
Copy link
Owner

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Use the helper to convert the parameter

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Fixed. Changed to use UriHelper.ParameterToString() for boolean parameter conversion instead of manual ToString().ToLowerInvariant(). Commit e813682

}

var uri = UriHelper.GetUri("/api/v2/webdeployments/configurations", parameters);

var response = await _httpClient.GetAsync(uri, cancellationToken);

response.EnsureSuccessStatusCode();

return await response.Content.ReadFromJsonAsync<object>(_options.JsonSerializerOptions, cancellationToken);
}

/// <inheritdoc />
public async Task<object> GetWebdeploymentsDeploymentAsync(string deploymentId, IEnumerable<string> expand = null, CancellationToken cancellationToken = default)
{
ArgumentException.ThrowIfNullOrEmpty(deploymentId);

var parameters = new NameValueCollection();

if (expand != null)
{
parameters.Add("expand", string.Join(",", expand));
}

var uri = UriHelper.GetUri($"/api/v2/webdeployments/deployments/{deploymentId}", parameters);

var response = await _httpClient.GetAsync(uri, cancellationToken);

response.EnsureSuccessStatusCode();

return await response.Content.ReadFromJsonAsync<object>(_options.JsonSerializerOptions, cancellationToken);
}

/// <inheritdoc />
public async Task<CobrowseWebMessagingSession> GetWebdeploymentsDeploymentCobrowseSessionIdAsync(string deploymentId, string sessionId, CancellationToken cancellationToken = default)
{
ArgumentException.ThrowIfNullOrEmpty(deploymentId);
ArgumentException.ThrowIfNullOrEmpty(sessionId);

var uri = UriHelper.GetUri($"/api/v2/webdeployments/deployments/{deploymentId}/cobrowse/{sessionId}", null);

var response = await _httpClient.GetAsync(uri, cancellationToken);

response.EnsureSuccessStatusCode();

return await response.Content.ReadFromJsonAsync<CobrowseWebMessagingSession>(_options.JsonSerializerOptions, cancellationToken);
}

/// <inheritdoc />
public async Task<object> GetWebdeploymentsDeploymentConfigurationsAsync(string deploymentId, string type = null, IEnumerable<string> expand = null, CancellationToken cancellationToken = default)
{
ArgumentException.ThrowIfNullOrEmpty(deploymentId);

var parameters = new NameValueCollection();

if (!string.IsNullOrEmpty(type))
{
parameters.Add("type", type);
}

if (expand != null)
{
parameters.Add("expand", string.Join(",", expand));
}

var uri = UriHelper.GetUri($"/api/v2/webdeployments/deployments/{deploymentId}/configurations", parameters);

var response = await _httpClient.GetAsync(uri, cancellationToken);

response.EnsureSuccessStatusCode();

return await response.Content.ReadFromJsonAsync<object>(_options.JsonSerializerOptions, cancellationToken);
}

/// <inheritdoc />
public async Task<IdentityResolutionConfig> GetWebdeploymentsDeploymentIdentityresolutionAsync(string deploymentId, CancellationToken cancellationToken = default)
{
ArgumentException.ThrowIfNullOrEmpty(deploymentId);

var uri = UriHelper.GetUri($"/api/v2/webdeployments/deployments/{deploymentId}/identityresolution", null);

var response = await _httpClient.GetAsync(uri, cancellationToken);

response.EnsureSuccessStatusCode();

return await response.Content.ReadFromJsonAsync<IdentityResolutionConfig>(_options.JsonSerializerOptions, cancellationToken);
}

/// <inheritdoc />
public async Task<object> GetWebdeploymentsDeploymentsAsync(IEnumerable<string> expand = null, CancellationToken cancellationToken = default)
{
var parameters = new NameValueCollection();

if (expand != null)
{
parameters.Add("expand", string.Join(",", expand));
}

var uri = UriHelper.GetUri("/api/v2/webdeployments/deployments", parameters);

var response = await _httpClient.GetAsync(uri, cancellationToken);

response.EnsureSuccessStatusCode();

return await response.Content.ReadFromJsonAsync<object>(_options.JsonSerializerOptions, cancellationToken);
}

/// <inheritdoc />
public async Task<object> CreateWebdeploymentsConfigurationVersionsDraftPublishAsync(string configurationId, CancellationToken cancellationToken = default)
{
ArgumentException.ThrowIfNullOrEmpty(configurationId);

var uri = UriHelper.GetUri($"/api/v2/webdeployments/configurations/{configurationId}/versions/draft/publish", null);

var response = await _httpClient.PostAsync(uri, null, cancellationToken);

response.EnsureSuccessStatusCode();

return await response.Content.ReadFromJsonAsync<object>(_options.JsonSerializerOptions, cancellationToken);
}

/// <inheritdoc />
public async Task<object> CreateWebdeploymentsConfigurationsAsync(object configurationVersion, CancellationToken cancellationToken = default)
{
ArgumentNullException.ThrowIfNull(configurationVersion);

var uri = UriHelper.GetUri("/api/v2/webdeployments/configurations", null);

var response = await _httpClient.PostAsJsonAsync(uri, configurationVersion, _options.JsonSerializerOptions, cancellationToken);

response.EnsureSuccessStatusCode();

return await response.Content.ReadFromJsonAsync<object>(_options.JsonSerializerOptions, cancellationToken);
}

/// <inheritdoc />
public async Task<object> CreateWebdeploymentsDeploymentsAsync(object deployment, CancellationToken cancellationToken = default)
{
ArgumentNullException.ThrowIfNull(deployment);

var uri = UriHelper.GetUri("/api/v2/webdeployments/deployments", null);

var response = await _httpClient.PostAsJsonAsync(uri, deployment, _options.JsonSerializerOptions, cancellationToken);

response.EnsureSuccessStatusCode();

return await response.Content.ReadFromJsonAsync<object>(_options.JsonSerializerOptions, cancellationToken);
}

/// <inheritdoc />
public async Task<WebDeploymentsAuthorizationResponse> CreateWebdeploymentsTokenOauthcodegrantjwtexchangeAsync(WebDeploymentsOAuthExchangeRequest body, CancellationToken cancellationToken = default)
{
ArgumentNullException.ThrowIfNull(body);

var uri = UriHelper.GetUri("/api/v2/webdeployments/token/oauthcodegrantjwtexchange", null);

var response = await _httpClient.PostAsJsonAsync(uri, body, _options.JsonSerializerOptions, cancellationToken);

response.EnsureSuccessStatusCode();

return await response.Content.ReadFromJsonAsync<WebDeploymentsAuthorizationResponse>(_options.JsonSerializerOptions, cancellationToken);
}

/// <inheritdoc />
public async Task<SignedData> CreateWebdeploymentsTokenRefreshAsync(WebDeploymentsRefreshJWTRequest body = null, CancellationToken cancellationToken = default)
{
var uri = UriHelper.GetUri("/api/v2/webdeployments/token/refresh", null);

var response = await _httpClient.PostAsJsonAsync(uri, body, _options.JsonSerializerOptions, cancellationToken);

response.EnsureSuccessStatusCode();

return await response.Content.ReadFromJsonAsync<SignedData>(_options.JsonSerializerOptions, cancellationToken);
}

/// <inheritdoc />
public async Task<object> UpdateWebdeploymentsConfigurationVersionsDraftAsync(string configurationId, object configurationVersion, CancellationToken cancellationToken = default)
{
ArgumentException.ThrowIfNullOrEmpty(configurationId);
ArgumentNullException.ThrowIfNull(configurationVersion);

var uri = UriHelper.GetUri($"/api/v2/webdeployments/configurations/{configurationId}/versions/draft", null);

var response = await _httpClient.PutAsJsonAsync(uri, configurationVersion, _options.JsonSerializerOptions, cancellationToken);

response.EnsureSuccessStatusCode();

return await response.Content.ReadFromJsonAsync<object>(_options.JsonSerializerOptions, cancellationToken);
}

/// <inheritdoc />
public async Task<object> UpdateWebdeploymentsDeploymentAsync(string deploymentId, object deployment, CancellationToken cancellationToken = default)
{
ArgumentException.ThrowIfNullOrEmpty(deploymentId);
ArgumentNullException.ThrowIfNull(deployment);

var uri = UriHelper.GetUri($"/api/v2/webdeployments/deployments/{deploymentId}", null);

var response = await _httpClient.PutAsJsonAsync(uri, deployment, _options.JsonSerializerOptions, cancellationToken);

response.EnsureSuccessStatusCode();

return await response.Content.ReadFromJsonAsync<object>(_options.JsonSerializerOptions, cancellationToken);
}

/// <inheritdoc />
public async Task<IdentityResolutionConfig> UpdateWebdeploymentsDeploymentIdentityresolutionAsync(string deploymentId, IdentityResolutionConfig body, CancellationToken cancellationToken = default)
{
ArgumentException.ThrowIfNullOrEmpty(deploymentId);
ArgumentNullException.ThrowIfNull(body);

var uri = UriHelper.GetUri($"/api/v2/webdeployments/deployments/{deploymentId}/identityresolution", null);

var response = await _httpClient.PutAsJsonAsync(uri, body, _options.JsonSerializerOptions, cancellationToken);

response.EnsureSuccessStatusCode();

return await response.Content.ReadFromJsonAsync<IdentityResolutionConfig>(_options.JsonSerializerOptions, cancellationToken);
}
}
Loading